Index: sys/amd64/amd64/pmap.c =================================================================== --- sys/amd64/amd64/pmap.c (revision 215352) +++ sys/amd64/amd64/pmap.c (working copy) @@ -180,10 +180,13 @@ static vm_paddr_t dmaplimit; vm_offset_t kernel_vm_end = VM_MIN_KERNEL_ADDRESS; pt_entry_t pg_nx; -static int pat_works = 0; /* Is page attribute table sane? */ - SYSCTL_NODE(_vm, OID_AUTO, pmap, CTLFLAG_RD, 0, "VM/pmap parameters"); +static int pat_works = 1; +TUNABLE_INT("vm.pmap.pat_works", &pat_works); +SYSCTL_INT(_vm_pmap, OID_AUTO, pat_works, CTLFLAG_RDTUN, &pat_works, 1, + "Is page attribute table fully functional?"); + static int pg_ps_enabled = 1; SYSCTL_INT(_vm_pmap, OID_AUTO, pg_ps_enabled, CTLFLAG_RDTUN, &pg_ps_enabled, 0, "Are large page mappings enabled?"); @@ -609,35 +612,15 @@ void pmap_init_pat(void) { uint64_t pat_msr; - char *sysenv; - static int pat_tested = 0; /* Bail if this CPU doesn't implement PAT. */ if (!(cpu_feature & CPUID_PAT)) panic("no PAT??"); - /* - * Some Apple Macs based on nVidia chipsets cannot enter ACPI mode - * via SMI# when we use upper 4 PAT entries for unknown reason. - */ - if (!pat_tested) { - pat_works = 1; - sysenv = getenv("smbios.system.product"); - if (sysenv != NULL) { - if (strncmp(sysenv, "MacBook5,1", 10) == 0 || - strncmp(sysenv, "MacBookPro5,5", 13) == 0 || - strncmp(sysenv, "Macmini3,1", 10) == 0 || - strncmp(sysenv, "iMac9,1", 7) == 0) - pat_works = 0; - freeenv(sysenv); - } - pat_tested = 1; - } - /* Initialize default PAT entries. */ pat_msr = PAT_VALUE(0, PAT_WRITE_BACK) | PAT_VALUE(1, PAT_WRITE_THROUGH) | - PAT_VALUE(2, PAT_UNCACHED) | + PAT_VALUE(2, PAT_WRITE_COMBINING) | PAT_VALUE(3, PAT_UNCACHEABLE) | PAT_VALUE(4, PAT_WRITE_BACK) | PAT_VALUE(5, PAT_WRITE_THROUGH) | @@ -646,19 +629,10 @@ pmap_init_pat(void) if (pat_works) { /* - * Leave the indices 0-3 at the default of WB, WT, UC-, and UC. - * Program 4 and 5 as WP and WC. - * Leave 6 and 7 as UC- and UC. + * Just replace PAT Index 5 with WP instead of WT. */ - pat_msr &= ~(PAT_MASK(4) | PAT_MASK(5)); - pat_msr |= PAT_VALUE(4, PAT_WRITE_PROTECTED) | - PAT_VALUE(5, PAT_WRITE_COMBINING); - } else { - /* - * Just replace PAT Index 2 with WC instead of UC-. - */ - pat_msr &= ~PAT_MASK(2); - pat_msr |= PAT_VALUE(2, PAT_WRITE_COMBINING); + pat_msr &= ~PAT_MASK(5); + pat_msr |= PAT_VALUE(5, PAT_WRITE_PROTECTED); } wrmsr(MSR_PAT, pat_msr); } @@ -829,13 +803,13 @@ pmap_cache_bits(int mode, boolean_t is_pde) pat_index = 0; break; case PAT_UNCACHED: - pat_index = 2; + pat_index = 6; break; case PAT_WRITE_COMBINING: - pat_index = 5; + pat_index = 2; break; case PAT_WRITE_PROTECTED: - pat_index = 4; + pat_index = 5; break; default: panic("Unknown caching mode %d\n", mode); Index: sys/i386/i386/pmap.c =================================================================== --- sys/i386/i386/pmap.c (revision 215352) +++ sys/i386/i386/pmap.c (working copy) @@ -217,10 +217,13 @@ pt_entry_t pg_nx; static uma_zone_t pdptzone; #endif -static int pat_works = 0; /* Is page attribute table sane? */ - SYSCTL_NODE(_vm, OID_AUTO, pmap, CTLFLAG_RD, 0, "VM/pmap parameters"); +static int pat_works = 1; +TUNABLE_INT("vm.pmap.pat_works", &pat_works); +SYSCTL_INT(_vm_pmap, OID_AUTO, pat_works, CTLFLAG_RDTUN, &pat_works, 1, + "Is page attribute table fully functional?"); + static int pg_ps_enabled = 1; SYSCTL_INT(_vm_pmap, OID_AUTO, pg_ps_enabled, CTLFLAG_RDTUN, &pg_ps_enabled, 0, "Are large page mappings enabled?"); @@ -491,12 +494,12 @@ void pmap_init_pat(void) { uint64_t pat_msr; - char *sysenv; - static int pat_tested = 0; /* Bail if this CPU doesn't implement PAT. */ - if (!(cpu_feature & CPUID_PAT)) + if (!(cpu_feature & CPUID_PAT)) { + pat_works = 0; return; + } /* * Due to some Intel errata, we can only safely use the lower 4 @@ -508,32 +511,15 @@ pmap_init_pat(void) * * Intel Pentium IV Processor Specification Update * Errata N46 (PAT Index MSB May Be Calculated Incorrectly) - * - * Some Apple Macs based on nVidia chipsets cannot enter ACPI mode - * via SMI# when we use upper 4 PAT entries for unknown reason. */ - if (!pat_tested) { - if (cpu_vendor_id != CPU_VENDOR_INTEL || - (CPUID_TO_FAMILY(cpu_id) == 6 && - CPUID_TO_MODEL(cpu_id) >= 0xe)) { - pat_works = 1; - sysenv = getenv("smbios.system.product"); - if (sysenv != NULL) { - if (strncmp(sysenv, "MacBook5,1", 10) == 0 || - strncmp(sysenv, "MacBookPro5,5", 13) == 0 || - strncmp(sysenv, "Macmini3,1", 10) == 0 || - strncmp(sysenv, "iMac9,1", 7) == 0) - pat_works = 0; - freeenv(sysenv); - } - } - pat_tested = 1; - } + if (cpu_vendor_id == CPU_VENDOR_INTEL && + !(CPUID_TO_FAMILY(cpu_id) == 6 && CPUID_TO_MODEL(cpu_id) >= 0xe)) + pat_works = 0; /* Initialize default PAT entries. */ pat_msr = PAT_VALUE(0, PAT_WRITE_BACK) | PAT_VALUE(1, PAT_WRITE_THROUGH) | - PAT_VALUE(2, PAT_UNCACHED) | + PAT_VALUE(2, PAT_WRITE_COMBINING) | PAT_VALUE(3, PAT_UNCACHEABLE) | PAT_VALUE(4, PAT_WRITE_BACK) | PAT_VALUE(5, PAT_WRITE_THROUGH) | @@ -542,19 +528,10 @@ pmap_init_pat(void) if (pat_works) { /* - * Leave the indices 0-3 at the default of WB, WT, UC-, and UC. - * Program 4 and 5 as WP and WC. - * Leave 6 and 7 as UC- and UC. + * Just replace PAT Index 5 with WP instead of WT. */ - pat_msr &= ~(PAT_MASK(4) | PAT_MASK(5)); - pat_msr |= PAT_VALUE(4, PAT_WRITE_PROTECTED) | - PAT_VALUE(5, PAT_WRITE_COMBINING); - } else { - /* - * Just replace PAT Index 2 with WC instead of UC-. - */ - pat_msr &= ~PAT_MASK(2); - pat_msr |= PAT_VALUE(2, PAT_WRITE_COMBINING); + pat_msr &= ~PAT_MASK(5); + pat_msr |= PAT_VALUE(5, PAT_WRITE_PROTECTED); } wrmsr(MSR_PAT, pat_msr); } @@ -825,13 +802,13 @@ pmap_cache_bits(int mode, boolean_t is_pde) pat_index = 0; break; case PAT_UNCACHED: - pat_index = 2; + pat_index = 6; break; case PAT_WRITE_COMBINING: - pat_index = 5; + pat_index = 2; break; case PAT_WRITE_PROTECTED: - pat_index = 4; + pat_index = 5; break; default: panic("Unknown caching mode %d\n", mode);