[FEAT] Decompiler

[BUG] Several address calculation errors
This commit is contained in:
2021-05-05 09:34:58 +02:00
parent 1516043f17
commit 37fdf1f42f
6 changed files with 80 additions and 4 deletions

10
decompiled.txt Normal file
View File

@@ -0,0 +1,10 @@
NOP
NOP
PUSH 4
LD 72
LD 60
MUL
SUB
ST 144
STL 4
STL 0

59
decompiler.cpp Normal file
View File

@@ -0,0 +1,59 @@
#include "decompiler.h"
#include <iostream>
#include <fstream>
#include <string.h>
#include "parser.h"
#define SIMPLE(X) f << X << std::endl; pos++; break
// [RZC 05/05/2021] To solve alignment problems on ARM architectures we have to first copy the 4 bytes to an aligned byte array, then cast it to float
#define FVAR(X) memcpy(data, &code[pos+1], 4); f << X << " " << *((float*)data) << std::endl; pos += 5; break
#define IVAR(X) memcpy(data, &code[pos+1], 4); f << X << " " << *((uint32_t*)data) << std::endl; pos += 5; break
void decompiler_save(const uint8_t *code, const int size) {
uint8_t data[4];
int pos = 0;
float fval = 0;
uint32_t ival = 0;
std::ofstream f("decompiled.txt");
if (f.is_open()) {
while (pos < size) {
switch (code[pos]) {
case OP_NOP: SIMPLE("NOP");
case OP_PUSH: FVAR("PUSH");
case OP_POP: SIMPLE("POP");
case OP_DUP: SIMPLE("DUP");
case OP_SWAP: SIMPLE("SWAP");
case OP_LD: IVAR("LD");
case OP_ST: IVAR("ST");
case OP_LDL: IVAR("LDL");
case OP_STL: IVAR("STL");
case OP_JMP: IVAR("JMP");
case OP_JNT: IVAR("JNT");
case OP_JTR: IVAR("JTR");
case OP_RET: SIMPLE("RET");
case OP_CALL: IVAR("CALL");
case OP_CALLEX: IVAR("CALLEX");
case OP_ADD: SIMPLE("ADD");
case OP_SUB: SIMPLE("SUB");
case OP_MUL: SIMPLE("MUL");
case OP_DIV: SIMPLE("DIV");
case OP_MOD: SIMPLE("MOD");
case OP_AND: SIMPLE("AND");
case OP_OR: SIMPLE("OR");
case OP_NOT: SIMPLE("NOT");
case OP_NEG: SIMPLE("NEG");
case OP_INC: SIMPLE("INC");
case OP_DEC: SIMPLE("DEC");
case OP_CONCAT: SIMPLE("CONCAT");
case OP_EQ: SIMPLE("EQ");
case OP_NEQ: SIMPLE("NEQ");
case OP_LT: SIMPLE("LT");
case OP_GT: SIMPLE("GT");
case OP_LEQ: SIMPLE("LEQ");
case OP_GEQ: SIMPLE("GEQ");
case OP_SLEEP: SIMPLE("SLEEP");
}
}
f.close();
}
}

4
decompiler.h Normal file
View File

@@ -0,0 +1,4 @@
#pragma once
#include <stdint.h>
void decompiler_save(const uint8_t *code, const int size);

View File

@@ -9,6 +9,7 @@
#include <stdio.h>
#include <string.h>
#include <stack>
#include "decompiler.h"
#define MAX_CODE_SIZE 65536
#define MAX_LABELS 256
@@ -326,7 +327,7 @@ static void parse_expr_atom() {
const int address = get_variable_address();
if (address == -1) return;
emmit(scope_is_local() ? OP_LDL : OP_LD);
emmit(address);
emmit_dw(address);
tkn_next();
return;
} else {
@@ -890,7 +891,9 @@ void parser_parse(const char* buffer, byte* mem) {
//codepos = 0xA000;
//emmit(OP_JMP);
//emmit_w(0xA000);
}
} else {
decompiler_save(code, codepos);
}
//FILE *f = fopen("test.bin", "wb");
//fwrite(mem, codepos, 1, f);

View File

@@ -65,7 +65,7 @@ const int scope_declare_variable(const std::string name, const uint32_t type, co
const uint32_t address = scope.total_size;
const t_variable var {name, type, length, address};
scope.variables.push_back(var);
scope.total_size += types_get_length(type) + (length == 0 ? 1 : length);
scope.total_size += types_get_length(type) * (length == 0 ? 1 : length);
return address;
}

View File

@@ -37,7 +37,7 @@ const int types_add_member(const uint32_t type, const std::string name, const ui
for (auto m : types[type].members) if (m.name == name) return -1;
const t_variable new_var {name, var_type, length, types[type].size};
types[type].members.push_back(new_var);
types[type].size += types_get_length(var_type) + length;
types[type].size += types_get_length(var_type) * length;
return types[type].members.size()-1;
}