簡體   English   中英

C結構的數據對齊

[英]Data Alignment for C struct

CS:APP中存在關於以下結構中所有字段的字節偏移的問題(3.45)。

struct {
  int    *a;
  float  b;
  char   c;
  short  d;
  long   e;
  double f;
  int    g;
  char   *h;
} rec;

下面是從書,這給出了答案c一個三個填充字節, d一個兩個字節填充和g的四個字節的填充。

field  size  offset
-----  ----  ------
a      8     0
b      4     8
c      1     12
d      2     16
e      8     24
f      8     32
g      4     40
h      8     48

這里是我的解決方案,只給c一個字節填充和g四個字節填充。

field  size  offset
-----  ----  ------
a      8     0
b      4     8
c      1     12
d      2     14
e      8     16
f      8     24
g      4     32
h      8     40

那么,我的解決方案有什么問題? 它似乎符合對齊規則(編輯*這里的“規則”只是我自己的簡化概念摘要,它沒有完成或一般),所有對象的偏移量是對象大小的倍數。

非常感謝任何解釋。

給定顯示的對象的大小和對齊規則,表明每個對象必須與其大小的倍數對齊,然后,當結構布局時只需要對齊所需的填充,偏移量應如Tetrau解決方案中所示。 書中的解決方案不正確。

Tetrau解決方案中顯示的偏移實際上是Apple LLVM 10.0.1產生的偏移,Clang 1001.0.46.4為x86-64編譯; 以下程序的輸出是:

0
8
12
14
16
24
32
40
48
struct foo {
  int    *a;
  float  b;
  char   c;
  short  d;
  long   e;
  double f;
  int    g;
  char   *h;
} rec;


#include <stddef.h>
#include <stdio.h>


int main(void)
{
    printf("%zu\n", offsetof(struct foo, a));
    printf("%zu\n", offsetof(struct foo, b));
    printf("%zu\n", offsetof(struct foo, c));
    printf("%zu\n", offsetof(struct foo, d));
    printf("%zu\n", offsetof(struct foo, e));
    printf("%zu\n", offsetof(struct foo, f));
    printf("%zu\n", offsetof(struct foo, g));
    printf("%zu\n", offsetof(struct foo, h));
    printf("%zu\n", sizeof rec);
}

注意

對象需要與其大小的倍數對齊的規則對於此練習是好的,但應該注意,這不是一般規則。 一台機器可能有一些8字節的對象,但只有一個總線和其他4字節寬的內存訪問特性,因此它只關心任何對象的最多四字節對齊。 或者結構成員可能是另一個結構,例如,大小為9個字節(例如struct bar { char x[9]; } ),但它的對齊要求不是9個字節。

答案取決於編譯器,平台和編譯選項。 一些例子: 在此輸入圖像描述

https://godbolt.org/z/4tAzB_

這本書的作者不理解我害怕的話題。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM