kernel/mm/vmm/traits.rs
1// SPDX-License-Identifier: GPL-3.0-only
2//!
3//!
4//! Authors: MarioS271
5
6use crate::lib::addr::{PhysAddr, VirtAddr};
7use crate::lib::types::boot_info::KernelSectionInfo;
8use crate::mm::pmm::Pmm;
9use crate::mm::vmm::boot_mapping::BootMappings;
10use crate::mm::vmm::vma::VmaFlags;
11use crate::mm::vmm::VmmResult;
12
13pub trait VmmPaging {
14 type PageType;
15 type PageTableFlags;
16
17 /// Initialize the kernel page tables and load them
18 ///
19 /// # Panics
20 /// Panics if the PMM cannot allocate memory for the page tables
21 fn setup_kernel_paging(sections: &KernelSectionInfo) -> (VirtAddr, BootMappings);
22
23 /// Map one virtual page to a physical frame. `PRESENT` is forced on regardless of `flags`.
24 ///
25 /// # Safety
26 /// The caller must ensure `virt` is a valid kernel virtual address and `phys` is a
27 /// valid, PMM-allocated frame.
28 unsafe fn map_page(
29 pmm: &mut Pmm,
30 page_ptr: VirtAddr,
31 virt: VirtAddr,
32 phys: PhysAddr,
33 page_type: Self::PageType,
34 flags: Self::PageTableFlags
35 ) -> VmmResult;
36
37 /// Map a certain block of physical memory to virtual pages calculated by the method
38 ///
39 /// # Safety
40 /// The caller must ensure `virt` is a valid kernel virtual address and `phys` is a
41 /// valid, PMM-allocated frame.
42 unsafe fn map_range(
43 pmm: &mut Pmm,
44 page_ptr: VirtAddr,
45 virt: VirtAddr,
46 phys: PhysAddr,
47 size: u64,
48 flags: Self::PageTableFlags,
49 can_overmap: bool
50 ) -> VmmResult;
51
52 /// Unmap one virtual page
53 ///
54 /// # Safety
55 /// The caller must ensure `virt` was previously mapped and that no live code or
56 /// data references the page after this call returns.
57 unsafe fn unmap_page(
58 page_ptr: VirtAddr,
59 virt: VirtAddr
60 ) -> VmmResult;
61
62 /// Change page table flags of an already mapped page
63 ///
64 /// # Safety
65 /// The caller must ensure `virt` was previously mapped and that changing the page's flags
66 /// will not violate anything (example: making a page non-writable while a mutable reference
67 /// is held to it)
68 unsafe fn remap_page(
69 page_ptr: VirtAddr,
70 virt: VirtAddr,
71 new_flags: Self::PageTableFlags
72 ) -> VmmResult;
73
74 /// Walk the page tables and return the phys address mapped at `virt` or `None` if the
75 /// address is not mapped
76 fn translate(
77 page_ptr: VirtAddr,
78 virt: VirtAddr
79 ) -> Option<PhysAddr>;
80
81 /// Walk the page tables and return a tuple of the phys address mapped at `virt` and the size of
82 /// the page `virt` is mapped in, or `None` if the address is not mapped
83 fn translate_with_size(
84 page_ptr: VirtAddr,
85 virt: VirtAddr
86 ) -> Option<(PhysAddr, u64)>;
87
88 /// Translate VMA flags to arch-specific page table flags
89 fn vma_flags_to_page_flags(
90 vma_flags: VmaFlags
91 ) -> Self::PageTableFlags;
92
93 /// Clone the kernel page's mappings into a user page
94 ///
95 /// # Safety
96 /// The caller must ensure that `dst` is a valid, mapped page
97 unsafe fn clone_kernel_mappings(
98 dst: VirtAddr
99 );
100}