2011-02-03 4 views
2

gccの定義済み変数のアライメントを明示的に無効にするにはどうすればよいですか?
は、このコードを取る:GCCの暗黙的な配置問題。 (64ビットコード)

typedef struct{ 
    unsigned long long offset; 
    unsigned long long size; 
    unsigned long type; 
    unsigned long acpi; 
}memstruct; 

memstruct *memstrx; 

これは24バイトの大きさを有する構造を定義します。私がやってみました

memstrx=(void*)(0x502); 

ので

&memstrx[0]はようになど0x502
&memstrx[1]の価値を持って、0x51A
&memstrx[2]、0x532

...とすべきです。

しかし、物事は正しいとは思われません。

&memstrx[1]代わり

は、などなど... 0x522
&memstrx[2]のアドレス、
&memstrx[3] 0x542、0x552

を表示します。

私は、GCCが構造を32バイト(24バイトから)に暗黙的にサイズ変更して、(各エントリの64ビットアライメント)を強制すると思われます。そして、私は本当にこの構造のためだけにこの動作を望んでいません。どのようにGCCにその構造を揃えないように伝えるべきですか?

答えて

6

いいえできません。

表示する構造の最小サイズは8 * 4 = 32バイトです。

のsizeof(unsigned long型)= 8 64ビットアーキテクチャ(Li​​nux)の上

編集:あなたが使用している場合

からunsigned代わりunsigned long

または

  • unsigned longおよびの代わりにuint32_tおよび

あなたは予想通りのアライメントを得るでしょう。

+0

「最小サイズは8×4 = 32バイトではありません」という意味は、構造のサイズですか? – prinzrainer

+0

@prinzrainer - 私の答えをもう一度読んでください:sizeof(long)= 8 not 4 – Artyom

+3

Artyomは、64ビットマシン上で 'unsigned long'が8バイトであることを意味します。 32ビットが必要な場合は普通の 'unsigned'を使用するか、大きさが異なる可能性のある型ではなく正確なサイズの型(' uint32_t'と 'uint64_t')を使用する方が良いでしょう。 –

1

ここではgccを使用してアライメントを制御するための1つの選択肢です:

http://gcc.gnu.org/onlinedocs/gcc/Structure_002dPacking-Pragmas.html

+2

アラインメントとは関係ありません - 彼はちょうど正しいタイプを逃しています – Artyom

+0

@Artyomその問題は投稿時に別の回答(あなたの投稿)で解決されていました。しかし、私が掲示した情報は、私が投稿した時点でいかなる回答でも提供されていなかった。読者/文脈に応じて、それぞれの答えが役に立つでしょう。乾杯 – justin

2

の#pragma pack(x)はGCCとMSVCの両方の構造アラインメントの制限を変更することができます。

GCCは64ビットビルドにLP64モデルを使用します。これは、ロングとポインタが64ビットであることを意味します。 32ビットフィールドの場合はunsigned intに変更し、安定したフィールドサイズの場合はuint32_tとuint64_tを使用する必要があります。

#pragma pack(1) 

typedef struct{ 
    unsigned long long offset; 
    unsigned long long size; 
    unsigned int type; 
    unsigned int acpi; 
}memstruct; 

#pragma pack() 
関連する問題