[PATCH RFC] x86: convert CET tool chain feature checks to mixed Kconfig/Makefile model

Jan Beulich posted 1 patch 1 year, 2 months ago
Failed in applying to current master (apply log)
[PATCH RFC] x86: convert CET tool chain feature checks to mixed Kconfig/Makefile model
Posted by Jan Beulich 1 year, 2 months ago
To make sure user choices solely affected by tool chain capabilities
can't silently go off, convert the two Kconfig controls from
"depends on ..." to "default ...". Suggest a default matching what the
presently selected tool chain is capable of. To compensate, double check
compiler option availability as well as the assembler recognizing the
necessary insns early on when actually starting a build.

This then also allows to run the configure step with a compiler version
different from (perhaps older than) the one later used for actual
building.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
---
Using warnings instead of errors in the Makefile-based checks for now,
despite the opposite suggestion during the design session in Cambridge.
This is primarily to avoid failing the build just in case our double-
checking is flawed. And in fact there is such a quirk right now with
the changes made here: arch.mk is included ahead of .config being
updated, so the checks are carried out with potentially stale CONFIG_*
settings. Perhaps the checks need suppressing when .config is in the
process of being updated (after which make will re-start, then doing
the checks with the correct CONFIG_* values). It's not (yet) clear to
me how to arrange for that, though, as the inclusion of arch.mk already
sits inside the !config-build section of the top-level Makefile.

For initial feedback I've modelled cc-option-check pretty closely after
cc-option-add, whereas I've tried to make as-insn-check's output more
useful while at the same time removing the need to pass both CFLAGS and
CC into the macro (if anything, HOST would now need passing if the check
was for the host compiler; we could certainly decide to drop that likely
unnecessary flexibility).

--- unstable.orig/Config.mk	2023-02-09 15:08:24.195431817 +0100
+++ unstable/Config.mk	2023-02-09 14:09:05.000000000 +0100
@@ -105,6 +105,18 @@ endef
 
 cc-options-add = $(foreach o,$(3),$(call cc-option-add,$(1),$(2),$(o)))
 
+# cc-option-check: Double-check availablility of a compiler option.
+# Usage: $(call cc-option-check CFLAGS,CC,-march=winchip-c6)
+cc-option-check = $(eval $(call cc-option-check-closure,$(1),$(2),$(3)))
+define cc-option-check-closure
+    ifeq ($$(call cc-option,$$($(2)),$(3),n),n)
+        $$(warning '$$($(2))' does not recognize '$(3)')
+    endif
+    $(1) += $(3)
+endef
+
+cc-options-check = $(foreach o,$(3),$(call cc-option-check,$(1),$(2),$(o)))
+
 # cc-ver: Check compiler against the version requirement. Return boolean 'y'/'n'.
 # Usage: ifeq ($(call cc-ver,$(CC),ge,0x030400),y)
 cc-ver = $(shell if [ $$((`$(1) -dumpversion | awk -F. \
--- unstable.orig/xen/arch/x86/Kconfig	2023-02-09 15:08:24.195431817 +0100
+++ unstable/xen/arch/x86/Kconfig	2023-02-09 11:59:29.000000000 +0100
@@ -119,9 +119,8 @@ config HVM
 
 config XEN_SHSTK
 	bool "Supervisor Shadow Stacks"
-	depends on HAS_AS_CET_SS
-	default y
-	---help---
+	default HAS_AS_CET_SS
+	help
 	  Control-flow Enforcement Technology (CET) is a set of features in
 	  hardware designed to combat Return-oriented Programming (ROP, also
 	  call/jump COP/JOP) attacks.  Shadow Stacks are one CET feature
@@ -133,8 +132,7 @@ config XEN_SHSTK
 
 config XEN_IBT
 	bool "Supervisor Indirect Branch Tracking"
-	depends on HAS_CC_CET_IBT
-	default y
+	default HAS_CC_CET_IBT
 	help
 	  Control-flow Enforcement Technology (CET) is a set of features in
 	  hardware designed to combat Return-oriented Programming (ROP, also
--- unstable.orig/xen/arch/x86/arch.mk	2023-02-09 15:08:24.195431817 +0100
+++ unstable/xen/arch/x86/arch.mk	2023-02-09 15:08:37.088842654 +0100
@@ -34,6 +34,10 @@ $(call as-option-add,CFLAGS,CC,\
 $(call as-option-add,CFLAGS,CC,\
     ".L1: .L2: .nops (.L2 - .L1)$$(comma)9",-DHAVE_AS_NOPS_DIRECTIVE)
 
+$(call as-insn-check,XEN_IBT,,endbr64)
+$(call as-insn-check,XEN_SHSTK,,wrssq %rax$(comma)0)
+$(call as-insn-check,XEN_SHSTK,,setssbsy)
+
 CFLAGS += -mno-red-zone -fpic
 
 # Xen doesn't use MMX or SSE interally.  If the compiler supports it, also skip
@@ -51,10 +55,11 @@ CFLAGS-$(CONFIG_CC_IS_CLANG) += -mretpol
 endif
 
 ifdef CONFIG_XEN_IBT
+$(call cc-options-check,CFLAGS,CC,-fcf-protection=branch -mmanual-endbr)
 # Force -fno-jump-tables to work around
 #   https://gcc.gnu.org/bugzilla/show_bug.cgi?id=104816
 #   https://github.com/llvm/llvm-project/issues/54247
-CFLAGS += -fcf-protection=branch -mmanual-endbr -fno-jump-tables
+CFLAGS += -fno-jump-tables
 $(call cc-option-add,CFLAGS,CC,-fcf-check-attribute=no)
 else
 $(call cc-option-add,CFLAGS,CC,-fcf-protection=none)
--- unstable.orig/xen/scripts/Kbuild.include	2023-02-09 15:08:24.195431817 +0100
+++ unstable/xen/scripts/Kbuild.include	2023-02-09 14:13:52.000000000 +0100
@@ -73,6 +73,18 @@ define as-option-add-closure
     endif
 endef
 
+# as-insn-check: Double-check that the assembler backing (or built into) the
+#                compiler recognizes "insn"
+# Usage: $(call as-insn-check,<config>,<tool-variant>,<insn>)
+as-insn-check = $(eval $(call as-insn-check-closure,$(1),$(2),$(3)))
+define as-insn-check-closure
+    ifeq ($$(CONFIG_$(1)),y)
+        ifneq ($$(call as-insn,$$($(2)CC) $$($(2)CFLAGS),"$$(3)",y,n),y)
+            $$(warning CONFIG_$(1)=y but assembler used by '$$($(2)CC)' doesn't recognize '$$(3)')
+        endif
+    endif
+endef
+
 # $(call if-success,<command>,<then>,<else>)
 # Return <then> if <command> exits with 0, <else> otherwise.
 if-success = $(shell { $(1); } >/dev/null 2>&1 && echo "$(2)" || echo "$(3)")