mirror of https://gitee.com/openkylin/linux.git
[PATCH] x86-64: fix perms/range of vsyscall vma in /proc/*/maps
The final line of /proc/<pid>/maps on x86_64 for native 64-bit tasks shows an incorrect ending address and incorrect permissions. There is only a single page mapped in this vsyscall region, and it is accessible for both read and execute. The patch below fixes this. (Since 32-bit-compat tasks have a real vma with correct perms/range, no change is necessary for that scenario.) Before the patch, a "cat /proc/self/maps | tail -1" shows this: ffffffffff600000-ffffffffffe00000 ---p 00000000 [...] After the patch, this is the output: ffffffffff600000-ffffffffff601000 r-xp 00000000 [...] Signed-off-by: Ernie Petrides <petrides@redhat.com> Signed-off-by: Andi Kleen <ak@suse.de>
This commit is contained in:
parent
c55d92d141
commit
103efcd9aa
|
@ -290,6 +290,7 @@ static void __init map_vsyscall(void)
|
||||||
extern char __vsyscall_0;
|
extern char __vsyscall_0;
|
||||||
unsigned long physaddr_page0 = __pa_symbol(&__vsyscall_0);
|
unsigned long physaddr_page0 = __pa_symbol(&__vsyscall_0);
|
||||||
|
|
||||||
|
/* Note that VSYSCALL_MAPPED_PAGES must agree with the code below. */
|
||||||
__set_fixmap(VSYSCALL_FIRST_PAGE, physaddr_page0, PAGE_KERNEL_VSYSCALL);
|
__set_fixmap(VSYSCALL_FIRST_PAGE, physaddr_page0, PAGE_KERNEL_VSYSCALL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -730,14 +730,15 @@ static __init int x8664_sysctl_init(void)
|
||||||
__initcall(x8664_sysctl_init);
|
__initcall(x8664_sysctl_init);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* A pseudo VMAs to allow ptrace access for the vsyscall page. This only
|
/* A pseudo VMA to allow ptrace access for the vsyscall page. This only
|
||||||
covers the 64bit vsyscall page now. 32bit has a real VMA now and does
|
covers the 64bit vsyscall page now. 32bit has a real VMA now and does
|
||||||
not need special handling anymore. */
|
not need special handling anymore. */
|
||||||
|
|
||||||
static struct vm_area_struct gate_vma = {
|
static struct vm_area_struct gate_vma = {
|
||||||
.vm_start = VSYSCALL_START,
|
.vm_start = VSYSCALL_START,
|
||||||
.vm_end = VSYSCALL_END,
|
.vm_end = VSYSCALL_START + (VSYSCALL_MAPPED_PAGES << PAGE_SHIFT),
|
||||||
.vm_page_prot = PAGE_READONLY
|
.vm_page_prot = PAGE_READONLY_EXEC,
|
||||||
|
.vm_flags = VM_READ | VM_EXEC
|
||||||
};
|
};
|
||||||
|
|
||||||
struct vm_area_struct *get_gate_vma(struct task_struct *tsk)
|
struct vm_area_struct *get_gate_vma(struct task_struct *tsk)
|
||||||
|
|
|
@ -10,6 +10,7 @@ enum vsyscall_num {
|
||||||
#define VSYSCALL_START (-10UL << 20)
|
#define VSYSCALL_START (-10UL << 20)
|
||||||
#define VSYSCALL_SIZE 1024
|
#define VSYSCALL_SIZE 1024
|
||||||
#define VSYSCALL_END (-2UL << 20)
|
#define VSYSCALL_END (-2UL << 20)
|
||||||
|
#define VSYSCALL_MAPPED_PAGES 1
|
||||||
#define VSYSCALL_ADDR(vsyscall_nr) (VSYSCALL_START+VSYSCALL_SIZE*(vsyscall_nr))
|
#define VSYSCALL_ADDR(vsyscall_nr) (VSYSCALL_START+VSYSCALL_SIZE*(vsyscall_nr))
|
||||||
|
|
||||||
#ifdef __KERNEL__
|
#ifdef __KERNEL__
|
||||||
|
|
Loading…
Reference in New Issue