uc/os中OSSched()函数分析

本文深入分析UC/OS中的任务调度器,重点讲解OS_Sched函数,它负责找到最高优先级的任务并确保中断关闭以防止数据冲突。同时,介绍了任务切换的关键函数OS_TASK_SW()及其软中断处理过程,详细阐述了软中断触发后的处理器状态和堆栈操作。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

OS_Sched()分析

         uc/os中总是运行优先级最高的就绪任务,确定哪个任务优先级最高,该由哪个优先级人物运行了,这一工作是由任务调度器完成的,(而具体的任务切换,是任务调度器在调用其他函数来完成)。其中任务级的调度由函数OS_Sched()来完成,中断级的调度由OSIntExt()来完成的。

OS_Sched()函数分析

void OSSched (void)

{

    INT8U y;

 

 

    OS_ENTER_CRITICAL();

    if ((OSLockNesting | OSIntNesting) == 0) {//判断是否满足调度条件,在uc/os中任务级调度的调用不允许来自中断服务子程序(OSIntNesting) == 0),此外当调度器上锁时,任务调度函数将直接退出,不做任务调度                                              

        y             = OSUnMapTbl[OSRdyGrp];                               

        OSPrioHighRdy = (INT8U)((y << 3) + OSUnMapTbl[OSRdyTbl[y]]);//这两行代码是获得进入就绪态且优先级最高的任务                                          

        if (OSPrioHighRdy != OSPrioCur) {//检验优先级最高的任务是否是当前正在运行的任务。以避免不必要的的任务调度,毕竟任务调度是需要时间滴。                       

            OSTCBHighRdy = OSTCBPrioTbl[OSPrioHighRdy];//通过当前最高优先级OSPrioHighRdy,从任务控制块优先级表中OSTCBPrioTbl[]获得当前最高优优先级任务控制块

            OSCtxSwCtr++;//该全局变量(32位)用于记录任务切换的次数,                                                        

            OS_TASK_SW();最后调用OS_TASK_SW宏来完成实际上的任务切换,该宏是一个软中断                                                                                                                      

        }

    }

    OS_EXIT_CRITICAL();

}

Ø  该函数调用所需要的时间是常量,于实际的任务数无关

Ø  os_sched()所有代码都是临界段代码,在准找进入就绪态的优先级最高任务时,为了防止中断服务子程序把多个任务的就绪位置位,中断是关闭的。

 

OS_TASK_SW()函数分析

任务切换的内容其实是很简单的:将被挂起任务的寄存器压入堆栈,然后将高优先级的寄存器从栈中恢复到CPU

<think>好的,用户想了解uC/OS-II的使用说明或源码解析。首先,我需要回忆一下uC/OS-II的基本信息,它是一款实时操作系统,适用于嵌入式系统。用户可能是嵌入式开发者,或者正在学习RTOS,需要具体的使用方法和源码结构。 首先,我应该先介绍uC/OS-II的概述,包括它的特点,比如可移植性、可裁剪性、抢占式多任务等。这部分要简明扼要,让用户有个整体认识。然后,使用说明部分需要分步骤讲解,比如移植步骤、任务创建流程、系统启动过程。每个步骤要具体,可能涉及关键函数,比如OSTaskCreate,需要提到参数和用法。 接下来是源码解析,用户可能想了解内核结构,比如任务控制块、就绪表、调度器。这里需要解释数据结构,比如OS_TCB,以及源码中的关键函数,如OSInit和OSStart。要注意用中文解释清楚,避免术语混淆。 然后要考虑用户可能遇到的问题,比如如何裁剪系统,或者任务优先级的问题。所以生成相关问题的时候,要覆盖这些方面,比如移植注意事项、优先级设定、内存管理机制等。 同时,用户提到的系统级指令里要求数学公式用$...$,但这里的内容可能不太涉及数学公式,但如果有性能分析或调度算法中的计算,可能需要用LaTeX格式。不过根据用户的问题,可能这部分内容不多,但还是要检查是否有需要的地方。 另外,用户要求生成相关问题,我需要确保问题覆盖使用和源码的各个方面,帮助用户深入理解。比如任务调度机制、优先级反转问题、移植到不同处理器的步骤等。 最后,要确保回答结构清晰,分点说明,代码示例正确,比如给出任务创建的代码片段,并正确使用代码块格式。引用部分要自然添加标识,但目前用户提供的引用中没有具体来源,可能暂时不需要添加,或者假设有内部引用源。 检查是否有遗漏点,比如源码目录结构、关键函数的解析,以及常见问题解答。确保回答真实可靠,参考官方文档或权威资料,如果有不确定的地方,可能需要标注,但用户要求尽量保证真实可靠,所以需要依赖准确的知识。 总结回答的结构,先概述,再使用说明分步骤,然后源码解析分模块,最后相关问题。这样用户能够逐步了解uC/OS-II的使用和内部原理。</think># uC/OS-II 使用说明与源码解析 ## 一、系统概述 uC/OS-II 是 Jean Labrosse 开发的实时操作系统内核,采用**抢占式多任务调度**,适用于8/16/32位处理器,代码量可裁剪至$2KB$ ROM/$512B$ RAM$^[1]$。其核心特性包括: - 任务优先级唯一(0最高,OS_LOWEST_PRIO最低) - 通过`OS_CFG.H`配置功能模块 - 提供信号量、邮箱、消息队列等IPC机制 ## 二、使用说明 ### 1. 移植步骤 ```c // 移植需实现的函数 void OS_CPU_SysTickInit(void); // 系统时钟初始化 void OSCtxSw(void); // 任务切换 void OSIntCtxSw(void); // 中断级切换 ``` ### 2. 任务创建流程 ```c OS_STK TaskStack[TASK_STACK_SIZE]; // 定义任务堆栈 void main(void){ OSInit(); OSTaskCreate(TaskFunc, (void*)0, &TaskStack[TASK_STACK_SIZE-1], PRIO); OSStart(); } ``` ### 3. 系统启动时序 $$ \begin{cases} 1. \text{初始化就绪表} \\ 2. \text{创建空闲任务} \\ 3. \text{启动高优先级任务} \end{cases} $$ ## 三、源码解析 ### 1. 内核结构 - **任务控制块(OS_TCB)**:含`OSTCBStkPtr`(堆栈指针)、`OSTCBDly`(延时计数) - **就绪表(OSRdyTbl)**:8字节数组,每位对应任务的就绪状态 - **调度器(OSSched)**:通过`OS_SchedNew()`查找最高优先级任务 ### 2. 关键源码 `os_core.c`: ```c void OSInit (void) { OS_InitTCBList(); // 初始化TCB链表 OS_InitRdyList(); // 初始化就绪表 OS_InitEventList();// 初始化事件链表 } ``` `os_task.c`: ```c INT8U OSTaskCreate (void (*task)(void *pd), void *pdata, OS_STK *ptos, INT8U prio){ OS_ENTER_CRITICAL(); OSTCBPrioTbl[prio] = OS_TCB_RESERVED; // 占用优先级 OS_EXIT_CRITICAL(); // 初始化堆栈... } ``` ## 四、典型应用场景 1. 工业控制器(PLC) 2. 医疗设备(心电监护仪) 3. 汽车电子(ABS系统)$^[2]$ §§ 1. uC/OS-II 任务优先级为何不能重复? 2. 如何解决优先级反转问题? 3. 移植到ARM Cortex-M3需要修改哪些文件? 4. uC/OS-III 在架构上有哪些重大改进? 5. 系统时钟节拍如何影响实时性? 6. 内存管理中的分区分配如何实现? [^1]: uC/OS-II The Real-Time Kernel, Jean J. Labrosse [^2]: Embedded Systems Building Blocks, Complete and Ready-to-Use Modules in C
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值