2015-04-02 12 views
5

Compiler typischerweise nachlauf Polsterung auf Strukturen einzufügen Ausrichtung Einschränkungen zu erfüllen, wenn sie in Arrays verwendet:Nachlauf padding in interne Struktur

// Size 4, alignment 2 
struct A { 
    uint16_t x; 
    uint8_t y; 
    // Padding 1 byte 
}; 

// Size 6, alignment 2 
struct B { 
    struct A xy; 
    uint8_t z; 
    // Padding 1 byte 
}; 

Nun Kombination dieser mit internen Struktur berücksichtigen:

struct AB { 
    struct { 
     uint16_t x; 
     uint8_t y; 
    } xy; 
    uint8_t z; 
}; 

Folgendes könnte in 4 Bytes passen, während die Ausrichtungsbeschränkungen nicht verletzt werden. Auch interne Struktur xy hat keinen Typ, der an anderer Stelle verwendet werden könnte, so Trailing Padding für es ist nicht erforderlich.

Nachteil ist, dass Mitglied xy wäre inkompatibel mit struct A, aber es ist kein Grund, warum es so sein sollte, wie sie in verschiedenen Typdefinitionen sind.

Kann der Compiler diese Größenoptimierung durchführen?

Oder anders ausgedrückt, verlangt der Standard, dass 2 Strukturen mit gleichen Elementen immer zu gleichem Layout führen?

+0

Ich denke, dass der Compiler dies tun würde, da der Standard den Compiler nicht benötigt, um Strukturen zu puffern. – qbt937

Antwort

1

Die Antwort wird wahrscheinlich durch den Begriff kompatible Typen gegeben. Wenn t1 und t2 kompatible Typen sind, kann ein Zeiger auf t1 verwendet werden, um auf Speicher zuzugreifen, der mit dem Typ t2 festgelegt wurde.

Im C11 Standard:

6.2.7 kompatible Art und Verbundtyp

  1. ... Darüber hinaus sind zwei Struktur, Vereinigung oder Enumerationstypen wenn sie in separaten Übersetzungseinheiten erklärt kompatibel sind Ihre Tags und Member erfüllen die folgenden Anforderungen: Wenn einer mit einem Tag deklariert ist, muss der andere mit demselben Tag deklariert werden. Wenn beide innerhalb ihrer jeweiligen Übersetzungseinheiten abgeschlossen sind, gelten die folgenden zusätzlichen Anforderungen: zwischen ihren Mitgliedern muss eine Eins-zu-eins-Korrespondenz bestehen, so dass jedes Paar entsprechender Mitglieder mit kompatiblen Typen deklariert wird; Wenn ein Mitglied des Paars mit einem Ausrichtungsspezifizierer deklariert ist, wird der andere mit einem entsprechenden Ausrichtungsspezifizierer deklariert. und wenn ein Mitglied des Paares mit einem Namen deklariert ist, wird das andere mit dem gleichen Namen deklariert. ...

Zwei structs, die nicht den gleichen Tag haben, sind nicht kompatible Typen, und ich sehe nichts, die sie zwingen, das gleiche Layout zu haben.

+1

In der Tat, darüber habe ich auch nachgedacht. Gut zu sehen, dass jemand anderes zu demselben Schluss kam. – user694733