警告#13212:引用需要堆栈对齐功能的EBX
warning #13212: Reference to ebx in function requiring stack alignment
我试图用ICC 2018编译以下代码:
__asm {
mov ebx, xx ;xx address to registers
}
其中XX是INT16类型的。这是我功能中的第一个指令。
我使用上述装配代码获得以下警告:警告#13212:引用需要堆栈对齐的功能中的EBX
令人惊讶的是,当我用EAX或ESI替换EBX时,我看到警告消失了。据我所知,我无法理解为什么我只看到EBX的问题,EBX和EAX都具有相同的架构(32位寄存器(。
另外,当我与ICC 2013编译相同的代码时,我没有看到警告。
谁能帮我解决此警告?
谢谢!
选择平台上的编译器(ICC模拟MSVC的行为(使用EBX使用EBX保存原始堆栈指针值,如果需要附加对齐。因此,您不能安全地覆盖它。该程序的行为将变得不确定。编译器警告只是告诉您这一点。
为了帮助保存/还原受汇编块影响的所有寄存器,建议使用带有所谓的Clobber列表的扩展语法。您的示例使用MSVC风格的__asm{...}
语法。在MSVC风格的语法中,编译器检测您触摸的寄存器并为您保存/还原它们。ICC还支持带有Clobber列表的扩展ASM的类似GCC的符号:asm("...":::)
。它还支持更简单的GCC asm("...")
,而无需Clobber列表部分。有关更多详细信息,请参阅此问题(感谢Peter Cordes的链接和解释(。
我在学习使用Clobber列表时发现有用的文档(我一直在使用它,因为不可能记住它的人类不友好的语法(:
- https://www.ibiblio.org/gferg/ldp/gcc-inline-sembly-howto.html#s5
- https://software.intel.com/en-us/node/694235
只有在以下情况下可以安全地使用没有clobber列表的简单内联装配块:
- 该块的说明不会修改ABI中定义的寄存器。因此,GPRS,堆栈计数器,标志应不受影响;如果函数中有浮点计算,则FPU/向量寄存器也没有限制。甚至内存写入也可能导致错误,因为编译器依靠已知值驻留在内存中。相比之下,可以发出
INT3
,HLT
,WRMSR
等指令,该指令触摸不寄存器或仅影响编译器不使用的系统寄存器。但是,大多数此类说明都是特权的,不能在用户应用程序中使用。也可以读取所有可用寄存器,只要此类读取没有副作用。 - 汇编器块是函数正文中的仅语句。在这种情况下,它必须遵守调用所选平台的惯例:如何通过函数的论点,应放置其退出代码等。该块还需要应对编译器生成的序言和具有其具有其具有其的ECILOGUE代码块的块自己关于登记册的假设。他们的代码并不严格稳定,也不是便携式,也不保证在不同的优化级别上相同。使用X86的GCC,我无法禁用序言/结语,因此仍然存在一些违反编译器假设的风险。
- 您可以保存所有笨拙的寄存器,然后将其恢复。这是相对容易的,因为您可以看到自己的汇编代码,并且可以判断寄存器是否通过它修改。但是,犯错,编译器将不会在这里指出。ICC 2018非常好的警告是非常好的,即使它可能只是将ASM块视为黑匣子。
- 您从编译器中"偷走"了一个寄存器。GCC允许使用
register asm
语句(不记得相同的技巧是否与其他编译器一起使用(。因此,您可以声明变量绑定到某个寄存器。请注意,这种技术会减少编译器可用于寄存器分配阶段的寄存器数量,并将降低其生成的代码质量。索要寄存器太多,编译器将无助并拒绝工作。同样,人们也不能要求登记处具有专用角色,要从编译器中删除,例如堆栈指针或程序计数器。
也就是说,带有Clobber列表的扩展asm
语法提供了一个不错的选择。它将asm
节从黑匣子转到一个内联内部"函数",该内部"函数"声明其自己的输入,输出和资源,它覆盖了与外部功能共享的。
- 如何理解将半精度指针转换为无符号长指针和相关的内存对齐
- 如何创建一个QTableWidgetItem,用长文本右对齐,左边有省略号
- 我可以检测和更改 gcc/g++ 中结构的当前数据对齐设置吗?
- 64位机器上的C++内存对齐
- 为什么我可以将变量存储在不是其最小对齐方式的倍数的地址?
- 使 std::vector 分配对齐内存的现代方法
- C++ cout 将双精度对齐到精度 2 并正确对齐
- 在 64 位边界上对齐C++结构数组?
- 使用 g++7 构建的代码在访问未对齐的内存时崩溃
- 在 capnp FlatArrayMessageReader 的对齐内存缓冲区中接收 zmq 消息
- 是否值得对齐变量?
- 初始化派生结构的基部分/意外打包派生结构字段以对齐基结构的间隙
- 对齐和对齐的实际用例C++关键字
- 如何减少代码的运行时间以对齐文本?
- 指向包含对齐 C 结构C++类的 C 指针的对齐问题
- Linux C++ 中的页面对齐内存分配
- C++ 类层次结构中的"对齐"是什么意思?
- 运行时错误:引用绑定到类型"int"的未对齐地址0xbebebebebebebec6,这需要 4 个字节对齐 (stl_vector.h)
- 具有调整对齐方式的类型定义
- 警告#13212:引用需要堆栈对齐功能的EBX