base
This commit is contained in:
commit
bb6dd4881b
19 changed files with 441 additions and 0 deletions
6
src/dev/alloc.rs
Normal file
6
src/dev/alloc.rs
Normal file
|
@ -0,0 +1,6 @@
|
|||
use crate::println;
|
||||
|
||||
pub fn init() {
|
||||
println!("Initializing Allocator.");
|
||||
// TODO
|
||||
}
|
118
src/dev/console.rs
Normal file
118
src/dev/console.rs
Normal file
|
@ -0,0 +1,118 @@
|
|||
use core::fmt;
|
||||
|
||||
use lazy_static::lazy_static;
|
||||
use spin::Mutex;
|
||||
|
||||
use crate::hard::vga::{self, Vga};
|
||||
|
||||
#[macro_export]
|
||||
macro_rules! print {
|
||||
($($arg:tt)*) => ($crate::dev::console::print_args(format_args!($($arg)*)));
|
||||
}
|
||||
|
||||
#[macro_export]
|
||||
macro_rules! println {
|
||||
() => ($crate::print!("\n"));
|
||||
($($arg:tt)*) => ($crate::print!("{}\n", format_args!($($arg)*)));
|
||||
}
|
||||
|
||||
lazy_static! {
|
||||
static ref Out: Mutex<Console> = Mutex::new(Console::init());
|
||||
}
|
||||
|
||||
pub struct Console {
|
||||
cursor: Cursor,
|
||||
vga: Vga,
|
||||
}
|
||||
|
||||
impl Console {
|
||||
pub fn init() -> Self {
|
||||
let cursor = Cursor::new(vga::WIDTH, vga::HEIGHT);
|
||||
let vga = Vga;
|
||||
Self { cursor, vga }
|
||||
}
|
||||
|
||||
pub fn print_(&mut self, text: &str) {
|
||||
for c in text.chars() {
|
||||
match c {
|
||||
'\n' => self.cursor.ret(),
|
||||
'\t' => self.print_(" "),
|
||||
_ => {
|
||||
self.vga.write_at(self.cursor.pos(), c);
|
||||
self.cursor.progress();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct Cursor {
|
||||
line: usize,
|
||||
column: usize,
|
||||
width: usize,
|
||||
height: usize,
|
||||
}
|
||||
|
||||
impl Cursor {
|
||||
pub fn new(width: usize, height: usize) -> Self {
|
||||
Self {
|
||||
line: 0,
|
||||
column: 0,
|
||||
width,
|
||||
height,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pos(&self) -> (usize, usize) {
|
||||
(self.column, self.line)
|
||||
}
|
||||
|
||||
pub fn set_line(&mut self, line: usize) {
|
||||
self.line = line;
|
||||
}
|
||||
|
||||
pub fn set_col(&mut self, col: usize) {
|
||||
self.column = col;
|
||||
}
|
||||
|
||||
pub fn line(&self) -> usize {
|
||||
self.line
|
||||
}
|
||||
|
||||
pub fn col(&self) -> usize {
|
||||
self.column
|
||||
}
|
||||
|
||||
pub fn progress(&mut self) {
|
||||
self.column += 1;
|
||||
if self.column < self.width {
|
||||
return;
|
||||
}
|
||||
self.column = 0;
|
||||
self.line += 1;
|
||||
if self.line < self.height {
|
||||
return;
|
||||
}
|
||||
self.line = 0;
|
||||
}
|
||||
|
||||
pub fn ret(&mut self) {
|
||||
self.column = self.width;
|
||||
self.progress();
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Write for Console {
|
||||
fn write_str(&mut self, s: &str) -> fmt::Result {
|
||||
self.print_(s);
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_args(args: fmt::Arguments) {
|
||||
use core::fmt::Write;
|
||||
use x86_64::instructions::interrupts;
|
||||
interrupts::without_interrupts(|| {
|
||||
Out.lock().write_fmt(args).unwrap();
|
||||
});
|
||||
}
|
23
src/dev/input.rs
Normal file
23
src/dev/input.rs
Normal file
|
@ -0,0 +1,23 @@
|
|||
use lazy_static::lazy_static;
|
||||
use spin::Mutex;
|
||||
|
||||
use crate::hard::keyboard::Keyboard;
|
||||
|
||||
lazy_static! {
|
||||
static ref In: Mutex<Input> = Mutex::new(Input::init());
|
||||
}
|
||||
|
||||
pub struct Input {
|
||||
keyboard: Keyboard,
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub fn init() -> Self {
|
||||
let keyboard = Keyboard;
|
||||
Self { keyboard }
|
||||
}
|
||||
|
||||
pub fn read(out: &mut [char]) -> usize {
|
||||
0
|
||||
}
|
||||
}
|
3
src/dev/mod.rs
Normal file
3
src/dev/mod.rs
Normal file
|
@ -0,0 +1,3 @@
|
|||
pub mod alloc;
|
||||
pub mod console;
|
||||
pub mod input;
|
49
src/hard/int.rs
Normal file
49
src/hard/int.rs
Normal file
|
@ -0,0 +1,49 @@
|
|||
use lazy_static::lazy_static;
|
||||
use pic8259::ChainedPics;
|
||||
use spin::Mutex;
|
||||
use x86_64::{
|
||||
instructions::{interrupts, port::Port},
|
||||
structures::idt::{InterruptDescriptorTable, InterruptStackFrame},
|
||||
};
|
||||
|
||||
use crate::{print, println};
|
||||
|
||||
pub fn init() {
|
||||
println!("Initializing interrupt handler.");
|
||||
IDT.load();
|
||||
unsafe { PICS.lock().initialize() };
|
||||
interrupts::enable();
|
||||
}
|
||||
|
||||
const INT_OFFSET: u8 = 32;
|
||||
const INT_IDX_TIMER: u8 = 32;
|
||||
const INT_IDX_KEYBOARD: u8 = 33;
|
||||
|
||||
lazy_static! {
|
||||
static ref IDT: InterruptDescriptorTable = {
|
||||
let mut idt = InterruptDescriptorTable::new();
|
||||
let entries = idt.slice_mut(INT_OFFSET..);
|
||||
entries[(INT_IDX_TIMER - INT_OFFSET) as usize].set_handler_fn(timer_handler);
|
||||
entries[(INT_IDX_KEYBOARD - INT_OFFSET) as usize].set_handler_fn(keyboard_handler);
|
||||
idt
|
||||
};
|
||||
}
|
||||
|
||||
static PICS: Mutex<ChainedPics> = Mutex::new(unsafe { ChainedPics::new(0x20, 0x28) });
|
||||
|
||||
extern "x86-interrupt" fn keyboard_handler(_stack_frame: InterruptStackFrame) {
|
||||
let mut port = Port::new(0x60);
|
||||
let _scancode: u8 = unsafe { port.read() };
|
||||
// crate::task::keyboard::add_scancode(scancode);
|
||||
println!("keyboard got scancode");
|
||||
unsafe {
|
||||
PICS.lock().notify_end_of_interrupt(INT_IDX_KEYBOARD);
|
||||
}
|
||||
}
|
||||
|
||||
extern "x86-interrupt" fn timer_handler(_stack_frame: InterruptStackFrame) {
|
||||
print!(".");
|
||||
unsafe {
|
||||
PICS.lock().notify_end_of_interrupt(INT_IDX_TIMER);
|
||||
}
|
||||
}
|
7
src/hard/keyboard.rs
Normal file
7
src/hard/keyboard.rs
Normal file
|
@ -0,0 +1,7 @@
|
|||
pub struct Keyboard;
|
||||
|
||||
impl Keyboard {
|
||||
pub fn record(key_code: u8) {
|
||||
// todo!()
|
||||
}
|
||||
}
|
5
src/hard/mod.rs
Normal file
5
src/hard/mod.rs
Normal file
|
@ -0,0 +1,5 @@
|
|||
pub mod vga;
|
||||
|
||||
pub mod keyboard;
|
||||
|
||||
pub mod int;
|
16
src/hard/vga.rs
Normal file
16
src/hard/vga.rs
Normal file
|
@ -0,0 +1,16 @@
|
|||
pub const WIDTH: usize = 80;
|
||||
pub const HEIGHT: usize = 25;
|
||||
|
||||
pub struct Vga;
|
||||
|
||||
impl Vga {
|
||||
const BUFF: *mut u8 = 0xb8000 as _;
|
||||
pub fn write_at(&self, pos: (usize, usize), text: char) {
|
||||
let index = (pos.0 + pos.1 * WIDTH) as isize;
|
||||
let byte = text as u8;
|
||||
unsafe {
|
||||
*Vga::BUFF.offset(index * 2) = byte;
|
||||
*Vga::BUFF.offset(index * 2 + 1) = 0xb;
|
||||
}
|
||||
}
|
||||
}
|
26
src/main.rs
Normal file
26
src/main.rs
Normal file
|
@ -0,0 +1,26 @@
|
|||
#![no_std]
|
||||
#![no_main]
|
||||
#![feature(abi_x86_interrupt)]
|
||||
|
||||
mod dev;
|
||||
mod hard;
|
||||
|
||||
use core::panic::PanicInfo;
|
||||
|
||||
use dev::alloc;
|
||||
use hard::int;
|
||||
|
||||
#[no_mangle]
|
||||
pub extern "C" fn _start() -> ! {
|
||||
println!("Starting.");
|
||||
int::init();
|
||||
alloc::init();
|
||||
println!("Finished initializations.");
|
||||
loop {}
|
||||
}
|
||||
|
||||
#[panic_handler]
|
||||
fn panic(_info: &PanicInfo) -> ! {
|
||||
println!("Paniced.");
|
||||
loop {}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue