Commit f3c01d2f authored by Chintan Pandya's avatar Chintan Pandya Committed by Linus Torvalds

mm: vmalloc: avoid racy handling of debugobjects in vunmap

Currently, __vunmap flow is,
 1) Release the VM area
 2) Free the debug objects corresponding to that vm area.

This leave some race window open.
 1) Release the VM area
 1.5) Some other client gets the same vm area
 1.6) This client allocates new debug objects on the same
      vm area
 2) Free the debug objects corresponding to this vm area.

Here, we actually free 'other' client's debug objects.

Fix this by freeing the debug objects first and then releasing the VM
area.

Link: http://lkml.kernel.org/r/1523961828-9485-2-git-send-email-cpandya@codeaurora.orgSigned-off-by: default avatarChintan Pandya <cpandya@codeaurora.org>
Reviewed-by: default avatarAndrew Morton <akpm@linux-foundation.org>
Cc: Ard Biesheuvel <ard.biesheuvel@linaro.org>
Cc: Byungchul Park <byungchul.park@lge.com>
Cc: Catalin Marinas <catalin.marinas@arm.com>
Cc: Florian Fainelli <f.fainelli@gmail.com>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: Laura Abbott <labbott@redhat.com>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Wei Yang <richard.weiyang@gmail.com>
Cc: Yisheng Xie <xieyisheng1@huawei.com>
Signed-off-by: default avatarAndrew Morton <akpm@linux-foundation.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@linux-foundation.org>
parent 82a2e924
...@@ -1504,7 +1504,7 @@ static void __vunmap(const void *addr, int deallocate_pages) ...@@ -1504,7 +1504,7 @@ static void __vunmap(const void *addr, int deallocate_pages)
addr)) addr))
return; return;
area = remove_vm_area(addr); area = find_vmap_area((unsigned long)addr)->vm;
if (unlikely(!area)) { if (unlikely(!area)) {
WARN(1, KERN_ERR "Trying to vfree() nonexistent vm area (%p)\n", WARN(1, KERN_ERR "Trying to vfree() nonexistent vm area (%p)\n",
addr); addr);
...@@ -1514,6 +1514,7 @@ static void __vunmap(const void *addr, int deallocate_pages) ...@@ -1514,6 +1514,7 @@ static void __vunmap(const void *addr, int deallocate_pages)
debug_check_no_locks_freed(addr, get_vm_area_size(area)); debug_check_no_locks_freed(addr, get_vm_area_size(area));
debug_check_no_obj_freed(addr, get_vm_area_size(area)); debug_check_no_obj_freed(addr, get_vm_area_size(area));
remove_vm_area(addr);
if (deallocate_pages) { if (deallocate_pages) {
int i; int i;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment