断点原理与实现

T 状态意味着: (TASK_STOPPED or TASK_TRACED),暂停状态或跟踪状态 ,接下来就可以通过 GDB 实现各种调试的操作了。

我们这次也要实现类似的效果,不过只是一个超简化版本,只考虑: 在指定的位置暂停,获得进程的控制权

前置知识准备

在实现之前,我们需要了解下必要的知识:

寄存器:RIP

如果之前没有了解 寄存器 的童鞋可以先看看:https://www.jianshu.com/p/0299f56edab5

直接摘抄里面的一段描述:

rip 指令地址寄存器,用来存储 CPU 即将要执行的指令地址。

每次 CPU 执行完相应的汇编指令之后,rip 寄存器的值就会自行累加;

Ptrace

如果之前没有了解 Ptrace 的童鞋可以先看看:http://fancy-blogs.com/2018/03/06/ptrace/

在ptrace中有两个角色:

  • tracee:被追踪者,它是被监控的进程,通过ptrace系统调用的操作作用在它之上 (譬如:上文的 22346 进程);

  • tracer:追踪者,它负责监视并处理被追踪者传来的信息(譬如:GDB);

下文会直接引用这两个名词。

实现思路

实现的思路非常简单

1. 先确定我们要断点的地址

在 GDB 中,我们是习惯对 行号 或者 函数名 直接设置断点,行号相对来说比较复杂,我们先展示 函数名 的。

在 Linux 环境下编译出来的可执行文件都是遵循 ELF 格式,如果没有特殊处理,它会保留比较完整的 符号表

就拿开头的程序来当例子,可以通过 readelf -s a.out 查看