xref: /DragonOS/kernel/src/mm/fault.rs (revision cf7f801e1d50ee5b04cb728e4251a57f4183bfbc)
1*cf7f801eSMemoryShore use core::{
2*cf7f801eSMemoryShore     alloc::Layout,
3*cf7f801eSMemoryShore     cmp::{max, min},
4*cf7f801eSMemoryShore     intrinsics::unlikely,
5*cf7f801eSMemoryShore     panic,
6*cf7f801eSMemoryShore };
7a17651b1SMemoryShore 
8a17651b1SMemoryShore use alloc::sync::Arc;
9a17651b1SMemoryShore 
10a17651b1SMemoryShore use crate::{
11a17651b1SMemoryShore     arch::{mm::PageMapper, MMArch},
12*cf7f801eSMemoryShore     libs::align::align_down,
13a17651b1SMemoryShore     mm::{
14*cf7f801eSMemoryShore         page::{page_manager_lock_irqsave, EntryFlags},
15a17651b1SMemoryShore         ucontext::LockedVMA,
16a17651b1SMemoryShore         VirtAddr, VmFaultReason, VmFlags,
17a17651b1SMemoryShore     },
18a17651b1SMemoryShore     process::{ProcessManager, ProcessState},
19a17651b1SMemoryShore };
20a17651b1SMemoryShore 
21a17651b1SMemoryShore use crate::mm::MemoryManagementArch;
22a17651b1SMemoryShore 
23*cf7f801eSMemoryShore use super::{
24*cf7f801eSMemoryShore     allocator::page_frame::FrameAllocator,
25*cf7f801eSMemoryShore     page::{page_reclaimer_lock_irqsave, Page, PageFlags},
26*cf7f801eSMemoryShore };
27*cf7f801eSMemoryShore 
28a17651b1SMemoryShore bitflags! {
29a17651b1SMemoryShore     pub struct FaultFlags: u64{
30a17651b1SMemoryShore         const FAULT_FLAG_WRITE = 1 << 0;
31a17651b1SMemoryShore         const FAULT_FLAG_MKWRITE = 1 << 1;
32a17651b1SMemoryShore         const FAULT_FLAG_ALLOW_RETRY = 1 << 2;
33a17651b1SMemoryShore         const FAULT_FLAG_RETRY_NOWAIT = 1 << 3;
34a17651b1SMemoryShore         const FAULT_FLAG_KILLABLE = 1 << 4;
35a17651b1SMemoryShore         const FAULT_FLAG_TRIED = 1 << 5;
36a17651b1SMemoryShore         const FAULT_FLAG_USER = 1 << 6;
37a17651b1SMemoryShore         const FAULT_FLAG_REMOTE = 1 << 7;
38a17651b1SMemoryShore         const FAULT_FLAG_INSTRUCTION = 1 << 8;
39a17651b1SMemoryShore         const FAULT_FLAG_INTERRUPTIBLE =1 << 9;
40a17651b1SMemoryShore         const FAULT_FLAG_UNSHARE = 1 << 10;
41a17651b1SMemoryShore         const FAULT_FLAG_ORIG_PTE_VALID = 1 << 11;
42a17651b1SMemoryShore         const FAULT_FLAG_VMA_LOCK = 1 << 12;
43a17651b1SMemoryShore     }
44a17651b1SMemoryShore }
45a17651b1SMemoryShore 
46a17651b1SMemoryShore /// # 缺页异常信息结构体
47a17651b1SMemoryShore /// 包含了页面错误处理的相关信息,例如出错的地址、VMA等
48a17651b1SMemoryShore #[derive(Debug)]
49*cf7f801eSMemoryShore pub struct PageFaultMessage<'a> {
50*cf7f801eSMemoryShore     /// 产生缺页的VMA结构体
51*cf7f801eSMemoryShore     vma: Arc<LockedVMA>,
52*cf7f801eSMemoryShore     /// 缺页地址
53*cf7f801eSMemoryShore     address: VirtAddr,
54*cf7f801eSMemoryShore     /// 异常处理标志
55*cf7f801eSMemoryShore     flags: FaultFlags,
56*cf7f801eSMemoryShore     /// 页表映射器
57*cf7f801eSMemoryShore     mapper: &'a mut PageMapper,
58*cf7f801eSMemoryShore     /// 缺页的文件页在文件中的偏移量
59*cf7f801eSMemoryShore     file_pgoff: Option<usize>,
60*cf7f801eSMemoryShore     /// 缺页对应PageCache中的文件页
61*cf7f801eSMemoryShore     page: Option<Arc<Page>>,
62*cf7f801eSMemoryShore     /// 写时拷贝需要的页面
63*cf7f801eSMemoryShore     cow_page: Option<Arc<Page>>,
64*cf7f801eSMemoryShore }
65*cf7f801eSMemoryShore 
66*cf7f801eSMemoryShore impl<'a> PageFaultMessage<'a> {
new( vma: Arc<LockedVMA>, address: VirtAddr, flags: FaultFlags, mapper: &'a mut PageMapper, ) -> Self67*cf7f801eSMemoryShore     pub fn new(
68a17651b1SMemoryShore         vma: Arc<LockedVMA>,
69a17651b1SMemoryShore         address: VirtAddr,
70a17651b1SMemoryShore         flags: FaultFlags,
71*cf7f801eSMemoryShore         mapper: &'a mut PageMapper,
72*cf7f801eSMemoryShore     ) -> Self {
73*cf7f801eSMemoryShore         let guard = vma.lock_irqsave();
74*cf7f801eSMemoryShore         let file_pgoff = guard.file_page_offset().map(|file_page_offset| {
75*cf7f801eSMemoryShore             ((address - guard.region().start()) >> MMArch::PAGE_SHIFT) + file_page_offset
76*cf7f801eSMemoryShore         });
77a17651b1SMemoryShore         Self {
78a17651b1SMemoryShore             vma: vma.clone(),
79*cf7f801eSMemoryShore             address: VirtAddr::new(crate::libs::align::page_align_down(address.data())),
80a17651b1SMemoryShore             flags,
81*cf7f801eSMemoryShore             file_pgoff,
82*cf7f801eSMemoryShore             page: None,
83*cf7f801eSMemoryShore             mapper,
84*cf7f801eSMemoryShore             cow_page: None,
85a17651b1SMemoryShore         }
86a17651b1SMemoryShore     }
87a17651b1SMemoryShore 
88a17651b1SMemoryShore     #[inline(always)]
89a17651b1SMemoryShore     #[allow(dead_code)]
vma(&self) -> Arc<LockedVMA>90a17651b1SMemoryShore     pub fn vma(&self) -> Arc<LockedVMA> {
91a17651b1SMemoryShore         self.vma.clone()
92a17651b1SMemoryShore     }
93a17651b1SMemoryShore 
94a17651b1SMemoryShore     #[inline(always)]
95a17651b1SMemoryShore     #[allow(dead_code)]
address(&self) -> VirtAddr96a17651b1SMemoryShore     pub fn address(&self) -> VirtAddr {
97a17651b1SMemoryShore         self.address
98a17651b1SMemoryShore     }
99a17651b1SMemoryShore 
100a17651b1SMemoryShore     #[inline(always)]
101a17651b1SMemoryShore     #[allow(dead_code)]
address_aligned_down(&self) -> VirtAddr102a17651b1SMemoryShore     pub fn address_aligned_down(&self) -> VirtAddr {
103a17651b1SMemoryShore         VirtAddr::new(crate::libs::align::page_align_down(self.address.data()))
104a17651b1SMemoryShore     }
105a17651b1SMemoryShore 
106a17651b1SMemoryShore     #[inline(always)]
107a17651b1SMemoryShore     #[allow(dead_code)]
flags(&self) -> FaultFlags108a17651b1SMemoryShore     pub fn flags(&self) -> FaultFlags {
109a17651b1SMemoryShore         self.flags
110a17651b1SMemoryShore     }
111a17651b1SMemoryShore }
112a17651b1SMemoryShore 
113a17651b1SMemoryShore /// 缺页中断处理结构体
114a17651b1SMemoryShore pub struct PageFaultHandler;
115a17651b1SMemoryShore 
116a17651b1SMemoryShore impl PageFaultHandler {
117a17651b1SMemoryShore     /// 处理缺页异常
118a17651b1SMemoryShore     /// ## 参数
119a17651b1SMemoryShore     ///
120a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
121a17651b1SMemoryShore     /// - `mapper`: 页表映射器
122a17651b1SMemoryShore     ///
123a17651b1SMemoryShore     /// ## 返回值
124a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
handle_mm_fault(mut pfm: PageFaultMessage) -> VmFaultReason125*cf7f801eSMemoryShore     pub unsafe fn handle_mm_fault(mut pfm: PageFaultMessage) -> VmFaultReason {
126a17651b1SMemoryShore         let flags = pfm.flags();
127a17651b1SMemoryShore         let vma = pfm.vma();
128a17651b1SMemoryShore         let current_pcb = ProcessManager::current_pcb();
129a17651b1SMemoryShore         let mut guard = current_pcb.sched_info().inner_lock_write_irqsave();
130a17651b1SMemoryShore         guard.set_state(ProcessState::Runnable);
131a17651b1SMemoryShore 
132a17651b1SMemoryShore         if !MMArch::vma_access_permitted(
133a17651b1SMemoryShore             vma.clone(),
134a17651b1SMemoryShore             flags.contains(FaultFlags::FAULT_FLAG_WRITE),
135a17651b1SMemoryShore             flags.contains(FaultFlags::FAULT_FLAG_INSTRUCTION),
136a17651b1SMemoryShore             flags.contains(FaultFlags::FAULT_FLAG_REMOTE),
137a17651b1SMemoryShore         ) {
138a17651b1SMemoryShore             return VmFaultReason::VM_FAULT_SIGSEGV;
139a17651b1SMemoryShore         }
140a17651b1SMemoryShore 
141*cf7f801eSMemoryShore         let guard = vma.lock_irqsave();
142a17651b1SMemoryShore         let vm_flags = *guard.vm_flags();
143a17651b1SMemoryShore         drop(guard);
144a17651b1SMemoryShore         if unlikely(vm_flags.contains(VmFlags::VM_HUGETLB)) {
145a17651b1SMemoryShore             //TODO: 添加handle_hugetlb_fault处理大页缺页异常
146a17651b1SMemoryShore         } else {
147*cf7f801eSMemoryShore             Self::handle_normal_fault(&mut pfm);
148a17651b1SMemoryShore         }
149a17651b1SMemoryShore 
150a17651b1SMemoryShore         VmFaultReason::VM_FAULT_COMPLETED
151a17651b1SMemoryShore     }
152a17651b1SMemoryShore 
153a17651b1SMemoryShore     /// 处理普通页缺页异常
154a17651b1SMemoryShore     /// ## 参数
155a17651b1SMemoryShore     ///
156a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
157a17651b1SMemoryShore     /// - `mapper`: 页表映射器
158a17651b1SMemoryShore     ///
159a17651b1SMemoryShore     /// ## 返回值
160a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
handle_normal_fault(pfm: &mut PageFaultMessage) -> VmFaultReason161*cf7f801eSMemoryShore     pub unsafe fn handle_normal_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
162a17651b1SMemoryShore         let address = pfm.address_aligned_down();
163a17651b1SMemoryShore         let vma = pfm.vma.clone();
164*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
165a17651b1SMemoryShore         if mapper.get_entry(address, 3).is_none() {
166a17651b1SMemoryShore             mapper
167a17651b1SMemoryShore                 .allocate_table(address, 2)
168a17651b1SMemoryShore                 .expect("failed to allocate PUD table");
169a17651b1SMemoryShore         }
170*cf7f801eSMemoryShore         let page_flags = vma.lock_irqsave().flags();
171a17651b1SMemoryShore 
172a17651b1SMemoryShore         for level in 2..=3 {
173a17651b1SMemoryShore             let level = MMArch::PAGE_LEVELS - level;
174a17651b1SMemoryShore             if mapper.get_entry(address, level).is_none() {
175a17651b1SMemoryShore                 if vma.is_hugepage() {
176a17651b1SMemoryShore                     if vma.is_anonymous() {
177a17651b1SMemoryShore                         mapper.map_huge_page(address, page_flags);
178a17651b1SMemoryShore                     }
179a17651b1SMemoryShore                 } else if mapper.allocate_table(address, level - 1).is_none() {
180a17651b1SMemoryShore                     return VmFaultReason::VM_FAULT_OOM;
181a17651b1SMemoryShore                 }
182a17651b1SMemoryShore             }
183a17651b1SMemoryShore         }
184a17651b1SMemoryShore 
185*cf7f801eSMemoryShore         Self::handle_pte_fault(pfm)
186a17651b1SMemoryShore     }
187a17651b1SMemoryShore 
188a17651b1SMemoryShore     /// 处理页表项异常
189a17651b1SMemoryShore     /// ## 参数
190a17651b1SMemoryShore     ///
191a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
192a17651b1SMemoryShore     /// - `mapper`: 页表映射器
193a17651b1SMemoryShore     ///
194a17651b1SMemoryShore     /// ## 返回值
195a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
handle_pte_fault(pfm: &mut PageFaultMessage) -> VmFaultReason196*cf7f801eSMemoryShore     pub unsafe fn handle_pte_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
197a17651b1SMemoryShore         let address = pfm.address_aligned_down();
198a17651b1SMemoryShore         let flags = pfm.flags;
199a17651b1SMemoryShore         let vma = pfm.vma.clone();
20017dc5589SMemoryShore         let mut ret = VmFaultReason::VM_FAULT_COMPLETED;
201*cf7f801eSMemoryShore         let mapper = &pfm.mapper;
202*cf7f801eSMemoryShore 
203*cf7f801eSMemoryShore         // pte存在
204a17651b1SMemoryShore         if let Some(mut entry) = mapper.get_entry(address, 0) {
205a17651b1SMemoryShore             if !entry.present() {
206*cf7f801eSMemoryShore                 ret = Self::do_swap_page(pfm);
207a17651b1SMemoryShore             }
208*cf7f801eSMemoryShore 
209a17651b1SMemoryShore             if entry.protnone() && vma.is_accessible() {
210*cf7f801eSMemoryShore                 ret = Self::do_numa_page(pfm);
211a17651b1SMemoryShore             }
212*cf7f801eSMemoryShore 
213a17651b1SMemoryShore             if flags.intersects(FaultFlags::FAULT_FLAG_WRITE | FaultFlags::FAULT_FLAG_UNSHARE) {
214a17651b1SMemoryShore                 if !entry.write() {
215*cf7f801eSMemoryShore                     ret = Self::do_wp_page(pfm);
216a17651b1SMemoryShore                 } else {
217*cf7f801eSMemoryShore                     entry.set_flags(EntryFlags::from_data(MMArch::ENTRY_FLAG_DIRTY));
218a17651b1SMemoryShore                 }
219a17651b1SMemoryShore             }
220a17651b1SMemoryShore         } else if vma.is_anonymous() {
221*cf7f801eSMemoryShore             ret = Self::do_anonymous_page(pfm);
222a17651b1SMemoryShore         } else {
223*cf7f801eSMemoryShore             ret = Self::do_fault(pfm);
224a17651b1SMemoryShore         }
225a17651b1SMemoryShore 
226*cf7f801eSMemoryShore         vma.lock_irqsave().set_mapped(true);
22717dc5589SMemoryShore 
22817dc5589SMemoryShore         return ret;
229a17651b1SMemoryShore     }
230a17651b1SMemoryShore 
231a17651b1SMemoryShore     /// 处理匿名映射页缺页异常
232a17651b1SMemoryShore     /// ## 参数
233a17651b1SMemoryShore     ///
234a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
235a17651b1SMemoryShore     /// - `mapper`: 页表映射器
236a17651b1SMemoryShore     ///
237a17651b1SMemoryShore     /// ## 返回值
238a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_anonymous_page(pfm: &mut PageFaultMessage) -> VmFaultReason239*cf7f801eSMemoryShore     pub unsafe fn do_anonymous_page(pfm: &mut PageFaultMessage) -> VmFaultReason {
240a17651b1SMemoryShore         let address = pfm.address_aligned_down();
241a17651b1SMemoryShore         let vma = pfm.vma.clone();
242*cf7f801eSMemoryShore         let guard = vma.lock_irqsave();
243*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
244*cf7f801eSMemoryShore 
245a17651b1SMemoryShore         if let Some(flush) = mapper.map(address, guard.flags()) {
246a17651b1SMemoryShore             flush.flush();
247a17651b1SMemoryShore             crate::debug::klog::mm::mm_debug_log(
248a17651b1SMemoryShore                 klog_types::AllocatorLogType::LazyAlloc(klog_types::AllocLogItem::new(
249a17651b1SMemoryShore                     Layout::from_size_align(MMArch::PAGE_SIZE, MMArch::PAGE_SIZE).unwrap(),
250a17651b1SMemoryShore                     Some(address.data()),
251a17651b1SMemoryShore                     Some(mapper.translate(address).unwrap().0.data()),
252a17651b1SMemoryShore                 )),
253a17651b1SMemoryShore                 klog_types::LogSource::Buddy,
254a17651b1SMemoryShore             );
255a17651b1SMemoryShore             let paddr = mapper.translate(address).unwrap().0;
256*cf7f801eSMemoryShore             let mut page_manager_guard = page_manager_lock_irqsave();
257*cf7f801eSMemoryShore             let page = page_manager_guard.get_unwrap(&paddr);
258*cf7f801eSMemoryShore             page.write_irqsave().insert_vma(vma.clone());
259a17651b1SMemoryShore             VmFaultReason::VM_FAULT_COMPLETED
260a17651b1SMemoryShore         } else {
261a17651b1SMemoryShore             VmFaultReason::VM_FAULT_OOM
262a17651b1SMemoryShore         }
263a17651b1SMemoryShore     }
264a17651b1SMemoryShore 
265a17651b1SMemoryShore     /// 处理文件映射页的缺页异常
266a17651b1SMemoryShore     /// ## 参数
267a17651b1SMemoryShore     ///
268a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
269a17651b1SMemoryShore     /// - `mapper`: 页表映射器
270a17651b1SMemoryShore     ///
271a17651b1SMemoryShore     /// ## 返回值
272a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_fault(pfm: &mut PageFaultMessage) -> VmFaultReason273*cf7f801eSMemoryShore     pub unsafe fn do_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
274*cf7f801eSMemoryShore         if !pfm.flags().contains(FaultFlags::FAULT_FLAG_WRITE) {
275*cf7f801eSMemoryShore             return Self::do_read_fault(pfm);
276*cf7f801eSMemoryShore         } else if !pfm
277*cf7f801eSMemoryShore             .vma()
278*cf7f801eSMemoryShore             .lock_irqsave()
279*cf7f801eSMemoryShore             .vm_flags()
280*cf7f801eSMemoryShore             .contains(VmFlags::VM_SHARED)
281*cf7f801eSMemoryShore         {
282*cf7f801eSMemoryShore             return Self::do_cow_fault(pfm);
283*cf7f801eSMemoryShore         } else {
284*cf7f801eSMemoryShore             return Self::do_shared_fault(pfm);
285*cf7f801eSMemoryShore         }
286a17651b1SMemoryShore     }
287a17651b1SMemoryShore 
288a17651b1SMemoryShore     /// 处理私有文件映射的写时复制
289a17651b1SMemoryShore     /// ## 参数
290a17651b1SMemoryShore     ///
291a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
292a17651b1SMemoryShore     /// - `mapper`: 页表映射器
293a17651b1SMemoryShore     ///
294a17651b1SMemoryShore     /// ## 返回值
295a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_cow_fault(pfm: &mut PageFaultMessage) -> VmFaultReason296*cf7f801eSMemoryShore     pub unsafe fn do_cow_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
297*cf7f801eSMemoryShore         let mut ret = Self::filemap_fault(pfm);
298*cf7f801eSMemoryShore 
299*cf7f801eSMemoryShore         if unlikely(ret.intersects(
300*cf7f801eSMemoryShore             VmFaultReason::VM_FAULT_ERROR
301*cf7f801eSMemoryShore                 | VmFaultReason::VM_FAULT_NOPAGE
302*cf7f801eSMemoryShore                 | VmFaultReason::VM_FAULT_RETRY
303*cf7f801eSMemoryShore                 | VmFaultReason::VM_FAULT_DONE_COW,
304*cf7f801eSMemoryShore         )) {
305*cf7f801eSMemoryShore             return ret;
306*cf7f801eSMemoryShore         }
307*cf7f801eSMemoryShore 
308*cf7f801eSMemoryShore         let cache_page = pfm.page.clone().unwrap();
309*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
310*cf7f801eSMemoryShore 
311*cf7f801eSMemoryShore         let cow_page_phys = mapper.allocator_mut().allocate_one();
312*cf7f801eSMemoryShore         if cow_page_phys.is_none() {
313*cf7f801eSMemoryShore             return VmFaultReason::VM_FAULT_OOM;
314*cf7f801eSMemoryShore         }
315*cf7f801eSMemoryShore         let cow_page_phys = cow_page_phys.unwrap();
316*cf7f801eSMemoryShore 
317*cf7f801eSMemoryShore         let cow_page = Arc::new(Page::new(false, cow_page_phys));
318*cf7f801eSMemoryShore         pfm.cow_page = Some(cow_page.clone());
319*cf7f801eSMemoryShore 
320*cf7f801eSMemoryShore         //复制PageCache内容到新的页内
321*cf7f801eSMemoryShore         let new_frame = MMArch::phys_2_virt(cow_page_phys).unwrap();
322*cf7f801eSMemoryShore         (new_frame.data() as *mut u8).copy_from_nonoverlapping(
323*cf7f801eSMemoryShore             MMArch::phys_2_virt(cache_page.read_irqsave().phys_address())
324*cf7f801eSMemoryShore                 .unwrap()
325*cf7f801eSMemoryShore                 .data() as *mut u8,
326*cf7f801eSMemoryShore             MMArch::PAGE_SIZE,
327a17651b1SMemoryShore         );
328*cf7f801eSMemoryShore 
329*cf7f801eSMemoryShore         let mut page_manager_guard = page_manager_lock_irqsave();
330*cf7f801eSMemoryShore 
331*cf7f801eSMemoryShore         // 新页加入页管理器中
332*cf7f801eSMemoryShore         page_manager_guard.insert(cow_page_phys, &cow_page);
333*cf7f801eSMemoryShore         cow_page.write_irqsave().set_page_cache_index(
334*cf7f801eSMemoryShore             cache_page.read_irqsave().page_cache(),
335*cf7f801eSMemoryShore             cache_page.read_irqsave().index(),
336*cf7f801eSMemoryShore         );
337*cf7f801eSMemoryShore 
338*cf7f801eSMemoryShore         ret = ret.union(Self::finish_fault(pfm));
339*cf7f801eSMemoryShore 
340*cf7f801eSMemoryShore         ret
341a17651b1SMemoryShore     }
342a17651b1SMemoryShore 
343a17651b1SMemoryShore     /// 处理文件映射页的缺页异常
344a17651b1SMemoryShore     /// ## 参数
345a17651b1SMemoryShore     ///
346a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
347a17651b1SMemoryShore     /// - `mapper`: 页表映射器
348a17651b1SMemoryShore     ///
349a17651b1SMemoryShore     /// ## 返回值
350a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_read_fault(pfm: &mut PageFaultMessage) -> VmFaultReason351*cf7f801eSMemoryShore     pub unsafe fn do_read_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
352*cf7f801eSMemoryShore         let fs = pfm.vma().lock_irqsave().vm_file().unwrap().inode().fs();
353*cf7f801eSMemoryShore 
354*cf7f801eSMemoryShore         let mut ret = Self::do_fault_around(pfm);
355*cf7f801eSMemoryShore         if !ret.is_empty() {
356*cf7f801eSMemoryShore             return ret;
357*cf7f801eSMemoryShore         }
358*cf7f801eSMemoryShore 
359*cf7f801eSMemoryShore         ret = fs.fault(pfm);
360*cf7f801eSMemoryShore 
361*cf7f801eSMemoryShore         ret = ret.union(Self::finish_fault(pfm));
362*cf7f801eSMemoryShore 
363*cf7f801eSMemoryShore         ret
364a17651b1SMemoryShore     }
365a17651b1SMemoryShore 
366a17651b1SMemoryShore     /// 处理对共享文件映射区写入引起的缺页
367a17651b1SMemoryShore     /// ## 参数
368a17651b1SMemoryShore     ///
369a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
370a17651b1SMemoryShore     /// - `mapper`: 页表映射器
371a17651b1SMemoryShore     ///
372a17651b1SMemoryShore     /// ## 返回值
373a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_shared_fault(pfm: &mut PageFaultMessage) -> VmFaultReason374*cf7f801eSMemoryShore     pub unsafe fn do_shared_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
375*cf7f801eSMemoryShore         let mut ret = Self::filemap_fault(pfm);
376*cf7f801eSMemoryShore 
377*cf7f801eSMemoryShore         let cache_page = pfm.page.clone().expect("no cache_page in PageFaultMessage");
378*cf7f801eSMemoryShore 
379*cf7f801eSMemoryShore         // 将pagecache页设为脏页,以便回收时能够回写
380*cf7f801eSMemoryShore         cache_page.write_irqsave().add_flags(PageFlags::PG_DIRTY);
381*cf7f801eSMemoryShore         ret = ret.union(Self::finish_fault(pfm));
382*cf7f801eSMemoryShore 
383*cf7f801eSMemoryShore         ret
384a17651b1SMemoryShore     }
385a17651b1SMemoryShore 
386a17651b1SMemoryShore     /// 处理被置换页面的缺页异常
387a17651b1SMemoryShore     /// ## 参数
388a17651b1SMemoryShore     ///
389a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
390a17651b1SMemoryShore     /// - `mapper`: 页表映射器
391a17651b1SMemoryShore     ///
392a17651b1SMemoryShore     /// ## 返回值
393a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
394a17651b1SMemoryShore     #[allow(unused_variables)]
do_swap_page(pfm: &mut PageFaultMessage) -> VmFaultReason395*cf7f801eSMemoryShore     pub unsafe fn do_swap_page(pfm: &mut PageFaultMessage) -> VmFaultReason {
396a17651b1SMemoryShore         panic!(
397a17651b1SMemoryShore             "do_swap_page has not yet been implemented,
398a17651b1SMemoryShore         fault message: {:?},
399a17651b1SMemoryShore         pid: {}\n",
400a17651b1SMemoryShore             pfm,
401a17651b1SMemoryShore             crate::process::ProcessManager::current_pid().data()
402a17651b1SMemoryShore         );
403a17651b1SMemoryShore         // TODO https://code.dragonos.org.cn/xref/linux-6.6.21/mm/memory.c#do_swap_page
404a17651b1SMemoryShore     }
405a17651b1SMemoryShore 
406a17651b1SMemoryShore     /// 处理NUMA的缺页异常
407a17651b1SMemoryShore     /// ## 参数
408a17651b1SMemoryShore     ///
409a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
410a17651b1SMemoryShore     /// - `mapper`: 页表映射器
411a17651b1SMemoryShore     ///
412a17651b1SMemoryShore     /// ## 返回值
413a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
414a17651b1SMemoryShore     #[allow(unused_variables)]
do_numa_page(pfm: &mut PageFaultMessage) -> VmFaultReason415*cf7f801eSMemoryShore     pub unsafe fn do_numa_page(pfm: &mut PageFaultMessage) -> VmFaultReason {
416a17651b1SMemoryShore         panic!(
417a17651b1SMemoryShore             "do_numa_page has not yet been implemented,
418a17651b1SMemoryShore         fault message: {:?},
419a17651b1SMemoryShore         pid: {}\n",
420a17651b1SMemoryShore             pfm,
421a17651b1SMemoryShore             crate::process::ProcessManager::current_pid().data()
422a17651b1SMemoryShore         );
423a17651b1SMemoryShore         // TODO https://code.dragonos.org.cn/xref/linux-6.6.21/mm/memory.c#do_numa_page
424a17651b1SMemoryShore     }
425a17651b1SMemoryShore 
426a17651b1SMemoryShore     /// 处理写保护页面的写保护异常
427a17651b1SMemoryShore     /// ## 参数
428a17651b1SMemoryShore     ///
429a17651b1SMemoryShore     /// - `pfm`: 缺页异常信息
430a17651b1SMemoryShore     /// - `mapper`: 页表映射器
431a17651b1SMemoryShore     ///
432a17651b1SMemoryShore     /// ## 返回值
433a17651b1SMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_wp_page(pfm: &mut PageFaultMessage) -> VmFaultReason434*cf7f801eSMemoryShore     pub unsafe fn do_wp_page(pfm: &mut PageFaultMessage) -> VmFaultReason {
435a17651b1SMemoryShore         let address = pfm.address_aligned_down();
436a17651b1SMemoryShore         let vma = pfm.vma.clone();
437*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
438*cf7f801eSMemoryShore 
439a17651b1SMemoryShore         let old_paddr = mapper.translate(address).unwrap().0;
440a17651b1SMemoryShore         let mut page_manager = page_manager_lock_irqsave();
441*cf7f801eSMemoryShore         let old_page = page_manager.get_unwrap(&old_paddr);
442*cf7f801eSMemoryShore         let map_count = old_page.read_irqsave().map_count();
443a17651b1SMemoryShore         drop(page_manager);
444a17651b1SMemoryShore 
445a17651b1SMemoryShore         let mut entry = mapper.get_entry(address, 0).unwrap();
446*cf7f801eSMemoryShore         let new_flags = entry.flags().set_write(true).set_dirty(true);
447a17651b1SMemoryShore 
448*cf7f801eSMemoryShore         if vma.lock().vm_flags().contains(VmFlags::VM_SHARED) {
449*cf7f801eSMemoryShore             // 共享映射,直接修改页表项保护位,标记为脏页
450*cf7f801eSMemoryShore             let table = mapper.get_table(address, 0).unwrap();
451*cf7f801eSMemoryShore             let i = table.index_of(address).unwrap();
452*cf7f801eSMemoryShore             entry.set_flags(new_flags);
453*cf7f801eSMemoryShore             table.set_entry(i, entry);
454*cf7f801eSMemoryShore 
455*cf7f801eSMemoryShore             old_page.write_irqsave().add_flags(PageFlags::PG_DIRTY);
456*cf7f801eSMemoryShore 
457*cf7f801eSMemoryShore             VmFaultReason::VM_FAULT_COMPLETED
458*cf7f801eSMemoryShore         } else if vma.is_anonymous() {
459*cf7f801eSMemoryShore             // 私有匿名映射,根据引用计数判断是否拷贝页面
460a17651b1SMemoryShore             if map_count == 1 {
461a17651b1SMemoryShore                 let table = mapper.get_table(address, 0).unwrap();
462a17651b1SMemoryShore                 let i = table.index_of(address).unwrap();
463a17651b1SMemoryShore                 entry.set_flags(new_flags);
464a17651b1SMemoryShore                 table.set_entry(i, entry);
465a17651b1SMemoryShore                 VmFaultReason::VM_FAULT_COMPLETED
466a17651b1SMemoryShore             } else if let Some(flush) = mapper.map(address, new_flags) {
467*cf7f801eSMemoryShore                 let mut page_manager_guard = page_manager_lock_irqsave();
468*cf7f801eSMemoryShore                 let old_page = page_manager_guard.get_unwrap(&old_paddr);
469*cf7f801eSMemoryShore                 old_page.write_irqsave().remove_vma(&vma);
470*cf7f801eSMemoryShore                 // drop(page_manager_guard);
471a17651b1SMemoryShore 
472a17651b1SMemoryShore                 flush.flush();
473a17651b1SMemoryShore                 let paddr = mapper.translate(address).unwrap().0;
474*cf7f801eSMemoryShore                 // let mut page_manager_guard = page_manager_lock_irqsave();
475*cf7f801eSMemoryShore                 let page = page_manager_guard.get_unwrap(&paddr);
476*cf7f801eSMemoryShore                 page.write_irqsave().insert_vma(vma.clone());
477a17651b1SMemoryShore 
478a17651b1SMemoryShore                 (MMArch::phys_2_virt(paddr).unwrap().data() as *mut u8).copy_from_nonoverlapping(
479a17651b1SMemoryShore                     MMArch::phys_2_virt(old_paddr).unwrap().data() as *mut u8,
480a17651b1SMemoryShore                     MMArch::PAGE_SIZE,
481a17651b1SMemoryShore                 );
482a17651b1SMemoryShore 
483a17651b1SMemoryShore                 VmFaultReason::VM_FAULT_COMPLETED
484a17651b1SMemoryShore             } else {
485a17651b1SMemoryShore                 VmFaultReason::VM_FAULT_OOM
486a17651b1SMemoryShore             }
487*cf7f801eSMemoryShore         } else {
488*cf7f801eSMemoryShore             // 私有文件映射,必须拷贝页面
489*cf7f801eSMemoryShore             if let Some(flush) = mapper.map(address, new_flags) {
490*cf7f801eSMemoryShore                 let mut page_manager_guard = page_manager_lock_irqsave();
491*cf7f801eSMemoryShore                 let old_page = page_manager_guard.get_unwrap(&old_paddr);
492*cf7f801eSMemoryShore                 old_page.write_irqsave().remove_vma(&vma);
493*cf7f801eSMemoryShore                 // drop(page_manager_guard);
494*cf7f801eSMemoryShore 
495*cf7f801eSMemoryShore                 flush.flush();
496*cf7f801eSMemoryShore                 let paddr = mapper.translate(address).unwrap().0;
497*cf7f801eSMemoryShore                 // let mut page_manager_guard = page_manager_lock_irqsave();
498*cf7f801eSMemoryShore                 let page = page_manager_guard.get_unwrap(&paddr);
499*cf7f801eSMemoryShore                 page.write_irqsave().insert_vma(vma.clone());
500*cf7f801eSMemoryShore 
501*cf7f801eSMemoryShore                 (MMArch::phys_2_virt(paddr).unwrap().data() as *mut u8).copy_from_nonoverlapping(
502*cf7f801eSMemoryShore                     MMArch::phys_2_virt(old_paddr).unwrap().data() as *mut u8,
503*cf7f801eSMemoryShore                     MMArch::PAGE_SIZE,
504*cf7f801eSMemoryShore                 );
505*cf7f801eSMemoryShore 
506*cf7f801eSMemoryShore                 VmFaultReason::VM_FAULT_COMPLETED
507*cf7f801eSMemoryShore             } else {
508*cf7f801eSMemoryShore                 VmFaultReason::VM_FAULT_OOM
509*cf7f801eSMemoryShore             }
510*cf7f801eSMemoryShore         }
511*cf7f801eSMemoryShore     }
512*cf7f801eSMemoryShore 
513*cf7f801eSMemoryShore     /// 缺页附近页预读
514*cf7f801eSMemoryShore     /// ## 参数
515*cf7f801eSMemoryShore     ///
516*cf7f801eSMemoryShore     /// - `pfm`: 缺页异常信息
517*cf7f801eSMemoryShore     /// - `mapper`: 页表映射器
518*cf7f801eSMemoryShore     ///
519*cf7f801eSMemoryShore     /// ## 返回值
520*cf7f801eSMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
do_fault_around(pfm: &mut PageFaultMessage) -> VmFaultReason521*cf7f801eSMemoryShore     pub unsafe fn do_fault_around(pfm: &mut PageFaultMessage) -> VmFaultReason {
522*cf7f801eSMemoryShore         let vma = pfm.vma();
523*cf7f801eSMemoryShore         let address = pfm.address();
524*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
525*cf7f801eSMemoryShore 
526*cf7f801eSMemoryShore         if mapper.get_table(address, 0).is_none() {
527*cf7f801eSMemoryShore             mapper
528*cf7f801eSMemoryShore                 .allocate_table(address, 0)
529*cf7f801eSMemoryShore                 .expect("failed to allocate pte table");
530*cf7f801eSMemoryShore         }
531*cf7f801eSMemoryShore         let vma_guard = vma.lock_irqsave();
532*cf7f801eSMemoryShore         let vma_region = *vma_guard.region();
533*cf7f801eSMemoryShore         drop(vma_guard);
534*cf7f801eSMemoryShore 
535*cf7f801eSMemoryShore         // 缺页在VMA中的偏移量
536*cf7f801eSMemoryShore         let vm_pgoff = (address - vma_region.start()) >> MMArch::PAGE_SHIFT;
537*cf7f801eSMemoryShore 
538*cf7f801eSMemoryShore         // 缺页在PTE中的偏移量
539*cf7f801eSMemoryShore         let pte_pgoff = (address.data() >> MMArch::PAGE_SHIFT) & (1 << MMArch::PAGE_ENTRY_SHIFT);
540*cf7f801eSMemoryShore 
541*cf7f801eSMemoryShore         // 缺页在文件中的偏移量
542*cf7f801eSMemoryShore         let file_pgoff = pfm.file_pgoff.expect("no file_pgoff");
543*cf7f801eSMemoryShore 
544*cf7f801eSMemoryShore         let vma_pages_count = (vma_region.end() - vma_region.start()) >> MMArch::PAGE_SHIFT;
545*cf7f801eSMemoryShore 
546*cf7f801eSMemoryShore         let fault_around_page_number = 16;
547*cf7f801eSMemoryShore 
548*cf7f801eSMemoryShore         // 开始位置不能超出当前pte和vma头部
549*cf7f801eSMemoryShore         let from_pte = max(
550*cf7f801eSMemoryShore             align_down(pte_pgoff, fault_around_page_number),
551*cf7f801eSMemoryShore             pte_pgoff - min(vm_pgoff, pte_pgoff),
552*cf7f801eSMemoryShore         );
553*cf7f801eSMemoryShore 
554*cf7f801eSMemoryShore         // pte结束位置不能超过:
555*cf7f801eSMemoryShore         // 1.最大预读上限(默认16)
556*cf7f801eSMemoryShore         // 2.最大pte(512)
557*cf7f801eSMemoryShore         // 3.vma结束位置(pte_pgoff + (vma_pages_count - vm_pgoff)计算出vma结束页号对当前pte开头的偏移)
558*cf7f801eSMemoryShore         let to_pte = min(
559*cf7f801eSMemoryShore             from_pte + fault_around_page_number,
560*cf7f801eSMemoryShore             min(
561*cf7f801eSMemoryShore                 1 << MMArch::PAGE_SHIFT,
562*cf7f801eSMemoryShore                 pte_pgoff + (vma_pages_count - vm_pgoff),
563*cf7f801eSMemoryShore             ),
564*cf7f801eSMemoryShore         );
565*cf7f801eSMemoryShore 
566*cf7f801eSMemoryShore         // 预先分配pte页表(如果不存在)
567*cf7f801eSMemoryShore         if mapper.get_table(address, 0).is_none() && mapper.allocate_table(address, 0).is_none() {
568*cf7f801eSMemoryShore             return VmFaultReason::VM_FAULT_OOM;
569*cf7f801eSMemoryShore         }
570*cf7f801eSMemoryShore 
571*cf7f801eSMemoryShore         let fs = pfm.vma().lock_irqsave().vm_file().unwrap().inode().fs();
572*cf7f801eSMemoryShore         // from_pte - pte_pgoff得出预读起始pte相对缺失页的偏移,加上pfm.file_pgoff(缺失页在文件中的偏移)得出起始页在文件中的偏移,结束pte同理
573*cf7f801eSMemoryShore         fs.map_pages(
574*cf7f801eSMemoryShore             pfm,
575*cf7f801eSMemoryShore             file_pgoff + (from_pte - pte_pgoff),
576*cf7f801eSMemoryShore             file_pgoff + (to_pte - pte_pgoff),
577*cf7f801eSMemoryShore         );
578*cf7f801eSMemoryShore 
579*cf7f801eSMemoryShore         VmFaultReason::empty()
580*cf7f801eSMemoryShore     }
581*cf7f801eSMemoryShore 
582*cf7f801eSMemoryShore     /// 通用的VMA文件映射页面映射函数,将PageCache中的页面映射到进程空间
583*cf7f801eSMemoryShore     /// ## 参数
584*cf7f801eSMemoryShore     ///
585*cf7f801eSMemoryShore     /// - `pfm`: 缺页异常信息
586*cf7f801eSMemoryShore     /// - `mapper`: 页表映射器
587*cf7f801eSMemoryShore     ///
588*cf7f801eSMemoryShore     /// ## 返回值
589*cf7f801eSMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
filemap_map_pages( pfm: &mut PageFaultMessage, start_pgoff: usize, end_pgoff: usize, ) -> VmFaultReason590*cf7f801eSMemoryShore     pub unsafe fn filemap_map_pages(
591*cf7f801eSMemoryShore         pfm: &mut PageFaultMessage,
592*cf7f801eSMemoryShore 
593*cf7f801eSMemoryShore         start_pgoff: usize,
594*cf7f801eSMemoryShore         end_pgoff: usize,
595*cf7f801eSMemoryShore     ) -> VmFaultReason {
596*cf7f801eSMemoryShore         let vma = pfm.vma();
597*cf7f801eSMemoryShore         let vma_guard = vma.lock_irqsave();
598*cf7f801eSMemoryShore         let file = vma_guard.vm_file().expect("no vm_file in vma");
599*cf7f801eSMemoryShore         let page_cache = file.inode().page_cache().unwrap();
600*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
601*cf7f801eSMemoryShore 
602*cf7f801eSMemoryShore         // 起始页地址
603*cf7f801eSMemoryShore         let addr = vma_guard.region().start
604*cf7f801eSMemoryShore             + ((start_pgoff
605*cf7f801eSMemoryShore                 - vma_guard
606*cf7f801eSMemoryShore                     .file_page_offset()
607*cf7f801eSMemoryShore                     .expect("file_page_offset is none"))
608*cf7f801eSMemoryShore                 << MMArch::PAGE_SHIFT);
609*cf7f801eSMemoryShore 
610*cf7f801eSMemoryShore         for pgoff in start_pgoff..=end_pgoff {
611*cf7f801eSMemoryShore             if let Some(page) = page_cache.get_page(pgoff) {
612*cf7f801eSMemoryShore                 let page_guard = page.read_irqsave();
613*cf7f801eSMemoryShore                 if page_guard.flags().contains(PageFlags::PG_UPTODATE) {
614*cf7f801eSMemoryShore                     let phys = page_guard.phys_address();
615*cf7f801eSMemoryShore 
616*cf7f801eSMemoryShore                     let address =
617*cf7f801eSMemoryShore                         VirtAddr::new(addr.data() + ((pgoff - start_pgoff) << MMArch::PAGE_SHIFT));
618*cf7f801eSMemoryShore                     mapper
619*cf7f801eSMemoryShore                         .map_phys(address, phys, vma_guard.flags())
620*cf7f801eSMemoryShore                         .unwrap()
621*cf7f801eSMemoryShore                         .flush();
622*cf7f801eSMemoryShore                 }
623*cf7f801eSMemoryShore             }
624*cf7f801eSMemoryShore         }
625*cf7f801eSMemoryShore         VmFaultReason::empty()
626*cf7f801eSMemoryShore     }
627*cf7f801eSMemoryShore 
628*cf7f801eSMemoryShore     /// 通用的VMA文件映射错误处理函数
629*cf7f801eSMemoryShore     /// ## 参数
630*cf7f801eSMemoryShore     ///
631*cf7f801eSMemoryShore     /// - `pfm`: 缺页异常信息
632*cf7f801eSMemoryShore     /// - `mapper`: 页表映射器
633*cf7f801eSMemoryShore     ///
634*cf7f801eSMemoryShore     /// ## 返回值
635*cf7f801eSMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
filemap_fault(pfm: &mut PageFaultMessage) -> VmFaultReason636*cf7f801eSMemoryShore     pub unsafe fn filemap_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
637*cf7f801eSMemoryShore         let vma = pfm.vma();
638*cf7f801eSMemoryShore         let vma_guard = vma.lock_irqsave();
639*cf7f801eSMemoryShore         let file = vma_guard.vm_file().expect("no vm_file in vma");
640*cf7f801eSMemoryShore         let page_cache = file.inode().page_cache().unwrap();
641*cf7f801eSMemoryShore         let file_pgoff = pfm.file_pgoff.expect("no file_pgoff");
642*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
643*cf7f801eSMemoryShore         let mut ret = VmFaultReason::empty();
644*cf7f801eSMemoryShore 
645*cf7f801eSMemoryShore         if let Some(page) = page_cache.get_page(file_pgoff) {
646*cf7f801eSMemoryShore             // TODO 异步从磁盘中预读页面进PageCache
647*cf7f801eSMemoryShore 
648*cf7f801eSMemoryShore             // 直接将PageCache中的页面作为要映射的页面
649*cf7f801eSMemoryShore             pfm.page = Some(page.clone());
650*cf7f801eSMemoryShore         } else {
651*cf7f801eSMemoryShore             // TODO 同步预读
652*cf7f801eSMemoryShore             //涉及磁盘IO,返回标志为VM_FAULT_MAJOR
653*cf7f801eSMemoryShore             ret = VmFaultReason::VM_FAULT_MAJOR;
654*cf7f801eSMemoryShore             // let mut buf: Vec<u8> = vec![0; MMArch::PAGE_SIZE];
655*cf7f801eSMemoryShore 
656*cf7f801eSMemoryShore             let allocator = mapper.allocator_mut();
657*cf7f801eSMemoryShore 
658*cf7f801eSMemoryShore             // 分配一个物理页面作为加入PageCache的新页
659*cf7f801eSMemoryShore             let new_cache_page = allocator.allocate_one().unwrap();
660*cf7f801eSMemoryShore             // (MMArch::phys_2_virt(new_cache_page).unwrap().data() as *mut u8)
661*cf7f801eSMemoryShore             //     .copy_from_nonoverlapping(buf.as_mut_ptr(), MMArch::PAGE_SIZE);
662*cf7f801eSMemoryShore             file.pread(
663*cf7f801eSMemoryShore                 file_pgoff * MMArch::PAGE_SIZE,
664*cf7f801eSMemoryShore                 MMArch::PAGE_SIZE,
665*cf7f801eSMemoryShore                 core::slice::from_raw_parts_mut(
666*cf7f801eSMemoryShore                     MMArch::phys_2_virt(new_cache_page).unwrap().data() as *mut u8,
667*cf7f801eSMemoryShore                     MMArch::PAGE_SIZE,
668*cf7f801eSMemoryShore                 ),
669*cf7f801eSMemoryShore             )
670*cf7f801eSMemoryShore             .expect("failed to read file to create pagecache page");
671*cf7f801eSMemoryShore 
672*cf7f801eSMemoryShore             let page = Arc::new(Page::new(true, new_cache_page));
673*cf7f801eSMemoryShore             pfm.page = Some(page.clone());
674*cf7f801eSMemoryShore 
675*cf7f801eSMemoryShore             page.write_irqsave().add_flags(PageFlags::PG_LRU);
676*cf7f801eSMemoryShore             page_manager_lock_irqsave().insert(new_cache_page, &page);
677*cf7f801eSMemoryShore             page_reclaimer_lock_irqsave().insert_page(new_cache_page, &page);
678*cf7f801eSMemoryShore             page_cache.add_page(file_pgoff, &page);
679*cf7f801eSMemoryShore 
680*cf7f801eSMemoryShore             page.write_irqsave()
681*cf7f801eSMemoryShore                 .set_page_cache_index(Some(page_cache), Some(file_pgoff));
682*cf7f801eSMemoryShore         }
683*cf7f801eSMemoryShore         ret
684*cf7f801eSMemoryShore     }
685*cf7f801eSMemoryShore 
686*cf7f801eSMemoryShore     /// 将文件页映射到缺页地址
687*cf7f801eSMemoryShore     /// ## 参数
688*cf7f801eSMemoryShore     ///
689*cf7f801eSMemoryShore     /// - `pfm`: 缺页异常信息
690*cf7f801eSMemoryShore     /// - `mapper`: 页表映射器
691*cf7f801eSMemoryShore     ///
692*cf7f801eSMemoryShore     /// ## 返回值
693*cf7f801eSMemoryShore     /// - VmFaultReason: 页面错误处理信息标志
finish_fault(pfm: &mut PageFaultMessage) -> VmFaultReason694*cf7f801eSMemoryShore     pub unsafe fn finish_fault(pfm: &mut PageFaultMessage) -> VmFaultReason {
695*cf7f801eSMemoryShore         let vma = pfm.vma();
696*cf7f801eSMemoryShore         let vma_guard = vma.lock_irqsave();
697*cf7f801eSMemoryShore         let flags = pfm.flags();
698*cf7f801eSMemoryShore         let cache_page = pfm.page.clone();
699*cf7f801eSMemoryShore         let cow_page = pfm.cow_page.clone();
700*cf7f801eSMemoryShore         let address = pfm.address();
701*cf7f801eSMemoryShore         let mapper = &mut pfm.mapper;
702*cf7f801eSMemoryShore 
703*cf7f801eSMemoryShore         let page_to_map = if flags.contains(FaultFlags::FAULT_FLAG_WRITE)
704*cf7f801eSMemoryShore             && !vma_guard.vm_flags().contains(VmFlags::VM_SHARED)
705*cf7f801eSMemoryShore         {
706*cf7f801eSMemoryShore             // 私有文件映射的写时复制
707*cf7f801eSMemoryShore             cow_page.expect("no cow_page in PageFaultMessage")
708*cf7f801eSMemoryShore         } else {
709*cf7f801eSMemoryShore             // 直接映射到PageCache
710*cf7f801eSMemoryShore             cache_page.expect("no cache_page in PageFaultMessage")
711*cf7f801eSMemoryShore         };
712*cf7f801eSMemoryShore 
713*cf7f801eSMemoryShore         let page_phys = page_to_map.read_irqsave().phys_address();
714*cf7f801eSMemoryShore 
715*cf7f801eSMemoryShore         mapper.map_phys(address, page_phys, vma_guard.flags());
716*cf7f801eSMemoryShore         page_to_map.write_irqsave().insert_vma(pfm.vma());
717*cf7f801eSMemoryShore         VmFaultReason::VM_FAULT_COMPLETED
718a17651b1SMemoryShore     }
719a17651b1SMemoryShore }
720