summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/core/hle/service/set/set_sys.cpp66
-rw-r--r--src/core/hle/service/set/set_sys.h24
-rw-r--r--src/yuzu/main.cpp39
-rw-r--r--src/yuzu/main.h2
4 files changed, 98 insertions, 33 deletions
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 @@
19 19
20namespace Service::Set { 20namespace Service::Set {
21 21
22namespace { 22Result GetFirmwareVersionImpl(FirmwareVersionFormat& out_firmware, Core::System& system,
23constexpr u64 SYSTEM_VERSION_FILE_MINOR_REVISION_OFFSET = 0x05; 23 GetFirmwareVersionType type) {
24
25enum class GetFirmwareVersionType {
26 Version1,
27 Version2,
28};
29
30void GetFirmwareVersionImpl(Core::System& system, HLERequestContext& ctx,
31 GetFirmwareVersionType type) {
32 ASSERT_MSG(ctx.GetWriteBufferSize() == 0x100,
33 "FirmwareVersion output buffer must be 0x100 bytes in size!");
34
35 constexpr u64 FirmwareVersionSystemDataId = 0x0100000000000809; 24 constexpr u64 FirmwareVersionSystemDataId = 0x0100000000000809;
36 auto& fsc = system.GetFileSystemController(); 25 auto& fsc = system.GetFileSystemController();
37 26
@@ -52,39 +41,34 @@ void GetFirmwareVersionImpl(Core::System& system, HLERequestContext& ctx,
52 FileSys::SystemArchive::SynthesizeSystemArchive(FirmwareVersionSystemDataId)); 41 FileSys::SystemArchive::SynthesizeSystemArchive(FirmwareVersionSystemDataId));
53 } 42 }
54 43
55 const auto early_exit_failure = [&ctx](std::string_view desc, Result code) { 44 const auto early_exit_failure = [](std::string_view desc, Result code) {
56 LOG_ERROR(Service_SET, "General failure while attempting to resolve firmware version ({}).", 45 LOG_ERROR(Service_SET, "General failure while attempting to resolve firmware version ({}).",
57 desc); 46 desc);
58 IPC::ResponseBuilder rb{ctx, 2}; 47 return code;
59 rb.Push(code);
60 }; 48 };
61 49
62 const auto ver_file = romfs->GetFile("file"); 50 const auto ver_file = romfs->GetFile("file");
63 if (ver_file == nullptr) { 51 if (ver_file == nullptr) {
64 early_exit_failure("The system version archive didn't contain the file 'file'.", 52 return early_exit_failure("The system version archive didn't contain the file 'file'.",
65 FileSys::ERROR_INVALID_ARGUMENT); 53 FileSys::ERROR_INVALID_ARGUMENT);
66 return;
67 } 54 }
68 55
69 auto data = ver_file->ReadAllBytes(); 56 auto data = ver_file->ReadAllBytes();
70 if (data.size() != 0x100) { 57 if (data.size() != sizeof(FirmwareVersionFormat)) {
71 early_exit_failure("The system version file 'file' was not the correct size.", 58 return early_exit_failure("The system version file 'file' was not the correct size.",
72 FileSys::ERROR_OUT_OF_BOUNDS); 59 FileSys::ERROR_OUT_OF_BOUNDS);
73 return;
74 } 60 }
75 61
62 std::memcpy(&out_firmware, data.data(), sizeof(FirmwareVersionFormat));
63
76 // If the command is GetFirmwareVersion (as opposed to GetFirmwareVersion2), hardware will 64 // If the command is GetFirmwareVersion (as opposed to GetFirmwareVersion2), hardware will
77 // zero out the REVISION_MINOR field. 65 // zero out the REVISION_MINOR field.
78 if (type == GetFirmwareVersionType::Version1) { 66 if (type == GetFirmwareVersionType::Version1) {
79 data[SYSTEM_VERSION_FILE_MINOR_REVISION_OFFSET] = 0; 67 out_firmware.revision_minor = 0;
80 } 68 }
81 69
82 ctx.WriteBuffer(data); 70 return ResultSuccess;
83
84 IPC::ResponseBuilder rb{ctx, 2};
85 rb.Push(ResultSuccess);
86} 71}
87} // Anonymous namespace
88 72
89void SET_SYS::SetLanguageCode(HLERequestContext& ctx) { 73void SET_SYS::SetLanguageCode(HLERequestContext& ctx) {
90 IPC::RequestParser rp{ctx}; 74 IPC::RequestParser rp{ctx};
@@ -98,12 +82,32 @@ void SET_SYS::SetLanguageCode(HLERequestContext& ctx) {
98 82
99void SET_SYS::GetFirmwareVersion(HLERequestContext& ctx) { 83void SET_SYS::GetFirmwareVersion(HLERequestContext& ctx) {
100 LOG_DEBUG(Service_SET, "called"); 84 LOG_DEBUG(Service_SET, "called");
101 GetFirmwareVersionImpl(system, ctx, GetFirmwareVersionType::Version1); 85
86 FirmwareVersionFormat firmware_data{};
87 const auto result =
88 GetFirmwareVersionImpl(firmware_data, system, GetFirmwareVersionType::Version1);
89
90 if (result.IsSuccess()) {
91 ctx.WriteBuffer(firmware_data);
92 }
93
94 IPC::ResponseBuilder rb{ctx, 2};
95 rb.Push(result);
102} 96}
103 97
104void SET_SYS::GetFirmwareVersion2(HLERequestContext& ctx) { 98void SET_SYS::GetFirmwareVersion2(HLERequestContext& ctx) {
105 LOG_DEBUG(Service_SET, "called"); 99 LOG_DEBUG(Service_SET, "called");
106 GetFirmwareVersionImpl(system, ctx, GetFirmwareVersionType::Version2); 100
101 FirmwareVersionFormat firmware_data{};
102 const auto result =
103 GetFirmwareVersionImpl(firmware_data, system, GetFirmwareVersionType::Version2);
104
105 if (result.IsSuccess()) {
106 ctx.WriteBuffer(firmware_data);
107 }
108
109 IPC::ResponseBuilder rb{ctx, 2};
110 rb.Push(result);
107} 111}
108 112
109void SET_SYS::GetAccountSettings(HLERequestContext& ctx) { 113void 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 @@
4#pragma once 4#pragma once
5 5
6#include "common/uuid.h" 6#include "common/uuid.h"
7#include "core/hle/result.h"
7#include "core/hle/service/service.h" 8#include "core/hle/service/service.h"
8#include "core/hle/service/time/clock_types.h" 9#include "core/hle/service/time/clock_types.h"
9 10
@@ -12,6 +13,29 @@ class System;
12} 13}
13 14
14namespace Service::Set { 15namespace Service::Set {
16enum class LanguageCode : u64;
17enum class GetFirmwareVersionType {
18 Version1,
19 Version2,
20};
21
22struct FirmwareVersionFormat {
23 u8 major;
24 u8 minor;
25 u8 micro;
26 INSERT_PADDING_BYTES(1);
27 u8 revision_major;
28 u8 revision_minor;
29 INSERT_PADDING_BYTES(2);
30 std::array<char, 0x20> platform;
31 std::array<u8, 0x40> version_hash;
32 std::array<char, 0x18> display_version;
33 std::array<char, 0x80> display_title;
34};
35static_assert(sizeof(FirmwareVersionFormat) == 0x100, "FirmwareVersionFormat is an invalid size");
36
37Result GetFirmwareVersionImpl(FirmwareVersionFormat& out_firmware, Core::System& system,
38 GetFirmwareVersionType type);
15 39
16class SET_SYS final : public ServiceFramework<SET_SYS> { 40class SET_SYS final : public ServiceFramework<SET_SYS> {
17public: 41public:
diff --git a/src/yuzu/main.cpp b/src/yuzu/main.cpp
index f22db233b..1848ac89f 100644
--- a/src/yuzu/main.cpp
+++ b/src/yuzu/main.cpp
@@ -47,6 +47,7 @@
47#include "core/hle/service/am/applet_ae.h" 47#include "core/hle/service/am/applet_ae.h"
48#include "core/hle/service/am/applet_oe.h" 48#include "core/hle/service/am/applet_oe.h"
49#include "core/hle/service/am/applets/applets.h" 49#include "core/hle/service/am/applets/applets.h"
50#include "core/hle/service/set/set_sys.h"
50#include "yuzu/multiplayer/state.h" 51#include "yuzu/multiplayer/state.h"
51#include "yuzu/util/controller_navigation.h" 52#include "yuzu/util/controller_navigation.h"
52 53
@@ -1047,7 +1048,12 @@ void GMainWindow::InitializeWidgets() {
1047 statusBar()->addPermanentWidget(label); 1048 statusBar()->addPermanentWidget(label);
1048 } 1049 }
1049 1050
1050 // TODO (flTobi): Add the widget when multiplayer is fully implemented 1051 firmware_label = new QLabel();
1052 firmware_label->setObjectName(QStringLiteral("FirmwareLabel"));
1053 firmware_label->setVisible(false);
1054 firmware_label->setFocusPolicy(Qt::NoFocus);
1055 statusBar()->addPermanentWidget(firmware_label);
1056
1051 statusBar()->addPermanentWidget(multiplayer_state->GetStatusText(), 0); 1057 statusBar()->addPermanentWidget(multiplayer_state->GetStatusText(), 0);
1052 statusBar()->addPermanentWidget(multiplayer_state->GetStatusIcon(), 0); 1058 statusBar()->addPermanentWidget(multiplayer_state->GetStatusIcon(), 0);
1053 1059
@@ -2161,6 +2167,10 @@ void GMainWindow::OnEmulationStopped() {
2161 emu_frametime_label->setVisible(false); 2167 emu_frametime_label->setVisible(false);
2162 renderer_status_button->setEnabled(!UISettings::values.has_broken_vulkan); 2168 renderer_status_button->setEnabled(!UISettings::values.has_broken_vulkan);
2163 2169
2170 if (!firmware_label->text().isEmpty()) {
2171 firmware_label->setVisible(true);
2172 }
2173
2164 current_game_path.clear(); 2174 current_game_path.clear();
2165 2175
2166 // When closing the game, destroy the GLWindow to clear the context after the game is closed 2176 // When closing the game, destroy the GLWindow to clear the context after the game is closed
@@ -4586,6 +4596,7 @@ void GMainWindow::UpdateStatusBar() {
4586 emu_speed_label->setVisible(!Settings::values.use_multi_core.GetValue()); 4596 emu_speed_label->setVisible(!Settings::values.use_multi_core.GetValue());
4587 game_fps_label->setVisible(true); 4597 game_fps_label->setVisible(true);
4588 emu_frametime_label->setVisible(true); 4598 emu_frametime_label->setVisible(true);
4599 firmware_label->setVisible(false);
4589} 4600}
4590 4601
4591void GMainWindow::UpdateGPUAccuracyButton() { 4602void GMainWindow::UpdateGPUAccuracyButton() {
@@ -4803,6 +4814,8 @@ void GMainWindow::OnReinitializeKeys(ReinitializeKeyBehavior behavior) {
4803 "games.")); 4814 "games."));
4804 } 4815 }
4805 4816
4817 SetFirmwareVersion();
4818
4806 if (behavior == ReinitializeKeyBehavior::Warning) { 4819 if (behavior == ReinitializeKeyBehavior::Warning) {
4807 game_list->PopulateAsync(UISettings::values.game_dirs); 4820 game_list->PopulateAsync(UISettings::values.game_dirs);
4808 } 4821 }
@@ -4830,7 +4843,7 @@ bool GMainWindow::CheckSystemArchiveDecryption() {
4830} 4843}
4831 4844
4832bool GMainWindow::CheckFirmwarePresence() { 4845bool GMainWindow::CheckFirmwarePresence() {
4833 constexpr u64 MiiEditId = 0x0100000000001009ull; 4846 constexpr u64 MiiEditId = static_cast<u64>(Service::AM::Applets::AppletProgramId::MiiEdit);
4834 4847
4835 auto bis_system = system->GetFileSystemController().GetSystemNANDContents(); 4848 auto bis_system = system->GetFileSystemController().GetSystemNANDContents();
4836 if (!bis_system) { 4849 if (!bis_system) {
@@ -4845,6 +4858,28 @@ bool GMainWindow::CheckFirmwarePresence() {
4845 return true; 4858 return true;
4846} 4859}
4847 4860
4861void GMainWindow::SetFirmwareVersion() {
4862 Service::Set::FirmwareVersionFormat firmware_data{};
4863 const auto result = Service::Set::GetFirmwareVersionImpl(
4864 firmware_data, *system, Service::Set::GetFirmwareVersionType::Version2);
4865
4866 if (result.IsError() || !CheckFirmwarePresence()) {
4867 LOG_INFO(Frontend, "Installed firmware: No firmware available");
4868 firmware_label->setVisible(false);
4869 return;
4870 }
4871
4872 firmware_label->setVisible(true);
4873
4874 const std::string display_version(firmware_data.display_version.data());
4875 const std::string display_title(firmware_data.display_title.data());
4876
4877 LOG_INFO(Frontend, "Installed firmware: {}", display_title);
4878
4879 firmware_label->setText(QString::fromStdString(display_version));
4880 firmware_label->setToolTip(QString::fromStdString(display_title));
4881}
4882
4848bool GMainWindow::SelectRomFSDumpTarget(const FileSys::ContentProvider& installed, u64 program_id, 4883bool GMainWindow::SelectRomFSDumpTarget(const FileSys::ContentProvider& installed, u64 program_id,
4849 u64* selected_title_id, u8* selected_content_record_type) { 4884 u64* selected_title_id, u8* selected_content_record_type) {
4850 using ContentInfo = std::tuple<u64, FileSys::TitleType, FileSys::ContentRecordType>; 4885 using ContentInfo = std::tuple<u64, FileSys::TitleType, FileSys::ContentRecordType>;
diff --git a/src/yuzu/main.h b/src/yuzu/main.h
index 49ee1e1d2..0c8b7606d 100644
--- a/src/yuzu/main.h
+++ b/src/yuzu/main.h
@@ -457,6 +457,7 @@ private:
457 bool CheckDarkMode(); 457 bool CheckDarkMode();
458 bool CheckSystemArchiveDecryption(); 458 bool CheckSystemArchiveDecryption();
459 bool CheckFirmwarePresence(); 459 bool CheckFirmwarePresence();
460 void SetFirmwareVersion();
460 void ConfigureFilesystemProvider(const std::string& filepath); 461 void ConfigureFilesystemProvider(const std::string& filepath);
461 /** 462 /**
462 * Open (or not) the right confirm dialog based on current setting and game exit lock 463 * Open (or not) the right confirm dialog based on current setting and game exit lock
@@ -511,6 +512,7 @@ private:
511 QLabel* game_fps_label = nullptr; 512 QLabel* game_fps_label = nullptr;
512 QLabel* emu_frametime_label = nullptr; 513 QLabel* emu_frametime_label = nullptr;
513 QLabel* tas_label = nullptr; 514 QLabel* tas_label = nullptr;
515 QLabel* firmware_label = nullptr;
514 QPushButton* gpu_accuracy_button = nullptr; 516 QPushButton* gpu_accuracy_button = nullptr;
515 QPushButton* renderer_status_button = nullptr; 517 QPushButton* renderer_status_button = nullptr;
516 QPushButton* dock_status_button = nullptr; 518 QPushButton* dock_status_button = nullptr;