mirror of
https://github.com/torvalds/linux.git
synced 2024-11-10 14:11:52 +00:00
mmap: fix vma_iterator in error path of vma_merge()
During the error path, the vma iterator may not be correctly positioned or
set to the correct range. Undo the vma_prev() call by resetting to the
passed in address. Re-walking to the same range will fix the range to the
area previously passed in.
Users would notice increased cycles as vma_merge() would be called an
extra time with vma == prev, and thus would fail to merge and return.
Link: https://lore.kernel.org/linux-mm/CAG48ez12VN1JAOtTNMY+Y2YnsU45yL5giS-Qn=ejtiHpgJAbdQ@mail.gmail.com/
Link: https://lkml.kernel.org/r/20230929183041.2835469-2-Liam.Howlett@oracle.com
Fixes: 18b098af28
("vma_merge: set vma iterator to correct position.")
Signed-off-by: Liam R. Howlett <Liam.Howlett@oracle.com>
Reported-by: Jann Horn <jannh@google.com>
Closes: https://lore.kernel.org/linux-mm/CAG48ez12VN1JAOtTNMY+Y2YnsU45yL5giS-Qn=ejtiHpgJAbdQ@mail.gmail.com/
Reviewed-by: Lorenzo Stoakes <lstoakes@gmail.com>
Acked-by: Vlastimil Babka <vbabka@suse.cz>
Cc: Matthew Wilcox (Oracle) <willy@infradead.org>
Cc: Suren Baghdasaryan <surenb@google.com>
Cc: <stable@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
This commit is contained in:
parent
e0f81ab1e4
commit
1419430c8a
10
mm/mmap.c
10
mm/mmap.c
@ -975,7 +975,7 @@ struct vm_area_struct *vma_merge(struct vma_iterator *vmi, struct mm_struct *mm,
|
||||
|
||||
/* Error in anon_vma clone. */
|
||||
if (err)
|
||||
return NULL;
|
||||
goto anon_vma_fail;
|
||||
|
||||
if (vma_start < vma->vm_start || vma_end > vma->vm_end)
|
||||
vma_expanded = true;
|
||||
@ -988,7 +988,7 @@ struct vm_area_struct *vma_merge(struct vma_iterator *vmi, struct mm_struct *mm,
|
||||
}
|
||||
|
||||
if (vma_iter_prealloc(vmi, vma))
|
||||
return NULL;
|
||||
goto prealloc_fail;
|
||||
|
||||
init_multi_vma_prep(&vp, vma, adjust, remove, remove2);
|
||||
VM_WARN_ON(vp.anon_vma && adjust && adjust->anon_vma &&
|
||||
@ -1016,6 +1016,12 @@ struct vm_area_struct *vma_merge(struct vma_iterator *vmi, struct mm_struct *mm,
|
||||
vma_complete(&vp, vmi, mm);
|
||||
khugepaged_enter_vma(res, vm_flags);
|
||||
return res;
|
||||
|
||||
prealloc_fail:
|
||||
anon_vma_fail:
|
||||
vma_iter_set(vmi, addr);
|
||||
vma_iter_load(vmi);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
|
Loading…
Reference in New Issue
Block a user