mirror of
https://github.com/Lime3DS/Lime3DS
synced 2024-12-27 09:32:30 -06:00
Merge pull request #3992 from Subv/applets_close
Services/HLE: Implement PrepareToCloseLibraryApplet and CloseLibraryApplet
This commit is contained in:
commit
04bd104c4a
6 changed files with 111 additions and 4 deletions
|
@ -396,6 +396,49 @@ ResultCode AppletManager::StartLibraryApplet(AppletId applet_id,
|
|||
}
|
||||
}
|
||||
|
||||
ResultCode AppletManager::PrepareToCloseLibraryApplet(bool not_pause, bool exiting,
|
||||
bool jump_home) {
|
||||
if (next_parameter) {
|
||||
return ResultCode(ErrCodes::ParameterPresent, ErrorModule::Applet,
|
||||
ErrorSummary::InvalidState, ErrorLevel::Status);
|
||||
}
|
||||
|
||||
if (!not_pause)
|
||||
library_applet_closing_command = SignalType::WakeupByPause;
|
||||
else if (jump_home)
|
||||
library_applet_closing_command = SignalType::WakeupToJumpHome;
|
||||
else if (exiting)
|
||||
library_applet_closing_command = SignalType::WakeupByCancel;
|
||||
else
|
||||
library_applet_closing_command = SignalType::WakeupByExit;
|
||||
|
||||
return RESULT_SUCCESS;
|
||||
}
|
||||
|
||||
ResultCode AppletManager::CloseLibraryApplet(Kernel::SharedPtr<Kernel::Object> object,
|
||||
std::vector<u8> buffer) {
|
||||
auto& slot = applet_slots[static_cast<size_t>(AppletSlot::LibraryApplet)];
|
||||
|
||||
MessageParameter param;
|
||||
// TODO(Subv): The destination id should be the "current applet slot id", which changes
|
||||
// constantly depending on what is going on in the system. Most of the time it is the running
|
||||
// application, but it could be something else if a system applet is launched.
|
||||
param.destination_id = AppletId::Application;
|
||||
param.sender_id = slot.applet_id;
|
||||
param.object = std::move(object);
|
||||
param.signal = library_applet_closing_command;
|
||||
param.buffer = std::move(buffer);
|
||||
|
||||
ResultCode result = SendParameter(param);
|
||||
|
||||
if (library_applet_closing_command != SignalType::WakeupByPause) {
|
||||
// TODO(Subv): Terminate the running applet title
|
||||
slot.Reset();
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
ResultVal<AppletManager::AppletInfo> AppletManager::GetAppletInfo(AppletId app_id) {
|
||||
const auto* slot = GetAppletSlotData(app_id);
|
||||
|
||||
|
|
|
@ -128,6 +128,8 @@ public:
|
|||
ResultCode FinishPreloadingLibraryApplet(AppletId applet_id);
|
||||
ResultCode StartLibraryApplet(AppletId applet_id, Kernel::SharedPtr<Kernel::Object> object,
|
||||
const std::vector<u8>& buffer);
|
||||
ResultCode PrepareToCloseLibraryApplet(bool not_pause, bool exiting, bool jump_home);
|
||||
ResultCode CloseLibraryApplet(Kernel::SharedPtr<Kernel::Object> object, std::vector<u8> buffer);
|
||||
|
||||
struct AppletInfo {
|
||||
u64 title_id;
|
||||
|
@ -164,6 +166,12 @@ private:
|
|||
AppletAttributes attributes;
|
||||
Kernel::SharedPtr<Kernel::Event> notification_event;
|
||||
Kernel::SharedPtr<Kernel::Event> parameter_event;
|
||||
|
||||
void Reset() {
|
||||
applet_id = AppletId::None;
|
||||
registered = false;
|
||||
attributes.raw = 0;
|
||||
}
|
||||
};
|
||||
|
||||
// Holds data about the concurrently running applets in the system.
|
||||
|
@ -172,6 +180,9 @@ private:
|
|||
// This overload returns nullptr if no applet with the specified id has been started.
|
||||
AppletSlotData* GetAppletSlotData(AppletId id);
|
||||
AppletSlotData* GetAppletSlotData(AppletAttributes attributes);
|
||||
|
||||
// Command that will be sent to the application when a library applet calls CloseLibraryApplet.
|
||||
SignalType library_applet_closing_command;
|
||||
};
|
||||
|
||||
} // namespace APT
|
||||
|
|
|
@ -552,6 +552,31 @@ void Module::Interface::CancelLibraryApplet(Kernel::HLERequestContext& ctx) {
|
|||
LOG_WARNING(Service_APT, "(STUBBED) called exiting={}", exiting);
|
||||
}
|
||||
|
||||
void Module::Interface::PrepareToCloseLibraryApplet(Kernel::HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp(ctx, 0x25, 3, 0); // 0x002500C0
|
||||
bool not_pause = rp.Pop<bool>();
|
||||
bool exiting = rp.Pop<bool>();
|
||||
bool jump_to_home = rp.Pop<bool>();
|
||||
|
||||
LOG_DEBUG(Service_APT, "called not_pause={} exiting={} jump_to_home={}", not_pause, exiting,
|
||||
jump_to_home);
|
||||
|
||||
IPC::RequestBuilder rb = rp.MakeBuilder(1, 0);
|
||||
rb.Push(apt->applet_manager->PrepareToCloseLibraryApplet(not_pause, exiting, jump_to_home));
|
||||
}
|
||||
|
||||
void Module::Interface::CloseLibraryApplet(Kernel::HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp(ctx, 0x28, 1, 4); // 0x00280044
|
||||
u32 parameter_size = rp.Pop<u32>();
|
||||
auto object = rp.PopGenericObject();
|
||||
std::vector<u8> buffer = rp.PopStaticBuffer();
|
||||
|
||||
LOG_DEBUG(Service_APT, "called size={}", parameter_size);
|
||||
|
||||
IPC::RequestBuilder rb = rp.MakeBuilder(1, 0);
|
||||
rb.Push(apt->applet_manager->CloseLibraryApplet(std::move(object), std::move(buffer)));
|
||||
}
|
||||
|
||||
void Module::Interface::SendCaptureBufferInfo(Kernel::HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp(ctx, 0x40, 1, 2); // 0x00400042
|
||||
u32 size = rp.Pop<u32>();
|
||||
|
|
|
@ -420,6 +420,34 @@ public:
|
|||
*/
|
||||
void CancelLibraryApplet(Kernel::HLERequestContext& ctx);
|
||||
|
||||
/**
|
||||
* APT::PrepareToCloseLibraryApplet service function
|
||||
* Inputs:
|
||||
* 0 : Command header [0x002500C0]
|
||||
* 1 : bool, Not pause
|
||||
* 2 : bool, Caller exiting
|
||||
* 3 : bool, Jump to home
|
||||
* Outputs:
|
||||
* 0 : Header code
|
||||
* 1 : Result code
|
||||
*/
|
||||
void PrepareToCloseLibraryApplet(Kernel::HLERequestContext& ctx);
|
||||
|
||||
/**
|
||||
* APT::CloseLibraryApplet service function
|
||||
* Inputs:
|
||||
* 0 : Command header [0x00280044]
|
||||
* 1 : Buffer size
|
||||
* 2 : 0x0
|
||||
* 3 : Object handle
|
||||
* 4 : (Size << 14) | 2
|
||||
* 5 : Input buffer virtual address
|
||||
* Outputs:
|
||||
* 0 : Header code
|
||||
* 1 : Result code
|
||||
*/
|
||||
void CloseLibraryApplet(Kernel::HLERequestContext& ctx);
|
||||
|
||||
/**
|
||||
* APT::SendCaptureBufferInfo service function
|
||||
* Inputs:
|
||||
|
|
|
@ -46,10 +46,10 @@ APT_A::APT_A(std::shared_ptr<Module> apt)
|
|||
{0x00220040, nullptr, "PrepareToCloseApplication"},
|
||||
{0x00230040, nullptr, "PrepareToJumpToApplication"},
|
||||
{0x00240044, nullptr, "JumpToApplication"},
|
||||
{0x002500C0, nullptr, "PrepareToCloseLibraryApplet"},
|
||||
{0x002500C0, &APT_A::PrepareToCloseLibraryApplet, "PrepareToCloseLibraryApplet"},
|
||||
{0x00260000, nullptr, "PrepareToCloseSystemApplet"},
|
||||
{0x00270044, nullptr, "CloseApplication"},
|
||||
{0x00280044, nullptr, "CloseLibraryApplet"},
|
||||
{0x00280044, &APT_A::CloseLibraryApplet, "CloseLibraryApplet"},
|
||||
{0x00290044, nullptr, "CloseSystemApplet"},
|
||||
{0x002A0000, nullptr, "OrderToCloseSystemApplet"},
|
||||
{0x002B0000, nullptr, "PrepareToJumpToHomeMenu"},
|
||||
|
|
|
@ -46,10 +46,10 @@ APT_U::APT_U(std::shared_ptr<Module> apt)
|
|||
{0x00220040, nullptr, "PrepareToCloseApplication"},
|
||||
{0x00230040, nullptr, "PrepareToJumpToApplication"},
|
||||
{0x00240044, nullptr, "JumpToApplication"},
|
||||
{0x002500C0, nullptr, "PrepareToCloseLibraryApplet"},
|
||||
{0x002500C0, &APT_U::PrepareToCloseLibraryApplet, "PrepareToCloseLibraryApplet"},
|
||||
{0x00260000, nullptr, "PrepareToCloseSystemApplet"},
|
||||
{0x00270044, nullptr, "CloseApplication"},
|
||||
{0x00280044, nullptr, "CloseLibraryApplet"},
|
||||
{0x00280044, &APT_U::CloseLibraryApplet, "CloseLibraryApplet"},
|
||||
{0x00290044, nullptr, "CloseSystemApplet"},
|
||||
{0x002A0000, nullptr, "OrderToCloseSystemApplet"},
|
||||
{0x002B0000, nullptr, "PrepareToJumpToHomeMenu"},
|
||||
|
|
Loading…
Reference in a new issue