summaryrefslogtreecommitdiff
path: root/Source/Core
diff options
context:
space:
mode:
authorLeo Lam <leolino.lam@gmail.com>2017-10-11 13:00:40 +0200
committerGitHub <noreply@github.com>2017-10-11 13:00:40 +0200
commitceed4d6f930f06aec6b68b353d99a19f46a0e26f (patch)
tree73ee67ad66e26098d2f264589de6e81e13ee9606 /Source/Core
parentbc6846ce3b7e3f52a5e010dd47c313c0d74f5f3d (diff)
parent0a301c0eec31ac69f0e606e369351d8da56bb4c2 (diff)
Merge pull request #6101 from sepalani/symbol-map-data
PPCSymbolDB: Handle data symbols in SymbolMap properly
Diffstat (limited to 'Source/Core')
-rw-r--r--Source/Core/Core/PowerPC/PPCSymbolDB.cpp104
1 files changed, 67 insertions, 37 deletions
diff --git a/Source/Core/Core/PowerPC/PPCSymbolDB.cpp b/Source/Core/Core/PowerPC/PPCSymbolDB.cpp
index f9ce0508a3..778fc5f896 100644
--- a/Source/Core/Core/PowerPC/PPCSymbolDB.cpp
+++ b/Source/Core/Core/PowerPC/PPCSymbolDB.cpp
@@ -13,6 +13,7 @@
#include "Common/File.h"
#include "Common/Logging/Log.h"
#include "Common/MsgHandler.h"
+#include "Common/StringUtil.h"
#include "Core/PowerPC/PPCAnalyst.h"
#include "Core/PowerPC/PowerPC.h"
#include "Core/PowerPC/SignatureDB/SignatureDB.h"
@@ -219,10 +220,12 @@ bool PPCSymbolDB::LoadMap(const std::string& filename, bool bad)
return false;
// four columns are used in American Mensa Academy map files and perhaps other games
- bool started = false, four_columns = false;
- int good_count = 0, bad_count = 0;
+ bool four_columns = false;
+ int good_count = 0;
+ int bad_count = 0;
char line[512];
+ std::string section_name;
while (fgets(line, 512, f.GetHandle()))
{
size_t length = strlen(line);
@@ -240,44 +243,48 @@ bool PPCSymbolDB::LoadMap(const std::string& filename, bool bad)
if (strcmp(temp, "UNUSED") == 0)
continue;
- if (strcmp(temp, ".text") == 0)
- {
- started = true;
- continue;
- };
- if (strcmp(temp, ".init") == 0)
+
+ // Support CodeWarrior and Dolphin map
+ if (StringEndsWith(line, " section layout\n") || strcmp(temp, ".text") == 0 ||
+ strcmp(temp, ".init") == 0)
{
- started = true;
+ section_name = temp;
continue;
- };
+ }
+
+ // Skip four columns' header.
+ //
+ // Four columns example:
+ //
+ // .text section layout
+ // Starting Virtual
+ // address Size address
+ // -----------------------
if (strcmp(temp, "Starting") == 0)
continue;
- if (strcmp(temp, "extab") == 0)
- continue;
- if (strcmp(temp, ".ctors") == 0)
- break; // uh?
- if (strcmp(temp, ".dtors") == 0)
- break;
- if (strcmp(temp, ".rodata") == 0)
- continue;
- if (strcmp(temp, ".data") == 0)
- continue;
- if (strcmp(temp, ".sbss") == 0)
- continue;
- if (strcmp(temp, ".sdata") == 0)
- continue;
- if (strcmp(temp, ".sdata2") == 0)
- continue;
if (strcmp(temp, "address") == 0)
continue;
if (strcmp(temp, "-----------------------") == 0)
continue;
- if (strcmp(temp, ".sbss2") == 0)
- break;
- if (temp[1] == ']')
+
+ // Skip link map.
+ //
+ // Link map example:
+ //
+ // Link map of __start
+ // 1] __start(func, weak) found in os.a __start.c
+ // 2] __init_registers(func, local) found in os.a __start.c
+ // 3] _stack_addr found as linker generated symbol
+ // ...
+ // 10] EXILock(func, global) found in exi.a EXIBios.c
+ if (StringEndsWith(temp, "]"))
continue;
- if (!started)
+ // TODO - Handle/Write a parser for:
+ // - Memory map
+ // - Link map
+ // - Linker generated symbols
+ if (section_name.empty())
continue;
u32 address, vaddress, size, offset, alignment;
@@ -344,7 +351,7 @@ bool PPCSymbolDB::LoadMap(const std::string& filename, bool bad)
name[strlen(name) - 1] = 0;
// Check if this is a valid entry.
- if (strcmp(name, ".text") != 0 && strcmp(name, ".init") != 0 && strlen(name) > 0)
+ if (strlen(name) > 0)
{
// Can't compute the checksum if not in RAM
bool good = !bad && PowerPC::HostIsInstructionRAMAddress(vaddress) &&
@@ -363,7 +370,10 @@ bool PPCSymbolDB::LoadMap(const std::string& filename, bool bad)
if (good)
{
++good_count;
- AddKnownSymbol(vaddress, size, name); // ST_FUNCTION
+ if (section_name == ".text" || section_name == ".init")
+ AddKnownSymbol(vaddress, size, name, Symbol::Type::Function);
+ else
+ AddKnownSymbol(vaddress, size, name, Symbol::Type::Data);
}
else
{
@@ -385,16 +395,36 @@ bool PPCSymbolDB::SaveSymbolMap(const std::string& filename) const
if (!f)
return false;
- // Write ".text" at the top
- fprintf(f.GetHandle(), ".text\n");
+ std::vector<const Symbol*> function_symbols;
+ std::vector<const Symbol*> data_symbols;
- // Write symbol address, size, virtual address, alignment, name
for (const auto& function : functions)
{
const Symbol& symbol = function.second;
- fprintf(f.GetHandle(), "%08x %08x %08x %i %s\n", symbol.address, symbol.size, symbol.address, 0,
- symbol.name.c_str());
+ if (symbol.type == Symbol::Type::Function)
+ function_symbols.push_back(&symbol);
+ else
+ data_symbols.push_back(&symbol);
}
+
+ // Write .text section
+ fprintf(f.GetHandle(), ".text section layout\n");
+ for (const auto& symbol : function_symbols)
+ {
+ // Write symbol address, size, virtual address, alignment, name
+ fprintf(f.GetHandle(), "%08x %08x %08x %i %s\n", symbol->address, symbol->size, symbol->address,
+ 0, symbol->name.c_str());
+ }
+
+ // Write .data section
+ fprintf(f.GetHandle(), "\n.data section layout\n");
+ for (const auto& symbol : data_symbols)
+ {
+ // Write symbol address, size, virtual address, alignment, name
+ fprintf(f.GetHandle(), "%08x %08x %08x %i %s\n", symbol->address, symbol->size, symbol->address,
+ 0, symbol->name.c_str());
+ }
+
return true;
}