C/C++调试---调试符号与调试器

调试符号与调试器

调试符号

调试符号由编译器生成,与相关的机器代码、全局数据对象等一同产生。链接器会收集并组织这些符号,将他们写入可执行文件的调试部分,或存储到一个单独文件中。

概览

  • 全局函数和变量

  • 源文件和行信息
    为了优化程序性能,编译器可能会对源代码进行位移,情况可能变得复杂。由于宏和内联函数的存在,源代码的行信息可能与实际执行的指令地址并不连续或者交织在在其他源代码行中。

  • 类型信息

  • 静态函数和局部变量

  • 架构和编译器以来信息
    某些调试功能与特定的架构和编译器有关

调试的角度查看

使用下面命令生成汇编文件

g++ -g -S test.cpp

解码文件,查看调试符号

readelf --debug-dump test.o

调试器

一般是3个模块:用户界面、符号管理、目标管理

用户界面

gui或者命令行

符号管理

提供调试目标的调试符号,如果调试符号错误或者不完整,那么调试器将无法正常工作

目标管理模块

目标管理模块在系统和硬件层面处理被调试的进程。
在linux中,内核提供了一个系统调用ptrace函数,允许进程查询和控制另一个进程的执行(strace就是通过ptrace)。

跟踪gdb的调用

strace -o/home/self/ptrace.log -rptrace gdb app.out

cat /home/self/ptrace.log

注意事项

特殊的调试符号

  • 已知某个变量的具体类型但无法打印该变量
    无法理解变量主要是缺乏对应变量的调试符号
    解决办法:
    1、重新编译并生成包含我们所需的调试符号的新库文件;
    2、使用Python扩展GDB

core文件

是进程内存映像在某一时刻的快照。

常见的生成core的原因:

  • 段错误。程序正在试图访问未分配给进程的地址空间或者被保护免于特定的操作(读、写或者是运行)的内存。
  • 总线错误。一般由访问未对齐的数据导致
  • 非法地址。比如程序下一个运行指令不数据CPU指令集时,访问函数指针地址在堆段而不是文本段
  • 未处理异常。c++程序抛出异常但没有代码捕获。
  • 浮点数异常。除0,溢出
  • 栈溢出。程序没有足够的栈空间来存储函数调用和本地变量。

core文件不完整
系统设置了仅允许部分转储;core文件超出了最大的核心转出文件大小的设置;磁盘空间不足等

参考:高效C/C++调试

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

麦兜c

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值