small-projects/cpu-emulator/program.c
2025-04-12 13:24:30 -05:00

40 lines
1.5 KiB
C

// hello.c
// Minimal RISC-V Linux program without the C library.
// It uses direct system calls via the ECALL instruction.
//
// System call numbers for RISC-V Linux:
// __NR_write = 64
// __NR_exit = 93
//
// Compile this program with:
// riscv64-unknown-elf-gcc -nostdlib -static -O2 -o hello hello.c
// _start is the entry point when not using the standard C runtime.
void _start() {
// Define the message to print.
const char msg[] = "Hello, world!\n";
// --- Write "Hello, world!\n" to stdout ---
// For the write(2) system call:
// a0: file descriptor (1 for stdout)
// a1: pointer to the message
// a2: length of the message (without the null terminator)
// a7: system call number (__NR_write, which is 64)
register long a0 asm("a0") = 1; // file descriptor (stdout)
register const char *a1 asm("a1") = msg; // pointer to message
register long a2 asm("a2") = sizeof(msg) - 1; // message length
register long a7 asm("a7") = 64; // syscall number: write
asm volatile ("ecall" : : "r"(a0), "r"(a1), "r"(a2), "r"(a7));
// --- Exit the program ---
// For the exit(2) system call:
// a0: exit code (0 for success)
// a7: system call number (__NR_exit, which is 93)
register long exit_code asm("a0") = 0;
register long a7_exit asm("a7") = 93; // syscall number: exit
asm volatile ("ecall" : : "r"(exit_code), "r"(a7_exit));
// We should never reach this point.
while (1) {}
}