Приоритет прерывания пользователя NVIC - PullRequest
0 голосов
/ 22 мая 2018

Я использую FreeRTOX V9.0.0 на Cortex M3 (Silicon Labs EFM32GG380F1024).Я получаю ошибку подтверждения при использовании TaskResumeFromISR через обработчик GPIO Irq.

Здесь происходит сбой подтверждения в port.c (GCC ARM CM3) в функции "void vPortValidateInterruptPriority (void)" on line "configASSERT (ucCurrentPriority)> = ucMaxSysCallPriority); "Значения: ucCurrentPriority равно 0, а ucMaxSysCallPriority равно 160.

// NVIC CORTEX M3
#define configPRIO_BITS 3

// FreeRTOS Config
#define configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY ( 0x05 )
#define configKERNEL_INTERRUPT_PRIORITY ( configLIBRARY_LOWEST_INTERRUPT_PRIORITY << (8 - configPRIO_BITS) )
#define configMAX_SYSCALL_INTERRUPT_PRIORITY ( configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY << (8 - configPRIO_BITS) )

// port.c
ucMaxSysCallPriority = configMAX_SYSCALL_INTERRUPT_PRIORITY & ucMaxPriorityValue; // ( ( 0x05 ) << (8 - ( 3 )) ) & 224 = 160

В коде пользователя, когда я читаю приоритет прерывания (где я в настоящее время использую значение по умолчанию "0"), я получаю все приоритеты прерываний, равные нулю, кроме2, которые установлены ядром (PendSV и Systick), равны 7.

// user code
prio = hal::nvic::getPriority(NonMaskableInt_IRQn); // =0
prio = hal::nvic::getPriority(HardFault_IRQn); // =0
prio = hal::nvic::getPriority(MemoryManagement_IRQn); // =0
prio = hal::nvic::getPriority(BusFault_IRQn); // =0
prio = hal::nvic::getPriority(UsageFault_IRQn); // =0
prio = hal::nvic::getPriority(SVCall_IRQn); // =0
prio = hal::nvic::getPriority(DebugMonitor_IRQn); // =0
prio = hal::nvic::getPriority(PendSV_IRQn); // =7
prio = hal::nvic::getPriority(SysTick_IRQn); // =7
prio = hal::nvic::getPriority(GPIO_EVEN_IRQn); // =0
prio = hal::nvic::getPriority(GPIO_ODD_IRQn); // =0
prio = hal::nvic::getPriority(USART1_RX_IRQn); // =0
prio = hal::nvic::getPriority(USART1_TX_IRQn); // =0
prio = hal::nvic::getPriority(LETIMER0_IRQn); // =0
prio = hal::nvic::getPriority(RTC_IRQn); // =0
prio = hal::nvic::getPriority(BURTC_IRQn); // =0

Как только я определяю приоритет прерывания 7 или выше, у меня больше нет проблем.

Когда я теперь определяю каждый приоритет для каждого прерывания, какие значения я могу использовать (где ниже - более высокий приоритет, и я должен быть больше 7, так как мои прерывания должны иметь более низкое значение prio, чем ядро).

Так же я долженначать с 8 и идти до где ??

Спасибо

1 Ответ

0 голосов
/ 23 мая 2018

Чем ниже номер приоритета прерывания, тем выше фактический приоритет.Таким образом, 0 является наивысшим приоритетом.

Я думаю, что в EFM32GG есть только 3 бита приоритета, поэтому доступны приоритеты от 0 до 7. (При наличии 4 битов приоритета доступные приоритеты от 0 до 15).

Эти приоритетные биты смещены влево в верхние биты.Поэтому доступны следующие приоритеты:

  • 0 << 5 (0) - Высший. </li>
  • 1 << 5 (32) </li>
  • 2 << 5 (64) </li>
  • 3 << 5 (96) </li>
  • 4 << 5 (128) </li>
  • 5 << 5 (160) </li>
  • 6 << 5(192) </li>
  • 7 << 5 (224) - самый низкий </li>

Иногда 5 неиспользуемых битов дополняются нулями.Так, например, 224 имеет тот же приоритет, что и 255, так как младшие 5 битов не влияют на работу обработчика (однако они влияют на утверждения).

Вы не можете выполнять вызовы FreeRTOS API из прерываний, которые имеютболее высокий приоритет, чем configMAX_SYSCALL_INTERRUPT_PRIORITY.Однако вы можете изменить это значение в соответствии со своими потребностями.

...