openblt

a hobby OS from the late 90s
git clone http://frotz.net/git/openblt.git
Log | Files | Refs | LICENSE

trampoline.S (2327B)


      1 /* $Id: //depot/blt/kernel/trampoline.S#2 $
      2 **
      3 ** Copyright 1998 Sidney Cammeresi.  All rights reserved.
      4 ** Distributed under the terms of the OpenBLT License.
      5 */
      6 
      7 /*
      8  * This is the initial bootstrap code for the application processors.  When
      9  * we get here, we are running on the AP in 16-bit real mode with a stack
     10  * allocated at 0x1000 * my_cpu_num by the kernel which we are not set up
     11  * to use yet.  Our text is at the bottom of this stack.  We have to be
     12  * careful until things are fixed up.
     13  *
     14  * Basically, we just set protected mode with a temporary GDT, and call
     15  * C code.  The IDT and paging are set up later since we can't reference
     16  * any global variable here declared outside this file.
     17  *
     18  * Memory map at this stage is
     19  *
     20  *     0x9000  location of our stack
     21  *     0x9004  null descriptor
     22  *     0x9008
     23  *     0x900c  kernel text descriptor
     24  *     0x9010
     25  *     0x9014  kernel data descriptor
     26  *     0x9018
     27  *     0x901c  gdt limit << 16
     28  *     0x9020  gdt base
     29  *     0x9024  address of page directory
     30  */
     31 
     32 .globl trampoline
     33 .globl trampoline_end
     34 .globl flush
     35 
     36 .code16
     37 trampoline:
     38 		cli                      # paranoia
     39 		xor %ax, %ax
     40 		mov %ax, %ds
     41 		mov %ax, %ss
     42 
     43 		movl $0x9000, %eax       # find the location of our stack
     44 		mov (%eax), %ebx
     45 
     46 		xor %eax, %eax
     47 		mov %ax, %ss
     48 		add $0x1000, %ebx
     49 		mov %bx, %sp
     50 
     51 		movl $0x18, %eax         # i[0] = limit << 16; (limit is 24 dec.)
     52 		movl $0x10, %ecx
     53 		shl %cl, %eax
     54 		mov $0x901c, %ebx
     55 		mov %eax, (%ebx)
     56 		mov $0x9004, %eax        # i[1] = base; (base = 0x9004)
     57 		mov %eax, 4(%ebx)
     58 		mov $0x901e, %eax
     59 		lgdt (%eax)
     60 
     61 		movl $0x9024, %eax
     62 		mov (%eax), %eax
     63 		mov %eax, %cr3
     64 
     65 		movl $0x80000001, %eax   # turn on paging and protected mode
     66 		mov %eax, %cr0
     67 
     68 		/*
     69 		 * Do a long jump to the kernel text segment to serialise the processor.
     70 		 * A jump to flush won't work since we are being linked to run at a
     71 		 * different address, so we calculate the offset in the segment ourselves.
     72 		 */
     73 		ljmp $0x8, $(0x1000 + flush - trampoline)
     74 
     75 .code32
     76 flush:
     77 		mov $0x10, %ax
     78 		mov %ax, %ds
     79 		mov %ax, %es
     80 		mov %ax, %fs
     81 		mov %ax, %gs
     82 		mov %ax, %ss
     83 
     84 		mov $0x66, %ax
     85 		mov $0x1000, %dx
     86 		mov %eax, (%edx)
     87 		cld                      # supposedly good for gcc > 2
     88 		movl $0x80000074, %eax   # jmp _start does not work for some reason
     89 		jmp *%eax
     90 
     91 trampoline_end:
     92