refactor: replace all stdint::uint32_t into short and more manageable u32_t
[lunaix-os.git] / lunaix-os / hal / cpu.c
1 #include <cpuid.h>
2 #include <hal/cpu.h>
3 #include <stdint.h>
4
5 void
6 cpu_get_model(char* model_out)
7 {
8     u32_t* out = (u32_t*)model_out;
9     reg32 eax = 0, ebx = 0, edx = 0, ecx = 0;
10
11     __get_cpuid(0, &eax, &ebx, &ecx, &edx);
12
13     out[0] = ebx;
14     out[1] = edx;
15     out[2] = ecx;
16     model_out[12] = '\0';
17 }
18
19 #define BRAND_LEAF 0x80000000UL
20
21 int
22 cpu_brand_string_supported()
23 {
24     reg32 supported = __get_cpuid_max(BRAND_LEAF, 0);
25     return (supported >= 0x80000004UL);
26 }
27
28 void
29 cpu_get_brand(char* brand_out)
30 {
31     if (!cpu_brand_string_supported()) {
32         brand_out[0] = '?';
33         brand_out[1] = '\0';
34     }
35     u32_t* out = (u32_t*)brand_out;
36     reg32 eax = 0, ebx = 0, edx = 0, ecx = 0;
37     for (u32_t i = 2, j = 0; i < 5; i++) {
38         __get_cpuid(BRAND_LEAF + i, &eax, &ebx, &ecx, &edx);
39         out[j] = eax;
40         out[j + 1] = ebx;
41         out[j + 2] = ecx;
42         out[j + 3] = edx;
43         j += 4;
44     }
45     brand_out[48] = '\0';
46 }
47
48 int
49 cpu_has_apic()
50 {
51     // reference: Intel manual, section 10.4.2
52     reg32 eax = 0, ebx = 0, edx = 0, ecx = 0;
53     __get_cpuid(1, &eax, &ebx, &ecx, &edx);
54
55     return (edx & 0x100);
56 }
57
58 void
59 cpu_rdmsr(u32_t msr_idx, u32_t* reg_high, u32_t* reg_low)
60 {
61     u32_t h = 0, l = 0;
62     asm volatile("rdmsr" : "=d"(h), "=a"(l) : "c"(msr_idx));
63
64     *reg_high = h;
65     *reg_low = l;
66 }
67
68 void
69 cpu_wrmsr(u32_t msr_idx, u32_t reg_high, u32_t reg_low)
70 {
71     asm volatile("wrmsr" : : "d"(reg_high), "a"(reg_low), "c"(msr_idx));
72 }