diff --git a/include/services/frd.hpp b/include/services/frd.hpp index c33aeb5b..c2f4f376 100644 --- a/include/services/frd.hpp +++ b/include/services/frd.hpp @@ -1,15 +1,25 @@ #pragma once +#include #include "helpers.hpp" #include "kernel_types.hpp" #include "logger.hpp" #include "memory.hpp" +// It's important to keep this struct to 16 bytes as we use its sizeof in the service functions in frd.cpp +struct FriendKey { + u32 friendID; + u32 dummy; + u64 friendCode; +}; +static_assert(sizeof(FriendKey) == 16); + class FRDService { Handle handle = KernelHandles::FRD; Memory& mem; MAKE_LOG_FUNCTION(log, frdLogger) // Service commands + void getFriendKeyList(u32 messagePointer); void getMyFriendKey(u32 messagePointer); void getMyPresence(u32 messagePointer); void setClientSDKVersion(u32 messagePointer); diff --git a/src/core/services/frd.cpp b/src/core/services/frd.cpp index cb93b06d..483fb9c8 100644 --- a/src/core/services/frd.cpp +++ b/src/core/services/frd.cpp @@ -4,7 +4,8 @@ namespace FRDCommands { enum : u32 { SetClientSdkVersion = 0x00320042, GetMyFriendKey = 0x00050000, - GetMyPresence = 0x00080000 + GetMyPresence = 0x00080000, + GetFriendKeyList = 0x00110080 }; } @@ -19,6 +20,7 @@ void FRDService::reset() {} void FRDService::handleSyncRequest(u32 messagePointer) { const u32 command = mem.read32(messagePointer); switch (command) { + case FRDCommands::GetFriendKeyList: getFriendKeyList(messagePointer); break; case FRDCommands::GetMyFriendKey: getMyFriendKey(messagePointer); break; case FRDCommands::GetMyPresence: getMyPresence(messagePointer); break; case FRDCommands::SetClientSdkVersion: setClientSDKVersion(messagePointer); break; @@ -27,7 +29,7 @@ void FRDService::handleSyncRequest(u32 messagePointer) { } void FRDService::getMyFriendKey(u32 messagePointer) { - log("FRD::GetMyFriendKey"); + log("FRD::GetMyFriendKey\n"); mem.write32(messagePointer + 4, Result::Success); mem.write32(messagePointer + 8, 0); // Principal ID @@ -36,6 +38,21 @@ void FRDService::getMyFriendKey(u32 messagePointer) { mem.write32(messagePointer + 20, 0); } +void FRDService::getFriendKeyList(u32 messagePointer) { + log("FRD::GetFriendKeyList\n"); + + const u32 count = mem.read32(messagePointer + 8); // From what I understand this is a cap on the number of keys to receive? + constexpr u32 friendCount = 0; // And this should be the number of friends whose keys were actually received? + + mem.write32(messagePointer + 4, Result::Success); + mem.write32(messagePointer + 8, 0); + + // Zero out friend keys + for (u32 i = 0; i < count * sizeof(FriendKey); i += 4) { + mem.write32(messagePointer + 12 + i, 0); + } +} + void FRDService::getMyPresence(u32 messagePointer) { static constexpr u32 presenceSize = 0x12C; // A presence seems to be 12C bytes of data, not sure what it contains log("FRD::GetMyPresence\n");