diff --git a/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp b/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp index 8e07340622..990ef2aef5 100644 --- a/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp +++ b/rpcs3/Emu/Cell/Modules/sceNpTrophy.cpp @@ -819,9 +819,19 @@ error_code sceNpTrophyUnlockTrophy(u32 context, u32 handle, s32 trophyId, vm::pt } if (trophyId < 0 || trophyId >= static_cast(ctxt->tropusr->GetTrophiesCount())) + { return SCE_NP_TROPHY_ERROR_INVALID_TROPHY_ID; + } + + if (ctxt->tropusr->GetTrophyGrade(trophyId) == SCE_NP_TROPHY_GRADE_PLATINUM) + { + return SCE_NP_TROPHY_ERROR_CANNOT_UNLOCK_PLATINUM; + } + if (ctxt->tropusr->GetTrophyUnlockState(trophyId)) + { return SCE_NP_TROPHY_ERROR_ALREADY_UNLOCKED; + } ctxt->tropusr->UnlockTrophy(trophyId, 0, 0); // TODO: add timestamps diff --git a/rpcs3/Loader/TROPUSR.cpp b/rpcs3/Loader/TROPUSR.cpp index 7a57df8b54..60d79d235a 100644 --- a/rpcs3/Loader/TROPUSR.cpp +++ b/rpcs3/Loader/TROPUSR.cpp @@ -291,6 +291,17 @@ u32 TROPUSRLoader::GetUnlockedPlatinumID(u32 trophy_id, const std::string& confi return pid; } +u32 TROPUSRLoader::GetTrophyGrade(u32 id) +{ + if (id >= m_table4.size()) + { + LOG_WARNING(LOADER, "TROPUSRLoader::GetTrophyGrade: Invalid id=%d", id); + return trophy_grade::unknown; + } + + return m_table4[id].trophy_grade; // Let's assume the trophies are stored ordered +} + u32 TROPUSRLoader::GetTrophyUnlockState(u32 id) { if (id >= m_table6.size()) diff --git a/rpcs3/Loader/TROPUSR.h b/rpcs3/Loader/TROPUSR.h index 5e5b037b52..2ecc92238e 100644 --- a/rpcs3/Loader/TROPUSR.h +++ b/rpcs3/Loader/TROPUSR.h @@ -86,6 +86,7 @@ public: virtual u32 GetUnlockedPlatinumID(u32 trophy_id, const std::string& config_path); + virtual u32 GetTrophyGrade(u32 id); virtual u32 GetTrophyUnlockState(u32 id); virtual u64 GetTrophyTimestamp(u32 id);