joxeankoret / pyew

Official repository for Pyew.
GNU General Public License v2.0
383 stars 95 forks source link

Improper division into basic blocks #36

Open 0x123456789 opened 6 years ago

0x123456789 commented 6 years ago

Hello, I try to enumerate all basic blocks using the following code:

from pyew import CPyew

def main(f):
    pyew = CPyew(plugins=True, batch=True)
    pyew.loadFile(f)
    ca = pyew._anal
    for _, block in ca.basic_blocks.iteritems():
        for instr in block.instructions:
            print "%s %s" % (instr.mnemonic, instr.operands)
        print '--------------------------------------------'

if __name__ == "__main__":
    if len(sys.argv) == 1:
        print "Usage:", sys.argv[0], "<program file>"
    else:
        main(sys.argv[1])

It get's me basic blocks, but some of them are incorrect because the last instruction in them is not ret, call, jmp and etc. Here the example (here you can see that the last block instruction is mov): code

joxeankoret commented 6 years ago

Can you share a binary to reproduce?

0x123456789 commented 6 years ago

Thanks for the quick response. Yes, here is exe file. It's a very simple program, just several asm instructions: ida

UPD: I use Windows

gg.zip

0x123456789 commented 6 years ago

Sorry, It's my mistake, I did not fully understand what a basic block. It also can be like pyew return (for example on the image above (there IDA's CFG) or the image below). gg

But I notice another thing, the code above enumerates basic blocks, but it doesn't return block with sub's (see the screen from IDA). Why is this block missing?

0x123456789 commented 6 years ago

UPD: I thought about blocks, and I realized that the case on the image in question is really probably a mistake because 'call' and 'mov' can't be in one basic block if 'call' is the first. ('call' should split this block) .