Delen via


pack pragma

Hiermee geeft u de uitlijning van de verpakking voor structuur, samenvoeging en klasseleden.

Syntaxis

#pragma pack( show )
#pragma pack( push [ ,identifier ] [ ,n ] )
#pragma pack( pop [ , { identifier | n } ] )
#pragma pack( [ n ] )

Parameters

show
(Optioneel) Geeft de huidige bytewaarde weer voor het uitlijnen van de verpakking. De waarde wordt weergegeven met een waarschuwingsbericht.

push
(Optioneel) Pusht de huidige uitlijningswaarde van de verpakking op de interne compilerstack en stelt de huidige uitlijningswaarde in op n. Als n niet is opgegeven, wordt de huidige waarde voor de uitlijning van de verpakking gepusht.

pop
(Optioneel) Hiermee verwijdert u de record boven aan de interne compilerstack. Als n niet is opgegeven met pop, is de verpakkingswaarde die is gekoppeld aan de resulterende record boven aan de stapel de nieuwe uitlijningswaarde voor de verpakking. Als n is opgegeven, bijvoorbeeld #pragma pack(pop, 16), wordt n de nieuwe uitlijningswaarde voor de verpakking. Als u een identifiergebruikt, bijvoorbeeld #pragma pack(pop, r1), worden alle records op de stapel weergegeven totdat de record met identifier is gevonden. Deze record wordt gepopt en de verpakkingswaarde die is gekoppeld aan de record die boven aan de stapel wordt gevonden, wordt de nieuwe uitlijningswaarde voor het inpakken. Als u een identifier gebruikt die niet in een record op de stapel staat, wordt de pop genegeerd.

De instructie #pragma pack (pop, r1, 2) is gelijk aan #pragma pack (pop, r1) gevolgd door #pragma pack(2).

identifier
(Optioneel) Wanneer deze wordt gebruikt met push, wijst u een naam toe aan de record op de interne compilerstack. Wanneer deze wordt gebruikt met pop, worden records van de interne stack verwijderd totdat identifier wordt verwijderd. Als identifier niet wordt gevonden op de interne stack, wordt er niets weergegeven.

n
(Optioneel) Hiermee geeft u de waarde in bytes die moet worden gebruikt voor verpakking. Als de compileroptie /Zp niet is ingesteld voor de module, is de standaardwaarde voor n 8. Geldige waarden zijn 1, 2, 4, 8 en 16. De uitlijning van een lid bevindt zich op een grens die een veelvoud van nis of een veelvoud van de grootte van het lid, afhankelijk van wat kleiner is.

Opmerkingen

Als u inpakken een klas de leden direct na elkaar in het geheugen wilt plaatsen. Dit kan betekenen dat sommige of alle leden kunnen worden uitgelijnd op een grens die kleiner is dan de standaarduitlijning van de doelarchitectuur. pack geeft controle op gegevensdeclaratieniveau. Het verschilt van de compileroptie /Zp, die alleen besturingselement op moduleniveau biedt. pack van kracht wordt bij de eerste struct, unionof class verklaring nadat de pragma is gezien. pack heeft geen effect op definities. Als u pack aanroept zonder argumenten, wordt n ingesteld op de waarde die is ingesteld in de compileroptie /Zp. Als de compileroptie niet is ingesteld, is de standaardwaarde 8 voor x86, ARM en ARM64. De standaardwaarde is 16 voor x64 native en ARM64EC.

Als u de uitlijning van een structuur wijzigt, wordt mogelijk niet zoveel ruimte in het geheugen gebruikt. Mogelijk ziet u echter een verlies van prestaties of krijgt u zelfs een door hardware gegenereerde uitzondering voor niet-uitgelijnde toegang. U kunt dit uitzonderingsgedrag wijzigen met behulp van SetErrorMode.

Zie de volgende artikelen voor meer informatie over het wijzigen van de uitlijning:

  • alignof

  • align

  • __unaligned

  • x64-structuuruitlijningsvoorbeelden

    Waarschuwing

    In Visual Studio 2015 en hoger kunt u de standaardoperators alignas en alignof gebruiken, die in tegenstelling tot __alignof en __declspec( align ) overdraagbaar zijn tussen compilers. De C++-standaard bevat geen adresverpakking, dus u moet nog steeds pack (of de bijbehorende extensie op andere compilers) gebruiken om uitlijningen op te geven die kleiner zijn dan de woordgrootte van de doelarchitectuur.

Voorbeelden

In het volgende voorbeeld ziet u hoe u de packpragma gebruikt om de uitlijning van een structuur te wijzigen.

// pragma_directives_pack.cpp
#include <stddef.h>
#include <stdio.h>

struct S {
   int i;   // size 4
   short j;   // size 2
   double k;   // size 8
};

#pragma pack(2)
struct T {
   int i;
   short j;
   double k;
};

int main() {
   printf("%zu ", offsetof(S, i));
   printf("%zu ", offsetof(S, j));
   printf("%zu\n", offsetof(S, k));

   printf("%zu ", offsetof(T, i));
   printf("%zu ", offsetof(T, j));
   printf("%zu\n", offsetof(T, k));
}
0 4 8
0 4 6

In het volgende voorbeeld ziet u hoe u de push-, pop-gebruikt en syntaxis weergeeft.

// pragma_directives_pack_2.cpp
// compile with: /W1 /c
#pragma pack()   // n defaults to 8; equivalent to /Zp8
#pragma pack(show)   // C4810
#pragma pack(4)   // n = 4
#pragma pack(show)   // C4810
#pragma pack(push, r1, 16)   // n = 16, pushed to stack
#pragma pack(show)   // C4810

// pop to the identifier and then set
// the value of the current packing alignment:
#pragma pack(pop, r1, 2)   // n = 2 , stack popped
#pragma pack(show)   // C4810

Zie ook

Pragma-instructies en de __pragma en _Pragma trefwoorden