Get initial bootstrap of APs working under xen.

Note that the APs still blow up in sched_throw().

MFC after:	1 month
This commit is contained in:
Kip Macy 2008-09-10 07:11:08 +00:00
parent c30b5c7330
commit 6859a304c6
9 changed files with 1251 additions and 29 deletions

View File

@ -63,7 +63,6 @@ options SYSVMSG # SYSV-style message queues
options SYSVSEM # SYSV-style semaphores
options _KPOSIX_PRIORITY_SCHEDULING # POSIX P1003_1B real-time extensions
options KBD_INSTALL_CDEV # install a CDEV entry in /dev
options STOP_NMI # Stop CPUS using NMI instead of IPI
options HWPMC_HOOKS # Necessary kernel hooks for hwpmc(4)
options AUDIT # Security event auditing

View File

@ -1012,7 +1012,6 @@ static struct apic_enumerator *best_enum;
void
apic_register_enumerator(struct apic_enumerator *enumerator)
{
#ifndef XEN
#ifdef INVARIANTS
struct apic_enumerator *apic_enum;
@ -1023,7 +1022,6 @@ apic_register_enumerator(struct apic_enumerator *enumerator)
}
#endif
SLIST_INSERT_HEAD(&enumerators, enumerator, apic_next);
#endif
}
/*
@ -1108,6 +1106,9 @@ apic_setup_io(void *dummy __unused)
printf("%s: Failed to setup I/O APICs: returned %d\n",
best_enum->apic_name, retval);
#ifdef XEN
return;
#endif
/*
* Finish setting up the local APIC on the BSP once we know how to
* properly program the LINT pins.

View File

@ -1213,7 +1213,7 @@ void (*cpu_idle_fn)(int) = cpu_idle_acpi;
void
cpu_idle(int busy)
{
#ifdef SMP
#if defined(SMP) && !defined(XEN)
if (mp_grab_cpu_hlt())
return;
#endif

View File

@ -184,7 +184,7 @@ vptetomachpte(vm_paddr_t *pte)
do { \
PANIC_IF(HYPERVISOR_update_va_mapping(((unsigned long)(_va)),\
(_ma), \
UVMF_INVLPG| UVMF_LOCAL) < 0); \
UVMF_INVLPG| UVMF_ALL) < 0); \
} while (/*CONSTCOND*/0)
#define PT_UPDATES_FLUSH() do { \

View File

@ -72,8 +72,8 @@ extern xen_pfn_t *xen_machine_phys;
#define PFNTOMFN(i) (xen_phys_machine[(i)])
#define MFNTOPFN(i) ((vm_paddr_t)xen_machine_phys[(i)])
#define VTOP(x) ((uintptr_t)(((uint8_t *)(x)) - KERNBASE))
#define PTOV(x) ((x) + KERNBASE)
#define VTOP(x) ((((uintptr_t)(x))) - KERNBASE)
#define PTOV(x) (((uintptr_t)(x)) + KERNBASE)
#define VTOPFN(x) (VTOP(x) >> PAGE_SHIFT)
#define PFNTOV(x) PTOV((vm_paddr_t)(x) << PAGE_SHIFT)

1095
sys/i386/xen/mp_machdep.c Normal file

File diff suppressed because it is too large Load Diff

130
sys/i386/xen/mptable.c Normal file
View File

@ -0,0 +1,130 @@
/*-
* Copyright (c) 2003 John Baldwin <jhb@FreeBSD.org>
* Copyright (c) 1996, by Steve Passe
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. The name of the developer may NOT be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <sys/cdefs.h>
__FBSDID("$FreeBSD$");
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/bus.h>
#include <sys/kernel.h>
#include <sys/malloc.h>
#include <vm/vm.h>
#include <vm/vm_param.h>
#include <vm/pmap.h>
#include <machine/apicreg.h>
#include <machine/frame.h>
#include <machine/intr_machdep.h>
#include <machine/apicvar.h>
#include <machine/md_var.h>
#include <machine/mptable.h>
#include <machine/specialreg.h>
#include <machine/xen/hypervisor.h>
#include <machine/xen/xen-os.h>
#include <machine/smp.h>
#include <xen/interface/vcpu.h>
static int mptable_probe(void);
static int mptable_probe_cpus(void);
static void mptable_register(void *dummy);
static int mptable_setup_local(void);
static int mptable_setup_io(void);
static struct apic_enumerator mptable_enumerator = {
"MPTable",
mptable_probe,
mptable_probe_cpus,
mptable_setup_local,
mptable_setup_io
};
static int
mptable_probe(void)
{
return (-100);
}
static int
mptable_probe_cpus(void)
{
int i, rc;
for (i = 0; i < MAXCPU; i++) {
rc = HYPERVISOR_vcpu_op(VCPUOP_is_up, i, NULL);
if (rc >= 0)
cpu_add(i, (i == 0));
}
return (0);
}
/*
* Initialize the local APIC on the BSP.
*/
static int
mptable_setup_local(void)
{
return (0);
}
static int
mptable_setup_io(void)
{
return (0);
}
static void
mptable_register(void *dummy __unused)
{
apic_register_enumerator(&mptable_enumerator);
}
SYSINIT(mptable_register, SI_SUB_CPU - 1, SI_ORDER_FIRST, mptable_register,
NULL);
int
mptable_pci_probe_table(int bus)
{
return (0);
}
int
mptable_pci_route_interrupt(device_t pcib, device_t dev, int pin)
{
return (0);
}

View File

@ -211,7 +211,7 @@ vm_offset_t virtual_end; /* VA of last avail page (end of kernel AS) */
int pgeflag = 0; /* PG_G or-in */
int pseflag = 0; /* PG_PS or-in */
static int nkpt;
int nkpt;
vm_offset_t kernel_vm_end;
extern u_int32_t KERNend;

View File

@ -42,10 +42,8 @@ __FBSDID("$FreeBSD$");
#include <sys/reboot.h>
#include <sys/sysproto.h>
#include <machine/xen/xen-os.h>
#include <vm/vm.h>
#include <vm/pmap.h>
#include <machine/segments.h>
@ -679,7 +677,7 @@ extern unsigned long *SMPpt;
extern struct user *proc0uarea;
extern vm_offset_t proc0kstack;
extern int vm86paddr, vm86phystk;
char *bootmem_start, *bootmem_current, *bootmem_end;
char *bootmem_start, *bootmem_current, *bootmem_end;
pteinfo_t *pteinfo_list;
void initvalues(start_info_t *startinfo);
@ -813,9 +811,17 @@ initvalues(start_info_t *startinfo)
vm_paddr_t pdir_shadow_ma;
#endif
unsigned long i;
int ncpus;
#ifdef SMP
ncpus = MAXCPU;
#else
ncpus = 1;
#endif
#if 0
HYPERVISOR_vm_assist(VMASST_CMD_enable, VMASST_TYPE_writable_pagetables);
#endif
HYPERVISOR_vm_assist(VMASST_CMD_enable, VMASST_TYPE_4gb_segments);
#ifdef notyet
/*
@ -864,7 +870,7 @@ initvalues(start_info_t *startinfo)
l1_pages = xen_start_info->nr_pt_frames - l2_pages - l3_pages;
KPTphysoff = (l2_pages + l3_pages)*PAGE_SIZE;
KPTphys = xpmap_ptom(VTOP(startinfo->pt_base + KPTphysoff));
XENPRINTF("IdlePTD %p\n", IdlePTD);
XENPRINTF("nr_pages: %ld shared_info: 0x%lx flags: 0x%lx pt_base: 0x%lx "
@ -876,7 +882,7 @@ initvalues(start_info_t *startinfo)
proc0kstack = cur_space; cur_space += (KSTACK_PAGES * PAGE_SIZE);
printk("proc0kstack=%u\n", proc0kstack);
/* vm86/bios stack */
cur_space += PAGE_SIZE;
@ -954,6 +960,7 @@ initvalues(start_info_t *startinfo)
}
xen_load_cr3(VTOP(IdlePDPTnew));
xen_pgdpt_pin(xpmap_ptom(VTOP(IdlePDPTnew)));
for (i = 0; i < 4; i++) {
xen_queue_pt_update((vm_paddr_t)(IdlePTDnewma[2] + (PTDPTDI - 1024 + i)*sizeof(vm_paddr_t)),
IdlePTDnewma[i] | PG_V);
@ -972,10 +979,13 @@ initvalues(start_info_t *startinfo)
IdlePDPTma = IdlePDPTnewma;
/* allocate page for gdt */
gdt = (union descriptor *)cur_space; cur_space += PAGE_SIZE;
/* allocate page for ldt */
ldt = (union descriptor *)cur_space; cur_space += PAGE_SIZE;
gdt = (union descriptor *)cur_space;
cur_space += PAGE_SIZE*ncpus;
/* allocate page for ldt */
ldt = (union descriptor *)cur_space; cur_space += PAGE_SIZE;
cur_space += PAGE_SIZE;
HYPERVISOR_shared_info = (shared_info_t *)cur_space;
cur_space += PAGE_SIZE;
@ -1001,18 +1011,6 @@ initvalues(start_info_t *startinfo)
printk("#5\n");
HYPERVISOR_shared_info->arch.pfn_to_mfn_frame_list_list = (unsigned long)xen_phys_machine;
#if 0 && defined(SMP)
for (i = 0; i < ncpus; i++) {
int j, npages = (sizeof(struct privatespace) + 1)/PAGE_SIZE;
for (j = 0; j < npages; j++) {
vm_paddr_t ma = xpmap_ptom(cur_space);
cur_space += PAGE_SIZE;
PT_SET_VA_MA(SMPpt + i*npages + j, ma | PG_KERNEL, FALSE);
}
}
xen_flush_queue();
#endif
set_iopl.iopl = 1;
PANIC_IF(HYPERVISOR_physdev_op(PHYSDEVOP_SET_IOPL, &set_iopl));
@ -1280,7 +1278,6 @@ xen_suspend(void *ignore)
vcpu_prepare(i);
#endif
/*
* Only resume xenbus /after/ we've prepared our VCPUs; otherwise
* the VCPU hotplug callback can race with our vcpu_prepare