aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/kernel
diff options
context:
space:
mode:
authorJon Medhurst <tixy@yxit.co.uk>2011-04-19 05:52:16 -0400
committerNicolas Pitre <nicolas.pitre@linaro.org>2011-04-28 23:40:59 -0400
commitf704a6e25bd07e1381af81f19fb1d123975807b1 (patch)
treedc571d149ae5a78c9adf667cf512438615470ebe /arch/arm/kernel
parent72c2bab2be734d63dee4342e67b1754c54fded70 (diff)
ARM: kprobes: Reject probing of undefined data processing instructions
The instruction decoding in space_cccc_000x needs to reject probing of instructions with undefined patterns as they may in future become defined and then emulated faultily - as has already happened with the SMC instruction. This fix is achieved by testing for the instruction patterns we want to probe and making the the default fall-through paths reject probes. This also allows us to remove some explicit tests for instructions that we wish to reject, as that is now the default action. Signed-off-by: Jon Medhurst <tixy@yxit.co.uk> Signed-off-by: Nicolas Pitre <nicolas.pitre@linaro.org>
Diffstat (limited to 'arch/arm/kernel')
-rw-r--r--arch/arm/kernel/kprobes-decode.c31
1 files changed, 17 insertions, 14 deletions
diff --git a/arch/arm/kernel/kprobes-decode.c b/arch/arm/kernel/kprobes-decode.c
index dc315c12d5f3..4715537b490c 100644
--- a/arch/arm/kernel/kprobes-decode.c
+++ b/arch/arm/kernel/kprobes-decode.c
@@ -966,14 +966,6 @@ space_cccc_000x(kprobe_opcode_t insn, struct arch_specific_insn *asi)
966 /* cccc 0001 0xx0 xxxx xxxx xxxx xxxx xxx0 xxxx */ 966 /* cccc 0001 0xx0 xxxx xxxx xxxx xxxx xxx0 xxxx */
967 if ((insn & 0x0f900010) == 0x01000000) { 967 if ((insn & 0x0f900010) == 0x01000000) {
968 968
969 /* BXJ : cccc 0001 0010 xxxx xxxx xxxx 0010 xxxx */
970 /* MSR : cccc 0001 0x10 xxxx xxxx xxxx 0000 xxxx */
971 /* MRS spsr : cccc 0001 0100 xxxx xxxx xxxx 0000 xxxx */
972 if ((insn & 0x0ff000f0) == 0x01200020 ||
973 (insn & 0x0fb000f0) == 0x01200000 ||
974 (insn & 0x0ff000f0) == 0x01400000)
975 return INSN_REJECTED;
976
977 /* MRS cpsr : cccc 0001 0000 xxxx xxxx xxxx 0000 xxxx */ 969 /* MRS cpsr : cccc 0001 0000 xxxx xxxx xxxx 0000 xxxx */
978 if ((insn & 0x0ff000f0) == 0x01000000) { 970 if ((insn & 0x0ff000f0) == 0x01000000) {
979 if (is_r15(insn, 12)) 971 if (is_r15(insn, 12))
@@ -994,17 +986,21 @@ space_cccc_000x(kprobe_opcode_t insn, struct arch_specific_insn *asi)
994 986
995 /* SMLAxy : cccc 0001 0000 xxxx xxxx xxxx 1xx0 xxxx : Q */ 987 /* SMLAxy : cccc 0001 0000 xxxx xxxx xxxx 1xx0 xxxx : Q */
996 /* SMLAWy : cccc 0001 0010 xxxx xxxx xxxx 1x00 xxxx : Q */ 988 /* SMLAWy : cccc 0001 0010 xxxx xxxx xxxx 1x00 xxxx : Q */
997 return prep_emulate_rd16rn12rs8rm0_wflags(insn, asi); 989 if ((insn & 0x0ff00090) == 0x01000080 ||
990 (insn & 0x0ff000b0) == 0x01200080)
991 return prep_emulate_rd16rn12rs8rm0_wflags(insn, asi);
992
993 /* BXJ : cccc 0001 0010 xxxx xxxx xxxx 0010 xxxx */
994 /* MSR : cccc 0001 0x10 xxxx xxxx xxxx 0000 xxxx */
995 /* MRS spsr : cccc 0001 0100 xxxx xxxx xxxx 0000 xxxx */
998 996
997 /* Other instruction encodings aren't yet defined */
998 return INSN_REJECTED;
999 } 999 }
1000 1000
1001 /* cccc 0001 0xx0 xxxx xxxx xxxx xxxx 0xx1 xxxx */ 1001 /* cccc 0001 0xx0 xxxx xxxx xxxx xxxx 0xx1 xxxx */
1002 else if ((insn & 0x0f900090) == 0x01000010) { 1002 else if ((insn & 0x0f900090) == 0x01000010) {
1003 1003
1004 /* BKPT : 1110 0001 0010 xxxx xxxx xxxx 0111 xxxx */
1005 if ((insn & 0xfff000f0) == 0xe1200070)
1006 return INSN_REJECTED;
1007
1008 /* BLX(2) : cccc 0001 0010 xxxx xxxx xxxx 0011 xxxx */ 1004 /* BLX(2) : cccc 0001 0010 xxxx xxxx xxxx 0011 xxxx */
1009 /* BX : cccc 0001 0010 xxxx xxxx xxxx 0001 xxxx */ 1005 /* BX : cccc 0001 0010 xxxx xxxx xxxx 0001 xxxx */
1010 if ((insn & 0x0ff000d0) == 0x01200010) { 1006 if ((insn & 0x0ff000d0) == 0x01200010) {
@@ -1022,7 +1018,14 @@ space_cccc_000x(kprobe_opcode_t insn, struct arch_specific_insn *asi)
1022 /* QSUB : cccc 0001 0010 xxxx xxxx xxxx 0101 xxxx :Q */ 1018 /* QSUB : cccc 0001 0010 xxxx xxxx xxxx 0101 xxxx :Q */
1023 /* QDADD : cccc 0001 0100 xxxx xxxx xxxx 0101 xxxx :Q */ 1019 /* QDADD : cccc 0001 0100 xxxx xxxx xxxx 0101 xxxx :Q */
1024 /* QDSUB : cccc 0001 0110 xxxx xxxx xxxx 0101 xxxx :Q */ 1020 /* QDSUB : cccc 0001 0110 xxxx xxxx xxxx 0101 xxxx :Q */
1025 return prep_emulate_rd12rn16rm0_wflags(insn, asi); 1021 if ((insn & 0x0f9000f0) == 0x01000050)
1022 return prep_emulate_rd12rn16rm0_wflags(insn, asi);
1023
1024 /* BKPT : 1110 0001 0010 xxxx xxxx xxxx 0111 xxxx */
1025 /* SMC : cccc 0001 0110 xxxx xxxx xxxx 0111 xxxx */
1026
1027 /* Other instruction encodings aren't yet defined */
1028 return INSN_REJECTED;
1026 } 1029 }
1027 1030
1028 /* cccc 0000 xxxx xxxx xxxx xxxx xxxx 1001 xxxx */ 1031 /* cccc 0000 xxxx xxxx xxxx xxxx xxxx 1001 xxxx */