0

I am verifying the struct member initialization. The compiler is gcc 4.8.5and the code is like this:

#include <stdio.h>

typedef struct
{
        int m1;
        int m2;
} A;

int main(void) {
        A a;
        A b = {.m1 =1};
        A c = {1};

        printf("%d, %d\n", a.m1, a.m2);
        printf("%d, %d\n", b.m1, b.m2);
        printf("%d, %d\n", c.m1, c.m2);
        return 0;
}

The result of executing it is:

-1498088800, 32765
1, 0
1, 0

And the assembly code is:

0x0000000000400530 <+0>:     push   %rbp
0x0000000000400531 <+1>:     mov    %rsp,%rbp
0x0000000000400534 <+4>:     sub    $0x30,%rsp
0x0000000000400538 <+8>:     movq   $0x0,-0x20(%rbp)
0x0000000000400540 <+16>:    movl   $0x1,-0x20(%rbp)
0x0000000000400547 <+23>:    movq   $0x0,-0x30(%rbp)
0x000000000040054f <+31>:    movl   $0x1,-0x30(%rbp)
0x0000000000400556 <+38>:    mov    -0xc(%rbp),%edx
0x0000000000400559 <+41>:    mov    -0x10(%rbp),%eax
0x000000000040055c <+44>:    mov    %eax,%esi
0x000000000040055e <+46>:    mov    $0x400640,%edi
0x0000000000400563 <+51>:    mov    $0x0,%eax
0x0000000000400568 <+56>:    callq  0x400410 <printf@plt>

From the assembly code:

0x0000000000400538 <+8>:     movq   $0x0,-0x20(%rbp)
0x0000000000400540 <+16>:    movl   $0x1,-0x20(%rbp)
0x0000000000400547 <+23>:    movq   $0x0,-0x30(%rbp)
0x000000000040054f <+31>:    movl   $0x1,-0x30(%rbp)

I can see if I initialize part members of structure, other members are default set to 0. Does this comply with C specification? Or just depends on the compiler?

Nan Xiao
  • 16,671
  • 18
  • 103
  • 164

2 Answers2

4

They are granteed to be zero.

Quote from N1256 6.7.8 Initialization

10 If an object that has automatic storage duration is not initialized explicitly, its value is indeterminate. If an object that has static storage duration is not initialized explicitly, then:
— if it has pointer type, it is initialized to a null pointer;
— if it has arithmetic type, it is initialized to (positive or unsigned) zero;
— if it is an aggregate, every member is initialized (recursively) according to these rules;
— if it is a union, the first named member is initialized (recursively) according to these rules.

21 If there are fewer initializers in a brace-enclosed list than there are elements or members of an aggregate, or fewer characters in a string literal used to initialize an array of known size than there are elements in the array, the remainder of the aggregate shall be initialized implicitly the same as objects that have static storage duration.

MikeCAT
  • 73,922
  • 11
  • 45
  • 70
  • "— if it is an aggregate, every member is initialized (recursively) according to these rules;" so if one field is another structure, which has no member initialized, then according to "If an object that has automatic storage duration is not initialized explicitly, its value is indeterminate." its fileds will have random values? Or "this rules" means only ones starting with '-'? – jbulatek Jul 07 '20 at 11:03
0

If you use brace initialisation and only partially initialise the structure, then the remainder are set in exactly the same way as they would be if the structure instance had static storage duration.

Note that the behaviour of printf("%d, %d\n", a.m1, a.m2); is undefined due to a not being initialised. Although your citing the output assembly somewhat mitigates your including that case.

Bathsheba
  • 231,907
  • 34
  • 361
  • 483