ANDROID: userfaultfd: Fix use-after-free in userfaultfd_using_sigbus()
In 582c6d188ec1 ("ANDROID: userfaultfd: allow SPF for UFFD_FEATURE_SIGBUS on private+anon"), we allowed userfaultfd registered VMAs using SIGBUS to be handled with SPF. But during page-fault handling, before userfaultfd_ctx is dereferenced, another thread may call userfaultfd_release(), unlink the VMA and then deallocate the same userfaultfd_ctx, leaving a dangling pointer behind for dereference. It is insufficient to do the access under rcu read-lock as the context may have been deallocated before entering the critical section. Checking vma has not changed in the critical section ensures we are not looking at dangling pointer to userfaultfd_ctx. Change-Id: I9c3ba0f1352e49f0ea387b92c18b5f1b5dcad7f1 Signed-off-by: Lokesh Gidra <lokeshgidra@google.com> Bug: 349936398 (cherry picked from commit c75b369e72da0283a20f794c0070c478b490f453)
This commit is contained in:
@@ -5058,6 +5058,7 @@ static vm_fault_t ___handle_speculative_fault(struct mm_struct *mm,
|
||||
|
||||
vmf.vma_flags = READ_ONCE(vmf.vma->vm_flags);
|
||||
vmf.vma_page_prot = READ_ONCE(vmf.vma->vm_page_prot);
|
||||
vmf.sequence = seq;
|
||||
|
||||
#ifdef CONFIG_USERFAULTFD
|
||||
/*
|
||||
@@ -5067,7 +5068,7 @@ static vm_fault_t ___handle_speculative_fault(struct mm_struct *mm,
|
||||
if (unlikely(vmf.vma_flags & __VM_UFFD_FLAGS)) {
|
||||
uffd_missing_sigbus = vma_is_anonymous(vmf.vma) &&
|
||||
(vmf.vma_flags & VM_UFFD_MISSING) &&
|
||||
userfaultfd_using_sigbus(vmf.vma);
|
||||
userfaultfd_using_sigbus(&vmf);
|
||||
if (!uffd_missing_sigbus) {
|
||||
trace_spf_vma_notsup(_RET_IP_, vmf.vma, address);
|
||||
return VM_FAULT_RETRY;
|
||||
@@ -5193,7 +5194,6 @@ static vm_fault_t ___handle_speculative_fault(struct mm_struct *mm,
|
||||
vmf.pte = NULL;
|
||||
}
|
||||
|
||||
vmf.sequence = seq;
|
||||
vmf.flags = flags;
|
||||
|
||||
local_irq_enable();
|
||||
|
Reference in New Issue
Block a user