Changes in kernel/arch/amd64/src/boot/boot.S [da52547:64f6ef04] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/arch/amd64/src/boot/boot.S
rda52547 r64f6ef04 1 /* 2 *Copyright (c) 2005 Ondrej Palkovsky3 *Copyright (c) 2006 Martin Decky4 *Copyright (c) 2008 Jakub Jermar5 *All rights reserved.6 * 7 *Redistribution and use in source and binary forms, with or without8 *modification, are permitted provided that the following conditions9 *are met:10 * 11 *- Redistributions of source code must retain the above copyright12 *notice, this list of conditions and the following disclaimer.13 *- Redistributions in binary form must reproduce the above copyright14 *notice, this list of conditions and the following disclaimer in the15 *documentation and/or other materials provided with the distribution.16 *- The name of the author may not be used to endorse or promote products17 *derived from this software without specific prior written permission.18 * 19 *THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR20 *IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES21 *OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.22 *IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,23 *INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT24 *NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,25 *DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY26 *THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT27 *(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF28 *THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.29 */ 1 # 2 # Copyright (c) 2005 Ondrej Palkovsky 3 # Copyright (c) 2006 Martin Decky 4 # Copyright (c) 2008 Jakub Jermar 5 # All rights reserved. 6 # 7 # Redistribution and use in source and binary forms, with or without 8 # modification, are permitted provided that the following conditions 9 # are met: 10 # 11 # - Redistributions of source code must retain the above copyright 12 # notice, this list of conditions and the following disclaimer. 13 # - Redistributions in binary form must reproduce the above copyright 14 # notice, this list of conditions and the following disclaimer in the 15 # documentation and/or other materials provided with the distribution. 16 # - The name of the author may not be used to endorse or promote products 17 # derived from this software without specific prior written permission. 18 # 19 # THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 20 # IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 21 # OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 22 # IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 23 # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 24 # NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 # THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 # 30 30 31 31 #include <arch/boot/boot.h> … … 37 37 #include <arch/cpuid.h> 38 38 39 #define START_STACK 39 #define START_STACK (BOOT_OFFSET - BOOT_STACK_SIZE) 40 40 41 41 .section K_TEXT_START, "ax" 42 42 43 43 .code32 44 45 .macro pm_error msg46 movl \msg, %esi47 jmp pm_error_halt48 .endm49 50 .macro pm_status msg51 #ifdef CONFIG_EGA52 pushl %esi53 movl \msg, %esi54 call pm_early_puts55 popl %esi56 #endif57 .endm58 59 .macro pm2_status msg60 #ifndef CONFIG_FB61 pm_status \msg62 #endif63 .endm64 65 44 .align 4 66 45 .global multiboot_image_start … … 68 47 .long MULTIBOOT_HEADER_MAGIC 69 48 .long MULTIBOOT_HEADER_FLAGS 70 .long -(MULTIBOOT_HEADER_MAGIC + MULTIBOOT_HEADER_FLAGS) /* checksum */49 .long -(MULTIBOOT_HEADER_MAGIC + MULTIBOOT_HEADER_FLAGS) # checksum 71 50 .long multiboot_header 72 51 .long unmapped_ktext_start … … 77 56 multiboot_image_start: 78 57 cld 79 80 /* Initialize stack pointer */ 81 movl $START_STACK, %esp 82 83 /* Initialize Global Descriptor Table register */ 84 lgdtl bootstrap_gdtr 85 86 /* Kernel data + stack */ 58 movl $START_STACK, %esp # initialize stack pointer 59 lgdtl bootstrap_gdtr # initialize Global Descriptor Table register 60 87 61 movw $gdtselector(KDATA_DES), %cx 88 62 movw %cx, %es 89 movw %cx, %ds 63 movw %cx, %ds # kernel data + stack 90 64 movw %cx, %ss 91 65 92 /* 93 * Simics seems to remove hidden part of GS on entering user mode 94 * when _visible_ part of GS does not point to user-mode segment. 95 */ 66 # 67 # Simics seems to remove hidden part of GS on entering user mode 68 # when _visible_ part of GS does not point to user-mode segment. 69 # 70 96 71 movw $gdtselector(UDATA_DES), %cx 97 72 movw %cx, %fs … … 101 76 multiboot_meeting_point: 102 77 103 /* Save GRUB arguments */ 104 movl %eax, grub_eax 78 movl %eax, grub_eax # save parameters from GRUB 105 79 movl %ebx, grub_ebx 106 80 107 pm_status $status_prot 81 # 82 # Protected 32-bit. We want to reuse the code-seg descriptor, 83 # the Default operand size must not be 1 when entering long mode. 84 # 108 85 109 86 movl $(INTEL_CPUID_EXTENDED), %eax … … 112 89 ja extended_cpuid_supported 113 90 114 pm_error $err_extended_cpuid 91 movl $extended_cpuid_msg, %esi 92 jmp error_halt 115 93 116 94 extended_cpuid_supported: … … 121 99 jc long_mode_supported 122 100 123 pm_error $err_long_mode 101 movl $long_mode_msg, %esi 102 jmp error_halt 124 103 125 104 long_mode_supported: … … 128 107 jc noexecute_supported 129 108 130 pm_error $err_noexecute 109 movl $noexecute_msg, %esi 110 jmp error_halt 131 111 132 112 noexecute_supported: … … 137 117 jc fx_supported 138 118 139 pm_error $err_fx 119 movl $fx_msg, %esi 120 jmp error_halt 140 121 141 122 fx_supported: … … 144 125 jc sse2_supported 145 126 146 pm_error $err_sse2 127 movl $sse2_msg, %esi 128 jmp error_halt 147 129 148 130 sse2_supported: 149 131 150 132 #include "vesa_prot.inc" 151 152 /* 153 * Protected 32-bit. We want to reuse the code-seg descriptor, 154 * the Default operand size must not be 1 when entering long mode. 155 */ 156 157 pm2_status $status_prot2 158 159 /* 160 * Enable 64-bit page translation entries - CR4.PAE = 1. 161 * Paging is not enabled until after long mode is enabled. 162 */ 133 134 # 135 # Enable 64-bit page translation entries - CR4.PAE = 1. 136 # Paging is not enabled until after long mode is enabled. 137 # 163 138 164 139 movl %cr4, %eax … … 166 141 movl %eax, %cr4 167 142 168 /* Set up paging tables */ 143 # set up paging tables 144 169 145 leal ptl_0, %eax 170 146 movl %eax, %cr3 171 147 172 /* Enable long mode */ 173 movl $EFER_MSR_NUM, %ecx 174 rdmsr /* read EFER */ 175 btsl $AMD_LME_FLAG, %eax /* set LME = 1 */ 176 wrmsr 177 178 /* Enable paging to activate long mode (set CR0.PG = 1) */ 148 # enable long mode 149 150 movl $EFER_MSR_NUM, %ecx # EFER MSR number 151 rdmsr # read EFER 152 btsl $AMD_LME_FLAG, %eax # set LME = 1 153 wrmsr # write EFER 154 155 # enable paging to activate long mode (set CR0.PG = 1) 156 179 157 movl %cr0, %eax 180 158 btsl $31, %eax 181 159 movl %eax, %cr0 182 160 183 /* At this point we are in compatibility mode */ 161 # at this point we are in compatibility mode 162 184 163 jmpl $gdtselector(KTEXT_DES), $start64 185 164 186 /** Print string to EGA display (in light red) and halt. 187 * 188 * Should be executed from 32 bit protected mode with paging 189 * turned off. Stack is not required. This routine is used even 190 * if CONFIG_EGA is not enabled. Since we are going to halt the 191 * CPU anyway, it is always better to at least try to print 192 * some hints. 193 * 194 * @param %esi Pointer to the NULL-terminated string 195 * to be print. 196 * 197 */ 198 pm_error_halt: 199 movl $0xb8000, %edi /* base of EGA text mode memory */ 165 .code64 166 start64: 167 movq $(PA2KA(START_STACK)), %rsp 168 169 # call arch_pre_main(grub_eax, grub_ebx) 170 xorq %rdi, %rdi 171 movl grub_eax, %edi 172 xorq %rsi, %rsi 173 movl grub_ebx, %esi 174 175 movabsq $arch_pre_main, %rax 176 callq *%rax 177 178 # create the first stack frame 179 pushq $0 180 movq %rsp, %rbp 181 182 movabsq $main_bsp, %rax 183 call *%rax 184 185 # not reached 186 187 cli 188 hlt0: 189 hlt 190 jmp hlt0 191 192 # Print string from %esi to EGA display (in red) and halt 193 error_halt: 194 movl $0xb8000, %edi # base of EGA text mode memory 200 195 xorl %eax, %eax 201 196 202 /* Read bits 8 - 15 of the cursor address */ 203 movw $0x3d4, %dx 197 movw $0x3d4, %dx # read bits 8 - 15 of the cursor address 204 198 movb $0xe, %al 205 199 outb %al, %dx … … 209 203 shl $8, %ax 210 204 211 /* Read bits 0 - 7 of the cursor address */ 212 movw $0x3d4, %dx 205 movw $0x3d4, %dx # read bits 0 - 7 of the cursor address 213 206 movb $0xf, %al 214 207 outb %al, %dx … … 217 210 inb %dx, %al 218 211 219 /* Sanity check for the cursor on screen */ 220 cmp $2000, %ax 221 jb err_cursor_ok 222 223 movw $1998, %ax 224 225 err_cursor_ok: 212 cmp $1920, %ax 213 jbe cursor_ok 214 215 movw $1920, %ax # sanity check for the cursor on the last line 216 217 cursor_ok: 226 218 227 219 movw %ax, %bx … … 229 221 addl %eax, %edi 230 222 231 err_ploop: 223 movw $0x0c00, %ax # black background, light red foreground 224 225 ploop: 232 226 lodsb 233 234 227 cmp $0, %al 235 je err_ploop_end 236 237 movb $0x0c, %ah /* black background, light red foreground */ 228 je ploop_end 238 229 stosw 239 240 /* Sanity check for the cursor on the last line */241 230 inc %bx 242 cmp $2000, %bx 243 jb err_ploop 244 245 /* Scroll the screen (24 rows) */ 246 movl %esi, %edx 247 movl $0xb80a0, %esi 248 movl $0xb8000, %edi 249 movl $1920, %ecx 250 rep movsw 251 252 /* Clear the 24th row */ 253 xorl %eax, %eax 254 movl $80, %ecx 255 rep stosw 256 257 /* Go to row 24 */ 258 movl %edx, %esi 259 movl $0xb8f00, %edi 260 movw $1920, %bx 261 262 jmp err_ploop 263 err_ploop_end: 264 265 /* Write bits 8 - 15 of the cursor address */ 266 movw $0x3d4, %dx 231 jmp ploop 232 ploop_end: 233 234 movw $0x3d4, %dx # write bits 8 - 15 of the cursor address 267 235 movb $0xe, %al 268 236 outb %al, %dx … … 272 240 outb %al, %dx 273 241 274 /* Write bits 0 - 7 of the cursor address */ 275 movw $0x3d4, %dx 242 movw $0x3d4, %dx # write bits 0 - 7 of the cursor address 276 243 movb $0xf, %al 277 244 outb %al, %dx … … 286 253 jmp hlt1 287 254 288 /** Print string to EGA display (in light green).289 *290 * Should be called from 32 bit protected mode with paging291 * turned off. A stack space of at least 24 bytes is required,292 * but the function does not establish a stack frame.293 *294 * Macros such as pm_status and pm2_status take care that295 * this function is used only when CONFIG_EGA is enabled296 * and CONFIG_FB is disabled.297 *298 * @param %esi Pointer to the NULL-terminated string299 * to be print.300 *301 */302 pm_early_puts:303 pushl %eax304 pushl %ebx305 pushl %ecx306 pushl %edx307 pushl %edi308 309 movl $0xb8000, %edi /* base of EGA text mode memory */310 xorl %eax, %eax311 312 /* Read bits 8 - 15 of the cursor address */313 movw $0x3d4, %dx314 movb $0xe, %al315 outb %al, %dx316 317 movw $0x3d5, %dx318 inb %dx, %al319 shl $8, %ax320 321 /* Read bits 0 - 7 of the cursor address */322 movw $0x3d4, %dx323 movb $0xf, %al324 outb %al, %dx325 326 movw $0x3d5, %dx327 inb %dx, %al328 329 /* Sanity check for the cursor on screen */330 cmp $2000, %ax331 jb pm_puts_cursor_ok332 333 movw $1998, %ax334 335 pm_puts_cursor_ok:336 337 movw %ax, %bx338 shl $1, %eax339 addl %eax, %edi340 341 pm_puts_ploop:342 lodsb343 344 cmp $0, %al345 je pm_puts_ploop_end346 347 movb $0x0a, %ah /* black background, light green foreground */348 stosw349 350 /* Sanity check for the cursor on the last line */351 inc %bx352 cmp $2000, %bx353 jb pm_puts_ploop354 355 /* Scroll the screen (24 rows) */356 movl %esi, %edx357 movl $0xb80a0, %esi358 movl $0xb8000, %edi359 movl $1920, %ecx360 rep movsw361 362 /* Clear the 24th row */363 xorl %eax, %eax364 movl $80, %ecx365 rep stosw366 367 /* Go to row 24 */368 movl %edx, %esi369 movl $0xb8f00, %edi370 movw $1920, %bx371 372 jmp pm_puts_ploop373 pm_puts_ploop_end:374 375 /* Write bits 8 - 15 of the cursor address */376 movw $0x3d4, %dx377 movb $0xe, %al378 outb %al, %dx379 380 movw $0x3d5, %dx381 movb %bh, %al382 outb %al, %dx383 384 /* Write bits 0 - 7 of the cursor address */385 movw $0x3d4, %dx386 movb $0xf, %al387 outb %al, %dx388 389 movw $0x3d5, %dx390 movb %bl, %al391 outb %al, %dx392 393 popl %edi394 popl %edx395 popl %ecx396 popl %ebx397 popl %eax398 399 ret400 401 .code64402 403 .macro long_status msg404 pushq %rdi405 movq \msg, %rdi406 call early_puts407 popq %rdi408 .endm409 410 start64:411 412 /*413 * Long mode.414 */415 416 movq $(PA2KA(START_STACK)), %rsp417 418 /* Create the first stack frame */419 pushq $0420 movq %rsp, %rbp421 422 long_status $status_long423 424 /* Call arch_pre_main(grub_eax, grub_ebx) */425 xorq %rdi, %rdi426 movl grub_eax, %edi427 xorq %rsi, %rsi428 movl grub_ebx, %esi429 430 movabsq $arch_pre_main, %rax431 callq *%rax432 433 long_status $status_main434 435 /* Call main_bsp() */436 movabsq $main_bsp, %rax437 call *%rax438 439 /* Not reached */440 cli441 hlt0:442 hlt443 jmp hlt0444 445 /** Print string to EGA display.446 *447 * Should be called from long mode (with paging enabled448 * and stack established). This function is ABI compliant449 * (without red-zone).450 *451 * If CONFIG_EGA is undefined or CONFIG_FB is defined452 * then this function does nothing.453 *454 * @param %rdi Pointer to the NULL-terminated string455 * to be printed.456 *457 */458 early_puts:459 460 #if ((defined(CONFIG_EGA)) && (!defined(CONFIG_FB)))461 462 /* Prologue, save preserved registers */463 pushq %rbp464 movq %rsp, %rbp465 pushq %rbx466 467 movq %rdi, %rsi468 movq $(PA2KA(0xb8000)), %rdi /* base of EGA text mode memory */469 xorq %rax, %rax470 471 /* Read bits 8 - 15 of the cursor address */472 movw $0x3d4, %dx473 movb $0xe, %al474 outb %al, %dx475 476 movw $0x3d5, %dx477 inb %dx, %al478 shl $8, %ax479 480 /* Read bits 0 - 7 of the cursor address */481 movw $0x3d4, %dx482 movb $0xf, %al483 outb %al, %dx484 485 movw $0x3d5, %dx486 inb %dx, %al487 488 /* Sanity check for the cursor on screen */489 cmp $2000, %ax490 jb early_puts_cursor_ok491 492 movw $1998, %ax493 494 early_puts_cursor_ok:495 496 movw %ax, %bx497 shl $1, %rax498 addq %rax, %rdi499 500 early_puts_ploop:501 lodsb502 503 cmp $0, %al504 je early_puts_ploop_end505 506 movb $0x0e, %ah /* black background, yellow foreground */507 stosw508 509 /* Sanity check for the cursor on the last line */510 inc %bx511 cmp $2000, %bx512 jb early_puts_ploop513 514 /* Scroll the screen (24 rows) */515 movq %rsi, %rdx516 movq $(PA2KA(0xb80a0)), %rsi517 movq $(PA2KA(0xb8000)), %rdi518 movq $1920, %rcx519 rep movsw520 521 /* Clear the 24th row */522 xorq %rax, %rax523 movq $80, %rcx524 rep stosw525 526 /* Go to row 24 */527 movq %rdx, %rsi528 movq $(PA2KA(0xb8f00)), %rdi529 movw $1920, %bx530 531 jmp early_puts_ploop532 early_puts_ploop_end:533 534 /* Write bits 8 - 15 of the cursor address */535 movw $0x3d4, %dx536 movb $0xe, %al537 outb %al, %dx538 539 movw $0x3d5, %dx540 movb %bh, %al541 outb %al, %dx542 543 /* Write bits 0 - 7 of the cursor address */544 movw $0x3d4, %dx545 movb $0xf, %al546 outb %al, %dx547 548 movw $0x3d5, %dx549 movb %bl, %al550 outb %al, %dx551 552 /* Epilogue, restore preserved registers */553 popq %rbx554 leave555 556 #endif557 558 ret559 560 255 #include "vesa_real.inc" 561 256 562 257 .section K_INI_PTLS, "aw", @progbits 563 258 564 /** Generate initial page table contents. 565 * 566 * @param cnt Number of entries to generate. Must be multiple of 8. 567 * @param g Number of GB that will be added to the mapping. 568 * 569 */ 259 # 260 # Macro for generating initial page table contents. 261 # @param cnt Number of entries to generate. Must be multiple of 8. 262 # @param g Number of GB that will be added to the mapping. 263 # 570 264 .macro ptl2gen cnt g 571 265 .if \cnt … … 582 276 .endm 583 277 584 /* Page table for pages in the 1st gigabyte. */ 278 # Page table for pages in the 1st gigabyte. 585 279 .align 4096 586 280 ptl_2_0g: 587 281 ptl2gen 512 0 588 282 589 /* Page table for pages in the 2nd gigabyte. */ 283 # Page table for pages in the 2nd gigabyte. 590 284 .align 4096 591 285 ptl_2_1g: 592 286 ptl2gen 512 1 593 287 594 /* Page table for pages in the 3rd gigabyte. */ 288 # Page table for pages in the 3rd gigabyte. 595 289 .align 4096 596 290 ptl_2_2g: 597 291 ptl2gen 512 2 598 292 599 /* Page table for pages in the 4th gigabyte. */ 293 # Page table for pages in the 4th gigabyte. 600 294 .align 4096 601 295 ptl_2_3g: 602 296 ptl2gen 512 3 603 297 604 /* Page table for pages in the 5th gigabyte. */ 298 # Page table for pages in the 5th gigabyte. 605 299 .align 4096 606 300 ptl_2_4g: 607 301 ptl2gen 512 3 608 302 609 /* Page table for pages in the 6th gigabyte. */ 303 # Page table for pages in the 6th gigabyte. 610 304 .align 4096 611 305 ptl_2_5g: 612 306 ptl2gen 512 3 613 307 614 /* Page table for pages in the 7th gigabyte. */ 308 # Page table for pages in the 7th gigabyte. 615 309 .align 4096 616 310 ptl_2_6g: 617 311 ptl2gen 512 3 618 312 619 /* Page table for pages in the 8th gigabyte. */ 313 # Page table for pages in the 8th gigabyte. 620 314 .align 4096 621 315 ptl_2_7g: … … 624 318 .align 4096 625 319 ptl_1: 626 /* Identity mapping for [0; 8G) */320 # Identity mapping for [0; 8G) 627 321 .quad ptl_2_0g + (PTL_WRITABLE | PTL_PRESENT) 628 322 .quad ptl_2_1g + (PTL_WRITABLE | PTL_PRESENT) … … 656 350 .long 0 657 351 658 e rr_extended_cpuid:352 extended_cpuid_msg: 659 353 .asciz "Error: Extended CPUID not supported -- CPU is not 64-bit. System halted." 660 err_long_mode:354 long_mode_msg: 661 355 .asciz "Error: 64-bit long mode not supported. System halted." 662 err_noexecute:356 noexecute_msg: 663 357 .asciz "Error: No-execute pages not supported. System halted." 664 err_fx:358 fx_msg: 665 359 .asciz "Error: FXSAVE/FXRESTORE instructions not supported. System halted." 666 err_sse2:360 sse2_msg: 667 361 .asciz "Error: SSE2 instructions not supported. System halted." 668 669 status_prot:670 .asciz "[prot] "671 status_vesa_copy:672 .asciz "[vesa_copy] "673 status_grub_cmdline:674 .asciz "[grub_cmdline] "675 status_vesa_real:676 .asciz "[vesa_real] "677 status_prot2:678 .asciz "[prot2] "679 status_long:680 .asciz "[long] "681 status_main:682 .asciz "[main] "
Note:
See TracChangeset
for help on using the changeset viewer.