vTaskNotifyGiveFromISR源码分析
2021/11/18 22:14:06
本文主要是介绍vTaskNotifyGiveFromISR源码分析,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
以STM32平台为例,在STM32中数值优先级越低,逻辑优先级越高。
void vTaskNotifyGiveFromISR( TaskHandle_t xTaskToNotify, BaseType_t *pxHigherPriorityTaskWoken ) { TCB_t * pxTCB; uint8_t ucOriginalNotifyState; UBaseType_t uxSavedInterruptStatus; configASSERT( xTaskToNotify ); (1) /* RTOS ports that support interrupt nesting have the concept of a maximum system call (or maximum API call) interrupt priority. Interrupts that are above the maximum system call priority are keep permanently enabled, even when the RTOS kernel is in a critical section, but cannot make any calls to FreeRTOS API functions. If configASSERT() is defined in FreeRTOSConfig.h then portASSERT_IF_INTERRUPT_PRIORITY_INVALID() will result in an assertion failure if a FreeRTOS API function is called from an interrupt that has been assigned a priority above the configured maximum system call priority. Only FreeRTOS functions that end in FromISR can be called from interrupts that have been assigned a priority at or (logically) below the maximum system call interrupt priority. FreeRTOS maintains a separate interrupt safe API to ensure interrupt entry is as fast and as simple as possible. More information (albeit Cortex-M specific) is provided on the following link: http://www.freertos.org/RTOS-Cortex-M3-M4.html */ portASSERT_IF_INTERRUPT_PRIORITY_INVALID(); (2) pxTCB = ( TCB_t * ) xTaskToNotify; uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR(); (3) { ucOriginalNotifyState = pxTCB->ucNotifyState; (4) pxTCB->ucNotifyState = taskNOTIFICATION_RECEIVED; (5) /* 'Giving' is equivalent to incrementing a count in a counting semaphore. */ ( pxTCB->ulNotifiedValue )++;/*任务通知值+1*/ traceTASK_NOTIFY_GIVE_FROM_ISR(); /* 如果任务在阻塞等待通知 */ if( ucOriginalNotifyState == taskWAITING_NOTIFICATION ) { /* 该任务不应该出现在事件列表中,如果在则触发断言. */ configASSERT( listLIST_ITEM_CONTAINER( &( pxTCB->xEventListItem ) ) == NULL ); /* 如果任务调度器运行中 */ if( uxSchedulerSuspended == ( UBaseType_t ) pdFALSE ) { /*唤醒任务,将任务从阻塞列表中移除,添加到就绪列表中*/ ( void ) uxListRemove( &( pxTCB->xStateListItem ) ); prvAddTaskToReadyList( pxTCB ); } else { /* 调度器处于挂起状态,中断依然正常发生,但是不能直接操作就绪列表 将任务加入到就绪挂起列表,任务调度恢复后会移动到就绪列表 */ vListInsertEnd( &( xPendingReadyList ), &( pxTCB->xEventListItem ) ); } /*如果刚刚唤醒的任务优先级比当前任务高,则设置上下文切换标识,等退出函数后手动切换上下文, 或者在系统节拍中断服务程序中自动切换上下文*/ if( pxTCB->uxPriority > pxCurrentTCB->uxPriority ) { /* 设置返回参数,表示需要任务切换,在退出中断前进行任务切换. */ if( pxHigherPriorityTaskWoken != NULL ) { *pxHigherPriorityTaskWoken = pdTRUE; } else { /* 设置自动切换标志. */ xYieldPending = pdTRUE; } } else { mtCOVERAGE_TEST_MARKER(); } } } portCLEAR_INTERRUPT_MASK_FROM_ISR( uxSavedInterruptStatus ); }
(1) 断言机制,如果 xTaskToNotify
为NULL,那么程序无法向后面运行
(2)
默认情况下源码定义的优先级如下
LIBRARY_LOWEST_INTERRUPT_PRIORITY 15
LIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY 5
如果一个中断的数值优先级小于5,那么他将被永久启用,即使是处于RTOS的临界区,并且该中断不能调用任何FreeRTOS的 API函数,否者将触发断言(如果启用了断言)。如果中断数值优先级处于5~15之间(包括等于),那么它能并且只能调用以FromISR 结尾的 FreeRTOS API函数。中断要尽可能简单。
(3) 关中断,中断数值优先级大于等于LIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY
的都将被屏蔽。
(4) 保存一份任务通知的原始状态,看看任务是否在等待通知,方便在发送通知后恢复任务。
(5)设置当前任务通知的状态为taskNOTIFICATION_RECEIVED
这篇关于vTaskNotifyGiveFromISR源码分析的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2024-11-13怎么通过 JavaScript 或其他编程语言来实现监听屏幕高度变化功能?-icode9专业技术文章分享
- 2024-11-12聊聊我们那些年用过的表达式引擎组件
- 2024-11-12让项目数据更有说服力:五款必备数据可视化管理工具推荐
- 2024-11-12人到一定年纪,要学会远离多巴胺
- 2024-11-12解读:精益生产管理的目的是什么?如何操作?
- 2024-11-12Sku预研作业
- 2024-11-12文心一言API密钥:分步申请指南
- 2024-11-12初学者指南:轻松掌握后台交互
- 2024-11-12从零开始学习:封装基础知识详解
- 2024-11-12JSON对象入门教程:轻松掌握基础用法