mirror of
https://github.com/shadps4-emu/shadPS4.git
synced 2025-04-20 19:44:46 +00:00
Applied Turtle's feedback (Thanks good teacher)
This commit is contained in:
parent
337b5413c6
commit
dd4f4866cc
8 changed files with 78 additions and 110 deletions
|
@ -135,17 +135,17 @@ public:
|
|||
return (variable) & static_cast<u32>(flag);
|
||||
}
|
||||
|
||||
std::vector<std::pair<PKGContentFlag, std::string>> flagNames = {
|
||||
{PKGContentFlag::FIRST_PATCH, "FIRST_PATCH"},
|
||||
{PKGContentFlag::PATCHGO, "PATCHGO"},
|
||||
{PKGContentFlag::REMASTER, "REMASTER"},
|
||||
{PKGContentFlag::PS_CLOUD, "PS_CLOUD"},
|
||||
{PKGContentFlag::GD_AC, "GD_AC"},
|
||||
{PKGContentFlag::NON_GAME, "NON_GAME"},
|
||||
{PKGContentFlag::UNKNOWN_0x8000000, "UNKNOWN_0x8000000"},
|
||||
{PKGContentFlag::SUBSEQUENT_PATCH, "SUBSEQUENT_PATCH"},
|
||||
{PKGContentFlag::DELTA_PATCH, "DELTA_PATCH"},
|
||||
{PKGContentFlag::CUMULATIVE_PATCH, "CUMULATIVE_PATCH"}};
|
||||
static constexpr std::array<std::pair<PKGContentFlag, std::string_view>, 10> flagNames = {
|
||||
{{PKGContentFlag::FIRST_PATCH, "FIRST_PATCH"},
|
||||
{PKGContentFlag::PATCHGO, "PATCHGO"},
|
||||
{PKGContentFlag::REMASTER, "REMASTER"},
|
||||
{PKGContentFlag::PS_CLOUD, "PS_CLOUD"},
|
||||
{PKGContentFlag::GD_AC, "GD_AC"},
|
||||
{PKGContentFlag::NON_GAME, "NON_GAME"},
|
||||
{PKGContentFlag::UNKNOWN_0x8000000, "UNKNOWN_0x8000000"},
|
||||
{PKGContentFlag::SUBSEQUENT_PATCH, "SUBSEQUENT_PATCH"},
|
||||
{PKGContentFlag::DELTA_PATCH, "DELTA_PATCH"},
|
||||
{PKGContentFlag::CUMULATIVE_PATCH, "CUMULATIVE_PATCH"}}};
|
||||
|
||||
private:
|
||||
Crypto crypto;
|
||||
|
|
|
@ -14,15 +14,9 @@ PSF::~PSF() = default;
|
|||
|
||||
bool PSF::open(const std::string& filepath, std::vector<u8> psfBuffer) {
|
||||
if (!psfBuffer.empty()) {
|
||||
psf.clear();
|
||||
map_integers.clear();
|
||||
map_strings.clear();
|
||||
psf.resize(psfBuffer.size());
|
||||
psf = psfBuffer;
|
||||
} else {
|
||||
psf.clear();
|
||||
map_integers.clear();
|
||||
map_strings.clear();
|
||||
Common::FS::IOFile file(filepath, Common::FS::FileAccessMode::Read);
|
||||
if (!file.IsOpen()) {
|
||||
return false;
|
||||
|
|
|
@ -6,20 +6,15 @@
|
|||
TRP::TRP() = default;
|
||||
TRP::~TRP() = default;
|
||||
|
||||
void TRP::GetNPcommID(std::filesystem::path trophyPath, int fileNbr) {
|
||||
void TRP::GetNPcommID(std::filesystem::path trophyPath, int index) {
|
||||
std::filesystem::path trpPath = trophyPath / "sce_sys/npbind.dat";
|
||||
Common::FS::IOFile npbindFile(trpPath, Common::FS::FileAccessMode::Read);
|
||||
if (!npbindFile.IsOpen()) {
|
||||
return;
|
||||
}
|
||||
for (int i = 0; i < fileNbr; i++) {
|
||||
std::vector<u8> vec(12);
|
||||
npbindFile.Seek(0x84 + (i * 0x180));
|
||||
npbindFile.Read(vec);
|
||||
vec.resize(16);
|
||||
NPcommID.push_back(vec);
|
||||
}
|
||||
npbindFile.Close();
|
||||
npbindFile.Seek(0x84 + (index * 0x180));
|
||||
npbindFile.Read(NPcommID);
|
||||
NPcommID.resize(16);
|
||||
}
|
||||
|
||||
void TRP::removePadding(std::vector<u8>& vec) {
|
||||
|
@ -39,81 +34,63 @@ bool TRP::Extract(std::filesystem::path trophyPath) {
|
|||
return false;
|
||||
}
|
||||
std::vector<std::filesystem::path> fileList;
|
||||
for (const auto& entry : std::filesystem::directory_iterator(gameSysDir)) {
|
||||
if (entry.is_regular_file()) {
|
||||
fileList.push_back(entry.path());
|
||||
}
|
||||
}
|
||||
for (int index = 0; const auto& it : std::filesystem::directory_iterator(gameSysDir)) {
|
||||
if (it.is_regular_file()) {
|
||||
GetNPcommID(trophyPath, index);
|
||||
|
||||
if (fileList.empty())
|
||||
return false;
|
||||
|
||||
GetNPcommID(trophyPath, fileList.size());
|
||||
for (int nbr = 0; const std::filesystem::path& fileinfo : fileList) {
|
||||
std::string multiTrp = fileinfo.stem().string();
|
||||
|
||||
Common::FS::IOFile file(fileinfo, Common::FS::FileAccessMode::Read);
|
||||
if (!file.IsOpen()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
trp_header header;
|
||||
file.ReadRaw<u8>(&header, sizeof(trp_header));
|
||||
|
||||
if (header.magic != 0xDCA24D00)
|
||||
return false;
|
||||
|
||||
s64 seekPos = sizeof(trp_header);
|
||||
std::filesystem::path trpFilesPath(std::filesystem::current_path() / "game_data" / title);
|
||||
std::filesystem::path multiPath(trpFilesPath / "TrophyFiles");
|
||||
if (fileList.size() > 1) {
|
||||
multiPath = trpFilesPath / "TrophyFiles" / multiTrp;
|
||||
}
|
||||
std::filesystem::create_directories(multiPath / "Icons");
|
||||
|
||||
for (int i = 0; i < header.entry_num; i++) {
|
||||
file.Seek(seekPos);
|
||||
seekPos += (s64)header.entry_size;
|
||||
trp_entry entry;
|
||||
file.ReadRaw<u8>(&entry, sizeof(trp_entry));
|
||||
std::string name(entry.entry_name);
|
||||
if (entry.flag == 0 && name.find("TROP") != std::string::npos) { // PNG
|
||||
file.Seek(entry.entry_pos);
|
||||
std::vector<u8> icon(entry.entry_len);
|
||||
file.Read(icon);
|
||||
|
||||
Common::FS::IOFile out(multiPath / "Icons" / name,
|
||||
Common::FS::FileAccessMode::Write);
|
||||
out.Write(icon);
|
||||
out.Close();
|
||||
Common::FS::IOFile file(it.path(), Common::FS::FileAccessMode::Read);
|
||||
if (!file.IsOpen()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (entry.flag == 3 && NPcommID.at(nbr)[0] == 'N' &&
|
||||
NPcommID.at(nbr)[1] == 'P') { // ESFM, encrypted.
|
||||
file.Seek(entry.entry_pos);
|
||||
efsmIv.resize(16);
|
||||
file.Read(efsmIv); // get iv key.
|
||||
TrpHeader header;
|
||||
file.Read(header);
|
||||
if (header.magic != 0xDCA24D00)
|
||||
return false;
|
||||
|
||||
std::vector<u8> ESFM(entry.entry_len - 16);
|
||||
std::vector<u8> XML(entry.entry_len - 16);
|
||||
XML.reserve(entry.entry_len - 16);
|
||||
file.Seek(entry.entry_pos + 16);
|
||||
file.ReadRaw<u8>(ESFM.data(), entry.entry_len - 16);
|
||||
s64 seekPos = sizeof(TrpHeader);
|
||||
std::filesystem::path trpFilesPath(std::filesystem::current_path() / "game_data" /
|
||||
title / "TrophyFiles" / it.path().stem());
|
||||
std::filesystem::create_directories(trpFilesPath / "Icons");
|
||||
std::filesystem::create_directory(trpFilesPath / "Xml");
|
||||
|
||||
crypto.decryptEFSM(NPcommID.at(nbr), efsmIv, ESFM, XML); // decrypt
|
||||
ESFM.clear();
|
||||
removePadding(XML);
|
||||
std::string xml_name = name;
|
||||
size_t pos = xml_name.find("ESFM");
|
||||
if (pos != std::string::npos)
|
||||
xml_name.replace(pos, xml_name.length(), "XML");
|
||||
Common::FS::IOFile out(multiPath / xml_name, Common::FS::FileAccessMode::Write);
|
||||
out.Write(XML);
|
||||
out.Close();
|
||||
for (int i = 0; i < header.entry_num; i++) {
|
||||
file.Seek(seekPos);
|
||||
seekPos += (s64)header.entry_size;
|
||||
TrpEntry entry;
|
||||
file.Read(entry);
|
||||
std::string_view name(entry.entry_name);
|
||||
if (entry.flag == 0 && name.find("TROP") != std::string::npos) { // PNG
|
||||
file.Seek(entry.entry_pos);
|
||||
std::vector<u8> icon(entry.entry_len);
|
||||
file.Read(icon);
|
||||
|
||||
Common::FS::IOFile out(trpFilesPath / "Icons" / name,
|
||||
Common::FS::FileAccessMode::Write);
|
||||
out.Write(icon);
|
||||
out.Close();
|
||||
}
|
||||
if (entry.flag == 3 && NPcommID[0] == 'N' &&
|
||||
NPcommID[1] == 'P') { // ESFM, encrypted.
|
||||
file.Seek(entry.entry_pos);
|
||||
file.Read(efsmIv); // get iv key.
|
||||
std::vector<u8> ESFM(entry.entry_len - 16);
|
||||
std::vector<u8> XML(entry.entry_len - 16);
|
||||
file.Seek(entry.entry_pos + 16);
|
||||
file.Read(ESFM);
|
||||
crypto.decryptEFSM(NPcommID, efsmIv, ESFM, XML); // decrypt
|
||||
removePadding(XML);
|
||||
std::string xml_name = entry.entry_name;
|
||||
size_t pos = xml_name.find("ESFM");
|
||||
if (pos != std::string::npos)
|
||||
xml_name.replace(pos, xml_name.length(), "XML");
|
||||
Common::FS::IOFile out(trpFilesPath / "Xml" / xml_name,
|
||||
Common::FS::FileAccessMode::Write);
|
||||
out.Write(XML);
|
||||
}
|
||||
}
|
||||
}
|
||||
file.Close();
|
||||
nbr++;
|
||||
index++;
|
||||
}
|
||||
return true;
|
||||
}
|
|
@ -5,11 +5,11 @@
|
|||
|
||||
#include <vector>
|
||||
#include "common/endian.h"
|
||||
#include "common/io_file.h"
|
||||
#include "common/types.h"
|
||||
#include "core/crypto/crypto.h"
|
||||
#include "src/common/io_file.h"
|
||||
#include "src/common/types.h"
|
||||
|
||||
struct trp_header {
|
||||
struct TrpHeader {
|
||||
u32_be magic; // (0xDCA24D00)
|
||||
u32_be version;
|
||||
u64_be file_size; // size of full trp file
|
||||
|
@ -21,7 +21,7 @@ struct trp_header {
|
|||
unsigned char padding[44];
|
||||
};
|
||||
|
||||
struct trp_entry {
|
||||
struct TrpEntry {
|
||||
char entry_name[32];
|
||||
u64_be entry_pos;
|
||||
u64_be entry_len;
|
||||
|
@ -34,12 +34,12 @@ public:
|
|||
TRP();
|
||||
~TRP();
|
||||
bool Extract(std::filesystem::path trophyPath);
|
||||
void GetNPcommID(std::filesystem::path trophyPath, int fileNbr);
|
||||
void GetNPcommID(std::filesystem::path trophyPath, int index);
|
||||
void removePadding(std::vector<u8>& vec);
|
||||
|
||||
private:
|
||||
Crypto crypto;
|
||||
std::vector<std::vector<CryptoPP::byte>> NPcommID;
|
||||
std::vector<CryptoPP::byte> efsmIv;
|
||||
std::vector<u8> NPcommID = std::vector<u8>(12);
|
||||
std::vector<u8> efsmIv = std::vector<u8>(16);
|
||||
std::filesystem::path trpFilesPath;
|
||||
};
|
|
@ -53,7 +53,7 @@ void ElfViewer::OpenElfFolder() {
|
|||
m_elf_list.append(fileInfo.absoluteFilePath());
|
||||
}
|
||||
}
|
||||
std::sort(m_elf_list.begin(), m_elf_list.end());
|
||||
std::ranges::sort(m_elf_list);
|
||||
OpenElfFiles();
|
||||
dir_list_std.clear();
|
||||
for (auto dir : dir_list) {
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <ranges>
|
||||
#include <QApplication>
|
||||
#include <QFileDialog>
|
||||
#include <QMainWindow>
|
||||
|
|
|
@ -124,7 +124,7 @@ void PKGViewer::ProcessPKGInfo() {
|
|||
if (package.isFlagSet(pkg_content_flag, flag.first)) {
|
||||
if (!flagss.isEmpty())
|
||||
flagss += (", ");
|
||||
flagss += QString::fromStdString(flag.second);
|
||||
flagss += QString::fromStdString(flag.second.data());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -33,13 +33,9 @@ void TrophyViewer::PopulateTrophyWidget(QString title) {
|
|||
if (dirList.isEmpty())
|
||||
return;
|
||||
|
||||
QString tabName = "trophy00";
|
||||
for (const QFileInfo& dirInfo : dirList) {
|
||||
QString trpDir = trophyDir;
|
||||
if (dirList.size() > 1) {
|
||||
tabName = dirInfo.completeBaseName();
|
||||
trpDir += "/" + tabName;
|
||||
}
|
||||
QString tabName = dirInfo.fileName();
|
||||
QString trpDir = trophyDir + "/" + tabName;
|
||||
|
||||
QString iconsPath = trpDir + "/Icons";
|
||||
QDir iconsDir(iconsPath);
|
||||
|
@ -60,7 +56,7 @@ void TrophyViewer::PopulateTrophyWidget(QString title) {
|
|||
QStringList trophyNames;
|
||||
QStringList trophyDetails;
|
||||
|
||||
QString xmlPath = trpDir + "/TROP.XML";
|
||||
QString xmlPath = trpDir + "/Xml/TROP.XML";
|
||||
QFile file(xmlPath);
|
||||
if (!file.open(QFile::ReadOnly | QFile::Text)) {
|
||||
return;
|
||||
|
|
Loading…
Add table
Reference in a new issue