如何在 IDA Pro 中获取操作数的字节大小?

逆向工程 艾达 蟒蛇 小精灵
2021-06-16 08:34:08

我试图从 IDA Pro 获取给定指令中所有操作数的字节大小。起初我尝试使用GetOperandValue(ea,n)查看值有多大并计算存储该值所需的字节数,但它不返回前导零,这意味着它不起作用。

现在我试图用它OpHex(ea,n)来获得答案,但它只是返回True(就像OpDecimalOpBinary、 和OpOctal)。

如何找到用于特定指令的操作数的字节数以及为什么OpHex返回 true?

编辑:我当前的解决方案有效,但我仍然想要一个技术上更正确且防弹的解决方案。现在我只是GetOperandValue(ea, op)用来获取所有指令的两个操作数(即使它们没有或只有一个),然后检查以确保操作数值大于FF. 如果它大于FF我只是假设它是一个地址,在这种情况下是四个字节。如果两个操作数都满足这个条件,我将大小分配为 8 个字节。

这暂时有效,但在最终迁移到其他架构时会遇到困难(现在我只是在使用 x86-64)。

2个回答

似乎没有直接的方法来实现这一目标。但是您可以查看IDA SDK 文档的这个页面

根据上一页的描述,我们可以写一个小辅助函数:

def size_of_operand(op):
    tbyte = 8
    dt_ldbl = 8
    n_bytes = [ 1, 2, 4, 4, 8,
            tbyte, -1, 8, 16, -1,
            -1, 6, -1, 4, 4,
            dt_ldbl, 32, 64 ]
    return n_bytes[op.dtype]

现在我们可以使用命令

insn = idautils.DecodeInstruction(ScreenEA())
index_of_operand = 0
size_of_operand(insn.Operand[index_of_operand])

获取操作数的大小。

例如,对于xor al, al,它返回 1。对于pop ebp,它返回 4。

你在寻找类似的东西吗

Message("%s\n" , GetCurrentLine());
Message("%x\n" , ItemSize(ScreenEA()));

这将给出如下结果

.text:010328BB 56                            push    esi
1
.text:010328BC BE 10 42 05 01                mov     esi, offset unk_1054210
5
.text:010328C1                               cmp     byte_1054309, bl
6
.text:010328C1 38 1D 09 43 05 01             cmp     byte_1054309, bl
6