sylveos

Toy Operating System
Log | Files | Refs

root.zig (4114B)


      1 const std = @import("std");
      2 
      3 pub const Coroutine = @import("coroutine.zig");
      4 pub const PSR = @import("./psr.zig").PSR;
      5 
      6 pub const interrupts = @import("./interrupts.zig");
      7 pub const switching = @import("./switching.zig");
      8 pub const register = @import("./register.zig");
      9 pub const journal = @import("./journal.zig");
     10 pub const procmap = @import("./procmap.zig");
     11 pub const faults = @import("./faults.zig");
     12 pub const thread = @import("./thread.zig");
     13 pub const pinned = @import("./pinned.zig");
     14 pub const system = @import("./system.zig");
     15 pub const debug = @import("./debug.zig");
     16 pub const mem = @import("./mem.zig");
     17 pub const mmu = @import("./mmu.zig");
     18 pub const pt = @import("./pt.zig");
     19 
     20 pub const devices = struct {
     21     pub const clock = @import("./devices/clock.zig");
     22     pub const gpio = @import("./devices/gpio.zig");
     23     pub const mini_uart = @import("./devices/mini-uart.zig");
     24     pub const sw_uart = @import("./devices/sw-uart.zig");
     25     pub const timer = @import("./devices/timer.zig");
     26     pub const mailbox = @import("./devices/mailbox.zig");
     27     pub const sd = @import("./devices/sd.zig");
     28     pub const spi = @import("./devices/spi.zig");
     29     pub const mini_spi = @import("./devices/mini-spi.zig");
     30     pub const nrf = @import("./devices/nrf.zig");
     31 };
     32 
     33 pub const fs = struct {
     34     pub const vfs = @import("./fs/vfs.zig");
     35     pub const fat = @import("./fs/fat.zig");
     36     pub const mbr = @import("./fs/mbr.zig");
     37     pub const FatVFS = @import("./fs/fatvfs.zig");
     38 };
     39 
     40 extern const __stack_end__: u32;
     41 extern const __int_stack_end__: u32;
     42 
     43 pub inline fn get_stack_address() u32 {
     44     return std.mem.alignForward(u32, @intFromPtr(&__stack_end__), 1024 * 1024);
     45 }
     46 pub inline fn get_interrupt_stack_address() u32 {
     47     return std.mem.alignForward(u32, @intFromPtr(&__int_stack_end__), 1024 * 1024);
     48 }
     49 
     50 pub inline fn cycle_counter_init() void {
     51     asm volatile ("MCR p15, 0, %[in], c15, c12, 0"
     52         :
     53         : [in] "r" (1),
     54     );
     55 }
     56 
     57 pub inline fn cycle_counter_read() u32 {
     58     return asm volatile ("MRC p15, 0, %[result], c15, c12, 1"
     59         : [result] "=r" (-> u32),
     60     );
     61 }
     62 
     63 pub inline fn cycle_wait_until(deadline: u32) void {
     64     while (cycle_counter_read() < deadline) {
     65         std.mem.doNotOptimizeAway(deadline);
     66     }
     67 }
     68 
     69 pub inline fn set_sp(sp: *usize) void {
     70     asm volatile ("mov sp, %[value]"
     71         :
     72         : [value] "r" (sp),
     73         : .{ .r13 = true }); // sp
     74 }
     75 
     76 pub inline fn get_sp() usize {
     77     return asm volatile ("mov %[result], sp"
     78         : [result] "=r" (-> usize),
     79     );
     80 }
     81 
     82 pub fn reboot() noreturn {
     83     // Prevent any more interrupts
     84     _ = mem.enter_critical_section();
     85 
     86     // Notify serial that we're done
     87     devices.mini_uart.write_byte_sync(0);
     88     // Flush remaining tx
     89     devices.mini_uart.flush();
     90 
     91     // Set watchdog and go into infinite loop, forcing a reboot
     92     const PM_RSTC: usize = 0x2010001c;
     93     const PM_WDOG: usize = 0x20100024;
     94     const PM_PASSWORD: u32 = 0x5a000000;
     95     const PM_RSTC_WRCFG_FULL_RESET: u32 = 0x00000020;
     96 
     97     mem.put_u32_barrier(@ptrFromInt(PM_WDOG), PM_PASSWORD | 1);
     98     mem.put_u32_barrier(@ptrFromInt(PM_RSTC), PM_PASSWORD | PM_RSTC_WRCFG_FULL_RESET);
     99 
    100     while (true) {}
    101 }
    102 
    103 // pi.h
    104 export fn delay_us(us: u32) void {
    105     devices.clock.delay(us);
    106 }
    107 export fn delay_ms(ms: u32) void {
    108     devices.clock.delay_ms(ms);
    109 }
    110 export fn delay_s(s: u32) void {
    111     devices.clock.delay_s(s);
    112 }
    113 export fn gpio_set_function(pin: u8, mode: u8) void {
    114     devices.gpio.fn_sel(pin, @enumFromInt(@as(u3, @truncate(mode)))) catch {};
    115 }
    116 export fn printk_0(a0: *u8) void {
    117     const msg: [:0]u8 = @ptrCast(a0);
    118     devices.mini_uart.print("{s}\n", .{msg});
    119 }
    120 export fn printk_1(a0: *u8, a1: i32) void {
    121     const msg: [:0]u8 = @ptrCast(a0);
    122     devices.mini_uart.print("{s} {d}\n", .{ msg, a1 });
    123 }
    124 export fn printk_2(a0: *u8, a1: i32, a2: i32) void {
    125     const msg: [:0]u8 = @ptrCast(a0);
    126     devices.mini_uart.print("{s} {d} {d}\n", .{ msg, a1, a2 });
    127 }
    128 export fn printk_3(a0: *u8, a1: i32, a2: i32, a3: i32) void {
    129     const msg: [:0]u8 = @ptrCast(a0);
    130     devices.mini_uart.print("{s} {d} {d} {d}\n", .{ msg, a1, a2, a3 });
    131 }