diff options
Diffstat (limited to 'sys/arch/amd64/amd64/machdep.c')
-rw-r--r-- | sys/arch/amd64/amd64/machdep.c | 44 |
1 files changed, 40 insertions, 4 deletions
diff --git a/sys/arch/amd64/amd64/machdep.c b/sys/arch/amd64/amd64/machdep.c index 9b65d6e..40950f9 100644 --- a/sys/arch/amd64/amd64/machdep.c +++ b/sys/arch/amd64/amd64/machdep.c @@ -44,6 +44,8 @@ #include <machine/intr.h> #include <machine/cdefs.h> #include <machine/isa/i8042var.h> +#include <dev/cons/cons.h> +#include <string.h> #define pr_trace(fmt, ...) kprintf("cpu: " fmt, ##__VA_ARGS__) #define pr_error(...) pr_trace(__VA_ARGS__) @@ -185,9 +187,10 @@ enable_simd(void) } static void -cpu_check_feat(struct cpu_info *ci) +cpu_get_info(struct cpu_info *ci) { - uint32_t unused, ebx; + uint32_t eax, ebx, unused; + uint8_t ext_model, ext_family; /* Extended features */ CPUID(0x07, unused, ebx, unused, unused); @@ -195,6 +198,33 @@ cpu_check_feat(struct cpu_info *ci) ci->feat |= CPU_FEAT_SMEP; if (ISSET(ebx, BIT(20))) ci->feat |= CPU_FEAT_SMAP; + + /* + * Processor info and feature bits + */ + CPUID(0x01, eax, unused, unused, unused); + ci->model = (eax >> 4) & 0xF; + ci->family = (eax >> 8) & 0xF; + + /* + * If the family ID is 15 then the actual family + * ID is the sum of the extended family and the + * family ID fields. + */ + if (ci->family == 0xF) { + ext_family = (eax >> 20) & 0xFF; + ci->family += ext_family; + } + + /* + * If the family has the value of either 6 or 15, + * then the extended model number would be used. + * Slap them together if this is the case. + */ + if (ci->family == 6 || ci->family == 15) { + ext_model = (eax >> 16) & 0xF; + ci->model |= (ext_model << 4); + } } void @@ -224,6 +254,7 @@ md_backtrace(void) uintptr_t rip; off_t off; const char *name; + char line[256]; __ASMV("mov %%rbp, %0" : "=r" (rbp) :: "memory"); while (1) { @@ -236,7 +267,8 @@ md_backtrace(void) if (name == NULL) name = "???"; - kprintf(OMIT_TIMESTAMP "%p @ <%s+0x%x>\n", rip, name, off); + snprintf(line, sizeof(line), "%p @ <%s+0x%x>\n", rip, name, off); + cons_putstr(&g_root_scr, line, strlen(line)); } } @@ -294,6 +326,10 @@ this_cpu(void) { struct cpu_info *ci; + if (rdmsr(IA32_GS_BASE) == 0) { + return NULL; + } + /* * This might look crazy but we are just leveraging the "m" * constraint to add the offset of the self field within @@ -375,7 +411,7 @@ cpu_startup(struct cpu_info *ci) init_tss(ci); try_mitigate_spectre(); - cpu_check_feat(ci); + cpu_get_info(ci); cpu_enable_smep(); enable_simd(); |