Frage zur Größe eines struct
-
Hi,
ich habe folgendes Beispiel:
#include <stdio.h> struct myStruct { char a; // 1 byte int b; // 4 byte double c; // 8 byte }; union myUnion { char a; int b; double c; }; int main(void) { printf("Size of myStruct: %d byte\n", sizeof(struct myStruct)); printf("Size of myUnion: %d byte\n", sizeof(union myUnion)); return 0; }
und erhalte als Ergebnis 16 byte für das struct??? Nach meiner Rechnung sind es 1+4+8 = 13 byte.
Wo kommen die restlichen 3 byte her?
-
Das sind sogenannte padding bytes
https://thoughts-on-coding.com/2020/09/14/structure-padding-in-cpp/
-
Siehe auch: https://en.cppreference.com/w/c/language/object (ein wichtiger Satz ist hier "In order to satisfy alignment requirements of all members of a struct, padding may be inserted after some of its members.")
oder auch mal was auf Deutsch: https://learn.microsoft.com/de-de/cpp/c-language/alignment-c?view=msvc-170
-
@ledi
In deinem Beispiel heisst das konkret dassb
an einem durch 4 teilbaren Offset liegen muss, daint
üblicherweise ein "alignment requirement" von 4 hat.
Der Offset direkt hintera
wäre allerdings 1. Um zu einem durch 4 teilbaren Offset zu kommen, müssen 3 sog. "padding bytes" eingefügt werden (1 + 3 = 4).c
muss dann üblicherweise an einem durch 8 teilbaren Offset liegen (alignment requirement vondouble
). Dort passt es dann so schon wieder, da 4 + 4 = 8, und 8 ist ja bereits durch 8 teilbar.Zuletzt muss dann noch sichergestellt werden dass auch die Grösse der Struktur zum alignment requirement der Struktur passt. Das alignment requirement der Struktur ist einfach das grösste alignment requirement eines Struktur-Members, in diesem Fall also auch wieder 8. Die Grösse ohne zusätzliches Padding ist 8 + 8 = 16, und das ist auch direkt durch 8 teilbar. D.h. es bleibt bei 16.
Anderes Beispiel:
struct myStruct2 { int x; // 4 byte double y; // 8 byte char z; // 1 byte };
x
kommt auf Offset 0, dazu gibt es nicht viel zu sagen.Der Offset direkt hinter
x
ist 4. Der Offset vony
muss aber durch 8 teilbar sein. Also kommen hier 4 padding bytes dazwischen undy
bekommt den Offset 8.Der Offset direkt hinter
y
ist 16. Daz
nur ein alignment requirement von 1 hat passt es überall.z
bekommt also den Offset 16.Der Offset direkt hinter
z
ist 17. Auf Grund des Membersy
ist das alignment requirement vonmyStruct2
allerdings 8. D.h. die Grösse vonmyStruct2
muss durch 8 teilbar sein, und 17 ist eben nicht durch 8 teilbar. Daher werden hinterz
noch 7 weitere padding bytes eingefügt um die Grösse auf einen durch 8 teilbaren Wert zu bringen.Daher ist die Grösse von
myStruct2
17 + 7 = 24.