diff options
author | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2024-03-29 11:17:02 +0100 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2024-03-29 11:17:02 +0100 |
commit | 1358e3c7660521fd3f674a4a4ceffe20cf17c8fe (patch) | |
tree | 91f177d2b7f6319221fa315d9fc144329aad72e6 /queue-5.4 | |
parent | 6fe915f6878d85093fc91c4ca29a3903c1782c58 (diff) | |
download | stable-queue-1358e3c7660521fd3f674a4a4ceffe20cf17c8fe.tar.gz |
5.4-stable patches
added patches:
objtool-add-support-for-intra-function-calls.patch
objtool-is_fentry_call-crashes-if-call-has-no-destination.patch
x86-speculation-support-intra-function-call-validation.patch
Diffstat (limited to 'queue-5.4')
4 files changed, 287 insertions, 0 deletions
diff --git a/queue-5.4/objtool-add-support-for-intra-function-calls.patch b/queue-5.4/objtool-add-support-for-intra-function-calls.patch new file mode 100644 index 0000000000..2c1b02a351 --- /dev/null +++ b/queue-5.4/objtool-add-support-for-intra-function-calls.patch @@ -0,0 +1,175 @@ +From 8aa8eb2a8f5b3305a95f39957dd2b715fa668e21 Mon Sep 17 00:00:00 2001 +From: Alexandre Chartre <alexandre.chartre@oracle.com> +Date: Tue, 14 Apr 2020 12:36:12 +0200 +Subject: objtool: Add support for intra-function calls + +From: Alexandre Chartre <alexandre.chartre@oracle.com> + +commit 8aa8eb2a8f5b3305a95f39957dd2b715fa668e21 upstream. + +Change objtool to support intra-function calls. On x86, an intra-function +call is represented in objtool as a push onto the stack (of the return +address), and a jump to the destination address. That way the stack +information is correctly updated and the call flow is still accurate. + +Signed-off-by: Alexandre Chartre <alexandre.chartre@oracle.com> +Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org> +Reviewed-by: Miroslav Benes <mbenes@suse.cz> +Acked-by: Josh Poimboeuf <jpoimboe@redhat.com> +Link: https://lkml.kernel.org/r/20200414103618.12657-4-alexandre.chartre@oracle.com +Signed-off-by: Rui Qi <qirui.001@bytedance.com> +Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> +--- + include/linux/frame.h | 11 ++++ + tools/objtool/Documentation/stack-validation.txt | 8 ++ + tools/objtool/arch/x86/decode.c | 6 ++ + tools/objtool/check.c | 62 +++++++++++++++++++++-- + 4 files changed, 83 insertions(+), 4 deletions(-) + +--- a/include/linux/frame.h ++++ b/include/linux/frame.h +@@ -15,9 +15,20 @@ + static void __used __section(.discard.func_stack_frame_non_standard) \ + *__func_stack_frame_non_standard_##func = func + ++/* ++ * This macro indicates that the following intra-function call is valid. ++ * Any non-annotated intra-function call will cause objtool to issue a warning. ++ */ ++#define ANNOTATE_INTRA_FUNCTION_CALL \ ++ 999: \ ++ .pushsection .discard.intra_function_calls; \ ++ .long 999b; \ ++ .popsection; ++ + #else /* !CONFIG_STACK_VALIDATION */ + + #define STACK_FRAME_NON_STANDARD(func) ++#define ANNOTATE_INTRA_FUNCTION_CALL + + #endif /* CONFIG_STACK_VALIDATION */ + +--- a/tools/objtool/Documentation/stack-validation.txt ++++ b/tools/objtool/Documentation/stack-validation.txt +@@ -290,6 +290,14 @@ they mean, and suggestions for how to fi + https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70646 + + ++11. file.o: warning: unannotated intra-function call ++ ++ This warning means that a direct call is done to a destination which ++ is not at the beginning of a function. If this is a legit call, you ++ can remove this warning by putting the ANNOTATE_INTRA_FUNCTION_CALL ++ directive right before the call. ++ ++ + If the error doesn't seem to make sense, it could be a bug in objtool. + Feel free to ask the objtool maintainer for help. + +--- a/tools/objtool/arch/x86/decode.c ++++ b/tools/objtool/arch/x86/decode.c +@@ -437,6 +437,12 @@ int arch_decode_instruction(struct elf * + + case 0xe8: + *type = INSN_CALL; ++ /* ++ * For the impact on the stack, a CALL behaves like ++ * a PUSH of an immediate value (the return address). ++ */ ++ op->src.type = OP_SRC_CONST; ++ op->dest.type = OP_DEST_PUSH; + break; + + case 0xfc: +--- a/tools/objtool/check.c ++++ b/tools/objtool/check.c +@@ -645,6 +645,7 @@ static int add_jump_destinations(struct + return 0; + } + ++ + /* + * Find the destination instructions for all calls. + */ +@@ -666,10 +667,7 @@ static int add_call_destinations(struct + dest_off); + + if (!insn->call_dest && !insn->ignore) { +- WARN_FUNC("unsupported intra-function call", +- insn->sec, insn->offset); +- if (retpoline) +- WARN("If this is a retpoline, please patch it in with alternatives and annotate it with ANNOTATE_NOSPEC_ALTERNATIVE."); ++ WARN_FUNC("unannotated intra-function call", insn->sec, insn->offset); + return -1; + } + +@@ -1291,6 +1289,58 @@ static int read_retpoline_hints(struct o + return 0; + } + ++ ++static int read_intra_function_calls(struct objtool_file *file) ++{ ++ struct instruction *insn; ++ struct section *sec; ++ struct rela *rela; ++ ++ sec = find_section_by_name(file->elf, ".rela.discard.intra_function_calls"); ++ if (!sec) ++ return 0; ++ ++ list_for_each_entry(rela, &sec->rela_list, list) { ++ unsigned long dest_off; ++ ++ if (rela->sym->type != STT_SECTION) { ++ WARN("unexpected relocation symbol type in %s", ++ sec->name); ++ return -1; ++ } ++ ++ insn = find_insn(file, rela->sym->sec, rela->addend); ++ if (!insn) { ++ WARN("bad .discard.intra_function_call entry"); ++ return -1; ++ } ++ ++ if (insn->type != INSN_CALL) { ++ WARN_FUNC("intra_function_call not a direct call", ++ insn->sec, insn->offset); ++ return -1; ++ } ++ ++ /* ++ * Treat intra-function CALLs as JMPs, but with a stack_op. ++ * See add_call_destinations(), which strips stack_ops from ++ * normal CALLs. ++ */ ++ insn->type = INSN_JUMP_UNCONDITIONAL; ++ ++ dest_off = insn->offset + insn->len + insn->immediate; ++ insn->jump_dest = find_insn(file, insn->sec, dest_off); ++ if (!insn->jump_dest) { ++ WARN_FUNC("can't find call dest at %s+0x%lx", ++ insn->sec, insn->offset, ++ insn->sec->name, dest_off); ++ return -1; ++ } ++ } ++ ++ return 0; ++} ++ + static void mark_rodata(struct objtool_file *file) + { + struct section *sec; +@@ -1346,6 +1396,10 @@ static int decode_sections(struct objtoo + if (ret) + return ret; + ++ ret = read_intra_function_calls(file); ++ if (ret) ++ return ret; ++ + ret = add_call_destinations(file); + if (ret) + return ret; diff --git a/queue-5.4/objtool-is_fentry_call-crashes-if-call-has-no-destination.patch b/queue-5.4/objtool-is_fentry_call-crashes-if-call-has-no-destination.patch new file mode 100644 index 0000000000..be541f2f3c --- /dev/null +++ b/queue-5.4/objtool-is_fentry_call-crashes-if-call-has-no-destination.patch @@ -0,0 +1,35 @@ +From 87cf61fe848ca8ddf091548671e168f52e8a718e Mon Sep 17 00:00:00 2001 +From: Alexandre Chartre <alexandre.chartre@oracle.com> +Date: Tue, 14 Apr 2020 12:36:10 +0200 +Subject: objtool: is_fentry_call() crashes if call has no destination + +From: Alexandre Chartre <alexandre.chartre@oracle.com> + +commit 87cf61fe848ca8ddf091548671e168f52e8a718e upstream. + +Fix is_fentry_call() so that it works if a call has no destination +set (call_dest). This needs to be done in order to support intra- +function calls. + +Signed-off-by: Alexandre Chartre <alexandre.chartre@oracle.com> +Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org> +Reviewed-by: Miroslav Benes <mbenes@suse.cz> +Acked-by: Josh Poimboeuf <jpoimboe@redhat.com> +Link: https://lkml.kernel.org/r/20200414103618.12657-2-alexandre.chartre@oracle.com +Signed-off-by: Rui Qi <qirui.001@bytedance.com> +Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> +--- + tools/objtool/check.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/tools/objtool/check.c ++++ b/tools/objtool/check.c +@@ -1367,7 +1367,7 @@ static int decode_sections(struct objtoo + + static bool is_fentry_call(struct instruction *insn) + { +- if (insn->type == INSN_CALL && ++ if (insn->type == INSN_CALL && insn->call_dest && + insn->call_dest->type == STT_NOTYPE && + !strcmp(insn->call_dest->name, "__fentry__")) + return true; diff --git a/queue-5.4/series b/queue-5.4/series index 5028952046..926cd06d48 100644 --- a/queue-5.4/series +++ b/queue-5.4/series @@ -89,3 +89,6 @@ usb-port-don-t-try-to-peer-unused-usb-ports-based-on-location.patch tty-serial-fsl_lpuart-avoid-idle-preamble-pending-if-cts-is-enabled.patch vt-fix-unicode-buffer-corruption-when-deleting-characters.patch fs-aio-check-iocb_aio_rw-before-the-struct-aio_kiocb-conversion.patch +objtool-is_fentry_call-crashes-if-call-has-no-destination.patch +objtool-add-support-for-intra-function-calls.patch +x86-speculation-support-intra-function-call-validation.patch diff --git a/queue-5.4/x86-speculation-support-intra-function-call-validation.patch b/queue-5.4/x86-speculation-support-intra-function-call-validation.patch new file mode 100644 index 0000000000..43b3904b6c --- /dev/null +++ b/queue-5.4/x86-speculation-support-intra-function-call-validation.patch @@ -0,0 +1,74 @@ +From qirui.001@bytedance.com Fri Mar 29 11:16:07 2024 +From: Rui Qi <qirui.001@bytedance.com> +Date: Wed, 27 Mar 2024 17:44:47 +0800 +Subject: x86/speculation: Support intra-function call validation +To: bp@alien8.de, mingo@redhat.com, tglx@linutronix.de, hpa@zytor.com, jpoimboe@redhat.com, peterz@infradead.org, mbenes@suse.cz, gregkh@linuxfoundation.org, stable@vger.kernel.org, alexandre.chartre@oracle.com +Cc: x86@kernel.org, linux-kernel@vger.kernel.org, sashal@kernel.org, Rui Qi <qirui.001@bytedance.com> +Message-ID: <20240327094447.47375-4-qirui.001@bytedance.com> + +From: Rui Qi <qirui.001@bytedance.com> + +commit 8afd1c7da2b0 ("x86/speculation: Change FILL_RETURN_BUFFER + to work with objtool") does not support intra-function call + stack validation, which causes kernel live patching to fail. +This commit adds support for this, and after testing, the kernel + live patching feature is restored to normal. + +Fixes: 8afd1c7da2b0 ("x86/speculation: Change FILL_RETURN_BUFFER to work with objtool") +Cc: <stable@vger.kernel.org> # v5.4.250+ +Signed-off-by: Rui Qi <qirui.001@bytedance.com> +Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> +--- + arch/x86/include/asm/nospec-branch.h | 7 +++++++ + arch/x86/include/asm/unwind_hints.h | 2 +- + 2 files changed, 8 insertions(+), 1 deletion(-) + +--- a/arch/x86/include/asm/nospec-branch.h ++++ b/arch/x86/include/asm/nospec-branch.h +@@ -13,6 +13,8 @@ + #include <asm/unwind_hints.h> + #include <asm/percpu.h> + ++#include <linux/frame.h> ++#include <asm/unwind_hints.h> + /* + * This should be used immediately before a retpoline alternative. It tells + * objtool where the retpolines are so that it can make sense of the control +@@ -51,14 +53,18 @@ + #define __FILL_RETURN_BUFFER(reg, nr, sp) \ + mov $(nr/2), reg; \ + 771: \ ++ ANNOTATE_INTRA_FUNCTION_CALL; \ + call 772f; \ + 773: /* speculation trap */ \ ++ UNWIND_HINT_EMPTY; \ + pause; \ + lfence; \ + jmp 773b; \ + 772: \ ++ ANNOTATE_INTRA_FUNCTION_CALL; \ + call 774f; \ + 775: /* speculation trap */ \ ++ UNWIND_HINT_EMPTY; \ + pause; \ + lfence; \ + jmp 775b; \ +@@ -152,6 +158,7 @@ + .endm + + .macro ISSUE_UNBALANCED_RET_GUARD ++ ANNOTATE_INTRA_FUNCTION_CALL; + call .Lunbalanced_ret_guard_\@ + int3 + .Lunbalanced_ret_guard_\@: +--- a/arch/x86/include/asm/unwind_hints.h ++++ b/arch/x86/include/asm/unwind_hints.h +@@ -101,7 +101,7 @@ + ".popsection\n\t" + + #define UNWIND_HINT_SAVE UNWIND_HINT(0, 0, UNWIND_HINT_TYPE_SAVE, 0) +- ++#define UNWIND_HINT_EMPTY + #define UNWIND_HINT_RESTORE UNWIND_HINT(0, 0, UNWIND_HINT_TYPE_RESTORE, 0) + + #endif /* __ASSEMBLY__ */ |