mirror of
https://github.com/xen-project/xen.git
synced 2026-10-28 10:11:27 +01:00
x86/cpuid: Drop get_cpu_vendor() completely
get_cpu_vendor() tries to do a number of things, and ends up doing none of them well. For calculating the vendor itself, use x86_cpuid_lookup_vendor() which is implemented in a far more efficient manner than looping over cpu_devs[]. For setting up this_cpu, set it up once on the BSP only, rather than latest-takes-precident across the APs. Such a system is probably not going to boot, but this feels like a less dangerous course of action. Adjust the printed errors to be more clear in the mismatch case. This removes the only user of cpu_dev->c_ident[], so drop that field as well. Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com> Reviewed-by: Jan Beulich <jbeulich@suse.com>
This commit is contained in:
1 parent
e72309ffbe
commit
00b4f4d0fb
8 files changed
+15
-46
No files matched your search
@@ -794,7 +794,6 @@ static void init_amd(struct cpuinfo_x86 *c)
|
||||
|
||||
static const struct cpu_dev amd_cpu_dev = {
|
||||
.c_vendor = "AMD",
|
||||
.c_ident = { "AuthenticAMD" },
|
||||
.c_early_init = early_init_amd,
|
||||
.c_init = init_amd,
|
||||
};
|
||||
|
||||
@@ -56,7 +56,6 @@ static void init_centaur(struct cpuinfo_x86 *c)
|
||||
|
||||
static const struct cpu_dev centaur_cpu_dev = {
|
||||
.c_vendor = "Centaur",
|
||||
.c_ident = { "CentaurHauls" },
|
||||
.c_init = init_centaur,
|
||||
};
|
||||
|
||||
|
||||
+13
-32
@@ -247,36 +247,6 @@ void display_cacheinfo(struct cpuinfo_x86 *c)
|
||||
l2size, ecx & 0xFF);
|
||||
}
|
||||
|
||||
int get_cpu_vendor(uint32_t b, uint32_t c, uint32_t d, enum get_cpu_vendor mode)
|
||||
{
|
||||
int i;
|
||||
static int printed;
|
||||
|
||||
for (i = 0; i < X86_VENDOR_NUM; i++) {
|
||||
if (cpu_devs[i]) {
|
||||
struct {
|
||||
uint32_t b, d, c;
|
||||
} *ptr = (void *)cpu_devs[i]->c_ident;
|
||||
|
||||
if (ptr->b == b && ptr->c == c && ptr->d == d) {
|
||||
if (mode == gcv_host)
|
||||
this_cpu = cpu_devs[i];
|
||||
return i;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (mode == gcv_guest)
|
||||
return X86_VENDOR_UNKNOWN;
|
||||
if (!printed) {
|
||||
printed++;
|
||||
printk(KERN_ERR "CPU: Vendor unknown, using generic init.\n");
|
||||
printk(KERN_ERR "CPU: Your system may be unstable.\n");
|
||||
}
|
||||
this_cpu = &default_cpu;
|
||||
|
||||
return X86_VENDOR_UNKNOWN;
|
||||
}
|
||||
|
||||
static inline u32 _phys_pkg_id(u32 cpuid_apic, int index_msb)
|
||||
{
|
||||
return cpuid_apic >> index_msb;
|
||||
@@ -313,7 +283,13 @@ static void __init early_cpu_detect(void)
|
||||
*(u32 *)&c->x86_vendor_id[8] = ecx;
|
||||
*(u32 *)&c->x86_vendor_id[4] = edx;
|
||||
|
||||
c->x86_vendor = get_cpu_vendor(ebx, ecx, edx, gcv_host);
|
||||
c->x86_vendor = x86_cpuid_lookup_vendor(ebx, ecx, edx);
|
||||
if (c->x86_vendor < ARRAY_SIZE(cpu_devs) && cpu_devs[c->x86_vendor])
|
||||
this_cpu = cpu_devs[c->x86_vendor];
|
||||
else
|
||||
printk(XENLOG_ERR
|
||||
"Unrecognised or unsupported CPU vendor '%.12s'\n",
|
||||
c->x86_vendor_id);
|
||||
|
||||
cpuid(0x00000001, &eax, &ebx, &ecx, &edx);
|
||||
c->x86 = get_cpu_family(eax, &c->x86_model, &c->x86_mask);
|
||||
@@ -361,7 +337,12 @@ static void generic_identify(struct cpuinfo_x86 *c)
|
||||
*(u32 *)&c->x86_vendor_id[8] = ecx;
|
||||
*(u32 *)&c->x86_vendor_id[4] = edx;
|
||||
|
||||
c->x86_vendor = get_cpu_vendor(ebx, ecx, edx, gcv_host);
|
||||
c->x86_vendor = x86_cpuid_lookup_vendor(ebx, ecx, edx);
|
||||
if (boot_cpu_data.x86_vendor != c->x86_vendor)
|
||||
printk(XENLOG_ERR "CPU%u vendor %u mismatch against BSP %u\n",
|
||||
smp_processor_id(), c->x86_vendor,
|
||||
boot_cpu_data.x86_vendor);
|
||||
|
||||
/* Initialize the standard set of capabilities */
|
||||
/* Note that the vendor-specific code below might override */
|
||||
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
/* attempt to consolidate cpu attributes */
|
||||
struct cpu_dev {
|
||||
char c_vendor[8];
|
||||
char c_ident[13];
|
||||
|
||||
void (*c_early_init)(struct cpuinfo_x86 *c);
|
||||
void (*c_init)(struct cpuinfo_x86 * c);
|
||||
|
||||
@@ -350,7 +350,6 @@ static void init_intel(struct cpuinfo_x86 *c)
|
||||
|
||||
static const struct cpu_dev intel_cpu_dev = {
|
||||
.c_vendor = "Intel",
|
||||
.c_ident = { "GenuineIntel" },
|
||||
.c_early_init = early_init_intel,
|
||||
.c_init = init_intel,
|
||||
};
|
||||
|
||||
@@ -17,7 +17,6 @@ static void init_shanghai(struct cpuinfo_x86 *c)
|
||||
|
||||
static const struct cpu_dev shanghai_cpu_dev = {
|
||||
.c_vendor = " Shang",
|
||||
.c_ident = {" Shanghai "},
|
||||
.c_init = init_shanghai,
|
||||
};
|
||||
|
||||
|
||||
@@ -459,8 +459,8 @@ void recalculate_cpuid_policy(struct domain *d)
|
||||
uint32_t fs[FSCAPINTS], max_fs[FSCAPINTS];
|
||||
unsigned int i;
|
||||
|
||||
p->x86_vendor = get_cpu_vendor(p->basic.vendor_ebx, p->basic.vendor_ecx,
|
||||
p->basic.vendor_edx, gcv_guest);
|
||||
p->x86_vendor = x86_cpuid_lookup_vendor(
|
||||
p->basic.vendor_ebx, p->basic.vendor_ecx, p->basic.vendor_edx);
|
||||
|
||||
p->basic.max_leaf = min(p->basic.max_leaf, max->basic.max_leaf);
|
||||
p->feat.max_subleaf = min(p->feat.max_subleaf, max->feat.max_subleaf);
|
||||
|
||||
@@ -579,13 +579,6 @@ int early_microcode_init(void);
|
||||
int microcode_init_intel(void);
|
||||
int microcode_init_amd(void);
|
||||
|
||||
enum get_cpu_vendor {
|
||||
gcv_host,
|
||||
gcv_guest,
|
||||
};
|
||||
|
||||
int get_cpu_vendor(uint32_t b, uint32_t c, uint32_t d, enum get_cpu_vendor mode);
|
||||
|
||||
static inline uint8_t get_cpu_family(uint32_t raw, uint8_t *model,
|
||||
uint8_t *stepping)
|
||||
{
|
||||
|
||||