acc.cpp 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. // Copyright 2018 yuzu emulator team
  2. // Licensed under GPLv2 or any later version
  3. // Refer to the license.txt file included.
  4. #include <array>
  5. #include "common/logging/log.h"
  6. #include "core/hle/ipc_helpers.h"
  7. #include "core/hle/service/acc/acc.h"
  8. #include "core/hle/service/acc/acc_aa.h"
  9. #include "core/hle/service/acc/acc_su.h"
  10. #include "core/hle/service/acc/acc_u0.h"
  11. #include "core/hle/service/acc/acc_u1.h"
  12. namespace Service::Account {
  13. // TODO: RE this structure
  14. struct UserData {
  15. INSERT_PADDING_WORDS(1);
  16. u32 icon_id;
  17. u8 bg_color_id;
  18. INSERT_PADDING_BYTES(0x7);
  19. INSERT_PADDING_BYTES(0x10);
  20. INSERT_PADDING_BYTES(0x60);
  21. };
  22. static_assert(sizeof(UserData) == 0x80, "UserData structure has incorrect size");
  23. struct ProfileBase {
  24. u128 user_id;
  25. u64 timestamp;
  26. std::array<u8, 0x20> username;
  27. };
  28. static_assert(sizeof(ProfileBase) == 0x38, "ProfileBase structure has incorrect size");
  29. static constexpr u128 DEFAULT_USER_ID{1ull, 0ull};
  30. class IProfile final : public ServiceFramework<IProfile> {
  31. public:
  32. explicit IProfile(u128 user_id) : ServiceFramework("IProfile"), user_id(user_id) {
  33. static const FunctionInfo functions[] = {
  34. {0, nullptr, "Get"},
  35. {1, &IProfile::GetBase, "GetBase"},
  36. {10, nullptr, "GetImageSize"},
  37. {11, nullptr, "LoadImage"},
  38. };
  39. RegisterHandlers(functions);
  40. }
  41. private:
  42. void GetBase(Kernel::HLERequestContext& ctx) {
  43. LOG_WARNING(Service_ACC, "(STUBBED) called");
  44. // TODO(Subv): Retrieve this information from somewhere.
  45. ProfileBase profile_base{};
  46. profile_base.user_id = user_id;
  47. profile_base.username = {'y', 'u', 'z', 'u'};
  48. IPC::ResponseBuilder rb{ctx, 16};
  49. rb.Push(RESULT_SUCCESS);
  50. rb.PushRaw(profile_base);
  51. }
  52. u128 user_id; ///< The user id this profile refers to.
  53. };
  54. class IManagerForApplication final : public ServiceFramework<IManagerForApplication> {
  55. public:
  56. IManagerForApplication() : ServiceFramework("IManagerForApplication") {
  57. static const FunctionInfo functions[] = {
  58. {0, &IManagerForApplication::CheckAvailability, "CheckAvailability"},
  59. {1, &IManagerForApplication::GetAccountId, "GetAccountId"},
  60. {2, nullptr, "EnsureIdTokenCacheAsync"},
  61. {3, nullptr, "LoadIdTokenCache"},
  62. {130, nullptr, "GetNintendoAccountUserResourceCacheForApplication"},
  63. {150, nullptr, "CreateAuthorizationRequest"},
  64. {160, nullptr, "StoreOpenContext"},
  65. };
  66. RegisterHandlers(functions);
  67. }
  68. private:
  69. void CheckAvailability(Kernel::HLERequestContext& ctx) {
  70. LOG_WARNING(Service_ACC, "(STUBBED) called");
  71. IPC::ResponseBuilder rb{ctx, 3};
  72. rb.Push(RESULT_SUCCESS);
  73. rb.Push(false); // TODO: Check when this is supposed to return true and when not
  74. }
  75. void GetAccountId(Kernel::HLERequestContext& ctx) {
  76. LOG_WARNING(Service_ACC, "(STUBBED) called");
  77. // TODO(Subv): Find out what this actually does and implement it. Stub it as an error for
  78. // now since we do not implement NNID. Returning a bogus id here will cause games to send
  79. // invalid IPC requests after ListOpenUsers is called.
  80. IPC::ResponseBuilder rb{ctx, 2};
  81. rb.Push(ResultCode(-1));
  82. }
  83. };
  84. void Module::Interface::GetUserExistence(Kernel::HLERequestContext& ctx) {
  85. LOG_WARNING(Service_ACC, "(STUBBED) called");
  86. IPC::ResponseBuilder rb{ctx, 3};
  87. rb.Push(RESULT_SUCCESS);
  88. rb.Push(true); // TODO: Check when this is supposed to return true and when not
  89. }
  90. void Module::Interface::ListAllUsers(Kernel::HLERequestContext& ctx) {
  91. LOG_WARNING(Service_ACC, "(STUBBED) called");
  92. // TODO(Subv): There is only one user for now.
  93. const std::vector<u128> user_ids = {DEFAULT_USER_ID};
  94. ctx.WriteBuffer(user_ids);
  95. IPC::ResponseBuilder rb{ctx, 2};
  96. rb.Push(RESULT_SUCCESS);
  97. }
  98. void Module::Interface::ListOpenUsers(Kernel::HLERequestContext& ctx) {
  99. LOG_WARNING(Service_ACC, "(STUBBED) called");
  100. // TODO(Subv): There is only one user for now.
  101. const std::vector<u128> user_ids = {DEFAULT_USER_ID};
  102. ctx.WriteBuffer(user_ids);
  103. IPC::ResponseBuilder rb{ctx, 2};
  104. rb.Push(RESULT_SUCCESS);
  105. }
  106. void Module::Interface::GetProfile(Kernel::HLERequestContext& ctx) {
  107. IPC::RequestParser rp{ctx};
  108. u128 user_id = rp.PopRaw<u128>();
  109. IPC::ResponseBuilder rb{ctx, 2, 0, 1};
  110. rb.Push(RESULT_SUCCESS);
  111. rb.PushIpcInterface<IProfile>(user_id);
  112. LOG_DEBUG(Service_ACC, "called user_id=0x{:016X}{:016X}", user_id[1], user_id[0]);
  113. }
  114. void Module::Interface::InitializeApplicationInfo(Kernel::HLERequestContext& ctx) {
  115. LOG_WARNING(Service_ACC, "(STUBBED) called");
  116. IPC::ResponseBuilder rb{ctx, 2};
  117. rb.Push(RESULT_SUCCESS);
  118. }
  119. void Module::Interface::GetBaasAccountManagerForApplication(Kernel::HLERequestContext& ctx) {
  120. IPC::ResponseBuilder rb{ctx, 2, 0, 1};
  121. rb.Push(RESULT_SUCCESS);
  122. rb.PushIpcInterface<IManagerForApplication>();
  123. LOG_DEBUG(Service_ACC, "called");
  124. }
  125. void Module::Interface::GetLastOpenedUser(Kernel::HLERequestContext& ctx) {
  126. LOG_WARNING(Service_ACC, "(STUBBED) called");
  127. IPC::ResponseBuilder rb{ctx, 6};
  128. rb.Push(RESULT_SUCCESS);
  129. rb.PushRaw(DEFAULT_USER_ID);
  130. }
  131. Module::Interface::Interface(std::shared_ptr<Module> module, const char* name)
  132. : ServiceFramework(name), module(std::move(module)) {}
  133. void InstallInterfaces(SM::ServiceManager& service_manager) {
  134. auto module = std::make_shared<Module>();
  135. std::make_shared<ACC_AA>(module)->InstallAsService(service_manager);
  136. std::make_shared<ACC_SU>(module)->InstallAsService(service_manager);
  137. std::make_shared<ACC_U0>(module)->InstallAsService(service_manager);
  138. std::make_shared<ACC_U1>(module)->InstallAsService(service_manager);
  139. }
  140. } // namespace Service::Account