aboutsummaryrefslogtreecommitdiff
path: root/Ryujinx.HLE/HOS/Services/IpcService.cs
diff options
context:
space:
mode:
Diffstat (limited to 'Ryujinx.HLE/HOS/Services/IpcService.cs')
-rw-r--r--Ryujinx.HLE/HOS/Services/IpcService.cs63
1 files changed, 56 insertions, 7 deletions
diff --git a/Ryujinx.HLE/HOS/Services/IpcService.cs b/Ryujinx.HLE/HOS/Services/IpcService.cs
index 095e332c..69d461de 100644
--- a/Ryujinx.HLE/HOS/Services/IpcService.cs
+++ b/Ryujinx.HLE/HOS/Services/IpcService.cs
@@ -11,7 +11,8 @@ namespace Ryujinx.HLE.HOS.Services
{
abstract class IpcService
{
- public IReadOnlyDictionary<int, MethodInfo> Commands { get; }
+ public IReadOnlyDictionary<int, MethodInfo> HipcCommands { get; }
+ public IReadOnlyDictionary<int, MethodInfo> TipcCommands { get; }
public ServerBase Server { get; private set; }
@@ -22,11 +23,18 @@ namespace Ryujinx.HLE.HOS.Services
public IpcService(ServerBase server = null)
{
- Commands = Assembly.GetExecutingAssembly().GetTypes()
+ HipcCommands = Assembly.GetExecutingAssembly().GetTypes()
.Where(type => type == GetType())
.SelectMany(type => type.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public))
- .SelectMany(methodInfo => methodInfo.GetCustomAttributes(typeof(CommandAttribute))
- .Select(command => (((CommandAttribute)command).Id, methodInfo)))
+ .SelectMany(methodInfo => methodInfo.GetCustomAttributes(typeof(CommandHipcAttribute))
+ .Select(command => (((CommandHipcAttribute)command).Id, methodInfo)))
+ .ToDictionary(command => command.Id, command => command.methodInfo);
+
+ TipcCommands = Assembly.GetExecutingAssembly().GetTypes()
+ .Where(type => type == GetType())
+ .SelectMany(type => type.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public))
+ .SelectMany(methodInfo => methodInfo.GetCustomAttributes(typeof(CommandTipcAttribute))
+ .Select(command => (((CommandTipcAttribute)command).Id, methodInfo)))
.ToDictionary(command => command.Id, command => command.methodInfo);
Server = server;
@@ -53,7 +61,7 @@ namespace Ryujinx.HLE.HOS.Services
_isDomain = false;
}
- public void CallMethod(ServiceCtx context)
+ public void CallHipcMethod(ServiceCtx context)
{
IpcService service = this;
@@ -99,7 +107,7 @@ namespace Ryujinx.HLE.HOS.Services
long sfciMagic = context.RequestData.ReadInt64();
int commandId = (int)context.RequestData.ReadInt64();
- bool serviceExists = service.Commands.TryGetValue(commandId, out MethodInfo processRequest);
+ bool serviceExists = service.HipcCommands.TryGetValue(commandId, out MethodInfo processRequest);
if (ServiceConfiguration.IgnoreMissingServices || serviceExists)
{
@@ -145,7 +153,48 @@ namespace Ryujinx.HLE.HOS.Services
{
string dbgMessage = $"{service.GetType().FullName}: {commandId}";
- throw new ServiceNotImplementedException(service, context, dbgMessage);
+ throw new ServiceNotImplementedException(service, context, dbgMessage, false);
+ }
+ }
+
+ public void CallTipcMethod(ServiceCtx context)
+ {
+ int commandId = (int)context.Request.Type - 0x10;
+
+ bool serviceExists = TipcCommands.TryGetValue(commandId, out MethodInfo processRequest);
+
+ if (ServiceConfiguration.IgnoreMissingServices || serviceExists)
+ {
+ ResultCode result = ResultCode.Success;
+
+ context.ResponseData.BaseStream.Seek(0x4, SeekOrigin.Begin);
+
+ if (serviceExists)
+ {
+ Logger.Debug?.Print(LogClass.KernelIpc, $"{GetType().Name}: {processRequest.Name}");
+
+ result = (ResultCode)processRequest.Invoke(this, new object[] { context });
+ }
+ else
+ {
+ string serviceName;
+
+ DummyService dummyService = this as DummyService;
+
+ serviceName = (dummyService == null) ? GetType().FullName : dummyService.ServiceName;
+
+ Logger.Warning?.Print(LogClass.KernelIpc, $"Missing service {serviceName}: {commandId} ignored");
+ }
+
+ context.ResponseData.BaseStream.Seek(0, SeekOrigin.Begin);
+
+ context.ResponseData.Write((uint)result);
+ }
+ else
+ {
+ string dbgMessage = $"{GetType().FullName}: {commandId}";
+
+ throw new ServiceNotImplementedException(this, context, dbgMessage, true);
}
}