When checking the surrounding VMAs, the VMA iterator is moved to the
previous VMA. If they can merge, then the VMA iterator is in the correct
position. If they are not, then the iterator needs to be moved back to
the gap that will be filled. Use vma_iter_next_range() to move the
iterator to the next range instead of re-walking the VMA tree.
Signed-off-by: Liam R. Howlett <Liam.Howlett@oracle.com>
next = vma_next(&vmi);
prev = vma_prev(&vmi);
- if (vm_flags & VM_SPECIAL)
+ if (vm_flags & VM_SPECIAL) {
+ vma_iter_next_range(&vmi);
goto cannot_expand;
+ }
/* Attempt to expand an old mapping */
/* Check next */
merge_start = prev->vm_start;
vma = prev;
vm_pgoff = prev->vm_pgoff;
+ } else {
+ vma_iter_next_range(&vmi);
}
goto expanded;
}
+ if (prev && prev == vma) /* vma_expand() failed to expand prev */
+ vma_iter_next_range(&vmi);
+
cannot_expand:
/*
* Determine the object being mapped and call the appropriate
goto unacct_error;
}
- vma_iter_set(&vmi, addr);
vma->vm_start = addr;
vma->vm_end = end;
vm_flags_init(vma, vm_flags);