我正在从Linux x86机器上的工作编译开始将net-snmp移植到ARM平台(ThreadX OS,而不是linux)
现在程序在init_snmp()函数内崩溃,因为在某些时候内存会发生一些可怕的事情。
然后我面对sizeof()所有数据类型,发现enum在Linux x86上是4个字节,在ARM上是1个字节。
这种不匹配是否有可能对内存分配造成严重破坏?尝试将字符串写入内存时,程序崩溃。
如何在ARM上强制枚举为4字节大?
我正在使用gcc arm-none-eabi进行编译
答案 0 :(得分:7)
这种不匹配是否有可能对内存分配造成严重破坏?
哦,是的。
如何在ARM上强制枚举为4字节大?
C标准说enum变量可能有几乎任何整数类型,大小和签名是实现定义的。因此,枚举通常是有问题的,特别是在嵌入式系统中。这是C语言的一个已知缺陷。
您可以强制枚举为特定编译器的特定大小,但这只是一个快速的&肮脏的修复。
专业的长期解决方案是重写所有代码,以便在任何地方都不依赖于枚举的大小或签名。
答案 1 :(得分:0)
有一种方法可以克服编译器的界限。此示例提供了一种在需要时更改enum
大小的方法。
#include <stdio.h>
enum small_enum {
a
};
enum large_enum {
b = 0x7FFFFFFFFFFFFFFFFF // 2^63-1, you should try 2^31-1
};
int main(){
printf("%d %d\n", sizeof(enum small_enum), sizeof(enum large_enum));
return 0;
}
此代码在Windows 8计算机上运行时提供以下输出:4 8
。通过为其中一个枚举值指定一个大数字,您强制枚举大于编译器定义的值。将其添加到代码中的示例:
enum my_enum {
... //your enums values
MEM_ALLIGNMENT_OF_THE_ENUM = 0x7FFFFFFF
};