Bus Error本质是CPU硬件拒绝非法内存访问,主因是目标类型对齐要求高于原地址实际对齐,如int[4]转long long*时若起始地址非8字节对齐,ARM64等平台会立即触发SIGBUS。

Bus Error 本质是硬件拒绝非法内存访问
Bus Error 不是段错误,也不是代码逻辑错,而是 CPU 在执行指令时发现地址不满足类型对齐要求,直接终止访问。常见于 reinterpret_cast 后立即解引用、或用引用绑定未对齐地址(如 double& 绑定到奇数地址),尤其在 ARM64、RISC-V 或 macOS M1+ 等默认启用严格对齐检查的平台会立刻崩溃。
快速验证是否为对齐问题
别猜,直接查:
- 用
alignof(T)查目标类型所需对齐值,例如alignof(long long)通常是 8,alignof(double)也是 8 - 用
uintptr_t检查实际地址:uintptr_t addr = reinterpret_cast<uintptr_t>(ptr); if (addr % alignof(T) != 0) { /* 这里就踩雷了 */ } - 编译时加
-Wcast-align(GCC/Clang),它会在reinterpret_cast转换可能破坏对齐时发出警告 - 运行时用
gdb查崩溃点:看info registers中pc指向哪条指令(常是ldp、movsd、ldr等加载指令),再结合x/4xg $pc-16看上下文
替代 reinterpret_cast 的安全做法
只要涉及“把一块内存按另一种类型解释”,优先用 std::memcpy,而不是指针强转:
int arr[4] = {1, 2, 3, 4};
long long buf[2];
std::memcpy(buf, arr, sizeof(buf)); // 安全:逐字节拷贝,不依赖地址对齐
// 后续操作 buf[0], buf[1],而非 reinterpret_cast<long long*>(arr)[0]
注意:std::memcpy 不规避越界,仍需确保源目标大小匹配;若必须零拷贝且确定对齐,应使用 std::aligned_alloc 分配内存,并用 static_cast 转换——reinterpret_cast 依然不推荐用于跨类型数组指针转换。
组合式C++代码评审方案,融合静态分析、AI推理、多轮迭代评审和C++专项检查,适用于PR审查、增量代码审查、全项目评审和代码质量评分,触发词包括review cpp、cpp代码评审、C++review、代码审查。
立即学习“C++免费学习笔记(深入)”;
结构体和栈上变量的对齐陷阱
栈上分配的数组(如 int arr[4])通常只保证 alignof(int)(即 4 字节)对齐,但若后续用它当 long long* 用,就可能出问题。同理:
-
vector<char></char>或裸char[]分配的内存是 1 字节对齐的,不能直接reinterpret_cast<double></double> - 含
double成员的结构体塞进vector时,若vector内部缓冲区起始地址不是 8 字节对齐,构造该结构体实例就会触发reference binding to misaligned address - 使用
__attribute__((packed))或#pragma pack会破坏成员自然对齐,仅在协议解析等必要场景使用,且访问时必须用memcpy
对齐问题最麻烦的地方在于:它可能在 x86-64 上静默运行,一换平台就崩;也可能本地跑通,CI 或 OJ 就报错。关键不是“有没有错”,而是“有没有被硬件盯上”。

















