接着以WCH沁恒微电子的赤菟V103(CH32V103)和赤菟V307(CH32V307)两款RISC-V内核单片机来详细说下针对RISC-V平台,移植实时操作系统的注意点。
今天聊下移植RTOS时RISC-V内核时单片机任务之间的切换。
了解了如何切换至第一个任务,如何实现不同任务之间的切换呢。在这之前想必对“任务优先级”,“时间片轮转”等概念有一定的了解。rt-thread正常运行也需要个定时器为其提供时钟,且任务初始化时设置了任务优先级。调度器在就绪的任务列表中寻找优先级较高的任务切换执行,当优先级相同时,调度器会按照设置的时间片大小来轮流调度线程,用时间片来约束任务的单次执行时长。不管因优先级还是时间片耗尽,从当前任务切换至新任务时均需要保存当前任务的上下文至当前任务的堆栈区,获取新任务的堆栈,并从新任务堆栈区恢复上下文,切换并执行。
在ARM中,系统的滴答时钟由内核定时器Systick提供,并且在pendSV中进行任务切换。类比RISC-V我们内核提供了一个64bit
Systick定时器,同时也有软中断SW_handler(其实整个切换也不一定要在某个中断中切换,只要做好上下文保存即可),需要切换时,置位其相应的pend位,即可触发进中断,实现切换。rt-thread中用了三个全局变量,用于中断切换上下文rt_interrupt_from_thread、rt_interrupt_to_thread、rt_thread_switch_interrupt_flag,前两个分别用来存储“from”线程sp指针和“to”线程的sp指针,当需要切换时,flag被函数rt_hw_context_switch_interrupt置位,并触发进软中断如图1所示。在中断中实现“from”到“to”线程的切换,并将flag清零。
图1 中断切换上下文
SW中断函数同样是一段汇编实现的代码,内容如下图2所示,其中重点代码已经给出注释,注意查看。从注释可以看出,其相较于启动第一个任务多了开头的就任务保存的过程。值得注意的是赤菟V307支持进中断后将硬件压栈临时关闭,这样在上下文切换的时候可以手动恢复我们想要的寄存器值,而当中断返回后,硬件压栈自动打开,不影响其他外设中断使用硬件压栈。而对于没有此功能的赤菟V103来说,移植操作系统时不能打开硬件压栈。
图2 软中断切换上下文过程
对于其他的RTOS也是大同小异,例如鸿蒙LiteOS_M中有个g_losTask全局变量,其是个结构体,内部为两个任务控制块类型的指针,分别为*runTask指向当前运行的任务,newTask指向要切换的新任务,腾讯的TencentOS_Tiny中亦有两个任务控制块类型的指针k_curr_task指向当前任务,*k_next_task指向下一个要切换任务。这和rt-thread中的“from”和“to”是为异曲同工之处。通过管理操作这些变量,实现任务到任务的切换。
全部0条评论
快来发表一下你的评论吧 !