^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) #include <linux/highmem.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) #include <linux/kdebug.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) #include <linux/types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) #include <linux/notifier.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <linux/sched.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/uprobes.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <asm/branch.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <asm/cpu-features.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <asm/ptrace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include "probes-common.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) static inline int insn_has_delay_slot(const union mips_instruction insn)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) return __insn_has_delay_slot(insn);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * arch_uprobe_analyze_insn - instruction analysis including validity and fixups.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * @mm: the probed address space.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * @arch_uprobe: the probepoint information.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * @addr: virtual address at which to install the probepoint
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) * Return 0 on success or a -ve number on error.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) int arch_uprobe_analyze_insn(struct arch_uprobe *aup,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) struct mm_struct *mm, unsigned long addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) union mips_instruction inst;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * For the time being this also blocks attempts to use uprobes with
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * MIPS16 and microMIPS.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) if (addr & 0x03)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) inst.word = aup->insn[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) if (__insn_is_compact_branch(inst)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) pr_notice("Uprobes for compact branches are not supported\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) aup->ixol[0] = aup->insn[insn_has_delay_slot(inst)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) aup->ixol[1] = UPROBE_BRK_UPROBE_XOL; /* NOP */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) * is_trap_insn - check if the instruction is a trap variant
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) * @insn: instruction to be checked.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) * Returns true if @insn is a trap variant.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * This definition overrides the weak definition in kernel/events/uprobes.c.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * and is needed for the case where an architecture has multiple trap
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * instructions (like PowerPC or MIPS). We treat BREAK just like the more
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) * modern conditional trap instructions.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) bool is_trap_insn(uprobe_opcode_t *insn)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) union mips_instruction inst;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) inst.word = *insn;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) switch (inst.i_format.opcode) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) case spec_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) switch (inst.r_format.func) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) case break_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) case teq_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) case tge_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) case tgeu_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) case tlt_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) case tltu_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) case tne_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) case bcond_op: /* Yes, really ... */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) switch (inst.u_format.rt) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) case teqi_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) case tgei_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) case tgeiu_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) case tlti_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) case tltiu_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) case tnei_op:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) #define UPROBE_TRAP_NR ULONG_MAX
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) * arch_uprobe_pre_xol - prepare to execute out of line.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) * @auprobe: the probepoint information.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) * @regs: reflects the saved user state of current task.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) int arch_uprobe_pre_xol(struct arch_uprobe *aup, struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) struct uprobe_task *utask = current->utask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) * Now find the EPC where to resume after the breakpoint has been
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) * dealt with. This may require emulation of a branch.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) aup->resume_epc = regs->cp0_epc + 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) if (insn_has_delay_slot((union mips_instruction) aup->insn[0])) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) __compute_return_epc_for_insn(regs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) (union mips_instruction) aup->insn[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) aup->resume_epc = regs->cp0_epc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) utask->autask.saved_trap_nr = current->thread.trap_nr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) current->thread.trap_nr = UPROBE_TRAP_NR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) regs->cp0_epc = current->utask->xol_vaddr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) int arch_uprobe_post_xol(struct arch_uprobe *aup, struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) struct uprobe_task *utask = current->utask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) current->thread.trap_nr = utask->autask.saved_trap_nr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) regs->cp0_epc = aup->resume_epc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) * If xol insn itself traps and generates a signal(Say,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) * SIGILL/SIGSEGV/etc), then detect the case where a singlestepped
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) * instruction jumps back to its own address. It is assumed that anything
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) * like do_page_fault/do_trap/etc sets thread.trap_nr != -1.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) * arch_uprobe_pre_xol/arch_uprobe_post_xol save/restore thread.trap_nr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) * arch_uprobe_xol_was_trapped() simply checks that ->trap_nr is not equal to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) * UPROBE_TRAP_NR == -1 set by arch_uprobe_pre_xol().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) bool arch_uprobe_xol_was_trapped(struct task_struct *tsk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) if (tsk->thread.trap_nr != UPROBE_TRAP_NR)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) int arch_uprobe_exception_notify(struct notifier_block *self,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) unsigned long val, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) struct die_args *args = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) struct pt_regs *regs = args->regs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) /* regs == NULL is a kernel bug */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) if (WARN_ON(!regs))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) return NOTIFY_DONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) /* We are only interested in userspace traps */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) if (!user_mode(regs))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) return NOTIFY_DONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) switch (val) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) case DIE_UPROBE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) if (uprobe_pre_sstep_notifier(regs))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) return NOTIFY_STOP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) case DIE_UPROBE_XOL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) if (uprobe_post_sstep_notifier(regs))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) return NOTIFY_STOP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) * This function gets called when XOL instruction either gets trapped or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) * the thread has a fatal signal. Reset the instruction pointer to its
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) * probed address for the potential restart or for post mortem analysis.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) void arch_uprobe_abort_xol(struct arch_uprobe *aup,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) struct uprobe_task *utask = current->utask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) instruction_pointer_set(regs, utask->vaddr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) unsigned long arch_uretprobe_hijack_return_addr(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) unsigned long trampoline_vaddr, struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) unsigned long ra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) ra = regs->regs[31];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) /* Replace the return address with the trampoline address */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) regs->regs[31] = trampoline_vaddr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) return ra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) * set_swbp - store breakpoint at a given address.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) * @auprobe: arch specific probepoint information.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) * @mm: the probed process address space.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) * @vaddr: the virtual address to insert the opcode.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) * For mm @mm, store the breakpoint instruction at @vaddr.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) * Return 0 (success) or a negative errno.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) * This version overrides the weak version in kernel/events/uprobes.c.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) * It is required to handle MIPS16 and microMIPS.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) int __weak set_swbp(struct arch_uprobe *auprobe, struct mm_struct *mm,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) unsigned long vaddr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) return uprobe_write_opcode(auprobe, mm, vaddr, UPROBE_SWBP_INSN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) void arch_uprobe_copy_ixol(struct page *page, unsigned long vaddr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) void *src, unsigned long len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) unsigned long kaddr, kstart;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) /* Initialize the slot */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) kaddr = (unsigned long)kmap_atomic(page);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) kstart = kaddr + (vaddr & ~PAGE_MASK);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) memcpy((void *)kstart, src, len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) flush_icache_range(kstart, kstart + len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) kunmap_atomic((void *)kaddr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) * uprobe_get_swbp_addr - compute address of swbp given post-swbp regs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) * @regs: Reflects the saved state of the task after it has hit a breakpoint
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) * instruction.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) * Return the address of the breakpoint instruction.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) * This overrides the weak version in kernel/events/uprobes.c.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) unsigned long uprobe_get_swbp_addr(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) return instruction_pointer(regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) * See if the instruction can be emulated.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) * Returns true if instruction was emulated, false otherwise.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) * For now we always emulate so this function just returns 0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) bool arch_uprobe_skip_sstep(struct arch_uprobe *auprobe, struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) }