Sadly, cf_check typechecking doesn't work through casts. Introduce an ad-hoc
typecheck and fix *_readline_rev() checks to be cf_check.
This is a latent bug. The affected models don't have CET-IBT, so won't
actually explode from lacking endbr64 instructions.
Reported-by: Jan Beulich <JBeulich@suse.com>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
---
CC: Jan Beulich <JBeulich@suse.com>
CC: Roger Pau Monné <roger.pau@citrix.com>
CC: Wei Liu <wl@xen.org>
---
xen/arch/x86/apic.c | 17 +++++++++++------
1 file changed, 11 insertions(+), 6 deletions(-)
diff --git a/xen/arch/x86/apic.c b/xen/arch/x86/apic.c
index 96d73a744964..794bbc21ae2c 100644
--- a/xen/arch/x86/apic.c
+++ b/xen/arch/x86/apic.c
@@ -1092,12 +1092,17 @@ static void setup_APIC_timer(void)
local_irq_restore(flags);
}
+#define DEADLINE_MODEL_FUNCT(m, fn) \
+ { .vendor = X86_VENDOR_INTEL, .family = 6, .model = (m), \
+ .feature = X86_FEATURE_TSC_DEADLINE, \
+ .driver_data = fn + (0 * sizeof(fn == ((unsigned int (*)(void))NULL))) }
+
#define DEADLINE_MODEL_MATCH(m, fr) \
{ .vendor = X86_VENDOR_INTEL, .family = 6, .model = (m), \
.feature = X86_FEATURE_TSC_DEADLINE, \
.driver_data = (void *)(unsigned long)(fr) }
-static unsigned int __init hsx_deadline_rev(void)
+static unsigned int __init cf_check hsx_deadline_rev(void)
{
switch ( boot_cpu_data.x86_mask )
{
@@ -1108,7 +1113,7 @@ static unsigned int __init hsx_deadline_rev(void)
return ~0U;
}
-static unsigned int __init bdx_deadline_rev(void)
+static unsigned int __init cf_check bdx_deadline_rev(void)
{
switch ( boot_cpu_data.x86_mask )
{
@@ -1121,7 +1126,7 @@ static unsigned int __init bdx_deadline_rev(void)
return ~0U;
}
-static unsigned int __init skx_deadline_rev(void)
+static unsigned int __init cf_check skx_deadline_rev(void)
{
switch ( boot_cpu_data.x86_mask )
{
@@ -1135,17 +1140,17 @@ static unsigned int __init skx_deadline_rev(void)
static const struct x86_cpu_id __initconstrel deadline_match[] = {
DEADLINE_MODEL_MATCH(0x3c, 0x22), /* Haswell */
- DEADLINE_MODEL_MATCH(0x3f, hsx_deadline_rev), /* Haswell EP/EX */
+ DEADLINE_MODEL_FUNCT(0x3f, hsx_deadline_rev), /* Haswell EP/EX */
DEADLINE_MODEL_MATCH(0x45, 0x20), /* Haswell D */
DEADLINE_MODEL_MATCH(0x46, 0x17), /* Haswell H */
DEADLINE_MODEL_MATCH(0x3d, 0x25), /* Broadwell */
DEADLINE_MODEL_MATCH(0x47, 0x17), /* Broadwell H */
DEADLINE_MODEL_MATCH(0x4f, 0x0b000020), /* Broadwell EP/EX */
- DEADLINE_MODEL_MATCH(0x56, bdx_deadline_rev), /* Broadwell D */
+ DEADLINE_MODEL_FUNCT(0x56, bdx_deadline_rev), /* Broadwell D */
DEADLINE_MODEL_MATCH(0x4e, 0xb2), /* Skylake M */
- DEADLINE_MODEL_MATCH(0x55, skx_deadline_rev), /* Skylake X */
+ DEADLINE_MODEL_FUNCT(0x55, skx_deadline_rev), /* Skylake X */
DEADLINE_MODEL_MATCH(0x5e, 0xb2), /* Skylake D */
DEADLINE_MODEL_MATCH(0x8e, 0x52), /* Kabylake M */
--
2.11.0
On 21.03.2022 15:12, Andrew Cooper wrote: > --- a/xen/arch/x86/apic.c > +++ b/xen/arch/x86/apic.c > @@ -1092,12 +1092,17 @@ static void setup_APIC_timer(void) > local_irq_restore(flags); > } > > +#define DEADLINE_MODEL_FUNCT(m, fn) \ > + { .vendor = X86_VENDOR_INTEL, .family = 6, .model = (m), \ > + .feature = X86_FEATURE_TSC_DEADLINE, \ > + .driver_data = fn + (0 * sizeof(fn == ((unsigned int (*)(void))NULL))) } Are you sure all compiler versions we support are happy about + of a function pointer and a constant? Even if that constant is zero, this is not legal as per the plain C spec. Also strictly speaking you would want to parenthesize both uses of fn. > #define DEADLINE_MODEL_MATCH(m, fr) \ > { .vendor = X86_VENDOR_INTEL, .family = 6, .model = (m), \ > .feature = X86_FEATURE_TSC_DEADLINE, \ > .driver_data = (void *)(unsigned long)(fr) } As long as we leave this in place, there's a (small) risk of the wrong macro being used again if another hook would need adding here. We might be safer if driver_data became "unsigned long" and the void * cast was dropped from here (with an "unsigned long" cast added in the new macro, which at the same time would address my other concern above). Jan
© 2016 - 2024 Red Hat, Inc.