add CPUID probe

Just print vendor, Hypervisor...
This commit is contained in:
Hojun-Cho 2024-12-09 21:28:45 +09:00
parent b1f7092fe2
commit 98601ac381
4 changed files with 61 additions and 1 deletions

View File

@ -5,7 +5,7 @@ PROG = boot
SRCS = srt0.S gdt.S boot.c SRCS = srt0.S gdt.S boot.c
OBJS = srt0.o gdt.o boot.o OBJS = srt0.o gdt.o boot.o
ESRCS = pccon.c sricon.c print.c fmt.c a20.c time.c mem.c ESRCS = pccon.c sricon.c print.c fmt.c a20.c time.c mem.c cpu.c
OBJS += $(ESRCS:.c=.o) OBJS += $(ESRCS:.c=.o)
include $(SDIR)/Makefile.inc include $(SDIR)/Makefile.inc

View File

@ -7,6 +7,7 @@ static void machdep(void);
void (*probe1[])(void) = { void (*probe1[])(void) = {
a20up, coninit, memprobe, a20up, coninit, memprobe,
cpuidprobe,
}; };
void (*probe2[])(void) = { void (*probe2[])(void) = {
}; };

56
boot/cpu.c Normal file
View File

@ -0,0 +1,56 @@
#include <u.h>
#include "dat.h"
#include "fn.h"
#define EFLAG_ID 0x00200000
#define CPUID(code, a, b, c, d) \
__asm volatile("cpuid" \
: "=a" (a), "=b" (b), "=c" (c), "=d" (d) \
: "a" (code))
void*
memset(void *dst, int v, int l)
{
char *p = dst;
for(int i = 0; i < l; ++i)
*p++ = 0;
return dst;
}
void
cpuidprobe(void)
{
int canuse;
union{
struct{u32 a,b,d,c;};
char arr[16];
}r = {0,};
__asm volatile("pushfl\n\t"
"popl %2\n\t"
"xorl %2, %0\n\t" /* Invert ID sotred in EFLAGS */
"pushl %0\n\t"
"popfl\n\t"
"pushfl\n\t"
"popl %0\n\t"
"xorl %2, %0\n\t"
: "=r" (canuse)
: "0" (EFLAG_ID), "r" (0) /* "EFLAGS_ID" same location "canuse" */
: "cc");
if(canuse != EFLAG_ID){
print("cpuid not available\n");
return;
}
// print vendor
CPUID(0x00, r.a, r.b, r.c, r.d);
print("CPU vender: %s\n", r.arr+4);
// Is running on Hypervisor?
// But nothing to do...
memset(&r, 0,sizeof(r));
CPUID(0x01, r.a, r.b, r.c, r.d);
if(r.c & (1<<31)){
CPUID(1<<30, r.a, r.b, r.c, r.d);
print("Running on Hypervisor: %s\n", r.arr+4);
}
}

View File

@ -29,6 +29,9 @@ void a20up(void);
// mem.c // mem.c
void memprobe(void); void memprobe(void);
// cpu.c
void cpuidprobe(void);
// time.c // time.c
long getsecs(void); long getsecs(void);