2 * arch/arm/kernel/kprobes-decode.c
4 * Copyright (C) 2006, 2007 Motorola Inc.
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
17 * We do not have hardware single-stepping on ARM, This
18 * effort is further complicated by the ARM not having a
19 * "next PC" register. Instructions that change the PC
20 * can't be safely single-stepped in a MP environment, so
21 * we have a lot of work to do:
23 * In the prepare phase:
24 * *) If it is an instruction that does anything
25 * with the CPU mode, we reject it for a kprobe.
26 * (This is out of laziness rather than need. The
27 * instructions could be simulated.)
29 * *) Otherwise, decode the instruction rewriting its
30 * registers to take fixed, ordered registers and
31 * setting a handler for it to run the instruction.
33 * In the execution phase by an instruction's handler:
35 * *) If the PC is written to by the instruction, the
36 * instruction must be fully simulated in software.
38 * *) Otherwise, a modified form of the instruction is
39 * directly executed. Its handler calls the
40 * instruction in insn[0]. In insn[1] is a
41 * "mov pc, lr" to return.
43 * Before calling, load up the reordered registers
44 * from the original instruction's registers. If one
45 * of the original input registers is the PC, compute
46 * and adjust the appropriate input register.
48 * After call completes, copy the output registers to
49 * the original instruction's original registers.
51 * We don't use a real breakpoint instruction since that
52 * would have us in the kernel go from SVC mode to SVC
53 * mode losing the link register. Instead we use an
54 * undefined instruction. To simplify processing, the
55 * undefined instruction used for kprobes must be reserved
56 * exclusively for kprobes use.
58 * TODO: ifdef out some instruction decoding based on architecture.
61 #include <linux/kernel.h>
62 #include <linux/kprobes.h>
63 #include <linux/module.h>
67 #define sign_extend(x, signbit) ((x) | (0 - ((x) & (1 << (signbit)))))
69 #define branch_displacement(insn) sign_extend(((insn) & 0xffffff) << 2, 25)
71 #if __LINUX_ARM_ARCH__ >= 6
72 #define BLX(reg) "blx "reg" \n\t"
74 #define BLX(reg) "mov lr, pc \n\t" \
79 * To avoid the complications of mimicing single-stepping on a
80 * processor without a Next-PC or a single-step mode, and to
81 * avoid having to deal with the side-effects of boosting, we
82 * simulate or emulate (almost) all ARM instructions.
84 * "Simulation" is where the instruction's behavior is duplicated in
85 * C code. "Emulation" is where the original instruction is rewritten
86 * and executed, often by altering its registers.
88 * By having all behavior of the kprobe'd instruction completed before
89 * returning from the kprobe_handler(), all locks (scheduler and
90 * interrupt) can safely be released. There is no need for secondary
91 * breakpoints, no race with MP or preemptable kernels, nor having to
92 * clean up resources counts at a later time impacting overall system
93 * performance. By rewriting the instruction, only the minimum registers
94 * need to be loaded and saved back optimizing performance.
96 * Calling the insnslot_*_rwflags version of a function doesn't hurt
97 * anything even when the CPSR flags aren't updated by the
98 * instruction. It's just a little slower in return for saving
99 * a little space by not having a duplicate function that doesn't
100 * update the flags. (The same optimization can be said for
101 * instructions that do or don't perform register writeback)
102 * Also, instructions can either read the flags, only write the
103 * flags, or read and write the flags. To save combinations
104 * rather than for sheer performance, flag functions just assume
105 * read and write of flags.
108 static void __kprobes
simulate_bbl(struct kprobe
*p
, struct pt_regs
*regs
)
110 kprobe_opcode_t insn
= p
->opcode
;
111 long iaddr
= (long)p
->addr
;
112 int disp
= branch_displacement(insn
);
114 if (insn
& (1 << 24))
115 regs
->ARM_lr
= iaddr
+ 4;
117 regs
->ARM_pc
= iaddr
+ 8 + disp
;
120 static void __kprobes
simulate_blx1(struct kprobe
*p
, struct pt_regs
*regs
)
122 kprobe_opcode_t insn
= p
->opcode
;
123 long iaddr
= (long)p
->addr
;
124 int disp
= branch_displacement(insn
);
126 regs
->ARM_lr
= iaddr
+ 4;
127 regs
->ARM_pc
= iaddr
+ 8 + disp
+ ((insn
>> 23) & 0x2);
128 regs
->ARM_cpsr
|= PSR_T_BIT
;
131 static void __kprobes
simulate_blx2bx(struct kprobe
*p
, struct pt_regs
*regs
)
133 kprobe_opcode_t insn
= p
->opcode
;
135 long rmv
= regs
->uregs
[rm
];
138 regs
->ARM_lr
= (long)p
->addr
+ 4;
140 regs
->ARM_pc
= rmv
& ~0x1;
141 regs
->ARM_cpsr
&= ~PSR_T_BIT
;
143 regs
->ARM_cpsr
|= PSR_T_BIT
;
146 static void __kprobes
simulate_mrs(struct kprobe
*p
, struct pt_regs
*regs
)
148 kprobe_opcode_t insn
= p
->opcode
;
149 int rd
= (insn
>> 12) & 0xf;
150 unsigned long mask
= 0xf8ff03df; /* Mask out execution state */
151 regs
->uregs
[rd
] = regs
->ARM_cpsr
& mask
;
154 static void __kprobes
simulate_mov_ipsp(struct kprobe
*p
, struct pt_regs
*regs
)
156 regs
->uregs
[12] = regs
->uregs
[13];
159 static void __kprobes
160 emulate_ldrdstrd(struct kprobe
*p
, struct pt_regs
*regs
)
162 kprobe_opcode_t insn
= p
->opcode
;
163 unsigned long pc
= (unsigned long)p
->addr
+ 8;
164 int rt
= (insn
>> 12) & 0xf;
165 int rn
= (insn
>> 16) & 0xf;
168 register unsigned long rtv
asm("r0") = regs
->uregs
[rt
];
169 register unsigned long rt2v
asm("r1") = regs
->uregs
[rt
+1];
170 register unsigned long rnv
asm("r2") = (rn
== 15) ? pc
172 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
174 __asm__
__volatile__ (
176 : "=r" (rtv
), "=r" (rt2v
), "=r" (rnv
)
177 : "0" (rtv
), "1" (rt2v
), "2" (rnv
), "r" (rmv
),
178 [fn
] "r" (p
->ainsn
.insn_fn
)
179 : "lr", "memory", "cc"
182 regs
->uregs
[rt
] = rtv
;
183 regs
->uregs
[rt
+1] = rt2v
;
184 if (is_writeback(insn
))
185 regs
->uregs
[rn
] = rnv
;
188 static void __kprobes
189 emulate_ldr(struct kprobe
*p
, struct pt_regs
*regs
)
191 kprobe_opcode_t insn
= p
->opcode
;
192 unsigned long pc
= (unsigned long)p
->addr
+ 8;
193 int rt
= (insn
>> 12) & 0xf;
194 int rn
= (insn
>> 16) & 0xf;
197 register unsigned long rtv
asm("r0");
198 register unsigned long rnv
asm("r2") = (rn
== 15) ? pc
200 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
202 __asm__
__volatile__ (
204 : "=r" (rtv
), "=r" (rnv
)
205 : "1" (rnv
), "r" (rmv
), [fn
] "r" (p
->ainsn
.insn_fn
)
206 : "lr", "memory", "cc"
210 load_write_pc(rtv
, regs
);
212 regs
->uregs
[rt
] = rtv
;
214 if (is_writeback(insn
))
215 regs
->uregs
[rn
] = rnv
;
218 static void __kprobes
219 emulate_str(struct kprobe
*p
, struct pt_regs
*regs
)
221 kprobe_opcode_t insn
= p
->opcode
;
222 unsigned long rtpc
= (unsigned long)p
->addr
+ str_pc_offset
;
223 unsigned long rnpc
= (unsigned long)p
->addr
+ 8;
224 int rt
= (insn
>> 12) & 0xf;
225 int rn
= (insn
>> 16) & 0xf;
228 register unsigned long rtv
asm("r0") = (rt
== 15) ? rtpc
230 register unsigned long rnv
asm("r2") = (rn
== 15) ? rnpc
232 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
234 __asm__
__volatile__ (
237 : "r" (rtv
), "0" (rnv
), "r" (rmv
), [fn
] "r" (p
->ainsn
.insn_fn
)
238 : "lr", "memory", "cc"
241 if (is_writeback(insn
))
242 regs
->uregs
[rn
] = rnv
;
245 static void __kprobes
246 emulate_rd12rn16rm0rs8_rwflags(struct kprobe
*p
, struct pt_regs
*regs
)
248 kprobe_opcode_t insn
= p
->opcode
;
249 unsigned long pc
= (unsigned long)p
->addr
+ 8;
250 int rd
= (insn
>> 12) & 0xf;
251 int rn
= (insn
>> 16) & 0xf;
253 int rs
= (insn
>> 8) & 0xf;
255 register unsigned long rdv
asm("r0") = regs
->uregs
[rd
];
256 register unsigned long rnv
asm("r2") = (rn
== 15) ? pc
258 register unsigned long rmv
asm("r3") = (rm
== 15) ? pc
260 register unsigned long rsv
asm("r1") = regs
->uregs
[rs
];
261 unsigned long cpsr
= regs
->ARM_cpsr
;
263 __asm__
__volatile__ (
264 "msr cpsr_fs, %[cpsr] \n\t"
266 "mrs %[cpsr], cpsr \n\t"
267 : "=r" (rdv
), [cpsr
] "=r" (cpsr
)
268 : "0" (rdv
), "r" (rnv
), "r" (rmv
), "r" (rsv
),
269 "1" (cpsr
), [fn
] "r" (p
->ainsn
.insn_fn
)
270 : "lr", "memory", "cc"
274 alu_write_pc(rdv
, regs
);
276 regs
->uregs
[rd
] = rdv
;
277 regs
->ARM_cpsr
= (regs
->ARM_cpsr
& ~APSR_MASK
) | (cpsr
& APSR_MASK
);
280 static void __kprobes
281 emulate_rd12rn16rm0_rwflags_nopc(struct kprobe
*p
, struct pt_regs
*regs
)
283 kprobe_opcode_t insn
= p
->opcode
;
284 int rd
= (insn
>> 12) & 0xf;
285 int rn
= (insn
>> 16) & 0xf;
288 register unsigned long rdv
asm("r0") = regs
->uregs
[rd
];
289 register unsigned long rnv
asm("r2") = regs
->uregs
[rn
];
290 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
291 unsigned long cpsr
= regs
->ARM_cpsr
;
293 __asm__
__volatile__ (
294 "msr cpsr_fs, %[cpsr] \n\t"
296 "mrs %[cpsr], cpsr \n\t"
297 : "=r" (rdv
), [cpsr
] "=r" (cpsr
)
298 : "0" (rdv
), "r" (rnv
), "r" (rmv
),
299 "1" (cpsr
), [fn
] "r" (p
->ainsn
.insn_fn
)
300 : "lr", "memory", "cc"
303 regs
->uregs
[rd
] = rdv
;
304 regs
->ARM_cpsr
= (regs
->ARM_cpsr
& ~APSR_MASK
) | (cpsr
& APSR_MASK
);
307 static void __kprobes
308 emulate_rd16rn12rm0rs8_rwflags_nopc(struct kprobe
*p
, struct pt_regs
*regs
)
310 kprobe_opcode_t insn
= p
->opcode
;
311 int rd
= (insn
>> 16) & 0xf;
312 int rn
= (insn
>> 12) & 0xf;
314 int rs
= (insn
>> 8) & 0xf;
316 register unsigned long rdv
asm("r2") = regs
->uregs
[rd
];
317 register unsigned long rnv
asm("r0") = regs
->uregs
[rn
];
318 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
319 register unsigned long rsv
asm("r1") = regs
->uregs
[rs
];
320 unsigned long cpsr
= regs
->ARM_cpsr
;
322 __asm__
__volatile__ (
323 "msr cpsr_fs, %[cpsr] \n\t"
325 "mrs %[cpsr], cpsr \n\t"
326 : "=r" (rdv
), [cpsr
] "=r" (cpsr
)
327 : "0" (rdv
), "r" (rnv
), "r" (rmv
), "r" (rsv
),
328 "1" (cpsr
), [fn
] "r" (p
->ainsn
.insn_fn
)
329 : "lr", "memory", "cc"
332 regs
->uregs
[rd
] = rdv
;
333 regs
->ARM_cpsr
= (regs
->ARM_cpsr
& ~APSR_MASK
) | (cpsr
& APSR_MASK
);
336 static void __kprobes
337 emulate_rd12rm0_noflags_nopc(struct kprobe
*p
, struct pt_regs
*regs
)
339 kprobe_opcode_t insn
= p
->opcode
;
340 int rd
= (insn
>> 12) & 0xf;
343 register unsigned long rdv
asm("r0") = regs
->uregs
[rd
];
344 register unsigned long rmv
asm("r3") = regs
->uregs
[rm
];
346 __asm__
__volatile__ (
349 : "0" (rdv
), "r" (rmv
), [fn
] "r" (p
->ainsn
.insn_fn
)
350 : "lr", "memory", "cc"
353 regs
->uregs
[rd
] = rdv
;
356 static void __kprobes
357 emulate_rdlo12rdhi16rn0rm8_rwflags_nopc(struct kprobe
*p
, struct pt_regs
*regs
)
359 kprobe_opcode_t insn
= p
->opcode
;
360 int rdlo
= (insn
>> 12) & 0xf;
361 int rdhi
= (insn
>> 16) & 0xf;
363 int rm
= (insn
>> 8) & 0xf;
365 register unsigned long rdlov
asm("r0") = regs
->uregs
[rdlo
];
366 register unsigned long rdhiv
asm("r2") = regs
->uregs
[rdhi
];
367 register unsigned long rnv
asm("r3") = regs
->uregs
[rn
];
368 register unsigned long rmv
asm("r1") = regs
->uregs
[rm
];
369 unsigned long cpsr
= regs
->ARM_cpsr
;
371 __asm__
__volatile__ (
372 "msr cpsr_fs, %[cpsr] \n\t"
374 "mrs %[cpsr], cpsr \n\t"
375 : "=r" (rdlov
), "=r" (rdhiv
), [cpsr
] "=r" (cpsr
)
376 : "0" (rdlov
), "1" (rdhiv
), "r" (rnv
), "r" (rmv
),
377 "2" (cpsr
), [fn
] "r" (p
->ainsn
.insn_fn
)
378 : "lr", "memory", "cc"
381 regs
->uregs
[rdlo
] = rdlov
;
382 regs
->uregs
[rdhi
] = rdhiv
;
383 regs
->ARM_cpsr
= (regs
->ARM_cpsr
& ~APSR_MASK
) | (cpsr
& APSR_MASK
);
387 * For the instruction masking and comparisons in all the "space_*"
388 * functions below, Do _not_ rearrange the order of tests unless
389 * you're very, very sure of what you are doing. For the sake of
390 * efficiency, the masks for some tests sometimes assume other test
391 * have been done prior to them so the number of patterns to test
392 * for an instruction set can be as broad as possible to reduce the
393 * number of tests needed.
396 static const union decode_item arm_1111_table
[] = {
397 /* Unconditional instructions */
399 /* memory hint 1111 0100 x001 xxxx xxxx xxxx xxxx xxxx */
400 /* PLDI (immediate) 1111 0100 x101 xxxx xxxx xxxx xxxx xxxx */
401 /* PLDW (immediate) 1111 0101 x001 xxxx xxxx xxxx xxxx xxxx */
402 /* PLD (immediate) 1111 0101 x101 xxxx xxxx xxxx xxxx xxxx */
403 DECODE_SIMULATE (0xfe300000, 0xf4100000, kprobe_simulate_nop
),
405 /* memory hint 1111 0110 x001 xxxx xxxx xxxx xxx0 xxxx */
406 /* PLDI (register) 1111 0110 x101 xxxx xxxx xxxx xxx0 xxxx */
407 /* PLDW (register) 1111 0111 x001 xxxx xxxx xxxx xxx0 xxxx */
408 /* PLD (register) 1111 0111 x101 xxxx xxxx xxxx xxx0 xxxx */
409 DECODE_SIMULATE (0xfe300010, 0xf6100000, kprobe_simulate_nop
),
411 /* BLX (immediate) 1111 101x xxxx xxxx xxxx xxxx xxxx xxxx */
412 DECODE_SIMULATE (0xfe000000, 0xfa000000, simulate_blx1
),
414 /* CPS 1111 0001 0000 xxx0 xxxx xxxx xx0x xxxx */
415 /* SETEND 1111 0001 0000 0001 xxxx xxxx 0000 xxxx */
416 /* SRS 1111 100x x1x0 xxxx xxxx xxxx xxxx xxxx */
417 /* RFE 1111 100x x0x1 xxxx xxxx xxxx xxxx xxxx */
419 /* Coprocessor instructions... */
420 /* MCRR2 1111 1100 0100 xxxx xxxx xxxx xxxx xxxx */
421 /* MRRC2 1111 1100 0101 xxxx xxxx xxxx xxxx xxxx */
422 /* LDC2 1111 110x xxx1 xxxx xxxx xxxx xxxx xxxx */
423 /* STC2 1111 110x xxx0 xxxx xxxx xxxx xxxx xxxx */
424 /* CDP2 1111 1110 xxxx xxxx xxxx xxxx xxx0 xxxx */
425 /* MCR2 1111 1110 xxx0 xxxx xxxx xxxx xxx1 xxxx */
426 /* MRC2 1111 1110 xxx1 xxxx xxxx xxxx xxx1 xxxx */
428 /* Other unallocated instructions... */
432 static const union decode_item arm_cccc_0001_0xx0____0xxx_table
[] = {
433 /* Miscellaneous instructions */
435 /* MRS cpsr cccc 0001 0000 xxxx xxxx xxxx 0000 xxxx */
436 DECODE_SIMULATEX(0x0ff000f0, 0x01000000, simulate_mrs
,
437 REGS(0, NOPC
, 0, 0, 0)),
439 /* BX cccc 0001 0010 xxxx xxxx xxxx 0001 xxxx */
440 DECODE_SIMULATE (0x0ff000f0, 0x01200010, simulate_blx2bx
),
442 /* BLX (register) cccc 0001 0010 xxxx xxxx xxxx 0011 xxxx */
443 DECODE_SIMULATEX(0x0ff000f0, 0x01200030, simulate_blx2bx
,
444 REGS(0, 0, 0, 0, NOPC
)),
446 /* CLZ cccc 0001 0110 xxxx xxxx xxxx 0001 xxxx */
447 DECODE_EMULATEX (0x0ff000f0, 0x01600010, emulate_rd12rm0_noflags_nopc
,
448 REGS(0, NOPC
, 0, 0, NOPC
)),
450 /* QADD cccc 0001 0000 xxxx xxxx xxxx 0101 xxxx */
451 /* QSUB cccc 0001 0010 xxxx xxxx xxxx 0101 xxxx */
452 /* QDADD cccc 0001 0100 xxxx xxxx xxxx 0101 xxxx */
453 /* QDSUB cccc 0001 0110 xxxx xxxx xxxx 0101 xxxx */
454 DECODE_EMULATEX (0x0f9000f0, 0x01000050, emulate_rd12rn16rm0_rwflags_nopc
,
455 REGS(NOPC
, NOPC
, 0, 0, NOPC
)),
457 /* BXJ cccc 0001 0010 xxxx xxxx xxxx 0010 xxxx */
458 /* MSR cccc 0001 0x10 xxxx xxxx xxxx 0000 xxxx */
459 /* MRS spsr cccc 0001 0100 xxxx xxxx xxxx 0000 xxxx */
460 /* BKPT 1110 0001 0010 xxxx xxxx xxxx 0111 xxxx */
461 /* SMC cccc 0001 0110 xxxx xxxx xxxx 0111 xxxx */
462 /* And unallocated instructions... */
466 static const union decode_item arm_cccc_0001_0xx0____1xx0_table
[] = {
467 /* Halfword multiply and multiply-accumulate */
469 /* SMLALxy cccc 0001 0100 xxxx xxxx xxxx 1xx0 xxxx */
470 DECODE_EMULATEX (0x0ff00090, 0x01400080, emulate_rdlo12rdhi16rn0rm8_rwflags_nopc
,
471 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
473 /* SMULWy cccc 0001 0010 xxxx xxxx xxxx 1x10 xxxx */
474 DECODE_OR (0x0ff000b0, 0x012000a0),
475 /* SMULxy cccc 0001 0110 xxxx xxxx xxxx 1xx0 xxxx */
476 DECODE_EMULATEX (0x0ff00090, 0x01600080, emulate_rd16rn12rm0rs8_rwflags_nopc
,
477 REGS(NOPC
, 0, NOPC
, 0, NOPC
)),
479 /* SMLAxy cccc 0001 0000 xxxx xxxx xxxx 1xx0 xxxx */
480 DECODE_OR (0x0ff00090, 0x01000080),
481 /* SMLAWy cccc 0001 0010 xxxx xxxx xxxx 1x00 xxxx */
482 DECODE_EMULATEX (0x0ff000b0, 0x01200080, emulate_rd16rn12rm0rs8_rwflags_nopc
,
483 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
488 static const union decode_item arm_cccc_0000_____1001_table
[] = {
489 /* Multiply and multiply-accumulate */
491 /* MUL cccc 0000 0000 xxxx xxxx xxxx 1001 xxxx */
492 /* MULS cccc 0000 0001 xxxx xxxx xxxx 1001 xxxx */
493 DECODE_EMULATEX (0x0fe000f0, 0x00000090, emulate_rd16rn12rm0rs8_rwflags_nopc
,
494 REGS(NOPC
, 0, NOPC
, 0, NOPC
)),
496 /* MLA cccc 0000 0010 xxxx xxxx xxxx 1001 xxxx */
497 /* MLAS cccc 0000 0011 xxxx xxxx xxxx 1001 xxxx */
498 DECODE_OR (0x0fe000f0, 0x00200090),
499 /* MLS cccc 0000 0110 xxxx xxxx xxxx 1001 xxxx */
500 DECODE_EMULATEX (0x0ff000f0, 0x00600090, emulate_rd16rn12rm0rs8_rwflags_nopc
,
501 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
503 /* UMAAL cccc 0000 0100 xxxx xxxx xxxx 1001 xxxx */
504 DECODE_OR (0x0ff000f0, 0x00400090),
505 /* UMULL cccc 0000 1000 xxxx xxxx xxxx 1001 xxxx */
506 /* UMULLS cccc 0000 1001 xxxx xxxx xxxx 1001 xxxx */
507 /* UMLAL cccc 0000 1010 xxxx xxxx xxxx 1001 xxxx */
508 /* UMLALS cccc 0000 1011 xxxx xxxx xxxx 1001 xxxx */
509 /* SMULL cccc 0000 1100 xxxx xxxx xxxx 1001 xxxx */
510 /* SMULLS cccc 0000 1101 xxxx xxxx xxxx 1001 xxxx */
511 /* SMLAL cccc 0000 1110 xxxx xxxx xxxx 1001 xxxx */
512 /* SMLALS cccc 0000 1111 xxxx xxxx xxxx 1001 xxxx */
513 DECODE_EMULATEX (0x0f8000f0, 0x00800090, emulate_rdlo12rdhi16rn0rm8_rwflags_nopc
,
514 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
519 static const union decode_item arm_cccc_0001_____1001_table
[] = {
520 /* Synchronization primitives */
522 #if __LINUX_ARM_ARCH__ < 6
523 /* Deprecated on ARMv6 and may be UNDEFINED on v7 */
524 /* SMP/SWPB cccc 0001 0x00 xxxx xxxx xxxx 1001 xxxx */
525 DECODE_EMULATEX (0x0fb000f0, 0x01000090, emulate_rd12rn16rm0_rwflags_nopc
,
526 REGS(NOPC
, NOPC
, 0, 0, NOPC
)),
528 /* LDREX/STREX{,D,B,H} cccc 0001 1xxx xxxx xxxx xxxx 1001 xxxx */
529 /* And unallocated instructions... */
533 static const union decode_item arm_cccc_000x_____1xx1_table
[] = {
534 /* Extra load/store instructions */
536 /* STRHT cccc 0000 xx10 xxxx xxxx xxxx 1011 xxxx */
537 /* ??? cccc 0000 xx10 xxxx xxxx xxxx 11x1 xxxx */
538 /* LDRHT cccc 0000 xx11 xxxx xxxx xxxx 1011 xxxx */
539 /* LDRSBT cccc 0000 xx11 xxxx xxxx xxxx 1101 xxxx */
540 /* LDRSHT cccc 0000 xx11 xxxx xxxx xxxx 1111 xxxx */
541 DECODE_REJECT (0x0f200090, 0x00200090),
543 /* LDRD/STRD lr,pc,{... cccc 000x x0x0 xxxx 111x xxxx 1101 xxxx */
544 DECODE_REJECT (0x0e10e0d0, 0x0000e0d0),
546 /* LDRD (register) cccc 000x x0x0 xxxx xxxx xxxx 1101 xxxx */
547 /* STRD (register) cccc 000x x0x0 xxxx xxxx xxxx 1111 xxxx */
548 DECODE_EMULATEX (0x0e5000d0, 0x000000d0, emulate_ldrdstrd
,
549 REGS(NOPCWB
, NOPCX
, 0, 0, NOPC
)),
551 /* LDRD (immediate) cccc 000x x1x0 xxxx xxxx xxxx 1101 xxxx */
552 /* STRD (immediate) cccc 000x x1x0 xxxx xxxx xxxx 1111 xxxx */
553 DECODE_EMULATEX (0x0e5000d0, 0x004000d0, emulate_ldrdstrd
,
554 REGS(NOPCWB
, NOPCX
, 0, 0, 0)),
556 /* STRH (register) cccc 000x x0x0 xxxx xxxx xxxx 1011 xxxx */
557 DECODE_EMULATEX (0x0e5000f0, 0x000000b0, emulate_str
,
558 REGS(NOPCWB
, NOPC
, 0, 0, NOPC
)),
560 /* LDRH (register) cccc 000x x0x1 xxxx xxxx xxxx 1011 xxxx */
561 /* LDRSB (register) cccc 000x x0x1 xxxx xxxx xxxx 1101 xxxx */
562 /* LDRSH (register) cccc 000x x0x1 xxxx xxxx xxxx 1111 xxxx */
563 DECODE_EMULATEX (0x0e500090, 0x00100090, emulate_ldr
,
564 REGS(NOPCWB
, NOPC
, 0, 0, NOPC
)),
566 /* STRH (immediate) cccc 000x x1x0 xxxx xxxx xxxx 1011 xxxx */
567 DECODE_EMULATEX (0x0e5000f0, 0x004000b0, emulate_str
,
568 REGS(NOPCWB
, NOPC
, 0, 0, 0)),
570 /* LDRH (immediate) cccc 000x x1x1 xxxx xxxx xxxx 1011 xxxx */
571 /* LDRSB (immediate) cccc 000x x1x1 xxxx xxxx xxxx 1101 xxxx */
572 /* LDRSH (immediate) cccc 000x x1x1 xxxx xxxx xxxx 1111 xxxx */
573 DECODE_EMULATEX (0x0e500090, 0x00500090, emulate_ldr
,
574 REGS(NOPCWB
, NOPC
, 0, 0, 0)),
579 static const union decode_item arm_cccc_000x_table
[] = {
580 /* Data-processing (register) */
582 /* <op>S PC, ... cccc 000x xxx1 xxxx 1111 xxxx xxxx xxxx */
583 DECODE_REJECT (0x0e10f000, 0x0010f000),
585 /* MOV IP, SP 1110 0001 1010 0000 1100 0000 0000 1101 */
586 DECODE_SIMULATE (0xffffffff, 0xe1a0c00d, simulate_mov_ipsp
),
588 /* TST (register) cccc 0001 0001 xxxx xxxx xxxx xxx0 xxxx */
589 /* TEQ (register) cccc 0001 0011 xxxx xxxx xxxx xxx0 xxxx */
590 /* CMP (register) cccc 0001 0101 xxxx xxxx xxxx xxx0 xxxx */
591 /* CMN (register) cccc 0001 0111 xxxx xxxx xxxx xxx0 xxxx */
592 DECODE_EMULATEX (0x0f900010, 0x01100000, emulate_rd12rn16rm0rs8_rwflags
,
593 REGS(ANY
, 0, 0, 0, ANY
)),
595 /* MOV (register) cccc 0001 101x xxxx xxxx xxxx xxx0 xxxx */
596 /* MVN (register) cccc 0001 111x xxxx xxxx xxxx xxx0 xxxx */
597 DECODE_EMULATEX (0x0fa00010, 0x01a00000, emulate_rd12rn16rm0rs8_rwflags
,
598 REGS(0, ANY
, 0, 0, ANY
)),
600 /* AND (register) cccc 0000 000x xxxx xxxx xxxx xxx0 xxxx */
601 /* EOR (register) cccc 0000 001x xxxx xxxx xxxx xxx0 xxxx */
602 /* SUB (register) cccc 0000 010x xxxx xxxx xxxx xxx0 xxxx */
603 /* RSB (register) cccc 0000 011x xxxx xxxx xxxx xxx0 xxxx */
604 /* ADD (register) cccc 0000 100x xxxx xxxx xxxx xxx0 xxxx */
605 /* ADC (register) cccc 0000 101x xxxx xxxx xxxx xxx0 xxxx */
606 /* SBC (register) cccc 0000 110x xxxx xxxx xxxx xxx0 xxxx */
607 /* RSC (register) cccc 0000 111x xxxx xxxx xxxx xxx0 xxxx */
608 /* ORR (register) cccc 0001 100x xxxx xxxx xxxx xxx0 xxxx */
609 /* BIC (register) cccc 0001 110x xxxx xxxx xxxx xxx0 xxxx */
610 DECODE_EMULATEX (0x0e000010, 0x00000000, emulate_rd12rn16rm0rs8_rwflags
,
611 REGS(ANY
, ANY
, 0, 0, ANY
)),
613 /* TST (reg-shift reg) cccc 0001 0001 xxxx xxxx xxxx 0xx1 xxxx */
614 /* TEQ (reg-shift reg) cccc 0001 0011 xxxx xxxx xxxx 0xx1 xxxx */
615 /* CMP (reg-shift reg) cccc 0001 0101 xxxx xxxx xxxx 0xx1 xxxx */
616 /* CMN (reg-shift reg) cccc 0001 0111 xxxx xxxx xxxx 0xx1 xxxx */
617 DECODE_EMULATEX (0x0f900090, 0x01100010, emulate_rd12rn16rm0rs8_rwflags
,
618 REGS(ANY
, 0, NOPC
, 0, ANY
)),
620 /* MOV (reg-shift reg) cccc 0001 101x xxxx xxxx xxxx 0xx1 xxxx */
621 /* MVN (reg-shift reg) cccc 0001 111x xxxx xxxx xxxx 0xx1 xxxx */
622 DECODE_EMULATEX (0x0fa00090, 0x01a00010, emulate_rd12rn16rm0rs8_rwflags
,
623 REGS(0, ANY
, NOPC
, 0, ANY
)),
625 /* AND (reg-shift reg) cccc 0000 000x xxxx xxxx xxxx 0xx1 xxxx */
626 /* EOR (reg-shift reg) cccc 0000 001x xxxx xxxx xxxx 0xx1 xxxx */
627 /* SUB (reg-shift reg) cccc 0000 010x xxxx xxxx xxxx 0xx1 xxxx */
628 /* RSB (reg-shift reg) cccc 0000 011x xxxx xxxx xxxx 0xx1 xxxx */
629 /* ADD (reg-shift reg) cccc 0000 100x xxxx xxxx xxxx 0xx1 xxxx */
630 /* ADC (reg-shift reg) cccc 0000 101x xxxx xxxx xxxx 0xx1 xxxx */
631 /* SBC (reg-shift reg) cccc 0000 110x xxxx xxxx xxxx 0xx1 xxxx */
632 /* RSC (reg-shift reg) cccc 0000 111x xxxx xxxx xxxx 0xx1 xxxx */
633 /* ORR (reg-shift reg) cccc 0001 100x xxxx xxxx xxxx 0xx1 xxxx */
634 /* BIC (reg-shift reg) cccc 0001 110x xxxx xxxx xxxx 0xx1 xxxx */
635 DECODE_EMULATEX (0x0e000090, 0x00000010, emulate_rd12rn16rm0rs8_rwflags
,
636 REGS(ANY
, ANY
, NOPC
, 0, ANY
)),
641 static const union decode_item arm_cccc_001x_table
[] = {
642 /* Data-processing (immediate) */
644 /* MOVW cccc 0011 0000 xxxx xxxx xxxx xxxx xxxx */
645 /* MOVT cccc 0011 0100 xxxx xxxx xxxx xxxx xxxx */
646 DECODE_EMULATEX (0x0fb00000, 0x03000000, emulate_rd12rm0_noflags_nopc
,
647 REGS(0, NOPC
, 0, 0, 0)),
649 /* YIELD cccc 0011 0010 0000 xxxx xxxx 0000 0001 */
650 DECODE_OR (0x0fff00ff, 0x03200001),
651 /* SEV cccc 0011 0010 0000 xxxx xxxx 0000 0100 */
652 DECODE_EMULATE (0x0fff00ff, 0x03200004, kprobe_emulate_none
),
653 /* NOP cccc 0011 0010 0000 xxxx xxxx 0000 0000 */
654 /* WFE cccc 0011 0010 0000 xxxx xxxx 0000 0010 */
655 /* WFI cccc 0011 0010 0000 xxxx xxxx 0000 0011 */
656 DECODE_SIMULATE (0x0fff00fc, 0x03200000, kprobe_simulate_nop
),
657 /* DBG cccc 0011 0010 0000 xxxx xxxx ffff xxxx */
658 /* unallocated hints cccc 0011 0010 0000 xxxx xxxx xxxx xxxx */
659 /* MSR (immediate) cccc 0011 0x10 xxxx xxxx xxxx xxxx xxxx */
660 DECODE_REJECT (0x0fb00000, 0x03200000),
662 /* <op>S PC, ... cccc 001x xxx1 xxxx 1111 xxxx xxxx xxxx */
663 DECODE_REJECT (0x0e10f000, 0x0210f000),
665 /* TST (immediate) cccc 0011 0001 xxxx xxxx xxxx xxxx xxxx */
666 /* TEQ (immediate) cccc 0011 0011 xxxx xxxx xxxx xxxx xxxx */
667 /* CMP (immediate) cccc 0011 0101 xxxx xxxx xxxx xxxx xxxx */
668 /* CMN (immediate) cccc 0011 0111 xxxx xxxx xxxx xxxx xxxx */
669 DECODE_EMULATEX (0x0f900000, 0x03100000, emulate_rd12rn16rm0rs8_rwflags
,
670 REGS(ANY
, 0, 0, 0, 0)),
672 /* MOV (immediate) cccc 0011 101x xxxx xxxx xxxx xxxx xxxx */
673 /* MVN (immediate) cccc 0011 111x xxxx xxxx xxxx xxxx xxxx */
674 DECODE_EMULATEX (0x0fa00000, 0x03a00000, emulate_rd12rn16rm0rs8_rwflags
,
675 REGS(0, ANY
, 0, 0, 0)),
677 /* AND (immediate) cccc 0010 000x xxxx xxxx xxxx xxxx xxxx */
678 /* EOR (immediate) cccc 0010 001x xxxx xxxx xxxx xxxx xxxx */
679 /* SUB (immediate) cccc 0010 010x xxxx xxxx xxxx xxxx xxxx */
680 /* RSB (immediate) cccc 0010 011x xxxx xxxx xxxx xxxx xxxx */
681 /* ADD (immediate) cccc 0010 100x xxxx xxxx xxxx xxxx xxxx */
682 /* ADC (immediate) cccc 0010 101x xxxx xxxx xxxx xxxx xxxx */
683 /* SBC (immediate) cccc 0010 110x xxxx xxxx xxxx xxxx xxxx */
684 /* RSC (immediate) cccc 0010 111x xxxx xxxx xxxx xxxx xxxx */
685 /* ORR (immediate) cccc 0011 100x xxxx xxxx xxxx xxxx xxxx */
686 /* BIC (immediate) cccc 0011 110x xxxx xxxx xxxx xxxx xxxx */
687 DECODE_EMULATEX (0x0e000000, 0x02000000, emulate_rd12rn16rm0rs8_rwflags
,
688 REGS(ANY
, ANY
, 0, 0, 0)),
693 static const union decode_item arm_cccc_0110_____xxx1_table
[] = {
694 /* Media instructions */
696 /* SEL cccc 0110 1000 xxxx xxxx xxxx 1011 xxxx */
697 DECODE_EMULATEX (0x0ff000f0, 0x068000b0, emulate_rd12rn16rm0_rwflags_nopc
,
698 REGS(NOPC
, NOPC
, 0, 0, NOPC
)),
700 /* SSAT cccc 0110 101x xxxx xxxx xxxx xx01 xxxx */
701 /* USAT cccc 0110 111x xxxx xxxx xxxx xx01 xxxx */
702 DECODE_OR(0x0fa00030, 0x06a00010),
703 /* SSAT16 cccc 0110 1010 xxxx xxxx xxxx 0011 xxxx */
704 /* USAT16 cccc 0110 1110 xxxx xxxx xxxx 0011 xxxx */
705 DECODE_EMULATEX (0x0fb000f0, 0x06a00030, emulate_rd12rn16rm0_rwflags_nopc
,
706 REGS(0, NOPC
, 0, 0, NOPC
)),
708 /* REV cccc 0110 1011 xxxx xxxx xxxx 0011 xxxx */
709 /* REV16 cccc 0110 1011 xxxx xxxx xxxx 1011 xxxx */
710 /* RBIT cccc 0110 1111 xxxx xxxx xxxx 0011 xxxx */
711 /* REVSH cccc 0110 1111 xxxx xxxx xxxx 1011 xxxx */
712 DECODE_EMULATEX (0x0fb00070, 0x06b00030, emulate_rd12rm0_noflags_nopc
,
713 REGS(0, NOPC
, 0, 0, NOPC
)),
715 /* ??? cccc 0110 0x00 xxxx xxxx xxxx xxx1 xxxx */
716 DECODE_REJECT (0x0fb00010, 0x06000010),
717 /* ??? cccc 0110 0xxx xxxx xxxx xxxx 1011 xxxx */
718 DECODE_REJECT (0x0f8000f0, 0x060000b0),
719 /* ??? cccc 0110 0xxx xxxx xxxx xxxx 1101 xxxx */
720 DECODE_REJECT (0x0f8000f0, 0x060000d0),
721 /* SADD16 cccc 0110 0001 xxxx xxxx xxxx 0001 xxxx */
722 /* SADDSUBX cccc 0110 0001 xxxx xxxx xxxx 0011 xxxx */
723 /* SSUBADDX cccc 0110 0001 xxxx xxxx xxxx 0101 xxxx */
724 /* SSUB16 cccc 0110 0001 xxxx xxxx xxxx 0111 xxxx */
725 /* SADD8 cccc 0110 0001 xxxx xxxx xxxx 1001 xxxx */
726 /* SSUB8 cccc 0110 0001 xxxx xxxx xxxx 1111 xxxx */
727 /* QADD16 cccc 0110 0010 xxxx xxxx xxxx 0001 xxxx */
728 /* QADDSUBX cccc 0110 0010 xxxx xxxx xxxx 0011 xxxx */
729 /* QSUBADDX cccc 0110 0010 xxxx xxxx xxxx 0101 xxxx */
730 /* QSUB16 cccc 0110 0010 xxxx xxxx xxxx 0111 xxxx */
731 /* QADD8 cccc 0110 0010 xxxx xxxx xxxx 1001 xxxx */
732 /* QSUB8 cccc 0110 0010 xxxx xxxx xxxx 1111 xxxx */
733 /* SHADD16 cccc 0110 0011 xxxx xxxx xxxx 0001 xxxx */
734 /* SHADDSUBX cccc 0110 0011 xxxx xxxx xxxx 0011 xxxx */
735 /* SHSUBADDX cccc 0110 0011 xxxx xxxx xxxx 0101 xxxx */
736 /* SHSUB16 cccc 0110 0011 xxxx xxxx xxxx 0111 xxxx */
737 /* SHADD8 cccc 0110 0011 xxxx xxxx xxxx 1001 xxxx */
738 /* SHSUB8 cccc 0110 0011 xxxx xxxx xxxx 1111 xxxx */
739 /* UADD16 cccc 0110 0101 xxxx xxxx xxxx 0001 xxxx */
740 /* UADDSUBX cccc 0110 0101 xxxx xxxx xxxx 0011 xxxx */
741 /* USUBADDX cccc 0110 0101 xxxx xxxx xxxx 0101 xxxx */
742 /* USUB16 cccc 0110 0101 xxxx xxxx xxxx 0111 xxxx */
743 /* UADD8 cccc 0110 0101 xxxx xxxx xxxx 1001 xxxx */
744 /* USUB8 cccc 0110 0101 xxxx xxxx xxxx 1111 xxxx */
745 /* UQADD16 cccc 0110 0110 xxxx xxxx xxxx 0001 xxxx */
746 /* UQADDSUBX cccc 0110 0110 xxxx xxxx xxxx 0011 xxxx */
747 /* UQSUBADDX cccc 0110 0110 xxxx xxxx xxxx 0101 xxxx */
748 /* UQSUB16 cccc 0110 0110 xxxx xxxx xxxx 0111 xxxx */
749 /* UQADD8 cccc 0110 0110 xxxx xxxx xxxx 1001 xxxx */
750 /* UQSUB8 cccc 0110 0110 xxxx xxxx xxxx 1111 xxxx */
751 /* UHADD16 cccc 0110 0111 xxxx xxxx xxxx 0001 xxxx */
752 /* UHADDSUBX cccc 0110 0111 xxxx xxxx xxxx 0011 xxxx */
753 /* UHSUBADDX cccc 0110 0111 xxxx xxxx xxxx 0101 xxxx */
754 /* UHSUB16 cccc 0110 0111 xxxx xxxx xxxx 0111 xxxx */
755 /* UHADD8 cccc 0110 0111 xxxx xxxx xxxx 1001 xxxx */
756 /* UHSUB8 cccc 0110 0111 xxxx xxxx xxxx 1111 xxxx */
757 DECODE_EMULATEX (0x0f800010, 0x06000010, emulate_rd12rn16rm0_rwflags_nopc
,
758 REGS(NOPC
, NOPC
, 0, 0, NOPC
)),
760 /* PKHBT cccc 0110 1000 xxxx xxxx xxxx x001 xxxx */
761 /* PKHTB cccc 0110 1000 xxxx xxxx xxxx x101 xxxx */
762 DECODE_EMULATEX (0x0ff00030, 0x06800010, emulate_rd12rn16rm0_rwflags_nopc
,
763 REGS(NOPC
, NOPC
, 0, 0, NOPC
)),
765 /* ??? cccc 0110 1001 xxxx xxxx xxxx 0111 xxxx */
766 /* ??? cccc 0110 1101 xxxx xxxx xxxx 0111 xxxx */
767 DECODE_REJECT (0x0fb000f0, 0x06900070),
769 /* SXTB16 cccc 0110 1000 1111 xxxx xxxx 0111 xxxx */
770 /* SXTB cccc 0110 1010 1111 xxxx xxxx 0111 xxxx */
771 /* SXTH cccc 0110 1011 1111 xxxx xxxx 0111 xxxx */
772 /* UXTB16 cccc 0110 1100 1111 xxxx xxxx 0111 xxxx */
773 /* UXTB cccc 0110 1110 1111 xxxx xxxx 0111 xxxx */
774 /* UXTH cccc 0110 1111 1111 xxxx xxxx 0111 xxxx */
775 DECODE_EMULATEX (0x0f8f00f0, 0x068f0070, emulate_rd12rm0_noflags_nopc
,
776 REGS(0, NOPC
, 0, 0, NOPC
)),
778 /* SXTAB16 cccc 0110 1000 xxxx xxxx xxxx 0111 xxxx */
779 /* SXTAB cccc 0110 1010 xxxx xxxx xxxx 0111 xxxx */
780 /* SXTAH cccc 0110 1011 xxxx xxxx xxxx 0111 xxxx */
781 /* UXTAB16 cccc 0110 1100 xxxx xxxx xxxx 0111 xxxx */
782 /* UXTAB cccc 0110 1110 xxxx xxxx xxxx 0111 xxxx */
783 /* UXTAH cccc 0110 1111 xxxx xxxx xxxx 0111 xxxx */
784 DECODE_EMULATEX (0x0f8000f0, 0x06800070, emulate_rd12rn16rm0_rwflags_nopc
,
785 REGS(NOPCX
, NOPC
, 0, 0, NOPC
)),
790 static const union decode_item arm_cccc_0111_____xxx1_table
[] = {
791 /* Media instructions */
793 /* UNDEFINED cccc 0111 1111 xxxx xxxx xxxx 1111 xxxx */
794 DECODE_REJECT (0x0ff000f0, 0x07f000f0),
796 /* SMLALD cccc 0111 0100 xxxx xxxx xxxx 00x1 xxxx */
797 /* SMLSLD cccc 0111 0100 xxxx xxxx xxxx 01x1 xxxx */
798 DECODE_EMULATEX (0x0ff00090, 0x07400010, emulate_rdlo12rdhi16rn0rm8_rwflags_nopc
,
799 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
801 /* SMUAD cccc 0111 0000 xxxx 1111 xxxx 00x1 xxxx */
802 /* SMUSD cccc 0111 0000 xxxx 1111 xxxx 01x1 xxxx */
803 DECODE_OR (0x0ff0f090, 0x0700f010),
804 /* SMMUL cccc 0111 0101 xxxx 1111 xxxx 00x1 xxxx */
805 DECODE_OR (0x0ff0f0d0, 0x0750f010),
806 /* USAD8 cccc 0111 1000 xxxx 1111 xxxx 0001 xxxx */
807 DECODE_EMULATEX (0x0ff0f0f0, 0x0780f010, emulate_rd16rn12rm0rs8_rwflags_nopc
,
808 REGS(NOPC
, 0, NOPC
, 0, NOPC
)),
810 /* SMLAD cccc 0111 0000 xxxx xxxx xxxx 00x1 xxxx */
811 /* SMLSD cccc 0111 0000 xxxx xxxx xxxx 01x1 xxxx */
812 DECODE_OR (0x0ff00090, 0x07000010),
813 /* SMMLA cccc 0111 0101 xxxx xxxx xxxx 00x1 xxxx */
814 DECODE_OR (0x0ff000d0, 0x07500010),
815 /* USADA8 cccc 0111 1000 xxxx xxxx xxxx 0001 xxxx */
816 DECODE_EMULATEX (0x0ff000f0, 0x07800010, emulate_rd16rn12rm0rs8_rwflags_nopc
,
817 REGS(NOPC
, NOPCX
, NOPC
, 0, NOPC
)),
819 /* SMMLS cccc 0111 0101 xxxx xxxx xxxx 11x1 xxxx */
820 DECODE_EMULATEX (0x0ff000d0, 0x075000d0, emulate_rd16rn12rm0rs8_rwflags_nopc
,
821 REGS(NOPC
, NOPC
, NOPC
, 0, NOPC
)),
823 /* SBFX cccc 0111 101x xxxx xxxx xxxx x101 xxxx */
824 /* UBFX cccc 0111 111x xxxx xxxx xxxx x101 xxxx */
825 DECODE_EMULATEX (0x0fa00070, 0x07a00050, emulate_rd12rm0_noflags_nopc
,
826 REGS(0, NOPC
, 0, 0, NOPC
)),
828 /* BFC cccc 0111 110x xxxx xxxx xxxx x001 1111 */
829 DECODE_EMULATEX (0x0fe0007f, 0x07c0001f, emulate_rd12rm0_noflags_nopc
,
830 REGS(0, NOPC
, 0, 0, 0)),
832 /* BFI cccc 0111 110x xxxx xxxx xxxx x001 xxxx */
833 DECODE_EMULATEX (0x0fe00070, 0x07c00010, emulate_rd12rm0_noflags_nopc
,
834 REGS(0, NOPC
, 0, 0, NOPCX
)),
839 static const union decode_item arm_cccc_01xx_table
[] = {
840 /* Load/store word and unsigned byte */
842 /* LDRB/STRB pc,[...] cccc 01xx x0xx xxxx xxxx xxxx xxxx xxxx */
843 DECODE_REJECT (0x0c40f000, 0x0440f000),
845 /* STRT cccc 01x0 x010 xxxx xxxx xxxx xxxx xxxx */
846 /* LDRT cccc 01x0 x011 xxxx xxxx xxxx xxxx xxxx */
847 /* STRBT cccc 01x0 x110 xxxx xxxx xxxx xxxx xxxx */
848 /* LDRBT cccc 01x0 x111 xxxx xxxx xxxx xxxx xxxx */
849 DECODE_REJECT (0x0d200000, 0x04200000),
851 /* STR (immediate) cccc 010x x0x0 xxxx xxxx xxxx xxxx xxxx */
852 /* STRB (immediate) cccc 010x x1x0 xxxx xxxx xxxx xxxx xxxx */
853 DECODE_EMULATEX (0x0e100000, 0x04000000, emulate_str
,
854 REGS(NOPCWB
, ANY
, 0, 0, 0)),
856 /* LDR (immediate) cccc 010x x0x1 xxxx xxxx xxxx xxxx xxxx */
857 /* LDRB (immediate) cccc 010x x1x1 xxxx xxxx xxxx xxxx xxxx */
858 DECODE_EMULATEX (0x0e100000, 0x04100000, emulate_ldr
,
859 REGS(NOPCWB
, ANY
, 0, 0, 0)),
861 /* STR (register) cccc 011x x0x0 xxxx xxxx xxxx xxxx xxxx */
862 /* STRB (register) cccc 011x x1x0 xxxx xxxx xxxx xxxx xxxx */
863 DECODE_EMULATEX (0x0e100000, 0x06000000, emulate_str
,
864 REGS(NOPCWB
, ANY
, 0, 0, NOPC
)),
866 /* LDR (register) cccc 011x x0x1 xxxx xxxx xxxx xxxx xxxx */
867 /* LDRB (register) cccc 011x x1x1 xxxx xxxx xxxx xxxx xxxx */
868 DECODE_EMULATEX (0x0e100000, 0x06100000, emulate_ldr
,
869 REGS(NOPCWB
, ANY
, 0, 0, NOPC
)),
874 static const union decode_item arm_cccc_100x_table
[] = {
875 /* Block data transfer instructions */
877 /* LDM cccc 100x x0x1 xxxx xxxx xxxx xxxx xxxx */
878 /* STM cccc 100x x0x0 xxxx xxxx xxxx xxxx xxxx */
879 DECODE_CUSTOM (0x0e400000, 0x08000000, kprobe_decode_ldmstm
),
881 /* STM (user registers) cccc 100x x1x0 xxxx xxxx xxxx xxxx xxxx */
882 /* LDM (user registers) cccc 100x x1x1 xxxx 0xxx xxxx xxxx xxxx */
883 /* LDM (exception ret) cccc 100x x1x1 xxxx 1xxx xxxx xxxx xxxx */
887 const union decode_item kprobe_decode_arm_table
[] = {
889 * Unconditional instructions
890 * 1111 xxxx xxxx xxxx xxxx xxxx xxxx xxxx
892 DECODE_TABLE (0xf0000000, 0xf0000000, arm_1111_table
),
895 * Miscellaneous instructions
896 * cccc 0001 0xx0 xxxx xxxx xxxx 0xxx xxxx
898 DECODE_TABLE (0x0f900080, 0x01000000, arm_cccc_0001_0xx0____0xxx_table
),
901 * Halfword multiply and multiply-accumulate
902 * cccc 0001 0xx0 xxxx xxxx xxxx 1xx0 xxxx
904 DECODE_TABLE (0x0f900090, 0x01000080, arm_cccc_0001_0xx0____1xx0_table
),
907 * Multiply and multiply-accumulate
908 * cccc 0000 xxxx xxxx xxxx xxxx 1001 xxxx
910 DECODE_TABLE (0x0f0000f0, 0x00000090, arm_cccc_0000_____1001_table
),
913 * Synchronization primitives
914 * cccc 0001 xxxx xxxx xxxx xxxx 1001 xxxx
916 DECODE_TABLE (0x0f0000f0, 0x01000090, arm_cccc_0001_____1001_table
),
919 * Extra load/store instructions
920 * cccc 000x xxxx xxxx xxxx xxxx 1xx1 xxxx
922 DECODE_TABLE (0x0e000090, 0x00000090, arm_cccc_000x_____1xx1_table
),
925 * Data-processing (register)
926 * cccc 000x xxxx xxxx xxxx xxxx xxx0 xxxx
927 * Data-processing (register-shifted register)
928 * cccc 000x xxxx xxxx xxxx xxxx 0xx1 xxxx
930 DECODE_TABLE (0x0e000000, 0x00000000, arm_cccc_000x_table
),
933 * Data-processing (immediate)
934 * cccc 001x xxxx xxxx xxxx xxxx xxxx xxxx
936 DECODE_TABLE (0x0e000000, 0x02000000, arm_cccc_001x_table
),
940 * cccc 011x xxxx xxxx xxxx xxxx xxx1 xxxx
942 DECODE_TABLE (0x0f000010, 0x06000010, arm_cccc_0110_____xxx1_table
),
943 DECODE_TABLE (0x0f000010, 0x07000010, arm_cccc_0111_____xxx1_table
),
946 * Load/store word and unsigned byte
947 * cccc 01xx xxxx xxxx xxxx xxxx xxxx xxxx
949 DECODE_TABLE (0x0c000000, 0x04000000, arm_cccc_01xx_table
),
952 * Block data transfer instructions
953 * cccc 100x xxxx xxxx xxxx xxxx xxxx xxxx
955 DECODE_TABLE (0x0e000000, 0x08000000, arm_cccc_100x_table
),
957 /* B cccc 1010 xxxx xxxx xxxx xxxx xxxx xxxx */
958 /* BL cccc 1011 xxxx xxxx xxxx xxxx xxxx xxxx */
959 DECODE_SIMULATE (0x0e000000, 0x0a000000, simulate_bbl
),
962 * Supervisor Call, and coprocessor instructions
965 /* MCRR cccc 1100 0100 xxxx xxxx xxxx xxxx xxxx */
966 /* MRRC cccc 1100 0101 xxxx xxxx xxxx xxxx xxxx */
967 /* LDC cccc 110x xxx1 xxxx xxxx xxxx xxxx xxxx */
968 /* STC cccc 110x xxx0 xxxx xxxx xxxx xxxx xxxx */
969 /* CDP cccc 1110 xxxx xxxx xxxx xxxx xxx0 xxxx */
970 /* MCR cccc 1110 xxx0 xxxx xxxx xxxx xxx1 xxxx */
971 /* MRC cccc 1110 xxx1 xxxx xxxx xxxx xxx1 xxxx */
972 /* SVC cccc 1111 xxxx xxxx xxxx xxxx xxxx xxxx */
973 DECODE_REJECT (0x0c000000, 0x0c000000),
977 #ifdef CONFIG_ARM_KPROBES_TEST_MODULE
978 EXPORT_SYMBOL_GPL(kprobe_decode_arm_table
);
981 static void __kprobes
arm_singlestep(struct kprobe
*p
, struct pt_regs
*regs
)
984 p
->ainsn
.insn_handler(p
, regs
);
988 * INSN_REJECTED If instruction is one not allowed to kprobe,
989 * INSN_GOOD If instruction is supported and uses instruction slot,
990 * INSN_GOOD_NO_SLOT If instruction is supported but doesn't use its slot.
992 * For instructions we don't want to kprobe (INSN_REJECTED return result):
993 * These are generally ones that modify the processor state making
994 * them "hard" to simulate such as switches processor modes or
995 * make accesses in alternate modes. Any of these could be simulated
996 * if the work was put into it, but low return considering they
997 * should also be very rare.
999 enum kprobe_insn __kprobes
1000 arm_kprobe_decode_insn(kprobe_opcode_t insn
, struct arch_specific_insn
*asi
)
1002 asi
->insn_singlestep
= arm_singlestep
;
1003 asi
->insn_check_cc
= kprobe_condition_checks
[insn
>>28];
1004 return kprobe_decode_insn(insn
, asi
, kprobe_decode_arm_table
, false);