mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-28 02:32:09 -04:00
procfs task exe symlink
The kernel implements readlink of /proc/pid/exe by getting the file from the first executable VMA. Then the path to the file is reconstructed and reported as the result. Because of the VMA walk the code is slightly different on nommu systems. This patch avoids separate /proc/pid/exe code on nommu systems. Instead of walking the VMAs to find the first executable file-backed VMA we store a reference to the exec'd file in the mm_struct. That reference would prevent the filesystem holding the executable file from being unmounted even after unmapping the VMAs. So we track the number of VM_EXECUTABLE VMAs and drop the new reference when the last one is unmapped. This avoids pinning the mounted filesystem. [[email protected]: improve comments] [[email protected]: fix dup_mmap] Signed-off-by: Matt Helsley <[email protected]> Cc: Oleg Nesterov <[email protected]> Cc: David Howells <[email protected]> Cc:"Eric W. Biederman" <[email protected]> Cc: Christoph Hellwig <[email protected]> Cc: Al Viro <[email protected]> Cc: Hugh Dickins <[email protected]> Signed-off-by: YAMAMOTO Takashi <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
This commit is contained in:
parent
e93b4ea20a
commit
925d1c401f
12 changed files with 157 additions and 81 deletions
24
mm/mmap.c
24
mm/mmap.c
|
|
@ -230,8 +230,11 @@ static struct vm_area_struct *remove_vma(struct vm_area_struct *vma)
|
|||
might_sleep();
|
||||
if (vma->vm_ops && vma->vm_ops->close)
|
||||
vma->vm_ops->close(vma);
|
||||
if (vma->vm_file)
|
||||
if (vma->vm_file) {
|
||||
fput(vma->vm_file);
|
||||
if (vma->vm_flags & VM_EXECUTABLE)
|
||||
removed_exe_file_vma(vma->vm_mm);
|
||||
}
|
||||
mpol_put(vma_policy(vma));
|
||||
kmem_cache_free(vm_area_cachep, vma);
|
||||
return next;
|
||||
|
|
@ -623,8 +626,11 @@ again: remove_next = 1 + (end > next->vm_end);
|
|||
spin_unlock(&mapping->i_mmap_lock);
|
||||
|
||||
if (remove_next) {
|
||||
if (file)
|
||||
if (file) {
|
||||
fput(file);
|
||||
if (next->vm_flags & VM_EXECUTABLE)
|
||||
removed_exe_file_vma(mm);
|
||||
}
|
||||
mm->map_count--;
|
||||
mpol_put(vma_policy(next));
|
||||
kmem_cache_free(vm_area_cachep, next);
|
||||
|
|
@ -1154,6 +1160,8 @@ munmap_back:
|
|||
error = file->f_op->mmap(file, vma);
|
||||
if (error)
|
||||
goto unmap_and_free_vma;
|
||||
if (vm_flags & VM_EXECUTABLE)
|
||||
added_exe_file_vma(mm);
|
||||
} else if (vm_flags & VM_SHARED) {
|
||||
error = shmem_zero_setup(vma);
|
||||
if (error)
|
||||
|
|
@ -1185,6 +1193,8 @@ munmap_back:
|
|||
mpol_put(vma_policy(vma));
|
||||
kmem_cache_free(vm_area_cachep, vma);
|
||||
fput(file);
|
||||
if (vm_flags & VM_EXECUTABLE)
|
||||
removed_exe_file_vma(mm);
|
||||
} else {
|
||||
vma_link(mm, vma, prev, rb_link, rb_parent);
|
||||
file = vma->vm_file;
|
||||
|
|
@ -1817,8 +1827,11 @@ int split_vma(struct mm_struct * mm, struct vm_area_struct * vma,
|
|||
}
|
||||
vma_set_policy(new, pol);
|
||||
|
||||
if (new->vm_file)
|
||||
if (new->vm_file) {
|
||||
get_file(new->vm_file);
|
||||
if (vma->vm_flags & VM_EXECUTABLE)
|
||||
added_exe_file_vma(mm);
|
||||
}
|
||||
|
||||
if (new->vm_ops && new->vm_ops->open)
|
||||
new->vm_ops->open(new);
|
||||
|
|
@ -2135,8 +2148,11 @@ struct vm_area_struct *copy_vma(struct vm_area_struct **vmap,
|
|||
new_vma->vm_start = addr;
|
||||
new_vma->vm_end = addr + len;
|
||||
new_vma->vm_pgoff = pgoff;
|
||||
if (new_vma->vm_file)
|
||||
if (new_vma->vm_file) {
|
||||
get_file(new_vma->vm_file);
|
||||
if (vma->vm_flags & VM_EXECUTABLE)
|
||||
added_exe_file_vma(mm);
|
||||
}
|
||||
if (new_vma->vm_ops && new_vma->vm_ops->open)
|
||||
new_vma->vm_ops->open(new_vma);
|
||||
vma_link(mm, new_vma, prev, rb_link, rb_parent);
|
||||
|
|
|
|||
Loading…
Reference in a new issue