#include "loader/symbolDatabase.h" #include "common/file.h" #include "common/magicEnum.h" #include namespace Loader { constexpr char LIB_PREFIX[] = "libSce"; static std::string UpdateName(const std::string& str) { return Common::StartsWith(str, LIB_PREFIX) ? Common::RemoveFirst(str, 6) : str; } std::string SymbolDatabase::GenerateName(const SymbolResolve& s) { auto library = UpdateName(s.library); auto module = UpdateName(s.module); return fmt::format("{}[{}_v{}][{}_v{}.{}][{}]", s.name.c_str(), library.c_str(), s.library_version, module.c_str(), s.module_version_major, s.module_version_minor, Common::EnumName(s.type).c_str()); } void SymbolDatabase::Add(const SymbolResolve& s, uint64_t vaddr) { SymbolRecord r {}; r.name = GenerateName(s); r.vaddr = vaddr; m_map.insert_or_assign(r.name, m_symbols.size()); m_symbols.push_back(r); } void SymbolDatabase::Add(const SymbolResolve& s, uint64_t vaddr, const std::string& dbg_name) { SymbolRecord r {}; r.name = GenerateName(s); r.vaddr = vaddr; r.dbg_name = dbg_name; m_map.insert_or_assign(r.name, m_symbols.size()); m_symbols.push_back(r); } void SymbolDatabase::DbgDump(const std::string& folder, const std::string& file_name) { auto folder_str = Common::FixDirectorySlash(folder); Common::File::CreateDirectories(folder_str); Common::File f; f.Create(folder_str + file_name); for (const auto& sym: m_symbols) { f.Printf("%" PRIx64 " %s\n", sym.vaddr, sym.name.c_str()); } f.Close(); } const SymbolRecord* SymbolDatabase::Find(const SymbolResolve& s) const { auto it = m_map.find(GenerateName(s)); if (it == m_map.end()) { return nullptr; } auto index = it->second; if (index >= m_symbols.size()) { return nullptr; } return &m_symbols[index]; } const SymbolRecord* SymbolDatabase::FindByNid(const std::string& nid, SymbolType type) const { auto prefix = nid + "["; auto suffix = fmt::format("[{}]", Common::EnumName(type).c_str()); for (const auto& symbol: m_symbols) { if (Common::StartsWith(symbol.name, prefix) && Common::EndsWith(symbol.name, suffix)) { return &symbol; } } return nullptr; } const SymbolRecord* SymbolDatabase::FindByName(const std::string& name, SymbolType type) const { auto prefix = name + "["; auto suffix = fmt::format("[{}]", Common::EnumName(type).c_str()); for (const auto& symbol: m_symbols) { if (Common::StartsWith(symbol.name, prefix) && Common::EndsWith(symbol.name, suffix)) { return &symbol; } } return nullptr; } } // namespace Loader