First of all, I love oalabs. Below of code is copied from his research, and I get a lot from just repeat it. And maybe there are also bogus-control-flow in this sample however.
2619862c382d3e375f13f3859c6ab44db1a4bce905b4a617df2390fbf36902e7 on the malshare(by the oalabs)
- Control Flow Flattening
- Deobfuscation - Recovering an ollvm
- Control Flow Unflattening
according to the jmp [register]
Our approach is to seperate the dispatcher bb from the payload bb. For each dispatcher bb the code is emulated with all conditions to
generate the conditional jump addresses. The bb is then replaced with a simple compare and conditional jmp. Emulation is done with Dumpulator.
Once the dispatcher has been deobfuscated we should be able to
see the control flow for the payload bb, and futher simplify the dispatcher using more traditional tools, possibly removing it completely.
- if the jump is relative it’s for a code bb
- if the jump is register then it’s a cf bb
- if there is a ret this is the end
build a table of bb the start is next head after jmp, end is jmp emulate patch the jmp for each table entry
There are two dispatcher bb formats,
one that uses cmovl, cmovz,
and one that uses setl and setz. We need to
match both patterns and
determine the type of condition for our jmp statement, and the eax cmp value. For each bb record the following information so it can be used in our emulator.
- bb start
- bb end
- add cmov instruction
- type of cmov instruction (l,z)
- eax cmp value
- jmp register
Results: (bb_start, bb_end, eax_value, jmp_condition,jmp_condition_address, jmp_register)
# Basic blocks for dispatcher
bb_table means the Dispatcher bb, and this bb has two formats that uses (cmovl, cmovz) or uses (setl and setz)
bb_orig_table means the origin payload bb
For each dispatcher bb emulate the block both satisfying the condition and not satisfying it to produce both the jmp address for the conditional jmp and the jmp address for the unconditional jmp.
DUMP_FILE = '13.25.dmp'
- cmovl setl————jl
- cmovz setz————jz
so why this???
cmovl rdx, r12 ; Move if Less (SF!=OF)
patch_jmp_cond_start jmp_rel_statisfied patch_jmp_start jmp_rel