花指令参考: https://xz.aliyun.com/news/14062
1、[MoeCTF 2022]chicken_soup
考点:jx+jnx类型花指令
(1)jnz和jz的互补跳转
去除方法:首先定位jz/jnz的跳转位置;然后按d或者u将汇编代码转为数据;然后patch为90;也就是nop指令;然后按c重新转为汇编代码;最后在函数起点按P重新编译函数;最后F5反汇编!
_asm{
//vc内联汇编插入花指令
jz Label;
jnz Label;
_emit 0xC7;//_emit;表示插入一个数据
Label:
}
跳转指令构造花指令
__asm {
push ebx;
xor ebx, ebx;//xor寄存器;此处为1
test ebx, ebx;//zf为1,执行jz
jnz LABEL7;
jz LABEL8;//永真条件跳转
LABEL7:
_emit 0xC7;//显示为db,影响反汇编(p和F5失效)
//上面这行patch成90,然后按C
LABEL8:
pop ebx;
}
(2)例题:[MoeCTF 2022]chicken_soup [HNCTF 2022 WEEK2]e@sy_flower
查壳为32位;分析主函数发现主要是loc_401000和loc_401008对v4数组加密;跟进发现函数被加花指令(类型是jz/jnz永恒跳转类型的花指令)
原理:jz和jnz互补跳转会跳转到E9 C7 45 F8 00;也就说卡在这了;后面的代码IDA无法反汇编;将此处改为nop指令;也就是跳过这个永恒跳转就行。
去花操作:打开opcode bytes的显示;先按d/u将汇编代码转为数据;然后将e8 patch为90;然后按c将数据转回为汇编代码;按P重新编译函数(在loc_401000函数的起点);再按F5进行反汇编
然后得到伪代码继续分析就行!很简单的两个函数;就不写了!
2、[NSSRound#3 Team]jump_by_jump_revenge
考点:花指令
(1)发现花指令
去花:按d或者u转为data
将E9 patch为90;也就是将jmp—>nop
按c还原为汇编代码;在看出开始出按p重新编译;最后按f5得到伪代码
Str2 = "~4G~M:=WV7iX,zlViGmu4?hJ0H-Q*";
for ( i = 0; i < 29; ++i )//处理str1
{
if ( i == 29 )
v1 = __indword(v0);
v0 = (Str1[i] + Str1[(i * i + 123) % 21]) % 96 + 32;
Str1[i] = v0;
}
if