Préparation d'un affichage bufferisé du désassemblage
This commit is contained in:
parent
5e2288fcc2
commit
af4e98a512
106
ia86.cpp
106
ia86.cpp
|
@ -162,11 +162,17 @@ void InstructionWindow::clear()
|
||||||
listview.redraw();
|
listview.redraw();
|
||||||
}
|
}
|
||||||
|
|
||||||
void InstructionWindow::setindex(int index)
|
void InstructionWindow::setmark(int index)
|
||||||
{
|
{
|
||||||
listview.setindex(index);
|
listview.setmark(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int InstructionWindow::getsize()
|
||||||
|
{
|
||||||
|
return listview.getCount();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void InstructionWindow::set(std::vector<std::array<std::string, 5>> src)
|
void InstructionWindow::set(std::vector<std::array<std::string, 5>> src)
|
||||||
{
|
{
|
||||||
content=src;
|
content=src;
|
||||||
|
@ -312,9 +318,9 @@ Desassembler::Desassembler(TextWindow *log) : log(log)
|
||||||
log->append("Initialisation du désassembleur X86");
|
log->append("Initialisation du désassembleur X86");
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::array<std::string, 5>> Desassembler::Desassemble(uint8_t *content, uint32_t address,uint32_t size)
|
Unasm *Desassembler::Desassemble(uint8_t *content, uint32_t address,uint32_t size)
|
||||||
{
|
{
|
||||||
|
Unasm *unasm=new Unasm;
|
||||||
std::stringstream out;
|
std::stringstream out;
|
||||||
srcsize=cs_disasm(handle, content, size, address, 0, &insn);
|
srcsize=cs_disasm(handle, content, size, address, 0, &insn);
|
||||||
if (srcsize == 0)
|
if (srcsize == 0)
|
||||||
|
@ -323,7 +329,7 @@ std::vector<std::array<std::string, 5>> Desassembler::Desassemble(uint8_t *conte
|
||||||
{
|
{
|
||||||
out << "Désassemblage réussi, taille du source :" << srcsize;
|
out << "Désassemblage réussi, taille du source :" << srcsize;
|
||||||
log->append(out.str());
|
log->append(out.str());
|
||||||
src.clear();
|
unasm->src.clear();
|
||||||
for (size_t j = 0; j < srcsize; j++)
|
for (size_t j = 0; j < srcsize; j++)
|
||||||
{
|
{
|
||||||
std::string *bytes = new std::string("");
|
std::string *bytes = new std::string("");
|
||||||
|
@ -333,11 +339,13 @@ std::vector<std::array<std::string, 5>> Desassembler::Desassemble(uint8_t *conte
|
||||||
std::string *menmonic = new std::string((char *)insn[j].mnemonic);
|
std::string *menmonic = new std::string((char *)insn[j].mnemonic);
|
||||||
std::string *op_str = new std::string((char *)insn[j].op_str);
|
std::string *op_str = new std::string((char *)insn[j].op_str);
|
||||||
std::array<std::string, 5> *array = new std::array<std::string, 5>{"", adresse, *bytes, *menmonic, *op_str};
|
std::array<std::string, 5> *array = new std::array<std::string, 5>{"", adresse, *bytes, *menmonic, *op_str};
|
||||||
src.push_back(*array);
|
unasm->src.push_back(*array);
|
||||||
|
std::array<int, 2> *array2 = new std::array<int, 2>{(int)insn[j].address,(int)insn[j].size};
|
||||||
|
unasm->pos.push_back(*array2);
|
||||||
}
|
}
|
||||||
cs_free(insn, srcsize);
|
cs_free(insn, srcsize);
|
||||||
}
|
}
|
||||||
return src;
|
return unasm;
|
||||||
}
|
}
|
||||||
|
|
||||||
//----------------------------------------------------------------------
|
//----------------------------------------------------------------------
|
||||||
|
@ -354,6 +362,7 @@ Assembler::Assembler(TextWindow *log) : log(log)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
log->append("Initialisation de l'assembleur X86");
|
log->append("Initialisation de l'assembleur X86");
|
||||||
|
ks_option(ks, KS_OPT_SYNTAX, KS_OPT_SYNTAX_NASM);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<Code> Assembler::MultiAssemble(std::string source,uint32_t address)
|
std::vector<Code> Assembler::MultiAssemble(std::string source,uint32_t address)
|
||||||
|
@ -449,7 +458,7 @@ VMEngine::VMEngine(TextWindow *log) : log(log)
|
||||||
// Level 10 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7
|
// Level 10 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7
|
||||||
// Level 11 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7 CR0 CR2 CR3 CR4 CR8
|
// Level 11 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7 CR0 CR2 CR3 CR4 CR8
|
||||||
// Level 12 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7 CR0 CR2 CR3 CR4 CR8 DB0 DB1 DB2 DB3 DB6 DB7
|
// Level 12 : EIP EAX EBX ECX EDX EFLAGS ESI EDI ESP EBP CS DS ES SS FS GS ST0 ST1 ST2 ST3 ST4 ST5 ST6 ST7 CR0 CR2 CR3 CR4 CR8 DB0 DB1 DB2 DB3 DB6 DB7
|
||||||
std::string VMEngine::getFlags(int rights)
|
std::string VMEngine::getFlags()
|
||||||
{
|
{
|
||||||
int eflags=0;
|
int eflags=0;
|
||||||
err = uc_reg_read(uc, UC_X86_REG_EFLAGS, &eflags);
|
err = uc_reg_read(uc, UC_X86_REG_EFLAGS, &eflags);
|
||||||
|
@ -506,7 +515,7 @@ uint8_t *VMEngine::getRamRaw(uint32_t address, uint32_t size)
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string VMEngine::getRegs(int rights)
|
std::string VMEngine::getRegs()
|
||||||
{
|
{
|
||||||
int regsi836[] = {
|
int regsi836[] = {
|
||||||
UC_X86_REG_EAX, UC_X86_REG_EBX, UC_X86_REG_ECX, UC_X86_REG_EDX,
|
UC_X86_REG_EAX, UC_X86_REG_EBX, UC_X86_REG_ECX, UC_X86_REG_EDX,
|
||||||
|
@ -636,16 +645,34 @@ void VMEngine::Halt()
|
||||||
this->executed=false;
|
this->executed=false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void VMEngine::Change()
|
void VMEngine::Unconfigure()
|
||||||
{
|
{
|
||||||
this->executed=false;
|
this->executed=false;
|
||||||
this->initialized=false;
|
this->initialized=false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void VMEngine::Configure(State *init, std::vector<Code> newmcode)
|
std::vector<std::array<std::string, 5>> VMEngine::getInstr(int address,int size)
|
||||||
|
{
|
||||||
|
if (address<alladdress || address+6>alladdress+500)
|
||||||
|
{
|
||||||
|
int begin=address-30;
|
||||||
|
if (begin<0) begin=0x00000000;
|
||||||
|
code=this->getRamRaw(begin, 500);
|
||||||
|
alladdress=begin;
|
||||||
|
}
|
||||||
|
crc = crc32(0, code, 500);
|
||||||
|
if (crc != crc_old)
|
||||||
|
{
|
||||||
|
unasmer.Desassemble(code, alladdress, 500);
|
||||||
|
crc_old=crc;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void VMEngine::Configure(State *init, std::string code)
|
||||||
{
|
{
|
||||||
int status;
|
int status;
|
||||||
mcode=newmcode;
|
mcode.clear();
|
||||||
|
mcode=asmer.MultiAssemble(code,init->dump.regs.eip);
|
||||||
Close();
|
Close();
|
||||||
Init();
|
Init();
|
||||||
this->initialized=false;
|
this->initialized=false;
|
||||||
|
@ -674,6 +701,11 @@ int VMEngine::verify()
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void VMEngine::setRights(int rights)
|
||||||
|
{
|
||||||
|
this->rights=rights;
|
||||||
|
}
|
||||||
|
|
||||||
int VMEngine::getEIP()
|
int VMEngine::getEIP()
|
||||||
{
|
{
|
||||||
int eip=-666;
|
int eip=-666;
|
||||||
|
@ -685,6 +717,28 @@ int VMEngine::getEIP()
|
||||||
return eip;
|
return eip;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int VMEngine::getCS()
|
||||||
|
{
|
||||||
|
int cs=-666;
|
||||||
|
err = uc_reg_read(uc, UC_X86_REG_CS, &cs);
|
||||||
|
if (err != UC_ERR_OK)
|
||||||
|
log->append("Impossible de récupérer le registre: CS");
|
||||||
|
if (cs<0)
|
||||||
|
cs=0;
|
||||||
|
return cs;
|
||||||
|
}
|
||||||
|
|
||||||
|
int VMEngine::getDS()
|
||||||
|
{
|
||||||
|
int ds=-666;
|
||||||
|
err = uc_reg_read(uc, UC_X86_REG_DS, &ds);
|
||||||
|
if (err != UC_ERR_OK)
|
||||||
|
log->append("Impossible de récupérer le registre: DS");
|
||||||
|
if (ds<0)
|
||||||
|
ds=0;
|
||||||
|
return ds;
|
||||||
|
}
|
||||||
|
|
||||||
void VMEngine::SetMem(Code *code)
|
void VMEngine::SetMem(Code *code)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
@ -805,6 +859,10 @@ void VMEngine::Run(State *init,uint64_t timeout)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//----------------------------------------------------------------------
|
||||||
|
// Classe
|
||||||
|
//----------------------------------------------------------------------
|
||||||
|
|
||||||
//----------------------------------------------------------------------
|
//----------------------------------------------------------------------
|
||||||
// Classe Menu
|
// Classe Menu
|
||||||
//----------------------------------------------------------------------
|
//----------------------------------------------------------------------
|
||||||
|
@ -968,7 +1026,7 @@ void Menu::initMenusCallBack()
|
||||||
(
|
(
|
||||||
"clicked",
|
"clicked",
|
||||||
this,
|
this,
|
||||||
&Menu::initWindows
|
&Menu::AdjustWindows
|
||||||
);
|
);
|
||||||
TraceInto.addCallback
|
TraceInto.addCallback
|
||||||
(
|
(
|
||||||
|
@ -1044,7 +1102,8 @@ void Menu::loadLevel()
|
||||||
edit.set(scenario.levels[scenar.getselected()].code);
|
edit.set(scenario.levels[scenar.getselected()].code);
|
||||||
AdjustWindows();
|
AdjustWindows();
|
||||||
debug.clear();
|
debug.clear();
|
||||||
vm.Change();
|
vm.Unconfigure();
|
||||||
|
vm.setRights(scenario.levels[scenar.getselected()].rights);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Menu::end()
|
void Menu::end()
|
||||||
|
@ -1054,9 +1113,7 @@ void Menu::end()
|
||||||
|
|
||||||
void Menu::compile()
|
void Menu::compile()
|
||||||
{
|
{
|
||||||
std::vector<Code> mcode;
|
vm.Configure(&scenario.levels[scenar.getselected()].init,edit.get());
|
||||||
mcode=asmer.MultiAssemble(edit.get(),scenario.levels[scenar.getselected()].init.dump.regs.eip);
|
|
||||||
vm.Configure(&scenario.levels[scenar.getselected()].init,mcode);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Menu::about()
|
void Menu::about()
|
||||||
|
@ -1090,8 +1147,8 @@ void Menu::refresh()
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
regs.set(vm.getRegs(scenario.levels[scenar.getselected()].rights));
|
regs.set(vm.getRegs());
|
||||||
flags.set(vm.getFlags(scenario.levels[scenar.getselected()].rights));
|
flags.set(vm.getFlags());
|
||||||
//debug.setindex(vm.getEIP(code));
|
//debug.setindex(vm.getEIP(code));
|
||||||
}
|
}
|
||||||
if (!vm.isExecuted())
|
if (!vm.isExecuted())
|
||||||
|
@ -1101,16 +1158,7 @@ void Menu::refresh()
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
finalcut::FApplication::setDefaultTheme();
|
finalcut::FApplication::setDefaultTheme();
|
||||||
eip=vm.getEIP()-256;
|
//debug.set(vm.getInstr(vm.getCS()*16+vm.getEIP(),debug.getsize()));
|
||||||
if (eip<0) eip=0x00000000;
|
|
||||||
code=vm.getRamRaw(eip, 512);
|
|
||||||
crc = crc32(0, code, 512);
|
|
||||||
if (crc != oldcrc || eip != oldeip)
|
|
||||||
{
|
|
||||||
debug.set(unasmer.Desassemble(code, eip,512));
|
|
||||||
oldcrc=crc;
|
|
||||||
oldeip=eip;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
auto root_widget = getRootWidget();
|
auto root_widget = getRootWidget();
|
||||||
root_widget->resetColors();
|
root_widget->resetColors();
|
||||||
|
|
42
ia86.h
42
ia86.h
|
@ -137,6 +137,12 @@ struct Code
|
||||||
std::string src;
|
std::string src;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct Unasm
|
||||||
|
{
|
||||||
|
std::vector<std::array<std::string, 5>> src;
|
||||||
|
std::vector<std::array<int, 2>> pos;
|
||||||
|
};
|
||||||
|
|
||||||
class ScenarioWindow final : public finalcut::FDialog
|
class ScenarioWindow final : public finalcut::FDialog
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
@ -175,7 +181,8 @@ class InstructionWindow final : public finalcut::FDialog
|
||||||
std::vector<std::array<std::string, 5>> get();
|
std::vector<std::array<std::string, 5>> get();
|
||||||
void set(std::vector<std::array<std::string, 5>> src);
|
void set(std::vector<std::array<std::string, 5>> src);
|
||||||
void clear();
|
void clear();
|
||||||
void setindex(int index);
|
void setmark(int index);
|
||||||
|
int getsize();
|
||||||
private:
|
private:
|
||||||
// Method
|
// Method
|
||||||
std::vector<std::array<std::string, 5>> content;
|
std::vector<std::array<std::string, 5>> content;
|
||||||
|
@ -239,7 +246,7 @@ class Desassembler
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Desassembler(TextWindow *log);
|
Desassembler(TextWindow *log);
|
||||||
std::vector<std::array<std::string, 5>> Desassemble(uint8_t *content, uint32_t address,uint32_t size);
|
Unasm *Desassemble(uint8_t *content, uint32_t address,uint32_t size);
|
||||||
private:
|
private:
|
||||||
csh handle;
|
csh handle;
|
||||||
cs_insn *insn;
|
cs_insn *insn;
|
||||||
|
@ -270,28 +277,38 @@ class VMEngine
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
VMEngine(TextWindow *log);
|
VMEngine(TextWindow *log);
|
||||||
void Configure(State *init, std::vector<Code> mcode);
|
void Configure(State *init, std::string code);
|
||||||
void Halt();
|
void Halt();
|
||||||
void Change();
|
void Unconfigure();
|
||||||
void Run(State *init,uint64_t timeout);
|
void Run(State *init,uint64_t timeout);
|
||||||
std::string getFlags(int rights);
|
std::string getFlags();
|
||||||
std::string getRegs(int rights);
|
std::string getRegs();
|
||||||
|
std::vector<std::array<std::string, 5>> getInstr(int address,int size);
|
||||||
void SetMem(Code *code);
|
void SetMem(Code *code);
|
||||||
void SetRegs(State *init);
|
void SetRegs(State *init);
|
||||||
uint8_t *getRamRaw(uint32_t address, uint32_t size);
|
|
||||||
int getEIP();
|
|
||||||
int verify();
|
int verify();
|
||||||
bool isExecuted();
|
bool isExecuted();
|
||||||
bool isInitialized();
|
bool isInitialized();
|
||||||
|
void setRights(int rights);
|
||||||
|
int getEIP();
|
||||||
|
int getCS();
|
||||||
|
int getDS();
|
||||||
private:
|
private:
|
||||||
|
TextWindow *log;
|
||||||
|
Assembler asmer{log};
|
||||||
|
Desassembler unasmer{log};
|
||||||
std::vector<Code> mcode;
|
std::vector<Code> mcode;
|
||||||
|
int rights;
|
||||||
|
uint8_t *getRamRaw(uint32_t address, uint32_t size);
|
||||||
void Init();
|
void Init();
|
||||||
void Close();
|
void Close();
|
||||||
bool executed=false;
|
bool executed=false;
|
||||||
bool initialized=false;
|
bool initialized=false;
|
||||||
uc_engine *uc;
|
uc_engine *uc;
|
||||||
uc_err err;
|
uc_err err;
|
||||||
TextWindow *log;
|
int alladdress,alladdress_old;
|
||||||
|
uint8_t *code;
|
||||||
|
uLong crc,crc_old;
|
||||||
};
|
};
|
||||||
|
|
||||||
class Menu final : public finalcut::FDialog
|
class Menu final : public finalcut::FDialog
|
||||||
|
@ -309,9 +326,6 @@ class Menu final : public finalcut::FDialog
|
||||||
void loadLevel();
|
void loadLevel();
|
||||||
TextWindow log{this};
|
TextWindow log{this};
|
||||||
private:
|
private:
|
||||||
int eip,oldeip;
|
|
||||||
uint8_t *code;
|
|
||||||
uLong crc,oldcrc;
|
|
||||||
void onTimer (finalcut::FTimerEvent*) override;
|
void onTimer (finalcut::FTimerEvent*) override;
|
||||||
void refresh();
|
void refresh();
|
||||||
void configureFileMenuItems();
|
void configureFileMenuItems();
|
||||||
|
@ -367,8 +381,6 @@ class Menu final : public finalcut::FDialog
|
||||||
TextEditWindow edit{this};
|
TextEditWindow edit{this};
|
||||||
ScenarioWindow scenar{this};
|
ScenarioWindow scenar{this};
|
||||||
VMEngine vm{&log};
|
VMEngine vm{&log};
|
||||||
Assembler asmer{&log};
|
|
||||||
Desassembler unasmer{&log};
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -51,9 +51,14 @@ hlt",
|
||||||
"niveau_description" : "Il faut connaitre...",
|
"niveau_description" : "Il faut connaitre...",
|
||||||
"niveau_tutoriel" : "Ceci vous...",
|
"niveau_tutoriel" : "Ceci vous...",
|
||||||
"niveau_code" : "mov ax,0x545
|
"niveau_code" : "mov ax,0x545
|
||||||
|
pop:
|
||||||
inc dx
|
inc dx
|
||||||
|
lea ebx,[pop]
|
||||||
|
db 'c','e','c','i',' ','e','s','t',' ','u','n',' ','t','e','s','t',0
|
||||||
.org 0x9000
|
.org 0x9000
|
||||||
pop db 'ceci est un test',0
|
pop:
|
||||||
|
db 0x00
|
||||||
|
lea eax,[pop]
|
||||||
mov esi,0x44441234
|
mov esi,0x44441234
|
||||||
.org 0x3002
|
.org 0x3002
|
||||||
hlt",
|
hlt",
|
||||||
|
|
Loading…
Reference in New Issue