From 2d4e7c826422fdbfa7e0ba837ab65f58801e3251 Mon Sep 17 00:00:00 2001 From: Narr the Reg Date: Fri, 24 Nov 2023 11:53:31 -0600 Subject: yuzu: Display firmware version --- src/core/hle/service/set/set_sys.cpp | 66 +++++++++++++++++++----------------- src/core/hle/service/set/set_sys.h | 24 +++++++++++++ 2 files changed, 59 insertions(+), 31 deletions(-) (limited to 'src/core/hle/service') diff --git a/src/core/hle/service/set/set_sys.cpp b/src/core/hle/service/set/set_sys.cpp index 19c667b42..f5edfdc8b 100644 --- a/src/core/hle/service/set/set_sys.cpp +++ b/src/core/hle/service/set/set_sys.cpp @@ -19,19 +19,8 @@ namespace Service::Set { -namespace { -constexpr u64 SYSTEM_VERSION_FILE_MINOR_REVISION_OFFSET = 0x05; - -enum class GetFirmwareVersionType { - Version1, - Version2, -}; - -void GetFirmwareVersionImpl(Core::System& system, HLERequestContext& ctx, - GetFirmwareVersionType type) { - ASSERT_MSG(ctx.GetWriteBufferSize() == 0x100, - "FirmwareVersion output buffer must be 0x100 bytes in size!"); - +Result GetFirmwareVersionImpl(FirmwareVersionFormat& out_firmware, Core::System& system, + GetFirmwareVersionType type) { constexpr u64 FirmwareVersionSystemDataId = 0x0100000000000809; auto& fsc = system.GetFileSystemController(); @@ -52,39 +41,34 @@ void GetFirmwareVersionImpl(Core::System& system, HLERequestContext& ctx, FileSys::SystemArchive::SynthesizeSystemArchive(FirmwareVersionSystemDataId)); } - const auto early_exit_failure = [&ctx](std::string_view desc, Result code) { + const auto early_exit_failure = [](std::string_view desc, Result code) { LOG_ERROR(Service_SET, "General failure while attempting to resolve firmware version ({}).", desc); - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(code); + return code; }; const auto ver_file = romfs->GetFile("file"); if (ver_file == nullptr) { - early_exit_failure("The system version archive didn't contain the file 'file'.", - FileSys::ERROR_INVALID_ARGUMENT); - return; + return early_exit_failure("The system version archive didn't contain the file 'file'.", + FileSys::ERROR_INVALID_ARGUMENT); } auto data = ver_file->ReadAllBytes(); - if (data.size() != 0x100) { - early_exit_failure("The system version file 'file' was not the correct size.", - FileSys::ERROR_OUT_OF_BOUNDS); - return; + if (data.size() != sizeof(FirmwareVersionFormat)) { + return early_exit_failure("The system version file 'file' was not the correct size.", + FileSys::ERROR_OUT_OF_BOUNDS); } + std::memcpy(&out_firmware, data.data(), sizeof(FirmwareVersionFormat)); + // If the command is GetFirmwareVersion (as opposed to GetFirmwareVersion2), hardware will // zero out the REVISION_MINOR field. if (type == GetFirmwareVersionType::Version1) { - data[SYSTEM_VERSION_FILE_MINOR_REVISION_OFFSET] = 0; + out_firmware.revision_minor = 0; } - ctx.WriteBuffer(data); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(ResultSuccess); + return ResultSuccess; } -} // Anonymous namespace void SET_SYS::SetLanguageCode(HLERequestContext& ctx) { IPC::RequestParser rp{ctx}; @@ -98,12 +82,32 @@ void SET_SYS::SetLanguageCode(HLERequestContext& ctx) { void SET_SYS::GetFirmwareVersion(HLERequestContext& ctx) { LOG_DEBUG(Service_SET, "called"); - GetFirmwareVersionImpl(system, ctx, GetFirmwareVersionType::Version1); + + FirmwareVersionFormat firmware_data{}; + const auto result = + GetFirmwareVersionImpl(firmware_data, system, GetFirmwareVersionType::Version1); + + if (result.IsSuccess()) { + ctx.WriteBuffer(firmware_data); + } + + IPC::ResponseBuilder rb{ctx, 2}; + rb.Push(result); } void SET_SYS::GetFirmwareVersion2(HLERequestContext& ctx) { LOG_DEBUG(Service_SET, "called"); - GetFirmwareVersionImpl(system, ctx, GetFirmwareVersionType::Version2); + + FirmwareVersionFormat firmware_data{}; + const auto result = + GetFirmwareVersionImpl(firmware_data, system, GetFirmwareVersionType::Version2); + + if (result.IsSuccess()) { + ctx.WriteBuffer(firmware_data); + } + + IPC::ResponseBuilder rb{ctx, 2}; + rb.Push(result); } void SET_SYS::GetAccountSettings(HLERequestContext& ctx) { diff --git a/src/core/hle/service/set/set_sys.h b/src/core/hle/service/set/set_sys.h index 93023c6dd..5f770fd32 100644 --- a/src/core/hle/service/set/set_sys.h +++ b/src/core/hle/service/set/set_sys.h @@ -4,6 +4,7 @@ #pragma once #include "common/uuid.h" +#include "core/hle/result.h" #include "core/hle/service/service.h" #include "core/hle/service/time/clock_types.h" @@ -12,6 +13,29 @@ class System; } namespace Service::Set { +enum class LanguageCode : u64; +enum class GetFirmwareVersionType { + Version1, + Version2, +}; + +struct FirmwareVersionFormat { + u8 major; + u8 minor; + u8 micro; + INSERT_PADDING_BYTES(1); + u8 revision_major; + u8 revision_minor; + INSERT_PADDING_BYTES(2); + std::array platform; + std::array version_hash; + std::array display_version; + std::array display_title; +}; +static_assert(sizeof(FirmwareVersionFormat) == 0x100, "FirmwareVersionFormat is an invalid size"); + +Result GetFirmwareVersionImpl(FirmwareVersionFormat& out_firmware, Core::System& system, + GetFirmwareVersionType type); class SET_SYS final : public ServiceFramework { public: -- cgit v1.2.3