EDA365电子论坛网

标题: ARM内存边界对齐以及sizeof问题 [打印本页]

作者: House    时间: 2018-10-24 10:48
标题: ARM内存边界对齐以及sizeof问题
ARM内存边界对齐以及sizeof问题
       默认情况下,在32位cpu里,gcc对于结构体的对齐方式是按照四个字节来对齐的。看以下结构体
. }8 e% f3 J( U9 }; C* N# N! e4 {0 T5 G0 ?" W

: a, Y8 Y9 f$ w' \7 L1 e6 z) ]% w
  typedef struct pack{) b1 ]1 X* U& N& ^
: [& d: y* m! n5 e& Y9 M+ w0 y
  char a;
$ w- ]% |& r  L: T1 {/ z7 C
  \$ T* x; S  u! l0 D; a) V; F  int b;
: f7 b' ~: e( l6 T$ \* Q5 F
. e6 T  n0 f4 e3 p4 `$ f( {  short c;7 \8 w  B. z* m2 G: X, D4 X
. H6 A* o' N8 ^1 _
  }pack;
- b* `; J5 }- Q' @7 ]& E
& d* t8 O: T# }( W. }( w  对于Pack结构体,默认情况下在arm/386平台下(别的平台没试过)sizeof(pack)=12,求解过程如下:# N, f. ^; A- r& N% Z  A

0 P- \+ Z3 A5 k( M' T( g( w; `  sizeof(char)=1;! U% B+ W6 ~' I  Q$ T6 V% _

- L, P0 O$ l! A% r  下一个int b,由于是四个字节,要求b的开始地址从32的整数倍开始,故需要在a后面填充3个没用的字节,记为dump(3),sizeof(b)=4,此时相当于结构体扩充为" l2 n' [; Q9 J
0 T- {2 d, j$ D
  char a;0 p! x! [" D  c; P1 ~/ b0 U* ^3 E

2 g, I* n( @9 {' t" Z  char dump(3);; v$ @: Z4 @- q; h! G8 U  e
4 M( Z1 W( a# w( J7 j( f
  int b;' M  [" h* [7 N9 f/ @& R4 D" c1 e

: ?- K3 U9 e0 m3 Q' C  看short c,现在c的前面有8个字节,c是两个字节,c的开始地址是从16的整数开始,在b前面不需再加东西.此时对于结构体来说,sizeof(pack)=10,但是这不是最终结果,最后总的字节数也要能被4个字节整除,所以还需在short c后面再加' t/ ~, l& ]6 p  Y+ y0 r
6 D& h1 o! M) d+ M" m, }
  dump(2);
6 j. W; W& k: ]5 ^3 s, Z4 R4 Z" \: u' X: q, O4 Q1 V8 Z+ P
  故总的字节数为12.$ w8 m; K+ q1 |% }" l) z9 V. Y: W

/ j: `  m/ x5 t+ Z7 a9 {! E/ L/ G% ~# E  当然以上说的只是简单的情况,下面谈谈arm,x86在gcc里关于内存边界字节对齐的区别.对于同样的结构体,在386下
, K' h" M/ D8 n* C' h3 E/ N
! J  ^! s5 L! ?/ H( V  #prama pack(1)3 v! ?$ B) z  Q

4 r" {) p3 _9 T. X  后,sizeof(pack)=1 4 2=7
/ m+ p1 U6 d/ t  e/ K6 r6 b4 d" Z
- }4 e$ ?3 Q, y& z  而在arm下同样的操作sizeof(pack)=1 4 2 1=8,即虽然b根a之间不要填充但总的长度必须要是4的整数倍.
1 x2 }+ F% X" r+ ?1 D+ {! @  H; Q3 Q. X1 u7 N. n
  在arm 下要使结构体按指定字节对齐,可行的方法
, H) f& z9 I5 A! s6 z& ]
5 C' M& z6 w) d0 X  1.在makefile里加-fpack-struct 选项,这样的话对所有的结构按一字节对齐.- x3 h6 v' G% t: L
9 H$ e+ n+ s: X4 ^9 U
  不得不说,确实有那么些质量较差的程序可能需要你部分自然对齐,部分一字 节对齐,此时  r, F( i3 g+ R4 a+ n8 z% W$ O
& p. S: W2 `8 c8 ]
  2. typedef struct pack{
+ m0 G' n. K' o* k) W/ b) g2 W, h' P! Y  z
  }__attribute__((packed)): @8 A" Z4 A6 e1 s: Y9 r' L2 e
! r4 f7 u5 s' O& _  ]2 F6 i3 Z) w; S
  可利用__attribute__属性+ X! ?6 a9 ]  b0 O% d! m: c
( H9 _4 ~0 m' u- y, W
  当然最后的方式,还是自己去看arm体系结构与gcc编译选项了。
/ P( S; G7 o- @0 J: K9 ?6 E6 J: |
: C/ ?; v* M: T; ^2 |: Z
作者: leleeda    时间: 2018-10-24 18:23
看看




欢迎光临 EDA365电子论坛网 (https://bbs.eda365.com/) Powered by Discuz! X3.2