Skip to main content

IAR Embedded Workbench for Arm 9.70.x

構造体型

このセクションの内容:

structのメンバは、宣言順で連続して格納されます。最初のメンバは、最下位のメモリアドレスに格納されます。

構造体型のアライメント

struct型およびunion型は、一番高いアライメント要求のあるメンバと同じアライメントとなります。このアライメント要求は構造体のメンバにも適用されます。アライメントされた構造体オブジェクトの配列を可能にするに、構造体のサイズはアライメントの偶数倍に調整されます。

一般的なレイアウト

structのメンバは、常に宣言で指定された順に割り当てられます。各メンバは、指定したアライメント(オフセット)に従ってstruct内に配置されます。

struct First
{
  char c;
  short s;
} s;

以下の図に、メモリでのレイアウトを示します。

StructLayout_70percent_02.png

構造体のアライメントは2バイトです。また、short sに正しいアライメントを保守するため、パディングバイトを挿入しなければならないことがあります。

パック構造体型

__packedデータ型属性または#pragma packディレクティブを使用して、構造体のメンバのアラインメント要件を緩和します。これにより、構造体のレイアウトが変更されます。メンバは、宣言時と同じ順序で配置されますが、メンバ間のパディングスペースが少なくなります。

注記

正しくアライメントされていないオブジェクトにアクセスする場合には、コードのサイズが大きくなり速度が低下します。そのような構造体へのアクセスが多数ある場合、パックされていない構造体で正しい値を構成し、この構造体にアクセスする方が通常は適しています。

アライメントが正しく設定されていないメンバへのポインタ作成および使用には、特別な注意も必要です。パックされたstructのアライメントが正しく設定されていないメンバに直接アクセスする場合、コンパイラは、必要に応じて正しいコード(ただし、サイズが大きく低速)を出力します。しかし、アライメントが正しく設定されていないメンバへのポインタを使用してそのメンバにアクセスする場合には、通常のコード(サイズが小さく高速)が使用されます。一般的なケースでは、これは機能しません。なぜなら、通常のコードは正しいアライメントに依存することがあるからです。

以下の例では、パックされた構造体を宣言します。

#pragma pack(1)
struct S 
{
  char c;
  short s;
};

#pragma pack()

構造S にはこのメモリレイアウトがあります。

StructLayout_Packed_70percent.png

次の例では、パックされていない別の構造体S2を宣言します。この構造体には、前の例で宣言した構造体sが含まれます。

struct S2
{
  struct S s;
  long l;
};

構造S2 にはこのメモリレイアウトがあります

StructLayoutCombined_70percent.png

構造体Sは、前の例で宣言したメモリレイアウト、サイズ、アライメントを使用します。メンバlのアライメントは4です。これは構造体 S2のアライメントが4になることを意味します。

詳細については、構造体要素のアライメントを参照してください。