diff --git a/kernel-rs/Makefile b/kernel-rs/Makefile
index f0ce373c..e43fe467 100644
--- a/kernel-rs/Makefile
+++ b/kernel-rs/Makefile
@@ -10,8 +10,8 @@ endif
project := bluesnow
arch ?= x86
-NASM := nasm -f elf
-LD := ld -m elf_i386 -L ./ -n --gc-sections
+NASM := /usr/bin/nasm -f elf
+LD := /usr/bin/ld -m elf_i386 -L ./ -n --gc-sections
# QEMU := qemu-system-x86_64 -device isa-debug-exit,iobase=0xf4,iosize=0x04 -gdb tcp::$(PORTG) -enable-kvm -monitor telnet:127.0.0.1:$(PORT),server,nowait
QEMU := qemu-system-x86_64 -gdb tcp::$(PORTG) -enable-kvm -monitor telnet:127.0.0.1:$(PORT),server,nowait
@@ -34,20 +34,19 @@ MONITOR := sleep 0.5;\
kill \`ps -x | grep \"[g]db\" | cut -d \ -f 1 \`;\
kill \`ps -x | grep \"[g]db\" | cut -d \ -f 2 \`
GDB := gdb -q\
- -ex \"set arch i386:x64-32\"\
+ -ex \"set arch i386:x86-64\"\
-ex \"file $(kernel)\"\
- -ex \"target remote localhost:$(PORTG)\" \
- -ex \"continue\"
+ -ex \"target remote :$(PORTG)\"
+ # -ex \"continue\"
all: $(kernel)
build/arch/$(arch)/%.o: src/arch/$(arch)/%.asm Makefile
@mkdir -p $(shell dirname $@)
- @$(NASM) $< -o $@
- @echo "Compiling (ASM) $@..."
+ $(NASM) $< -o $@
$(kernel): $(rust_os) $(asm_object) $(linker_script) Makefile
- @$(LD) -o $@ -T $(linker_script) $(asm_object) $(rust_os)
+ $(LD) -o $@ -T $(linker_script) $(asm_object) $(rust_os)
$(iso): $(kernel) $(grub.cfg) Makefile
@mkdir -p $(DIRISO)/boot/grub
@@ -71,7 +70,7 @@ R:
@tmux new-window 'tmux split-window -h "$(MONITOR)"; tmux split-window -fv "$(GDB)"; tmux select-pane -t 1; tmux resize-pane -x 80 -y 25; $(KERNEL_RUN)'
clean:
- @cargo clean
+ @xargo clean
@rm -r build
$(rust_os): $(target).json Makefile
diff --git a/kernel-rs/src/arch/x86/boot.asm b/kernel-rs/src/arch/x86/boot.asm
index ff6ad86e..c6cb7cb3 100644
--- a/kernel-rs/src/arch/x86/boot.asm
+++ b/kernel-rs/src/arch/x86/boot.asm
@@ -12,9 +12,12 @@ start:
call check_multiboot
call set_up_page_tables
- call enable_paging
+ ; call enable_pse
+ ; call enable_paging
+
+ ; load the new gdt
+ lgdt [GDTR.ptr]
- lgdt [GDTR.ptr] ; load the new gdt
jmp GDTR.gdt_cs:x86_start
check_multiboot:
@@ -45,13 +48,22 @@ set_up_page_tables:
cmp ecx, 1023 ; if counter == 1023, the whole P2 table is mapped
jne .map_p2_table ; else map the next entry
- ; load P2 to cr3 register (cpu uses this to access the P2 table)
- mov eax, p2_table
- mov cr3, eax
+ ret
+
+; PSE (Page Size Extension) allows huge pages to exist
+enable_pse:
+ ; enable PSE in the cr4 register
+ mov eax, cr4
+ or eax, 1 << 2
+ mov cr4, eax
ret
enable_paging:
+ ; load P2 to cr3 register (cpu uses this to access the P2 table)
+ mov eax, p2_table
+ mov cr3, eax
+
; enable paging in the cr0 register
mov eax, cr0
or eax, 1 << 31
diff --git a/kernel-rs/src/arch/x86/start.asm b/kernel-rs/src/arch/x86/start.asm
index d93b89af..8c69f1ce 100644
--- a/kernel-rs/src/arch/x86/start.asm
+++ b/kernel-rs/src/arch/x86/start.asm
@@ -13,7 +13,6 @@ x86_start:
call kmain
-; if main return, loop forever ; that should NEVER append
cli ; clear interrupt
HALT:
hlt
diff --git a/kernel-rs/src/context.rs b/kernel-rs/src/context.rs
index 03f810ad..25e0e30b 100644
--- a/kernel-rs/src/context.rs
+++ b/kernel-rs/src/context.rs
@@ -106,6 +106,6 @@ fn context() -> &'static mut Context {
pub fn init(multiboot_info_addr: usize) {
unsafe { CONTEXT = Some(Context::new(multiboot_info_addr)) };
- // memory::remap_the_kernel(frame_allocator(), boot_info());
+ memory::remap_the_kernel(frame_allocator(), boot_info());
self::init_screen();
}
diff --git a/kernel-rs/src/memory/paging/mapper.rs b/kernel-rs/src/memory/paging/mapper.rs
index 91a41aa6..b17d4ee7 100644
--- a/kernel-rs/src/memory/paging/mapper.rs
+++ b/kernel-rs/src/memory/paging/mapper.rs
@@ -33,14 +33,24 @@ impl Mapper {
pub fn translate_page(&self, page: Page) -> Option {
- // huge page handler, unimplemented
- let huge_page = || {
- unimplemented!()
- };
+ let p1 = self.p2().next_table(page.p2_index());
- self.p2().next_table(page.p2_index())
- .and_then(|p1| p1[page.p1_index()].pointed_frame())
- .or_else(huge_page)
+ let huge_page = || {
+ let p2_entry = &self.p2()[page.p2_index()];
+ if let Some(start_frame) = p2_entry.pointed_frame() {
+ if p2_entry.flags().contains(EntryFlags::HUGE_PAGE) {
+ // 2MiB alignment check
+ assert!(start_frame.number % ENTRY_COUNT == 0);
+ return Some(Frame {
+ number: start_frame.number + page.p1_index()
+ });
+ }
+ }
+ None
+ };
+
+ p1.and_then(|p1| p1[page.p1_index()].pointed_frame())
+ .or_else(huge_page)
}
diff --git a/kernel-rs/src/memory/paging/table.rs b/kernel-rs/src/memory/paging/table.rs
index 705f0a87..57988f06 100644
--- a/kernel-rs/src/memory/paging/table.rs
+++ b/kernel-rs/src/memory/paging/table.rs
@@ -51,11 +51,12 @@ impl Table where L: HierarchicalLevel
where A: FrameAllocator
{
if self.next_table(index).is_none() {
- // assert!(!self.entries[index].flags().contains(EntryFlags::HUGE_PAGE),
- // "mapping code does not support huge pages");
+ assert!(!self[index].flags().contains(EntryFlags::HUGE_PAGE),
+ "mapping code does not support huge pages");
let frame = allocator.allocate_frame().expect("no frames available");
- self.entries[index].set(frame, EntryFlags::PRESENT | EntryFlags::WRITABLE);
- self.next_table_mut(index).expect("no next next table 1").zero()
+ self[index].set(frame, EntryFlags::PRESENT | EntryFlags::WRITABLE);
+ panic!("wtf");
+ self.next_table_mut(index).expect("real wtf now").zero()
}
self.next_table_mut(index).expect("no next table 2")
}
diff --git a/kernel-rs/src/vga/mod.rs b/kernel-rs/src/vga/mod.rs
index 0a09fe1b..2ab62cbd 100644
--- a/kernel-rs/src/vga/mod.rs
+++ b/kernel-rs/src/vga/mod.rs
@@ -5,6 +5,7 @@ pub use self::color::{Color, ColorCode};
use context;
use cpuio;
use console;
+use x86;
#[derive(Debug, Clone, Copy)]
#[repr(C)]
@@ -164,7 +165,11 @@ impl Writer {
pub fn flush(&mut self) {
let slice = unsafe { core::slice::from_raw_parts_mut(0xb8000 as *mut u8, 4000) };
+
+ let cr0 = x86::cr0() & !(1 << 31);
+ unsafe { x86::cr0_write(cr0); }
slice.as_mut().clone_from_slice(&self.buffer);
+ unsafe { x86::cr0_write(cr0 | (1 << 31)); }
self.flush_cursor();
}
diff --git a/kernel-rs/src/x86/mod.rs b/kernel-rs/src/x86/mod.rs
index cd5ce658..3659eb88 100644
--- a/kernel-rs/src/x86/mod.rs
+++ b/kernel-rs/src/x86/mod.rs
@@ -1,5 +1,9 @@
//! x86 (32 bit) only
+pub unsafe fn cr0_write(val: usize) {
+ asm!("mov $0, %cr0" :: "r"(val) : "memory");
+}
+
pub fn cr0() -> usize {
let ret: usize;
unsafe { asm!("mov %cr0, $0" : "=r" (ret)) };
diff --git a/kernel-rs/x86-bluesnow.json b/kernel-rs/x86-bluesnow.json
index 6be11f62..6e895d2b 100644
--- a/kernel-rs/x86-bluesnow.json
+++ b/kernel-rs/x86-bluesnow.json
@@ -1,6 +1,5 @@
{
"arch": "x86",
- "cpu": "pentium4",
"data-layout": "e-m:e-p:32:32-f64:32:64-f80:32-n8:16:32-S128",
"llvm-target": "i686-unknown-none",
"linker-flavor": "gcc",