Allocate a read-only page which user code has attempted to write to. This is called by the page fault handler
(
addr: VirtAddr
)
| 806 | /// has attempted to write to. |
| 807 | /// This is called by the page fault handler |
| 808 | pub fn allocate_missing_ondemand_frame( |
| 809 | addr: VirtAddr |
| 810 | ) -> Result<(), &'static str> { |
| 811 | |
| 812 | let table = active_level_1_table_containing(addr); |
| 813 | let entry = &mut table[addr.p1_index()]; |
| 814 | |
| 815 | if entry.flags() != (PageTableFlags::PRESENT | |
| 816 | PageTableFlags::USER_ACCESSIBLE) { |
| 817 | println!("Unexpected flags: {:?} addr: {:?}", entry.flags(), addr); |
| 818 | return Err("Error: Unexpected table flags"); |
| 819 | } |
| 820 | |
| 821 | // Get a new frame and update page table |
| 822 | let memory_info = unsafe {MEMORY_INFO.as_mut().unwrap()}; |
| 823 | let frame = memory_info.frame_allocator.allocate_frame() |
| 824 | .ok_or("Could not allocate frame")?; |
| 825 | |
| 826 | entry.set_addr(frame.start_address(), |
| 827 | PageTableFlags::PRESENT | |
| 828 | PageTableFlags::WRITABLE | |
| 829 | PageTableFlags::USER_ACCESSIBLE); |
| 830 | Ok(()) |
| 831 | } |
| 832 | |
| 833 | /// Free frames used for a thread stack |
| 834 | /// given virtual address |
no test coverage detected