RISC-V Fixes for 6.6-rc6
* A handful of build fixes. * A fix to avoid mixing up user/kernel-mode breakpoints, which can manifest as a hang when mixing k/uprobes with other breakpoint sources. * A fix to avoid double-allocting crash kernel memory. * A fix for tracefs syscall name mangling, which was causing syscalls not to show up in tracefs. * A fix to the perf driver to enable the hw events when selected, which can trigger a BUG on some userspace access patterns. -----BEGIN PGP SIGNATURE----- iQJHBAABCAAxFiEEKzw3R0RoQ7JKlDp6LhMZ81+7GIkFAmUpTGoTHHBhbG1lckBk YWJiZWx0LmNvbQAKCRAuExnzX7sYiT3KEACCeF+jaVW7/jkc2nRr4gnxl4VAxmMC p/UGwZbtBUtGPQAWFWZqcpDw6qkxGM96HK12+8CLgEjjOEZVAchFpix+G48mEgHn LMA4MrPyJ5WxY7qbqD3V6d52UNpLwpJWU9oxlv7p417mkYzqfVs5Ey6r1Gh8E3pK YRh6VEHBLxMw+qAb90MgzhzK39TZNkJ01U5kDedskpZ/qZCI+W5Jl0Rz88xcixUI oO67a5lV5CmcGSxmeLKJXp1p0dV73c9wuMJMmCGyxMHX8UAHFRQqBrHvDpNUSPhD BEne8Y1oSQAx8xsTe8HBksKSJeB3cqZ/EqqQkab2Q+RoQbfiE5daVbR5q7rNI+R9 EI9oakH59f5y2ohaiT3Kf+06nRBketKT1bnkIhQ9aEB6E7ilqS6iv+A2BEKCq3PP GOHxDSSxal1+PcNObdx6RsHu82QSbUBp3LKcUV9bPrJqzXDRQrNlgf8B56IPp5yy gj29xCu+vrTv2Y3uChCEdnJ0uXO/JUT02/FGMTSB12Ec43K3p2KCBhSzJyAD6kfa WqfBJ1SWfBvL0vhsxuOuVS44/JKQUlDWt9H9Mo+SRR3K8yk83AALQ295RdE+AFBt ZUBcv7FQH9yDmt/NsV8f0i1hHVSE35PwrMhIR2G4pddtoiC1L8CBxHl9g9R9IxQ9 jwt5vxqQx9izPg== =kOgc -----END PGP SIGNATURE----- Merge tag 'riscv-for-linus-6.6-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux Pull RISC-V fixes from Palmer Dabbelt: - A handful of build fixes - A fix to avoid mixing up user/kernel-mode breakpoints, which can manifest as a hang when mixing k/uprobes with other breakpoint sources - A fix to avoid double-allocting crash kernel memory - A fix for tracefs syscall name mangling, which was causing syscalls not to show up in tracefs - A fix to the perf driver to enable the hw events when selected, which can trigger a BUG on some userspace access patterns * tag 'riscv-for-linus-6.6-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux: drivers: perf: Fix panic in riscv SBI mmap support riscv: Fix ftrace syscall handling which are now prefixed with __riscv_ RISC-V: Fix wrong use of CONFIG_HAVE_SOFTIRQ_ON_OWN_STACK riscv: kdump: fix crashkernel reserving problem on RISC-V riscv: Remove duplicate objcopy flag riscv: signal: fix sigaltstack frame size checking riscv: errata: andes: Makefile: Fix randconfig build issue riscv: Only consider swbp/ss handlers for correct privileged mode riscv: kselftests: Fix mm build by removing testcases subdirectory
This commit is contained in:
commit
b82fbd8f39
arch/riscv
drivers/perf
tools/testing/selftests/riscv/mm
|
@ -6,7 +6,6 @@
|
|||
# for more details.
|
||||
#
|
||||
|
||||
OBJCOPYFLAGS := -O binary
|
||||
LDFLAGS_vmlinux := -z norelro
|
||||
ifeq ($(CONFIG_RELOCATABLE),y)
|
||||
LDFLAGS_vmlinux += -shared -Bsymbolic -z notext --emit-relocs
|
||||
|
|
|
@ -1 +1,5 @@
|
|||
ifdef CONFIG_RISCV_ALTERNATIVE_EARLY
|
||||
CFLAGS_errata.o := -mcmodel=medany
|
||||
endif
|
||||
|
||||
obj-y += errata.o
|
||||
|
|
|
@ -31,6 +31,27 @@ static inline unsigned long ftrace_call_adjust(unsigned long addr)
|
|||
return addr;
|
||||
}
|
||||
|
||||
/*
|
||||
* Let's do like x86/arm64 and ignore the compat syscalls.
|
||||
*/
|
||||
#define ARCH_TRACE_IGNORE_COMPAT_SYSCALLS
|
||||
static inline bool arch_trace_is_compat_syscall(struct pt_regs *regs)
|
||||
{
|
||||
return is_compat_task();
|
||||
}
|
||||
|
||||
#define ARCH_HAS_SYSCALL_MATCH_SYM_NAME
|
||||
static inline bool arch_syscall_match_sym_name(const char *sym,
|
||||
const char *name)
|
||||
{
|
||||
/*
|
||||
* Since all syscall functions have __riscv_ prefix, we must skip it.
|
||||
* However, as we described above, we decided to ignore compat
|
||||
* syscalls, so we don't care about __riscv_compat_ prefix here.
|
||||
*/
|
||||
return !strcmp(sym + 8, name);
|
||||
}
|
||||
|
||||
struct dyn_arch_ftrace {
|
||||
};
|
||||
#endif
|
||||
|
|
|
@ -40,6 +40,15 @@ void arch_remove_kprobe(struct kprobe *p);
|
|||
int kprobe_fault_handler(struct pt_regs *regs, unsigned int trapnr);
|
||||
bool kprobe_breakpoint_handler(struct pt_regs *regs);
|
||||
bool kprobe_single_step_handler(struct pt_regs *regs);
|
||||
#else
|
||||
static inline bool kprobe_breakpoint_handler(struct pt_regs *regs)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
static inline bool kprobe_single_step_handler(struct pt_regs *regs)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
#endif /* CONFIG_KPROBES */
|
||||
#endif /* _ASM_RISCV_KPROBES_H */
|
||||
|
|
|
@ -34,7 +34,18 @@ struct arch_uprobe {
|
|||
bool simulate;
|
||||
};
|
||||
|
||||
#ifdef CONFIG_UPROBES
|
||||
bool uprobe_breakpoint_handler(struct pt_regs *regs);
|
||||
bool uprobe_single_step_handler(struct pt_regs *regs);
|
||||
#else
|
||||
static inline bool uprobe_breakpoint_handler(struct pt_regs *regs)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
static inline bool uprobe_single_step_handler(struct pt_regs *regs)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
#endif /* CONFIG_UPROBES */
|
||||
#endif /* _ASM_RISCV_UPROBES_H */
|
||||
|
|
|
@ -60,7 +60,7 @@ static void init_irq_stacks(void)
|
|||
}
|
||||
#endif /* CONFIG_VMAP_STACK */
|
||||
|
||||
#ifdef CONFIG_HAVE_SOFTIRQ_ON_OWN_STACK
|
||||
#ifdef CONFIG_SOFTIRQ_ON_OWN_STACK
|
||||
void do_softirq_own_stack(void)
|
||||
{
|
||||
#ifdef CONFIG_IRQ_STACKS
|
||||
|
@ -92,7 +92,7 @@ void do_softirq_own_stack(void)
|
|||
#endif
|
||||
__do_softirq();
|
||||
}
|
||||
#endif /* CONFIG_HAVE_SOFTIRQ_ON_OWN_STACK */
|
||||
#endif /* CONFIG_SOFTIRQ_ON_OWN_STACK */
|
||||
|
||||
#else
|
||||
static void init_irq_stacks(void) {}
|
||||
|
|
|
@ -173,19 +173,6 @@ static void __init init_resources(void)
|
|||
if (ret < 0)
|
||||
goto error;
|
||||
|
||||
#ifdef CONFIG_KEXEC_CORE
|
||||
if (crashk_res.start != crashk_res.end) {
|
||||
ret = add_resource(&iomem_resource, &crashk_res);
|
||||
if (ret < 0)
|
||||
goto error;
|
||||
}
|
||||
if (crashk_low_res.start != crashk_low_res.end) {
|
||||
ret = add_resource(&iomem_resource, &crashk_low_res);
|
||||
if (ret < 0)
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_CRASH_DUMP
|
||||
if (elfcorehdr_size > 0) {
|
||||
elfcorehdr_res.start = elfcorehdr_addr;
|
||||
|
|
|
@ -311,13 +311,6 @@ static inline void __user *get_sigframe(struct ksignal *ksig,
|
|||
/* Align the stack frame. */
|
||||
sp &= ~0xfUL;
|
||||
|
||||
/*
|
||||
* Fail if the size of the altstack is not large enough for the
|
||||
* sigframe construction.
|
||||
*/
|
||||
if (current->sas_ss_size && sp < current->sas_ss_sp)
|
||||
return (void __user __force *)-1UL;
|
||||
|
||||
return (void __user *)sp;
|
||||
}
|
||||
|
||||
|
|
|
@ -13,6 +13,8 @@
|
|||
#include <linux/kdebug.h>
|
||||
#include <linux/uaccess.h>
|
||||
#include <linux/kprobes.h>
|
||||
#include <linux/uprobes.h>
|
||||
#include <asm/uprobes.h>
|
||||
#include <linux/mm.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/irq.h>
|
||||
|
@ -247,22 +249,28 @@ static inline unsigned long get_break_insn_length(unsigned long pc)
|
|||
return GET_INSN_LENGTH(insn);
|
||||
}
|
||||
|
||||
static bool probe_single_step_handler(struct pt_regs *regs)
|
||||
{
|
||||
bool user = user_mode(regs);
|
||||
|
||||
return user ? uprobe_single_step_handler(regs) : kprobe_single_step_handler(regs);
|
||||
}
|
||||
|
||||
static bool probe_breakpoint_handler(struct pt_regs *regs)
|
||||
{
|
||||
bool user = user_mode(regs);
|
||||
|
||||
return user ? uprobe_breakpoint_handler(regs) : kprobe_breakpoint_handler(regs);
|
||||
}
|
||||
|
||||
void handle_break(struct pt_regs *regs)
|
||||
{
|
||||
#ifdef CONFIG_KPROBES
|
||||
if (kprobe_single_step_handler(regs))
|
||||
if (probe_single_step_handler(regs))
|
||||
return;
|
||||
|
||||
if (kprobe_breakpoint_handler(regs))
|
||||
return;
|
||||
#endif
|
||||
#ifdef CONFIG_UPROBES
|
||||
if (uprobe_single_step_handler(regs))
|
||||
if (probe_breakpoint_handler(regs))
|
||||
return;
|
||||
|
||||
if (uprobe_breakpoint_handler(regs))
|
||||
return;
|
||||
#endif
|
||||
current->thread.bad_cause = regs->cause;
|
||||
|
||||
if (user_mode(regs))
|
||||
|
|
|
@ -23,7 +23,8 @@ static bool riscv_perf_user_access(struct perf_event *event)
|
|||
return ((event->attr.type == PERF_TYPE_HARDWARE) ||
|
||||
(event->attr.type == PERF_TYPE_HW_CACHE) ||
|
||||
(event->attr.type == PERF_TYPE_RAW)) &&
|
||||
!!(event->hw.flags & PERF_EVENT_FLAG_USER_READ_CNT);
|
||||
!!(event->hw.flags & PERF_EVENT_FLAG_USER_READ_CNT) &&
|
||||
(event->hw.idx != -1);
|
||||
}
|
||||
|
||||
void arch_perf_update_userpage(struct perf_event *event,
|
||||
|
|
|
@ -510,16 +510,18 @@ static void pmu_sbi_set_scounteren(void *arg)
|
|||
{
|
||||
struct perf_event *event = (struct perf_event *)arg;
|
||||
|
||||
csr_write(CSR_SCOUNTEREN,
|
||||
csr_read(CSR_SCOUNTEREN) | (1 << pmu_sbi_csr_index(event)));
|
||||
if (event->hw.idx != -1)
|
||||
csr_write(CSR_SCOUNTEREN,
|
||||
csr_read(CSR_SCOUNTEREN) | (1 << pmu_sbi_csr_index(event)));
|
||||
}
|
||||
|
||||
static void pmu_sbi_reset_scounteren(void *arg)
|
||||
{
|
||||
struct perf_event *event = (struct perf_event *)arg;
|
||||
|
||||
csr_write(CSR_SCOUNTEREN,
|
||||
csr_read(CSR_SCOUNTEREN) & ~(1 << pmu_sbi_csr_index(event)));
|
||||
if (event->hw.idx != -1)
|
||||
csr_write(CSR_SCOUNTEREN,
|
||||
csr_read(CSR_SCOUNTEREN) & ~(1 << pmu_sbi_csr_index(event)));
|
||||
}
|
||||
|
||||
static void pmu_sbi_ctr_start(struct perf_event *event, u64 ival)
|
||||
|
@ -541,7 +543,8 @@ static void pmu_sbi_ctr_start(struct perf_event *event, u64 ival)
|
|||
|
||||
if ((hwc->flags & PERF_EVENT_FLAG_USER_ACCESS) &&
|
||||
(hwc->flags & PERF_EVENT_FLAG_USER_READ_CNT))
|
||||
pmu_sbi_set_scounteren((void *)event);
|
||||
on_each_cpu_mask(mm_cpumask(event->owner->mm),
|
||||
pmu_sbi_set_scounteren, (void *)event, 1);
|
||||
}
|
||||
|
||||
static void pmu_sbi_ctr_stop(struct perf_event *event, unsigned long flag)
|
||||
|
@ -551,7 +554,8 @@ static void pmu_sbi_ctr_stop(struct perf_event *event, unsigned long flag)
|
|||
|
||||
if ((hwc->flags & PERF_EVENT_FLAG_USER_ACCESS) &&
|
||||
(hwc->flags & PERF_EVENT_FLAG_USER_READ_CNT))
|
||||
pmu_sbi_reset_scounteren((void *)event);
|
||||
on_each_cpu_mask(mm_cpumask(event->owner->mm),
|
||||
pmu_sbi_reset_scounteren, (void *)event, 1);
|
||||
|
||||
ret = sbi_ecall(SBI_EXT_PMU, SBI_EXT_PMU_COUNTER_STOP, hwc->idx, 1, flag, 0, 0, 0);
|
||||
if (ret.error && (ret.error != SBI_ERR_ALREADY_STOPPED) &&
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
# Additional include paths needed by kselftest.h and local headers
|
||||
CFLAGS += -D_GNU_SOURCE -std=gnu99 -I.
|
||||
|
||||
TEST_GEN_FILES := testcases/mmap_default testcases/mmap_bottomup
|
||||
TEST_GEN_FILES := mmap_default mmap_bottomup
|
||||
|
||||
TEST_PROGS := testcases/run_mmap.sh
|
||||
TEST_PROGS := run_mmap.sh
|
||||
|
||||
include ../../lib.mk
|
||||
|
||||
$(OUTPUT)/mm: testcases/mmap_default.c testcases/mmap_bottomup.c testcases/mmap_tests.h
|
||||
$(OUTPUT)/mm: mmap_default.c mmap_bottomup.c mmap_tests.h
|
||||
$(CC) -o$@ $(CFLAGS) $(LDFLAGS) $^
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-only
|
||||
#include <sys/mman.h>
|
||||
#include <testcases/mmap_test.h>
|
||||
#include <mmap_test.h>
|
||||
|
||||
#include "../../kselftest_harness.h"
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-only
|
||||
#include <sys/mman.h>
|
||||
#include <testcases/mmap_test.h>
|
||||
#include <mmap_test.h>
|
||||
|
||||
#include "../../kselftest_harness.h"
|
||||
|
Loading…
Reference in New Issue