debuggers.hg

annotate xen/arch/x86/setup.c @ 3658:0ef6e8e6e85d

bitkeeper revision 1.1159.212.71 (4200f0afX_JumfbEHQex6TdFENULMQ)

Merge labyrinth.cl.cam.ac.uk:/auto/groups/xeno-xenod/BK/xen-unstable.bk
into labyrinth.cl.cam.ac.uk:/auto/groups/xeno/users/iap10/xeno-clone/xen-unstable.bk
author iap10@labyrinth.cl.cam.ac.uk
date Wed Feb 02 15:24:31 2005 +0000 (2005-02-02)
parents fec8b1778268 552dd1f1c64c
children 060c1ea52343
rev   line source
kaf24@1490 1
kaf24@1490 2 #include <xen/config.h>
kaf24@1490 3 #include <xen/init.h>
kaf24@1490 4 #include <xen/lib.h>
kaf24@1490 5 #include <xen/sched.h>
kaf24@1490 6 #include <xen/pci.h>
kaf24@1490 7 #include <xen/serial.h>
kaf24@1544 8 #include <xen/softirq.h>
kaf24@1490 9 #include <xen/acpi.h>
kaf24@3376 10 #include <xen/console.h>
kaf24@3376 11 #include <xen/trace.h>
kaf24@3376 12 #include <xen/multiboot.h>
kaf24@1490 13 #include <asm/bitops.h>
kaf24@1490 14 #include <asm/smp.h>
kaf24@1490 15 #include <asm/processor.h>
kaf24@1490 16 #include <asm/mpspec.h>
kaf24@1490 17 #include <asm/apic.h>
kaf24@1490 18 #include <asm/desc.h>
kaf24@1490 19 #include <asm/domain_page.h>
kaf24@1490 20 #include <asm/pdb.h>
kaf24@3376 21 #include <asm/shadow.h>
kaf24@3382 22 #include <asm/e820.h>
kaf24@3376 23
kaf24@3376 24 /* opt_dom0_mem: Kilobytes of memory allocated to domain 0. */
kaf24@3376 25 static unsigned int opt_dom0_mem = 16000;
kaf24@3376 26 integer_param("dom0_mem", opt_dom0_mem);
kaf24@3376 27
kaf24@3376 28 /*
kaf24@3376 29 * opt_xenheap_megabytes: Size of Xen heap in megabytes, excluding the
kaf24@3376 30 * pfn_info table and allocation bitmap.
kaf24@3376 31 */
kaf24@3376 32 static unsigned int opt_xenheap_megabytes = XENHEAP_DEFAULT_MB;
kaf24@3392 33 #if defined(__x86_64__)
kaf24@3376 34 integer_param("xenheap_megabytes", opt_xenheap_megabytes);
kaf24@3392 35 #endif
kaf24@1490 36
kaf24@3372 37 /* opt_noht: If true, Hyperthreading is ignored. */
kaf24@3372 38 int opt_noht = 0;
kaf24@3372 39 boolean_param("noht", opt_noht);
kaf24@3372 40
kaf24@3372 41 /* opt_noacpi: If true, ACPI tables are not parsed. */
kaf24@3372 42 static int opt_noacpi = 0;
kaf24@3372 43 boolean_param("noacpi", opt_noacpi);
kaf24@3372 44
kaf24@3372 45 /* opt_nosmp: If true, secondary processors are ignored. */
kaf24@3372 46 static int opt_nosmp = 0;
kaf24@3372 47 boolean_param("nosmp", opt_nosmp);
kaf24@3372 48
kaf24@3372 49 /* opt_ignorebiostables: If true, ACPI and MP tables are ignored. */
kaf24@3372 50 /* NB. This flag implies 'nosmp' and 'noacpi'. */
kaf24@3372 51 static int opt_ignorebiostables = 0;
kaf24@3372 52 boolean_param("ignorebiostables", opt_ignorebiostables);
kaf24@3372 53
kaf24@3372 54 /* opt_watchdog: If true, run a watchdog NMI on each processor. */
kaf24@3372 55 static int opt_watchdog = 0;
kaf24@3372 56 boolean_param("watchdog", opt_watchdog);
kaf24@3372 57
kaf24@3632 58 int early_boot = 1;
kaf24@3632 59
kaf24@3376 60 unsigned long xenheap_phys_end;
kaf24@3376 61
kaf24@2336 62 extern void arch_init_memory(void);
kaf24@1627 63 extern void init_IRQ(void);
kaf24@1627 64 extern void trap_init(void);
kaf24@1627 65 extern void time_init(void);
kaf24@1627 66 extern void ac_timer_init(void);
kaf24@1627 67 extern void initialize_keytable();
kaf24@1627 68 extern int do_timer_lists_from_pit;
kaf24@1627 69
kaf24@1490 70 char ignore_irq13; /* set if exception 16 works */
kaf24@1518 71 struct cpuinfo_x86 boot_cpu_data = { 0, 0, 0, 0, -1 };
kaf24@1490 72
kaf24@1708 73 #if defined(__x86_64__)
kaf24@1708 74 unsigned long mmu_cr4_features = X86_CR4_PSE | X86_CR4_PGE | X86_CR4_PAE;
kaf24@1708 75 #else
kaf24@1490 76 unsigned long mmu_cr4_features = X86_CR4_PSE | X86_CR4_PGE;
kaf24@1708 77 #endif
kaf24@1490 78 EXPORT_SYMBOL(mmu_cr4_features);
kaf24@1490 79
kaf24@1490 80 unsigned long wait_init_idle;
kaf24@1490 81
cl349@2957 82 struct exec_domain *idle_task[NR_CPUS] = { &idle0_exec_domain };
kaf24@1490 83
kaf24@1490 84 #ifdef CONFIG_ACPI_INTERPRETER
kaf24@1490 85 int acpi_disabled = 0;
kaf24@1490 86 #else
kaf24@1490 87 int acpi_disabled = 1;
kaf24@1490 88 #endif
kaf24@1490 89 EXPORT_SYMBOL(acpi_disabled);
kaf24@1490 90
kaf24@1490 91 int phys_proc_id[NR_CPUS];
kaf24@1490 92 int logical_proc_id[NR_CPUS];
kaf24@1490 93
kaf24@1710 94 #if defined(__i386__)
kaf24@1710 95
kaf24@1490 96 /* Standard macro to see if a specific flag is changeable */
kaf24@1490 97 static inline int flag_is_changeable_p(u32 flag)
kaf24@1490 98 {
kaf24@1490 99 u32 f1, f2;
kaf24@1490 100
kaf24@1490 101 asm("pushfl\n\t"
kaf24@1490 102 "pushfl\n\t"
kaf24@1490 103 "popl %0\n\t"
kaf24@1490 104 "movl %0,%1\n\t"
kaf24@1490 105 "xorl %2,%0\n\t"
kaf24@1490 106 "pushl %0\n\t"
kaf24@1490 107 "popfl\n\t"
kaf24@1490 108 "pushfl\n\t"
kaf24@1490 109 "popl %0\n\t"
kaf24@1490 110 "popfl\n\t"
kaf24@1490 111 : "=&r" (f1), "=&r" (f2)
kaf24@1490 112 : "ir" (flag));
kaf24@1490 113
kaf24@1490 114 return ((f1^f2) & flag) != 0;
kaf24@1490 115 }
kaf24@1490 116
kaf24@1490 117 /* Probe for the CPUID instruction */
kaf24@1490 118 static int __init have_cpuid_p(void)
kaf24@1490 119 {
kaf24@1490 120 return flag_is_changeable_p(X86_EFLAGS_ID);
kaf24@1490 121 }
kaf24@1490 122
kaf24@1710 123 #elif defined(__x86_64__)
kaf24@1710 124
kaf24@1710 125 #define have_cpuid_p() (1)
kaf24@1710 126
kaf24@1710 127 #endif
kaf24@1710 128
kaf24@1490 129 void __init get_cpu_vendor(struct cpuinfo_x86 *c)
kaf24@1490 130 {
kaf24@1490 131 char *v = c->x86_vendor_id;
kaf24@1490 132
kaf24@1490 133 if (!strcmp(v, "GenuineIntel"))
kaf24@1490 134 c->x86_vendor = X86_VENDOR_INTEL;
kaf24@1490 135 else if (!strcmp(v, "AuthenticAMD"))
kaf24@1490 136 c->x86_vendor = X86_VENDOR_AMD;
kaf24@1490 137 else if (!strcmp(v, "CyrixInstead"))
kaf24@1490 138 c->x86_vendor = X86_VENDOR_CYRIX;
kaf24@1490 139 else if (!strcmp(v, "UMC UMC UMC "))
kaf24@1490 140 c->x86_vendor = X86_VENDOR_UMC;
kaf24@1490 141 else if (!strcmp(v, "CentaurHauls"))
kaf24@1490 142 c->x86_vendor = X86_VENDOR_CENTAUR;
kaf24@1490 143 else if (!strcmp(v, "NexGenDriven"))
kaf24@1490 144 c->x86_vendor = X86_VENDOR_NEXGEN;
kaf24@1490 145 else if (!strcmp(v, "RiseRiseRise"))
kaf24@1490 146 c->x86_vendor = X86_VENDOR_RISE;
kaf24@1490 147 else if (!strcmp(v, "GenuineTMx86") ||
kaf24@1490 148 !strcmp(v, "TransmetaCPU"))
kaf24@1490 149 c->x86_vendor = X86_VENDOR_TRANSMETA;
kaf24@1490 150 else
kaf24@1490 151 c->x86_vendor = X86_VENDOR_UNKNOWN;
kaf24@1490 152 }
kaf24@1490 153
kaf24@1490 154 static void __init init_intel(struct cpuinfo_x86 *c)
kaf24@1490 155 {
kaf24@1490 156 /* SEP CPUID bug: Pentium Pro reports SEP but doesn't have it */
kaf24@1490 157 if ( c->x86 == 6 && c->x86_model < 3 && c->x86_mask < 3 )
kaf24@1490 158 clear_bit(X86_FEATURE_SEP, &c->x86_capability);
kaf24@1490 159
kaf24@1490 160 #ifdef CONFIG_SMP
kaf24@1490 161 if ( test_bit(X86_FEATURE_HT, &c->x86_capability) )
kaf24@1490 162 {
kaf24@1490 163 u32 eax, ebx, ecx, edx;
kaf24@1490 164 int initial_apic_id, siblings, cpu = smp_processor_id();
kaf24@1490 165
kaf24@1490 166 cpuid(1, &eax, &ebx, &ecx, &edx);
cl349@2741 167 ht_per_core = siblings = (ebx & 0xff0000) >> 16;
cl349@2741 168
cl349@2741 169 if ( opt_noht )
cl349@2741 170 clear_bit(X86_FEATURE_HT, &c->x86_capability[0]);
cl349@2741 171
kaf24@1490 172 if ( siblings <= 1 )
kaf24@1490 173 {
kaf24@1490 174 printk(KERN_INFO "CPU#%d: Hyper-Threading is disabled\n", cpu);
kaf24@1490 175 }
kaf24@1490 176 else if ( siblings > 2 )
kaf24@1490 177 {
kaf24@1490 178 panic("We don't support more than two logical CPUs per package!");
kaf24@1490 179 }
kaf24@1490 180 else
kaf24@1490 181 {
kaf24@1490 182 initial_apic_id = ebx >> 24 & 0xff;
kaf24@1490 183 phys_proc_id[cpu] = initial_apic_id >> 1;
kaf24@1490 184 logical_proc_id[cpu] = initial_apic_id & 1;
kaf24@1490 185 printk(KERN_INFO "CPU#%d: Physical ID: %d, Logical ID: %d\n",
kaf24@1490 186 cpu, phys_proc_id[cpu], logical_proc_id[cpu]);
kaf24@1490 187 }
kaf24@1490 188 }
kaf24@1490 189 #endif
iap10@3328 190
iap10@3328 191 #ifdef CONFIG_VMX
iap10@3328 192 start_vmx();
iap10@3328 193 #endif
iap10@3328 194
kaf24@1490 195 }
kaf24@1490 196
kaf24@1490 197 static void __init init_amd(struct cpuinfo_x86 *c)
kaf24@1490 198 {
kaf24@1490 199 /* Bit 31 in normal CPUID used for nonstandard 3DNow ID;
kaf24@1490 200 3DNow is IDd by bit 31 in extended CPUID (1*32+31) anyway */
kaf24@1490 201 clear_bit(0*32+31, &c->x86_capability);
kaf24@1490 202
kaf24@1490 203 switch(c->x86)
kaf24@1490 204 {
kaf24@1490 205 case 5:
kaf24@1490 206 panic("AMD K6 is not supported.\n");
kaf24@1490 207 case 6: /* An Athlon/Duron. We can trust the BIOS probably */
kaf24@1490 208 break;
kaf24@1490 209 }
kaf24@1490 210 }
kaf24@1490 211
kaf24@1490 212 /*
kaf24@1490 213 * This does the hard work of actually picking apart the CPU stuff...
kaf24@1490 214 */
kaf24@1490 215 void __init identify_cpu(struct cpuinfo_x86 *c)
kaf24@1490 216 {
kaf24@1490 217 int junk, i, cpu = smp_processor_id();
kaf24@1490 218 u32 xlvl, tfms;
kaf24@1490 219
kaf24@1490 220 phys_proc_id[cpu] = cpu;
kaf24@1490 221 logical_proc_id[cpu] = 0;
kaf24@1490 222
kaf24@1490 223 c->x86_vendor = X86_VENDOR_UNKNOWN;
kaf24@1490 224 c->cpuid_level = -1; /* CPUID not detected */
kaf24@1490 225 c->x86_model = c->x86_mask = 0; /* So far unknown... */
kaf24@1490 226 c->x86_vendor_id[0] = '\0'; /* Unset */
kaf24@1490 227 memset(&c->x86_capability, 0, sizeof c->x86_capability);
kaf24@1490 228
kaf24@1490 229 if ( !have_cpuid_p() )
kaf24@1490 230 panic("Ancient processors not supported\n");
kaf24@1490 231
kaf24@1490 232 /* Get vendor name */
kaf24@1490 233 cpuid(0x00000000, &c->cpuid_level,
kaf24@1490 234 (int *)&c->x86_vendor_id[0],
kaf24@1490 235 (int *)&c->x86_vendor_id[8],
kaf24@1490 236 (int *)&c->x86_vendor_id[4]);
kaf24@1490 237
kaf24@1490 238 get_cpu_vendor(c);
kaf24@1490 239
kaf24@1490 240 if ( c->cpuid_level == 0 )
kaf24@1490 241 panic("Decrepit CPUID not supported\n");
kaf24@1490 242
kaf24@1490 243 cpuid(0x00000001, &tfms, &junk, &junk,
kaf24@1490 244 &c->x86_capability[0]);
kaf24@1490 245 c->x86 = (tfms >> 8) & 15;
kaf24@1490 246 c->x86_model = (tfms >> 4) & 15;
kaf24@1490 247 c->x86_mask = tfms & 15;
kaf24@1490 248
kaf24@1490 249 /* AMD-defined flags: level 0x80000001 */
kaf24@1490 250 xlvl = cpuid_eax(0x80000000);
kaf24@1490 251 if ( (xlvl & 0xffff0000) == 0x80000000 ) {
kaf24@1490 252 if ( xlvl >= 0x80000001 )
kaf24@1490 253 c->x86_capability[1] = cpuid_edx(0x80000001);
kaf24@1490 254 }
kaf24@1490 255
kaf24@1490 256 /* Transmeta-defined flags: level 0x80860001 */
kaf24@1490 257 xlvl = cpuid_eax(0x80860000);
kaf24@1490 258 if ( (xlvl & 0xffff0000) == 0x80860000 ) {
kaf24@1490 259 if ( xlvl >= 0x80860001 )
kaf24@1490 260 c->x86_capability[2] = cpuid_edx(0x80860001);
kaf24@1490 261 }
kaf24@1490 262
kaf24@1490 263 printk("CPU%d: Before vendor init, caps: %08x %08x %08x, vendor = %d\n",
kaf24@1490 264 smp_processor_id(),
kaf24@1490 265 c->x86_capability[0],
kaf24@1490 266 c->x86_capability[1],
kaf24@1490 267 c->x86_capability[2],
kaf24@1490 268 c->x86_vendor);
kaf24@1490 269
kaf24@1490 270 switch ( c->x86_vendor ) {
kaf24@1490 271 case X86_VENDOR_INTEL:
kaf24@1490 272 init_intel(c);
kaf24@1490 273 break;
kaf24@1490 274 case X86_VENDOR_AMD:
kaf24@1490 275 init_amd(c);
kaf24@1490 276 break;
kaf24@1490 277 case X86_VENDOR_UNKNOWN: /* Connectix Virtual PC reports this */
kaf24@1490 278 break;
kaf24@1490 279 case X86_VENDOR_CENTAUR:
kaf24@1490 280 break;
kaf24@1490 281 default:
kaf24@1490 282 printk("Unknown CPU identifier (%d): continuing anyway, "
kaf24@1490 283 "but might fail.\n", c->x86_vendor);
kaf24@1490 284 }
kaf24@1490 285
kaf24@1490 286 printk("CPU caps: %08x %08x %08x %08x\n",
kaf24@1490 287 c->x86_capability[0],
kaf24@1490 288 c->x86_capability[1],
kaf24@1490 289 c->x86_capability[2],
kaf24@1490 290 c->x86_capability[3]);
kaf24@1490 291
kaf24@1490 292 /*
kaf24@1490 293 * On SMP, boot_cpu_data holds the common feature set between
kaf24@1490 294 * all CPUs; so make sure that we indicate which features are
kaf24@1490 295 * common between the CPUs. The first time this routine gets
kaf24@1490 296 * executed, c == &boot_cpu_data.
kaf24@1490 297 */
kaf24@1490 298 if ( c != &boot_cpu_data ) {
kaf24@1490 299 /* AND the already accumulated flags with these */
kaf24@1490 300 for ( i = 0 ; i < NCAPINTS ; i++ )
kaf24@1490 301 boot_cpu_data.x86_capability[i] &= c->x86_capability[i];
kaf24@1490 302 }
kaf24@1490 303 }
kaf24@1490 304
kaf24@1490 305
kaf24@1490 306 unsigned long cpu_initialized;
kaf24@1490 307 void __init cpu_init(void)
kaf24@1490 308 {
kaf24@1710 309 #if defined(__i386__) /* XXX */
kaf24@1490 310 int nr = smp_processor_id();
kaf24@1490 311 struct tss_struct * t = &init_tss[nr];
kaf24@1490 312
kaf24@1490 313 if ( test_and_set_bit(nr, &cpu_initialized) )
kaf24@1490 314 panic("CPU#%d already initialized!!!\n", nr);
kaf24@1490 315 printk("Initializing CPU#%d\n", nr);
kaf24@1490 316
kaf24@3088 317 t->bitmap = IOBMP_INVALID_OFFSET;
kaf24@1524 318 memset(t->io_bitmap, ~0, sizeof(t->io_bitmap));
kaf24@1524 319
kaf24@1490 320 /* Set up GDT and IDT. */
kaf24@1490 321 SET_GDT_ENTRIES(current, DEFAULT_GDT_ENTRIES);
kaf24@1490 322 SET_GDT_ADDRESS(current, DEFAULT_GDT_ADDRESS);
kaf24@1490 323 __asm__ __volatile__("lgdt %0": "=m" (*current->mm.gdt));
kaf24@1490 324 __asm__ __volatile__("lidt %0": "=m" (idt_descr));
kaf24@1490 325
kaf24@1490 326 /* No nested task. */
kaf24@1490 327 __asm__("pushfl ; andl $0xffffbfff,(%esp) ; popfl");
kaf24@1490 328
kaf24@1490 329 /* Ensure FPU gets initialised for each domain. */
kaf24@1490 330 stts();
kaf24@1490 331
kaf24@1490 332 /* Set up and load the per-CPU TSS and LDT. */
kaf24@1490 333 t->ss0 = __HYPERVISOR_DS;
kaf24@1490 334 t->esp0 = get_stack_top();
kaf24@1490 335 set_tss_desc(nr,t);
kaf24@1490 336 load_TR(nr);
kaf24@1490 337 __asm__ __volatile__("lldt %%ax"::"a" (0));
kaf24@1490 338
kaf24@1490 339 /* Clear all 6 debug registers. */
kaf24@1490 340 #define CD(register) __asm__("movl %0,%%db" #register ::"r"(0) );
kaf24@1490 341 CD(0); CD(1); CD(2); CD(3); /* no db4 and db5 */; CD(6); CD(7);
kaf24@1490 342 #undef CD
kaf24@1490 343
kaf24@1490 344 /* Install correct page table. */
kaf24@1490 345 write_ptbase(&current->mm);
kaf24@1490 346
kaf24@1490 347 init_idle_task();
kaf24@1710 348 #endif
kaf24@1490 349 }
kaf24@1490 350
kaf24@1490 351 static void __init do_initcalls(void)
kaf24@1490 352 {
kaf24@1490 353 initcall_t *call;
kaf24@1490 354 for ( call = &__initcall_start; call < &__initcall_end; call++ )
kaf24@1490 355 (*call)();
kaf24@1490 356 }
kaf24@1490 357
kaf24@1490 358 unsigned long pci_mem_start = 0x10000000;
kaf24@1490 359
kaf24@3376 360 static void __init start_of_day(void)
kaf24@1490 361 {
kaf24@1490 362 unsigned long low_mem_size;
kaf24@1490 363
kaf24@1490 364 #ifdef MEMORY_GUARD
kaf24@1490 365 /* Unmap the first page of CPU0's stack. */
kaf24@1490 366 extern unsigned long cpu0_stack[];
kaf24@1490 367 memguard_guard_range(cpu0_stack, PAGE_SIZE);
kaf24@1490 368 #endif
kaf24@1490 369
kaf24@1543 370 open_softirq(NEW_TLBFLUSH_CLOCK_PERIOD_SOFTIRQ, new_tlbflush_clock_period);
kaf24@1490 371
kaf24@1490 372 if ( opt_watchdog )
kaf24@1490 373 nmi_watchdog = NMI_LOCAL_APIC;
kaf24@1490 374
kaf24@3158 375 sort_exception_tables();
kaf24@3158 376
kaf24@3310 377 arch_do_createdomain(current);
kaf24@3310 378
kaf24@1490 379 /* Tell the PCI layer not to allocate too close to the RAM area.. */
kaf24@1490 380 low_mem_size = ((max_page << PAGE_SHIFT) + 0xfffff) & ~0xfffff;
kaf24@1490 381 if ( low_mem_size > pci_mem_start ) pci_mem_start = low_mem_size;
kaf24@1490 382
kaf24@1490 383 identify_cpu(&boot_cpu_data); /* get CPU type info */
kaf24@1490 384 if ( cpu_has_fxsr ) set_in_cr4(X86_CR4_OSFXSR);
kaf24@1490 385 if ( cpu_has_xmm ) set_in_cr4(X86_CR4_OSXMMEXCPT);
kaf24@1490 386 #ifdef CONFIG_SMP
kaf24@1490 387 if ( opt_ignorebiostables )
kaf24@1490 388 {
kaf24@1490 389 opt_nosmp = 1; /* No SMP without configuration */
kaf24@1490 390 opt_noacpi = 1; /* ACPI will just confuse matters also */
kaf24@1490 391 }
kaf24@1490 392 else
kaf24@1490 393 {
kaf24@1490 394 find_smp_config();
kaf24@1490 395 smp_alloc_memory(); /* trampoline which other CPUs jump at */
kaf24@1490 396 }
kaf24@1490 397 #endif
kaf24@1490 398 paging_init(); /* not much here now, but sets up fixmap */
kaf24@1490 399 if ( !opt_noacpi )
kaf24@1490 400 acpi_boot_init();
kaf24@1490 401 #ifdef CONFIG_SMP
kaf24@1490 402 if ( smp_found_config )
kaf24@1490 403 get_smp_config();
kaf24@1490 404 #endif
kaf24@1490 405 scheduler_init();
kaf24@1535 406 init_IRQ(); /* installs simple interrupt wrappers. Starts HZ clock. */
kaf24@1490 407 trap_init();
kaf24@1490 408 time_init(); /* installs software handler for HZ clock. */
kaf24@1490 409 init_apic_mappings(); /* make APICs addressable in our pagetables. */
kaf24@1490 410
kaf24@2336 411 arch_init_memory();
kaf24@2336 412
kaf24@1490 413 #ifndef CONFIG_SMP
kaf24@1490 414 APIC_init_uniprocessor();
kaf24@1490 415 #else
kaf24@1490 416 if ( opt_nosmp )
kaf24@1490 417 APIC_init_uniprocessor();
kaf24@1490 418 else
kaf24@1490 419 smp_boot_cpus();
kaf24@1490 420 /*
kaf24@1490 421 * Does loads of stuff, including kicking the local
kaf24@1490 422 * APIC, and the IO APIC after other CPUs are booted.
kaf24@1490 423 * Each IRQ is preferably handled by IO-APIC, but
kaf24@1490 424 * fall thru to 8259A if we have to (but slower).
kaf24@1490 425 */
kaf24@1490 426 #endif
kaf24@1490 427
kaf24@1490 428 __sti();
kaf24@1490 429
kaf24@1543 430 initialize_keytable(); /* call back handling for key codes */
kaf24@1490 431
kaf24@1490 432 serial_init_stage2();
kaf24@1490 433
kaf24@1490 434 #ifdef XEN_DEBUGGER
kaf24@1490 435 initialize_pdb(); /* pervasive debugger */
kaf24@1490 436 #endif
kaf24@1490 437
kaf24@1490 438 if ( !cpu_has_apic )
kaf24@1490 439 {
kaf24@1490 440 do_timer_lists_from_pit = 1;
kaf24@1490 441 if ( smp_num_cpus != 1 )
kaf24@1490 442 panic("We need local APICs on SMP machines!");
kaf24@1490 443 }
kaf24@1490 444
kaf24@1490 445 ac_timer_init(); /* init accurate timers */
kaf24@1490 446 init_xen_time(); /* initialise the time */
kaf24@1490 447 schedulers_start(); /* start scheduler for each CPU */
kaf24@1490 448
kaf24@1490 449 check_nmi_watchdog();
kaf24@1490 450
kaf24@1490 451 #ifdef CONFIG_PCI
kaf24@1490 452 pci_init();
kaf24@1490 453 #endif
kaf24@1490 454 do_initcalls();
kaf24@1490 455
kaf24@1490 456 #ifdef CONFIG_SMP
kaf24@1490 457 wait_init_idle = cpu_online_map;
kaf24@1490 458 clear_bit(smp_processor_id(), &wait_init_idle);
kaf24@1490 459 smp_threads_ready = 1;
kaf24@1490 460 smp_commence(); /* Tell other CPUs that state of the world is stable. */
kaf24@2382 461 while ( wait_init_idle != 0 )
kaf24@1490 462 {
kaf24@1490 463 cpu_relax();
kaf24@1490 464 barrier();
kaf24@1490 465 }
kaf24@1490 466 #endif
kaf24@1490 467
kaf24@1490 468 watchdog_on = 1;
kaf24@1490 469 }
kaf24@3376 470
kaf24@3376 471 void __init __start_xen(multiboot_info_t *mbi)
kaf24@3376 472 {
kaf24@3376 473 unsigned char *cmdline;
kaf24@3376 474 module_t *mod = (module_t *)__va(mbi->mods_addr);
kaf24@3376 475 void *heap_start;
kaf24@3392 476 unsigned long firsthole_start, nr_pages;
kaf24@3376 477 unsigned long dom0_memory_start, dom0_memory_end;
kaf24@3376 478 unsigned long initial_images_start, initial_images_end;
kaf24@3382 479 struct e820entry e820_raw[E820MAX];
kaf24@3392 480 int i, e820_raw_nr = 0, bytes = 0;
kaf24@3376 481
kaf24@3376 482 /* Parse the command-line options. */
kaf24@3382 483 if ( (mbi->flags & MBI_CMDLINE) && (mbi->cmdline != 0) )
kaf24@3382 484 cmdline_parse(__va(mbi->cmdline));
kaf24@3376 485
kaf24@3376 486 /* Must do this early -- e.g., spinlocks rely on get_current(). */
kaf24@3378 487 set_current(&idle0_exec_domain);
kaf24@3376 488
kaf24@3376 489 /* We initialise the serial devices very early so we can get debugging. */
kaf24@3376 490 serial_init_stage1();
kaf24@3376 491
kaf24@3376 492 init_console();
kaf24@3376 493
kaf24@3382 494 /* Check that we have at least one Multiboot module. */
kaf24@3382 495 if ( !(mbi->flags & MBI_MODULES) || (mbi->mods_count == 0) )
kaf24@3376 496 {
kaf24@3382 497 printk("FATAL ERROR: Require at least one Multiboot module.\n");
kaf24@3376 498 for ( ; ; ) ;
kaf24@3376 499 }
kaf24@3376 500
kaf24@3376 501 xenheap_phys_end = opt_xenheap_megabytes << 20;
kaf24@3376 502
kaf24@3382 503 if ( mbi->flags & MBI_MEMMAP )
kaf24@3382 504 {
kaf24@3382 505 while ( bytes < mbi->mmap_length )
kaf24@3382 506 {
kaf24@3382 507 memory_map_t *map = __va(mbi->mmap_addr + bytes);
kaf24@3382 508 e820_raw[e820_raw_nr].addr =
kaf24@3382 509 ((u64)map->base_addr_high << 32) | (u64)map->base_addr_low;
kaf24@3382 510 e820_raw[e820_raw_nr].size =
kaf24@3382 511 ((u64)map->length_high << 32) | (u64)map->length_low;
kaf24@3382 512 e820_raw[e820_raw_nr].type =
kaf24@3384 513 (map->type > E820_SHARED_PAGE) ? E820_RESERVED : map->type;
kaf24@3382 514 e820_raw_nr++;
kaf24@3382 515 bytes += map->size + 4;
kaf24@3382 516 }
kaf24@3382 517 }
kaf24@3382 518 else if ( mbi->flags & MBI_MEMLIMITS )
kaf24@3382 519 {
kaf24@3382 520 e820_raw[0].addr = 0;
kaf24@3382 521 e820_raw[0].size = mbi->mem_lower << 10;
kaf24@3382 522 e820_raw[0].type = E820_RAM;
kaf24@3392 523 e820_raw[1].addr = 0x100000;
kaf24@3392 524 e820_raw[1].size = mbi->mem_upper << 10;
kaf24@3392 525 e820_raw[1].type = E820_RAM;
kaf24@3382 526 e820_raw_nr = 2;
kaf24@3382 527 }
kaf24@3382 528 else
kaf24@3382 529 {
kaf24@3382 530 printk("FATAL ERROR: Bootloader provided no memory information.\n");
kaf24@3382 531 for ( ; ; ) ;
kaf24@3382 532 }
kaf24@3382 533
kaf24@3392 534 max_page = init_e820(e820_raw, e820_raw_nr);
kaf24@3376 535
kaf24@3392 536 /* Find the first high-memory RAM hole. */
kaf24@3392 537 for ( i = 0; i < e820.nr_map; i++ )
kaf24@3392 538 if ( (e820.map[i].type == E820_RAM) &&
kaf24@3392 539 (e820.map[i].addr >= 0x100000) )
kaf24@3392 540 break;
kaf24@3392 541 firsthole_start = e820.map[i].addr + e820.map[i].size;
kaf24@3376 542
kaf24@3392 543 /* Relocate the Multiboot modules. */
kaf24@3392 544 initial_images_start = xenheap_phys_end;
kaf24@3376 545 initial_images_end = initial_images_start +
kaf24@3376 546 (mod[mbi->mods_count-1].mod_end - mod[0].mod_start);
kaf24@3392 547 if ( initial_images_end > firsthole_start )
kaf24@3376 548 {
kaf24@3376 549 printk("Not enough memory to stash the DOM0 kernel image.\n");
kaf24@3376 550 for ( ; ; ) ;
kaf24@3376 551 }
kaf24@3392 552 #if defined(__i386__)
kaf24@3376 553 memmove((void *)initial_images_start, /* use low mapping */
kaf24@3376 554 (void *)mod[0].mod_start, /* use low mapping */
kaf24@3376 555 mod[mbi->mods_count-1].mod_end - mod[0].mod_start);
kaf24@3376 556 #elif defined(__x86_64__)
kaf24@3376 557 memmove(__va(initial_images_start),
kaf24@3376 558 __va(mod[0].mod_start),
kaf24@3376 559 mod[mbi->mods_count-1].mod_end - mod[0].mod_start);
kaf24@3376 560 #endif
kaf24@3376 561
kaf24@3392 562 /* Initialise boot-time allocator with all RAM situated after modules. */
kaf24@3392 563 heap_start = memguard_init(&_end);
kaf24@3392 564 heap_start = __va(init_boot_allocator(__pa(heap_start)));
kaf24@3392 565 nr_pages = 0;
kaf24@3392 566 for ( i = 0; i < e820.nr_map; i++ )
kaf24@3392 567 {
kaf24@3392 568 if ( e820.map[i].type != E820_RAM )
kaf24@3392 569 continue;
kaf24@3392 570 nr_pages += e820.map[i].size >> PAGE_SHIFT;
kaf24@3392 571 if ( (e820.map[i].addr + e820.map[i].size) >= initial_images_end )
kaf24@3392 572 init_boot_pages((e820.map[i].addr < initial_images_end) ?
kaf24@3392 573 initial_images_end : e820.map[i].addr,
kaf24@3392 574 e820.map[i].addr + e820.map[i].size);
kaf24@3392 575 }
kaf24@3392 576
kaf24@3392 577 printk("System RAM: %luMB (%lukB)\n",
kaf24@3392 578 nr_pages >> (20 - PAGE_SHIFT),
kaf24@3392 579 nr_pages << (PAGE_SHIFT - 10));
kaf24@3392 580
kaf24@3392 581 /* Allocate an aligned chunk of RAM for DOM0. */
kaf24@3392 582 dom0_memory_start = alloc_boot_pages(opt_dom0_mem << 10, 4UL << 20);
kaf24@3392 583 dom0_memory_end = dom0_memory_start + (opt_dom0_mem << 10);
kaf24@3392 584 if ( dom0_memory_start == 0 )
kaf24@3376 585 {
kaf24@3376 586 printk("Not enough memory for DOM0 memory reservation.\n");
kaf24@3376 587 for ( ; ; ) ;
kaf24@3376 588 }
kaf24@3376 589
kaf24@3392 590 init_frametable();
kaf24@3392 591
kaf24@3392 592 end_boot_allocator();
kaf24@3376 593
kaf24@3376 594 init_xenheap_pages(__pa(heap_start), xenheap_phys_end);
kaf24@3392 595 printk("Xen heap: %luMB (%lukB)\n",
kaf24@3392 596 (xenheap_phys_end-__pa(heap_start)) >> 20,
kaf24@3392 597 (xenheap_phys_end-__pa(heap_start)) >> 10);
kaf24@3376 598
kaf24@3632 599 early_boot = 0;
kaf24@3632 600
iap10@3654 601 /* Initialise the slab allocator. */
iap10@3654 602 xmem_cache_init();
iap10@3654 603 xmem_cache_sizes_init(max_page);
iap10@3654 604
kaf24@3376 605 start_of_day();
kaf24@3376 606
kaf24@3376 607 grant_table_init();
kaf24@3376 608
kaf24@3376 609 shadow_mode_init();
kaf24@3376 610
kaf24@3376 611 /* Create initial domain 0. */
kaf24@3376 612 dom0 = do_createdomain(0, 0);
kaf24@3376 613 if ( dom0 == NULL )
kaf24@3376 614 panic("Error creating domain 0\n");
kaf24@3376 615
kaf24@3378 616 set_bit(DF_PRIVILEGED, &dom0->d_flags);
kaf24@3376 617
kaf24@3376 618 /* Grab the DOM0 command line. Skip past the image name. */
kaf24@3376 619 cmdline = (unsigned char *)(mod[0].string ? __va(mod[0].string) : NULL);
kaf24@3376 620 if ( cmdline != NULL )
kaf24@3376 621 {
kaf24@3376 622 while ( *cmdline == ' ' ) cmdline++;
kaf24@3376 623 if ( (cmdline = strchr(cmdline, ' ')) != NULL )
kaf24@3376 624 while ( *cmdline == ' ' ) cmdline++;
kaf24@3376 625 }
kaf24@3376 626
kaf24@3376 627 /*
kaf24@3376 628 * We're going to setup domain0 using the module(s) that we stashed safely
kaf24@3376 629 * above our heap. The second module, if present, is an initrd ramdisk.
kaf24@3376 630 */
kaf24@3376 631 if ( construct_dom0(dom0, dom0_memory_start, dom0_memory_end,
kaf24@3376 632 (char *)initial_images_start,
kaf24@3376 633 mod[0].mod_end-mod[0].mod_start,
kaf24@3376 634 (mbi->mods_count == 1) ? 0 :
kaf24@3376 635 (char *)initial_images_start +
kaf24@3376 636 (mod[1].mod_start-mod[0].mod_start),
kaf24@3376 637 (mbi->mods_count == 1) ? 0 :
kaf24@3376 638 mod[mbi->mods_count-1].mod_end - mod[1].mod_start,
kaf24@3376 639 cmdline) != 0)
kaf24@3376 640 panic("Could not set up DOM0 guest OS\n");
kaf24@3376 641
kaf24@3376 642 /* The stash space for the initial kernel image can now be freed up. */
kaf24@3392 643 init_domheap_pages(initial_images_start, initial_images_end);
kaf24@3376 644
kaf24@3376 645 scrub_heap_pages();
kaf24@3376 646
kaf24@3376 647 init_trace_bufs();
kaf24@3376 648
kaf24@3376 649 /* Give up the VGA console if DOM0 is configured to grab it. */
kaf24@3376 650 console_endboot(cmdline && strstr(cmdline, "tty0"));
kaf24@3376 651
kaf24@3378 652 domain_unpause_by_systemcontroller(current->domain);
kaf24@3376 653 domain_unpause_by_systemcontroller(dom0);
kaf24@3376 654 startup_cpu_idle_loop();
kaf24@3376 655 }