summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Subv2017-09-23 13:59:07 -0500
committerGravatar Subv2017-09-24 08:59:30 -0500
commitb57d58c0dc94857d28a3ef197d9656f0fbad8e08 (patch)
treeee63fba3ff78cc6dc35d2eb280dd84858fabf043
parentMerge pull request #2928 from huwpascoe/master (diff)
downloadyuzu-b57d58c0dc94857d28a3ef197d9656f0fbad8e08.tar.gz
yuzu-b57d58c0dc94857d28a3ef197d9656f0fbad8e08.tar.xz
yuzu-b57d58c0dc94857d28a3ef197d9656f0fbad8e08.zip
HLE/APT: Prepare the APT Wakeup parameter when the game calls Initialize
We need to know what is being run so we can set the APT parameter destination AppId correctly. Delaying the preparation of the parameter until we know which AppId is running lets us support booting both the Home Menu and normal game Applications.
-rw-r--r--src/core/hle/service/apt/apt.cpp25
1 files changed, 19 insertions, 6 deletions
diff --git a/src/core/hle/service/apt/apt.cpp b/src/core/hle/service/apt/apt.cpp
index 8c0ba73f2..ea964bab1 100644
--- a/src/core/hle/service/apt/apt.cpp
+++ b/src/core/hle/service/apt/apt.cpp
@@ -65,6 +65,7 @@ union AppletAttributes {
65 u32 raw; 65 u32 raw;
66 66
67 BitField<0, 3, u32> applet_pos; 67 BitField<0, 3, u32> applet_pos;
68 BitField<29, 1, u32> is_home_menu;
68 69
69 AppletAttributes() : raw(0) {} 70 AppletAttributes() : raw(0) {}
70 AppletAttributes(u32 attributes) : raw(attributes) {} 71 AppletAttributes(u32 attributes) : raw(attributes) {}
@@ -158,6 +159,11 @@ static AppletSlotData* GetAppletSlotData(AppletAttributes attributes) {
158 if (slot == AppletSlot::Error) 159 if (slot == AppletSlot::Error)
159 return nullptr; 160 return nullptr;
160 161
162 // The Home Menu is a system applet, however, it has its own applet slot so that it can run
163 // concurrently with other system applets.
164 if (slot == AppletSlot::SystemApplet && attributes.is_home_menu)
165 return &applet_slots[static_cast<size_t>(AppletSlot::HomeMenu)];
166
161 return &applet_slots[static_cast<size_t>(slot)]; 167 return &applet_slots[static_cast<size_t>(slot)];
162} 168}
163 169
@@ -197,6 +203,19 @@ void Initialize(Service::Interface* self) {
197 rb.Push(RESULT_SUCCESS); 203 rb.Push(RESULT_SUCCESS);
198 rb.PushCopyHandles(Kernel::g_handle_table.Create(slot_data->notification_event).Unwrap(), 204 rb.PushCopyHandles(Kernel::g_handle_table.Create(slot_data->notification_event).Unwrap(),
199 Kernel::g_handle_table.Create(slot_data->parameter_event).Unwrap()); 205 Kernel::g_handle_table.Create(slot_data->parameter_event).Unwrap());
206
207 if (slot_data->applet_id == AppletId::Application ||
208 slot_data->applet_id == AppletId::HomeMenu) {
209 // Initialize the APT parameter to wake up the application.
210 next_parameter.emplace();
211 next_parameter->signal = static_cast<u32>(SignalType::Wakeup);
212 next_parameter->sender_id = static_cast<u32>(AppletId::None);
213 next_parameter->destination_id = app_id;
214 // Not signaling the parameter event will cause the application (or Home Menu) to hang
215 // during startup. In the real console, it is usually the Kernel and Home Menu who cause NS
216 // to signal the HomeMenu and Application parameter events, respectively.
217 slot_data->parameter_event->Signal();
218 }
200} 219}
201 220
202static u32 DecompressLZ11(const u8* in, u8* out) { 221static u32 DecompressLZ11(const u8* in, u8* out) {
@@ -1041,12 +1060,6 @@ void Init() {
1041 slot_data.parameter_event = 1060 slot_data.parameter_event =
1042 Kernel::Event::Create(Kernel::ResetType::OneShot, "APT:Parameter"); 1061 Kernel::Event::Create(Kernel::ResetType::OneShot, "APT:Parameter");
1043 } 1062 }
1044
1045 // Initialize the parameter to wake up the application.
1046 next_parameter.emplace();
1047 next_parameter->signal = static_cast<u32>(SignalType::Wakeup);
1048 next_parameter->destination_id = static_cast<u32>(AppletId::Application);
1049 applet_slots[static_cast<size_t>(AppletSlot::Application)].parameter_event->Signal();
1050} 1063}
1051 1064
1052void Shutdown() { 1065void Shutdown() {