错误处理不太可能成为任何用于嵌入式系统应用程序的操作系统的主要功能。这是资源限制的必然结果——所有嵌入式系统都有某种限制。这也是合乎逻辑的,因为只有有限数量的嵌入式系统有机会像桌面系统一样运行——即为用户提供机会来决定在发生某些异常事件时下一步要做什么。

在 Nucleus SE 中,大致有三种类型的错误检查:

“健全性检查”所选配置的工具——只是为了确保所选选项一致

可选包含代码以检查运行时行为

有助于设计更健壮的代码的特定 API 函数

本文将涵盖所有这些内容以及有关用户实现的诊断的一些想法。

配置检查

Nucleus SE 的设计非常易于用户配置,因此可以对其进行定制以充分利用可用资源。这种可配置性是一个挑战,因为选项的数量以及它们之间的相互依赖性非常大。正如之前许多文章中所述,Nucleus SE 的大多数用户配置是通过 在文件nuse_config.h 中设置#define常量来执行的。

为了帮助识别配置错误,包含了一个文件 – nuse_config_check.h –(即通过#include 进入nuse_config.c),它对#define 符号执行许多一致性检查。以下是该文件的摘录:
/*** 任务和任务控制 /
#if NUSE_TASK_NUMBER < 1 || NUSE_TASK_NUMBER> 16
#ERROR NUSE:任务数量无效-必须是1-16
#ENDIF
#如果NUSE_TASK_RELINQUISH &&(NUSE_SCHEDULER_TYPE == NUSE_PRIORITY_SCHEDULER)
#ERROR NUSE:NUSE_Task_Relinquish()选择-不是有效
的优先级调度
#ENDIF
#如果NUSE_TASK_RESUME &&! NUSE_SUSPEND_ENABLE
#error NUSE: NUSE_Task_Resume() 选择 – 任务暂停未
启用
#endif
#if NUSE_TASK_SUSPEND && !NUSE_SUSPEND_ENABLE
#error NUSE: NUSE_Task_Suspend() 选择 – 任务暂停不
启用
#endif
#if NUSE_INITIAL_TASK_STATE_SUPPORT && !NUSE_SUSPEND_ENABLE
#error NUSE:初始任务状态已启用 – 任务挂起未
启用
#endif
/
分区池 ***/
#if NUSE_PARTITION_POOL_NUMBER > 16
#error NUSE:分区池数量无效 – 必须为 0-16
#endif
#if NUSE_PARTITION_POOL_NUMBER == 0
#if NUSE_PARTITION_ALLOCATE
#error NUSE: NUSE_Partition_Allocate() 已启用 – 未
配置分区池
#endif
#if NUSE_PARTITION_DEALLOCATE
#error NUSE:NUSE_Partition_Deallocate() 已启用 – 未
配置分区池
#endif
#if NUSE_PARTITION_POOL_INFORMATION
#error NUSE:NUSE_Partition_Pool_Information() 已启用 –
未配置分区池
#endif
#endif
执行的检查包括以下内容:

验证至少配置了一个,但不超过 16 个任务

确认所选的 API 函数与所选的调度程序或其他选项不一致

验证是否指定了不超过 16 个其他内核对象的实例

确认尚未为根本未实例化的对象选择 API 函数

确保在未启用这些功能时不选择信号和系统时间的 API 函数

验证选定的调度程序类型和相关选项

在所有情况下,检测到错误都会导致编译#error 语句。这通常会导致编译以指定的消息终止。

此文件不会使创建不合逻辑的配置成为不可能,但使其极不可能。

API参数检查

与 Nucleus RTOS 一样,Nucleus SE 可以选择性地包含代码以在运行时验证 API 函数调用参数。通常这只会在初始调试和测试期间使用,因为内存和运行时开销在生产代码中是不受欢迎的。

通过将nuse_config.h 中的NUSE_API_PARAMETER_CHECKING设置 为TRUE来启用参数检查。这使得编译所需的附加代码成为可能。以下是 API 函数参数检查的示例:
STATUS NUSE_Mailbox_Send(NUSE_MAILBOX 邮箱, ADDR *message,
U8 挂起)
{
STATUS return_value;
#if NUSE_API_PARAMETER_CHECKING
if (mailbox >= NUSE_MAILBOX_NUMBER)
{
return NUSE_INVALID_MAILBOX;
}
if (message == NULL)
{
return NUSE_INVALID_POINTER;
}
#if NUSE_BLOCKING_ENABLE
if ((suspend != NUSE_NO_SUSPEND) &&
(suspend != NUSE_SUSPEND))
{
return NUSE_INVALID_SUSPEND;
}
的#else
如果(挂起!= NUSE_NO_SUSPEND)
{
返回 NUSE_INVALID_SUSPEND;
}
#endif
#endif
此参数检查可能会导致 API 函数调用返回错误代码。这些都是NUSE_INVALID_xxx形式的负值 (例如NUSE_INVALID_POINTER)——一整套定义包含在nuse_codes.h 中。

可能会包含额外的应用程序代码(可能是有条件编译的)来处理这些错误值,但最好使用现代嵌入式调试器的数据监控工具来检测它们。

参数检查会在内存(额外代码)和运行时性能方面引入开销,因此它的使用有些侵入性。由于 Nucleus SE 的完整源代码可供开发人员使用,如果需要绝对精度,可以“手动”对生产代码进行检查和调试。

任务堆栈检查

只要未使用 Run to Completion 调度程序,Nucleus SE 就有一个可用的任务堆栈检查工具,它类似于 Nucleus RTOS 中提供的工具,并提供剩余堆栈空间的指示。这个 API 调用——NUSE_Task_Check_Stack() ——在之前的文章中有详细描述。本文后面的“用户诊断”部分讨论了有关堆栈错误检查的一些想法。

版本信息

Nucleus RTOS 和 Nucleus SE 有一个 API 函数,它只返回有关内核的版本/发布信息。

Nucleus RTOS API 调用

服务调用原型:

CHAR *NU_Release_Information(VOID);

参数:

没有任何

返回:

指向以 NULL 结尾的版本字符串的指针

Nucleus SE API 调用

此 API 调用支持 Nucleus RTOS API 的关键功能。

服务调用原型:

char *NUSE_Release_Information(void);

参数:

没有任何

返回:

指向以 NULL 结尾的版本字符串的指针

发布信息的 Nucleus SE 实现

这个 API 调用的实现几乎是微不足道的。返回指向字符串常量NUSE_Release_Info 的指针,该常量在nuse_globals.c 中声明和初始化。

该字符串采用 Nucleus SE – Xyymmdd的形式,其中:

X 是发布状态:A = alpha;B = 测试版;R = 发布
yy 是发布年份
mm 是发布月份
dd 是发布日期

与 Nucleus RTOS 的兼容性

Nucleus RTOS 包括一个用于维护历史日志的可选工具。内核记录各种系统活动的详细信息。提供 API 函数使应用程序能够:

启用/禁用历史保存

输入历史记录

检索历史条目

Nucleus SE 不支持此功能。

Nucleus RTOS 还包括一些错误管理宏,它们执行断言并提供一种方法,通过该方法可以调用用户定义的致命错误函数。这些有条件地包含在操作系统构建中。Nucleus SE 不支持这种类型的设施。

用户诊断

到目前为止,在本文中,我们已经了解了 Nucleus SE 本身提供的诊断和错误检查工具。现在是考虑如何使用内核提供的工具和/或应用我们对其内部结构和实现的知识来实现​​用户定义或面向应用程序的诊断的好机会。

特定应用诊断

几乎任何应用程序都可以添加额外的代码来在运行时检查自身的完整性。使用多任务内核,让特定任务完成这项工作非常方便和直接。显然,非常针对应用程序的诊断不在本系列文章的范围内,但我们可以考虑一些广泛的想法。

内存检查

内存的正确操作显然对任何基于处理器的系统的完整性至关重要。同样明显的是,灾难性故障会阻止任何软件运行,更不用说诊断了。但是在某些情况下,发生一定程度的故障并且是一个主要问题,但并不能完全阻止代码执行。测试内存是一个相当复杂的话题,超出了本文的范围,所以我只能给出一些大致的想法。

RAM 中可能出现的两种最常见的故障是: “卡住位”——位的值为零或一且无法更改;和“串扰”——相邻位相互干扰。这些都可以通过依次向每个 RAM 位置写入和读回适当的测试模式来测试。有些测试只能在启动时进行,甚至在建立堆栈之前;例如,“移动一个”测试,其中内存中的每一位都设置为 1,并且检查其他每一位以确保它为零。其他逐字节模式测试可以即时执行,只要您确保在 RAM 位置损坏时不会发生上下文切换。使用 Nucleus SE 临界区分隔宏NUSE_CS_Enter() 和NUSE_CS_Exit(),在nuse_types.h中定义,简单且可移植。

各种类型的 ROM 也会偶尔出现故障,但软件可以执行的检查有限。构建代码时生成的校验和会很有用。这可以在启动时检查,也可以在运行时检查。

内存寻址逻辑故障会影响 ROM 和 RAM。可能会专门为此设计一个测试,但它最有可能出现在上述其他测试中。

外围设备检查

在 CPU 之外,外围电路可能会出现故障。当然,从一个系统到另一个系统,这将有很大差异,但设备通常有一些方法可以通过诊断软件验证其完整性。例如,一条通信线路可能具有环回模式,从而立即返回写入其中的任何数据。

看门狗服务

嵌入式系统设计人员通常包括一个“看门狗”电路。这是一个外围设备,它要么中断 CPU 并期待快速响应,要么(更好)需要由软件启动的定期访问。在任何一种情况下,看门狗“咬”的常见结果是系统重置。

在多任务环境中有效地使用看门狗具有挑战性。简单地从一项任务中维护它只会确认该特定任务正在运行。解决此问题的一种方法是实施“主管任务”——本文稍后将介绍一个示例。

堆栈溢出检查

除非您选择 Run to Completion 调度程序,否则 Nucleus SE 应用程序将为每个任务包含一个堆栈。这些堆栈的完整性至关重要,但 RAM 可能有限,因此获得最佳大小至关重要。静态预测每个任务的堆栈需求是可能的,但非常困难——它需要有足够的容量来满足最嵌套的函数调用以及最需要堆栈的中断服务例程的需求。一种更简单的方法是执行详尽的运行时测试。

堆栈验证大致有两种方法。如果正在使用复杂的嵌入式软件调试器,则可以监控堆栈边界,并检测任何违规行为。Nucleus SE 堆栈的位置和大小可通过 ROM 中的全局数据结构轻松访问:NUSE_Task_Stack_Base[] 和NUSE_Task_Stack_Size[]。

另一种方法是执行运行时测试。通常的方法是在每个堆栈的末尾添加“保护字”——通常这些是每个堆栈数据区域中的第一个位置。这些词被初始化为可识别的非零值。然后,诊断程序/任务检查它们是否已更改并采取适当的措施。保护字的覆盖并不意味着堆栈实际上已经溢出,而是表明它即将溢出;因此,软件可能会继续执行足够长的时间以采取纠正措施或警告用户。

主管任务

尽管 Nucleus SE 不保留可能的 16 项任务中的任何一项供其自己使用,但用户可以选择将一项专门用于诊断。这可能是一个低优先级的任务,它只是利用了任何“空闲”的 CPU 时间;或者它可能是偶尔运行短时间的高优先级任务,从而确保始终定期执行诊断。

下面是一个示例的运行方式:

监督任务的信号标志用于监控系统中六个关键任务的操作。这些任务每个都使用一个特定的标志(位 0 到位 5)并且需要定期设置它。主管任务会清除所有标志,然后自己暂停一段时间。当它恢复时,它希望通过设置适当的标志来“签入”所有六个任务;它寻求与值b00111111 (来自nuse_binary.h)的精确匹配。如果满足,它会清除标志并再次挂起。如果没有,它会调用关键错误处理例程,例如,它可以执行系统重置。

另一种实现可能使用了事件标志组。如果信号没有在应用程序的其他地方使用(因为所有任务都会产生 RAM 开销),这将是有意义的,如果将事件标志用于其他目的,则更是如此。

跟踪和分析

尽管许多现代嵌入式软件调试器都具有很强的可定制性并且可以实现“RTOS 感知”,但调试多线程应用程序仍然具有挑战性。一种广泛使用的方法是执行后分析,其中对 (RTOS) 代码进行检测,以便对其操作的详细审计可以进行回顾性分析。通常,实施此类设施涉及两个组成部分:

附加代码被添加到 RTOS(即它被“检测”)以记录活动。通常,这将包含在预处理器指令中以促进条件编译。当发生重大事件时,此代码会存储几个字节的信息 - 例如 API 调用或上下文切换。这些信息是这样的:

– 当前地址 (PC)。

– 当前任务 ID(索引)。

– 涉及的任何其他对象的索引。

– 指示已执行操作的代码。

一项专门用于将配置文件信息缓冲区清空到外部存储器(通常是主机)的任务。

对这些捕获数据的分析也需要一些工作,但这可能就像使用 Excel 电子表格一样简单。

在下一篇文章中,我们将详细回顾 Nucleus SE 与 Nucleus RTOS 的兼容性。
相关实战:https://www.yunduoketang.com/article/zaixianjiaoyupingtai9.html
https://www.yunduoketang.com/article/lubopingtaixitong9.html
https://www.yunduoketang.com/article/jiaoxuexitongdajian9.html
https://www.yunduoketang.com/article/jiaoxuexitongdajian9.html
https://www.yunduoketang.com/article/jiaoxuexitongdajian9.html

RTOS 诊断和错误检查相关推荐

  1. RTOS诊断和错误检查

    RTOS诊断和错误检查 RTOS diagnostics and error checking 查看RTOS显示系列 错误处理不太可能是任何用于嵌入式系统应用程序的操作系统的主要功能.这是资源限制的必 ...

  2. ORACLE ORA-28545: 连接代理时 Net8 诊断到错误 解决办法

    oralce透明网关很好很强大,可以把多种数据库当成一个数据库来使用,比如在你的oracle数据库里面想和db2里面的数据一起使用,通过透明网关就可以将db2连接到oracle中,具体怎么配置可以参见 ...

  3. AIDE支持实时错误检查、代码重构、代码智能导航、生成APK

    AIDE是一个Android Java集成开发环境,可以在Android系统内进行Android软件和游戏的开发.它不仅仅是一个编辑器,而是支持编写-编译-调试运行整个周期,开发人员可以在Androi ...

  4. vscode 语法检查_Jenkins 声明式流水线的语法错误检查

    在做 Jenkins 声明式流水线开发时常会遇到的问题是:Pipeline 看起来没有问题,当提交到代码仓库后进行 Jenkins 构建时发现原来有语法错误,然后再去修改.提交.构建,结果可能还有有其 ...

  5. 视频编解码(十七):视频流错误检查步骤-进程查看内存方法

    一.视频流错误检查步骤 1.基本检查流程:     (1) 验证码流是否有错,保存bitstream文件或者awsp文件,直接播放码流文件:     (2) 输入码流的对比, parser 传入跟工具 ...

  6. 用java代码检查sql语法错误_您的SQL语法有错误;检查与MariaDB服务器版本对应的手册,以便在第1行'?'附近使用正确的语法...

    我正在使用 Java 和 JDBC 制作库存系统 . 我在查询表时遇到了这个错误 . com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException ...

  7. oracle服务器 绿灯闪频繁,IBM x86服务器光通路诊断指示灯错误信息

    1.无,但系统错误指示灯点亮.已发生错误但无法诊断,或 Remote Supervisor Adapter II SlimLine 上的高级系统管理(ASM)处理器发生故障.光通路诊断指示灯不表示该错 ...

  8. securecrt遇到一个致命的错误且必须关闭_高性能服务器之路 | 浅谈 Valgrind 内存错误检查神器 Memcheck...

    本文是 高性能服务器开发 第一篇 导读 Memcheck 可以检查哪些内存错误? 使用 Memcheck 解决问题的原则 原则 1,内存非法读写错误一定要解决 原则 2,变量未初始化错误一定要解决 原 ...

  9. 诊断ORA-08103错误

    ORA-08103问题的诊断最好是能生成8103错误的ERROR STACK TRACE, 在TRACE中会记录具体引发8103的对象的OBJ和OBJD,这便于我们定位可能存在corruption的对 ...

  10. git PHP commit 规范,git commit 时自动对所有 php 文件执行语法错误检查

    使用 Shell 编写 hooks 下的 pre-commit 钩子,实现在 git commit 时检查所有的 .php 文件(忽略所有删除状态的文件)是否存在语法错误,如果存在错误,则终止提交,并 ...

最新文章

  1. android webview 加载本地pdf,android – 在WebView中打开PDF
  2. 多模态人物识别技术及其在视频场景中的应用 | CSDN技术公开课
  3. 大数据开发源码视频今日免费送!
  4. IOS开发笔记7-C语言基础复习
  5. C++shell sort希尔排序的实现算法之二(附完整源码)
  6. Android setColor
  7. GDI+入门——带你走进Windows图形的世界
  8. 第39天-进程 _1(2013.09.11)
  9. Tomcat9.0部署iot.war(环境mysql8.0,centos7.2)
  10. h3c c语言题库,H3C认证试题
  11. Cesium基础使用介绍
  12. 唯一标识 微信小程序_微信小程序中用户唯一ID的获取
  13. 计算理论重点——Theory of Computation
  14. OverFeat心得
  15. 计算机病毒是如何入侵你的电脑吗,怎么样正确处理被病毒侵入的电脑
  16. OpenModelica模型导入Simulink运行的方法
  17. 2021-06-11打开VMware虚拟机时提示“锁定文件失败 打不开磁盘或它所依赖的某个快照磁盘。
  18. 毕设 数据库ER图绘制过程中的参考资料
  19. java数据库连接Druidsql失败_Druid数据库连接池异常connection holder is null
  20. Google Guava 的 5 个鲜为人知的特性

热门文章

  1. 【mediasoup 带宽估计】aimd算法2 : AimdRateControl
  2. 小菜鸟的Python笔记002:如何识别Word文档中的复选框
  3. html复选框,不打勾默认值是0,打钩默认值是1,方框打钩符号复制(一招教你方框里打勾的符号)...
  4. 智能创新引导工具软件——工作量分配和里程碑安排
  5. 为什么下载小电影时,经常会卡在 99%?
  6. Win11更新后电脑没有声音,声卡驱动失效,卸载重装依然无效
  7. 读取excel数据批量填充world
  8. 基于蓝墨云平台的计算机教学,基于蓝墨云班课平台的计算机应用基础翻转课堂教学研究 精读...
  9. Java SE《基础篇》——(二)程序基础01
  10. 读取微信聊天记录并制作词云图