From 6a5c32fa6ae8ec34e3e5b44d7e5a78ded8fe729b Mon Sep 17 00:00:00 2001 From: salmonik Date: Fri, 31 Jul 2026 02:58:31 +0200 Subject: restructure: rsnix kernel + shell crate + rsdos entry point MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Architecture: rs-dos/ (workspace root, was raisernics/) ├── rsnix/ — kernel lib crate (uefi, serial, gop, ps2, interrupts, memory) ├── shell/ — shell lib crate (prompt, commands, line input) ├── rsdos/ — binary crate (efi_main, init, panic handler) └── rsboot/ — future git submodule No functional changes — boots to shell prompt identically. Version auto-pulled from Cargo.toml via env!("CARGO_PKG_VERSION"). --- src/gop.rs | 232 ------------------------------------------------------------- 1 file changed, 232 deletions(-) delete mode 100644 src/gop.rs (limited to 'src/gop.rs') diff --git a/src/gop.rs b/src/gop.rs deleted file mode 100644 index 9645bb0..0000000 --- a/src/gop.rs +++ /dev/null @@ -1,232 +0,0 @@ -/// GOP framebuffer driver — renders text via a bitmap font. -use crate::font; -use crate::uefi::{GraphicsOutputProtocol, PIXEL_BGR, PIXEL_RGB}; -use core::fmt; -use core::ptr; - -/// Framebuffer state captured before ExitBootServices. -pub struct Framebuffer { - base: *mut u8, - #[allow(dead_code)] - width: usize, - height: usize, - pitch: usize, // bytes per scan line - bytes_per_pixel: usize, - bg: u32, // packed BGRA or RGBA background colour - fg: u32, // packed foreground colour - cursor_x: usize, - cursor_y: usize, - rows: usize, - cols: usize, -} - -static mut FB: Option = None; - -/// Initialise the framebuffer from GOP. Call *before* ExitBootServices. -pub fn init(gop: &mut GraphicsOutputProtocol) { - let mode = unsafe { &*gop.mode }; - let info = unsafe { &*mode.info }; - let base = mode.framebuffer_base as *mut u8; - let width = info.horizontal_resolution as usize; - let height = info.vertical_resolution as usize; - let pitch = info.pixels_per_scan_line as usize * 4; // 32-bit pixel - let bpp = 4; - - // Pick colours based on pixel format - let (fg, bg) = match info.pixel_format { - PIXEL_BGR => (0x00_FF_FF_FFu32, 0x00_00_00_00u32), // white fg, black bg - PIXEL_RGB => (0x00_FF_FF_FFu32, 0x00_00_00_00u32), - _ => (0x00_FF_FF_FFu32, 0x00_00_00_00u32), - }; - - let rows = height / 16; - let cols = width / 8; - - let fb = Framebuffer { - base, - width, - height, - pitch, - bytes_per_pixel: bpp, - bg, - fg, - cursor_x: 0, - cursor_y: 0, - rows, - cols, - }; - - fb.clear(); - - unsafe { - FB = Some(fb); - } -} - -/// Draw a character at the current cursor position and advance. -pub fn put_char(c: char) { - let fb = unsafe { - match FB.as_mut() { - Some(f) => f, - None => return, - } - }; - - if c == '\x08' { - // Backspace - move cursor back and erase - if fb.cursor_x > 0 { - fb.cursor_x -= 1; - } else if fb.cursor_y > 0 { - fb.cursor_y -= 1; - fb.cursor_x = fb.cols - 1; - } else { - return; - } - // Draw glyph 32 (space) to erase — glyph 0 is NUL, not blank - fb.draw_glyph(32, fb.cursor_x, fb.cursor_y); - return; - } - if c == '\n' { - fb.cursor_x = 0; - fb.cursor_y += 1; - if fb.cursor_y >= fb.rows { - fb.scroll(); - } - return; - } - if c == '\r' { - fb.cursor_x = 0; - return; - } - - let idx = c as usize; - if idx >= 256 { - // Unmapped character: draw a space - fb.draw_glyph(0, fb.cursor_x, fb.cursor_y); - } else { - fb.draw_glyph(idx, fb.cursor_x, fb.cursor_y); - } - - fb.cursor_x += 1; - if fb.cursor_x >= fb.cols { - fb.cursor_x = 0; - fb.cursor_y += 1; - if fb.cursor_y >= fb.rows { - fb.scroll(); - } - } -} - -/// Write a string to the framebuffer. -pub fn write_str(s: &str) { - for c in s.chars() { - put_char(c); - } -} - -/// Clear the entire screen to background colour and reset cursor to (0, 0). -pub fn clear_screen() { - let fb = unsafe { - match FB.as_mut() { - Some(f) => f, - None => return, - } - }; - fb.clear(); - // Reset cursor back to top-left so the next prompt appears at (0, 0) - fb.cursor_x = 0; - fb.cursor_y = 0; -} - -// --------------------------------------------------------------------------- -// Framebuffer implementation -// --------------------------------------------------------------------------- -impl Framebuffer { - fn clear(&self) { - let size = self.pitch * self.height; - // Fill with background colour (32-bit writes) - let mut p = self.base; - let end = unsafe { p.add(size) }; - unsafe { - while p < end { - ptr::write_volatile(p as *mut u32, self.bg); - p = p.add(4); - } - } - } - - fn scroll(&mut self) { - // Move everything up one row (16 pixels) - let row_bytes = self.pitch * 16; - let total = self.pitch * self.height; - unsafe { - ptr::copy(self.base.add(row_bytes), self.base, total - row_bytes); - // Clear last row - let last_row = self.base.add(total - row_bytes); - for i in 0..(self.pitch * 16 / 4) { - ptr::write_volatile(last_row.add(i * 4) as *mut u32, self.bg); - } - } - self.cursor_y -= 1; - } - - fn draw_glyph(&self, glyph_idx: usize, col: usize, row: usize) { - let glyph = font::GLYPH_8X16; - let data = match glyph.get(glyph_idx) { - Some(d) => *d, - None => return, - }; - - let x = col * 8; - let y = row * 16; - - for cy in 0..16 { - let row_bits = data[cy]; - for cx in 0..8 { - if row_bits & (0x80 >> cx) != 0 { - // Set foreground pixel - let offset = (y + cy) * self.pitch + (x + cx) * self.bytes_per_pixel; - unsafe { - ptr::write_volatile(self.base.add(offset) as *mut u32, self.fg); - } - } else { - // Set background pixel - let offset = (y + cy) * self.pitch + (x + cx) * self.bytes_per_pixel; - unsafe { - ptr::write_volatile(self.base.add(offset) as *mut u32, self.bg); - } - } - } - } - } -} - -// --------------------------------------------------------------------------- -// fmt::Write wrapper -// --------------------------------------------------------------------------- -pub struct GopWriter; - -impl fmt::Write for GopWriter { - fn write_str(&mut self, s: &str) -> fmt::Result { - write_str(s); - Ok(()) - } -} - -/// Write a formatted string to the framebuffer. -#[macro_export] -macro_rules! gop_print { - ($($arg:tt)*) => {{ - use core::fmt::Write; - let _ = write!(&mut $crate::gop::GopWriter, $($arg)*); - }}; -} - -#[macro_export] -macro_rules! gop_println { - () => { $crate::gop::write_str("\n"); }; - ($($arg:tt)*) => {{ - $crate::gop_print!($($arg)*); - $crate::gop::write_str("\n"); - }}; -} -- cgit v1.2.3