📄 reparse.h
字号:
curbb->hcode.back().operands.push_back(new expr_t());
curbb->hcode.back().operands.back()->make_literal32(4);
curbb->hcode.back().operands.push_back(new expr_t());
curbb->hcode.back().operands.back()->make_literal32(s.icode->asz + 0x300);
break;
case insn__loop:
curbb->hcode.back().operands.push_back(NULL);
curbb->hcode.back().operands.push_back(new expr_t());
curbb->hcode.back().operands.back()->make_literal32(s.icode->asz + 0x300);
break;
}
// ** add hll condition expression argument here.
//curbb->hcode.back().operands.push_back(cc);
if(memory.meta[tmp].local == 0)
{
bb_t &bb = proc.map[tmp];
bb.address = tmp;
bb.proc = &proc;
bb.in_edges.insert(curbb);
curbb->out_edges.push_back(&bb);
locals.insert(tmp);
}
offset = (U8)s.icode->imm + (U8)target + (U8)s.size + (U8)memory.image_base;
offset &= memory.rip_mask;
tmp = offset - (U8)memory.image_base;
if(s.icode->imm != 0)
{
bb_t &bb2 = proc.map[tmp];
bb2.address = tmp;
bb2.proc = &proc;
bb2.in_edges.insert(curbb);
curbb->out_edges.push_back(&bb2);
if(memory.meta[tmp].local == 0)
locals.insert(tmp);
}
continue;
}
case insn__calli:
// high level languages CAN do indirect calls.
no_decompile = true;
break;
case insn__callfd:
case insn__callfi:
no_decompile = true;
break;
case insn__jmpfd:
case insn__jmpfi:
no_decompile = true;
continue;
case insn__jmpi:
// consult peep-hole buffer to see if we can handle it.
// fixme--do this.
// cmp [ebp-<#>],<#>
// ja/jae target
// mov reg,[ebp-<#>]
// jmp [reg*osz+<#>]
//reg/[ebp-<#>] : have osz size.
no_decompile = true;
continue;
default:
{
if(s.icode->lockrep == 1)
{
no_decompile = true;
break;
}
tcode_element &te = x86_tcode_table[encodings[s.encoding].insn];
if(te.index == 0)
{
no_decompile = true;
break;
}
if(no_decompile)
break;
// add hcode.
// FIXME--do something about arguments and temporaries.
// for now, leave in arg(x) and tmp(x) nodes.
sp.accept(s.encoding, *s.icode, s.dsz);
//expr_count = 0;
tnode *tn;
for(U4 i = 0; i < sp.tnodes_count; ++i)
{
tn = sp.tnodes + i;
if(tn->type == nt_literal)
{
expr[i] = new expr_t();
expr[i]->make_literal32(tn->data[0]);
}
else
if(tn->type == nt_void)
{
// this should NEVER be encountered.
expr[i] = new expr_t();
expr[i]->make_void();
}
else
if(tn->type == nt_asgn)
{
expr[i] = new expr_t();
expr[i]->type = et_asgn;
expr[i]->u.subexpr[0] = NULL;
load_operand(expr[i]->u.subexpr[0], tn->data[0], expr);
if(expr[i]->u.subexpr[0] == NULL)
std::cout << ":(" << std::endl;
const U4 sz0 = sp.get_operand_size(tn->data[0]);
expr[i]->size = sz0;
expr[i]->u.subexpr[0]->size = sz0;
load_operand(expr[i]->u.subexpr[1], tn->data[1], expr);
expr[i]->u.subexpr[1]->size = sz0;
expr[i]->u.subexpr[2] = NULL;
// add hcode.
curbb->hcode.push_back(hcode_t());
curbb->hcode.back().opcode = ht_expr;
curbb->hcode.back().operands.push_back(expr[i]);
}
else
if(tn->type == nt_arg)
{
// et_reg, // subtype is 0 for general register, u.data[0] is argsize_*, u.data[1] is register index number
// et_reg_reg // subtype is 0. u.data[0] is argsize_*, u.data[1] is 1st reg index, u.data[2] is 2nd reg index.
// et_ea16, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[0] is disp.
// et_ea32, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[0] is disp.
// et_ea64, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[0] is disp.
//U2 which_arg = expr->u.subexpr[0]->u.subexpr[0]->u.data[0];
U2 which_arg = expr[tn->data[0]]->u.data[0];
delete expr[tn->data[0]];
expr[tn->data[0]] = NULL;
expr[i] = new expr_t();
expr[i]->size = tn->size;
switch(get_argtype_lo(s.icode->argtype[which_arg]))
{
case argtype_reg:
switch(get_argtype_hi(s.icode->argtype[which_arg]))
{
case argtypehi_reg_r:
expr[i]->type = et_reg;
expr[i]->subtype = 0;
expr[i]->size = ns_void;
expr[i]->u.data[0] = get_argsize_lo(s.icode->argsize[which_arg]);
expr[i]->u.data[1] = s.icode->argvalue[which_arg];
break;
default:
expr[i]->type = et_nodeoperand;
expr[i]->subtype = no_void;
}
break;
case argtype_imm:
expr[i]->type = et_literal32;
expr[i]->subtype = 0;
expr[i]->size = ns_void;
if(get_argtype_hi(s.icode->argtype[which_arg]) == argtypehi_imm_implict8 ||
get_argtype_hi(s.icode->argtype[which_arg]) == argtypehi_imm_cc
)
{
expr[i]->u.data[0] = s.icode->argvalue[which_arg];
}
else
{
U4 j;
for(j = 0; j < which_arg; ++j)
if(get_argtype_lo(s.icode->argtype[j]) == argtype_imm)
break;
if(j == which_arg)
expr[i]->u.data[0] = s.icode->imm;
else
expr[i]->u.data[0] = s.icode->disp;
}
break;
case argtype_mem:
switch(get_argtype_hi(s.icode->argtype[which_arg]))
{
case argtypehi_mem_disp:
{
expr_t *ea = expr[i];
expr[i]->type = et_nodetype;
expr[i]->subtype = nt_deref;
expr[i]->u.subexpr[0] = new expr_t();
expr[i]->u.subexpr[1] = NULL;
expr[i]->u.subexpr[2] = NULL;
ea = expr[i]->u.subexpr[0];
ea->size = ns_void;
if(s.icode->asz == argsize_16)
ea->type = et_ea16;
else
if(s.icode->asz == argsize_32)
ea->type = et_ea32;
else
ea->type = et_ea64;
ea->subtype = s.icode->ea.sreg;
ea->u.data[0] = 31 + 32 * 31;
ea->u.data[1] = s.icode->disp;
}
break;
case argtypehi_mem_mem:
// et_ea16, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[1] is disp. +128 if no seg reg.
// et_ea32, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[1] is disp. +128 if no seg reg.
// et_ea64, // subtype is segreg + 8 * index_shift. u.data[0] is base + 32 * index (use 31 for none). data[1] is disp. +128 if no seg reg.
{
expr_t *ea = expr[i];
if(encodings[s.encoding].suffix.ea == ea_itself)
ea->subtype = s.icode->ea.index_scale * 8 + 128; // no seg reg
else
if(encodings[s.encoding].suffix.ea == ea_noaccess)
ea->subtype = s.icode->ea.index_scale * 8 + s.icode->ea.sreg;
else
{
expr[i]->type = et_nodetype;
expr[i]->subtype = nt_deref;
expr[i]->u.subexpr[0] = new expr_t();
expr[i]->u.subexpr[1] = NULL;
expr[i]->u.subexpr[2] = NULL;
ea = expr[i]->u.subexpr[0];
ea->subtype = s.icode->ea.index_scale * 8 + s.icode->ea.sreg;
}
ea->size = ns_void;
if(s.icode->asz == argsize_16)
ea->type = et_ea16;
else
if(s.icode->asz == argsize_32)
ea->type = et_ea32;
else
ea->type = et_ea64;
ea->u.data[0] = s.icode->ea.base + s.icode->ea.index * 32;
ea->u.data[1] = s.icode->disp;
}
break;
default:
throw std::runtime_error("Unsupported argument type! (1)");
break;
}
break;
default:
throw std::runtime_error("Unsupported argument type! (2)");
//expr[i]->type = et_nodeoperand;
//expr[i]->subtype = no_void;
break;
}
}
else
{
expr[i] = new expr_t();
expr[i]->size = tn->size;
expr[i]->type = et_nodetype;
expr[i]->subtype = tn->type;
for(int j = 0; j < 3; ++j)
{
load_operand(expr[i]->u.subexpr[j], tn->data[j], expr);
}
}
}
}
break;
}
// next insn.
s.insn += s.size;
target += s.size;
// *** check for CS wraparound here !!! (important for 16-bit code...)
if(s.insn == (memory.image_size + memory.image))
{
no_decompile = true;
break;
}
goto again;
}
if(no_decompile)
xgraph[proc.address].decompile = false;
return !no_decompile;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -