3

たとえば、long 変数を宣言した場合、それは常に「sizeof(long)」境界で整列されると想定できますか? Microsoft Visual C++ のオンライン ヘルプにはそう書かれていますが、これは標準的な動作ですか?

いくつかの詳細情報:

a. 整列されていない整数 (*bar) を明示的に作成することが可能です。

char foo[5]

int * bar = (int *)(&foo[1]);

b. どうやら、 #pragma pack() は構造体、クラス、および共用体にのみ影響します。

c. MSVC のドキュメントには、POD 型はそれぞれのサイズに合わせて配置されていると記載されています (ただし、それは常にまたは既定であり、標準的な動作なのかはわかりません)。

4

6 に答える 6

10

他の人が述べたように、これは標準の一部ではなく、問題のプロセッサに適していると思われるため、実装するコンパイラに任されています。たとえば、VC は、x86 プロセッサとは異なるアライメント要件を ARM プロセッサに簡単に実装できます。

Microsoft VC は、#pragma pack ディレクティブまたは /Zp コマンド ライン オプションで指定されたサイズまで、基本的に自然配置と呼ばれるものを実装します。これは、たとえば、サイズが 8 バイト以下の POD タイプは、そのサイズに基づいて整列されることを意味します。それより大きいものは、8 バイト境界に整列されます。

さまざまなプロセッサやさまざまなコンパイラのアライメントを制御することが重要な場合は、パッキング サイズ 1 を使用して構造体を埋め込むことができます。

#pragma pack(push)
#pragma pack(1)    
struct Example
{
   short data1;     // offset 0
   short padding1;  // offset 2
   long data2;      // offset 4
};
#pragma pack(pop)

このコードでは、padding1data2 が自然に配置されるようにするためだけに変数が存在します。

への答え:

はい、それは簡単にデータの不整合を引き起こす可能性があります。x86 プロセッサでは、これはまったく問題になりません。他のプロセッサでは、これによりクラッシュが発生したり、実行が非常に遅くなる可能性があります。たとえば、Alpha プロセッサは、OS によってキャッチされるプロセッサ例外をスローします。次に、OS は命令を検査し、位置合わせされていないデータを処理するために必要な作業を行います。その後、実行が続行されます。この__unalignedキーワードを VC で使用して、x86 以外のプログラム (CE など) のアライメントされていないアクセスをマークすることができます。

于 2008-09-18T15:50:56.647 に答える
3

デフォルトでは、はい。ただし、pack() #pragma を介して変更できます。

私は、C++ 標準がこの点に関して要件を設けているとは思わず、実装に任せています。

于 2008-09-18T15:31:11.390 に答える
1

C and C++ don't mandate any kind of alignment. But natural alignment is strongly preferred by x86 and is required by most other CPU architectures, and compilers generally do their utmost to keep CPUs happy. So in practice you won't see a compiler generate misaligned data unless you really twist it's arm.

于 2008-09-18T16:26:47.293 に答える
0

はい、すべてのタイプは常に、少なくともそのアライメント要件に合わせてアライメントされています。

それ以外の場合はどうですか?

ただし、型の sizeof() は配置と同じではないことに注意してください。

次のマクロを使用して、型のアラインメント要件を決定できます。

#define ALIGNMENT_OF( t ) offsetof( struct { char x; t test; }, test )
于 2008-09-18T15:28:38.167 に答える
0

コンパイラ、プラグマ、および最適化レベルによって異なります。最新のコンパイラでは、時間または空間の最適化を選択することもできます。これにより、型の配置も変更される可能性があります。

于 2008-09-18T15:34:17.123 に答える
0

一般的には、その方が読み取り/書き込みが高速になるためです。しかし、ほとんどすべてのコンパイラには、これをオフにするスイッチがあります。gcc では -malign-???. 集合体を使用すると、一般に、各要素の配置要件に基づいて配置され、サイズが調整されます。

于 2008-09-18T15:37:43.027 に答える