code wiki / (root) / nx_emu_rv64_test.nx

nx_emu_rv64_test.nx source

↩ module page · 68 lines · 2771 B

1// nx_emu_rv64_test.nx -- prove the sovereign RV64 interpreter runs real 2// RV64 machine code (no qemu). Hand-encodes RV64I words (verified vs the 3// RISC-V ISA manual; the 0x02a00513 word is the same one asm_enc.nx's KAT 4// uses) and asserts the emulated exit code. 5// 6// expect_exit: 0 7// license_tier: ORIGINAL 8 9import "nx_emu_rv64.nx" 10import "nx_syscalls_x86_64.nx" 11 12func emu_put_w(code: *u8, off: i64, w: i64) -> i64 { 13 code[off] = w & 0xff 14 code[off + 1] = (w >> 8) & 0xff 15 code[off + 2] = (w >> 16) & 0xff 16 code[off + 3] = (w >> 24) & 0xff 17 return off + 4 18} 19 20func main() -> i64 { 21 // Program 1: li a0,40 ; li t0,2 ; add a0,a0,t0 ; li a7,93 ; ecall -> exit 42 22 let code: *u8 = sys_mmap(64) 23 var o: i64 = 0 24 o = emu_put_w(code, o, 0x02800513) // addi a0,zero,40 (li a0,40) 25 o = emu_put_w(code, o, 0x00200293) // addi t0,zero,2 (li t0,2; t0=x5) 26 o = emu_put_w(code, o, 0x00550533) // add a0,a0,t0 -> 42 27 o = emu_put_w(code, o, 0x05d00893) // addi a7,zero,93 (li a7,93 = exit) 28 o = emu_put_w(code, o, 0x00000073) // ecall 29 let r: i64 = emu_rv64_run(code, o) 30 if r != 42 { return 1 } 31 32 // Program 2: the canonical KAT word addi a0,zero,42 (0x02a00513) ; exit 33 let c2: *u8 = sys_mmap(64) 34 var o2: i64 = 0 35 o2 = emu_put_w(c2, o2, 0x02a00513) // addi a0,zero,42 36 o2 = emu_put_w(c2, o2, 0x05d00893) // li a7,93 37 o2 = emu_put_w(c2, o2, 0x00000073) // ecall 38 let r2: i64 = emu_rv64_run(c2, o2) 39 if r2 != 42 { return 2 } 40 41 // Program 3: sub path -- li a0,50 ; li t0,8 ; sub a0,a0,t0 -> 42 42 let c3: *u8 = sys_mmap(64) 43 var o3: i64 = 0 44 o3 = emu_put_w(c3, o3, 0x03200513) // addi a0,zero,50 45 o3 = emu_put_w(c3, o3, 0x00800293) // addi t0,zero,8 46 o3 = emu_put_w(c3, o3, 0x40550533) // sub a0,a0,t0 (funct7=0x20) -> 42 47 o3 = emu_put_w(c3, o3, 0x05d00893) // li a7,93 48 o3 = emu_put_w(c3, o3, 0x00000073) // ecall 49 let r3: i64 = emu_rv64_run(c3, o3) 50 if r3 != 42 { return 3 } 51 52 // Program 4: REAL control flow -- sum 0..9 via a bne back-branch loop -> 45. 53 // Words are exactly what riscv64-as emits (oracle-verified); qemu exits 45. 54 let c4: *u8 = sys_mmap(64) 55 var o4: i64 = 0 56 o4 = emu_put_w(c4, o4, 0x00000513) // li a0,0 57 o4 = emu_put_w(c4, o4, 0x00000293) // li t0,0 58 o4 = emu_put_w(c4, o4, 0x00a00313) // li t1,10 59 o4 = emu_put_w(c4, o4, 0x00550533) // loop: add a0,a0,t0 60 o4 = emu_put_w(c4, o4, 0x00128293) // addi t0,t0,1 61 o4 = emu_put_w(c4, o4, 0xfe629ce3) // bne t0,t1,loop (offset -8) 62 o4 = emu_put_w(c4, o4, 0x05d00893) // li a7,93 63 o4 = emu_put_w(c4, o4, 0x00000073) // ecall 64 let r4: i64 = emu_rv64_run(c4, o4) 65 if r4 != 45 { return 4 } 66 67 return 0 68}