|
|
|
@ -134,14 +134,14 @@ impl MemoryManager {
|
|
|
|
|
// the MMU
|
|
|
|
|
unsafe { mstatus::clear_mie() };
|
|
|
|
|
|
|
|
|
|
let ranges = [
|
|
|
|
|
let mut ranges = [
|
|
|
|
|
mem_range!(&_sbss, &_ebss),
|
|
|
|
|
mem_range!(&_sdata, &_edata),
|
|
|
|
|
mem_range!(&_estack, &_sstack), // NOTE: Stack is reversed
|
|
|
|
|
mem_range!(&_stext, &_etext),
|
|
|
|
|
];
|
|
|
|
|
for range in &ranges {
|
|
|
|
|
for region in range.clone() {
|
|
|
|
|
for range in &mut ranges {
|
|
|
|
|
for region in range {
|
|
|
|
|
mm.claim_page(region & !0xfff, 1)
|
|
|
|
|
.expect("Unable to claim region for PID 1");
|
|
|
|
|
}
|
|
|
|
@ -190,11 +190,12 @@ impl MemoryManager {
|
|
|
|
|
phys: usize,
|
|
|
|
|
virt: usize,
|
|
|
|
|
) -> Result<(), XousError> {
|
|
|
|
|
let ppn1 = (phys >> 20) & ((1 << 12) - 1);
|
|
|
|
|
let ppn0 = (phys >> 10) & ((1 << 10) - 1);
|
|
|
|
|
let ppn1 = (phys >> 22) & ((1 << 12) - 1);
|
|
|
|
|
let ppn0 = (phys >> 12) & ((1 << 10) - 1);
|
|
|
|
|
let ppo = (phys >> 0) & ((1 << 12) - 1);
|
|
|
|
|
|
|
|
|
|
let vpn1 = (virt >> 22) & ((1 << 10) - 1);
|
|
|
|
|
let vpn0 = (virt >> 10) & ((1 << 10) - 1);
|
|
|
|
|
let vpn0 = (virt >> 12) & ((1 << 10) - 1);
|
|
|
|
|
let vpo = (virt >> 0) & ((1 << 12) - 1);
|
|
|
|
|
|
|
|
|
|
println!(
|
|
|
|
@ -213,7 +214,10 @@ impl MemoryManager {
|
|
|
|
|
|
|
|
|
|
// Allocate a new level 1 pagetable entry if one doesn't exist.
|
|
|
|
|
if l1_pt[vpn1] & 1 == 0 {
|
|
|
|
|
println!(" top-level VPN1 {:04x}: {:08x} (will allocate a new one)", vpn1, l1_pt[vpn1]);
|
|
|
|
|
println!(
|
|
|
|
|
" top-level VPN1 {:04x}: {:08x} (will allocate a new one)",
|
|
|
|
|
vpn1, l1_pt[vpn1]
|
|
|
|
|
);
|
|
|
|
|
// Allocate the page to the kernel (PID 1)
|
|
|
|
|
let new_addr = self.alloc_page(1)?.get();
|
|
|
|
|
println!(
|
|
|
|
@ -223,64 +227,65 @@ impl MemoryManager {
|
|
|
|
|
|
|
|
|
|
// Mark this entry as a leaf node (WRX as 0), and indicate
|
|
|
|
|
// it is a valid page by setting "V".
|
|
|
|
|
l1_pt[vpn1] = (((new_addr >> 10) & ((1 << 22) - 1)) << 10) | 1;
|
|
|
|
|
let ppn = new_addr >> 12;
|
|
|
|
|
l1_pt[vpn1] = (ppn << 10) | 1;
|
|
|
|
|
println!(" New top-level page entry: {:08x}", l1_pt[vpn1]);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
let mut l0_pt = unsafe {
|
|
|
|
|
let tmp = (l1_pt[vpn1] & ((1 << 10) - 1)) as *mut PageTable;
|
|
|
|
|
(*tmp).entries
|
|
|
|
|
};
|
|
|
|
|
let l0_pt_idx =
|
|
|
|
|
unsafe { &mut (*(((l1_pt[vpn1] << 2) & !((1 << 12) - 1)) as *mut PageTable)) };
|
|
|
|
|
let ref mut l0_pt = l0_pt_idx.entries;
|
|
|
|
|
println!(" l0_pt is at {:p} ({:p})", &l0_pt, &l0_pt[vpn0]);
|
|
|
|
|
|
|
|
|
|
// Allocate a new level 0 pagetable entry if one doesn't exist.
|
|
|
|
|
if l0_pt[vpn0] & 1 != 0 {
|
|
|
|
|
panic!("Page already allocated!");
|
|
|
|
|
println!("Page already allocated!");
|
|
|
|
|
}
|
|
|
|
|
l0_pt[vpn0] = (ppn1 << 20) | (ppn0 << 10) | 1 | 0xe;
|
|
|
|
|
l0_pt[vpn0] = (ppn1 << 20) | (ppn0 << 10) | 1 | 0xe | 0xc0;
|
|
|
|
|
Ok(())
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/// Create an identity mapping, copying the kernel to itself
|
|
|
|
|
pub fn create_identity(&mut self, process: &Process) -> Result<(), XousError> {
|
|
|
|
|
let root_page = (process.satp & ((1 << 22) - 1)) << 9;
|
|
|
|
|
let root_page = (process.satp & ((1 << 22) - 1)) << 12;
|
|
|
|
|
let pt = unsafe { &mut (*(root_page as *mut PageTable)) };
|
|
|
|
|
println!("SATP value: {:08x} Root page: {:08x} pt: {:p} pt: {:p}", process.satp, root_page, &pt, pt);
|
|
|
|
|
println!(
|
|
|
|
|
"SATP value: {:08x} Root page: {:08x} pt: {:p} pt: {:p}",
|
|
|
|
|
process.satp, root_page, &pt, pt
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
let ranges = [
|
|
|
|
|
let mut ranges = [
|
|
|
|
|
mem_range!(&_sbss, &_ebss),
|
|
|
|
|
mem_range!(&_sdata, &_edata),
|
|
|
|
|
mem_range!(&_estack, &_sstack), // NOTE: Stack is reversed
|
|
|
|
|
mem_range!(&_stext, &_etext),
|
|
|
|
|
];
|
|
|
|
|
for range in &ranges {
|
|
|
|
|
for region in range.clone() {
|
|
|
|
|
for range in &mut ranges {
|
|
|
|
|
for region in range {
|
|
|
|
|
// mm.claim_page(region & !0xfff, 1)
|
|
|
|
|
// .expect("Unable to claim region for PID 1");
|
|
|
|
|
self.map_page(
|
|
|
|
|
pt,
|
|
|
|
|
region,
|
|
|
|
|
region,
|
|
|
|
|
)?;
|
|
|
|
|
print!("Entries mapped: >");
|
|
|
|
|
let mut i = 0;
|
|
|
|
|
for (entry_idx, entry) in pt.entries.iter().enumerate() {
|
|
|
|
|
i = i + 1;
|
|
|
|
|
if *entry != 0 {
|
|
|
|
|
print!(" {}:{:08x}", entry_idx, entry);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
println!(" < ({})", i);
|
|
|
|
|
self.map_page(pt, region, region)?;
|
|
|
|
|
// print!("Entries mapped: >");
|
|
|
|
|
// let mut i = 0;
|
|
|
|
|
// for (entry_idx, entry) in pt.entries.iter().enumerate() {
|
|
|
|
|
// i = i + 1;
|
|
|
|
|
// if *entry != 0 {
|
|
|
|
|
// print!(" {}:{:08x}", entry_idx, entry);
|
|
|
|
|
// }
|
|
|
|
|
// }
|
|
|
|
|
// println!(" < ({})", i);
|
|
|
|
|
println!("");
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
self.map_page(pt, 0xE000_1800, 0xE000_1800)?;
|
|
|
|
|
// let flash_orig = self.flash.clone();
|
|
|
|
|
// for (flash_idx, flash_pid) in flash_orig.iter().enumerate() {
|
|
|
|
|
// if *flash_pid == pid {
|
|
|
|
|
// println!(
|
|
|
|
|
// "Flash addr {:08x} owned by PID {}, mapping it as ident",
|
|
|
|
|
// flash_idx * PAGE_SIZE + FLASH_START,
|
|
|
|
|
// pid
|
|
|
|
|
// );
|
|
|
|
|
// println!(
|
|
|
|
|
// "Flash addr {:08x} owned by PID {}, mapping it as ident",
|
|
|
|
|
// flash_idx * PAGE_SIZE + FLASH_START,
|
|
|
|
|
// pid
|
|
|
|
|
// );
|
|
|
|
|
// }
|
|
|
|
|
// }
|
|
|
|
|
|
|
|
|
|