我正在将一大堆代码从MASM移植到C内联汇编程序(x86,Windows,MS VC) Foolowing不是一个真正的代码,只是欺骗提出一个想法。假设我将一些数据定义为静态数组,甚至是两个标签之间的代码块,我需要获得它的大小。
label1:
bla bla bla
label2:
....
mov eax, (offset label2 - offset label1)
这样的代码在MASM中像魅力一样工作,但在C中我得到以下错误消息: “错误C2425:' - ':'第二个操作数'中的非常量表达式” 我可以编译:
mov eax, offset label1
mov eax, offset label2
我希望编译器在编译时评估(offset label1 - offset label2),但看起来我错了。我也不能添加偏移量(为什么?这些只是编译期间添加的两个整数...?) 当然,我可以得到 mov eax,offset label2 mov edx,offset label1 sub eax,edx 已编译,但这是一个额外的代码,仅用于计算常量。 有人可以解释一下,我的代码有什么问题吗?
这可能是搬迁造成的吗?如何推动它?
期待一个答案, 谢谢。
答案 0 :(得分:0)
在获得所有标签的固定地址之前,真正的汇编程序可能会在几次传递中运行代码。例如,某些跳跃有短的和长的形式,具体取决于你想跳多远。如果标签之间有这样的跳跃,则距离取决于跳转的位置。
C编译器可能会将其中一些内容留给链接器/加载器,而不是在编译时修复这些值。
您可以将地址计算代码简化为两条指令
mov EAX, offset Label2
sub EAX, offset Label1
我认为这不会完全破坏代码的性能。
答案 1 :(得分:0)
是的,它可能是由于重新安置的威胁造成的,也可能是由于长度指令处于相对跳跃的威胁造成的。很可能是因为一些小麻烦,汇编程序编写者采取了简单的方法并实现了1次传递或两次传递编译器,尽快做出最终决定。因此不支持一些方便的表达。
正如评论中已经建议的那样,汇编程序仍然可能支持mov + sub组合。