sylveos

Toy Operating System
Log | Files | Refs

commit 9f3a50f47df68a52adf217b63253305298d91460
parent ad80f6ddfb0d3eb655413a166fa15fab1b19d1f8
Author: Sylvia Ivory <git@sivory.net>
Date:   Tue, 20 Jan 2026 20:28:28 -0800

Improve kmain

Diffstat:
Mbuild.zig | 3+--
Mfake-pi/root.zig | 4----
Mlinker.ld | 25++++++++++++++-----------
Mpi/root.zig | 1-
Msrc/main.zig | 4+++-
Msrc/root.zig | 47+++++++++++++++++++++++++++++++++++++++++------
Dstart.s | 13-------------
7 files changed, 59 insertions(+), 38 deletions(-)

diff --git a/build.zig b/build.zig @@ -68,14 +68,13 @@ fn add_exe_real(exe_name: []const u8, path: std.Build.LazyPath, b: *std.Build) ! const boot = b.createModule(.{ .root_source_file = path, .target = b.resolveTargetQuery(target), - .optimize = .ReleaseSmall, + .optimize = .ReleaseSafe, .unwind_tables = .none, .single_threaded = true, .error_tracing = false, .link_libc = false, .no_builtin = true, }); - boot.addAssemblyFile(b.path("start.s")); boot.addImport("pi", pi); const exe = b.addExecutable(.{ diff --git a/fake-pi/root.zig b/fake-pi/root.zig @@ -75,10 +75,6 @@ export fn put_u32(address: *u32, value: u32) void { } } -// TODO; these should not be here ideally as they only relate to test-runner -// but there is a chance we mess up stdout if we don't have it here... -export fn nop() void {} - export fn delay_cycles(cycles: u32) void { trace("delaying {} cycles\n", .{cycles}); } diff --git a/linker.ld b/linker.ld @@ -1,40 +1,43 @@ -/* - * this is a trivial "linker script" given to the linker - * and is used to control how the program is linked together. - * - * the main important thing for us is that we want the program - * to be linked starting at 0x8000. the reason: by default the - * pi-install bootloader will copy the program it receives - * to address 0x8000 and jump to it. - */ +OUTPUT_ARCH(arm) ENTRY(_start) SECTIONS { /* link the code first at 0x8000. */ .text 0x8000 : { + __code_start__ = .; + KEEP(*(.kmain)) *(.text*) + __code_end__ = .; . = ALIGN(8); } /* read-only data */ .rodata : { + . = ALIGN(4); *(.rodata*) - . = ALIGN(8); } /* rw data */ .data : { + __data_start__ = .; *(.data*) . = ALIGN(8); + __data_end__ = .; } /* 0 data */ .bss : { + . = ALIGN(4); + __bss_start__ = .; *(.bss*) + *(COMMON) . = ALIGN(8); + __bss_end__ = .; } - /* discard debug info so the .lists are smaller */ + . = ALIGN(16); + __heap_start__ = .; + /DISCARD/ : { *(.debug*) } /DISCARD/ : { *(.comment*) } /DISCARD/ : { *(*.attributes*) } diff --git a/pi/root.zig b/pi/root.zig @@ -1,5 +1,4 @@ pub const mem = @import("./mem.zig"); -pub extern fn nop() void; pub inline fn cycle_counter_init() void { const in: u32 = 1; diff --git a/src/main.zig b/src/main.zig @@ -1 +1,3 @@ -pub fn main() !void {} +pub fn main() !void { + return error.Oops; +} diff --git a/src/root.zig b/src/root.zig @@ -1,15 +1,50 @@ const std = @import("std"); const uart = @import("devices/mini-uart.zig"); -const fake_main = @import("main.zig").main; +const user_main = @import("main.zig").main; -export fn abort() noreturn { - @branchHint(.cold); - while (true) {} +extern const __bss_start__: usize; +extern const __bss_end__: usize; + +fn zero_bss() void { + for (__bss_start__..__bss_end__) |b| { + // Force a write + const ptr: *volatile u8 = @ptrFromInt(b); + ptr.* = 0; + } +} + +noinline fn kmain() void { + zero_bss(); + + uart.initialize(115200, .Gpio14, .Gpio15) catch {}; + + user_main() catch |e| { + if (uart.is_initialized()) { + var buffer: [1024]u8 = undefined; + const slice = std.fmt.bufPrint(&buffer, "main: {t}\n", .{e}) catch { + uart.write_slice("failed to print error\n"); + abort(); + }; + uart.write_slice(slice); + } + }; +} + +export fn _start() linksection(".kmain") callconv(.naked) noreturn { + asm volatile ( + \\ mov sp, 0x800000 + \\ bl %[kmain:P] + \\ bl %[abort:P] + : + : [kmain] "X" (&kmain), + [abort] "X" (&abort), + ); } -pub export fn kmain() void { - _ = fake_main() catch {}; +noinline fn abort() noreturn { + @branchHint(.cold); + while (true) {} } fn panic_handler(msg: []const u8, trace_addr: ?usize) noreturn { diff --git a/start.s b/start.s @@ -1,13 +0,0 @@ -.global _start -.type _start, function -.align 8 -_start: - mov sp, 0x800000 - bl kmain - bl abort - -.global nop -.type nop, function -.align 8 -nop: - bx lr