aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/arm/kernel/kprobes-thumb.c38
1 files changed, 38 insertions, 0 deletions
diff --git a/arch/arm/kernel/kprobes-thumb.c b/arch/arm/kernel/kprobes-thumb.c
index 997fc6d59a40..d3133fd2d4e8 100644
--- a/arch/arm/kernel/kprobes-thumb.c
+++ b/arch/arm/kernel/kprobes-thumb.c
@@ -141,6 +141,35 @@ t16_decode_it(kprobe_opcode_t insn, struct arch_specific_insn *asi)
141 return INSN_GOOD_NO_SLOT; 141 return INSN_GOOD_NO_SLOT;
142} 142}
143 143
144static void __kprobes
145t16_simulate_cond_branch(struct kprobe *p, struct pt_regs *regs)
146{
147 kprobe_opcode_t insn = p->opcode;
148 unsigned long pc = thumb_probe_pc(p);
149 long offset = insn & 0x7f;
150 offset -= insn & 0x80; /* Apply sign bit */
151 regs->ARM_pc = pc + (offset * 2);
152}
153
154static enum kprobe_insn __kprobes
155t16_decode_cond_branch(kprobe_opcode_t insn, struct arch_specific_insn *asi)
156{
157 int cc = (insn >> 8) & 0xf;
158 asi->insn_check_cc = kprobe_condition_checks[cc];
159 asi->insn_handler = t16_simulate_cond_branch;
160 return INSN_GOOD_NO_SLOT;
161}
162
163static void __kprobes
164t16_simulate_branch(struct kprobe *p, struct pt_regs *regs)
165{
166 kprobe_opcode_t insn = p->opcode;
167 unsigned long pc = thumb_probe_pc(p);
168 long offset = insn & 0x3ff;
169 offset -= insn & 0x400; /* Apply sign bit */
170 regs->ARM_pc = pc + (offset * 2);
171}
172
144static unsigned long __kprobes 173static unsigned long __kprobes
145t16_emulate_loregs(struct kprobe *p, struct pt_regs *regs) 174t16_emulate_loregs(struct kprobe *p, struct pt_regs *regs)
146{ 175{
@@ -472,6 +501,15 @@ const union decode_item kprobe_decode_thumb16_table[] = {
472 /* SVC 1101 1111 xxxx xxxx */ 501 /* SVC 1101 1111 xxxx xxxx */
473 DECODE_REJECT (0xfe00, 0xde00), 502 DECODE_REJECT (0xfe00, 0xde00),
474 503
504 /* Conditional branch 1101 xxxx xxxx xxxx */
505 DECODE_CUSTOM (0xf000, 0xd000, t16_decode_cond_branch),
506
507 /*
508 * Unconditional branch
509 * B 1110 0xxx xxxx xxxx
510 */
511 DECODE_SIMULATE (0xf800, 0xe000, t16_simulate_branch),
512
475 DECODE_END 513 DECODE_END
476}; 514};
477 515