CH32V307 FreeRTOS的浮点问题

在使用官方提供的FreeRTOS例程中,默认是不使用F指令子集的。我在开启了F指令子集后,并在“freertos_risc_v_chip_specific_extensions.h”文件中将宏ARCH_FPU修改为1后,无法进行浮点数的计算。工程配置如下

图片.png

测试程序如下:

图片.png

打印的内容如下:

图片.png

但是不开F指令子集的话是可以正常打印计算的。请问是有什么操作不正确吗

您好,可以检查一下操作系统中任务堆栈的对齐方式是否为8字节对齐,若不是,改为8字节对齐应该可以解决问题。printf的C运行库要求8字节对齐,若没有对齐导致发送浮点数失败,因此操作操作系统需要对任务堆栈做出要求,需要进行8字节对齐。FreeRTOS的字节对齐方式设置如下图

image.png

此外需要注意下,当需要打印浮点类型时,MRS要进行如下配置,具体如下图:

image.png



你好,我检查了工程,已经进行了8字节对齐,另外也已经打开了打印浮点数的配置。下面附上我的工程:

icon_rar.gifEXAM.zip



您好,工程配置将下图圈出部分也勾选上

image.png


你好,我已经勾选上了该配置,但是仍然无法正常输出。串口的输出信息如下:

SystemClk:144000000
FreeRTOS Kernel Version:V10.4.6
task2 entry 1.200000
task1 entry 0.100000
task1 entry 0.000000
task2 entry 0.000000
task1 entry 0.000000
task1 entry 0.000000
task2 entry 0.000000
task1 entry 0.000000

可以看到,在第一次进入task的时候是能正常计算出值的,但是后面经过任务调度之后就变成0了。我猜测是否是任务调度器在切换任务的时候没有把浮点CPU寄存器正常压栈,即“freertos_risc_v_chip_specific_extensions.h”文件中的语句无法正常工作?


您好,附件为我的测试例程,在我们EVT例程基础上修改的,若配置没问题,测试打印正常的,你可以看一下或直接用我的测试例程,任务配置和你一样的

icon_rar.gifCH32V307 FreeRTOS浮点运算.zip

image.png


你好,我使用了你的测试例程,确实可以打印但是我发现“freertos_risc_v_chip_specific_extensions.h”中的ARCH_FPU宏没有打开。该宏的用途是在任务切换时对FPU寄存器进行压栈和弹栈处理。

图片.png

由于该宏没有打开,导致了task1和task2互相使用了对方的计算结果,该现象在串口打印的数值中也可以看出:

SystemClk:144000000
FreeRTOS Kernel Version:V10.4.6
task2 entry, b = 1.200000
task1 entry, a = 0.100000
task1 entry, a = 0.200000
task2 entry, b = 0.300000
task1 entry, a = 0.400000
task1 entry, a = 0.500000
task2 entry, b = 0.600000
task1 entry, a = 0.700000
task1 entry, a = 0.800000
task2 entry, b = 0.900000
task1 entry, a = 1.000000
task1 entry, a = 1.100000
task2 entry, b = 1.200000

同样,在第一次进入task的时候正常打印了值a和b,分别是1.2和0.1。然而在进行过一次任务切换后,b的值变成了0.3,这说明浮点寄存器没有被压栈,使用的值是之前计算a时调用FPU寄存器的值。


我找到问题了。贵公司提供的例程:/downloads/CH32V307EVT_ZIP.html  中FreeRTOS的例程中使用的“freertos_risc_v_chip_specific_extensions.h”文件第106行至第133行,FPU寄存器全部从同一个栈地址弹栈,导致切换任务时恢复浮点寄存器现场出现错误。

图片.png

在你提供给我的这个工程中,该错误是被修复的。


您好,感谢你的反馈,最新的EVT工程关于该问题已修改





只有登录才能回复,可以选择微信账号登录