__asm void xPortPendSVHandler( void )
{
extern uxCriticalNesting;
extern pxCurrentTCB;
extern vTaskSwitchContext; PRESERVE8        //栈的8字节对齐 mrs r0, psp          //读取当前psp进程指针,存入r0
isb
/* 获取当前任务控制块 */
ldr r3, =pxCurrentTCB  //把当前任务控制块的指针给r3
ldr r2, [r3]        //把r3地址中的值给r2,r2中就存储当前的任务控制块 /* 是否使用了FPU,使用的话要手动保存s16~s31 */
tst r14, #0x10
it eq
vstmdbeq r0!, {s16-s31} /* Save the core registers. */
stmdb r0!, {r4-r11, r14} //含义::依次压栈r0 = r0 - 4,先压r14,r0 = r14(即将r14中的内容放入r0所指的内存地址)
// r0 = r0 - 4,再压r11,r0 = r11。
// r0 = r0 - 4,再压r10,r0 = r10......r0 = r0 - 4,最后压r4,r0 = r4。
// 则r0中就保存最新的栈顶指针值 /* 保存最新的栈顶指针到当前任务控制块的第一字段*/
str r0, [r2]       //把r0的值存入r2的地址,相当于*r2 = r0,[r2]中已经保存了最新的任务的控制块,经过上面的两个ldr指令,r2中已经保存最新的任务控制块的地址 stmdb sp!, {r3}      //将寄存器R3的值临时压栈,寄存器r3中仍然保存着当前任务的任务控制块,
      //而接下来要调用函数vTaskSwitchContext,防止r3的值被改写,故临时压栈 mov r0, #configMAX_SYSCALL_INTERRUPT_PRIORITY
msr basepri, r0 //关中断,进入临界区 dsb
isb
bl vTaskSwitchContext  //调用函数vTaskSwitchContext,此函数用来获取下一个要运行的任务,并将pxCurrentTCB更新为要运行的这个任务 mov r0, #
msr basepri, r0      //开中断,退出临界区 ldmia sp!, {r3} //刚刚保存的寄存器R3的值出栈,恢复寄存器R3的值。注意,经过调用函数vTaskSwitchContext,此时
//pxCurrentTCB的值已经改变了,所以读取R3所保存的地址处的数据就会发现其值改变了,成
//为了下一个要运行的任务的任务控制块。 ldr r1, [r3]
ldr r0, [r1] //获取新的运行任务的栈顶,并存到r0中去 /* 弹出内核寄存器 */
ldmia r0!, {r4-r11, r14} //含义::依次出栈 r0 = r0 + 4,先弹出r14,r0 = r14(即将r14中的内容放入r0所指的内存地址)
// r0 = r0 + 4,再弹r11,r0 = r11。
// r0 = r0 + 4,再弹r10,r0 = r10......r0 = r0 - 4,最后出r4,r0 = r4。 /*是够使用了FPU,使用了徐要手动保存s16~s31*/
tst r14, #0x10
it eq
vldmiaeq r0!, {s16-s31} msr psp, r0 //更新进程栈指针PSP的值
isb
#ifdef WORKAROUND_PMU_CM001 /* XMC4000 specific errata *///这块暂时不用管
#if WORKAROUND_PMU_CM001 == 1
push { r14 }
pop { pc }
nop
#endif
#endif bx r14 //执行此行代码以后硬件自动恢复寄存器R0~R3、R12、LR、PC和xPSR的值,确定异常返回以后应该进入处理器模式还是进程模式,使用主栈指针(MSP)还是进程栈指针(PSP)。
        很明显这里会进入进程模式,并且使用进程栈指针(PSP), 寄存器PC值会被恢复为即将运行的任务的任务函数,新的任务开始运行!至此,任务切换成功。
}

freeertos中关于PendSV中断服务函数的解析的更多相关文章

  1. 探究为什么FreeRTOS 有些API不能在中断服务函数中调用,转而需要调用带ISR的版本

    用了好久的FreeRTOS以前只是知道,如果在中断服务程序中调用某一些FreeRTOS的API函数时需要注意,如果有ISR版本的一定要调用末尾带ISR的函数,并且中断服务程序要调用freeRTOS的A ...

  2. 在中断服务函数中使用FreeRTOS系统延时函数vTaskDelay导致看门狗复位的情况

    @2019-04-09 [问题] 控制程序工作一段时间异常重启 [分析] 经定位分析重启原因为看门狗复位导致 [解决] 经排查发现在中断服务函数中使用了FreeRTOS的系统时延函数vTaskDela ...

  3. request_irq() | 注册中断服务函数【转】

    本文转载自:http://blog.csdn.net/wealoong/article/details/7566546#t0 参考  : ARM Linux 中断机制分析.pdf linux-2.6. ...

  4. STM32是如何进入中断服务函数xxx_IRQHandler的

    今天在看stm32的中断,一时间不理解stm32主函数是如何进入中断函数的,按C编程的理解,会有个特定的入口之类的,但是看demo过程中没有发现入口. 以串口中断服务函数void USART1_IRQ ...

  5. (C/C++学习)5.C++中的虚继承-虚函数-多态解析

    说明:在C++学习的过程中,虚继承-虚函数经常是初学者容易产生误解的两个概念,它们与C++中多态形成的关系,也是很多初学者经常产生困惑的地方,这篇文章将依次分别对三者进行解析,并讲述其之间的联系与不同 ...

  6. stm32中断服务函数

    你打开stm32的启动文件,例如startup_stm32f10x_hd.s 里面有很多中断跳转的入口.用白话说就是固件库帮你写好了发生什么中断时跳转到哪里,这些名字是一个函数名,你要把这些函数写出来 ...

  7. request_irq() | 注册中断服务

    一.中断注册方法 在linux内核中用于申请中断的函数是request_irq(),函数原型在Kernel/irq/manage.c中定义: int request_irq(unsigned int ...

  8. 函数可重入问题reentrant functions(函数执行过程中可以被中断,允许多个副本)

    最近经常听到这个名词,以前也听到过,不过接触更多的是“线程安全问题”,而且本人也一直理解的是两个名字的含义是一样的.今天仔细总结一下这个名词相关的概念. 引用博文:可重入函数和不可重入函数 (http ...

  9. AngularJS 中的Promise --- $q服务详解

    先说说什么是Promise,什么是$q吧.Promise是一种异步处理模式,有很多的实现方式,比如著名的Kris Kwal's Q还有JQuery的Deffered. 什么是Promise 以前了解过 ...

随机推荐

  1. [leetcode_easy]558. Quad Tree Intersection

    problem 558. Quad Tree Intersection re 1. Leetcode_easy_558. Quad Tree Intersection; 2. Grandyang; e ...

  2. 使用sproto buff 的陷阱

    当sproto协议包中的数组元素,长度为0时,会出现接收异常.在没有调试断点的情况下,会停止接收其它协议.

  3. FFMPEG 常用命令行

    目录 1. 分离音视频 2. 解复用 3. 视频转码 4. 视频封装 5. 视频剪切 6. 视频录制 7.叠加水印 8.将MP3转换为PCM数据 9. 推送RTP流.接收RTP流并存为ts文件 10. ...

  4. Ultimate Guide to Line For Business (May 2019)

    Ultimate Guide to Line For Business (May 2019) By Iaroslav Kudritskiy February 4, 2019 No Comments I ...

  5. 在Ubuntu上安装Intellij IDEA并创建桌面快捷方式

    环境信息 版本号 Ubuntu 18.04 LTS Intellij IDEA 2019.1.3 1.首先从官网获取安装包 官方下载地址传送门 然后我就在下载目录下得到了tar.gz的包 2.接下来开 ...

  6. LeetCode刷题1——只出现一次的数字

    一.题目要求 二.题目背景 位运算:或,异或,与,移位 三.解题思路 (1)要求算法时间复杂度是线性的,O(n),想到的是先将列表排序,排序后相同的数值两两之间前后相邻,进行偶数次循环,判断两两数值是 ...

  7. eNSP——利用单臂路由实现VLAN间路由

    原理: 以太网中,通常会使用VLAN技术隔离二层广播域来减少广播的影响,并增强网络的安全性和可管理性.其缺点是同时也严格地隔离了不同VLAN之间的任何二层流量,使分属于不同VLAN的用户不能直接互相通 ...

  8. 2019牛客多校赛第一场 补题 I题

    I题  Points Division 题意: 给你n个点,每个点有坐标(xi,yi)和属性(ai,bi),将点集划分为两个集合, 任意 A 集合的点 i 和 B 集合点 j, 不允许 xi > ...

  9. SQL SERVER YEAR函数

    定义: YEAR函数返回指定日期的年的部分 语法: YEAR(date) 参数: ①date参数是合法的日期表达式. 返回值: int型数据 例:  声明:本文是本人查阅网上及书籍等各种资料,再加上自 ...

  10. Hadoop环境搭建过程中遇到的问题以及解决方法

    1.启动hadoop之前,ssh免密登录slave主机正常,使用命令start-all.sh启动hadoop时,需要输入slave主机的密码,说明ssh文件权限有问题,需要执行以下操作: 1)进入.s ...