From: Jon Medhurst Date: Sat, 2 Jul 2011 14:51:03 +0000 (+0100) Subject: ARM: kprobes: Decode 16-bit Thumb BX and BLX instructions X-Git-Tag: firefly_0821_release~3680^2~4950^2^2~2^2~51 X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=a9c3c29e72cc459be0ecd597f0af11a67713175b;p=firefly-linux-kernel-4.4.55.git ARM: kprobes: Decode 16-bit Thumb BX and BLX instructions Signed-off-by: Jon Medhurst Acked-by: Nicolas Pitre --- diff --git a/arch/arm/kernel/kprobes-thumb.c b/arch/arm/kernel/kprobes-thumb.c index e1cef8273126..b457da0e7397 100644 --- a/arch/arm/kernel/kprobes-thumb.c +++ b/arch/arm/kernel/kprobes-thumb.c @@ -26,6 +26,31 @@ */ #define current_cond(cpsr) ((cpsr >> 12) & 0xf) +/* + * Return the PC value for a probe in thumb code. + * This is the address of the probed instruction plus 4. + * We subtract one because the address will have bit zero set to indicate + * a pointer to thumb code. + */ +static inline unsigned long __kprobes thumb_probe_pc(struct kprobe *p) +{ + return (unsigned long)p->addr - 1 + 4; +} + +static void __kprobes +t16_simulate_bxblx(struct kprobe *p, struct pt_regs *regs) +{ + kprobe_opcode_t insn = p->opcode; + unsigned long pc = thumb_probe_pc(p); + int rm = (insn >> 3) & 0xf; + unsigned long rmv = (rm == 15) ? pc : regs->uregs[rm]; + + if (insn & (1 << 7)) /* BLX ? */ + regs->ARM_lr = (unsigned long)p->addr + 2; + + bx_write_pc(rmv, regs); +} + static unsigned long __kprobes t16_emulate_loregs(struct kprobe *p, struct pt_regs *regs) { @@ -131,6 +156,18 @@ const union decode_item kprobe_decode_thumb16_table[] = { /* MVN (register) 0100 0011 10xx xxxx */ DECODE_EMULATE (0xfc00, 0x4000, t16_emulate_loregs_noitrwflags), + /* + * Special data instructions and branch and exchange + * 0100 01xx xxxx xxxx + */ + + /* BLX pc 0100 0111 1111 1xxx */ + DECODE_REJECT (0xfff8, 0x47f8), + + /* BX (register) 0100 0111 0xxx xxxx */ + /* BLX (register) 0100 0111 1xxx xxxx */ + DECODE_SIMULATE (0xff00, 0x4700, t16_simulate_bxblx), + /* * Miscellaneous 16-bit instructions * 1011 xxxx xxxx xxxx