调试时C++指针地址异常递增但运行正常的问题排查
问题:VS Code调试C++时指针地址异常变化的排查与解决
环境信息
- 系统:Ubuntu 20.04.6
- 编译器:g++-9 (Ubuntu 9.4.0-1ubuntu1~20.04.2) 9.4.0
代码示例
main.cpp
// main.cpp #include "crc.h" #include <cstdint> #include <iostream> #include <vector> int main() { int size; unsigned char *bytes = new unsigned char[20]; for (int i = 0; i < 16; ++i) { *(bytes + i) = i; } size = 16; uint16_t crc_value = crc(bytes, size); // 原代码存在笔误:unit16_t → uint16_t std::cout << "crc: " << std::hex << crc_value << std::endl; return 0; }
crc.h
// crc.h #include <cstdint> uint16_t crc(const unsigned char*, const int);
crc.cpp
// crc.cpp #include <cstdint> #include <iostream> uint16_t crc(const unsigned char *ptr, const int count) { uint16_t crc = 0; for (int i = 0; i < count; ++i) //Iterate over every byte in *ptr { crc = crc ^ (static_cast<uint16_t>(*(ptr + i)) << 8); //Byte from *ptr ^ with crc for (int bit = 0; bit < 8; ++bit) //Iterate over every bit in crc { if (crc & 0x8000) //The highest bit is 1 crc = (crc << 1) ^ 0x1021; else crc = crc << 1; } std::cout << i << " crc: " << std::hex << crc << std::endl; } return crc; }
调试异常现象
在VS Code中调试时:
- 执行
main.cpp里的crc(bytes, size);时,变量栏显示bytes的地址为0x55555556aeb0 - 进入
crc.cpp执行uint16_t crc = 0;时,ptr的地址变为0x55555556aeb2 - 执行
for (int i = 0; i < count; ++i)时,ptr地址变为0x55555556aeb4 - 执行
crc = crc ^ (static_cast<uint16_t>(*(ptr + i)) << 8);时,地址变为0x55555556aeb5 - 每执行一步,
ptr的地址就增加0x02
程序直接运行时输出正常,但预期crc函数中ptr指向的地址应保持不变,询问是指针使用错误还是调试配置有误,以及解决方法。
问题分析与解决
1. 先修正代码笔误
main.cpp中存在明显笔误:unit16_t crc_value应为uint16_t crc_value,该错误会导致编译失败,需先修正。
2. 区分「指针变量自身的地址」与「指针指向的地址」
你看到的变量栏显示的地址,是指针变量ptr自身在栈上的存储地址,而非ptr指向的内存地址:
main中的bytes和crc函数中的ptr是两个不同的指针变量,分别存在各自的栈帧中,所以它们自身的地址必然不同。- 调试时地址的递增变化,是指针变量
ptr自身在栈上的地址偏移,而非它指向的内存地址变化。
你需要关注的是ptr的值(即它指向的内存地址),该值应该始终等于main中bytes的地址0x55555556aeb0。
3. 调试显示与配置修正
在VS Code调试面板中:
- 展开
ptr变量,查看value字段,这才是指针指向的内存地址,正常情况下该值不会变化。 - 确保编译时添加了
-g参数生成调试信息,tasks.json中的编译命令应为:g++ -g main.cpp crc.cpp -o crc_test - 检查
launch.json配置,确保使用gdb作为调试器,默认配置即可满足需求。
4. 指针使用正确性验证
你的代码指针逻辑完全正确:
crc函数中未对ptr本身做修改(如ptr++),所以它指向的地址不会改变。- 程序直接运行输出正常,也证明了指针操作的逻辑没有问题,异常仅源于调试显示的理解偏差。
内容的提问来源于stack exchange,提问作者Waterfall_11
相关产品推荐
相关产品推荐

