Keil Logo

Variable Alignment

The __packed keyword specifies byte alignment for a single data object. This means that:

  • No padding gaps are inserted to align struct members.
  • Objects defined with the __packed keyword are read and written using byte instructions.

By default, the CARM Compiler aligns:

  • 1-byte data objects on 1-byte boundaries,
  • 2-byte data objects on 2-byte boundaries,
  • 4-byte and 8-byte data objects on 4-byte boundaries.

The default alignment used by the compiler provides reasonably efficient instruction sequences to access variables without consuming a whole word for smaller (1-byte and 2-byte) data types. Of course, pad bytes may be inserted to force alignment of objects larger than 1 byte.

The __packed keyword is useful for those applications that require efficient use of memory without regard for the the number of instructions required to access variables or for those applications that require access to byte-aligned variables (for example data inter-communication protocols).

The PACK directive is useful when variables must be aligned on 1-byte, 2-byte, or 4-byte boundaries.

The following example demonstrates how variables and structures are aligned when the __packed keyword and PACK directive are specified.

struct s1  {
  char            c;
  int             i;
  short           s;
  long long      ll;
} __packed;                   // all members are byte aligned

typedef __packed int  *pint;  // pointer to byte-aligned int

struct s2  {
  char            c;
  __packed int   ip;          // byte-alignment
  __packed short sp;          // byte-alignment
  int             i;          // default alignment (4-byte boundary)
};

#pragma SAVE                  // save current pack setting
#pragma PACK(2)               // alignment 2-byte for following definitions

struct s3  {
  char            c;
  int             i;          // uses 2-byte alignment due to pack
};

#pragma PACK(1)               // alignment 1-byte for following definitions

struct s4  {
  char            c;
  int             i;          // uses 1-byte alignment due to pack
};

#pragma RESTORE               // restore default pack setting


struct s1  s1;
struct s1 *ps1;
pint       pi;
struct s2  s2;
struct s3  s3;
struct s4  s4;

long long  ll;
int         i;
short       s;

void main (void)  {
  ps1     = &s1;

  s1.s    = 5;
  s1.i    = 123456789;
  ps1->ll = 0x1234567890ABCDEFLL;

  s = s1.s;
  i = s1.i;
  ll = ps1->ll;

  i      = *pi;

  s2.c   = 0;
  s2.ip  = 0x12345678;
  s2.sp  = 0x1234;
  s2.i   = 0x89ABCDEF;

  s3.c   = 0;
  s3.i   = 1;

  s4.c   = s3.c;
  s4.i   = s3.i;
}

Related Knowledgebase Articles

  Arm logo
Important information

This site uses cookies to store information on your computer. By continuing to use our site, you consent to our cookies.

Change Settings

Privacy Policy Update

Arm’s Privacy Policy has been updated. By continuing to use our site, you consent to Arm’s Privacy Policy. Please review our Privacy Policy to learn more about our collection, use and transfers
of your data.