Landin library reference discuss source

compiler/tests/fixtures/runtime/library-platform-riscv/main.ldn

1--  platform/riscv's critical section, nested, on rv32: masking clears
2--  mstatus.MIE, a nested mask returns it already clear, and restoring in
3--  reverse order gives back exactly the state the program started with,
4--  whether reset left interrupts enabled or not.  The module declares
5--  nothing on the other targets (D687), so the program imports it
6--  everywhere and calls it from the rv32 arm.
7import platform/riscv
8
9fixed if compiler.arch == rv32 then
10    nested_masks_restore: () -> (ok: bool) =
11        before: u32 = riscv.interrupt_mask()
12        outer: u32 = riscv.disable_interrupts()
13        inner: u32 = riscv.disable_interrupts()
14        masked: u32 = riscv.interrupt_mask()
15        riscv.compiler_barrier()
16        riscv.restore_interrupts(inner)
17        still: u32 = riscv.interrupt_mask()
18        riscv.restore_interrupts(outer)
19        after: u32 = riscv.interrupt_mask()
20        riscv.device_barrier()
21        riscv.completion_barrier()
22        ok = outer == before and inner == 0 and masked == 0 and still == 0
23             and after == before
24    end nested_masks_restore
25else
26    nested_masks_restore: () -> (ok: bool) =
27        ok = true
28    end nested_masks_restore
29end if
30
31public main: () -> (code: i32) =
32    code = 1
33    if nested_masks_restore() then
34        code = 42
35    end if
36end main