除錯經驗 位元組對齊

2021-07-08 15:59:41 字數 2239 閱讀 9307

除錯經驗--位元組對齊

在使用c語言開發時,有時會遇到記憶體中資料對齊的問題,如果對齊問題沒有判斷正確,很可能導致結果完全異於預期。

我們在除錯程式時,在資料對齊方面遇到一些問題,也做了一些總結:

1,c語言預設對齊方式;

2,c語言強制指定對齊方式;

3,指標資料型別轉換;

4,乙個位元組對齊問題的例子。

1,c語言預設對齊方式

在預設情況下,c編譯器為每乙個變數或是資料單元按其自然對界條件分配空間。

結構體成員對齊有乙個重要的條件,即每個成員分別對齊.即每個成員按自己的方式對齊.其對齊的規則是,每個成員按其型別的對齊引數(通常是這個型別的大小)和指定對齊引數(若未指定,就是最大的成員對齊引數)中較小的乙個對齊.並且結構的長度必須為所用過的所有對齊引數的整數倍,不夠就補空位元組.

這裡有三點很重要:

1.每個成員分別按自己的方式對齊,並能最小化長度。

2.複雜型別(如結構)的預設對齊方式是它最長的成員的對齊方式,這樣在成員是複雜型別時,可以最小化長度。

3.對齊後的長度必須是成員中最大的對齊引數的整數倍,這樣在處理陣列時可以保證每一項都邊界對齊。

對於陣列,比如:

char a[3];這種,它的對齊方式和分別寫3個char是一樣的.也就是說它還是按1個位元組對齊。

如果寫: typedef char array3[3];

array3這種型別的對齊方式還是按1個位元組對齊,而不是按它的長度。

不論型別是什麼,對齊的邊界一定是1,2,4,8,16,32,64....中的乙個。

2,c語言強制指定對齊方式

可以指定為按1位元組對齊,如下:

#pragma pack(push,pack1,1)

或:#pragma pack(1)

或指定為按4位元組對齊,如下:

#pragma pack(push,pack1,4)

或:#pragma pack(4)

注意,要恰當的取消對齊方式,否則,強制的對齊方式會輻射影響所有相關檔案,帶來意料之外的結果,例如,不同檔案中,同乙個結構體的sizeof結果不同!!

(包含結構體的標頭檔案在不同檔案中包含,又有其他標頭檔案中指定了不同的對齊方式)

#pragma pack(pop,pack1)

或:#pragma pack()

按照cpu的字長進行對齊,執行效率高。

#pragma pack(8)

struct s1;

struct s2;

#pragma pack()

問 1.sizeof(s2) = ?

2.s2的c後面空了幾個位元組接著是d?

結果如下:sizeof(s2)結果為24。s2的c後面空了3個位元組接著是d。

a       b

s1的記憶體布局:11**,1111,

c     s1.a   s1.b        d

s2的記憶體布局:1***,11**,1111,****11111111

3,指標資料型別轉換

乙個int,對於32位的cpu來說,通常是需要4位元組對齊的。

若對字元陣列進行強制轉換時,沒有4位元組對齊,則報錯資訊如下:

例如:char aa[100];

int bb_used=*(int *)(aa+read_num);

而((char *)(aa+read_num)

若read_num不是4的整數倍,則會導致

((char *)(aa+read_num)

不是4位元組對齊的,將它強制轉換為int,則會遇到對齊錯誤,取的值也不對,但是可以繼續執行。

此種情況下,使用memcpy是安全的:

memcpy(&bb_used, aa+read_num, sizeof(bb_used));

4,乙個位元組對齊問題的例子

我定義了乙個結構體,包含4個char,4個int。另外開闢了乙個字元陣列,準備儲存100個結構體的內容,開闢的大小是(4+4×4)×100=2000。結果卻發現程式執行異常。後來仔細分析,發現是結構體的大小判斷錯了。結構體如下:

struct st1;

在這個結構體中,由於每個char後面緊跟乙個int,而int要求4位元組對齊,則char後面的3個位元組是空著的。這個結構體的實際使用空間應該如下計算:

(1+3)+4+(1+3)+4+(1+3)+4+(1+3)+4=32

存放100個結構體的內容,需要記憶體大小為32×100=3200。對於2000位元組的陣列,有嚴重的越界!由於越界,導致寫壞了後面記憶體中的資料,從而執行異常。通過調整陣列大小,解決問題。

位元組順序 位元組對齊

一.位元組順序的產生 在計算機中,資料是以位元組為單位存放的,而c語言中只有char才是乙個位元組,其他如int,float都是大於乙個位元組,所以就存在將資料按怎樣的順序存放的問題。一般有大端序和小端序兩種方式,特殊的還有混合序,也就是兩種存放方式同時存在於乙個計算機系統中。上面講的都是主機位元組...

位元組順序 位元組對齊

一.位元組順序的產生 在計算機中,資料是以位元組為單位存放的,而c語言中只有char才是乙個位元組,其他如int,float都是大於乙個位元組,所以就存在將資料按怎樣的順序存放的問題。一般有大端序和小端序兩種方式,特殊的還有混合序,也就是兩種存放方式同時存在於乙個計算機系統中。上面講的都是主機位元組...

位元組對齊 8位元組對齊

參考博文 參考1 參考2 參考3 在記憶體管理中經常使用位元組對齊來管理分配的記憶體。1 原理 2 演算法 2.1unsigned intcalc align unsigned int n,unsigned align 2.2 更好的演算法 unsigned intcalc align unsign...