【ARMv8M Cortex-M33 系列 7.2 -- HardFault 问题定位 1】

文章目录

    • 问题背景
    • 堆栈对齐要求
      • Cortex-M33 的 FPU 功能

问题背景

rt-thread 在PendSV_Handler退出的时候发生了HardFault_Handler是什么原因?且 LR 的值为0xfffffffd

堆栈对齐要求

在 ARM Cortex-M 架构中,堆栈指针 (SP) 必须始终保持 8 字节对齐。这是因为从 ARMv7-M 开始,堆栈帧可能包含额外的浮点寄存器,而要求 8 字节对齐以实现更有效的访问和与浮点寄存器大小相一致。

在进入异常处理时,处理器会自动将 xPSR、返回地址、LRR12R3R2R1R0 压入堆栈;如果使用浮点单元且由异常激活,则还会压入 S0-S15FPSCR 寄存器。

当从异常返回时,处理器会根据 LR 中的 EXC_RETURN 值来检查堆栈指针,以确保正确地恢复寄存器状态。

发生 HardFault 的原因可能很多,但当你看到 LR(链接寄存器)的值为 0xFFFFFFFD 时,这表明异常返回时处理器试图从进程堆栈指针(PSP)恢复上下文。这个特定的 EXC_RETURN 值意味着在从异常(这种情况下是 PendSV)返回时,发生了与堆栈或上下文恢复有关的问题。

以下是一些可能导致你在 PendSV_Handler 退出时遭遇 HardFault 的原因:

  1. 堆栈指针 (PSP) 不正确:如果 PSP 被错误地设置或在异常处理期间被破坏,它可能不再指向有效的堆栈帧,导致在尝试恢复寄存器时访问了错误的内存地址。
  2. 堆栈溢出:如果任务的堆栈空间不足,可能在堆栈中写入时超过了分配的边界,导致堆栈损坏。
  3. 上下文保存不完整或不正确:在进入 PendSV_Handler 时,必须保存当前任务的上下文,包括所有必要的寄存器。如果保存过程中出错,或者未能保存足够的寄存器状态,那么恢复这些寄存器时会遇到问题。
  4. 上下文恢复到错误的地址:如果保存的程序计数器(PC)或状态寄存器(xPSR)的值不正确,那么在尝试返回到这些地址时会触发 HardFault
  5. 错误的异常返回指令:虽然 LR 的值是正确的 EXC_RETURN,但如果在异常处理的汇编代码中有错误,可能会导致错误的堆栈操作或错误的异常返回。

为了调试此 HardFault,可以采取以下步骤:

  • 检查 PSP 的值:在 HardFault_Handler 中,检查 PSP 是否指向有效的内存区域。
  • 检查堆栈大小:验证所有任务的堆栈大小是否足够,并没有发生堆栈溢出。
  • 使用调试器:如果可能,使用调试器单步执行 PendSV_Handler 中的代码,观察 PSPPCxPSR 的值以及它们的变化。
  • 查看 HardFault_Handler :实现一个 HardFault_Handler 来捕获硬件错误,从中可以读取更多的系统状态和错误信息,例如配置故障状态寄存器 CFSRHFSRMMFARBFAR
  • 审查 RT-Thread 的系统配置:确认 RT-Thread 的配置与你的硬件设备兼容,尤其是关于任务堆栈和堆内存的部分。
  • 堆栈帧对齐检查:确保在进入 PendSV_Handler 之前堆栈帧是正确对齐的,因为 ARM Cortex-M 系列处理器要求堆栈必须8字节对齐。如果启用了自动堆栈对齐检查,STKALIGN 位在 CCR 寄存器内,那么在对齐错误时可能会引发 UsageFault,如果没有启用相关的 UsageFault,则会变成 HardFault

接着上篇文章:【ARMv8M Cortex-M33 系列 7.1 – xPSR | CFSR | HFSR | BFAR | MMFAR 寄存器】 来通过JLink 来对 错误提示信息寄存器进行debug,它们的地址如下:

#define SCB_CFSR        (*(volatile const unsigned *)0xE000ED28) /* Configurable Fault Status Register */
#define SCB_HFSR        (*(volatile const unsigned *)0xE000ED2C) /* HardFault Status Register */
#define SCB_MMAR        (*(volatile const unsigned *)0xE000ED34) /* MemManage Fault Address register */
#define SCB_BFAR        (*(volatile const unsigned *)0xE000ED38) /* Bus Fault Address Register */
#define SCB_AIRCR       (*(volatile unsigned long *)0xE000ED0C)  /* Reset control Address Register */
#define SCB_RESET_VALUE 0x05FA0004                               /* Reset value, write to SCB_AIRCR can reset cpu */

通过JTAG 读取上面debug 寄存器SCB_CFSR的值:

mem32 0xe000ed28 1
E000ED28 = 00040000

在这里插入图片描述
INVPC, bit [2]
Invalid PC flag. Sticky flag indicating whether an integrity check error has occurred.

可以看到发生 INVPC 这个错误。

继续 Debug 其它寄存器:

mem32 0xe000ed2c 1
E000ED2C = 40000000

在这里插入图片描述
FORCED, bit [30]
Forced. Indicates that a fault with configurable priority has been escalated to a HardFault exception, because
it could not be made active, because of priority, or because it was disabled.

从上面的解释可以看到问题原因是由于某个异常升级为了 HardFault 异常了,可能是由于这个异常没有enable,所以后面就需要查看如何使能Cortex-M33 的各种异常。

继续 Debug 其它寄存器:

mem32 0xe000ed34 1
E000ED34 = 20000BF4

在这里插入图片描述
ADDRESS, bits [31:0]
Data address for an MemManage fault. This register is updated with the address of a location that produced a
MemManage fault. The MMFSR shows the cause of the fault, and whether this field is valid. This field is
valid only when MMFSR.MMARVALID is set, otherwise it is UNKNOWN.

Attributes
8-bit read/write-one-to-clear register located at 0xE000ED28.
在这里插入图片描述
这个寄存器也就是寄存器CFSR 的 低8bits,由于低8bits 为0,所以,不是memmanage fault 的问题。

mem32 0xe000ed38 1
E000ED38 = 20000BF4

在这里插入图片描述
ADDRESS, bits [31:0]
Data address for a precise BusFault. This register is updated with the address of a location that produced
a BusFault. BFSR shows the reason for the fault. This field is valid only when BFSR.BFARVALID is set,
otherwise it is UNKNOWN.
由于 BFSR.BFARVALID 值为0,所以也不是 Busfault。

当将编译参数中的硬浮点修改为软浮点之后,再去读CFSR 寄存器的值为:

J-Link>mem32 0xe000ed28 1
E000ED28 = 01000000

也就是报出 UNALIGNED 错误(Debug 到最后发现也不是这个问题引起的)。到目前为止仍然没有找到问题所在!!!

那么如何配置不使用fpu功能?
要在 ARM Cortex-M33 上使用 ARM GCC 编译器配置不使用 FPU(浮点单元)功能,需要在编译选项中指定不使用硬件浮点支持。这可以通过设置适当的编译器标志实现。

ARM Cortex-M33 可以配置为带有或不带有 FPU。如果你的 Cortex-M33 核心不包含 FPU,或者你的应用程序不需要浮点运算支持,你应该确保编译器不生成任何浮点指令或链接到浮点库。

以下是如何在编译器选项中禁用 FPU 支持的示例:

-mcpu=cortex-m33 -mthumb -mfloat-abi=soft 

这里的编译器选项说明如下:

  • -mcpu=cortex-m33: 指定目标 CPU 是 Cortex-M33。
  • -mthumb: 指示编译器生成 Thumb 指令集的代码。
  • -mfloat-abi=soft: 指定浮点 Application Binary Interface (ABI) 为软件实现(soft)。

这意味着即使硬件支持浮点运算,也将使用软件库来执行浮点运算。这个选项确保编译器不会生成使用 FPU 的代码。

如果你的应用程序确实包含浮点运算,上述设置会导致所有浮点运算都通过软件库函数实现,而不是使用 FPU。这会导致浮点运算性能降低,但可以避免在不包含 FPU 的 Cortex-M33 核心或者选择不使用 FPU 的情况下,发生与硬件相关的问题。

请确保编译器选项在整个项目的编译和链接过程中保持一致,包括任何库或外部模块。如果链接到了已编译的库,也需要确保这些库是在不使用 FPU 支持的情况下编译的。

最后在Makefile 中的配置如下

#LDS_INC = -L $(LIB_PATH)/lib/gcc/arm-none-eabi/10.2.1/thumb/v8-m.main+fp/hard
LDS_INC = -L $(LIB_PATH)/lib/gcc/arm-none-eabi/10.2.1/thumb/v8-m.main/nofp \
        -L $(LIB_PATH)/arm-none-eabi/lib/thumb/v8-m.main/nofp
all: $(TARGET) postbuild

$(TARGET): $(OBJS)
        @echo Building target: $@
        $(LD) $(LDS_INC) -T $(LDS) --gc-sections -Map ra4m2.map -o $@ $(OBJS) -lc -lm -lgcc

Cortex-M33 的 FPU 功能

ARM Cortex-M33 处理器是 ARMv8-M 架构的一部分,可选地包含一个符合 IEEE 754 标准的单精度浮点单元 (FPU),支持所有单精度浮点数据类型的运算。包含 FPU 的 Cortex-M33 可以提高浮点计算的性能,适用于需要执行大量浮点计算的应用程序。

Cortex-M33 的 FPU 支持以下特性:

  • 编译器可以生成硬件 FPU 指令来完成浮点运算,这通常比软件实现更快。
  • FPU 支持单精度(32位)浮点数的加、减、乘、除运算和其他复杂运算。
  • 浮点运算的结果可以直接用于程序流程控制,如浮点比较和分支。

如果选择在 Cortex-M33 上使用 FPU 功能,需要使用 -mfloat-abi=hard-mfloat-abi=softfp 编译器选项来启用硬件浮点支持。这些选项会使编译器产生使用 FPU 的代码,并链接到相应的浮点库。

Q:cortex-m33默认安全状态下如何启动rt-thread os,需要配置哪些内容? 可以一直在安全状态下运行os吗?
A: 要在 Cortex-M33 默认的安全状态下启动 RT-Thread OS,需要执行一系列的初始化步骤来配置处理器,启动操作系统,并确保操作系统及其任务在安全状态下正确运行。

下面是一般需要执行的步骤:

  1. 初始化硬件
    • 配置系统时钟,包括 CPU 时钟、外设时钟等。
    • 初始化必要的外设,如定时器、串口、中断控制器等。
  2. 配置中断向量表
    • 将 RT-Thread 的中断向量表的位置设置到默认的中断向量表寄存器(VTOR)。
  3. 配置堆栈指针
    • 设置 MSP 或 PSP 的值,确保为 RT-Thread OS 的中断和任务提供正确的堆栈。
  4. 初始化 RT-Thread OS
    • 调用 RT-Thread 提供的初始化函数,如 rt_system_scheduler_init 初始化调度器,rt_system_timer_init 初始化系统定时器等。
  5. 创建任务(线程)
    • 使用 RT-Thread 提供的 API,如 rt_thread_create,来创建并初始化操作系统任务。
  6. 启动调度器
    • 调用 rt_system_scheduler_start 来启动 RT-Thread 的调度器。
  7. 附加系统服务和中断处理
    • 将 RT-Thread 的系统服务和中断处理函数附加到 Cortex-M33 的异常和中断向量。
  8. TrustZone 配置(如果使用 TrustZone)
    • 如果打算使用 TrustZone,你需要正确配置安全属性单元(SAU),确保内存和外设的安全状态符合 RT-Thread 的要求。在默认安全状态下,这一步可能不是必需的。 你可以一直在安全状态下运行 RT-Thread OS。

实际上,如果你不需要 TrustZone 提供的安全状态和非安全状态之间的隔离,或者不打算在非安全状态下运行任何代码,那么你可以简单地将整个系统配置为安全状态,并在该状态下运行操作系统。这种情况下,你不需要配置任何有关 TrustZone 的特定内容,系统将作为一个普通的单状态(只有安全状态)系统运行。

如果你使用了 TrustZone 并且需要在系统的非安全状态下运行某些代码,那么你需要在系统启动时配置 TrustZone 的相关设置,并实现从安全状态到非安全状态的切换逻辑。

总之,RT-Thread OS 作为一个灵活的实时操作系统,能够在 Cortex-M33 处理器的安全状态下运行,无论是独立于 TrustZone 特性,还是与 TrustZone 安全特性一起使用。具体配置和启动步骤应参考 RT-Thread OS 的文档和 Cortex-M33 的硬件手册。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/334764.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【ChatGPT】利用ChatGPT将图片转换成JSON文件

前言 我在创建自己的GPT时,通常会上传一些JSON文件作为知识库,我还制作了一些脚本工具,将PDF文件转换成JSON文件。但是在这个过程中产生一个问题,PDF文件中会有一些图表,JSON文件就不能存储和表达这些图表的内容了。那该怎么办呢?这里跟大家介绍一个方法,可以有效地将图…

大数据开发之Hadoop(完整版+练习)

第 1 章:Hadoop概述 1.1 Hadoop是什么 1、Hadoop是一个由Apache基金会所开发的分布式系统基础架构。 2、主要解决,海量数据的存储和海量数据的分析计算问题。 3、Hadoop通常是指一个更广泛的概念-Hadoop生态圈 1.2 Hadoop优势(4高&#xf…

vue中内置指令v-model的作用和常见使用方法介绍以及在自定义组件上支持

文章目录 一、v-model是什么二、什么是语法糖三、v-model常见的用法1、对于输入框(input):2、对于复选框(checkbox):3、对于选择框(select):4、对于组件(comp…

关于C#中的LINQ的延迟执行

简介 Linq中的绝大多数查询运算符都有延迟执行的特性,查询并不是在查询创建的时候执行,而是在遍历的时候执行 实例&#xff1a; public void Test2(){List<int> items new List<int>() { -1, 1, 3, 5 };IEnumerable<int> items2 items.Where(x > x &g…

ChatGPT 如何解决 “Something went wrong. lf this issue persists ….” 错误

Something went wrong. If this issue persists please contact us through our help center at help.openai.com. ChatGPT经常用着用着就出现 “Something went wrong” 错误&#xff0c;不管是普通账号还是Plus账号&#xff0c;不管是切换到哪个节点&#xff0c;没聊两次就报…

《数字图像处理-OpenCV/Python》连载:傅里叶变换与频域滤波

《数字图像处理-OpenCV/Python》连载&#xff1a;空间滤波之高斯滤波器 本书京东 优惠购书链接 https://item.jd.com/14098452.html 本书CSDN 独家连载专栏 https://blog.csdn.net/youcans/category_12418787.html 第 11 章 傅里叶变换与频域滤波 空间图像滤波是图像与滤波器核…

mysql B+树索引

数据库索引用于提高查询性能和数据访问效率。索引可以加速数据的查找和筛选&#xff0c;减少查询的时间复杂度。数据库索引有很多类型&#xff0c;这里不展开也不比较&#xff0c;只介绍最常见一种索引结构B树索引。mysql中InnoDB引擎默认使用的就是BTREE索引。 B树数据结构 …

实验三 Oracle数据库的创建和管理

&#x1f57a;作者&#xff1a; 主页 我的专栏C语言从0到1探秘C数据结构从0到1探秘Linux &#x1f618;欢迎关注&#xff1a;&#x1f44d;点赞&#x1f64c;收藏✍️留言 &#x1f3c7;码字不易&#xff0c;你的&#x1f44d;点赞&#x1f64c;收藏❤️关注对我真的很重要&…

fastjson-BCEL不出网打法原理分析

FastJson反序列化漏洞 与原生的 Java 反序列化的区别在于&#xff0c;FastJson 反序列化并未使用 readObject 方法&#xff0c;而是由 FastJson 自定一套反序列化的过程。通过在反序列化的过程中自动调用类属性的 setter 方法和 getter 方法&#xff0c;将JSON 字符串还原成对…

我在代码随想录|写代码Day9之28. 实现 strStr(),459. 重复的子字符串,55. 右旋字符串(第八期模拟笔试)

博主介绍: 27dCnc 专题 : 数据结构帮助小白快速入门 28. 实现 strStr() 题目; 代码 1 class Solution { public: //KMPint strStr(string s, string t) {int n s.size(),mt.size();if(m0) return 0;s.insert(s.begin(), );t.insert(t.begin(), );vector<int> next(m1);…

容器技术1-容器与镜像简介

目录 1、容器与虚拟化 2、容器发展历程 3、镜像简介 4、镜像原理 &#xff08;1&#xff09;分层存储 &#xff08;2&#xff09;写时复制 &#xff08;3&#xff09;内容寻址 &#xff08;4&#xff09;联合挂载 1、容器与虚拟化 容器技术在操作系统层面实现了对计算机…

基于ORB算法的图像匹配

基础理论 2006年Rosten和Drummond提出一种使用决策树学习方法加速的角点检测算法&#xff0c;即FAST算法&#xff0c;该算法认为若某点像素值与其周围某邻域内一定数量的点的像素值相差较大&#xff0c;则该像素可能是角点。 其计算步骤如下&#xff1a; 1&#xff09;基于F…

个人实现的QT拼图游戏(开源),QT拖拽事件详解

文章目录 效果图引言玩法 拖拽概念基本概念如何在Qt中使用拖放注意事项 游戏关键问题总结 效果图 ![在这里插入图片描述](https://img-blog.csdnimg.cn/direct/c6dd66befd314442adf07e1dec0d550c.png 引言 在学习QT demo时&#xff0c;发现有一个拼图demo&#xff0c;介绍拖…

LLVM 环境配置

这里选择下载源码, 然后编译的安装方式。 下载地址 (在这里可以找到多版本, 多平台的LLVM下载资源) # 解压源码 sudo tar xvf llvm-project-17.0.6.src.tar.xz # 新建安装目录 sudo mkdir -p /usr/local/llvm # 新建编译目录 sudo mkdir -p llvm-project-17.0.6.src/build #…

非线性最小二乘问题的数值方法 —— 狗腿法 Powell‘s Dog Leg Method (I - 原理与算法)

Title: 非线性最小二乘问题的数值方法 —— 狗腿法 Powell’s Dog Leg Method (I - 原理与算法) 文章目录 I. 前言II. 线搜索类型和信赖域类型1. 线搜索类型 —— 最速下降法2. 信赖域类型3. 柯西点 III. 狗腿法的原理1. 狗腿法的构建2. 狗腿法的优化说明3. 狗腿法的插值权重 I…

Java中打印图案最常用的25个图案程序

Java是公认的最流行的编程语言&#xff0c;因为它的简单性和多功能性。还可以使用它开发各种应用程序&#xff0c;包括Web、移动和桌面应用程序。此外&#xff0c;Java为开发人员提供了强大的工具来轻松高效地创建复杂的程序。Java最有前途的特性之一是它能够创建可以以特定格式…

Linux环境下部署Tomcat(详细图文)

目录 一、下载地址 1.服务器不能联网情况下载 2.服务器能够联网 二、安装 1. Tomcat解压 2. Tomcat目录说明&#xff1a; 3. 重命名解压后的文件名 4. 配置环境变量 5. 修改配置文件 6.启动Tomcat 7.访问Tomcat 8. 停止Tomcat 一、下载地址 1.服务器不能联网情况下…

PyTorch视觉工具箱:图像变换与上采样技术详解(1)

目录 Pytorch中Vision functions详解 pixel_shuffle 用途 用法 使用技巧 注意事项 参数 数学理论公式 示例代码及输出 pixel_unshuffle 用途 用法 使用技巧 注意事项 参数 数学理论公式 示例代码及输出 pad 用途 用法 使用技巧 注意事项 参数 示例代码…

SMT回流焊工艺之回流温度曲线

引言 在SMT生产流程中&#xff0c;如何控制回焊炉的温度是非常重要的一环&#xff0c;好的炉温曲线图意味着可以形成良好的焊点。 上一期分享&#xff08;SMT回流焊温度解析之锡膏焊接特性&#xff09;中&#xff0c;我们着重介绍了SMT回流工艺中的锡膏焊接部分。本期内容主要…

Leetcode2957. 消除相邻近似相等字符

Every day a Leetcode 题目来源&#xff1a;2957. 消除相邻近似相等字符 解法1&#xff1a;遍历 分类讨论 遍历字符串 word&#xff0c;比较相邻的 3 个元素 word[i - 1]、word[i] 和 word[i 1]&#xff0c;记 left_distance abs(mid - left)&#xff0c;right_distance…
最新文章