@@ -579,15 +579,29 @@ void unvic_init(void)
579
579
/* Verify that the priority bits read at runtime are realistic. */
580
580
assert (g_nvic_prio_bits > 0 && g_nvic_prio_bits <= 8 );
581
581
582
- /* check that minimum priority is still in the range of possible priority
583
- * levels */
582
+ /* Check that minimum priority is still in the range of possible priority
583
+ * levels. */
584
584
assert (__UVISOR_NVIC_MIN_PRIORITY < UVISOR_VIRQ_MAX_PRIORITY );
585
585
586
- /* by setting the priority group to 0 we make sure that all priority levels
586
+ /* Set the priority of each exception. SVC is lower priority than
587
+ * MemManage, BusFault, and UsageFault, so that we can recover from
588
+ * stacking MemManage faults more simply. */
589
+ static const uint32_t priority_0 = __UVISOR_NVIC_MIN_PRIORITY - 2 ;
590
+ static const uint32_t priority_1 = __UVISOR_NVIC_MIN_PRIORITY - 1 ;
591
+ assert (priority_0 < __UVISOR_NVIC_MIN_PRIORITY );
592
+ assert (priority_1 < __UVISOR_NVIC_MIN_PRIORITY );
593
+ NVIC_SetPriority (MemoryManagement_IRQn , priority_0 );
594
+ NVIC_SetPriority (BusFault_IRQn , priority_0 );
595
+ NVIC_SetPriority (UsageFault_IRQn , priority_0 );
596
+ NVIC_SetPriority (SVCall_IRQn , priority_1 );
597
+ NVIC_SetPriority (DebugMonitor_IRQn , __UVISOR_NVIC_MIN_PRIORITY );
598
+ NVIC_SetPriority (PendSV_IRQn , UVISOR_VIRQ_MAX_PRIORITY );
599
+ NVIC_SetPriority (SysTick_IRQn , UVISOR_VIRQ_MAX_PRIORITY );
600
+
601
+ /* By setting the priority group to 0 we make sure that all priority levels
587
602
* are available for pre-emption and that interrupts with the same priority
588
603
* level occurring at the same time are served in the default way, that is,
589
- * by IRQ number
590
- * for example, IRQ 0 has precedence over IRQ 1 if both have the same
591
- * priority level */
604
+ * by IRQ number. For example, IRQ 0 has precedence over IRQ 1 if both have
605
+ * the same priority level. */
592
606
NVIC_SetPriorityGrouping (0 );
593
607
}
0 commit comments