IFriendService.cs 5.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170
  1. using Ryujinx.Common;
  2. using Ryujinx.Common.Logging;
  3. using Ryujinx.HLE.HOS.Services.Account.Acc;
  4. using Ryujinx.HLE.HOS.Services.Friend.ServiceCreator.FriendService;
  5. using Ryujinx.HLE.Utilities;
  6. using System.IO;
  7. using System.Runtime.InteropServices;
  8. namespace Ryujinx.HLE.HOS.Services.Friend.ServiceCreator
  9. {
  10. class IFriendService : IpcService
  11. {
  12. private FriendServicePermissionLevel _permissionLevel;
  13. public IFriendService(FriendServicePermissionLevel permissionLevel)
  14. {
  15. _permissionLevel = permissionLevel;
  16. }
  17. [Command(10100)]
  18. // nn::friends::GetFriendListIds(int offset, nn::account::Uid userUUID, nn::friends::detail::ipc::SizedFriendFilter friendFilter, ulong pidPlaceHolder, pid)
  19. // -> int outCount, array<nn::account::NetworkServiceAccountId, 0xa>
  20. public ResultCode GetFriendListIds(ServiceCtx context)
  21. {
  22. int offset = context.RequestData.ReadInt32();
  23. // Padding
  24. context.RequestData.ReadInt32();
  25. UInt128 uuid = context.RequestData.ReadStruct<UInt128>();
  26. FriendFilter filter = context.RequestData.ReadStruct<FriendFilter>();
  27. // Pid placeholder
  28. context.RequestData.ReadInt64();
  29. if (uuid.IsNull)
  30. {
  31. return ResultCode.InvalidArgument;
  32. }
  33. // There are no friends online, so we return 0 because the nn::account::NetworkServiceAccountId array is empty.
  34. context.ResponseData.Write(0);
  35. Logger.PrintStub(LogClass.ServiceFriend, new
  36. {
  37. UserId = uuid.ToString(),
  38. offset,
  39. filter.PresenceStatus,
  40. filter.IsFavoriteOnly,
  41. filter.IsSameAppPresenceOnly,
  42. filter.IsSameAppPlayedOnly,
  43. filter.IsArbitraryAppPlayedOnly,
  44. filter.PresenceGroupId,
  45. });
  46. return ResultCode.Success;
  47. }
  48. [Command(10101)]
  49. // nn::friends::GetFriendList(int offset, nn::account::Uid userUUID, nn::friends::detail::ipc::SizedFriendFilter friendFilter, ulong pidPlaceHolder, pid)
  50. // -> int outCount, array<nn::friends::detail::FriendImpl, 0x6>
  51. public ResultCode GetFriendList(ServiceCtx context)
  52. {
  53. int offset = context.RequestData.ReadInt32();
  54. // Padding
  55. context.RequestData.ReadInt32();
  56. UInt128 uuid = context.RequestData.ReadStruct<UInt128>();
  57. FriendFilter filter = context.RequestData.ReadStruct<FriendFilter>();
  58. // Pid placeholder
  59. context.RequestData.ReadInt64();
  60. if (uuid.IsNull)
  61. {
  62. return ResultCode.InvalidArgument;
  63. }
  64. // There are no friends online, so we return 0 because the nn::account::NetworkServiceAccountId array is empty.
  65. context.ResponseData.Write(0);
  66. Logger.PrintStub(LogClass.ServiceFriend, new {
  67. UserId = uuid.ToString(),
  68. offset,
  69. filter.PresenceStatus,
  70. filter.IsFavoriteOnly,
  71. filter.IsSameAppPresenceOnly,
  72. filter.IsSameAppPlayedOnly,
  73. filter.IsArbitraryAppPlayedOnly,
  74. filter.PresenceGroupId,
  75. });
  76. return ResultCode.Success;
  77. }
  78. [Command(10600)]
  79. // nn::friends::DeclareOpenOnlinePlaySession(nn::account::Uid)
  80. public ResultCode DeclareOpenOnlinePlaySession(ServiceCtx context)
  81. {
  82. UInt128 uuid = context.RequestData.ReadStruct<UInt128>();
  83. if (uuid.IsNull)
  84. {
  85. return ResultCode.InvalidArgument;
  86. }
  87. if (context.Device.System.State.Account.TryGetUser(uuid, out UserProfile profile))
  88. {
  89. profile.OnlinePlayState = AccountState.Open;
  90. }
  91. Logger.PrintStub(LogClass.ServiceFriend, new { UserId = uuid.ToString(), profile.OnlinePlayState });
  92. return ResultCode.Success;
  93. }
  94. [Command(10601)]
  95. // nn::friends::DeclareCloseOnlinePlaySession(nn::account::Uid)
  96. public ResultCode DeclareCloseOnlinePlaySession(ServiceCtx context)
  97. {
  98. UInt128 uuid = context.RequestData.ReadStruct<UInt128>();
  99. if (uuid.IsNull)
  100. {
  101. return ResultCode.InvalidArgument;
  102. }
  103. if (context.Device.System.State.Account.TryGetUser(uuid, out UserProfile profile))
  104. {
  105. profile.OnlinePlayState = AccountState.Closed;
  106. }
  107. Logger.PrintStub(LogClass.ServiceFriend, new { UserId = uuid.ToString(), profile.OnlinePlayState });
  108. return ResultCode.Success;
  109. }
  110. [Command(10610)]
  111. // nn::friends::UpdateUserPresence(nn::account::Uid, u64, pid, buffer<nn::friends::detail::UserPresenceImpl, 0x19>)
  112. public ResultCode UpdateUserPresence(ServiceCtx context)
  113. {
  114. UInt128 uuid = context.RequestData.ReadStruct<UInt128>();
  115. // Pid placeholder
  116. context.RequestData.ReadInt64();
  117. long position = context.Request.PtrBuff[0].Position;
  118. long size = context.Request.PtrBuff[0].Size;
  119. byte[] bufferContent = context.Memory.ReadBytes(position, size);
  120. if (uuid.IsNull)
  121. {
  122. return ResultCode.InvalidArgument;
  123. }
  124. int elementCount = bufferContent.Length / Marshal.SizeOf<UserPresence>();
  125. using (BinaryReader bufferReader = new BinaryReader(new MemoryStream(bufferContent)))
  126. {
  127. UserPresence[] userPresenceInputArray = bufferReader.ReadStructArray<UserPresence>(elementCount);
  128. Logger.PrintStub(LogClass.ServiceFriend, new { UserId = uuid.ToString(), userPresenceInputArray });
  129. }
  130. return ResultCode.Success;
  131. }
  132. }
  133. }