Added decoding known mappings
This commit is contained in:
parent
88e7f0d8b8
commit
596aaabb6e
|
@ -28,6 +28,8 @@
|
|||
#include <sstream>
|
||||
#include <iomanip>
|
||||
#include "OutputContext.h"
|
||||
#include "instructions/Write.h"
|
||||
#include "instructions/Jump.h"
|
||||
|
||||
std::string OutputContext::getLabel(uint32_t location, bool force) const{
|
||||
if(mappings.find(location) != mappings.end()){
|
||||
|
@ -35,7 +37,7 @@ std::string OutputContext::getLabel(uint32_t location, bool force) const{
|
|||
}
|
||||
if(force){
|
||||
std::stringstream s;
|
||||
s << "func_" << std::hex << std::setw(6) << std::setfill('0') << location;
|
||||
s << "loc_" << std::hex << std::setw(6) << std::setfill('0') << location;
|
||||
return s.str();
|
||||
}
|
||||
return "";
|
||||
|
@ -60,7 +62,13 @@ std::string OutputContext::getDataHeader(uint32_t location) const {
|
|||
}
|
||||
|
||||
std::string OutputContext::getDataEntry(uint32_t location, const std::string &representation) const {
|
||||
return getDataHeader(location) + representation + getComment(location);
|
||||
std::string result = getDataHeader(location) + representation;
|
||||
uint32_t padLength = 64;
|
||||
if(result.size() < padLength){
|
||||
result.append(padLength - result.size(), ' ');
|
||||
}
|
||||
result += getComment(location);
|
||||
return result;
|
||||
}
|
||||
|
||||
std::string OutputContext::getInstructionString(const Instruction::Instruction& instruction) const {
|
||||
|
@ -78,11 +86,15 @@ void OutputContext::analyze() {
|
|||
std::stringstream from;
|
||||
from << "XREF.CallFrom: ";
|
||||
bool hasContinue = false;
|
||||
bool justAbsolute = true;
|
||||
bool justReturn = true;
|
||||
for(auto& j : e.second){
|
||||
if(j.second != JumpKind::Return){
|
||||
justReturn = false;
|
||||
}
|
||||
if(j.second != JumpKind::Absolute){
|
||||
justAbsolute = false;
|
||||
}
|
||||
if(j.second != JumpKind::Continue){
|
||||
from << std::hex << std::setw(6) << std::setfill('0') << j.first << "(";
|
||||
switch (j.second) {
|
||||
|
@ -104,11 +116,34 @@ void OutputContext::analyze() {
|
|||
hasContinue = true;
|
||||
}
|
||||
}
|
||||
if(!hasContinue){
|
||||
|
||||
if(justReturn || justAbsolute){
|
||||
if(!e.second.empty() && justReturn){
|
||||
auto& instruction = image.findConstInstructionByAddress(e.first - 1, true);
|
||||
if(instruction != nullptr && instruction->getCommand() == Instruction::Instruction::CommandOp::JUMP){
|
||||
//TODO, mark join?
|
||||
auto& jumpInstruction = dynamic_cast<const Instruction::Jump&>(*instruction);
|
||||
|
||||
bool foundReturn = false;
|
||||
uint32_t addressLocation = instruction->getAddress() - 1;
|
||||
while (true){
|
||||
auto& instructionBefore = image.findConstInstructionByAddress(addressLocation, true);
|
||||
if(instructionBefore != nullptr && instructionBefore->getCommand() == Instruction::Instruction::CommandOp::WRITE){
|
||||
auto& writeInstruction = dynamic_cast<const Instruction::Write&>(*instructionBefore);
|
||||
if(writeInstruction.data.size() == 1 && writeInstruction.data[0] == e.first){ //Return value!
|
||||
//TODO: mark join?
|
||||
addComment(writeInstruction.getAddress() + 4, "RETURN location for " + getLabel(jumpInstruction.jumpAddress));
|
||||
foundReturn = true;
|
||||
break;
|
||||
}
|
||||
addressLocation = instructionBefore->getAddress() - 1;
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!foundReturn){
|
||||
addMapping(e.first, getLabel(e.first, true));
|
||||
}
|
||||
}else{
|
||||
addMapping(e.first, getLabel(e.first, true));
|
||||
}
|
||||
|
@ -116,8 +151,9 @@ void OutputContext::analyze() {
|
|||
addMapping(e.first, getLabel(e.first, true));
|
||||
}
|
||||
}
|
||||
|
||||
if(e.second.size() > 1 || (!hasContinue && !e.second.empty())){
|
||||
addComment(e.first, from.str());
|
||||
addComment(e.first, "<" + getLabel(e.first, true) + "> " + from.str());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -48,8 +48,8 @@ public:
|
|||
|
||||
}
|
||||
|
||||
void addMapping(uint32_t location, const std::string& name){
|
||||
if(comments.find(location) == comments.end()) {
|
||||
void addMapping(uint32_t location, const std::string& name, bool force = false){
|
||||
if(force || comments.find(location) == comments.end()) {
|
||||
mappings[location] = name;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -124,7 +124,7 @@ std::vector<Instruction::OutputFormat> Instruction::Load::toOutputFormat(const O
|
|||
f.emplace_back(OutputFormat{getAddress() + offset++ * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " COUNT " << std::dec << data.size()).str()});
|
||||
|
||||
for (auto d : data) {
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " " << " = 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
offset++;
|
||||
}
|
||||
|
||||
|
@ -140,7 +140,7 @@ std::vector<Instruction::OutputFormat> Instruction::Load::toOutputFormat(const O
|
|||
f.emplace_back(OutputFormat{getAddress() + offset++ * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " COUNT " << std::dec << data.size()).str()});
|
||||
|
||||
for (auto d : data) {
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " " << " = 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
offset++;
|
||||
}
|
||||
|
||||
|
@ -155,7 +155,7 @@ std::vector<Instruction::OutputFormat> Instruction::Load::toOutputFormat(const O
|
|||
f.emplace_back(OutputFormat{getAddress() + offset++ * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " COUNT " << std::dec << data.size()).str()});
|
||||
|
||||
for (auto d : data) {
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " " << getAddressRegisterName(address + offset - 1, addressOffset) << " = 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
f.emplace_back(OutputFormat{getAddress() + offset * 4, dynamic_cast<std::stringstream&>(std::stringstream("") << " " << getAddressRegisterName(address + offset - 2, addressOffset) << " = 0x" << std::hex << std::setw(8) << std::setfill('0') << d).str()});
|
||||
offset++;
|
||||
}
|
||||
|
||||
|
|
89
src/main.cpp
89
src/main.cpp
|
@ -56,13 +56,96 @@ void decodeImage(const std::string &fileName) {
|
|||
}
|
||||
|
||||
OutputContext ctx(imageObject);
|
||||
|
||||
std::unordered_map<uint32_t, std::string> knownNames{
|
||||
{imageObject.getHeader().baseAddress, "__ENTRYPOINT"},
|
||||
|
||||
{0x1000, "load_bootCfg_pep_serialNumber"},
|
||||
{0x1054, "load_bootCfg_customMac"},
|
||||
|
||||
{0x088000, "load_bootCfg_pep0_vpd"},
|
||||
{0x0881c7, "load_bootCfg_pep1_vpd"},
|
||||
{0x08838e, "load_bootCfg_pep2_vpd"},
|
||||
{0x088555, "load_bootCfg_pep3_vpd"},
|
||||
{0x08871c, "load_bootCfg_pep4_vpd"},
|
||||
{0x0888e3, "load_bootCfg_pep5_vpd"},
|
||||
{0x088aaa, "load_bootCfg_pep6_vpd"},
|
||||
{0x088c71, "load_bootCfg_pep7_vpd"},
|
||||
{0x088e38, "load_bootCfg_pep8_vpd"},
|
||||
|
||||
{0x089000, "load_bootCfg_systimeClockSource"},
|
||||
|
||||
{0x089010, "load_bootCfg_pep0_mode"},
|
||||
{0x089020, "load_bootCfg_pep2_mode"},
|
||||
{0x089030, "load_bootCfg_pep4_mode"},
|
||||
{0x089040, "load_bootCfg_pep6_mode"},
|
||||
|
||||
{0x089050, "load_bootCfg_pep0_enable"},
|
||||
{0x089060, "load_bootCfg_pep1_enable"},
|
||||
{0x089070, "load_bootCfg_pep2_enable"},
|
||||
{0x089080, "load_bootCfg_pep3_enable"},
|
||||
{0x089090, "load_bootCfg_pep4_enable"},
|
||||
{0x0890a0, "load_bootCfg_pep5_enable"},
|
||||
{0x0890b0, "load_bootCfg_pep6_enable"},
|
||||
{0x0890c0, "load_bootCfg_pep7_enable"},
|
||||
{0x0890d0, "load_bootCfg_pep8_enable"},
|
||||
|
||||
{0x0890e0, "load_bootCfg_GPIO_PIN14_DRIVE"},
|
||||
|
||||
{0x0890f0, "load_bootCfg_spiTransferMode"},
|
||||
{0x089100, "load_bootCfg_spiTransferSpeed"},
|
||||
|
||||
{0x089130, "load_bootCfg_pep_numberOfLanes"},
|
||||
|
||||
{0x0891f0, "load_bootCfg_pep_mgmtPep"},
|
||||
{0x089230, "load_bootCfg_pep_vendor_device"},
|
||||
{0x089260, "load_bootCfg_pep_subVendor_subDevice"},
|
||||
|
||||
{0x0892f0, "load_bootCfg_pep_gen"},
|
||||
|
||||
{0x089380, "load_bootCfg_pep_ASPMEnable"},
|
||||
|
||||
|
||||
{0x083900, "execute_SerialBus_PCIE_Command"},
|
||||
{0x080b00, "mark_SOFT_RESET_ClocksStable_ColdReset"},
|
||||
|
||||
{0x081100, "init_MASTER_SPICO"},
|
||||
{0x08a004, "load_MASTER_SPICO_FW"},
|
||||
|
||||
{0x081400, "init_SERDES"},
|
||||
{0x08c004, "load_SERDES_FW"},
|
||||
|
||||
//Merge function
|
||||
{0x080004, ""},
|
||||
{0x080008, ""},
|
||||
{0x08000c, ""},
|
||||
{0x08001c, ""},
|
||||
{0x080038, ""},
|
||||
{0x080068, ""},
|
||||
|
||||
{0x0870c4, ""},
|
||||
};
|
||||
|
||||
std::unordered_map<uint32_t, std::string> comments{
|
||||
{0x080260, "Setting BSM_ARGS means this will be called again when reset, BSM_SCRATCH[0x149] is set to ~ 084000"},
|
||||
{0x084000, "XREF From BSM_ARGS"}
|
||||
};
|
||||
|
||||
for(auto& e : knownNames){
|
||||
ctx.addMapping(e.first, e.second);
|
||||
}
|
||||
|
||||
for(auto& c : comments){
|
||||
ctx.addComment(c.first, c.second);
|
||||
}
|
||||
|
||||
ctx.analyze();
|
||||
|
||||
uint32_t prevAddress = 0;
|
||||
for (const auto &entry : imageObject.getInstructions()) {
|
||||
const auto &instruction = entry.second;
|
||||
if (instruction->getAddress() < prevAddress) {
|
||||
std::cout << "====== DECODE ERROR? ========== " << std::hex << std::setw(8) << std::setfill('0')
|
||||
std::cout << "========== DECODE ERROR? ========== " << std::hex << std::setw(8) << std::setfill('0')
|
||||
<< prevAddress << " - " << std::hex << std::setw(8) << std::setfill('0')
|
||||
<< instruction->getAddress() << "\n";
|
||||
} else if ((instruction->getAddress() - prevAddress) >= 4 &&
|
||||
|
@ -85,13 +168,13 @@ void decodeImage(const std::string &fileName) {
|
|||
std::cout << op.str();
|
||||
}
|
||||
} else if ((instruction->getAddress() - prevAddress) >= 1024) {
|
||||
std::cout << "================ " << std::hex << std::setw(8) << std::setfill('0') << prevAddress
|
||||
std::cout << "\n\n================ " << std::hex << std::setw(8) << std::setfill('0') << prevAddress
|
||||
<< " - " << std::hex << std::setw(8) << std::setfill('0') << instruction->getAddress()
|
||||
<< "\n";
|
||||
}
|
||||
|
||||
if(!ctx.getLabel(instruction->getAddress(), false).empty()){
|
||||
std::cout << "\n\n; == FUNCTION " << ctx.getLabel(instruction->getAddress()) << " ==\n";
|
||||
std::cout << "\n\n; ================ FUNCTION " << ctx.getLabel(instruction->getAddress()) << " ================\n";
|
||||
}
|
||||
|
||||
std::cout << ctx.getInstructionString(*instruction);
|
||||
|
|
Loading…
Reference in a new issue