https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101559
--- Comment #3 from Joël Porquet <joel.porquet at gmail dot com> --- Thanks for the quick replies and the clear explanation! I'm a little bummed because this construct enabled me to write --what I considered to be-- clean code for a bootloader. As shown below, I could temporarily change the exception vector with a label's address located further down, which corresponds to the restoration of the previous exception vector. If any operation in between fails, we just skip ahead and ignore the rest. ``` static void setup_pmp(void) { uintptr_t otvec; /* Ignore possible exception if some PMP registers are not implemented */ otvec = csr_read_write(CSR_MTVEC, &&restore_mtvec); /* Reset configuration */ csr_write(CSR_PMPCFG0, 0); /* Range for M-mode bootloader */ ... restore_mtvec: csr_write(CSR_MTVEC, otvec); } ``` This code unfortunately doesn't work because the label's address (`restore_mtvec`) is moved to the beginning of the function and it goes into an infinite loop if an exception is raised. The only other way to write this code effectively seems to be to do it fully in assembly, like they do in BBL (https://github.com/riscv/riscv-pk/blob/66d7fcb56d6a4cd4879922f184bb2274918ac3cd/bbl/bbl.c#L53), which I was trying to avoid since it felt pretty ugly :( Do you see any alternative apart from the switch to assembly code? Thanks in advance for your time.