The patch titled Subject: vsprintf: refactor %pK code out of pointer() has been added to the -mm tree. Its filename is vsprintf-refactor-%pk-code-out-of-pointer.patch This patch should soon appear at http://ozlabs.org/~akpm/mmots/broken-out/vsprintf-refactor-%25pk-code-out-of-pointer.patch and later at http://ozlabs.org/~akpm/mmotm/broken-out/vsprintf-refactor-%25pk-code-out-of-pointer.patch Before you just go and hit "reply", please: a) Consider who else should be cc'ed b) Prefer to cc a suitable mailing list as well c) Ideally: find the original patch on the mailing list and do a reply-to-all to that, adding suitable additional cc's *** Remember to use Documentation/SubmitChecklist when testing your code *** The -mm tree is included into linux-next and is updated there every 3-4 working days ------------------------------------------------------ From: "Tobin C. Harding" <me@xxxxxxxx> Subject: vsprintf: refactor %pK code out of pointer() Currently code to handle %pK is all within the switch statement in pointer(). This is the wrong level of abstraction. Each of the other switch clauses call a helper function, pK should do the same. Refactor code out of pointer() to new function restricted_pointer(). Link: http://lkml.kernel.org/r/1511921105-3647-3-git-send-email-me@xxxxxxxx Signed-off-by: Tobin C. Harding <me@xxxxxxxx> Cc: Alexander Potapenko <glider@xxxxxxxxxx> Cc: Andrey Ryabinin <aryabinin@xxxxxxxxxxxxx> Cc: Catalin Marinas <catalin.marinas@xxxxxxx> Cc: Chris Fries <cfries@xxxxxxxxxx> Cc: Daniel Micay <danielmicay@xxxxxxxxx> Cc: Dave Weinstein <olorin@xxxxxxxxxx> Cc: David Miller <davem@xxxxxxxxxxxxx> Cc: Djalal Harouni <tixxdz@xxxxxxxxx> Cc: Dmitry Vyukov <dvyukov@xxxxxxxxxx> Cc: Greg KH <gregkh@xxxxxxxxxxxxxxxxxxx> Cc: Ian Campbell <ijc@xxxxxxxxxxxxxx> Cc: "Jason A. Donenfeld" <Jason@xxxxxxxxx> Cc: Joe Perches <joe@xxxxxxxxxxx> Cc: Jordan Glover <Golden_Miller83@xxxxxxxxxxxxx> Cc: Kees Cook <keescook@xxxxxxxxxxxx> Cc: Paolo Bonzini <pbonzini@xxxxxxxxxx> Cc: Petr Mladek <pmladek@xxxxxxxx> Cc: Radim Krčmář <rkrcmar@xxxxxxxxxx> Cc: "Roberts, William C" <william.c.roberts@xxxxxxxxx> Cc: Sergey Senozhatsky <sergey.senozhatsky@xxxxxxxxx> Cc: Stephen Rothwell <sfr@xxxxxxxxxxxxxxxx> Cc: Steven Rostedt <rostedt@xxxxxxxxxxx> Cc: Tejun Heo <tj@xxxxxxxxxx> Cc: "Theodore Ts'o" <tytso@xxxxxxx> Cc: Tycho Andersen <tycho@xxxxxxxx> Cc: Will Deacon <wilal.deacon@xxxxxxx> Signed-off-by: Andrew Morton <akpm@xxxxxxxxxxxxxxxxxxxx> --- lib/vsprintf.c | 97 ++++++++++++++++++++++++++--------------------- 1 file changed, 54 insertions(+), 43 deletions(-) diff -puN lib/vsprintf.c~vsprintf-refactor-%pk-code-out-of-pointer lib/vsprintf.c --- a/lib/vsprintf.c~vsprintf-refactor-%pk-code-out-of-pointer +++ a/lib/vsprintf.c @@ -1343,6 +1343,59 @@ char *uuid_string(char *buf, char *end, return string(buf, end, uuid, spec); } +int kptr_restrict __read_mostly; + +static noinline_for_stack +char *restricted_pointer(char *buf, char *end, const void *ptr, + struct printf_spec spec) +{ + spec.base = 16; + spec.flags |= SMALL; + if (spec.field_width == -1) { + spec.field_width = 2 * sizeof(ptr); + spec.flags |= ZEROPAD; + } + + switch (kptr_restrict) { + case 0: + /* Always print %pK values */ + break; + case 1: { + const struct cred *cred; + + /* + * kptr_restrict==1 cannot be used in IRQ context + * because its test for CAP_SYSLOG would be meaningless. + */ + if (in_irq() || in_serving_softirq() || in_nmi()) + return string(buf, end, "pK-error", spec); + + /* + * Only print the real pointer value if the current + * process has CAP_SYSLOG and is running with the + * same credentials it started with. This is because + * access to files is checked at open() time, but %pK + * checks permission at read() time. We don't want to + * leak pointer values if a binary opens a file using + * %pK and then elevates privileges before reading it. + */ + cred = current_cred(); + if (!has_capability_noaudit(current, CAP_SYSLOG) || + !uid_eq(cred->euid, cred->uid) || + !gid_eq(cred->egid, cred->gid)) + ptr = NULL; + break; + } + case 2: + default: + /* Always print 0's for %pK */ + ptr = NULL; + break; + } + + return number(buf, end, (unsigned long)ptr, spec); +} + static noinline_for_stack char *netdev_bits(char *buf, char *end, const void *addr, const char *fmt) { @@ -1591,8 +1644,6 @@ char *device_node_string(char *buf, char return widen_string(buf, buf - buf_start, end, spec); } -int kptr_restrict __read_mostly; - /* * Show a '%p' thing. A kernel extension is that the '%p' is followed * by an extra set of alphanumeric characters that are extended format @@ -1792,47 +1843,7 @@ char *pointer(const char *fmt, char *buf return buf; } case 'K': - switch (kptr_restrict) { - case 0: - /* Always print %pK values */ - break; - case 1: { - const struct cred *cred; - - /* - * kptr_restrict==1 cannot be used in IRQ context - * because its test for CAP_SYSLOG would be meaningless. - */ - if (in_irq() || in_serving_softirq() || in_nmi()) { - if (spec.field_width == -1) - spec.field_width = default_width; - return string(buf, end, "pK-error", spec); - } - - /* - * Only print the real pointer value if the current - * process has CAP_SYSLOG and is running with the - * same credentials it started with. This is because - * access to files is checked at open() time, but %pK - * checks permission at read() time. We don't want to - * leak pointer values if a binary opens a file using - * %pK and then elevates privileges before reading it. - */ - cred = current_cred(); - if (!has_capability_noaudit(current, CAP_SYSLOG) || - !uid_eq(cred->euid, cred->uid) || - !gid_eq(cred->egid, cred->gid)) - ptr = NULL; - break; - } - case 2: - default: - /* Always print 0's for %pK */ - ptr = NULL; - break; - } - break; - + return restricted_pointer(buf, end, ptr, spec); case 'N': return netdev_bits(buf, end, ptr, fmt); case 'a': _ Patches currently in -mm which might be from me@xxxxxxxx are docs-correct-documentation-for-%pk.patch vsprintf-refactor-%pk-code-out-of-pointer.patch printk-hash-addresses-printed-with-%p.patch vsprintf-add-printk-specifier-%px.patch kasan-use-%px-to-print-addresses-instead-of-%p.patch -- To unsubscribe from this list: send the line "unsubscribe mm-commits" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html