[PATCH] x86/cpu/centaur: Disable X86_FEATURE_FSGSBASE on Zhaoxin C4600

From: Yao Zi

Date: Sat Feb 28 2026 - 13:27:58 EST


Zhaoxin C4600, which names itself as CentaurHauls, claims
X86_FEATURE_FSGSBASE support in CPUID, while execution of fsgsbase-
related instructions fails with #UD exception. This will cause kernel
to crash early in current_save_fsgs().

Let's disable the feature on this problematic CPU and warn the user
about the quirk. x86_model_id is used to match the platform to avoid
unexpectedly breaking other CentaurHauls cores with conflicting
family/model ID.

Cc: stable@xxxxxxxxxxxxxxx
Signed-off-by: Yao Zi <me@xxxxxxxx>
---
arch/x86/kernel/cpu/centaur.c | 25 +++++++++++++++++++++++++
1 file changed, 25 insertions(+)

diff --git a/arch/x86/kernel/cpu/centaur.c b/arch/x86/kernel/cpu/centaur.c
index 81695da9c524..3773784ba6a9 100644
--- a/arch/x86/kernel/cpu/centaur.c
+++ b/arch/x86/kernel/cpu/centaur.c
@@ -108,6 +108,29 @@ static void early_init_centaur(struct cpuinfo_x86 *c)
}
}

+/*
+ * Zhaoxin C4600 (family 6, model 15) names itself as CentaurHauls, it claims
+ * X86_FEATURE_FSGSBASE support in CPUID, while executing any fsgsbase-related
+ * instructions on it results in #UD.
+ */
+static void fixup_zhaoxin_fsgsbase(struct cpuinfo_x86 *c)
+{
+ const char *name, *model_names[] = {
+ "C-QuadCore C4600"
+ };
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(model_names); i++) {
+ name = model_names[i];
+
+ if (!strncmp(c->x86_model_id, name, strlen(name))) {
+ pr_warn_once("CPU has broken FSGSBASE support\n");
+ setup_clear_cpu_cap(X86_FEATURE_FSGSBASE);
+ return;
+ }
+ }
+}
+
static void init_centaur(struct cpuinfo_x86 *c)
{
#ifdef CONFIG_X86_32
@@ -201,6 +224,8 @@ static void init_centaur(struct cpuinfo_x86 *c)
set_cpu_cap(c, X86_FEATURE_LFENCE_RDTSC);
#endif

+ fixup_zhaoxin_fsgsbase(c);
+
init_ia32_feat_ctl(c);
}

--
2.53.0