目录
文章目录
- 目录
- 摘要
- 1.ChibiOS Debugging Guide (ChibiOS调试指南)
- 2.Problems with debugging Embedded Code(调试嵌入代码的问题)
- 3.Kinds of Malfunctions(故障种类)
- 4.System Crashed(系统崩溃)
- 5.System Stuck(系统卡住)
- 6.System Halted(系统停止)
- 7.System Misbehaving(系统行为不当)
- 8.Debug First Actions(调试第一个操作)
- 9.Debug Configuration Settings(调试配置设置)
- 10.CH_DBG_SYSTEM_STATE_CHECK=TRUE
- 11.CH_DBG_ENABLE_CHECKS=TRUE
- 12.CH_DBG_ENABLE_ASSERTS=TRUE
- 13.CH_DBG_ENABLE_TRACE=TRUE
- 14.CH_DBG_ENABLE_STACK_CHECK=TRUE
- 15.CH_DBG_FILL_THREADS=TRUE
- 16.CH_CFG_OPTIMIZE_SPEED=FALSE
- 17.CH_CFG_ST_TIMEDELTA=0
- 18.Eclipse Debug Plugin(Eclipse调试插件)
- 19.General Suggestions
摘要
本节主要介绍ChibiOS的调试指南
1.ChibiOS Debugging Guide (ChibiOS调试指南)
操作系统中最重要的特性之一是支持开发人员调试应用程序代码。chibios/rt提供了几种在开发周期的调试阶段有帮助的机制。
2.Problems with debugging Embedded Code(调试嵌入代码的问题)
调试嵌入式代码通常很困难,因为任务的固有性质:
•系统通常与调试中的应用程序一起死亡。
•问题通常是间歇性的,很难抓住。
•问题不一定是由明显的原因引起的,更可能是有隐藏的原因。
3.Kinds of Malfunctions(故障种类)
系统故障有几种方法。首先,让我们为系统异常定义一些类别。
4.System Crashed(系统崩溃)
崩溃被定义为系统进入一个异常向量,在这个向量中通常停止崩溃。
chibios是静态的,这意味着它本身就很健壮,如果您遇到崩溃,那么原因可能是系统外部的。在静态系统中,最常见的崩溃原因是:
- 内存冲突。这是最明显的,如果您访问无效的地址或使用无效的内存对齐,那么CPU将直接进入异常。
- 堆栈溢出。对于每个线程,系统都有一个堆栈,对于异常,所有堆栈的大小都必须正确。溢出堆栈会损坏关键数据结构或其他堆栈,这会使CPU跳转到未映射的地址并陷入异常。
- 无效呼叫。从错误的上下文调用OS函数可能导致崩溃。并非所有操作系统函数都可以从任何上下文调用,例如,不能从ISR调用类似于wait的函数。每个操作系统都有要遵循的规则。从无效上下文调用函数是错误的常见原因,通常是随机的,很难捕获错误。
- 功能指针。如果代码中有函数指针,例如回调,那么这可能是系统失控的一种方式。指针可能包含空地址或无效地址。
- 未定义的ISR。如果触发的中断没有ISR,则系统将其视为异常并进入未处理的异常代码(闭环)。
5.System Stuck(系统卡住)
这种情况下,系统总是一次又一次地执行相同的代码,而不退出闭环。例如,由于列表损坏,您可以看到系统在不退出循环的情况下遍历线程就绪列表。
如果在系统代码中验证这种情况,则应考虑以下原因之一。
- 无效呼叫。以不正确的方式调用操作系统函数可能导致内部数据结构损坏。影响是系统代码中的死锁,但原因是外部的。
- 无限中断。写入ISR时,必须重置IRQ源,否则IRQ将在ISR退出后立即重新触发,从而阻塞系统。
6.System Halted(系统停止)
中止是操作系统或应用程序的自愿行为。当检测到异常情况时,系统调用一个进入停止状态的特殊处理程序。这是通过在chibios/rt中调用chsyshalt()来完成的。
暂停是件好事,因为:
- 这意味着已经检测到错误,并且没有被忽视。
- 从HALT处理程序可以检查堆栈跟踪和各种其他系统结构,并了解问题的性质。
所有chibios调试机制都将停止,以向开发人员发出检测到问题的信号。
所有chibios调试机制都将停止,以向开发人员发出检测到问题的信号。
7.System Misbehaving(系统行为不当)
当系统没有死机,而是以一种意想不到的方式运行时,就会发生这种情况。这可能是好事也可能是坏事。很好,因为可以使用调试器并尝试理解问题。坏,因为系统本身没有发现问题。
8.Debug First Actions(调试第一个操作)
在开发过程中,您应该使用启用的调试选项配置操作系统,并使用最少的优化来编译代码,gcc用户可以使用-o0。
9.Debug Configuration Settings(调试配置设置)
现在让我们看看所有可用的调试选项,以及它们应该如何帮助我们。所有选项都位于chconf.h文件中,通常位于项目源树的根目录中。
10.CH_DBG_SYSTEM_STATE_CHECK=TRUE
这可能是最重要的调试选项,它确保从适当的上下文调用所有RTOS函数。如果检测到无效的函数调用,则系统停止,全局变量ch.dbg.panic_msg指向错误字符串。可能的错误代码是:
- SV#1. 函数chsysdisable()已从ISR或关键区域内调用。
- SV#2. 函数chsyssuspend()已从ISR或关键区域内调用。.
- SV#3. 函数chsysEnable()是从ISR或关键区域内调用的。.
- SV#4. 函数chsyslock()是从ISR或关键区域内调用的。例如,如果您两次调用chsyslock(),就会发生这种情况。
- SV#5. 函数chsysunlock()是从ISR或关键区域内调用的。例如,如果您两次调用chSysUnlock()或不事先调用chSysLock(),就会发生这种情况。
- SV#6. 函数chSyslockFromISR()不是从ISR调用的,也不是从关键区域内调用的。例如,如果您两次调用chSyslockFromISR(),就会发生这种情况。
- SV#7. 函数chSysUnlockFromISR()未从ISR或关键区域内调用。例如,如果您两次调用chSysUnlockFromISR()或不事先调用chSysLockFromISR(),就会发生这种情况。
- SV#8. 宏ch_irq_prologue()尚未放置在ISR的最开始位置,或已放置在关键区域内。
- SV#9. 宏ch-irq-epilogue()未放置在ISR的最后,或放置在关键区域内,或ISR缺少ch-irq-prologue()。
- SV#10. 从临界区外调用了一个I类函数。
- SV#11. 已从关键区域外调用了S类函数,或从ISR调用了S类函数。
您可以看到这个选项非常有用,因为它允许在开发过程的早期捕获非常常见的使用错误。只是一个说明,“SV”代表“违反状态”。在chibios/rt中对系统状态进行了非常严格的检查。
另请参阅文章RT State Checker。
11.CH_DBG_ENABLE_CHECKS=TRUE
此选项允许检查API函数参数,如果出现错误,系统将暂停,并由ch.dbg.panic_msg指向一条消息。
12.CH_DBG_ENABLE_ASSERTS=TRUE
此选项启用系统断言。断言是放置在能够检测异常情况的关键位置的检查。如果出现错误,系统将暂停,并由ch.dbg.panic_msg指向一条消息。
13.CH_DBG_ENABLE_TRACE=TRUE
跟踪缓冲区存储最后n个上下文切换操作。它可以用来确定导致停机的操作顺序。跟踪缓冲区是内存结构,但是chibios/rt eclipse调试插件能够在表中显示内容。
14.CH_DBG_ENABLE_STACK_CHECK=TRUE
此选项启用端口定义的堆栈检查。注意,检查通常在上下文切换时执行,不一定捕获所有溢出条件。
15.CH_DBG_FILL_THREADS=TRUE
在运行线程之前,堆栈将填充固定模式(0x55555555)。模式允许确定实际使用了多少堆栈区域。在运行线程之前,堆栈将填充固定模式(0x55555555)。模式允许确定实际使用了多少堆栈区域。
16.CH_CFG_OPTIMIZE_SPEED=FALSE
将此选项设置为false将禁用一些内部代码内联,使操作系统代码更易于调试。它本身不是调试选项,但可以使调试体验更好。
17.CH_CFG_ST_TIMEDELTA=0
此选项禁用无滴答模式。如果您的问题是由于使用的虚拟计时器超出了系统为所有计时器提供服务的能力,那么这可能非常有用。
18.Eclipse Debug Plugin(Eclipse调试插件)
chibistudio for Eclipse插件包括调试rtos意识增to the Eclipse调试器。allows to the inspect插件在运行时数据结构和核心是强大的支持。信息包括:accessible
- 主动线程,线程列表(注册)表中显示了最重要的参数和name。
- 主动虚拟定时器列表。
- 跟踪缓冲区、在最后n个上下文切换事件与时间戳和其他相关信息一起显示。
- 调试变量。
- 全局变量。
- 统计。
19.General Suggestions
对于不太专业的用户,您可以做以下几件事,以最小化调试的需要:
-
首先仔细阅读文件。
-
在开发应用程序时启用各种调试选项。
-
试着为你要做的事情找到一个代码示例,好的来源是:
-
文件。
-
内核测试代码,在“./test”下,可以找到chibios/rt内核中几乎所有API的示例,以及与RTOS相关的最常见任务。
-
HAL测试代码,在“./test hal”下有关于各种设备驱动程序的示例。
-
演示应用程序。
-
从现有演示启动应用程序,一次添加一个,并经常测试,如果一次添加太多东西,则发现小问题可能成为调试的噩梦。遵循这个循环:思考、实施、测试、重复。
-
如果你被困太久,那么考虑征求意见。
-
报告错误和问题,可以修复错误,问题可以成为文档中的新文章(这篇文章和其他文档文章源自论坛或跟踪程序中的问题)。
-永不放弃