5 基于IntelVt技术的Linux内核调试器主要问题以及解决
来源:互联网 发布:mac上照片存在哪里 编辑:程序博客网 时间:2024/06/18 01:46
在开发基于虚拟化的调试器时遇到了很多问题,有些问题看似简单,但是解决起来很不容易。这是因为我们的调试器工作在VMXroot模式,而在这种模式下引发的崩溃性BUG,没有任何软件调试器可以对其进行跟踪分析,除非这个调试器同样运行在VMXroot模式。
专业的虚拟机开发人员可以使用硬件调试器来解决开发中遇到的问题。x86架构是支持外接硬件调试器的,类似于JTAG接口,这种调试器价格昂贵,大概两万美金左右,而且一般的主板并没有导出调试插座,只有Intel的一些高端主板才导出了配套的调试界面。
我在没有硬件调试器的情况下,遇到了一些很奇怪的问题,经过不断的摸索最终得到了解决。
5.1调试器运行后几秒内死机
现象描述:在使用insmodvmxice.ko命令插入内核模块之后,系统在几秒钟内完全死机,游标不闪烁,不响应任何键盘操作。
故障诊断:如果崩溃发生在操作系统层应该会提示崩溃信息,而我遇到的这种死机是完全的死掉,所以死机可能是发生在VMExit之后。我尝试在进入VMExit处理函数时立即在屏幕上打印出计数器数值,这个计数器在每次进入VMExit之后都会递增,我以此可以证明死机发生点是VMExit中的某一段程序。结果出乎意料,在插入调试器内核模块后,屏幕上立即开始输出计数器数字,但是几秒后计数器停止输出,证明了死机是发生在VMExit,而且是崩溃性的,时钟中断都已经不再被处理。
这个故障我纠结了大概2个星期,后来重新阅读源代码时发觉,可能是页表出了问题,我写了一个小程序以验证我的思路。我首先在模块入口打印出CR3寄存器内容,然后再模块出口再次打印出CR3寄存器。我以此来判断内核模块的整个生命周期是否使用同一个页目录。
结果是页目录不同!后来经过详细分析认为这是正常的,因为在模块入口的函数被执行时,是属于insmod这个进程空间的,当入口函数执行完毕,insmod进程退出,这个页目录就顺其自然地被操作系统毁掉。而我的调试器依然在使用这个页目录,就发生了致命的错误:无法定位VMExit函数,因此在进行VMExit切换时一定会死机。
解决办法:在构造HOST端VMCS结构体时,为HOST重新分配一个页目录,并把当前页目录完整的复制过来,这样我们调试器就使用自己的页目录,操作系统在insmod进程退出后销毁insmod的页目录也不会影响我们调试器所使用的页目录了。
5.2呼出调试器后死机
故障现象:按下F12,然后进行某项操作时突然死机,不响应任何键盘操作。
故障诊断:首先可以肯定死机是发生在VMExit处理函数中。我使用排除法。我猜测故障发生在某处,我就在他前面和后面分别加一个打印字符串的语句,这样,假如真是在这里发生死机,那么只会打印出前面的字符串,后面的字符串就打印不出来了。这种办法很有效,通过不断的排除,缩小范围,通常都可以定位到崩溃发生点。
解决办法:经过诊断,发觉是调试器访问了非法的内存页面,导致发生页异常,而我们的调试器没有接管处理页异常的中断,所以就死机了。我为HOST端构造了一个简单的页异常处理函数,只是简单的打开蜂鸣器,这样一旦发生页异常蜂鸣器就会长响,我就可以知道是发生了页异常错误。
解决页异常的方法,就是避免访问非法内存,所以,我在写代码时会特别注意,如果某段代码会可能访问非法内存,那么我会在访问前对页面进行判断,如果页面存在,则继续访问,如果页面不存在,则不访问,改为错误通知。
例如使用U 0这个指令试图反汇编内存地址0处的代码,而这个地址是不存在的,调试器就会返回INVALIDADDRESS的错误,而不是傻傻的真的去反汇编,导致崩溃的发生。
- 5 基于IntelVt技术的Linux内核调试器主要问题以及解决
- 2.基于IntelVt技术的Linux内核调试器- 调试器主要原理与环境搭建
- 1. 基于IntelVt技术的Linux内核调试器- 引言与IntelVT-x 技术简介
- 4 基于IntelVt技术的Linux内核调试器- 调试器设计与实现(2):调试核心
- 3.基于IntelVt技术的Linux内核调试器- 调试器设计与实现(1):基本框架
- 开源项目-基于Intel VT技术的Linux内核调试器
- 开源项目-基于Intel VT技术的Linux内核调试器
- linux内核的调试技术
- Linux 内核调试技术
- Linux内核调试技术
- linux 内核调试技术
- Linux内核调试技术
- [转贴]基于ARM7内核的嵌入式应用程序调试技术
- 基于ARM7内核的嵌入式应用程序调试技术(转)
- linux调试器的实现---主要框架
- 基于VMware调试linux内核
- linux内核的移植与遭遇问题的解决 启动调试 printascii
- linux内核的移植与遭遇问题的解决 启动调试 printascii
- dbms_stats.gather_table_stats与analyze table 的区别
- Linux Top 命令详解[内存使用情况]
- java监听器模式
- soj3538 幸运数字 容斥原理应用
- 时间管理工具推荐
- 5 基于IntelVt技术的Linux内核调试器主要问题以及解决
- SQL Join的一些总结
- [转] web向另一台server上传文件: access the path is denied
- Delphi属性Property学习应用总结
- 羌笛声声胡笳怨,此心长寄天涯远
- 关于type_info与typeid
- 程序1-1 连通性问题的快速查找解决方案:
- Eclipse导出JavaDoc中文乱码问题解决
- iphone 自定义控件,通讯录,网络,电子书,控件特效 等源码