Vector35 / binaryninja-api

Public API, examples, documentation and issues for Binary Ninja
https://binary.ninja/
MIT License
910 stars 207 forks source link

MIPS/PPC: No medium_level_il for code ref #850

Closed bambu closed 3 years ago

bambu commented 6 years ago

Trying to get the MLIL for a call to a function. The only cross ref that it shows is where the address of the function gets stored to a register to then be called with $t9. Getting the mlil at the jalr $t9.

Asm:

...
lw $v0, -0x7fb4($gp) {puts@GOT}
move $t9, $v0
jalr $t9
...

Attempt at getting the mlil:

>>> puts = bv.symbols['puts@GOT']
>>> refs = bv.get_code_refs(puts.address)
>>> refs
[<ref: mipsel32@0x4007d4>]
>>> func, addr = refs[0].function, refs[0].address
>>> llil = func.get_low_level_il_at(addr)
>>> llil
<il: $v0 = [$gp - 0x7fb4].d>
>>> llil.medium_level_il
>>>

In this toy example it is easy to just iterate over the block and find the MLIL_CALL that takes in that example. However, another case that i have seen would require iterating to multiple blocks between the assignment and the call.

bambu commented 6 years ago

This also applies to PPC.

Asm:

lis r11, 0x1002 {0x10020000}
lwz r11, -11888(r11) {__libc_start_main@GOT}
mtctr r11
bctr

Python:

>>> refs = bv.get_code_refs(sym.address)
>>> refs
[<ref: ppc@0x1000afa4>]
>>> func, addr = refs[0].function, refs[0].address
>>> llil = func.get_low_level_il_at(addr)
>>> llil
<il: r11 = [r11 - 0x2e70].d>
>>> llil.medium_level_il
>>>
plafosse commented 6 years ago

I believe this was recently fixed. I'm going to assign this to Brian to verify.

bambu commented 6 years ago

Just re-tested with the MIPS binary from #843 on 1.1.1041. Still has the same issue. Only the load llil is returned as a ref and the mlil for that lllil returns None. I would expect either the mlil for the load to be the function call or for there to be another ref to the indirect call. iirc the latter is how it is handled in x86/x86_64.

also, while i see that the example shows the address is first being loaded into $v0 then moved to $t9 before the jalr $t9. Functions that load directly into $t9 have this same issue.

quend commented 5 years ago

Also still having this issue.

I can find the loads of the GOT function, but cannot find the jalr use of the loaded register -- instead I just get the phi node instruction in the exit basic block. My interim patch for this is to find functions which load the target function and traverse the function again, collecting relative calls, then matching the dest with the concrete address of the called function.

bpotchik commented 3 years ago

This issue is now fixed in build 2.1.2449-dev

See #1371