Commit 4708ea14 authored by Josh Poimboeuf's avatar Josh Poimboeuf Committed by Peter Zijlstra
Browse files

x86,objtool: Separate unret validation from unwind hints



The ENTRY unwind hint type is serving double duty as both an empty
unwind hint and an unret validation annotation.

Unret validation is unrelated to unwinding. Separate it out into its own
annotation.

Signed-off-by: default avatarJosh Poimboeuf <jpoimboe@kernel.org>
Signed-off-by: default avatarPeter Zijlstra (Intel) <peterz@infradead.org>
Acked-by: default avatarPeter Zijlstra (Intel) <peterz@infradead.org>
Link: https://lore.kernel.org/r/ff7448d492ea21b86d8a90264b105fbd0d751077.1677683419.git.jpoimboe@kernel.org
parent f902cfdd
Loading
Loading
Loading
Loading
+7 −7
Original line number Diff line number Diff line
@@ -388,9 +388,9 @@ SYM_CODE_START(\asmsym)

	.if \vector == X86_TRAP_BP
		/* #BP advances %rip to the next instruction */
		UNWIND_HINT_IRET_REGS offset=\has_error_code*8 signal=0
		UNWIND_HINT_IRET_ENTRY offset=\has_error_code*8 signal=0
	.else
		UNWIND_HINT_IRET_REGS offset=\has_error_code*8
		UNWIND_HINT_IRET_ENTRY offset=\has_error_code*8
	.endif

	ENDBR
@@ -461,7 +461,7 @@ SYM_CODE_END(\asmsym)
 */
.macro idtentry_mce_db vector asmsym cfunc
SYM_CODE_START(\asmsym)
	UNWIND_HINT_IRET_REGS
	UNWIND_HINT_IRET_ENTRY
	ENDBR
	ASM_CLAC
	cld
@@ -518,7 +518,7 @@ SYM_CODE_END(\asmsym)
 */
.macro idtentry_vc vector asmsym cfunc
SYM_CODE_START(\asmsym)
	UNWIND_HINT_IRET_REGS
	UNWIND_HINT_IRET_ENTRY
	ENDBR
	ASM_CLAC
	cld
@@ -582,7 +582,7 @@ SYM_CODE_END(\asmsym)
 */
.macro idtentry_df vector asmsym cfunc
SYM_CODE_START(\asmsym)
	UNWIND_HINT_IRET_REGS offset=8
	UNWIND_HINT_IRET_ENTRY offset=8
	ENDBR
	ASM_CLAC
	cld
@@ -1107,7 +1107,7 @@ SYM_CODE_START(error_entry)
	FENCE_SWAPGS_KERNEL_ENTRY
	CALL_DEPTH_ACCOUNT
	leaq	8(%rsp), %rax			/* return pt_regs pointer */
	ANNOTATE_UNRET_END
	VALIDATE_UNRET_END
	RET

.Lbstep_iret:
@@ -1153,7 +1153,7 @@ SYM_CODE_END(error_return)
 *	      when PAGE_TABLE_ISOLATION is in use.  Do not clobber.
 */
SYM_CODE_START(asm_exc_nmi)
	UNWIND_HINT_IRET_REGS
	UNWIND_HINT_IRET_ENTRY
	ENDBR

	/*
+4 −4
Original line number Diff line number Diff line
@@ -210,8 +210,8 @@
 * Abuse ANNOTATE_RETPOLINE_SAFE on a NOP to indicate UNRET_END, should
 * eventually turn into it's own annotation.
 */
.macro ANNOTATE_UNRET_END
#ifdef CONFIG_DEBUG_ENTRY
.macro VALIDATE_UNRET_END
#if defined(CONFIG_NOINSTR_VALIDATION) && defined(CONFIG_CPU_UNRET_ENTRY)
	ANNOTATE_RETPOLINE_SAFE
	nop
#endif
@@ -286,7 +286,7 @@
.macro UNTRAIN_RET
#if defined(CONFIG_CPU_UNRET_ENTRY) || defined(CONFIG_CPU_IBPB_ENTRY) || \
	defined(CONFIG_CALL_DEPTH_TRACKING)
	ANNOTATE_UNRET_END
	VALIDATE_UNRET_END
	ALTERNATIVE_3 "",						\
		      CALL_ZEN_UNTRAIN_RET, X86_FEATURE_UNRET,		\
		      "call entry_ibpb", X86_FEATURE_ENTRY_IBPB,	\
@@ -297,7 +297,7 @@
.macro UNTRAIN_RET_FROM_CALL
#if defined(CONFIG_CPU_UNRET_ENTRY) || defined(CONFIG_CPU_IBPB_ENTRY) || \
	defined(CONFIG_CALL_DEPTH_TRACKING)
	ANNOTATE_UNRET_END
	VALIDATE_UNRET_END
	ALTERNATIVE_3 "",						\
		      CALL_ZEN_UNTRAIN_RET, X86_FEATURE_UNRET,		\
		      "call entry_ibpb", X86_FEATURE_ENTRY_IBPB,	\
+7 −1
Original line number Diff line number Diff line
@@ -12,7 +12,8 @@
.endm

.macro UNWIND_HINT_ENTRY
	UNWIND_HINT type=UNWIND_HINT_TYPE_ENTRY end=1
	VALIDATE_UNRET_BEGIN
	UNWIND_HINT_EMPTY
.endm

.macro UNWIND_HINT_REGS base=%rsp offset=0 indirect=0 extra=1 partial=0 signal=1
@@ -52,6 +53,11 @@
	UNWIND_HINT_REGS base=\base offset=\offset partial=1 signal=\signal
.endm

.macro UNWIND_HINT_IRET_ENTRY base=%rsp offset=0 signal=1
	VALIDATE_UNRET_BEGIN
	UNWIND_HINT_IRET_REGS base=\base offset=\offset signal=\signal
.endm

.macro UNWIND_HINT_FUNC
	UNWIND_HINT sp_reg=ORC_REG_SP sp_offset=8 type=UNWIND_HINT_TYPE_FUNC
.endm
+0 −5
Original line number Diff line number Diff line
@@ -390,8 +390,6 @@ SYM_CODE_START_NOALIGN(vc_boot_ghcb)
	UNWIND_HINT_IRET_REGS offset=8
	ENDBR

	ANNOTATE_UNRET_END

	/* Build pt_regs */
	PUSH_AND_CLEAR_REGS

@@ -451,7 +449,6 @@ SYM_CODE_END(early_idt_handler_array)

SYM_CODE_START_LOCAL(early_idt_handler_common)
	UNWIND_HINT_IRET_REGS offset=16
	ANNOTATE_UNRET_END
	/*
	 * The stack is the hardware frame, an error code or zero, and the
	 * vector number.
@@ -501,8 +498,6 @@ SYM_CODE_START_NOALIGN(vc_no_ghcb)
	UNWIND_HINT_IRET_REGS offset=8
	ENDBR

	ANNOTATE_UNRET_END

	/* Build pt_regs */
	PUSH_AND_CLEAR_REGS

+16 −0
Original line number Diff line number Diff line
@@ -124,6 +124,22 @@
	.popsection
.endm

/*
 * Use objtool to validate the entry requirement that all code paths do
 * VALIDATE_UNRET_END before RET.
 *
 * NOTE: The macro must be used at the beginning of a global symbol, otherwise
 * it will be ignored.
 */
.macro VALIDATE_UNRET_BEGIN
#if defined(CONFIG_NOINSTR_VALIDATION) && defined(CONFIG_CPU_UNRET_ENTRY)
.Lhere_\@:
	.pushsection .discard.validate_unret
	.long	.Lhere_\@ - .
	.popsection
#endif
.endm

.macro REACHABLE
.Lhere_\@:
	.pushsection .discard.reachable
Loading