【发布时间】:2013-08-18 05:39:21
【问题描述】:
我正在构建一个 Windows Phone 项目,其中的一些部分正在组装中。我的程序集文件处于 ARM 模式 (CODE32),它会尝试跳转到我知道已编译为 Thumb 的 C 函数。代码如下:
ldr r12, [pFunc]
mov pc, r12
pFunc
dcd My_C_Function
这是奇怪的事情。 sn-p 中pFunc 的值是指向函数thunk 的指针加一。也就是说,第 0 位被设置,好像跳转目标是 Thumb,跳转指令是 BX。但重击显然是 ARM! thunk 加载函数体的地址加一并对其执行 BX,正确切换模式。
尝试 BX 到该地址可能会崩溃,因为这会切换模式并尝试在 Thumb 模式下执行 ARM 代码不是一个好主意。尝试简单地跳转到该地址(就像当前代码一样)也可能会崩溃,因为 PC 最终会未对齐。
理论上,我可以手动清理第 0 位然后跳转,但我的想法肯定有一些错误。 thunk 是由 C 编译器生成的 - 对吧? C 编译器知道 thunk 是 ARM 代码。 pFunc 下的地址是由链接器生成的,因为它是一个跨模块调用。所以低位被链接器放在那里;为什么链接器不知道这些 thunk 是 ARM?
请解释一下?
我现在没有 WP8 设备,所以无法在真实硬件中试用。盯着生成的代码是我唯一的调试技巧:(
编辑:但是如果这些 thunk 不是 ARM,而是 Thumb-2 怎么办? Thumb-2 支持一些 32 位命令 IIRC。它们的编码是否与 ARM 模式相同?无论如何,Thumb-2 如何解码命令?
【问题讨论】:
-
如果您已经在汇编中定义了所有标签(使用 gnu 汇编器,您在拇指标签之前使用 .thumb_func,不确定如何使用其他工具链执行此操作),并且 C 应该自行处理.从那里,汇编器、编译器和链接器将根据目的地注意 bx 到偶数或奇数地址。
-
汇编器是 MASM 的 ARM 风格。我会检查我是否可以相应地装饰标签。但在一般情况下,理论上我可能不知道其他对象文件处于什么模式。如果它们是第三方对象怎么办?我希望链接器对此很聪明。
-
这是我的观点,我希望链接器对此很聪明,如果您有反汇编器来检查并确保工具正确,请使用反汇编器。
-
这正是我正在做的,缺少设备。
标签: assembly arm windows-phone thumb