diff options
Diffstat (limited to 'src/core/hle/service')
-rw-r--r-- | src/core/hle/service/nfp/nfp.cpp | 2 | ||||
-rw-r--r-- | src/core/hle/service/service.cpp | 4 | ||||
-rw-r--r-- | src/core/hle/service/sm/controller.cpp | 5 | ||||
-rw-r--r-- | src/core/hle/service/sm/sm.cpp | 33 | ||||
-rw-r--r-- | src/core/hle/service/sm/sm.h | 6 |
5 files changed, 28 insertions, 22 deletions
diff --git a/src/core/hle/service/nfp/nfp.cpp b/src/core/hle/service/nfp/nfp.cpp index ec0367978..4b79eb81d 100644 --- a/src/core/hle/service/nfp/nfp.cpp +++ b/src/core/hle/service/nfp/nfp.cpp @@ -189,7 +189,7 @@ private: LOG_DEBUG(Service_NFP, "called"); auto nfc_event = nfp_interface.GetNFCEvent(); - if (!nfc_event->ShouldWait(Kernel::GetCurrentThread()) && !has_attached_handle) { + if (!nfc_event->ShouldWait(&ctx.GetThread()) && !has_attached_handle) { device_state = DeviceState::TagFound; nfc_event->Clear(); } diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index 5698f429f..fa5347af9 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -186,7 +186,7 @@ ResultCode ServiceFrameworkBase::HandleSyncRequest(Kernel::HLERequestContext& co UNIMPLEMENTED_MSG("command_type={}", static_cast<int>(context.GetCommandType())); } - context.WriteToOutgoingCommandBuffer(*Kernel::GetCurrentThread()); + context.WriteToOutgoingCommandBuffer(context.GetThread()); return RESULT_SUCCESS; } @@ -201,7 +201,7 @@ void Init(std::shared_ptr<SM::ServiceManager>& sm, Core::System& system) { auto nv_flinger = std::make_shared<NVFlinger::NVFlinger>(system); system.GetFileSystemController().CreateFactories(*system.GetFilesystem(), false); - SM::ServiceManager::InstallInterfaces(sm); + SM::ServiceManager::InstallInterfaces(sm, system.Kernel()); Account::InstallInterfaces(system); AM::InstallInterfaces(*sm, nv_flinger, system); diff --git a/src/core/hle/service/sm/controller.cpp b/src/core/hle/service/sm/controller.cpp index af2fadcef..c45b285f8 100644 --- a/src/core/hle/service/sm/controller.cpp +++ b/src/core/hle/service/sm/controller.cpp @@ -30,10 +30,7 @@ void Controller::DuplicateSession(Kernel::HLERequestContext& ctx) { IPC::ResponseBuilder rb{ctx, 2, 0, 1, IPC::ResponseBuilder::Flags::AlwaysMoveHandles}; rb.Push(RESULT_SUCCESS); - std::shared_ptr<Kernel::ClientSession> session{ctx.Session()->GetParent()->client}; - rb.PushMoveObjects(session); - - LOG_DEBUG(Service, "session={}", session->GetObjectId()); + rb.PushMoveObjects(ctx.Session()->GetParent()->Client()); } void Controller::DuplicateSessionEx(Kernel::HLERequestContext& ctx) { diff --git a/src/core/hle/service/sm/sm.cpp b/src/core/hle/service/sm/sm.cpp index a0a7206bb..88909504d 100644 --- a/src/core/hle/service/sm/sm.cpp +++ b/src/core/hle/service/sm/sm.cpp @@ -36,10 +36,11 @@ static ResultCode ValidateServiceName(const std::string& name) { return RESULT_SUCCESS; } -void ServiceManager::InstallInterfaces(std::shared_ptr<ServiceManager> self) { +void ServiceManager::InstallInterfaces(std::shared_ptr<ServiceManager> self, + Kernel::KernelCore& kernel) { ASSERT(self->sm_interface.expired()); - auto sm = std::make_shared<SM>(self); + auto sm = std::make_shared<SM>(self, kernel); sm->InstallAsNamedPort(); self->sm_interface = sm; self->controller_interface = std::make_unique<Controller>(); @@ -114,8 +115,6 @@ void SM::GetService(Kernel::HLERequestContext& ctx) { std::string name(name_buf.begin(), end); - // TODO(yuriks): Permission checks go here - auto client_port = service_manager->GetServicePort(name); if (client_port.Failed()) { IPC::ResponseBuilder rb{ctx, 2}; @@ -127,14 +126,22 @@ void SM::GetService(Kernel::HLERequestContext& ctx) { return; } - auto session = client_port.Unwrap()->Connect(); - ASSERT(session.Succeeded()); - if (session.Succeeded()) { - LOG_DEBUG(Service_SM, "called service={} -> session={}", name, (*session)->GetObjectId()); - IPC::ResponseBuilder rb{ctx, 2, 0, 1, IPC::ResponseBuilder::Flags::AlwaysMoveHandles}; - rb.Push(session.Code()); - rb.PushMoveObjects(std::move(session).Unwrap()); + auto [client, server] = Kernel::Session::Create(kernel, name); + + const auto& server_port = client_port.Unwrap()->GetServerPort(); + if (server_port->GetHLEHandler()) { + server_port->GetHLEHandler()->ClientConnected(server); + } else { + server_port->AppendPendingSession(server); } + + // Wake the threads waiting on the ServerPort + server_port->WakeupAllWaitingThreads(); + + LOG_DEBUG(Service_SM, "called service={} -> session={}", name, client->GetObjectId()); + IPC::ResponseBuilder rb{ctx, 2, 0, 1, IPC::ResponseBuilder::Flags::AlwaysMoveHandles}; + rb.Push(RESULT_SUCCESS); + rb.PushMoveObjects(std::move(client)); } void SM::RegisterService(Kernel::HLERequestContext& ctx) { @@ -178,8 +185,8 @@ void SM::UnregisterService(Kernel::HLERequestContext& ctx) { rb.Push(service_manager->UnregisterService(name)); } -SM::SM(std::shared_ptr<ServiceManager> service_manager) - : ServiceFramework("sm:", 4), service_manager(std::move(service_manager)) { +SM::SM(std::shared_ptr<ServiceManager> service_manager, Kernel::KernelCore& kernel) + : ServiceFramework{"sm:", 4}, service_manager{std::move(service_manager)}, kernel{kernel} { static const FunctionInfo functions[] = { {0x00000000, &SM::Initialize, "Initialize"}, {0x00000001, &SM::GetService, "GetService"}, diff --git a/src/core/hle/service/sm/sm.h b/src/core/hle/service/sm/sm.h index 3de22268b..b06d2f103 100644 --- a/src/core/hle/service/sm/sm.h +++ b/src/core/hle/service/sm/sm.h @@ -18,6 +18,7 @@ namespace Kernel { class ClientPort; class ClientSession; +class KernelCore; class ServerPort; class SessionRequestHandler; } // namespace Kernel @@ -29,7 +30,7 @@ class Controller; /// Interface to "sm:" service class SM final : public ServiceFramework<SM> { public: - explicit SM(std::shared_ptr<ServiceManager> service_manager); + explicit SM(std::shared_ptr<ServiceManager> service_manager, Kernel::KernelCore& kernel); ~SM() override; private: @@ -39,11 +40,12 @@ private: void UnregisterService(Kernel::HLERequestContext& ctx); std::shared_ptr<ServiceManager> service_manager; + Kernel::KernelCore& kernel; }; class ServiceManager { public: - static void InstallInterfaces(std::shared_ptr<ServiceManager> self); + static void InstallInterfaces(std::shared_ptr<ServiceManager> self, Kernel::KernelCore& kernel); ServiceManager(); ~ServiceManager(); |