debuggers.hg

annotate xen/arch/x86/boot/x86_64.S @ 3635:ed902e5c4b49

bitkeeper revision 1.1159.212.62 (41fff40aESe4aWS82z_rLHeonXpxuQ)

More x86/64 stuff.
Signed-off-by: keir.fraser@cl.cam.ac.uk
author kaf24@scramble.cl.cam.ac.uk
date Tue Feb 01 21:26:34 2005 +0000 (2005-02-01)
parents fec8b1778268
children 9a9c5a491401 e6af5d8f8b39 fd1dd0663b09
rev   line source
kaf24@1694 1 #include <xen/config.h>
kaf24@2827 2 #include <public/xen.h>
kaf24@1694 3 #include <asm/page.h>
kaf24@1777 4 #include <asm/msr.h>
kaf24@1694 5
kaf24@1694 6 #define SECONDARY_CPU_FLAG 0xA5A5A5A5
kaf24@1694 7
kaf24@1777 8 .text
kaf24@1694 9 .code32
kaf24@1694 10
kaf24@1694 11 ENTRY(start)
kaf24@1694 12 jmp __start
kaf24@1750 13
kaf24@1750 14 .org 0x004
kaf24@1694 15 /*** MULTIBOOT HEADER ****/
kaf24@1694 16 /* Magic number indicating a Multiboot header. */
kaf24@1777 17 .long 0x1BADB002
kaf24@1777 18 /* Flags to bootloader (see Multiboot spec). */
kaf24@1777 19 .long 0x00000002
kaf24@1777 20 /* Checksum: must be the negated sum of the first two fields. */
kaf24@1777 21 .long -0x1BADB004
kaf24@1750 22
kaf24@1750 23 .org 0x010
kaf24@1830 24 .asciz "ERR: Not a 64-bit CPU!"
kaf24@1830 25 .org 0x028
kaf24@1830 26 .asciz "ERR: Not a Multiboot bootloader!"
kaf24@1694 27 bad_cpu:
kaf24@1750 28 mov $0x100010,%esi # Error message
kaf24@1830 29 jmp print_err
kaf24@1830 30 not_multiboot:
kaf24@1830 31 mov $0x100028,%esi # Error message
kaf24@1830 32 print_err:
kaf24@1708 33 mov $0xB8000,%edi # VGA framebuffer
kaf24@1708 34 1: mov (%esi),%bl
kaf24@1708 35 test %bl,%bl # Terminate on '\0' sentinel
kaf24@1708 36 2: je 2b
kaf24@1708 37 mov $0x3f8+5,%dx # UART Line Status Register
kaf24@1708 38 3: in %dx,%al
kaf24@1708 39 test $0x20,%al # Test THR Empty flag
kaf24@1708 40 je 3b
kaf24@1708 41 mov $0x3f8+0,%dx # UART Transmit Holding Register
kaf24@1708 42 mov %bl,%al
kaf24@1708 43 out %al,%dx # Send a character over the serial line
kaf24@1708 44 movsb # Write a character to the VGA framebuffer
kaf24@1708 45 mov $7,%al
kaf24@1708 46 stosb # Write an attribute to the VGA framebuffer
kaf24@1708 47 jmp 1b
kaf24@1694 48
kaf24@1694 49 __start:
kaf24@1750 50 cld
kaf24@1750 51 cli
kaf24@1750 52
kaf24@1694 53 /* Set up a few descriptors: on entry only CS is guaranteed good. */
kaf24@1750 54 lgdt %cs:0x1001f0
kaf24@1694 55 mov $(__HYPERVISOR_DS),%ecx
kaf24@1694 56 mov %ecx,%ds
kaf24@1694 57 mov %ecx,%es
kaf24@1694 58
kaf24@1830 59 /* Check for Multiboot bootloader */
kaf24@1830 60 cmp $(SECONDARY_CPU_FLAG),%ebx
kaf24@1830 61 je skip_multiboot_check
kaf24@1830 62 cmp $0x2BADB002,%eax
kaf24@1830 63 jne not_multiboot
kaf24@1830 64 skip_multiboot_check:
kaf24@1830 65
kaf24@1830 66 /* Save the Multiboot info structure for later use. */
kaf24@1830 67 mov %ebx,0x1001e0
kaf24@1830 68
kaf24@1708 69 /* We begin by interrogating the CPU for the presence of long mode. */
kaf24@1708 70 mov $0x80000000,%eax
kaf24@1708 71 cpuid
kaf24@1708 72 cmp $0x80000000,%eax # any function > 0x80000000?
kaf24@1708 73 jbe bad_cpu
kaf24@1708 74 mov $0x80000001,%eax
kaf24@1708 75 cpuid
kaf24@1708 76 bt $29,%edx # Long mode feature?
kaf24@1708 77 jnc bad_cpu
kaf24@1708 78
kaf24@1694 79 /* Set up FPU. */
kaf24@1694 80 fninit
kaf24@1694 81
kaf24@1750 82 /* Enable PAE in CR4. */
kaf24@1750 83 mov $0x20,%ecx # X86_CR4_PAE
kaf24@1694 84 mov %ecx,%cr4
kaf24@1750 85
kaf24@1777 86 /* Load pagetable base register. */
kaf24@1750 87 mov $0x101000,%eax /* idle_pg_table */
kaf24@1694 88 mov %eax,%cr3
kaf24@1777 89
kaf24@1777 90 /* Set up EFER (Extended Feature Enable Register). */
kaf24@1777 91 movl $MSR_EFER, %ecx
kaf24@1777 92 rdmsr
kaf24@1777 93 /* Long Mode, SYSCALL/SYSRET, No-Execute */
kaf24@1777 94 movl $(EFER_LME|EFER_SCE|EFER_NX),%eax
kaf24@1777 95 wrmsr
kaf24@1777 96
kaf24@1694 97 mov $0x80050033,%eax /* hi-to-lo: PG,AM,WP,NE,ET,MP,PE */
kaf24@1694 98 mov %eax,%cr0
kaf24@1694 99 jmp 1f
kaf24@1750 100
kaf24@1777 101 1: /* Now in compatibility mode. Long-jump into 64-bit mode. */
kaf24@1777 102 ljmp $(__HYPERVISOR_CS64),$0x100100
kaf24@1750 103
kaf24@1777 104 .code64
kaf24@1777 105 .org 0x0100
kaf24@1777 106
kaf24@1750 107 /* Install relocated selectors (FS/GS unused). */
kaf24@1750 108 lgdt gdt_descr(%rip)
kaf24@1750 109
kaf24@1750 110 /* Enable full CR4 features. */
kaf24@1750 111 mov mmu_cr4_features(%rip),%rcx
kaf24@1708 112 mov %rcx,%cr4
kaf24@1694 113
kaf24@1750 114 mov stack_start(%rip),%rsp
kaf24@1750 115
kaf24@1750 116 /* Reset EFLAGS (subsumes CLI and CLD). */
kaf24@1777 117 pushq $0
kaf24@1777 118 popf
kaf24@1750 119
kaf24@1777 120 /* Jump to high mappings. */
kaf24@1777 121 mov high_start(%rip),%rax
kaf24@1777 122 push %rax
kaf24@1777 123 ret
kaf24@1777 124 __high_start:
kaf24@1777 125
kaf24@1750 126 lidt idt_descr(%rip)
kaf24@1694 127
kaf24@1694 128 cmp $(SECONDARY_CPU_FLAG),%ebx
kaf24@1694 129 je start_secondary
kaf24@1694 130
kaf24@1750 131 /* Initialize BSS (no nasty surprises!) */
kaf24@1750 132 lea __bss_start(%rip),%rdi
kaf24@1750 133 lea _end(%rip),%rcx
kaf24@1750 134 sub %rdi,%rcx
kaf24@1750 135 xor %rax,%rax
kaf24@1750 136 rep stosb
kaf24@1750 137
kaf24@1750 138 /* Initialise IDT with simple error defaults. */
kaf24@1750 139 lea ignore_int(%rip),%rdx
kaf24@1750 140 mov $(__HYPERVISOR_CS64 << 16),%eax
kaf24@1750 141 mov %dx,%ax /* selector = 0x0010 = cs */
kaf24@1750 142 mov $0x8E00,%dx /* interrupt gate - dpl=0, present */
kaf24@1750 143 lea idt_table(%rip),%rdi
kaf24@1750 144 mov $256,%rcx
kaf24@1750 145 1: mov %eax,(%rdi)
kaf24@1750 146 mov %edx,4(%rdi)
kaf24@1750 147 add $8,%rdi
kaf24@1750 148 loop 1b
kaf24@1750 149
kaf24@1830 150 /* Pass off the Multiboot info structure to C land. */
kaf24@1830 151 mov 0x1001e0,%edi
kaf24@1830 152 lea start(%rip),%rax
kaf24@1830 153 sub $0x100000,%rax
kaf24@1830 154 add %rax,%rdi
kaf24@3613 155 call __start_xen
kaf24@3613 156 ud2 /* Force a panic (invalid opcode). */
kaf24@1694 157
kaf24@1694 158 /* This is the default interrupt handler. */
kaf24@1694 159 int_msg:
kaf24@1694 160 .asciz "Unknown interrupt\n"
kaf24@1694 161 ignore_int:
kaf24@1694 162 cld
kaf24@1830 163 lea int_msg(%rip),%rdi
kaf24@1694 164 call SYMBOL_NAME(printf)
kaf24@1694 165 1: jmp 1b
kaf24@1694 166
kaf24@1708 167 .code32
kaf24@1777 168
kaf24@1777 169 .org 0x1e0
kaf24@1777 170
kaf24@1694 171 /*** DESCRIPTOR TABLES ***/
kaf24@1694 172
kaf24@1694 173 .globl SYMBOL_NAME(idt)
kaf24@1694 174 .globl SYMBOL_NAME(gdt)
kaf24@1694 175
kaf24@1750 176 .org 0x1f0
kaf24@1694 177 .word (LAST_RESERVED_GDT_ENTRY*8)+7
kaf24@1750 178 .long 0x100200 # gdt_table
kaf24@1694 179
kaf24@1750 180 .org 0x200
kaf24@1694 181 ENTRY(gdt_table)
kaf24@1694 182 .fill FIRST_RESERVED_GDT_ENTRY,8,0
kaf24@1694 183 .quad 0x0000000000000000 /* unused */
kaf24@1694 184 .quad 0x00cf9a000000ffff /* 0x0808 ring 0 code, compatability */
kaf24@1694 185 .quad 0x00af9a000000ffff /* 0x0810 ring 0 code, 64-bit mode */
kaf24@1694 186 .quad 0x00cf92000000ffff /* 0x0818 ring 0 data */
kaf24@1694 187 .quad 0x00cffa000000ffff /* 0x0823 ring 3 code, compatibility */
kaf24@1694 188 .quad 0x00affa000000ffff /* 0x082b ring 3 code, 64-bit mode */
kaf24@1694 189 .quad 0x00cff2000000ffff /* 0x0833 ring 3 data */
kaf24@1750 190 .quad 0x0000000000000000 /* unused */
kaf24@1750 191 .fill 2*NR_CPUS,8,0 /* space for TSS and LDT per CPU */
kaf24@1750 192
kaf24@1750 193 .word 0
kaf24@1750 194 gdt_descr:
kaf24@1777 195 .word (LAST_RESERVED_GDT_ENTRY*8)+7
kaf24@1750 196 SYMBOL_NAME(gdt):
kaf24@1750 197 .quad SYMBOL_NAME(gdt_table)
kaf24@1694 198
kaf24@1750 199 .word 0
kaf24@1750 200 idt_descr:
kaf24@1777 201 .word 256*8-1
kaf24@1750 202 SYMBOL_NAME(idt):
kaf24@1777 203 .quad SYMBOL_NAME(idt_table)
kaf24@1750 204
kaf24@1750 205 ENTRY(stack_start)
kaf24@1777 206 .quad SYMBOL_NAME(cpu0_stack) + 8100
kaf24@1750 207
kaf24@1750 208 high_start:
kaf24@1750 209 .quad __high_start
kaf24@1750 210
kaf24@1777 211 /* Initial PML4 -- level-4 page table */
kaf24@1694 212 .org 0x1000
kaf24@1750 213 ENTRY(idle_pg_table)
kaf24@1750 214 ENTRY(idle_pg_table_4)
kaf24@1750 215 .quad 0x0000000000102007 # PML4[0]
kaf24@1750 216 .fill 261,8,0
kaf24@1750 217 .quad 0x0000000000102007 # PML4[262]
kaf24@1777 218
kaf24@1777 219 /* Initial PDP -- level-3 page table */
kaf24@1694 220 .org 0x2000
kaf24@1750 221 ENTRY(idle_pg_table_l3)
kaf24@1750 222 .quad 0x0000000000103007
kaf24@1777 223
kaf24@1777 224 /* Initial PDE -- level-2 page table. */
kaf24@1750 225 .org 0x3000
kaf24@1750 226 ENTRY(idle_pg_table_l2)
kaf24@1777 227 .macro identmap from=0, count=512
kaf24@1777 228 .if \count-1
kaf24@1777 229 identmap "(\from+0)","(\count/2)"
kaf24@1777 230 identmap "(\from+(0x200000*(\count/2)))","(\count/2)"
kaf24@1777 231 .else
kaf24@1777 232 .quad 0x00000000000001e3 + \from
kaf24@1777 233 .endif
kaf24@1777 234 .endm
kaf24@1777 235 identmap /* Too orangey for crows :-) */
kaf24@1777 236
kaf24@1750 237 .org 0x4000
kaf24@1694 238 ENTRY(cpu0_stack) # Initial stack is 8kB
kaf24@1777 239
kaf24@1750 240 .org 0x6000
kaf24@1694 241 ENTRY(stext)
kaf24@1694 242 ENTRY(_stext)
kaf24@1750 243
kaf24@3632 244 .globl ret_from_intr, copy_to_user, set_intr_gate, die
kaf24@1750 245 ret_from_intr:
kaf24@1750 246 copy_to_user:
kaf24@1750 247 set_intr_gate:
kaf24@1750 248 die:
kaf24@3314 249 .globl copy_from_user, show_registers, do_iopl
kaf24@1750 250 copy_from_user:
kaf24@1750 251 show_registers:
kaf24@1750 252 do_iopl:
kaf24@3613 253 .globl idt_table, copy_user_generic, idt_tables, new_thread
kaf24@1750 254 idt_table:
kaf24@1750 255 copy_user_generic:
kaf24@1750 256 idt_tables:
kaf24@1750 257 new_thread:
kaf24@3314 258 .globl switch_to, __get_user_1, __get_user_4, __get_user_8, trap_init
kaf24@1750 259 switch_to:
kaf24@1750 260 __get_user_1:
kaf24@3314 261 __get_user_4:
kaf24@1750 262 __get_user_8:
kaf24@3314 263 trap_init:
kaf24@3314 264 .globl set_debugreg
kaf24@1750 265 set_debugreg:
kaf24@1750 266