1 2#include "apic-defs.h" 3 4.globl boot_idt 5boot_idt = 0 6 7ipi_vector = 0x20 8 9max_cpus = 64 10 11.bss 12 13 . = . + 4096 * max_cpus 14 .align 16 15stacktop: 16 17 . = . + 4096 18 .align 16 19ring0stacktop: 20 21.data 22 23.align 4096 24pt: 25i = 0 26 .rept 1024 27 .long 0x1e7 | (i << 22) 28 i = i + 1 29 .endr 30 31.globl gdt32 32gdt32: 33 .quad 0 34 .quad 0x00cf9b000000ffff // flat 32-bit code segment 35 .quad 0x00cf93000000ffff // flat 32-bit data segment 36 .quad 0x00cf1b000000ffff // flat 32-bit code segment, not present 37 .quad 0x00cffb000000ffff // 64-bit code segment (user) 38 .quad 0x00cff3000000ffff // 64-bit data segment (user) 39 40 .quad 0 // 10 spare selectors 41 .quad 0 42 .quad 0 43 .quad 0 44 .quad 0 45 .quad 0 46 .quad 0 47 .quad 0 48 .quad 0 49 .quad 0 50 51tss_descr: 52 .rept max_cpus 53 .quad 0x000089000000ffff // 32-bit avail tss 54 .endr 55gdt32_end: 56 57i = 0 58.globl tss 59tss: 60 .rept max_cpus 61 .long 0 62 .long ring0stacktop - i * 4096 63 .long 16 64 .quad 0, 0 65 .quad 0, 0, 0, 0, 0, 0, 0, 0 66 .long 0, 0, 0 67 i = i + 1 68 .endr 69tss_end: 70 71idt_descr: 72 .word 16 * 256 - 1 73 .long boot_idt 74 75.section .init 76 77.code32 78 79mb_magic = 0x1BADB002 80mb_flags = 0x0 81 82 # multiboot header 83 .long mb_magic, mb_flags, 0 - (mb_magic + mb_flags) 84mb_cmdline = 16 85 86MSR_GS_BASE = 0xc0000101 87 88.macro setup_percpu_area 89 lea -4096(%esp), %eax 90 mov $0, %edx 91 mov $MSR_GS_BASE, %ecx 92 wrmsr 93.endm 94 95.globl start 96start: 97 push %ebx 98 call setup_get_initrd 99 mov mb_cmdline(%ebx), %eax 100 mov %eax, __args 101 call __setup_args 102 mov $stacktop, %esp 103 setup_percpu_area 104 call prepare_32 105 jmpl $8, $start32 106 107prepare_32: 108 lgdtl gdt32_descr 109 110 mov %cr4, %eax 111 bts $4, %eax // pse 112 mov %eax, %cr4 113 114 mov $pt, %eax 115 mov %eax, %cr3 116 117 mov %cr0, %eax 118 bts $0, %eax 119 bts $31, %eax 120 mov %eax, %cr0 121 ret 122 123smp_stacktop: .long 0xa0000 124 125ap_start32: 126 mov $0x10, %ax 127 mov %ax, %ds 128 mov %ax, %es 129 mov %ax, %fs 130 mov %ax, %gs 131 mov %ax, %ss 132 mov $-4096, %esp 133 lock/xaddl %esp, smp_stacktop 134 setup_percpu_area 135 call prepare_32 136 call load_tss 137 call enable_apic 138 call enable_x2apic 139 sti 140 nop 141 lock incw cpu_online_count 142 1431: hlt 144 jmp 1b 145 146start32: 147 call load_tss 148 call mask_pic_interrupts 149 call enable_apic 150 call smp_init 151 call enable_x2apic 152 push $__argv 153 push __argc 154 call main 155 push %eax 156 call exit 157 158load_tss: 159 lidt idt_descr 160 mov $16, %eax 161 mov %ax, %ss 162 mov $(APIC_DEFAULT_PHYS_BASE + APIC_ID), %eax 163 mov (%eax), %eax 164 shr $24, %eax 165 mov %eax, %ebx 166 shl $3, %ebx 167 mov $((tss_end - tss) / max_cpus), %edx 168 imul %edx 169 add $tss, %eax 170 mov %ax, tss_descr+2(%ebx) 171 shr $16, %eax 172 mov %al, tss_descr+4(%ebx) 173 shr $8, %eax 174 mov %al, tss_descr+7(%ebx) 175 lea tss_descr-gdt32(%ebx), %eax 176 ltr %ax 177 ret 178 179smp_init: 180 cld 181 lea sipi_entry, %esi 182 xor %edi, %edi 183 mov $(sipi_end - sipi_entry), %ecx 184 rep/movsb 185 mov $APIC_DEFAULT_PHYS_BASE, %eax 186 movl $(APIC_DEST_ALLBUT | APIC_DEST_PHYSICAL | APIC_DM_INIT | APIC_INT_ASSERT), APIC_ICR(%eax) 187 movl $(APIC_DEST_ALLBUT | APIC_DEST_PHYSICAL | APIC_DM_INIT), APIC_ICR(%eax) 188 movl $(APIC_DEST_ALLBUT | APIC_DEST_PHYSICAL | APIC_DM_STARTUP), APIC_ICR(%eax) 189 call fwcfg_get_nb_cpus 1901: pause 191 cmpw %ax, cpu_online_count 192 jne 1b 193smp_init_done: 194 ret 195 196cpu_online_count: .word 1 197 198.code16 199sipi_entry: 200 mov %cr0, %eax 201 or $1, %eax 202 mov %eax, %cr0 203 lgdtl gdt32_descr - sipi_entry 204 ljmpl $8, $ap_start32 205 206gdt32_descr: 207 .word gdt32_end - gdt32 - 1 208 .long gdt32 209 210sipi_end: 211