mirror of
				https://git.suyu.dev/suyu/suyu
				synced 2025-10-28 22:49:02 -05:00 
			
		
		
		
	Merge pull request #2855 from bunnei/telemetry-additional-fields
Telemetry: Add several more useful fields
This commit is contained in:
		| @@ -295,11 +295,18 @@ function(create_directory_groups) | |||||||
|     endforeach() |     endforeach() | ||||||
| endfunction() | endfunction() | ||||||
|  |  | ||||||
| # generate git revision information | # Gets a UTC timstamp and sets the provided variable to it | ||||||
|  | function(get_timestamp _var) | ||||||
|  |     string(TIMESTAMP timestamp UTC) | ||||||
|  |     set(${_var} "${timestamp}" PARENT_SCOPE) | ||||||
|  | endfunction() | ||||||
|  |  | ||||||
|  | # generate git/build information | ||||||
| include(GetGitRevisionDescription) | include(GetGitRevisionDescription) | ||||||
| get_git_head_revision(GIT_REF_SPEC GIT_REV) | get_git_head_revision(GIT_REF_SPEC GIT_REV) | ||||||
| git_describe(GIT_DESC --always --long --dirty) | git_describe(GIT_DESC --always --long --dirty) | ||||||
| git_branch_name(GIT_BRANCH) | git_branch_name(GIT_BRANCH) | ||||||
|  | get_timestamp(BUILD_DATE) | ||||||
|  |  | ||||||
| enable_testing() | enable_testing() | ||||||
| add_subdirectory(externals) | add_subdirectory(externals) | ||||||
|   | |||||||
| @@ -8,6 +8,7 @@ | |||||||
| #define GIT_BRANCH   "@GIT_BRANCH@" | #define GIT_BRANCH   "@GIT_BRANCH@" | ||||||
| #define GIT_DESC     "@GIT_DESC@" | #define GIT_DESC     "@GIT_DESC@" | ||||||
| #define BUILD_NAME   "@REPO_NAME@" | #define BUILD_NAME   "@REPO_NAME@" | ||||||
|  | #define BUILD_DATE   "@BUILD_DATE@" | ||||||
|  |  | ||||||
| namespace Common { | namespace Common { | ||||||
|  |  | ||||||
| @@ -15,6 +16,7 @@ const char g_scm_rev[]      = GIT_REV; | |||||||
| const char g_scm_branch[]   = GIT_BRANCH; | const char g_scm_branch[]   = GIT_BRANCH; | ||||||
| const char g_scm_desc[]     = GIT_DESC; | const char g_scm_desc[]     = GIT_DESC; | ||||||
| const char g_build_name[]   = BUILD_NAME; | const char g_build_name[]   = BUILD_NAME; | ||||||
|  | const char g_build_date[]   = BUILD_DATE; | ||||||
|  |  | ||||||
| } // namespace | } // namespace | ||||||
|  |  | ||||||
|   | |||||||
| @@ -10,5 +10,6 @@ extern const char g_scm_rev[]; | |||||||
| extern const char g_scm_branch[]; | extern const char g_scm_branch[]; | ||||||
| extern const char g_scm_desc[]; | extern const char g_scm_desc[]; | ||||||
| extern const char g_build_name[]; | extern const char g_build_name[]; | ||||||
|  | extern const char g_build_date[]; | ||||||
|  |  | ||||||
| } // namespace | } // namespace | ||||||
|   | |||||||
| @@ -7,6 +7,7 @@ | |||||||
| #include <memory> | #include <memory> | ||||||
| #include <string> | #include <string> | ||||||
| #include "common/common_types.h" | #include "common/common_types.h" | ||||||
|  | #include "core/loader/loader.h" | ||||||
| #include "core/memory.h" | #include "core/memory.h" | ||||||
| #include "core/perf_stats.h" | #include "core/perf_stats.h" | ||||||
| #include "core/telemetry_session.h" | #include "core/telemetry_session.h" | ||||||
| @@ -14,10 +15,6 @@ | |||||||
| class EmuWindow; | class EmuWindow; | ||||||
| class ARM_Interface; | class ARM_Interface; | ||||||
|  |  | ||||||
| namespace Loader { |  | ||||||
| class AppLoader; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| namespace Core { | namespace Core { | ||||||
|  |  | ||||||
| class System { | class System { | ||||||
| @@ -119,6 +116,10 @@ public: | |||||||
|         return status_details; |         return status_details; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     Loader::AppLoader& GetAppLoader() const { | ||||||
|  |         return *app_loader; | ||||||
|  |     } | ||||||
|  |  | ||||||
| private: | private: | ||||||
|     /** |     /** | ||||||
|      * Initialize the emulated system. |      * Initialize the emulated system. | ||||||
|   | |||||||
| @@ -75,6 +75,10 @@ void Initialize(Service::Interface* self) { | |||||||
| void GetSharedFont(Service::Interface* self) { | void GetSharedFont(Service::Interface* self) { | ||||||
|     IPC::RequestParser rp(Kernel::GetCommandBuffer(), 0x44, 0, 0); // 0x00440000 |     IPC::RequestParser rp(Kernel::GetCommandBuffer(), 0x44, 0, 0); // 0x00440000 | ||||||
|     IPC::RequestBuilder rb = rp.MakeBuilder(2, 2); |     IPC::RequestBuilder rb = rp.MakeBuilder(2, 2); | ||||||
|  |  | ||||||
|  |     // Log in telemetry if the game uses the shared font | ||||||
|  |     Core::Telemetry().AddField(Telemetry::FieldType::Session, "RequiresSharedFont", true); | ||||||
|  |  | ||||||
|     if (!shared_font_loaded) { |     if (!shared_font_loaded) { | ||||||
|         LOG_ERROR(Service_APT, "shared font file missing - go dump it from your 3ds"); |         LOG_ERROR(Service_APT, "shared font file missing - go dump it from your 3ds"); | ||||||
|         rb.Push<u32>(-1); // TODO: Find the right error code |         rb.Push<u32>(-1); // TODO: Find the right error code | ||||||
|   | |||||||
| @@ -166,6 +166,15 @@ public: | |||||||
|         return ResultStatus::ErrorNotImplemented; |         return ResultStatus::ErrorNotImplemented; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     /** | ||||||
|  |      * Get the title of the application | ||||||
|  |      * @param title Reference to store the application title into | ||||||
|  |      * @return ResultStatus result of function | ||||||
|  |      */ | ||||||
|  |     virtual ResultStatus ReadTitle(std::string& title) { | ||||||
|  |         return ResultStatus::ErrorNotImplemented; | ||||||
|  |     } | ||||||
|  |  | ||||||
| protected: | protected: | ||||||
|     FileUtil::IOFile file; |     FileUtil::IOFile file; | ||||||
|     bool is_loaded = false; |     bool is_loaded = false; | ||||||
|   | |||||||
| @@ -4,7 +4,9 @@ | |||||||
|  |  | ||||||
| #include <algorithm> | #include <algorithm> | ||||||
| #include <cinttypes> | #include <cinttypes> | ||||||
|  | #include <codecvt> | ||||||
| #include <cstring> | #include <cstring> | ||||||
|  | #include <locale> | ||||||
| #include <memory> | #include <memory> | ||||||
| #include "common/logging/log.h" | #include "common/logging/log.h" | ||||||
| #include "common/string_util.h" | #include "common/string_util.h" | ||||||
| @@ -420,4 +422,22 @@ ResultStatus AppLoader_NCCH::ReadRomFS(std::shared_ptr<FileUtil::IOFile>& romfs_ | |||||||
|     return ResultStatus::ErrorNotUsed; |     return ResultStatus::ErrorNotUsed; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | ResultStatus AppLoader_NCCH::ReadTitle(std::string& title) { | ||||||
|  |     std::vector<u8> data; | ||||||
|  |     Loader::SMDH smdh; | ||||||
|  |     ReadIcon(data); | ||||||
|  |  | ||||||
|  |     if (!Loader::IsValidSMDH(data)) { | ||||||
|  |         return ResultStatus::ErrorInvalidFormat; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     memcpy(&smdh, data.data(), sizeof(Loader::SMDH)); | ||||||
|  |  | ||||||
|  |     const auto& short_title = smdh.GetShortTitle(SMDH::TitleLanguage::English); | ||||||
|  |     auto title_end = std::find(short_title.begin(), short_title.end(), u'\0'); | ||||||
|  |     title = Common::UTF16ToUTF8(std::u16string{short_title.begin(), title_end}); | ||||||
|  |  | ||||||
|  |     return ResultStatus::Success; | ||||||
|  | } | ||||||
|  |  | ||||||
| } // namespace Loader | } // namespace Loader | ||||||
|   | |||||||
| @@ -191,23 +191,13 @@ public: | |||||||
|  |  | ||||||
|     ResultStatus ReadLogo(std::vector<u8>& buffer) override; |     ResultStatus ReadLogo(std::vector<u8>& buffer) override; | ||||||
|  |  | ||||||
|     /** |  | ||||||
|      * Get the program id of the application |  | ||||||
|      * @param out_program_id Reference to store program id into |  | ||||||
|      * @return ResultStatus result of function |  | ||||||
|      */ |  | ||||||
|     ResultStatus ReadProgramId(u64& out_program_id) override; |     ResultStatus ReadProgramId(u64& out_program_id) override; | ||||||
|  |  | ||||||
|     /** |  | ||||||
|      * Get the RomFS of the application |  | ||||||
|      * @param romfs_file Reference to buffer to store data |  | ||||||
|      * @param offset     Offset in the file to the RomFS |  | ||||||
|      * @param size       Size of the RomFS in bytes |  | ||||||
|      * @return ResultStatus result of function |  | ||||||
|      */ |  | ||||||
|     ResultStatus ReadRomFS(std::shared_ptr<FileUtil::IOFile>& romfs_file, u64& offset, |     ResultStatus ReadRomFS(std::shared_ptr<FileUtil::IOFile>& romfs_file, u64& offset, | ||||||
|                            u64& size) override; |                            u64& size) override; | ||||||
|  |  | ||||||
|  |     ResultStatus ReadTitle(std::string& title) override; | ||||||
|  |  | ||||||
| private: | private: | ||||||
|     /** |     /** | ||||||
|      * Reads an application ExeFS section of an NCCH file into AppLoader (e.g. .code, .logo, etc.) |      * Reads an application ExeFS section of an NCCH file into AppLoader (e.g. .code, .logo, etc.) | ||||||
|   | |||||||
| @@ -7,6 +7,7 @@ | |||||||
| #include "common/assert.h" | #include "common/assert.h" | ||||||
| #include "common/scm_rev.h" | #include "common/scm_rev.h" | ||||||
| #include "common/x64/cpu_detect.h" | #include "common/x64/cpu_detect.h" | ||||||
|  | #include "core/core.h" | ||||||
| #include "core/settings.h" | #include "core/settings.h" | ||||||
| #include "core/telemetry_session.h" | #include "core/telemetry_session.h" | ||||||
|  |  | ||||||
| @@ -39,12 +40,19 @@ TelemetrySession::TelemetrySession() { | |||||||
|                             std::chrono::system_clock::now().time_since_epoch()) |                             std::chrono::system_clock::now().time_since_epoch()) | ||||||
|                             .count()}; |                             .count()}; | ||||||
|     AddField(Telemetry::FieldType::Session, "Init_Time", init_time); |     AddField(Telemetry::FieldType::Session, "Init_Time", init_time); | ||||||
|  |     std::string program_name; | ||||||
|  |     const Loader::ResultStatus res{System::GetInstance().GetAppLoader().ReadTitle(program_name)}; | ||||||
|  |     if (res == Loader::ResultStatus::Success) { | ||||||
|  |         AddField(Telemetry::FieldType::Session, "ProgramName", program_name); | ||||||
|  |     } | ||||||
|  |  | ||||||
|     // Log application information |     // Log application information | ||||||
|     const bool is_git_dirty{std::strstr(Common::g_scm_desc, "dirty") != nullptr}; |     const bool is_git_dirty{std::strstr(Common::g_scm_desc, "dirty") != nullptr}; | ||||||
|     AddField(Telemetry::FieldType::App, "Git_IsDirty", is_git_dirty); |     AddField(Telemetry::FieldType::App, "Git_IsDirty", is_git_dirty); | ||||||
|     AddField(Telemetry::FieldType::App, "Git_Branch", Common::g_scm_branch); |     AddField(Telemetry::FieldType::App, "Git_Branch", Common::g_scm_branch); | ||||||
|     AddField(Telemetry::FieldType::App, "Git_Revision", Common::g_scm_rev); |     AddField(Telemetry::FieldType::App, "Git_Revision", Common::g_scm_rev); | ||||||
|  |     AddField(Telemetry::FieldType::App, "BuildDate", Common::g_build_date); | ||||||
|  |     AddField(Telemetry::FieldType::App, "BuildName", Common::g_build_name); | ||||||
|  |  | ||||||
|     // Log user system information |     // Log user system information | ||||||
|     AddField(Telemetry::FieldType::UserSystem, "CPU_Model", Common::GetCPUCaps().cpu_string); |     AddField(Telemetry::FieldType::UserSystem, "CPU_Model", Common::GetCPUCaps().cpu_string); | ||||||
| @@ -68,6 +76,15 @@ TelemetrySession::TelemetrySession() { | |||||||
|              Common::GetCPUCaps().sse4_1); |              Common::GetCPUCaps().sse4_1); | ||||||
|     AddField(Telemetry::FieldType::UserSystem, "CPU_Extension_x64_SSE42", |     AddField(Telemetry::FieldType::UserSystem, "CPU_Extension_x64_SSE42", | ||||||
|              Common::GetCPUCaps().sse4_2); |              Common::GetCPUCaps().sse4_2); | ||||||
|  | #ifdef __APPLE__ | ||||||
|  |     AddField(Telemetry::FieldType::UserSystem, "OsPlatform", "Apple"); | ||||||
|  | #elif defined(_WIN32) | ||||||
|  |     AddField(Telemetry::FieldType::UserSystem, "OsPlatform", "Windows"); | ||||||
|  | #elif defined(__linux__) || defined(linux) || defined(__linux) | ||||||
|  |     AddField(Telemetry::FieldType::UserSystem, "OsPlatform", "Linux"); | ||||||
|  | #else | ||||||
|  |     AddField(Telemetry::FieldType::UserSystem, "OsPlatform", "Unknown"); | ||||||
|  | #endif | ||||||
|  |  | ||||||
|     // Log user configuration information |     // Log user configuration information | ||||||
|     AddField(Telemetry::FieldType::UserConfig, "Audio_EnableAudioStretching", |     AddField(Telemetry::FieldType::UserConfig, "Audio_EnableAudioStretching", | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 James Rowe
					James Rowe