summaryrefslogtreecommitdiff
path: root/src/bootloader/cpu_check.asm
blob: ffdd908b438d0c84da25a8668b48a60bd0346d25 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
; TODO move this file to something like "system_check", now that we do ram checks here
[extern _meminfo_loc]
detect_arch:
; todo: figure out how to just handle invalid opcode exceptions, it would be faster and (maybe?) easier 
; todo: digest this part a little better when it's _not_ 1am.
pushfd    ; pushes eflags to stack
pushfd    ; pushes eflags to stack a second time
xor dword [esp], 0x00200000 ; inverses the ID bit to see if cpuid is a thing
pop eax         ;gets our modified cpuid back
xor eax, [esp]  ; checks with the first time we pushed it; the OG eflag
popfd           ; pops the flags back I guess?
and eax, 0x00200000 ; checks to see if the bit was inverted
jz .print_cpuid_error
;now we detect if we support long slong (aka 64 bit)

;https://www.amd.com/system/files/TechDocs/25481.pdf page 21
;So apperently some dumbass engineers thought it would be funny to sell CPUs that have the long mode bit set without it being supported, dispite including it in their own documentation.
;there's a work around by checking other bits, and it's a low priority TODO. However, I really think us coming accross this will be extremely rare.
mov eax, 0x80000001
cpuid ;cpuid returns into edx
and edx, 0x0020000000 ; the 21st bit is cpuid.
jz .print_long_error

mov eax, 0x00000001
cpuid
and edx, 0x00000200
jz .print_apic_error


mov bx, .no_error
mov cx, 0
call bios_print


;mapping memory
mov ax, 0
mov es, ax
mov ax, _meminfo_loc
mov di, ax

mov eax, 0xe820
mov ebx, 0
mov ecx, 24
mov edx, 0x534d4150
int 0x15

jc .print_mem_error
cmp eax, 0x534D4150
jne .print_mem_error

.mem_detect_loop:
add di, 24
mov [di + 20], dword 1
mov eax, 0xe820
mov ecx, 24

int 0x15
jc .mem_detected
cmp ebx, 0
je .mem_detected
jmp .mem_detect_loop
.mem_detected:

ret


.print_cpuid_error:
mov bx, .cpuid_error
mov cx, 0
call bios_print
jmp $

.print_long_error:
mov bx, .arch_error ; lets just test for now
mov cx, 0
call bios_print
jmp $

.print_apic_error:
mov bx, .apic_error
mov cx, 0
call bios_print

.print_mem_error:
mov bx, .mem_error
mov cx, 0
call bios_print


.cpuid_error:
  db "No CPUID capabilitity", 0x0
.arch_error:
 db "This operating system was compiled to run in 64 bit mode!", 0x0
.apic_error:
  db "No apic support", 0x0
.mem_error:
  db "Could not get information on memory!", 0x0
.no_error:
  db "CPU info gathered!", 0x0