1 RTEMS操作系统简介
RTEMS,即实时多处理器系统(Real Time Executivefor Multiprocessor Systems),是一个开源的实时嵌入式操作系统。它最早用于美国国防系统,现在它在航空航天、军工及民用领域都有着广泛的应用。
从结构上来看,RTEMS是微内核抢占式实时系统。图1显示了RTEMS操作系统的基本结构。图中白色部分为RTEMS操作系统的硬件支持部分(Board SupportPackage),它包括了硬件抽象代码、硬件设备驱动代码和操作系统启动代码。灰色部分为RTEMS内核以及系统提供给应用程序的API。在具体应用场景中,图中所有系统模块都被编译成一个静态连接库,用户编写的应用程序和RTEMS库静态链接成一个整体,形成运行在目标环境的镜像文件。应用程序只将需要的系统支持模块链接进来,最大程度地缩小了可执行镜像的大小。
此外,RTEMS十分简洁,力求实时性。它不支持虚拟内存,整个系统内核以及应用程序运行在共同的平板内存空间之上。因此,RTEMS镜像文件的运行可以看作是一个大型的、处理时钟中断的裸板程序。
2 GDB远程调试
GDB全称GNU symbolic debugger。在大多数情况下,在UNIx或者Linux环境下使用GDB调试本机程序,GDB通过waitpid、ptrace等系统调用对被调试进程进行监查和控制。这种调试模式很常见,但它只是GDB调试的一种特殊情况:GDB本身的运行环境和被调试程序的运行环境恰巧是同一个。在有些情况下,被调试程序运行环境下可能无法方便地运行GDB,那么远程调试就会派上用场。
2.1 远程调试中程序的交互途径
如图2所示,GDB和被调试程序运行于不同的环境中。在GDB加载了和被调试程序对应的调试信息之后,用户可以通过它对被调程序进行源代码级调试。用户向GDB下达调试命令,GDB将用户的调试命令翻译、打包,通过串口或者网络接口发送至被调试程序端的GDB—SERVER。GDB—SERVER将接收到的调试命令包解包,并将其表达的调试命令实施于被调试程序。如果需要,还应将命令执行结果通过远程通信返回给GDB端。
2.2 GDB与GDB—SERVER
GDB和GDB—SERVER之间的数据通道上传输的信息遵循GDB Remote Serial Protocol。它是一种简洁的、基于ASCII的协议。每一个RSP报文由ASCII符号“$”开头,由“#”将报文内容和两个字节的报文校验隔开,如下所示:
接收方对报文进行校验,如果校验成功,回复ASCII字符“+”,否则回复“一”。
通过RSP传输的命令种类很多,比较常用的罗列于表1中。当用户使用GDB远程调试程序时,GDB将用户的命令翻译成若干条RSP命令的序列下达给GDB—SERVER。GDB—SERVER对命令进行实施,并回复运行结果。作为一个能实现基本调试功能的GDB—SERVER,至少需要实现表1中列出的命令。
2.3 GDB—SERVER与被调试程序
GDB—SERVER和被调试程序之间的交互方式就比较灵活了,在没有虚拟内存管理的环境中可以使用指针直接访问被调试程序的内存,而在引入了嵌入式操作系统的环境中可以使用系统调用实现。GDB—SERVER是GDB调试命令的实施者,依照GDB的调试基本需求,GDB—SERVER和被调试程序之间的交互方式只要能够完成表1中列出的操作就可以了。
3 传统STUB调试模式概述
GDB—STUB是嵌入在被调试程序中的小段程序,它肩负了和GDB通信并执行GDB调试命令的重任。可以说GDB—STUB是轻量级的GDB—SERVER。它代码量很少,在RTEMS启动初始化阶段,将它以软中断处理程序的身份嵌入到RTEMS之中,成为RTEMS的一部分。当被调试程序运行到这个特殊的软中断时,STUB程序获得运行的权力,和GDB进行远程通信,执行调试命令,直到收到被调试程序继续执行的命令,STUB恢复被调试程序的执行,如图3所示。
由于它和被调试程序融为一体,所以它可以直接访问被调试程序的内存地址,查询或者修改被调试程序内存空间的值。
此方法将RTEMS系统看作一个嵌入式裸板程序,可以在源码级别对整个RTEMS系统进行调试。可以想象,此时GDB根本不知道被调试程序是一个操作系统,一旦STUB获得了执行机会,整个RTEMS系统进入暂停状态,无论系统中运行的是应用还是系统内核本身。而调试系统本身远远没有调试系统中应用程序的需求量大,在调试应用的时候,希望只是被调试的任务暂停,系统中其他任务不受我们调试行为的影响。下文将介绍RTEMS任务级别的GDB远程调试方法。