在我们的代码中,我们曾经有这样的东西:
*(controller->bigstruct) = ( struct bigstruct ){ 0 };
这曾经很好用,然后我们升级了 GCC 版本,突然开始看到堆栈溢出。查看程序集,旧的 GCC 代码(2.x)基本上是这样做的:
memset(controller->bigstruct, 0, sizeof(struct bigstruct));
新的 GCC (3.4.x) 正在这样做
struct bigstruct temp = { 0 };
controller->bigstruct = temp;
在查看了 C99 规范后,我明白了原因;C99 基本上要求堆栈上存在匿名结构。这是一个很好的概念,但这个结构有 4 MB 大,而且只打算存在于堆上!
我们已经使用了我们自己的“初始化”函数来显式设置成员,但这很丑陋并且令人头疼。我不认为 memset 是一个合适的解决方案,因为我不知道 0 的位值是该类型的适当零值(挑剔,我知道,但你在那里;我不介意编译器会这样做,因为它可以知道)
初始化这样的大型结构的“正确”或至少最好的方法是什么?
进一步澄清为什么我认为 memset 不是解决方案: 未显式初始化的成员的初始化规则与静态初始化相同,如下所示: - 如果它具有指针类型,则将其初始化为空指针;- 如果它具有算术类型,则将其初始化为(正或无符号)零;...
'memset' 会将内存设置为位模式零,这不一定是同一件事。想象一个不使用 IEEE 浮点数的系统。不寻常,但由 C 支持。 0.0 的表示不一定意味着“所有位为零”,它可以是处理器方便的任何东西。