ARM7架构(基于ARMv4T)的结构体内存对齐遵循以下规则,以确保数据访问的正确性和效率。由于ARM7处理器不支持非对齐内存访问,编译器会通过填充字节来保证每个成员正确对齐:
- 成员对齐规则
每个结构体成员的偏移地址必须是其类型大小或编译器默认对齐值(取较小者)的整数倍。
char(1字节):1字节对齐,偏移地址可为任意。
short(2字节):2字节对齐,偏移地址必须是偶数(如0x0, 0x2, 0x4等)。
int/指针(4字节):4字节对齐,偏移地址必须是4的倍数(如0x0, 0x4, 0x8等)。
double(8字节):在ARM7中通常视为两个4字节字,按4字节对齐(但需根据编译器实现确认)。
- 结构体总大小对齐
结构体的总大小必须是其最大成员对齐值的整数倍。例如,若最大成员是int(4字节对齐),则结构体大小必须是4的倍数,不足时末尾填充字节。 - 编译器填充策略
编译器会在成员之间插入填充字节(Padding),确保下一个成员正确对齐。
成员顺序影响填充量,合理排列可减少内存占用。
示例分析
示例1:默认成员顺序
c
struct S1 {
char a; // 偏移0(1字节对齐)
// 填充3字节(偏移1-3)
int b; // 偏移4(4字节对齐)
short c; // 偏移8(2字节对齐)
}; // 总大小=8+2=10,但需对齐到4→末尾填充2字节→总大小12字节。
示例2:优化成员顺序
c
struct S2 {
int b; // 偏移0(4字节对齐)
char a; // 偏移4(1字节对齐)
short c; // 偏移6(填充1字节后,2字节对齐)
}; // 总大小=6+2=8,已对齐到4→无需填充。
调整顺序后,结构体大小从12字节降至8字节。
关键点总结
硬件限制:ARM7不支持非对齐访问,编译器必须严格对齐。
成员顺序优化:合理排列成员可减少填充,节省内存。
编译器指令:使用#pragma pack(n)或__attribute__((packed))可修改对齐规则,但可能导致性能下降或错误。
验证方法
c
#include <stdio.h>
struct S1 { char a; int b; short c; };
struct S2 { int b; char a; short c; };
int main() {
printf("S1大小: %zu\n", sizeof(struct S1)); // 输出12
printf("S2大小: %zu\n", sizeof(struct S2)); // 输出8
return 0;
}
通过sizeof可验证结构体实际大小,结合调试器查看内存布局。