sizeof rundet?



  • hallo,
    heute ist mir etwas seltsames bei der Verwendung von sizeof(..) aufgefallen:

    class test
    {
    public:
    	int   lala1[2];
    	float lala2;
    	char  lala3[24];
    	float lala4[13];
    	char  lala5[18];
    };
    
    sizeof(test) -> 0x6C
    

    soweit, sogut. Wenn ich aber die Klasse leicht abändere:

    class test
    {
    public:
    	int   lala1[2];
    	float lala2;
    	char  lala3[24];
    	float lala4[13];
    	char  lala5[17]; //<---
    };
    
    sizeof(test) -> 0x6C
    

    Warum gibt sizeof immernoch 0x6C aus? Erst wenn ich Größenänderungen im 2 Byte Bereich mache, gibt sizeof einen neuen Wert aus. Allerdings auch dann noch falsch:

    lala5[16] -> 0x68 sollte doch erst bei [14] kommen?!

    greetz KN4CK3R



  • http://de.wikipedia.org/wiki/Speicherausrichtung

    2*4 + 4 + 24*1 + 13*4 + 18 = 106

    In deinem Compiler ist wahrscheinlich ein 4 Byte-Alignment eingestellt, also wird auf das nächste Vielfache von 4 "gerundet", also 108 = 0x6C.
    Wenn du jetzt 2 char (Byte) runter gehst passt du genau in ein Vielfaches von 4 104 = 0x68.



  • Nicht sizeof rundet, sondern der Compiler fügt hier padding bytes ein.

    http://de.wikipedia.org/wiki/Padding



  • aber das ist doch total fehlerlastig, wenn ich das zB bei memcpy benutze oder?
    In einem Fall wird zuviel kopiert, im anderen zu wenig.

    Edit: zu wenig kann ja gar nicht kopiert werden. Das Überschüssige ist also nur leer. Danke für die Aufklärung.

    greetz KN4CK3R



  • KN4CK3R schrieb:

    aber das ist doch total fehlerlastig, wenn ich das zB bei memcpy benutze oder?

    Nein, es wird sicher genügend kopiert. Je nachdem halt Speicher, den du nicht verwendest.

    In C++ solltest du mit memcpy() vorsichtig sein - angewendet auf Non-PODs kann es schnell einmal zu undefiniertem Verhalten führen. Benutze lieber die Kopiermöglichkeiten der Objektorientierung - Kopierkonstruktor für einzelne Objekte, std::copy() für Arrays oder Container.



  • KN4CK3R schrieb:

    aber das ist doch total fehlerlastig, wenn ich das zB bei memcpy benutze oder?
    In einem Fall wird zuviel kopiert, im anderen zu wenig.

    Edit: zu wenig kann ja gar nicht kopiert werden. Das Überschüssige ist also nur leer. Danke für die Aufklärung.

    greetz KN4CK3R

    Bitte lies nach was Padding heisst/ist.
    Noch ein Wort dass du nachschlagen solltest: Alignment.



  • rean schrieb:

    In deinem Compiler ist wahrscheinlich ein 4 Byte-Alignment eingestellt, also wird auf das nächste Vielfache von 4 "gerundet", also 108 = 0x6C.

    Hallo,
    mit der Compilereinstellung hat das gar nicht so viel zu tun. Das erste Feld der Struktur ist ein int-Array, also muss die Struktur mindestens genauso ausgerichtet werden wie int.



  • Bashar schrieb:

    rean schrieb:

    In deinem Compiler ist wahrscheinlich ein 4 Byte-Alignment eingestellt, also wird auf das nächste Vielfache von 4 "gerundet", also 108 = 0x6C.

    Hallo,
    mit der Compilereinstellung hat das gar nicht so viel zu tun. Das erste Feld der Struktur ist ein int-Array, also muss die Struktur mindestens genauso ausgerichtet werden wie int.

    Naja aber wer sagt dass int auf einer 4 Byte Grenze ausgerichtet werden muss? Hmmmm?
    Auf x86 (und x64) CPUs ist das nämlich schonmal nicht so.
    Eine "int + char" struct dürfte daher gerne 5 Byte haben.



  • Der Grund für die Ausrichtung von int sei mal dahingestellt (ich vermute, dass es deutlich performanter ist), aber der Grund für die Ausrichtung der Struktur lässt sich darauf zurückführen.



  • Bashar schrieb:

    Der Grund für die Ausrichtung von int sei mal dahingestellt (ich vermute, dass es deutlich performanter ist), aber der Grund für die Ausrichtung der Struktur lässt sich darauf zurückführen.

    Ja, natürlich. Ich wollte nur darauf hinweisen dass es nicht so sein muss.


Anmelden zum Antworten