硬件断点的原理

Intel 80306以上的CPU给我们提供了调试寄存器用于软件调试,硬件断点是通过设置调试寄存器实现的。

 

上图为Intel手册提供的32位操作系统下8个调试寄存器的图示(Intel手册卷3 17章第二节 Debug Registers,有兴趣的朋友可以查阅),根据介绍,DR0-DR3为设置断点的地址,DR4和DR5为保留,DR6为调试异常产生后显示的一些信息,DR7保存了断点是否启用、断点类型和长度等信息。

我们在使用硬件断点的时候,就是要设置调试寄存器,将断点的位置设置到DR0-DR3中,断点的长度设置到DR7的LEN0-LEN3中,将断点的类型设置到DR7的RW0-RW3中,将是否启用断点设置到DR7的L0-L3中。设置硬件断点需要的DR0-DR3很简单,就是下断点的地址,DR7寄存器很复杂,位段信息结构体如下:

typedef struct_DBG_REG7
{
/*// 局部断点(L0~3)与全局断点(G0~3)的标记位*/unsigned L0 :1; //对Dr0保存的地址启用 局部断点 unsigned G0 : 1; //对Dr0保存的地址启用 全局断点 unsigned L1 : 1; //对Dr1保存的地址启用 局部断点 unsigned G1 : 1; //对Dr1保存的地址启用 全局断点 unsigned L2 : 1; //对Dr2保存的地址启用 局部断点 unsigned G2 : 1; //对Dr2保存的地址启用 全局断点 unsigned L3 : 1; //对Dr3保存的地址启用 局部断点 unsigned G3 : 1; //对Dr3保存的地址启用 全局断点 /*// 【以弃用】用于降低CPU频率,以方便准确检测断点异常*/unsigned LE :1;
unsigned GE :
1;/*// 保留字段*/unsigned Reserve1 :3;/*// 保护调试寄存器标志位,如果此位为1,则有指令修改条是寄存器时会触发异常*/unsigned GD :1;/*// 保留字段*/unsigned Reserve2 :2;

unsigned RW0 :
2; //设定Dr0指向地址的断点类型 unsigned LEN0 : 2; //设定Dr0指向地址的断点长度 unsigned RW1 : 2; //设定Dr1指向地址的断点类型 unsigned LEN1 : 2; //设定Dr1指向地址的断点长度 unsigned RW2 : 2; //设定Dr2指向地址的断点类型 unsigned LEN2 : 2; //设定Dr2指向地址的断点长度 unsigned RW3 : 2; //设定Dr3指向地址的断点类型 unsigned LEN3 : 2; //设定Dr3指向地址的断点长度 }DBG_REG7, *PDBG_REG7;

标签: none

添加新评论