WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-changelog

[Xen-changelog] [IA64] SMP-guest

# HG changeset patch
# User awilliam@xxxxxxxxxxx
# Node ID de0c04ed4ab7b9c4572c42df2de838e2b243a8e2
# Parent  bbf325d767687745c6838ac43fe48692b6792e54
[IA64] SMP-guest

Final SMP-guest patch: add IPI and boot rendez-vous support.

Signed-off-by: Tristan Gingold <tristan.gingold@xxxxxxxx>

diff -r bbf325d76768 -r de0c04ed4ab7 
linux-2.6-xen-sparse/arch/ia64/kernel/irq_ia64.c
--- a/linux-2.6-xen-sparse/arch/ia64/kernel/irq_ia64.c  Fri Apr 21 09:20:13 
2006 -0600
+++ b/linux-2.6-xen-sparse/arch/ia64/kernel/irq_ia64.c  Fri Apr 21 10:40:17 
2006 -0600
@@ -265,6 +265,14 @@ ia64_send_ipi (int cpu, int vector, int 
        unsigned long ipi_data;
        unsigned long phys_cpu_id;
 
+#ifdef CONFIG_XEN
+        if (running_on_xen) {
+                extern void xen_send_ipi (int cpu, int vec);
+                xen_send_ipi (cpu, vector);
+                return;
+        }
+#endif /* CONFIG_XEN */
+
 #ifdef CONFIG_SMP
        phys_cpu_id = cpu_physical_id(cpu);
 #else
diff -r bbf325d76768 -r de0c04ed4ab7 
linux-2.6-xen-sparse/arch/ia64/xen/hypercall.S
--- a/linux-2.6-xen-sparse/arch/ia64/xen/hypercall.S    Fri Apr 21 09:20:13 
2006 -0600
+++ b/linux-2.6-xen-sparse/arch/ia64/xen/hypercall.S    Fri Apr 21 10:40:17 
2006 -0600
@@ -341,3 +341,13 @@ GLOBAL_ENTRY(xen_set_eflag)
        br.ret.sptk.many rp
 END(xen_set_eflag)
 #endif
+
+GLOBAL_ENTRY(xen_send_ipi)
+        mov r14=r32
+        mov r15=r33
+        mov r2=0x380
+        break 0x1000
+        ;;
+        br.ret.sptk.many rp
+        ;;
+END(xen_send_ipi)
diff -r bbf325d76768 -r de0c04ed4ab7 xen/arch/ia64/xen/dom_fw.c
--- a/xen/arch/ia64/xen/dom_fw.c        Fri Apr 21 09:20:13 2006 -0600
+++ b/xen/arch/ia64/xen/dom_fw.c        Fri Apr 21 10:40:17 2006 -0600
@@ -94,9 +94,24 @@ unsigned long dom_fw_setup(struct domain
 
 /* the following heavily leveraged from linux/arch/ia64/hp/sim/fw-emu.c */
 
-#define NUM_EFI_SYS_TABLES 6
-# define NUM_MEM_DESCS 5
-
+/* Set IP and GR1 of not yet initialized vcpu.  */
+static void
+set_os_boot_rendez (struct domain *d, unsigned long pc, unsigned long gr1)
+{
+       struct vcpu *v;
+       int i;
+
+       printf ("set_os_boot_rendez: %lx %lx\n", pc, gr1);
+       for (i = 1; i < MAX_VIRT_CPUS; i++) {
+               v = d->vcpu[i];
+               if (v != NULL
+                   && !test_bit(_VCPUF_initialised, &v->vcpu_flags)) {
+                       struct pt_regs *regs = vcpu_regs (v);
+                       regs->cr_iip = pc;
+                       regs->r1 = gr1;
+               }
+       }
+}
 
 struct sal_ret_values
 sal_emulator (long index, unsigned long in1, unsigned long in2,
@@ -155,7 +170,18 @@ sal_emulator (long index, unsigned long 
                     printf("NON-PRIV DOMAIN CALLED SAL_PCI_CONFIG_WRITE\n");
                break;
            case SAL_SET_VECTORS:
-               printf("*** CALLED SAL_SET_VECTORS.  IGNORED...\n");
+               if (in1 == SAL_VECTOR_OS_BOOT_RENDEZ) {
+                       if (in4 != 0 || in5 != 0 || in6 != 0 || in7 != 0) {
+                               /* Sanity check: cs_length1 must be 0,
+                                  second vector is reserved.  */
+                               status = -2;
+                       }
+                       else
+                               set_os_boot_rendez (current->domain, in2, in3);
+               }
+               else
+                       printf("*** CALLED SAL_SET_VECTORS %lu.  IGNORED...\n",
+                              in1);
                break;
            case SAL_GET_STATE_INFO:
                /* No more info.  */
@@ -618,6 +644,9 @@ dom_fw_fake_acpi(struct domain *d, struc
        return;
 }
 
+#define NUM_EFI_SYS_TABLES 6
+#define NUM_MEM_DESCS  5
+
 static struct ia64_boot_param *
 dom_fw_init (struct domain *d, const char *args, int arglen, char *fw_mem, int 
fw_mem_size)
 {
@@ -625,8 +654,9 @@ dom_fw_init (struct domain *d, const cha
        efi_runtime_services_t *efi_runtime;
        efi_config_table_t *efi_tables;
        struct ia64_sal_systab *sal_systab;
+       struct ia64_sal_desc_entry_point *sal_ed;
+       struct ia64_sal_desc_ap_wakeup *sal_wakeup;
        efi_memory_desc_t *efi_memmap, *md;
-       struct ia64_sal_desc_entry_point *sal_ed;
        struct ia64_boot_param *bp;
        unsigned long *pfn;
        unsigned char checksum = 0;
@@ -662,6 +692,7 @@ dom_fw_init (struct domain *d, const cha
        efi_tables  = (void *) cp; cp += NUM_EFI_SYS_TABLES * 
sizeof(*efi_tables);
        sal_systab  = (void *) cp; cp += sizeof(*sal_systab);
        sal_ed      = (void *) cp; cp += sizeof(*sal_ed);
+       sal_wakeup  = (void *) cp; cp += sizeof(*sal_wakeup);
        efi_memmap  = (void *) cp; cp += NUM_MEM_DESCS*sizeof(*efi_memmap);
        bp          = (void *) cp; cp += sizeof(*bp);
        pfn         = (void *) cp; cp += NFUNCPTRS * 2 * sizeof(pfn);
@@ -779,7 +810,7 @@ dom_fw_init (struct domain *d, const cha
        sal_systab->size = sizeof(*sal_systab);
        sal_systab->sal_rev_minor = 1;
        sal_systab->sal_rev_major = 0;
-       sal_systab->entry_count = 1;
+       sal_systab->entry_count = 2;
 
        strcpy((char *)sal_systab->oem_id, "Xen/ia64");
        strcpy((char *)sal_systab->product_id, "Xen/ia64");
@@ -791,6 +822,11 @@ dom_fw_init (struct domain *d, const cha
        sal_ed->sal_proc = FW_HYPERCALL_SAL_CALL_PADDR + start_mpaddr;
        dom_fw_hypercall_patch (d, sal_ed->sal_proc, FW_HYPERCALL_SAL_CALL, 1);
        sal_ed->gp = 0;  // will be ignored
+
+       /* Fill an AP wakeup descriptor.  */
+       sal_wakeup->type = SAL_DESC_AP_WAKEUP;
+       sal_wakeup->mechanism = IA64_SAL_AP_EXTERNAL_INT;
+       sal_wakeup->vector = XEN_SAL_BOOT_RENDEZ_VEC;
 
        for (cp = (char *) sal_systab; cp < (char *) efi_memmap; ++cp)
                checksum += *cp;
diff -r bbf325d76768 -r de0c04ed4ab7 xen/arch/ia64/xen/hypercall.c
--- a/xen/arch/ia64/xen/hypercall.c     Fri Apr 21 09:20:13 2006 -0600
+++ b/xen/arch/ia64/xen/hypercall.c     Fri Apr 21 10:40:17 2006 -0600
@@ -132,6 +132,65 @@ xen_hypercall (struct pt_regs *regs)
 }
 
 
+static void
+fw_hypercall_ipi (struct pt_regs *regs)
+{
+       int cpu = regs->r14;
+       int vector = regs->r15;
+       struct vcpu *targ;
+                   
+       if (0 && vector == 254)
+               printf ("send_ipi from %d to %d vector=%d\n",
+                       current->vcpu_id, cpu, vector);
+
+       if (cpu > MAX_VIRT_CPUS)
+               return;
+
+       targ = current->domain->vcpu[cpu];
+       if (targ == NULL)
+               return;
+
+       if (vector == XEN_SAL_BOOT_RENDEZ_VEC
+           && !test_bit(_VCPUF_initialised, &targ->vcpu_flags)) {
+               struct pt_regs *targ_regs = vcpu_regs (targ);
+               struct vcpu_guest_context c;
+               
+               printf ("arch_boot_vcpu: %p %p\n",
+                       (void *)targ_regs->cr_iip,
+                       (void *)targ_regs->r1);
+               memset (&c, 0, sizeof (c));
+               /* Copy regs.  */
+               c.regs.cr_iip = targ_regs->cr_iip;
+               c.regs.r1 = targ_regs->r1;
+               
+               /* Copy from vcpu 0.  */
+               c.vcpu.evtchn_vector =
+                       current->domain->vcpu[0]->vcpu_info->arch.evtchn_vector;
+               if (arch_set_info_guest (targ, &c) != 0) {
+                       printf ("arch_boot_vcpu: failure\n");
+                       return;
+               }
+               if (test_and_clear_bit(_VCPUF_down,
+                                      &targ->vcpu_flags)) {
+                       vcpu_wake(targ);
+                       printf ("arch_boot_vcpu: vcpu %d awaken %016lx!\n",
+                               targ->vcpu_id, targ_regs->cr_iip);
+               }
+               else
+                       printf ("arch_boot_vcpu: huu, already awaken!");
+       }
+       else {
+               int running = test_bit(_VCPUF_running,
+                                      &targ->vcpu_flags);
+               
+               vcpu_pend_interrupt(targ, vector);
+               vcpu_unblock(targ);
+               if (running)
+                       smp_send_event_check_cpu(targ->processor);
+       }
+       return;
+}
+
 static int
 fw_hypercall (struct pt_regs *regs)
 {
@@ -232,6 +291,9 @@ fw_hypercall (struct pt_regs *regs)
                // FIXME: need fixes in efi.h from 2.6.9
                regs->r8 = EFI_UNSUPPORTED;
                break;
+           case FW_HYPERCALL_IPI:
+               fw_hypercall_ipi (regs);
+               break;
            default:
                printf("unknown ia64 fw hypercall %lx\n", regs->r2);
                regs->r8 = do_ni_hypercall();
diff -r bbf325d76768 -r de0c04ed4ab7 xen/include/asm-ia64/dom_fw.h
--- a/xen/include/asm-ia64/dom_fw.h     Fri Apr 21 09:20:13 2006 -0600
+++ b/xen/include/asm-ia64/dom_fw.h     Fri Apr 21 10:40:17 2006 -0600
@@ -125,8 +125,13 @@ extern unsigned long dom_fw_setup(struct
 */
 #define FW_HYPERCALL_FIRST_ARCH                0x300UL
 
+#define FW_HYPERCALL_IPI               0x380UL
+
 /* Xen/ia64 user hypercalls.  Only used for debugging.  */
 #define FW_HYPERCALL_FIRST_USER                0xff00UL
+
+/* Interrupt vector used for os boot rendez vous.  */
+#define XEN_SAL_BOOT_RENDEZ_VEC        0xF3
 
 extern struct ia64_pal_retval xen_pal_emulator(UINT64, u64, u64, u64);
 extern struct sal_ret_values sal_emulator (long index, unsigned long in1, 
unsigned long in2, unsigned long in3, unsigned long in4, unsigned long in5, 
unsigned long in6, unsigned long in7);

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog

<Prev in Thread] Current Thread [Next in Thread>
  • [Xen-changelog] [IA64] SMP-guest, Xen patchbot -unstable <=