freertos 源码详解六 任务的切换

本文详细介绍了FreeRTOS中任务切换的过程,包括在PenSV中断服务函数中的具体步骤,如设置 PendSV 异常、任务堆栈的保存与恢复、中断的开启与关闭,以及在vTaskSwitchContext函数中的任务选择逻辑。通过这些步骤,理解了FreeRTOS如何在不同任务间进行上下文切换。
摘要由CSDN通过智能技术生成

PenSV异常

1、任务切换的具体过程在PenSV中断服务函数里
2、ICSR寄存器bit28置1,则引起PenSV中断

#define portYIELD()
{
/* Set a PendSV to request a context switch. /
portNVIC_INT_CTRL_REG = portNVIC_PENDSVSET_BIT;

/
Barriers are normally not required but do ensure the code is completely
within the specified behaviour for the architecture. */
__dsb( portSY_FULL_READ_WRITE );
__isb( portSY_FULL_READ_WRITE );
}

#define portNVIC_PENDSVSET_BIT ( 1UL << 28UL )

在这里插入图片描述

3、任务切换场合:
1.执行系统调用,如:taskYIELD() vTaskDelay->portYIELD_WITHIN_API();
2.systick中断服务函数里:
SysTick_Handler->xPortSysTickHandler->portNVIC_INT_CTRL_REG = portNVIC_PENDSVSET_BIT;

PendSV_Handler
FREERTOS_CONFIG_H中
#define xPortPendSVHandler PendSV_Handler

__asm void xPortPendSVHandler( void )
{
extern uxCriticalNesting;
extern pxCurrentTCB;
extern vTaskSwitchContext;

PRESERVE8

mrs r0, psp
isb
/* Get the location of the current TCB. */
ldr	r3, =pxCurrentTCB
ldr	r2, [r3]

/* Is the task using the FPU context?  If so, push high vfp registers. */
tst r14, #0x10
it eq
vstmdbeq r0!, {s16-s31}

/* Save the core registers. */
stmdb r0!, {r4-r11, r14}

/* Save the new top of stack into the first member of the TCB. */
str r0, [r2]

stmdb sp!, {r3}
mov r0, #configMAX_SYSCALL_INTERRUPT_PRIORITY
msr basepri, r0
dsb
isb
bl vTaskSwitchContext
mov r0, #0
msr basepri, r0
ldmia sp!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值