re-enable AMD Topology extension on certain models if disabled by BIOS
Some BIOSes disable AMD Topology extension on AMD Family 15h notebook processors. We re-enable the extension, so that we can properly discover core and cache topology. Linux seems to do the same. Reported by: Johannes Dieterich <dieterich.joh@gmail.com> Reviewed by: jhb, kib Tested by: Johannes Dieterich <dieterich.joh@gmail.com> (earlier version) MFC after: 3 weeks Differential Revision: https://reviews.freebsd.org/D5883
This commit is contained in:
parent
53791a95a4
commit
0d63fc3ed8
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=297857
@ -247,7 +247,7 @@ init_secondary(void)
|
||||
wrmsr(MSR_FSBASE, 0); /* User value */
|
||||
wrmsr(MSR_GSBASE, (u_int64_t)pc);
|
||||
wrmsr(MSR_KGSBASE, (u_int64_t)pc); /* XXX User value while we're in the kernel */
|
||||
intel_fix_cpuid();
|
||||
fix_cpuid();
|
||||
|
||||
lidt(&r_idt);
|
||||
|
||||
|
@ -242,7 +242,7 @@ init_secondary(void)
|
||||
pc->pc_prvspace = pc;
|
||||
pc->pc_curthread = 0;
|
||||
|
||||
intel_fix_cpuid();
|
||||
fix_cpuid();
|
||||
|
||||
gdt_segs[GPRIV_SEL].ssd_base = (int) pc;
|
||||
gdt_segs[GPROC0_SEL].ssd_base = (int) &pc->pc_common_tss;
|
||||
|
@ -816,6 +816,7 @@
|
||||
#define MSR_P_STATE_CONFIG(n) (0xc0010064 + (n)) /* P-state Config */
|
||||
#define MSR_SMM_ADDR 0xc0010112 /* SMM TSEG base address */
|
||||
#define MSR_SMM_MASK 0xc0010113 /* SMM TSEG address mask */
|
||||
#define MSR_EXTFEATURES 0xc0011005 /* Extended CPUID Features override */
|
||||
#define MSR_IC_CFG 0xc0011021 /* Instruction Cache Configuration */
|
||||
#define MSR_K8_UCODE_UPDATE 0xc0010020 /* update microcode */
|
||||
#define MSR_MC0_CTL_MASK 0xc0010044
|
||||
|
@ -103,7 +103,7 @@ void dump_drop_page(vm_paddr_t);
|
||||
void identify_cpu(void);
|
||||
void initializecpu(void);
|
||||
void initializecpucache(void);
|
||||
bool intel_fix_cpuid(void);
|
||||
bool fix_cpuid(void);
|
||||
void fillw(int /*u_short*/ pat, void *base, size_t cnt);
|
||||
int is_physical_memory(vm_paddr_t addr);
|
||||
int isa_nmi(int cd);
|
||||
|
@ -1342,23 +1342,22 @@ identify_hypervisor(void)
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Clear "Limit CPUID Maxval" bit and return true if the caller should
|
||||
* get the largest standard CPUID function number again if it is set
|
||||
* from BIOS. It is necessary for probing correct CPU topology later
|
||||
* and for the correct operation of the AVX-aware userspace.
|
||||
*/
|
||||
bool
|
||||
intel_fix_cpuid(void)
|
||||
fix_cpuid(void)
|
||||
{
|
||||
uint64_t msr;
|
||||
|
||||
if (cpu_vendor_id != CPU_VENDOR_INTEL)
|
||||
return (false);
|
||||
if ((CPUID_TO_FAMILY(cpu_id) == 0xf &&
|
||||
/*
|
||||
* Clear "Limit CPUID Maxval" bit and return true if the caller should
|
||||
* get the largest standard CPUID function number again if it is set
|
||||
* from BIOS. It is necessary for probing correct CPU topology later
|
||||
* and for the correct operation of the AVX-aware userspace.
|
||||
*/
|
||||
if (cpu_vendor_id == CPU_VENDOR_INTEL &&
|
||||
((CPUID_TO_FAMILY(cpu_id) == 0xf &&
|
||||
CPUID_TO_MODEL(cpu_id) >= 0x3) ||
|
||||
(CPUID_TO_FAMILY(cpu_id) == 0x6 &&
|
||||
CPUID_TO_MODEL(cpu_id) >= 0xe)) {
|
||||
CPUID_TO_MODEL(cpu_id) >= 0xe))) {
|
||||
msr = rdmsr(MSR_IA32_MISC_ENABLE);
|
||||
if ((msr & IA32_MISC_EN_LIMCPUID) != 0) {
|
||||
msr &= ~IA32_MISC_EN_LIMCPUID;
|
||||
@ -1366,6 +1365,22 @@ intel_fix_cpuid(void)
|
||||
return (true);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Re-enable AMD Topology Extension that could be disabled by BIOS
|
||||
* on some notebook processors. Without the extension it's really
|
||||
* hard to determine the correct CPU cache topology.
|
||||
* See BIOS and Kernel Developer’s Guide (BKDG) for AMD Family 15h
|
||||
* Models 60h-6Fh Processors, Publication # 50742.
|
||||
*/
|
||||
if (cpu_vendor_id == CPU_VENDOR_AMD && CPUID_TO_FAMILY(cpu_id) == 0x15) {
|
||||
msr = rdmsr(MSR_EXTFEATURES);
|
||||
if ((msr & ((uint64_t)1 << 54)) == 0) {
|
||||
msr |= (uint64_t)1 << 54;
|
||||
wrmsr(MSR_EXTFEATURES, msr);
|
||||
return (true);
|
||||
}
|
||||
}
|
||||
return (false);
|
||||
}
|
||||
|
||||
@ -1403,7 +1418,7 @@ identify_cpu(void)
|
||||
identify_hypervisor();
|
||||
cpu_vendor_id = find_cpu_vendor_id();
|
||||
|
||||
if (intel_fix_cpuid()) {
|
||||
if (fix_cpuid()) {
|
||||
do_cpuid(0, regs);
|
||||
cpu_high = regs[0];
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user