The keyword __attribute__ allows you to specify special
attributes of struct and union types when you define such
types. This keyword is followed by an attribute specification inside
double parentheses. Three attributes are currently defined for types:
aligned, packed, and transparent_union. Other
attributes are defined for functions (see section Declaring Attributes of Functions) and
for variables (see section Specifying Attributes of Variables).
You may also specify any one of these attributes with `__'
preceding and following its keyword. This allows you to use these
attributes in header files without being concerned about a possible
macro of the same name. For example, you may use __aligned__
instead of aligned.
You may specify the aligned and transparent_union
attributes either in a typedef declaration or just past the
closing curly brace of a complete enum, struct or union type
definition and the packed attribute only past the closing
brace of a definition.
aligned (alignment)
struct S { short f[3]; } __attribute__ ((aligned (8));
typedef int more_aligned_int __attribute__ ((aligned (8));
force the compiler to insure (as fas as it can) that each variable whose
type is struct S or more_aligned_int will be allocated and
aligned at least on a 8-byte boundary. On a Sparc, having all
variables of type struct S aligned to 8-byte boundaries allows
the compiler to use the ldd and std (doubleword load and
store) instructions when copying one variable of type struct S to
another, thus improving run-time efficiency.
Note that the alignment of any given struct or union type
is required by the ANSI C standard to be at least a perfect multiple of
the lowest common multiple of the alignments of all of the members of
the struct or union in question. This means that you can
effectively adjust the alignment of a struct or union
type by attaching an aligned attribute to any one of the members
of such a type, but the notation illustrated in the example above is a
more obvious, intuitive, and readable way to request the compiler to
adjust the alignment of an entire struct or union type.
As in the preceding example, you can explicitly specify the alignment
(in bytes) that you wish the compiler to use for a given struct
or union type. Alternatively, you can leave out the alignment factor
and just ask the compiler to align a type to the maximum
useful alignment for the target machine you are compiling for. For
example, you could write:
struct S { short f[3]; } __attribute__ ((aligned));
Whenever you leave out the alignment factor in an aligned
attribute specification, the compiler automatically sets the alignment
for the type to the largest alignment which is ever used for any data
type on the target machine you are compiling for. Doing this can often
make copy operations more efficient, because the compiler can use
whatever instructions copy the biggest chunks of memory when performing
copies to or from the variables which have types that you have aligned
this way.
In the example above, if the size of each short is 2 bytes, then
the size of the entire struct S type is 6 bytes. The smallest
power of two which is greater than or equal to that is 8, so the
compiler sets the alignment for the entire struct S type to 8
bytes.
Note that although you can ask the compiler to select a time-efficient
alignment for a given type and then declare only individual stand-alone
objects of that type, the compiler's ability to select a time-efficient
alignment is primarily useful only when you plan to create arrays of
variables having the relevant (efficiently aligned) type. If you
declare or use arrays of variables of an efficiently-aligned type, then
it is likely that your program will also be doing pointer arithmetic (or
subscripting, which amounts to the same thing) on pointers to the
relevant type, and the code that the compiler generates for these
pointer arithmetic operations will often be more efficient for
efficiently-aligned types than for other types.
The aligned attribute can only increase the alignment; but you
can decrease it by specifying packed as well. See below.
Note that the effectiveness of aligned attributes may be limited
by inherent limitations in your linker. On many systems, the linker is
only able to arrange for variables to be aligned up to a certain maximum
alignment. (For some linkers, the maximum supported alignment may
be very very small.) If your linker is only able to align variables
up to a maximum of 8 byte alignment, then specifying aligned(16)
in an __attribute__ will still only provide you with 8 byte
alignment. See your linker documentation for further information.
packed
enum, struct, or
union type definition, specified that the minimum required memory
be used to represent the type.
Specifying this attribute for struct and union types is
equivalent to specifying the packed attribute on each of the
structure or union members. Specifying the `-fshort-enums'
flag on the line is equivalent to specifying the packed
attribute on all enum definitions.
You may only specify this attribute after a closing curly brace on an
enum definition, not in a typedef declaration.
transparent_union
union type definition, indicates
that any variable having that union type should, if passed to a
function, be passed in the same way that the first union member would be
passed. For example:
union foo
{
char a;
int x[2];
} __attribute__ ((transparent_union));
To specify multiple attributes, separate them by commas within the double parentheses: for example, `__attribute__ ((aligned (16), packed))'.