linux-stable/arch/riscv
Stefan O'Rear d8dcba0691 riscv: process: Fix kernel gp leakage
commit d14fa1fcf6 upstream.

childregs represents the registers which are active for the new thread
in user context. For a kernel thread, childregs->gp is never used since
the kernel gp is not touched by switch_to. For a user mode helper, the
gp value can be observed in user space after execve or possibly by other
means.

[From the email thread]

The /* Kernel thread */ comment is somewhat inaccurate in that it is also used
for user_mode_helper threads, which exec a user process, e.g. /sbin/init or
when /proc/sys/kernel/core_pattern is a pipe. Such threads do not have
PF_KTHREAD set and are valid targets for ptrace etc. even before they exec.

childregs is the *user* context during syscall execution and it is observable
from userspace in at least five ways:

1. kernel_execve does not currently clear integer registers, so the starting
   register state for PID 1 and other user processes started by the kernel has
   sp = user stack, gp = kernel __global_pointer$, all other integer registers
   zeroed by the memset in the patch comment.

   This is a bug in its own right, but I'm unwilling to bet that it is the only
   way to exploit the issue addressed by this patch.

2. ptrace(PTRACE_GETREGSET): you can PTRACE_ATTACH to a user_mode_helper thread
   before it execs, but ptrace requires SIGSTOP to be delivered which can only
   happen at user/kernel boundaries.

3. /proc/*/task/*/syscall: this is perfectly happy to read pt_regs for
   user_mode_helpers before the exec completes, but gp is not one of the
   registers it returns.

4. PERF_SAMPLE_REGS_USER: LOCKDOWN_PERF normally prevents access to kernel
   addresses via PERF_SAMPLE_REGS_INTR, but due to this bug kernel addresses
   are also exposed via PERF_SAMPLE_REGS_USER which is permitted under
   LOCKDOWN_PERF. I have not attempted to write exploit code.

5. Much of the tracing infrastructure allows access to user registers. I have
   not attempted to determine which forms of tracing allow access to user
   registers without already allowing access to kernel registers.

Fixes: 7db91e57a0 ("RISC-V: Task implementation")
Cc: stable@vger.kernel.org
Signed-off-by: Stefan O'Rear <sorear@fastmail.com>
Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
Link: https://lore.kernel.org/r/20240327061258.2370291-1-sorear@fastmail.com
Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2024-04-10 16:38:20 +02:00
..
boot riscv: dts: starfive: jh7100: fix root clock names 2024-03-26 18:16:52 -04:00
configs Merge patch series "RISC-V SBI debug console extension support" 2024-01-11 07:36:27 -08:00
errata Merge patch series "riscv: errata: thead: use riscv_nonstd_cache_ops for CMO" 2024-01-11 07:36:30 -08:00
include riscv: Fix spurious errors from __get/put_kernel_nofault 2024-04-10 16:38:20 +02:00
kernel riscv: process: Fix kernel gp leakage 2024-04-10 16:38:20 +02:00
kvm RISC-V: KVM: Fix APLIC in_clrip[x] read emulation 2024-04-10 16:38:00 +02:00
lib work around gcc bugs with 'asm goto' with outputs 2024-02-09 15:57:48 -08:00
mm riscv: mm: Fix prototype to avoid discarding const 2024-04-10 16:38:09 +02:00
net riscv, bpf: Fix unpredictable kernel crash about RV64 struct_ops 2024-01-23 23:21:38 +01:00
purgatory riscv: Use SYM_*() assembly macros instead of deprecated ones 2023-11-06 09:42:47 -08:00
tools
Kbuild kexec: rename ARCH_HAS_KEXEC_PURGATORY 2023-08-18 10:18:54 -07:00
Kconfig RISC-V: Drop invalid test from CONFIG_AS_HAS_OPTION_ARCH 2024-02-16 16:07:08 -08:00
Kconfig.debug riscv: Add tests for riscv module loading 2023-11-07 14:59:32 -08:00
Kconfig.errata RISC-V Patches for the 6.8 Merge Window, Part 4 2024-01-20 11:06:04 -08:00
Kconfig.socs SoC driver updates for 6.7 2023-11-01 14:46:51 -10:00
Makefile riscv: add dependency among Image(.gz), loader(.bin), and vmlinuz.efi 2024-01-17 18:18:20 -08:00
Makefile.postlink kbuild: remove ARCH_POSTLINK from module builds 2023-10-28 21:10:08 +09:00