Thread (59 messages) 59 messages, 9 authors, 2019-03-01

Re: [RFC][PATCH] objtool: STAC/CLAC validation

flat view

From: Peter Zijlstra <peterz@infradead.org>
Date: 2019-02-25 13:21:17
Also in: lkml

On Mon, Feb 25, 2019 at 12:47:00AM -0800, hpa@zytor.com wrote:
It doesn't have to understand the contents of the memop, but it seems
that the presence of a modrm with mode ≠ 3 should be plenty. It needs
to know that much in order to know the length of instructions anyway.
For extra credit, ignore LEA or hinting instructions.
A little something like so then?

arch/x86/kernel/fpu/signal.o: warning: objtool: .altinstr_replacement+0x9c: UACCESS disable without MEMOPs: copy_fpstate_to_sigframe()

00000000023c  000200000002 R_X86_64_PC32     0000000000000000 .text + 604
000000000240  000700000002 R_X86_64_PC32     0000000000000000 .altinstr_replacement + 99
000000000249  000200000002 R_X86_64_PC32     0000000000000000 .text + 610
00000000024d  000700000002 R_X86_64_PC32     0000000000000000 .altinstr_replacement + 9c

.text

604:   90                      nop
605:   90                      nop
606:   90                      nop
607:   83 ce 03                or     $0x3,%esi
60a:   89 b3 00 02 00 00       mov    %esi,0x200(%rbx)
610:   90                      nop
611:   90                      nop
612:   90                      nop

.altinstr_replacement

99:   0f 01 cb                stac
9c:   0f 01 ca                clac

Which looks like the tool failed to recognise that MOV as a memop.



---
--- a/tools/objtool/arch.h
+++ b/tools/objtool/arch.h
@@ -37,7 +37,8 @@
 #define INSN_CLAC		12
 #define INSN_STD		13
 #define INSN_CLD		14
-#define INSN_OTHER		15
+#define INSN_MEMOP		15
+#define INSN_OTHER		16
 #define INSN_LAST		INSN_OTHER
 
 enum op_dest_type {
--- a/tools/objtool/arch/x86/decode.c
+++ b/tools/objtool/arch/x86/decode.c
@@ -123,6 +123,9 @@ int arch_decode_instruction(struct elf *
 		modrm_mod = X86_MODRM_MOD(modrm);
 		modrm_reg = X86_MODRM_REG(modrm);
 		modrm_rm = X86_MODRM_RM(modrm);
+
+		if (modrm_mod != 3)
+			*type = INSN_MEMOP;
 	}
 
 	if (insn.sib.nbytes)
--- a/tools/objtool/check.c
+++ b/tools/objtool/check.c
@@ -2047,6 +2047,7 @@ static int validate_branch(struct objtoo
 				WARN_FUNC("recursive UACCESS enable", sec, insn->offset);
 
 			state.uaccess = true;
+			state.memop = false;
 			break;
 
 		case INSN_CLAC:
@@ -2058,6 +2059,9 @@ static int validate_branch(struct objtoo
 				break;
 			}
 
+			if (!state.memop && insn->func)
+				WARN_FUNC("UACCESS disable without MEMOPs: %s()", sec, insn->offset, insn->func->name);
+
 			state.uaccess = false;
 			break;
 
@@ -2075,6 +2079,10 @@ static int validate_branch(struct objtoo
 			state.df = false;
 			break;
 
+		case INSN_MEMOP:
+			state.memop = true;
+			break;
+
 		default:
 			break;
 		}
--- a/tools/objtool/check.h
+++ b/tools/objtool/check.h
@@ -31,7 +31,7 @@ struct insn_state {
 	int stack_size;
 	unsigned char type;
 	bool bp_scratch;
-	bool drap, end, uaccess, uaccess_safe, df;
+	bool drap, end, uaccess, uaccess_safe, df, memop;
 	int drap_reg, drap_offset;
 	struct cfi_reg vals[CFI_NUM_REGS];
 };
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help