diff --git a/mm/mmap.c b/mm/mmap.c index aa072afea2ee..eedd39382561 100644 --- a/mm/mmap.c +++ b/mm/mmap.c @@ -2347,22 +2347,8 @@ struct vm_area_struct *get_vma(struct mm_struct *mm, unsigned long addr) read_lock(&mm->mm_rb_lock); vma = __find_vma(mm, addr); - - /* - * If there is a concurrent fast mremap, bail out since the entire - * PMD/PUD subtree may have been remapped. - * - * This is usually safe for conventional mremap since it takes the - * PTE locks as does SPF. However fast mremap only takes the lock - * at the PMD/PUD level which is ok as it is done with the mmap - * write lock held. But since SPF, as the term implies forgoes, - * taking the mmap read lock and also cannot take PTL lock at the - * larger PMD/PUD granualrity, since it would introduce huge - * contention in the page fault path; fall back to regular fault - * handling. - */ - if (vma && !atomic_inc_unless_negative(&vma->vm_ref_count)) - vma = NULL; + if (vma) + atomic_inc(&vma->vm_ref_count); read_unlock(&mm->mm_rb_lock); return vma; diff --git a/mm/mremap.c b/mm/mremap.c index 4588c5d90884..f0064331dbd3 100644 --- a/mm/mremap.c +++ b/mm/mremap.c @@ -210,39 +210,11 @@ static void move_ptes(struct vm_area_struct *vma, pmd_t *old_pmd, drop_rmap_locks(vma); } -#ifdef CONFIG_SPECULATIVE_PAGE_FAULT -static inline bool trylock_vma_ref_count(struct vm_area_struct *vma) -{ - /* - * If we have the only reference, swap the refcount to -1. This - * will prevent other concurrent references by get_vma() for SPFs. - */ - return atomic_cmpxchg(&vma->vm_ref_count, 1, -1) == 1; -} - /* - * Restore the VMA reference count to 1 after a fast mremap. + * Speculative page fault handlers will not detect page table changes done + * without ptl locking. */ -static inline void unlock_vma_ref_count(struct vm_area_struct *vma) -{ - /* - * This should only be called after a corresponding, - * successful trylock_vma_ref_count(). - */ - VM_BUG_ON_VMA(atomic_cmpxchg(&vma->vm_ref_count, -1, 1) != -1, - vma); -} -#else /* !CONFIG_SPECULATIVE_PAGE_FAULT */ -static inline bool trylock_vma_ref_count(struct vm_area_struct *vma) -{ - return true; -} -static inline void unlock_vma_ref_count(struct vm_area_struct *vma) -{ -} -#endif /* CONFIG_SPECULATIVE_PAGE_FAULT */ - -#ifdef CONFIG_HAVE_MOVE_PMD +#if defined(CONFIG_HAVE_MOVE_PMD) && !defined(CONFIG_SPECULATIVE_PAGE_FAULT) static bool move_normal_pmd(struct vm_area_struct *vma, unsigned long old_addr, unsigned long new_addr, unsigned long old_end, pmd_t *old_pmd, pmd_t *new_pmd) @@ -262,14 +234,6 @@ static bool move_normal_pmd(struct vm_area_struct *vma, unsigned long old_addr, if (WARN_ON(!pmd_none(*new_pmd))) return false; - /* - * We hold both exclusive mmap_lock and rmap_lock at this point and - * cannot block. If we cannot immediately take exclusive ownership - * of the VMA fallback to the move_ptes(). - */ - if (!trylock_vma_ref_count(vma)) - return false; - /* * We don't have to worry about the ordering of src and dst * ptlocks because exclusive mmap_sem prevents deadlock. @@ -292,7 +256,6 @@ static bool move_normal_pmd(struct vm_area_struct *vma, unsigned long old_addr, spin_unlock(new_ptl); spin_unlock(old_ptl); - unlock_vma_ref_count(vma); return true; } #else