* Lokesh Gidra <lokeshgidra@xxxxxxxxxx> [240130 21:49]: > On Mon, Jan 29, 2024 at 6:58 PM Liam R. Howlett <Liam.Howlett@xxxxxxxxxx> wrote: > > > > * Lokesh Gidra <lokeshgidra@xxxxxxxxxx> [240129 19:28]: > > > On Mon, Jan 29, 2024 at 12:53 PM Suren Baghdasaryan <surenb@xxxxxxxxxx> wrote: > > > > > > ... > > > > > Your suggestion is definitely simpler and easier to follow, but due to > > > the overflow situation that Suren pointed out, I would still need to > > > keep the locking/boolean dance, no? IIUC, even if I were to return > > > EAGAIN to the userspace, there is no guarantee that subsequent ioctls > > > on the same vma will succeed due to the same overflow, until someone > > > acquires and releases mmap_lock in write-mode. > > > Also, sometimes it seems insufficient whether we managed to lock vma > > > or not. For instance, lock_vma_under_rcu() checks if anon_vma (for > > > anonymous vma) exists. If not then it bails out. > > > So it seems to me that we have to provide some fall back in > > > userfaultfd operations which executes with mmap_lock in read-mode. > > > > Fair enough, what if we didn't use the sequence number and just locked > > the vma directly? > > Looks good to me, unless someone else has any objections. > > > > /* This will wait on the vma lock, so once we return it's locked */ > > void vma_aquire_read_lock(struct vm_area_struct *vma) > > { > > mmap_assert_locked(vma->vm_mm); > > down_read(&vma->vm_lock->lock); > > } > > > > struct vm_area_struct *lock_vma(struct mm_struct *mm, > > unsigned long addr)) /* or some better name.. */ > > { > > struct vm_area_struct *vma; > > > > vma = lock_vma_under_rcu(mm, addr); > > if (vma) > > return vma; > > > > mmap_read_lock(mm); > > /* mm sequence cannot change, no mm writers anyways. > > * find_mergeable_anon_vma is only a concern in the page fault > > * path > > * start/end won't change under the mmap_lock > > * vma won't become detached as we have the mmap_lock in read > > * We are now sure no writes will change the VMA > > * So let's make sure no other context is isolating the vma > > */ > > vma = lookup_vma(mm, addr); > > if (vma) > We can take care of anon_vma as well here right? I can take a bool > parameter ('prepare_anon' or something) and then: > > if (vma) { > if (prepare_anon && vma_is_anonymous(vma)) && > !anon_vma_prepare(vma)) { > vma = ERR_PTR(-ENOMEM); > goto out_unlock; > } > > vma_aquire_read_lock(vma); > } > out_unlock: > > mmap_read_unlock(mm); > > return vma; > > } Do you need this? I didn't think this was happening in the code as written? If you need it I would suggest making it happen always and ditch the flag until a user needs this variant, but document what's going on in here or even have a better name. Thanks, Liam