vfs/proc/kcore, x86/mm/kcore: Fix SMAP fault when dumping vsyscall user page

"Linux Kernel Mailing List" <[email protected]> Thu, 15 Feb 2018 01:48:52 +0000 (UTC)
Newsgroups gmane.linux.kernel.commits.head
Message-ID <[email protected]>
Web:        https://git.kernel.org/torvalds/c/595dd46ebfc10be041a365d0a3fa99df50b6ba73
Commit:     595dd46ebfc10be041a365d0a3fa99df50b6ba73
Parent:     aec6487e994d2f625197970a56a4aac40c2c7547
Refname:    refs/heads/master
Author:     Jia Zhang <[email protected]>
AuthorDate: Mon Feb 12 22:44:53 2018 +0800
Committer:  Ingo Molnar <[email protected]>
CommitDate: Tue Feb 13 09:15:58 2018 +0100

    vfs/proc/kcore, x86/mm/kcore: Fix SMAP fault when dumping vsyscall user page
    
    Commit:
    
      df04abfd181a ("fs/proc/kcore.c: Add bounce buffer for ktext data")
    
    ... introduced a bounce buffer to work around CONFIG_HARDENED_USERCOPY=y.
    However, accessing the vsyscall user page will cause an SMAP fault.
    
    Replace memcpy() with copy_from_user() to fix this bug works, but adding
    a common way to handle this sort of user page may be useful for future.
    
    Currently, only vsyscall page requires KCORE_USER.
    
    Signed-off-by: Jia Zhang <[email protected]>
    Reviewed-by: Jiri Olsa <[email protected]>
    Cc: Al Viro <[email protected]>
    Cc: Linus Torvalds <[email protected]>
    Cc: Peter Zijlstra <[email protected]>
    Cc: Thomas Gleixner <[email protected]>
    Cc: [email protected]
    Link: http://lkml.kernel.org/r/[email protected]
    Signed-off-by: Ingo Molnar <[email protected]>
---
 arch/x86/mm/init_64.c | 3 +--
 fs/proc/kcore.c       | 4 ++++
 include/linux/kcore.h | 1 +
 3 files changed, 6 insertions(+), 2 deletions(-)

diff --git a/arch/x86/mm/init_64.c b/arch/x86/mm/init_64.c
index 1ab42c852069..6aa33d1e198f 100644
--- a/arch/x86/mm/init_64.c
+++ b/arch/x86/mm/init_64.c
@@ -1193,8 +1193,7 @@ void __init mem_init(void)
 	register_page_bootmem_info();
 
 	/* Register memory areas for /proc/kcore */
-	kclist_add(&kcore_vsyscall, (void *)VSYSCALL_ADDR,
-			 PAGE_SIZE, KCORE_OTHER);
+	kclist_add(&kcore_vsyscall, (void *)VSYSCALL_ADDR, PAGE_SIZE, KCORE_USER);
 
 	mem_init_print_info(NULL);
 }
diff --git a/fs/proc/kcore.c b/fs/proc/kcore.c
index e8a93bc8285d..d1e82761de81 100644
--- a/fs/proc/kcore.c
+++ b/fs/proc/kcore.c
@@ -510,6 +510,10 @@ read_kcore(struct file *file, char __user *buffer, size_t buflen, loff_t *fpos)
 			/* we have to zero-fill user buffer even if no read */
 			if (copy_to_user(buffer, buf, tsz))
 				return -EFAULT;
+		} else if (m->type == KCORE_USER) {
+			/* User page is handled prior to normal kernel page: */
+			if (copy_to_user(buffer, (char *)start, tsz))
+				return -EFAULT;
 		} else {
 			if (kern_addr_valid(start)) {
 				/*
diff --git a/include/linux/kcore.h b/include/linux/kcore.h
index 7ff25a808fef..80db19d3a505 100644
--- a/include/linux/kcore.h
+++ b/include/linux/kcore.h
@@ -10,6 +10,7 @@ enum kcore_type {
 	KCORE_VMALLOC,
 	KCORE_RAM,
 	KCORE_VMEMMAP,
+	KCORE_USER,
 	KCORE_OTHER,
 };
 
--
To unsubscribe from this list: send the line "unsubscribe git-commits-head" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html