Merge tag 'perf_urgent_for_v6.1_rc6' of git://git.kernel.org/pub/scm/linux/kernel...
[platform/kernel/linux-starfive.git] / mm / memory.c
index df678fa..f88c351 100644 (file)
@@ -1393,10 +1393,12 @@ zap_install_uffd_wp_if_needed(struct vm_area_struct *vma,
                              unsigned long addr, pte_t *pte,
                              struct zap_details *details, pte_t pteval)
 {
+#ifdef CONFIG_PTE_MARKER_UFFD_WP
        if (zap_drop_file_uffd_wp(details))
                return;
 
        pte_install_uffd_wp_if_needed(vma, addr, pte, pteval);
+#endif
 }
 
 static unsigned long zap_pte_range(struct mmu_gather *tlb,
@@ -3748,7 +3750,21 @@ vm_fault_t do_swap_page(struct vm_fault *vmf)
                        ret = remove_device_exclusive_entry(vmf);
                } else if (is_device_private_entry(entry)) {
                        vmf->page = pfn_swap_entry_to_page(entry);
-                       ret = vmf->page->pgmap->ops->migrate_to_ram(vmf);
+                       vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd,
+                                       vmf->address, &vmf->ptl);
+                       if (unlikely(!pte_same(*vmf->pte, vmf->orig_pte))) {
+                               spin_unlock(vmf->ptl);
+                               goto out;
+                       }
+
+                       /*
+                        * Get a page reference while we know the page can't be
+                        * freed.
+                        */
+                       get_page(vmf->page);
+                       pte_unmap_unlock(vmf->pte, vmf->ptl);
+                       vmf->page->pgmap->ops->migrate_to_ram(vmf);
+                       put_page(vmf->page);
                } else if (is_hwpoison_entry(entry)) {
                        ret = VM_FAULT_HWPOISON;
                } else if (is_swapin_error_entry(entry)) {
@@ -4118,7 +4134,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
        vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
                        &vmf->ptl);
        if (!pte_none(*vmf->pte)) {
-               update_mmu_cache(vma, vmf->address, vmf->pte);
+               update_mmu_tlb(vma, vmf->address, vmf->pte);
                goto release;
        }