diff --git a/crate/memory/src/memory_set.rs b/crate/memory/src/memory_set.rs index 7c5c1c8..7886509 100644 --- a/crate/memory/src/memory_set.rs +++ b/crate/memory/src/memory_set.rs @@ -223,7 +223,7 @@ pub struct MemoryAttr { readonly: bool, execute: bool, hide: bool, - mmio: usize, + mmio: u8, } impl MemoryAttr { @@ -255,7 +255,7 @@ impl MemoryAttr { ** @brief set the MMIO type ** @retval MemoryAttr the memory attribute itself */ - pub fn mmio(mut self, value: usize) -> Self { + pub fn mmio(mut self, value: u8) -> Self { self.mmio = value; self } diff --git a/crate/memory/src/paging/mod.rs b/crate/memory/src/paging/mod.rs index 0fa7447..af8b0ae 100644 --- a/crate/memory/src/paging/mod.rs +++ b/crate/memory/src/paging/mod.rs @@ -198,13 +198,13 @@ pub trait Entry { /* ** @brief get MMIO type ** (e.g. aarch64 can have normal/device/normal_non_cacheable memory) - ** @retval usize + ** @retval u8 the MMIO type */ - fn mmio(&self) -> usize; + fn mmio(&self) -> u8; /* ** @brief set MMIO type - ** @param value: usize the value distinguished memory type + ** @param value: u8 the MMIO type ** @retval none */ - fn set_mmio(&mut self, value: usize); + fn set_mmio(&mut self, value: u8); } diff --git a/kernel/Cargo.lock b/kernel/Cargo.lock index 47635c9..1228664 100644 --- a/kernel/Cargo.lock +++ b/kernel/Cargo.lock @@ -1,7 +1,7 @@ [[package]] name = "aarch64" version = "2.2.2" -source = "git+https://github.com/equation314/aarch64#9770a21c00f5d74c32ed044ca200f0459caca828" +source = "git+https://github.com/equation314/aarch64#b6a0f4a3be6f74927c88305a6af5ad2be079bccd" dependencies = [ "bit_field 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/kernel/src/arch/aarch64/board/raspi3/fb.rs b/kernel/src/arch/aarch64/board/raspi3/fb.rs index ef3b187..5d6d8f3 100644 --- a/kernel/src/arch/aarch64/board/raspi3/fb.rs +++ b/kernel/src/arch/aarch64/board/raspi3/fb.rs @@ -48,7 +48,7 @@ use self::ColorFormat::*; #[repr(C)] union ColorBuffer { - base_addr: u32, + base_addr: usize, buf16: &'static mut [u16], buf32: &'static mut [u32], } @@ -154,10 +154,11 @@ impl Framebuffer { } #[inline] - pub fn base_addr(&self) -> u32 { + pub fn base_addr(&self) -> usize { unsafe { self.buf.base_addr } } + /// Read pixel at `(x, y)`. #[inline] pub fn read(&self, x: u32, y: u32) -> u32 { match self.color_format { @@ -166,6 +167,7 @@ impl Framebuffer { } } + /// Write pixel at `(x, y)`. #[inline] pub fn write(&mut self, x: u32, y: u32, pixel: u32) { match self.color_format { diff --git a/kernel/src/arch/aarch64/board/raspi3/mailbox.rs b/kernel/src/arch/aarch64/board/raspi3/mailbox.rs index 1bee860..9b63027 100644 --- a/kernel/src/arch/aarch64/board/raspi3/mailbox.rs +++ b/kernel/src/arch/aarch64/board/raspi3/mailbox.rs @@ -8,7 +8,7 @@ use lazy_static::lazy_static; use alloc::string::String; use core::mem; use spin::Mutex; -use aarch64::{asm, barrier}; +use aarch64::asm; lazy_static! { static ref MAILBOX: Mutex = Mutex::new(Mailbox::new()); diff --git a/kernel/src/arch/aarch64/memory.rs b/kernel/src/arch/aarch64/memory.rs index 00ff312..60a3334 100644 --- a/kernel/src/arch/aarch64/memory.rs +++ b/kernel/src/arch/aarch64/memory.rs @@ -1,6 +1,7 @@ //! Memory initialization for aarch64. use crate::memory::{init_heap, MemoryArea, MemoryAttr, MemorySet, FRAME_ALLOCATOR}; +use super::paging::MMIOType; use aarch64::paging::{memory_attribute::*, PhysFrame as Frame}; use aarch64::{addr::*, barrier, regs::*}; use atags::atags::Atags; @@ -32,8 +33,8 @@ pub fn init_mmu_early() { // device. MAIR_EL1.write( - MAIR_EL1::Attr0.val(MairDevice::config_value()) + - MAIR_EL1::Attr1.val(MairNormal::config_value()) + + MAIR_EL1::Attr0.val(MairNormal::config_value()) + + MAIR_EL1::Attr1.val(MairDevice::config_value()) + MAIR_EL1::Attr2.val(MairNormalNonCacheable::config_value()), ); @@ -116,7 +117,7 @@ fn remap_the_kernel() { ms.push(MemoryArea::new_identity( IO_REMAP_BASE, IO_REMAP_END, - MemoryAttr::default().mmio(MairDevice::attr_value().value as usize), + MemoryAttr::default().mmio(MMIOType::Device as u8), "io_remap", )); @@ -129,7 +130,7 @@ pub fn ioremap(start: usize, len: usize, name: &'static str) -> usize { let area = MemoryArea::new_identity( start, start + len, - MemoryAttr::default().mmio(MairNormalNonCacheable::attr_value().value as usize), + MemoryAttr::default().mmio(MMIOType::NormalNonCacheable as u8), name, ); ms.push(area); diff --git a/kernel/src/arch/aarch64/paging.rs b/kernel/src/arch/aarch64/paging.rs index cfe1770..453f7c8 100644 --- a/kernel/src/arch/aarch64/paging.rs +++ b/kernel/src/arch/aarch64/paging.rs @@ -22,7 +22,7 @@ pub fn setup_temp_page_table(frame_lvl4: Frame, frame_lvl3: Frame, frame_lvl2: F p2.zero(); let (start_addr, end_addr) = (0, 0x40000000); - let block_flags = EF::VALID | EF::AF | EF::WRITE | EF::XN; + let block_flags = EF::VALID | EF::AF | EF::WRITE | EF::UXN; for page in Page::::range_of(start_addr, end_addr) { let paddr = PhysAddr::new(page.start_address().as_u64()); @@ -106,6 +106,14 @@ impl ActivePageTable { } } +#[repr(u8)] +pub enum MMIOType { + Normal = 0, + Device = 1, + NormalNonCacheable = 2, + Unsupported = 3, +} + impl Entry for PageEntry { fn update(&mut self) { let addr = VirtAddr::new_unchecked((self as *const _ as u64) << 9); @@ -150,22 +158,38 @@ impl Entry for PageEntry { } fn execute(&self) -> bool { if self.user() { - !self.0.flags().contains(EF::XN) + !self.0.flags().contains(EF::UXN) } else { !self.0.flags().contains(EF::PXN) } } fn set_execute(&mut self, value: bool) { if self.user() { - self.as_flags().set(EF::XN, !value) + self.as_flags().set(EF::UXN, !value) } else { self.as_flags().set(EF::PXN, !value) } } - fn mmio(&self) -> usize { self.0.attr().value as usize } - fn set_mmio(&mut self, value: usize) { - use aarch64::paging::{PageTableAttribute, MEMORY_ATTR_MASK}; - self.0.modify_attr(PageTableAttribute::new(MEMORY_ATTR_MASK, 0, value as u64)) + fn mmio(&self) -> u8 { + let value = self.0.attr().value; + if value == MairNormal::attr_value().value { + 0 + } else if value == MairDevice::attr_value().value { + 1 + } else if value == MairNormalNonCacheable::attr_value().value { + 2 + } else { + 3 + } + } + fn set_mmio(&mut self, value: u8) { + let attr = match value { + 0 => MairNormal::attr_value(), + 1 => MairDevice::attr_value(), + 2 => MairNormalNonCacheable::attr_value(), + _ => return, + }; + self.0.modify_attr(attr); } } diff --git a/kernel/src/arch/riscv32/paging.rs b/kernel/src/arch/riscv32/paging.rs index 6cce3f3..631a9f8 100644 --- a/kernel/src/arch/riscv32/paging.rs +++ b/kernel/src/arch/riscv32/paging.rs @@ -26,7 +26,7 @@ pub fn setup_page_table(frame: Frame) { // Set kernel identity map // 0x10000000 ~ 1K area p2.map_identity(0x40, EF::VALID | EF::READABLE | EF::WRITABLE); - // 0x80000000 ~ 12M area + // 0x80000000 ~ 12M area p2.map_identity(KERNEL_P2_INDEX, EF::VALID | EF::READABLE | EF::WRITABLE | EF::EXECUTABLE); p2.map_identity(KERNEL_P2_INDEX + 1, EF::VALID | EF::READABLE | EF::WRITABLE | EF::EXECUTABLE); p2.map_identity(KERNEL_P2_INDEX + 2, EF::VALID | EF::READABLE | EF::WRITABLE | EF::EXECUTABLE); @@ -196,8 +196,8 @@ impl Entry for PageEntry { fn set_user(&mut self, value: bool) { self.as_flags().set(EF::USER, value); } fn execute(&self) -> bool { self.0.flags().contains(EF::EXECUTABLE) } fn set_execute(&mut self, value: bool) { self.as_flags().set(EF::EXECUTABLE, value); } - fn mmio(&self) -> bool { unimplemented!() } - fn set_mmio(&mut self, value: bool) { unimplemented!() } + fn mmio(&self) -> u8 { 0 } + fn set_mmio(&mut self, _value: u8) { } } impl PageEntry { diff --git a/kernel/src/arch/x86_64/paging.rs b/kernel/src/arch/x86_64/paging.rs index bdf9a4c..e269935 100644 --- a/kernel/src/arch/x86_64/paging.rs +++ b/kernel/src/arch/x86_64/paging.rs @@ -142,8 +142,8 @@ impl Entry for PageEntry { } fn execute(&self) -> bool { !self.0.flags().contains(EF::NO_EXECUTE) } fn set_execute(&mut self, value: bool) { self.as_flags().set(EF::NO_EXECUTE, !value); } - fn mmio(&self) -> bool { unimplemented!() } - fn set_mmio(&mut self, value: bool) { unimplemented!() } + fn mmio(&self) -> u8 { 0 } + fn set_mmio(&mut self, _value: u8) { } } fn get_entry_ptr(addr: usize, level: u8) -> *mut PageEntry {