From c6de9657be71a9c659f9c991ec8d024ebf44d56e Mon Sep 17 00:00:00 2001 From: bunnei Date: Mon, 10 May 2021 15:57:59 -0700 Subject: hle: kernel: Implement named service ports using service interface factory. - This allows us to create a new interface each time ConnectToNamedPort is called, removing the assumption that these are static. --- src/core/hle/service/service.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'src/core/hle/service/service.cpp') diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index 00e683c2f..f3fd0f534 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -111,7 +111,7 @@ void ServiceFrameworkBase::InstallAsService(SM::ServiceManager& service_manager) port_installed = true; } -void ServiceFrameworkBase::InstallAsNamedPort(Kernel::KernelCore& kernel) { +Kernel::KClientPort& ServiceFrameworkBase::CreatePort(Kernel::KernelCore& kernel) { const auto guard = LockService(); ASSERT(!port_installed); @@ -119,9 +119,10 @@ void ServiceFrameworkBase::InstallAsNamedPort(Kernel::KernelCore& kernel) { auto* port = Kernel::KPort::Create(kernel); port->Initialize(max_sessions, false, service_name); port->GetServerPort().SetHleHandler(shared_from_this()); - kernel.AddNamedPort(service_name, &port->GetClientPort()); port_installed = true; + + return port->GetClientPort(); } void ServiceFrameworkBase::RegisterHandlersBase(const FunctionInfoBase* functions, std::size_t n) { -- cgit v1.2.3 From 41928dfdda96528f2c99d6ee00989a365f1a7ab1 Mon Sep 17 00:00:00 2001 From: bunnei Date: Mon, 10 May 2021 16:03:39 -0700 Subject: hle: service: sm: Use RegisterNamedService to register the service. --- src/core/hle/service/service.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/core/hle/service/service.cpp') diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index f3fd0f534..d7e09e8f1 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -208,7 +208,7 @@ Services::Services(std::shared_ptr& sm, Core::System& system system.GetFileSystemController().CreateFactories(*system.GetFilesystem(), false); - SM::ServiceManager::InstallInterfaces(sm, system); + system.Kernel().RegisterNamedService("sm:", SM::ServiceManager::InterfaceFactory); Account::InstallInterfaces(system); AM::InstallInterfaces(*sm, *nv_flinger, system); -- cgit v1.2.3 From da25a5986666c55de1421aed978f7e92e5a87c8f Mon Sep 17 00:00:00 2001 From: bunnei Date: Mon, 10 May 2021 16:05:37 -0700 Subject: hle: service: Implement IPC::CommandType::Close. - This was not actually closing sessions before. --- src/core/hle/service/service.cpp | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) (limited to 'src/core/hle/service/service.cpp') diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index d7e09e8f1..e36c35a86 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -167,33 +167,36 @@ void ServiceFrameworkBase::InvokeRequest(Kernel::HLERequestContext& ctx) { handler_invoker(this, info->handler_callback, ctx); } -ResultCode ServiceFrameworkBase::HandleSyncRequest(Kernel::HLERequestContext& context) { +ResultCode ServiceFrameworkBase::HandleSyncRequest(Kernel::KServerSession& session, + Kernel::HLERequestContext& ctx) { const auto guard = LockService(); - switch (context.GetCommandType()) { - case IPC::CommandType::Close: { - IPC::ResponseBuilder rb{context, 2}; + switch (ctx.GetCommandType()) { + case IPC::CommandType::Close: + case IPC::CommandType::TIPC_Close: { + session.Close(); + IPC::ResponseBuilder rb{ctx, 2}; rb.Push(RESULT_SUCCESS); return IPC::ERR_REMOTE_PROCESS_DEAD; } case IPC::CommandType::ControlWithContext: case IPC::CommandType::Control: { - system.ServiceManager().InvokeControlRequest(context); + system.ServiceManager().InvokeControlRequest(ctx); break; } case IPC::CommandType::RequestWithContext: case IPC::CommandType::Request: { - InvokeRequest(context); + InvokeRequest(ctx); break; } default: - UNIMPLEMENTED_MSG("command_type={}", context.GetCommandType()); + UNIMPLEMENTED_MSG("command_type={}", ctx.GetCommandType()); } // If emulation was shutdown, we are closing service threads, do not write the response back to // memory that may be shutting down as well. if (system.IsPoweredOn()) { - context.WriteToOutgoingCommandBuffer(context.GetThread()); + ctx.WriteToOutgoingCommandBuffer(ctx.GetThread()); } return RESULT_SUCCESS; -- cgit v1.2.3 From 21671d05a362f98cd24dcc520a3da163e349fe07 Mon Sep 17 00:00:00 2001 From: bunnei Date: Mon, 10 May 2021 16:08:06 -0700 Subject: hle: service: Add support for dispatching TIPC requests. --- src/core/hle/service/service.cpp | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) (limited to 'src/core/hle/service/service.cpp') diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index e36c35a86..2c9b2ce6d 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -133,6 +133,16 @@ void ServiceFrameworkBase::RegisterHandlersBase(const FunctionInfoBase* function } } +void ServiceFrameworkBase::RegisterHandlersBaseTipc(const FunctionInfoBase* functions, + std::size_t n) { + handlers_tipc.reserve(handlers_tipc.size() + n); + for (std::size_t i = 0; i < n; ++i) { + // Usually this array is sorted by id already, so hint to insert at the end + handlers_tipc.emplace_hint(handlers_tipc.cend(), functions[i].expected_header, + functions[i]); + } +} + void ServiceFrameworkBase::ReportUnimplementedFunction(Kernel::HLERequestContext& ctx, const FunctionInfoBase* info) { auto cmd_buf = ctx.CommandBuffer(); @@ -167,6 +177,20 @@ void ServiceFrameworkBase::InvokeRequest(Kernel::HLERequestContext& ctx) { handler_invoker(this, info->handler_callback, ctx); } +void ServiceFrameworkBase::InvokeRequestTipc(Kernel::HLERequestContext& ctx) { + boost::container::flat_map::iterator itr; + + itr = handlers_tipc.find(ctx.GetCommand()); + + const FunctionInfoBase* info = itr == handlers_tipc.end() ? nullptr : &itr->second; + if (info == nullptr || info->handler_callback == nullptr) { + return ReportUnimplementedFunction(ctx, info); + } + + LOG_TRACE(Service, "{}", MakeFunctionString(info->name, GetServiceName(), ctx.CommandBuffer())); + handler_invoker(this, info->handler_callback, ctx); +} + ResultCode ServiceFrameworkBase::HandleSyncRequest(Kernel::KServerSession& session, Kernel::HLERequestContext& ctx) { const auto guard = LockService(); @@ -190,6 +214,11 @@ ResultCode ServiceFrameworkBase::HandleSyncRequest(Kernel::KServerSession& sessi break; } default: + if (ctx.IsTipc()) { + InvokeRequestTipc(ctx); + break; + } + UNIMPLEMENTED_MSG("command_type={}", ctx.GetCommandType()); } -- cgit v1.2.3