Skip to content

Commit c1a462e

Browse files
dcpleungnashif
authored andcommitted
xtensa: mmu: bail on semantic triple faults
There actually is no triple faults on Xtensa. Once PS.EXCM is set, it keeps going through double exception vector for any new exceptions. However, our exception code needs to unmask PS.EXCM to enable register window operations. So after that, any new exceptions will go through the kernel or user vectors depending on PS.UM. If there is continuous faults, it may keep ping-ponging between double and kernel/user exception vectors that may never get resolved. Since we stash DEPC during double exception, and the stashed one is only cleared once the double exception has been processed, we can use the stashed DEPC value to detect if the next exception could be considered a triple fault. If such a case exists, simply jump to an infinite loop, or quit the simulator, or invoke debugger. Signed-off-by: Daniel Leung <[email protected]>
1 parent d344a6b commit c1a462e

File tree

2 files changed

+30
-2
lines changed

2 files changed

+30
-2
lines changed

arch/xtensa/core/xtensa_asm2_util.S

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -501,7 +501,9 @@ _DoubleExceptionVector:
501501
rsr a0, ZSR_DBLEXC
502502

503503
j _Level1Vector
504-
#else
504+
505+
_TripleFault:
506+
#endif /* CONFIG_XTENSA_MMU */
505507

506508
#if XCHAL_HAVE_DEBUG && defined(CONFIG_XTENSA_BREAK_ON_UNRECOVERABLE_EXCEPTIONS)
507509
/* Signals an unhandled double exception, and unrecoverable exceptions.
@@ -521,7 +523,6 @@ _DoubleExceptionVector:
521523
#endif
522524
1:
523525
j 1b
524-
#endif /* CONFIG_XTENSA_MMU */
525526

526527
#ifdef CONFIG_XTENSA_MMU
527528
_handle_tlb_miss_dblexc:

arch/xtensa/include/xtensa_asm2_s.h

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -622,6 +622,33 @@ _Level\LVL\()Vector:
622622

623623
esync
624624

625+
rsr a0, ZSR_DEPC_SAVE
626+
beqz a0, _not_triple_fault
627+
628+
/* If stashed DEPC is not zero, we have started servicing
629+
* a double exception and yet we are here because there is
630+
* another exception (through user/kernel if PS.EXCM is
631+
* cleared, or through double if PS.EXCM is set). This can
632+
* be considered triple fault. Although there is no triple
633+
* faults on Xtensa. Once PS.EXCM is set, it keeps going
634+
* through double exception vector for any new exceptions.
635+
* However, our exception code needs to unmask PS.EXCM to
636+
* enable register window operations. So after that, any
637+
* new exceptions will go through the kernel or user vectors
638+
* depending on PS.UM. If there is continuous faults, it may
639+
* keep ping-ponging between double and kernel/user exception
640+
* vectors that may never get resolved. Since we stash DEPC
641+
* during double exception, and the stashed one is only cleared
642+
* once the double exception has been processed, we can use
643+
* the stashed DEPC value to detect if the next exception could
644+
* be considered a triple fault. If such a case exists, simply
645+
* jump to an infinite loop, or quit the simulator, or invoke
646+
* debugger.
647+
*/
648+
rsr a0, ZSR_EXCCAUSE_SAVE
649+
j _TripleFault
650+
651+
_not_triple_fault:
625652
rsr.exccause a0
626653

627654
xsr a0, ZSR_EXCCAUSE_SAVE

0 commit comments

Comments
 (0)