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] merge.

# HG changeset patch
# User kevin@xxxxxxxxxxxxxxxxxxxxx
# Node ID e3d811cca4e1d385a793cc515d72c8e671fd6267
# Parent  b5196e075602b1463f93d06a8ec14842c1217f22
# Parent  a6bb479191613810dd22974219198f24e0935c4e
merge.

diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/Makefile
--- a/xen/arch/ia64/Makefile    Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/Makefile    Tue Aug 16 04:15:23 2005
@@ -1,4 +1,6 @@
 include $(BASEDIR)/Rules.mk
+
+VPATH = linux linux-xen
 
 # libs-y       += arch/ia64/lib/lib.a
 
@@ -75,7 +77,7 @@
                -o xen.lds.s xen.lds.S
 
 ia64lib.o:
-       $(MAKE) -C lib && cp lib/ia64lib.o .
+       $(MAKE) -C linux/lib && cp linux/lib/ia64lib.o .
 
 clean:
        rm -f *.o *~ core  xen.lds.s 
$(BASEDIR)/include/asm-ia64/.offsets.h.stamp asm-offsets.s
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/Rules.mk
--- a/xen/arch/ia64/Rules.mk    Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/Rules.mk    Tue Aug 16 04:15:23 2005
@@ -6,14 +6,21 @@
 CROSS_COMPILE ?= /usr/local/sp_env/v2.2.5/i686/bin/ia64-unknown-linux-
 endif
 AFLAGS  += -D__ASSEMBLY__
-CPPFLAGS  += -I$(BASEDIR)/include -I$(BASEDIR)/include/asm-ia64
+CPPFLAGS  += -I$(BASEDIR)/include -I$(BASEDIR)/include/asm-ia64        \
+             -I$(BASEDIR)/include/asm-ia64/linux                       \
+            -I$(BASEDIR)/include/asm-ia64/linux-xen                    \
+             -I$(BASEDIR)/arch/ia64/linux -I$(BASEDIR)/arch/ia64/linux-xen
+
 CFLAGS  := -nostdinc -fno-builtin -fno-common -fno-strict-aliasing
 #CFLAGS  += -O3                # -O3 over-inlines making debugging tough!
 CFLAGS  += -O2         # but no optimization causes compile errors!
 #CFLAGS  += -iwithprefix include -Wall -DMONITOR_BASE=$(MONITOR_BASE)
 CFLAGS  += -iwithprefix include -Wall
 CFLAGS  += -fomit-frame-pointer -I$(BASEDIR)/include -D__KERNEL__
-CFLAGS  += -I$(BASEDIR)/include/asm-ia64
+CFLAGS  += -I$(BASEDIR)/include/asm-ia64 -I$(BASEDIR)/include/asm-ia64/linux \
+           -I$(BASEDIR)/include/asm-ia64/linux                                 
\
+           -I$(BASEDIR)/include/asm-ia64/linux-xen                     \
+           -I$(BASEDIR)/arch/ia64/linux -I$(BASEDIR)/arch/ia64/linux-xen
 CFLAGS  += -Wno-pointer-arith -Wredundant-decls
 CFLAGS  += -DIA64 -DXEN -DLINUX_2_6
 CFLAGS += -ffixed-r13 -mfixed-range=f12-f15,f32-f127
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/asm-offsets.c
--- a/xen/arch/ia64/asm-offsets.c       Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/asm-offsets.c       Tue Aug 16 04:15:23 2005
@@ -139,14 +139,14 @@
        DEFINE(IA64_PT_REGS_R2_OFFSET, offsetof (struct pt_regs, r2));
        DEFINE(IA64_PT_REGS_R3_OFFSET, offsetof (struct pt_regs, r3));
 #ifdef CONFIG_VTI
-       DEFINE(IA64_PT_REGS_R4_OFFSET, offsetof (struct xen_regs, r4));
-       DEFINE(IA64_PT_REGS_R5_OFFSET, offsetof (struct xen_regs, r5));
-       DEFINE(IA64_PT_REGS_R6_OFFSET, offsetof (struct xen_regs, r6));
-       DEFINE(IA64_PT_REGS_R7_OFFSET, offsetof (struct xen_regs, r7));
-       DEFINE(IA64_PT_REGS_CR_IIPA_OFFSET, offsetof (struct xen_regs, 
cr_iipa));
-       DEFINE(IA64_PT_REGS_CR_ISR_OFFSET, offsetof (struct xen_regs, cr_isr));
-       DEFINE(IA64_PT_REGS_EML_UNAT_OFFSET, offsetof (struct xen_regs, 
eml_unat));
-       DEFINE(IA64_PT_REGS_RFI_PFS_OFFSET, offsetof (struct xen_regs, 
rfi_pfs));
+       DEFINE(IA64_PT_REGS_R4_OFFSET, offsetof (struct pt_regs, r4));
+       DEFINE(IA64_PT_REGS_R5_OFFSET, offsetof (struct pt_regs, r5));
+       DEFINE(IA64_PT_REGS_R6_OFFSET, offsetof (struct pt_regs, r6));
+       DEFINE(IA64_PT_REGS_R7_OFFSET, offsetof (struct pt_regs, r7));
+       DEFINE(IA64_PT_REGS_CR_IIPA_OFFSET, offsetof (struct pt_regs, cr_iipa));
+       DEFINE(IA64_PT_REGS_CR_ISR_OFFSET, offsetof (struct pt_regs, cr_isr));
+       DEFINE(IA64_PT_REGS_EML_UNAT_OFFSET, offsetof (struct pt_regs, 
eml_unat));
+       DEFINE(IA64_PT_REGS_RFI_PFS_OFFSET, offsetof (struct pt_regs, rfi_pfs));
        DEFINE(RFI_IIP_OFFSET, offsetof(struct vcpu, arch.arch_vmx.rfi_iip));
        DEFINE(RFI_IPSR_OFFSET, offsetof(struct vcpu, arch.arch_vmx.rfi_ipsr));
        DEFINE(RFI_IFS_OFFSET,offsetof(struct vcpu ,arch.arch_vmx.rfi_ifs));
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/domain.c
--- a/xen/arch/ia64/domain.c    Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/domain.c    Tue Aug 16 04:15:23 2005
@@ -450,7 +450,7 @@
                 unsigned long start_info)
 {
        struct domain *d = v->domain;
-       struct xen_regs *regs;
+       struct pt_regs *regs;
        struct ia64_boot_param *bp;
        extern char saved_command_line[];
        //char *dom0_cmdline = "BOOT_IMAGE=scsi0:\EFI\redhat\xenlinux nomca 
root=/dev/sdb1 ro";
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/mmio.c
--- a/xen/arch/ia64/mmio.c      Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/mmio.c      Tue Aug 16 04:15:23 2005
@@ -25,7 +25,7 @@
 #include <asm/tlb.h>
 #include <asm/vmx_mm_def.h>
 #include <asm/gcc_intrin.h>
-#include <xen/interrupt.h>
+#include <linux/interrupt.h>
 #include <asm/vmx_vcpu.h>
 #include <asm/privop.h>
 #include <asm/types.h>
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/tools/mkbuildtree
--- a/xen/arch/ia64/tools/mkbuildtree   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/tools/mkbuildtree   Tue Aug 16 04:15:23 2005
@@ -3,15 +3,10 @@
 # run in xen-X.X/xen directory after unpacking linux in same directory
 
 XEN=$PWD
-LINUX=$XEN/../../linux-2.6.11
-LINUXPATCH=$XEN/arch/ia64/patch/linux-2.6.11
-XENPATCH=$XEN/arch/ia64/patch/xen-2.0.1
 
 cp_patch ()
 {
-       #diff -u $LINUX/$1 $XEN/$2 > $LINUXPATCH/$3
-       cp $LINUX/$1 $XEN/$2
-       patch <$LINUXPATCH/$3 $XEN/$2
+       true;
 }
 
 xen_patch ()
@@ -22,34 +17,13 @@
 
 softlink ()
 {
-       ln -s $LINUX/$1 $XEN/$2
+       true;
 }
 
 null ()
 {
-       touch $XEN/$1
+       true;
 }
-
-
-# ensure linux directory is set up
-if [ ! -d $LINUX ]; then
-       echo "ERROR: $LINUX directory doesn't exist"
-       exit
-fi
-
-# setup
-
-#mkdir arch/ia64
-#mkdir arch/ia64/lib
-#mkdir include/asm-ia64
-mkdir include/asm-generic
-mkdir include/asm-ia64/linux
-mkdir include/asm-ia64/linux/byteorder
-mkdir include/asm-ia64/sn
-# use "gcc -Iinclude/asm-ia64" to find these linux includes
-#ln -s $XEN/include/xen $XEN/include/linux
-#ln -s $XEN/include/asm-ia64/linux $XEN/include/asm-ia64/xen 
-ln -s ../slab.h include/asm-ia64/linux/slab.h
 
 # prepare for building asm-offsets (circular dependency)
 #echo '#define IA64_TASK_SIZE 0' > include/asm-ia64/asm-offsets.h
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/vmmu.c
--- a/xen/arch/ia64/vmmu.c      Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/vmmu.c      Tue Aug 16 04:15:23 2005
@@ -24,7 +24,7 @@
 #include <asm/tlb.h>
 #include <asm/gcc_intrin.h>
 #include <asm/vcpu.h>
-#include <xen/interrupt.h>
+#include <linux/interrupt.h>
 #include <asm/vmx_vcpu.h>
 #include <asm/vmx_mm_def.h>
 #include <asm/vmx.h>
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/vmx_vcpu.c
--- a/xen/arch/ia64/vmx_vcpu.c  Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/vmx_vcpu.c  Tue Aug 16 04:15:23 2005
@@ -111,7 +111,7 @@
     }
     new_psr.val=vmx_vcpu_get_psr(vcpu);
     {
-    struct xen_regs *regs = vcpu_regs(vcpu);
+    struct pt_regs *regs = vcpu_regs(vcpu);
     guest_psr_buf[guest_psr_index].ip = regs->cr_iip;
     guest_psr_buf[guest_psr_index].psr = new_psr.val;
     if (++guest_psr_index >= 100)
@@ -141,7 +141,7 @@
     return IA64_NO_FAULT;
 }
 
-/* Adjust slot both in xen_regs and vpd, upon vpsr.ri which
+/* Adjust slot both in pt_regs and vpd, upon vpsr.ri which
  * should have sync with ipsr in entry.
  *
  * Clear some bits due to successfully emulation.
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/vtlb.c
--- a/xen/arch/ia64/vtlb.c      Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/vtlb.c      Tue Aug 16 04:15:23 2005
@@ -26,7 +26,7 @@
 #include <asm/mm.h>
 #include <asm/vmx_mm_def.h>
 #include <asm/gcc_intrin.h>
-#include <xen/interrupt.h>
+#include <linux/interrupt.h>
 #include <asm/vmx_vcpu.h>
 #define  MAX_CCH_LENGTH     40
 
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/regs.h
--- a/xen/include/asm-ia64/regs.h       Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/regs.h       Tue Aug 16 04:15:23 2005
@@ -1,3 +1,2 @@
 #include <asm/ptrace.h>
-#define cpu_user_regs pt_regs
 #define xen_regs pt_regs
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/vcpu.h
--- a/xen/include/asm-ia64/vcpu.h       Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/vcpu.h       Tue Aug 16 04:15:23 2005
@@ -6,6 +6,7 @@
 
 //#include "thread.h"
 #include <asm/ia64_int.h>
+#include <public/arch-ia64.h>
 
 typedef        unsigned long UINT64;
 typedef        unsigned int UINT;
@@ -13,7 +14,7 @@
 struct vcpu;
 typedef        struct vcpu VCPU;
 
-typedef struct pt_regs REGS;
+typedef cpu_user_regs_t REGS;
 
 #define VCPU(_v,_x)    _v->vcpu_info->arch.privregs->_x
 
diff -r b5196e075602 -r e3d811cca4e1 xen/include/public/arch-ia64.h
--- a/xen/include/public/arch-ia64.h    Mon Aug 15 20:28:07 2005
+++ b/xen/include/public/arch-ia64.h    Tue Aug 16 04:15:23 2005
@@ -57,7 +57,7 @@
         } u;
 };
 
-struct pt_regs {
+typedef struct cpu_user_regs{
        /* The following registers are saved by SAVE_MIN: */
        unsigned long b6;               /* scratch */
        unsigned long b7;               /* scratch */
@@ -138,7 +138,7 @@
        struct pt_fpreg f9;             /* scratch */
        struct pt_fpreg f10;            /* scratch */
        struct pt_fpreg f11;            /* scratch */
-};
+}cpu_user_regs_t;
 
 typedef union {
        unsigned long value;
@@ -274,7 +274,7 @@
        unsigned long vm_assist;   /* VMASST_TYPE_* bitmap, now none on IPF */
        unsigned long guest_iip;   /* Guest entry point */
 
-       struct pt_regs regs;
+       cpu_user_regs_t regs;
        arch_vcpu_info_t vcpu;
        arch_shared_info_t shared;
 } vcpu_guest_context_t;
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/efi.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/efi.c     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,866 @@
+/*
+ * Extensible Firmware Interface
+ *
+ * Based on Extensible Firmware Interface Specification version 0.9 April 30, 
1999
+ *
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999-2003 Hewlett-Packard Co.
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * All EFI Runtime Services are not implemented yet as EFI only
+ * supports physical mode addressing on SoftSDV. This is to be fixed
+ * in a future version.  --drummond 1999-07-20
+ *
+ * Implemented EFI runtime services and virtual mode calls.  --davidm
+ *
+ * Goutham Rao: <goutham.rao@xxxxxxxxx>
+ *     Skip non-WB memory and ignore empty memory ranges.
+ */
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/types.h>
+#include <linux/time.h>
+#include <linux/efi.h>
+
+#include <asm/io.h>
+#include <asm/kregs.h>
+#include <asm/meminit.h>
+#include <asm/pgtable.h>
+#include <asm/processor.h>
+#include <asm/mca.h>
+
+#define EFI_DEBUG      0
+
+extern efi_status_t efi_call_phys (void *, ...);
+
+struct efi efi;
+EXPORT_SYMBOL(efi);
+static efi_runtime_services_t *runtime;
+static unsigned long mem_limit = ~0UL, max_addr = ~0UL;
+
+#define efi_call_virt(f, args...)      (*(f))(args)
+
+#define STUB_GET_TIME(prefix, adjust_arg)                                      
                  \
+static efi_status_t                                                            
                  \
+prefix##_get_time (efi_time_t *tm, efi_time_cap_t *tc)                         
                  \
+{                                                                              
                  \
+       struct ia64_fpreg fr[6];                                                
                  \
+       efi_time_cap_t *atc = NULL;                                             
                  \
+       efi_status_t ret;                                                       
                  \
+                                                                               
                  \
+       if (tc)                                                                 
                  \
+               atc = adjust_arg(tc);                                           
                  \
+       ia64_save_scratch_fpregs(fr);                                           
                  \
+       ret = efi_call_##prefix((efi_get_time_t *) __va(runtime->get_time), 
adjust_arg(tm), atc); \
+       ia64_load_scratch_fpregs(fr);                                           
                  \
+       return ret;                                                             
                  \
+}
+
+#define STUB_SET_TIME(prefix, adjust_arg)                                      
                \
+static efi_status_t                                                            
                \
+prefix##_set_time (efi_time_t *tm)                                             
                \
+{                                                                              
                \
+       struct ia64_fpreg fr[6];                                                
                \
+       efi_status_t ret;                                                       
                \
+                                                                               
                \
+       ia64_save_scratch_fpregs(fr);                                           
                \
+       ret = efi_call_##prefix((efi_set_time_t *) __va(runtime->set_time), 
adjust_arg(tm));    \
+       ia64_load_scratch_fpregs(fr);                                           
                \
+       return ret;                                                             
                \
+}
+
+#define STUB_GET_WAKEUP_TIME(prefix, adjust_arg)                               
                \
+static efi_status_t                                                            
                \
+prefix##_get_wakeup_time (efi_bool_t *enabled, efi_bool_t *pending, efi_time_t 
*tm)            \
+{                                                                              
                \
+       struct ia64_fpreg fr[6];                                                
                \
+       efi_status_t ret;                                                       
                \
+                                                                               
                \
+       ia64_save_scratch_fpregs(fr);                                           
                \
+       ret = efi_call_##prefix((efi_get_wakeup_time_t *) 
__va(runtime->get_wakeup_time),       \
+                               adjust_arg(enabled), adjust_arg(pending), 
adjust_arg(tm));      \
+       ia64_load_scratch_fpregs(fr);                                           
                \
+       return ret;                                                             
                \
+}
+
+#define STUB_SET_WAKEUP_TIME(prefix, adjust_arg)                               
                \
+static efi_status_t                                                            
                \
+prefix##_set_wakeup_time (efi_bool_t enabled, efi_time_t *tm)                  
                \
+{                                                                              
                \
+       struct ia64_fpreg fr[6];                                                
                \
+       efi_time_t *atm = NULL;                                                 
                \
+       efi_status_t ret;                                                       
                \
+                                                                               
                \
+       if (tm)                                                                 
                \
+               atm = adjust_arg(tm);                                           
                \
+       ia64_save_scratch_fpregs(fr);                                           
                \
+       ret = efi_call_##prefix((efi_set_wakeup_time_t *) 
__va(runtime->set_wakeup_time),       \
+                               enabled, atm);                                  
                \
+       ia64_load_scratch_fpregs(fr);                                           
                \
+       return ret;                                                             
                \
+}
+
+#define STUB_GET_VARIABLE(prefix, adjust_arg)                                  
        \
+static efi_status_t                                                            
        \
+prefix##_get_variable (efi_char16_t *name, efi_guid_t *vendor, u32 *attr,      
        \
+                      unsigned long *data_size, void *data)                    
        \
+{                                                                              
        \
+       struct ia64_fpreg fr[6];                                                
        \
+       u32 *aattr = NULL;                                                      
                \
+       efi_status_t ret;                                                       
        \
+                                                                               
        \
+       if (attr)                                                               
        \
+               aattr = adjust_arg(attr);                                       
        \
+       ia64_save_scratch_fpregs(fr);                                           
        \
+       ret = efi_call_##prefix((efi_get_variable_t *) 
__va(runtime->get_variable),     \
+                               adjust_arg(name), adjust_arg(vendor), aattr,    
        \
+                               adjust_arg(data_size), adjust_arg(data));       
        \
+       ia64_load_scratch_fpregs(fr);                                           
        \
+       return ret;                                                             
        \
+}
+
+#define STUB_GET_NEXT_VARIABLE(prefix, adjust_arg)                             
                \
+static efi_status_t                                                            
                \
+prefix##_get_next_variable (unsigned long *name_size, efi_char16_t *name, 
efi_guid_t *vendor)  \
+{                                                                              
                \
+       struct ia64_fpreg fr[6];                                                
                \
+       efi_status_t ret;                                                       
                \
+                                                                               
                \
+       ia64_save_scratch_fpregs(fr);                                           
                \
+       ret = efi_call_##prefix((efi_get_next_variable_t *) 
__va(runtime->get_next_variable),   \
+                               adjust_arg(name_size), adjust_arg(name), 
adjust_arg(vendor));   \
+       ia64_load_scratch_fpregs(fr);                                           
                \
+       return ret;                                                             
                \
+}
+
+#define STUB_SET_VARIABLE(prefix, adjust_arg)                                  
        \
+static efi_status_t                                                            
        \
+prefix##_set_variable (efi_char16_t *name, efi_guid_t *vendor, unsigned long 
attr,     \
+                      unsigned long data_size, void *data)                     
        \
+{                                                                              
        \
+       struct ia64_fpreg fr[6];                                                
        \
+       efi_status_t ret;                                                       
        \
+                                                                               
        \
+       ia64_save_scratch_fpregs(fr);                                           
        \
+       ret = efi_call_##prefix((efi_set_variable_t *) 
__va(runtime->set_variable),     \
+                               adjust_arg(name), adjust_arg(vendor), attr, 
data_size,  \
+                               adjust_arg(data));                              
        \
+       ia64_load_scratch_fpregs(fr);                                           
        \
+       return ret;                                                             
        \
+}
+
+#define STUB_GET_NEXT_HIGH_MONO_COUNT(prefix, adjust_arg)                      
                \
+static efi_status_t                                                            
                \
+prefix##_get_next_high_mono_count (u32 *count)                                 
                \
+{                                                                              
                \
+       struct ia64_fpreg fr[6];                                                
                \
+       efi_status_t ret;                                                       
                \
+                                                                               
                \
+       ia64_save_scratch_fpregs(fr);                                           
                \
+       ret = efi_call_##prefix((efi_get_next_high_mono_count_t *)              
                \
+                               __va(runtime->get_next_high_mono_count), 
adjust_arg(count));    \
+       ia64_load_scratch_fpregs(fr);                                           
                \
+       return ret;                                                             
                \
+}
+
+#define STUB_RESET_SYSTEM(prefix, adjust_arg)                                  
\
+static void                                                                    
\
+prefix##_reset_system (int reset_type, efi_status_t status,                    
\
+                      unsigned long data_size, efi_char16_t *data)             
\
+{                                                                              
\
+       struct ia64_fpreg fr[6];                                                
\
+       efi_char16_t *adata = NULL;                                             
\
+                                                                               
\
+       if (data)                                                               
\
+               adata = adjust_arg(data);                                       
\
+                                                                               
\
+       ia64_save_scratch_fpregs(fr);                                           
\
+       efi_call_##prefix((efi_reset_system_t *) __va(runtime->reset_system),   
\
+                         reset_type, status, data_size, adata);                
\
+       /* should not return, but just in case... */                            
\
+       ia64_load_scratch_fpregs(fr);                                           
\
+}
+
+#define phys_ptr(arg)  ((__typeof__(arg)) ia64_tpa(arg))
+
+STUB_GET_TIME(phys, phys_ptr)
+STUB_SET_TIME(phys, phys_ptr)
+STUB_GET_WAKEUP_TIME(phys, phys_ptr)
+STUB_SET_WAKEUP_TIME(phys, phys_ptr)
+STUB_GET_VARIABLE(phys, phys_ptr)
+STUB_GET_NEXT_VARIABLE(phys, phys_ptr)
+STUB_SET_VARIABLE(phys, phys_ptr)
+STUB_GET_NEXT_HIGH_MONO_COUNT(phys, phys_ptr)
+STUB_RESET_SYSTEM(phys, phys_ptr)
+
+#define id(arg)        arg
+
+STUB_GET_TIME(virt, id)
+STUB_SET_TIME(virt, id)
+STUB_GET_WAKEUP_TIME(virt, id)
+STUB_SET_WAKEUP_TIME(virt, id)
+STUB_GET_VARIABLE(virt, id)
+STUB_GET_NEXT_VARIABLE(virt, id)
+STUB_SET_VARIABLE(virt, id)
+STUB_GET_NEXT_HIGH_MONO_COUNT(virt, id)
+STUB_RESET_SYSTEM(virt, id)
+
+void
+efi_gettimeofday (struct timespec *ts)
+{
+       efi_time_t tm;
+
+       memset(ts, 0, sizeof(ts));
+       if ((*efi.get_time)(&tm, NULL) != EFI_SUCCESS)
+               return;
+
+       ts->tv_sec = mktime(tm.year, tm.month, tm.day, tm.hour, tm.minute, 
tm.second);
+       ts->tv_nsec = tm.nanosecond;
+}
+
+static int
+is_available_memory (efi_memory_desc_t *md)
+{
+       if (!(md->attribute & EFI_MEMORY_WB))
+               return 0;
+
+       switch (md->type) {
+             case EFI_LOADER_CODE:
+             case EFI_LOADER_DATA:
+             case EFI_BOOT_SERVICES_CODE:
+             case EFI_BOOT_SERVICES_DATA:
+             case EFI_CONVENTIONAL_MEMORY:
+               return 1;
+       }
+       return 0;
+}
+
+/*
+ * Trim descriptor MD so its starts at address START_ADDR.  If the descriptor 
covers
+ * memory that is normally available to the kernel, issue a warning that some 
memory
+ * is being ignored.
+ */
+static void
+trim_bottom (efi_memory_desc_t *md, u64 start_addr)
+{
+       u64 num_skipped_pages;
+
+       if (md->phys_addr >= start_addr || !md->num_pages)
+               return;
+
+       num_skipped_pages = (start_addr - md->phys_addr) >> EFI_PAGE_SHIFT;
+       if (num_skipped_pages > md->num_pages)
+               num_skipped_pages = md->num_pages;
+
+       if (is_available_memory(md))
+               printk(KERN_NOTICE "efi.%s: ignoring %luKB of memory at 0x%lx 
due to granule hole "
+                      "at 0x%lx\n", __FUNCTION__,
+                      (num_skipped_pages << EFI_PAGE_SHIFT) >> 10,
+                      md->phys_addr, start_addr - IA64_GRANULE_SIZE);
+       /*
+        * NOTE: Don't set md->phys_addr to START_ADDR because that could cause 
the memory
+        * descriptor list to become unsorted.  In such a case, md->num_pages 
will be
+        * zero, so the Right Thing will happen.
+        */
+       md->phys_addr += num_skipped_pages << EFI_PAGE_SHIFT;
+       md->num_pages -= num_skipped_pages;
+}
+
+static void
+trim_top (efi_memory_desc_t *md, u64 end_addr)
+{
+       u64 num_dropped_pages, md_end_addr;
+
+       md_end_addr = md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT);
+
+       if (md_end_addr <= end_addr || !md->num_pages)
+               return;
+
+       num_dropped_pages = (md_end_addr - end_addr) >> EFI_PAGE_SHIFT;
+       if (num_dropped_pages > md->num_pages)
+               num_dropped_pages = md->num_pages;
+
+       if (is_available_memory(md))
+               printk(KERN_NOTICE "efi.%s: ignoring %luKB of memory at 0x%lx 
due to granule hole "
+                      "at 0x%lx\n", __FUNCTION__,
+                      (num_dropped_pages << EFI_PAGE_SHIFT) >> 10,
+                      md->phys_addr, end_addr);
+       md->num_pages -= num_dropped_pages;
+}
+
+/*
+ * Walks the EFI memory map and calls CALLBACK once for each EFI memory 
descriptor that
+ * has memory that is available for OS use.
+ */
+void
+efi_memmap_walk (efi_freemem_callback_t callback, void *arg)
+{
+       int prev_valid = 0;
+       struct range {
+               u64 start;
+               u64 end;
+       } prev, curr;
+       void *efi_map_start, *efi_map_end, *p, *q;
+       efi_memory_desc_t *md, *check_md;
+       u64 efi_desc_size, start, end, granule_addr, last_granule_addr, 
first_non_wb_addr = 0;
+       unsigned long total_mem = 0;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+
+               /* skip over non-WB memory descriptors; that's all we're 
interested in... */
+               if (!(md->attribute & EFI_MEMORY_WB))
+                       continue;
+
+#ifdef XEN
+// this works around a problem in the ski bootloader
+{
+               extern long running_on_sim;
+               if (running_on_sim && md->type != EFI_CONVENTIONAL_MEMORY)
+                       continue;
+}
+// this is a temporary hack to avoid CONFIG_VIRTUAL_MEM_MAP
+               if (md->phys_addr >= 0x100000000) continue;
+#endif
+               /*
+                * granule_addr is the base of md's first granule.
+                * [granule_addr - first_non_wb_addr) is guaranteed to
+                * be contiguous WB memory.
+                */
+               granule_addr = GRANULEROUNDDOWN(md->phys_addr);
+               first_non_wb_addr = max(first_non_wb_addr, granule_addr);
+
+               if (first_non_wb_addr < md->phys_addr) {
+                       trim_bottom(md, granule_addr + IA64_GRANULE_SIZE);
+                       granule_addr = GRANULEROUNDDOWN(md->phys_addr);
+                       first_non_wb_addr = max(first_non_wb_addr, 
granule_addr);
+               }
+
+               for (q = p; q < efi_map_end; q += efi_desc_size) {
+                       check_md = q;
+
+                       if ((check_md->attribute & EFI_MEMORY_WB) &&
+                           (check_md->phys_addr == first_non_wb_addr))
+                               first_non_wb_addr += check_md->num_pages << 
EFI_PAGE_SHIFT;
+                       else
+                               break;          /* non-WB or hole */
+               }
+
+               last_granule_addr = GRANULEROUNDDOWN(first_non_wb_addr);
+               if (last_granule_addr < md->phys_addr + (md->num_pages << 
EFI_PAGE_SHIFT))
+                       trim_top(md, last_granule_addr);
+
+               if (is_available_memory(md)) {
+                       if (md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) 
>= max_addr) {
+                               if (md->phys_addr >= max_addr)
+                                       continue;
+                               md->num_pages = (max_addr - md->phys_addr) >> 
EFI_PAGE_SHIFT;
+                               first_non_wb_addr = max_addr;
+                       }
+
+                       if (total_mem >= mem_limit)
+                               continue;
+
+                       if (total_mem + (md->num_pages << EFI_PAGE_SHIFT) > 
mem_limit) {
+                               unsigned long limit_addr = md->phys_addr;
+
+                               limit_addr += mem_limit - total_mem;
+                               limit_addr = GRANULEROUNDDOWN(limit_addr);
+
+                               if (md->phys_addr > limit_addr)
+                                       continue;
+
+                               md->num_pages = (limit_addr - md->phys_addr) >>
+                                               EFI_PAGE_SHIFT;
+                               first_non_wb_addr = max_addr = md->phys_addr +
+                                             (md->num_pages << EFI_PAGE_SHIFT);
+                       }
+                       total_mem += (md->num_pages << EFI_PAGE_SHIFT);
+
+                       if (md->num_pages == 0)
+                               continue;
+
+                       curr.start = PAGE_OFFSET + md->phys_addr;
+                       curr.end   = curr.start + (md->num_pages << 
EFI_PAGE_SHIFT);
+
+                       if (!prev_valid) {
+                               prev = curr;
+                               prev_valid = 1;
+                       } else {
+                               if (curr.start < prev.start)
+                                       printk(KERN_ERR "Oops: EFI memory table 
not ordered!\n");
+
+                               if (prev.end == curr.start) {
+                                       /* merge two consecutive memory ranges 
*/
+                                       prev.end = curr.end;
+                               } else {
+                                       start = PAGE_ALIGN(prev.start);
+                                       end = prev.end & PAGE_MASK;
+                                       if ((end > start) && (*callback)(start, 
end, arg) < 0)
+                                               return;
+                                       prev = curr;
+                               }
+                       }
+               }
+       }
+       if (prev_valid) {
+               start = PAGE_ALIGN(prev.start);
+               end = prev.end & PAGE_MASK;
+               if (end > start)
+                       (*callback)(start, end, arg);
+       }
+}
+
+/*
+ * Look for the PAL_CODE region reported by EFI and maps it using an
+ * ITR to enable safe PAL calls in virtual mode.  See IA-64 Processor
+ * Abstraction Layer chapter 11 in ADAG
+ */
+
+void *
+efi_get_pal_addr (void)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+       int pal_code_count = 0;
+       u64 vaddr, mask;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+               if (md->type != EFI_PAL_CODE)
+                       continue;
+
+               if (++pal_code_count > 1) {
+                       printk(KERN_ERR "Too many EFI Pal Code memory ranges, 
dropped @ %lx\n",
+                              md->phys_addr);
+                       continue;
+               }
+               /*
+                * The only ITLB entry in region 7 that is used is the one 
installed by
+                * __start().  That entry covers a 64MB range.
+                */
+               mask  = ~((1 << KERNEL_TR_PAGE_SHIFT) - 1);
+               vaddr = PAGE_OFFSET + md->phys_addr;
+
+               /*
+                * We must check that the PAL mapping won't overlap with the 
kernel
+                * mapping.
+                *
+                * PAL code is guaranteed to be aligned on a power of 2 between 
4k and
+                * 256KB and that only one ITR is needed to map it. This 
implies that the
+                * PAL code is always aligned on its size, i.e., the closest 
matching page
+                * size supported by the TLB. Therefore PAL code is guaranteed 
never to
+                * cross a 64MB unless it is bigger than 64MB (very unlikely!). 
 So for
+                * now the following test is enough to determine whether or not 
we need a
+                * dedicated ITR for the PAL code.
+                */
+               if ((vaddr & mask) == (KERNEL_START & mask)) {
+                       printk(KERN_INFO "%s: no need to install ITR for PAL 
code\n",
+                              __FUNCTION__);
+                       continue;
+               }
+
+               if (md->num_pages << EFI_PAGE_SHIFT > IA64_GRANULE_SIZE)
+                       panic("Woah!  PAL code size bigger than a granule!");
+
+#if EFI_DEBUG
+               mask  = ~((1 << IA64_GRANULE_SHIFT) - 1);
+
+               printk(KERN_INFO "CPU %d: mapping PAL code [0x%lx-0x%lx) into 
[0x%lx-0x%lx)\n",
+                       smp_processor_id(), md->phys_addr,
+                       md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT),
+                       vaddr & mask, (vaddr & mask) + IA64_GRANULE_SIZE);
+#endif
+               return __va(md->phys_addr);
+       }
+       printk(KERN_WARNING "%s: no PAL-code memory-descriptor found",
+              __FUNCTION__);
+       return NULL;
+}
+
+void
+efi_map_pal_code (void)
+{
+       void *pal_vaddr = efi_get_pal_addr ();
+       u64 psr;
+
+       if (!pal_vaddr)
+               return;
+
+       /*
+        * Cannot write to CRx with PSR.ic=1
+        */
+       psr = ia64_clear_ic();
+       ia64_itr(0x1, IA64_TR_PALCODE, GRANULEROUNDDOWN((unsigned long) 
pal_vaddr),
+                pte_val(pfn_pte(__pa(pal_vaddr) >> PAGE_SHIFT, PAGE_KERNEL)),
+                IA64_GRANULE_SHIFT);
+       ia64_set_psr(psr);              /* restore psr */
+       ia64_srlz_i();
+}
+
+void __init
+efi_init (void)
+{
+       void *efi_map_start, *efi_map_end;
+       efi_config_table_t *config_tables;
+       efi_char16_t *c16;
+       u64 efi_desc_size;
+       char *cp, *end, vendor[100] = "unknown";
+       extern char saved_command_line[];
+       int i;
+
+       /* it's too early to be able to use the standard kernel command line 
support... */
+       for (cp = saved_command_line; *cp; ) {
+               if (memcmp(cp, "mem=", 4) == 0) {
+                       cp += 4;
+                       mem_limit = memparse(cp, &end);
+                       if (end != cp)
+                               break;
+                       cp = end;
+               } else if (memcmp(cp, "max_addr=", 9) == 0) {
+                       cp += 9;
+                       max_addr = GRANULEROUNDDOWN(memparse(cp, &end));
+                       if (end != cp)
+                               break;
+                       cp = end;
+               } else {
+                       while (*cp != ' ' && *cp)
+                               ++cp;
+                       while (*cp == ' ')
+                               ++cp;
+               }
+       }
+       if (max_addr != ~0UL)
+               printk(KERN_INFO "Ignoring memory above %luMB\n", max_addr >> 
20);
+
+       efi.systab = __va(ia64_boot_param->efi_systab);
+
+       /*
+        * Verify the EFI Table
+        */
+       if (efi.systab == NULL)
+               panic("Woah! Can't find EFI system table.\n");
+       if (efi.systab->hdr.signature != EFI_SYSTEM_TABLE_SIGNATURE)
+               panic("Woah! EFI system table signature incorrect\n");
+       if ((efi.systab->hdr.revision ^ EFI_SYSTEM_TABLE_REVISION) >> 16 != 0)
+               printk(KERN_WARNING "Warning: EFI system table major version 
mismatch: "
+                      "got %d.%02d, expected %d.%02d\n",
+                      efi.systab->hdr.revision >> 16, efi.systab->hdr.revision 
& 0xffff,
+                      EFI_SYSTEM_TABLE_REVISION >> 16, 
EFI_SYSTEM_TABLE_REVISION & 0xffff);
+
+       config_tables = __va(efi.systab->tables);
+
+       /* Show what we know for posterity */
+       c16 = __va(efi.systab->fw_vendor);
+       if (c16) {
+               for (i = 0;i < (int) sizeof(vendor) && *c16; ++i)
+                       vendor[i] = *c16++;
+               vendor[i] = '\0';
+       }
+
+       printk(KERN_INFO "EFI v%u.%.02u by %s:",
+              efi.systab->hdr.revision >> 16, efi.systab->hdr.revision & 
0xffff, vendor);
+
+       for (i = 0; i < (int) efi.systab->nr_tables; i++) {
+               if (efi_guidcmp(config_tables[i].guid, MPS_TABLE_GUID) == 0) {
+                       efi.mps = __va(config_tables[i].table);
+                       printk(" MPS=0x%lx", config_tables[i].table);
+               } else if (efi_guidcmp(config_tables[i].guid, 
ACPI_20_TABLE_GUID) == 0) {
+                       efi.acpi20 = __va(config_tables[i].table);
+                       printk(" ACPI 2.0=0x%lx", config_tables[i].table);
+               } else if (efi_guidcmp(config_tables[i].guid, ACPI_TABLE_GUID) 
== 0) {
+                       efi.acpi = __va(config_tables[i].table);
+                       printk(" ACPI=0x%lx", config_tables[i].table);
+               } else if (efi_guidcmp(config_tables[i].guid, 
SMBIOS_TABLE_GUID) == 0) {
+                       efi.smbios = __va(config_tables[i].table);
+                       printk(" SMBIOS=0x%lx", config_tables[i].table);
+               } else if (efi_guidcmp(config_tables[i].guid, 
SAL_SYSTEM_TABLE_GUID) == 0) {
+                       efi.sal_systab = __va(config_tables[i].table);
+                       printk(" SALsystab=0x%lx", config_tables[i].table);
+               } else if (efi_guidcmp(config_tables[i].guid, HCDP_TABLE_GUID) 
== 0) {
+                       efi.hcdp = __va(config_tables[i].table);
+                       printk(" HCDP=0x%lx", config_tables[i].table);
+               }
+       }
+       printk("\n");
+
+       runtime = __va(efi.systab->runtime);
+       efi.get_time = phys_get_time;
+       efi.set_time = phys_set_time;
+       efi.get_wakeup_time = phys_get_wakeup_time;
+       efi.set_wakeup_time = phys_set_wakeup_time;
+       efi.get_variable = phys_get_variable;
+       efi.get_next_variable = phys_get_next_variable;
+       efi.set_variable = phys_set_variable;
+       efi.get_next_high_mono_count = phys_get_next_high_mono_count;
+       efi.reset_system = phys_reset_system;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+#if EFI_DEBUG
+       /* print EFI memory map: */
+       {
+               efi_memory_desc_t *md;
+               void *p;
+
+               for (i = 0, p = efi_map_start; p < efi_map_end; ++i, p += 
efi_desc_size) {
+                       md = p;
+                       printk("mem%02u: type=%u, attr=0x%lx, 
range=[0x%016lx-0x%016lx) (%luMB)\n",
+                              i, md->type, md->attribute, md->phys_addr,
+                              md->phys_addr + (md->num_pages << 
EFI_PAGE_SHIFT),
+                              md->num_pages >> (20 - EFI_PAGE_SHIFT));
+               }
+       }
+#endif
+
+       efi_map_pal_code();
+       efi_enter_virtual_mode();
+}
+
+void
+efi_enter_virtual_mode (void)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       efi_status_t status;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+               if (md->attribute & EFI_MEMORY_RUNTIME) {
+                       /*
+                        * Some descriptors have multiple bits set, so the 
order of
+                        * the tests is relevant.
+                        */
+                       if (md->attribute & EFI_MEMORY_WB) {
+                               md->virt_addr = (u64) __va(md->phys_addr);
+                       } else if (md->attribute & EFI_MEMORY_UC) {
+                               md->virt_addr = (u64) ioremap(md->phys_addr, 0);
+                       } else if (md->attribute & EFI_MEMORY_WC) {
+#if 0
+                               md->virt_addr = ia64_remap(md->phys_addr, 
(_PAGE_A | _PAGE_P
+                                                                          | 
_PAGE_D
+                                                                          | 
_PAGE_MA_WC
+                                                                          | 
_PAGE_PL_0
+                                                                          | 
_PAGE_AR_RW));
+#else
+                               printk(KERN_INFO "EFI_MEMORY_WC mapping\n");
+                               md->virt_addr = (u64) ioremap(md->phys_addr, 0);
+#endif
+                       } else if (md->attribute & EFI_MEMORY_WT) {
+#if 0
+                               md->virt_addr = ia64_remap(md->phys_addr, 
(_PAGE_A | _PAGE_P
+                                                                          | 
_PAGE_D | _PAGE_MA_WT
+                                                                          | 
_PAGE_PL_0
+                                                                          | 
_PAGE_AR_RW));
+#else
+                               printk(KERN_INFO "EFI_MEMORY_WT mapping\n");
+                               md->virt_addr = (u64) ioremap(md->phys_addr, 0);
+#endif
+                       }
+               }
+       }
+
+       status = efi_call_phys(__va(runtime->set_virtual_address_map),
+                              ia64_boot_param->efi_memmap_size,
+                              efi_desc_size, 
ia64_boot_param->efi_memdesc_version,
+                              ia64_boot_param->efi_memmap);
+       if (status != EFI_SUCCESS) {
+               printk(KERN_WARNING "warning: unable to switch EFI into virtual 
mode "
+                      "(status=%lu)\n", status);
+               return;
+       }
+
+       /*
+        * Now that EFI is in virtual mode, we call the EFI functions more 
efficiently:
+        */
+       efi.get_time = virt_get_time;
+       efi.set_time = virt_set_time;
+       efi.get_wakeup_time = virt_get_wakeup_time;
+       efi.set_wakeup_time = virt_set_wakeup_time;
+       efi.get_variable = virt_get_variable;
+       efi.get_next_variable = virt_get_next_variable;
+       efi.set_variable = virt_set_variable;
+       efi.get_next_high_mono_count = virt_get_next_high_mono_count;
+       efi.reset_system = virt_reset_system;
+}
+
+/*
+ * Walk the EFI memory map looking for the I/O port range.  There can only be 
one entry of
+ * this type, other I/O port ranges should be described via ACPI.
+ */
+u64
+efi_get_iobase (void)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+               if (md->type == EFI_MEMORY_MAPPED_IO_PORT_SPACE) {
+                       if (md->attribute & EFI_MEMORY_UC)
+                               return md->phys_addr;
+               }
+       }
+       return 0;
+}
+
+#ifdef XEN
+// variation of efi_get_iobase which returns entire memory descriptor
+efi_memory_desc_t *
+efi_get_io_md (void)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+               if (md->type == EFI_MEMORY_MAPPED_IO_PORT_SPACE) {
+                       if (md->attribute & EFI_MEMORY_UC)
+                               return md;
+               }
+       }
+       return 0;
+}
+#endif
+
+u32
+efi_mem_type (unsigned long phys_addr)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+
+               if (phys_addr - md->phys_addr < (md->num_pages << 
EFI_PAGE_SHIFT))
+                        return md->type;
+       }
+       return 0;
+}
+
+u64
+efi_mem_attributes (unsigned long phys_addr)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+
+               if (phys_addr - md->phys_addr < (md->num_pages << 
EFI_PAGE_SHIFT))
+                       return md->attribute;
+       }
+       return 0;
+}
+EXPORT_SYMBOL(efi_mem_attributes);
+
+int
+valid_phys_addr_range (unsigned long phys_addr, unsigned long *size)
+{
+       void *efi_map_start, *efi_map_end, *p;
+       efi_memory_desc_t *md;
+       u64 efi_desc_size;
+
+       efi_map_start = __va(ia64_boot_param->efi_memmap);
+       efi_map_end   = efi_map_start + ia64_boot_param->efi_memmap_size;
+       efi_desc_size = ia64_boot_param->efi_memdesc_size;
+
+       for (p = efi_map_start; p < efi_map_end; p += efi_desc_size) {
+               md = p;
+
+               if (phys_addr - md->phys_addr < (md->num_pages << 
EFI_PAGE_SHIFT)) {
+                       if (!(md->attribute & EFI_MEMORY_WB))
+                               return 0;
+
+                       if (*size > md->phys_addr + (md->num_pages << 
EFI_PAGE_SHIFT) - phys_addr)
+                               *size = md->phys_addr + (md->num_pages << 
EFI_PAGE_SHIFT) - phys_addr;
+                       return 1;
+               }
+       }
+       return 0;
+}
+
+int __init
+efi_uart_console_only(void)
+{
+       efi_status_t status;
+       char *s, name[] = "ConOut";
+       efi_guid_t guid = EFI_GLOBAL_VARIABLE_GUID;
+       efi_char16_t *utf16, name_utf16[32];
+       unsigned char data[1024];
+       unsigned long size = sizeof(data);
+       struct efi_generic_dev_path *hdr, *end_addr;
+       int uart = 0;
+
+       /* Convert to UTF-16 */
+       utf16 = name_utf16;
+       s = name;
+       while (*s)
+               *utf16++ = *s++ & 0x7f;
+       *utf16 = 0;
+
+       status = efi.get_variable(name_utf16, &guid, NULL, &size, data);
+       if (status != EFI_SUCCESS) {
+               printk(KERN_ERR "No EFI %s variable?\n", name);
+               return 0;
+       }
+
+       hdr = (struct efi_generic_dev_path *) data;
+       end_addr = (struct efi_generic_dev_path *) ((u8 *) data + size);
+       while (hdr < end_addr) {
+               if (hdr->type == EFI_DEV_MSG &&
+                   hdr->sub_type == EFI_DEV_MSG_UART)
+                       uart = 1;
+               else if (hdr->type == EFI_DEV_END_PATH ||
+                         hdr->type == EFI_DEV_END_PATH2) {
+                       if (!uart)
+                               return 0;
+                       if (hdr->sub_type == EFI_DEV_END_ENTIRE)
+                               return 1;
+                       uart = 0;
+               }
+               hdr = (struct efi_generic_dev_path *) ((u8 *) hdr + 
hdr->length);
+       }
+       printk(KERN_ERR "Malformed %s value\n", name);
+       return 0;
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/entry.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/entry.S   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1653 @@
+/*
+ * ia64/kernel/entry.S
+ *
+ * Kernel entry points.
+ *
+ * Copyright (C) 1998-2003, 2005 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999, 2002-2003
+ *     Asit Mallick <Asit.K.Mallick@xxxxxxxxx>
+ *     Don Dugger <Don.Dugger@xxxxxxxxx>
+ *     Suresh Siddha <suresh.b.siddha@xxxxxxxxx>
+ *     Fenghua Yu <fenghua.yu@xxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ */
+/*
+ * ia64_switch_to now places correct virtual mapping in in TR2 for
+ * kernel stack. This allows us to handle interrupts without changing
+ * to physical mode.
+ *
+ * Jonathan Nicklin    <nicklin@xxxxxxxxxxxxxxxxxxxxxxxx>
+ * Patrick O'Rourke    <orourke@xxxxxxxxxxxxxxxxxxxxxxxx>
+ * 11/07/2000
+ */
+/*
+ * Global (preserved) predicate usage on syscall entry/exit path:
+ *
+ *     pKStk:          See entry.h.
+ *     pUStk:          See entry.h.
+ *     pSys:           See entry.h.
+ *     pNonSys:        !pSys
+ */
+
+#include <linux/config.h>
+
+#include <asm/asmmacro.h>
+#include <asm/cache.h>
+#include <asm/errno.h>
+#include <asm/kregs.h>
+#include <asm/offsets.h>
+#include <asm/pgtable.h>
+#include <asm/percpu.h>
+#include <asm/processor.h>
+#include <asm/thread_info.h>
+#include <asm/unistd.h>
+
+#include "minstate.h"
+
+#ifndef XEN
+       /*
+        * execve() is special because in case of success, we need to
+        * setup a null register window frame.
+        */
+ENTRY(ia64_execve)
+       /*
+        * Allocate 8 input registers since ptrace() may clobber them
+        */
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc loc1=ar.pfs,8,2,4,0
+       mov loc0=rp
+       .body
+       mov out0=in0                    // filename
+       ;;                              // stop bit between alloc and call
+       mov out1=in1                    // argv
+       mov out2=in2                    // envp
+       add out3=16,sp                  // regs
+       br.call.sptk.many rp=sys_execve
+.ret0:
+#ifdef CONFIG_IA32_SUPPORT
+       /*
+        * Check if we're returning to ia32 mode. If so, we need to restore 
ia32 registers
+        * from pt_regs.
+        */
+       adds r16=PT(CR_IPSR)+16,sp
+       ;;
+       ld8 r16=[r16]
+#endif
+       cmp4.ge p6,p7=r8,r0
+       mov ar.pfs=loc1                 // restore ar.pfs
+       sxt4 r8=r8                      // return 64-bit result
+       ;;
+       stf.spill [sp]=f0
+(p6)   cmp.ne pKStk,pUStk=r0,r0        // a successful execve() lands us in 
user-mode...
+       mov rp=loc0
+(p6)   mov ar.pfs=r0                   // clear ar.pfs on success
+(p7)   br.ret.sptk.many rp
+
+       /*
+        * In theory, we'd have to zap this state only to prevent leaking of
+        * security sensitive state (e.g., if current->mm->dumpable is zero).  
However,
+        * this executes in less than 20 cycles even on Itanium, so it's not 
worth
+        * optimizing for...).
+        */
+       mov ar.unat=0;          mov ar.lc=0
+       mov r4=0;               mov f2=f0;              mov b1=r0
+       mov r5=0;               mov f3=f0;              mov b2=r0
+       mov r6=0;               mov f4=f0;              mov b3=r0
+       mov r7=0;               mov f5=f0;              mov b4=r0
+       ldf.fill f12=[sp];      mov f13=f0;             mov b5=r0
+       ldf.fill f14=[sp];      ldf.fill f15=[sp];      mov f16=f0
+       ldf.fill f17=[sp];      ldf.fill f18=[sp];      mov f19=f0
+       ldf.fill f20=[sp];      ldf.fill f21=[sp];      mov f22=f0
+       ldf.fill f23=[sp];      ldf.fill f24=[sp];      mov f25=f0
+       ldf.fill f26=[sp];      ldf.fill f27=[sp];      mov f28=f0
+       ldf.fill f29=[sp];      ldf.fill f30=[sp];      mov f31=f0
+#ifdef CONFIG_IA32_SUPPORT
+       tbit.nz p6,p0=r16, IA64_PSR_IS_BIT
+       movl loc0=ia64_ret_from_ia32_execve
+       ;;
+(p6)   mov rp=loc0
+#endif
+       br.ret.sptk.many rp
+END(ia64_execve)
+
+/*
+ * sys_clone2(u64 flags, u64 ustack_base, u64 ustack_size, u64 parent_tidptr, 
u64 child_tidptr,
+ *           u64 tls)
+ */
+GLOBAL_ENTRY(sys_clone2)
+       /*
+        * Allocate 8 input registers since ptrace() may clobber them
+        */
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc r16=ar.pfs,8,2,6,0
+       DO_SAVE_SWITCH_STACK
+       adds r2=PT(R16)+IA64_SWITCH_STACK_SIZE+16,sp
+       mov loc0=rp
+       mov loc1=r16                            // save ar.pfs across do_fork
+       .body
+       mov out1=in1
+       mov out3=in2
+       tbit.nz p6,p0=in0,CLONE_SETTLS_BIT
+       mov out4=in3    // parent_tidptr: valid only w/CLONE_PARENT_SETTID
+       ;;
+(p6)   st8 [r2]=in5                            // store TLS in r16 for 
copy_thread()
+       mov out5=in4    // child_tidptr:  valid only w/CLONE_CHILD_SETTID or 
CLONE_CHILD_CLEARTID
+       adds out2=IA64_SWITCH_STACK_SIZE+16,sp  // out2 = &regs
+       mov out0=in0                            // out0 = clone_flags
+       br.call.sptk.many rp=do_fork
+.ret1: .restore sp
+       adds sp=IA64_SWITCH_STACK_SIZE,sp       // pop the switch stack
+       mov ar.pfs=loc1
+       mov rp=loc0
+       br.ret.sptk.many rp
+END(sys_clone2)
+
+/*
+ * sys_clone(u64 flags, u64 ustack_base, u64 parent_tidptr, u64 child_tidptr, 
u64 tls)
+ *     Deprecated.  Use sys_clone2() instead.
+ */
+GLOBAL_ENTRY(sys_clone)
+       /*
+        * Allocate 8 input registers since ptrace() may clobber them
+        */
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc r16=ar.pfs,8,2,6,0
+       DO_SAVE_SWITCH_STACK
+       adds r2=PT(R16)+IA64_SWITCH_STACK_SIZE+16,sp
+       mov loc0=rp
+       mov loc1=r16                            // save ar.pfs across do_fork
+       .body
+       mov out1=in1
+       mov out3=16                             // stacksize (compensates for 
16-byte scratch area)
+       tbit.nz p6,p0=in0,CLONE_SETTLS_BIT
+       mov out4=in2    // parent_tidptr: valid only w/CLONE_PARENT_SETTID
+       ;;
+(p6)   st8 [r2]=in4                            // store TLS in r13 (tp)
+       mov out5=in3    // child_tidptr:  valid only w/CLONE_CHILD_SETTID or 
CLONE_CHILD_CLEARTID
+       adds out2=IA64_SWITCH_STACK_SIZE+16,sp  // out2 = &regs
+       mov out0=in0                            // out0 = clone_flags
+       br.call.sptk.many rp=do_fork
+.ret2: .restore sp
+       adds sp=IA64_SWITCH_STACK_SIZE,sp       // pop the switch stack
+       mov ar.pfs=loc1
+       mov rp=loc0
+       br.ret.sptk.many rp
+END(sys_clone)
+#endif /* !XEN */
+
+/*
+ * prev_task <- ia64_switch_to(struct task_struct *next)
+ *     With Ingo's new scheduler, interrupts are disabled when this routine 
gets
+ *     called.  The code starting at .map relies on this.  The rest of the code
+ *     doesn't care about the interrupt masking status.
+ */
+GLOBAL_ENTRY(ia64_switch_to)
+       .prologue
+       alloc r16=ar.pfs,1,0,0,0
+       DO_SAVE_SWITCH_STACK
+       .body
+
+       adds r22=IA64_TASK_THREAD_KSP_OFFSET,r13
+       movl r25=init_task
+       mov r27=IA64_KR(CURRENT_STACK)
+       adds r21=IA64_TASK_THREAD_KSP_OFFSET,in0
+#ifdef XEN
+       dep r20=0,in0,60,4              // physical address of "next"
+#else
+       dep r20=0,in0,61,3              // physical address of "next"
+#endif
+       ;;
+       st8 [r22]=sp                    // save kernel stack pointer of old task
+       shr.u r26=r20,IA64_GRANULE_SHIFT
+       cmp.eq p7,p6=r25,in0
+       ;;
+       /*
+        * If we've already mapped this task's page, we can skip doing it again.
+        */
+(p6)   cmp.eq p7,p6=r26,r27
+(p6)   br.cond.dpnt .map
+       ;;
+.done:
+(p6)   ssm psr.ic                      // if we had to map, reenable the 
psr.ic bit FIRST!!!
+       ;;
+(p6)   srlz.d
+       ld8 sp=[r21]                    // load kernel stack pointer of new task
+       mov IA64_KR(CURRENT)=in0        // update "current" application register
+       mov r8=r13                      // return pointer to previously running 
task
+       mov r13=in0                     // set "current" pointer
+       ;;
+       DO_LOAD_SWITCH_STACK
+
+#ifdef CONFIG_SMP
+       sync.i                          // ensure "fc"s done by this CPU are 
visible on other CPUs
+#endif
+       br.ret.sptk.many rp             // boogie on out in new context
+
+.map:
+#ifdef XEN
+       // avoid overlapping with kernel TR
+       movl r25=KERNEL_START
+       dep  r23=0,in0,0,KERNEL_TR_PAGE_SHIFT
+       ;;
+       cmp.eq p7,p0=r25,r23
+       ;;
+(p7)   mov IA64_KR(CURRENT_STACK)=r26  // remember last page we mapped...
+(p7)   br.cond.sptk .done
+#endif
+       rsm psr.ic                      // interrupts (psr.i) are already 
disabled here
+       movl r25=PAGE_KERNEL
+       ;;
+       srlz.d
+       or r23=r25,r20                  // construct PA | page properties
+       mov r25=IA64_GRANULE_SHIFT<<2
+       ;;
+       mov cr.itir=r25
+       mov cr.ifa=in0                  // VA of next task...
+       ;;
+       mov r25=IA64_TR_CURRENT_STACK
+       mov IA64_KR(CURRENT_STACK)=r26  // remember last page we mapped...
+       ;;
+       itr.d dtr[r25]=r23              // wire in new mapping...
+       br.cond.sptk .done
+END(ia64_switch_to)
+
+/*
+ * Note that interrupts are enabled during save_switch_stack and 
load_switch_stack.  This
+ * means that we may get an interrupt with "sp" pointing to the new kernel 
stack while
+ * ar.bspstore is still pointing to the old kernel backing store area.  Since 
ar.rsc,
+ * ar.rnat, ar.bsp, and ar.bspstore are all preserved by interrupts, this is 
not a
+ * problem.  Also, we don't need to specify unwind information for preserved 
registers
+ * that are not modified in save_switch_stack as the right unwind information 
is already
+ * specified at the call-site of save_switch_stack.
+ */
+
+/*
+ * save_switch_stack:
+ *     - r16 holds ar.pfs
+ *     - b7 holds address to return to
+ *     - rp (b0) holds return address to save
+ */
+GLOBAL_ENTRY(save_switch_stack)
+       .prologue
+       .altrp b7
+       flushrs                 // flush dirty regs to backing store (must be 
first in insn group)
+       .save @priunat,r17
+       mov r17=ar.unat         // preserve caller's
+       .body
+#ifdef CONFIG_ITANIUM
+       adds r2=16+128,sp
+       adds r3=16+64,sp
+       adds r14=SW(R4)+16,sp
+       ;;
+       st8.spill [r14]=r4,16           // spill r4
+       lfetch.fault.excl.nt1 [r3],128
+       ;;
+       lfetch.fault.excl.nt1 [r2],128
+       lfetch.fault.excl.nt1 [r3],128
+       ;;
+       lfetch.fault.excl [r2]
+       lfetch.fault.excl [r3]
+       adds r15=SW(R5)+16,sp
+#else
+       add r2=16+3*128,sp
+       add r3=16,sp
+       add r14=SW(R4)+16,sp
+       ;;
+       st8.spill [r14]=r4,SW(R6)-SW(R4)        // spill r4 and prefetch offset 
0x1c0
+       lfetch.fault.excl.nt1 [r3],128  //              prefetch offset 0x010
+       ;;
+       lfetch.fault.excl.nt1 [r3],128  //              prefetch offset 0x090
+       lfetch.fault.excl.nt1 [r2],128  //              prefetch offset 0x190
+       ;;
+       lfetch.fault.excl.nt1 [r3]      //              prefetch offset 0x110
+       lfetch.fault.excl.nt1 [r2]      //              prefetch offset 0x210
+       adds r15=SW(R5)+16,sp
+#endif
+       ;;
+       st8.spill [r15]=r5,SW(R7)-SW(R5)        // spill r5
+       mov.m ar.rsc=0                  // put RSE in mode: enforced lazy, 
little endian, pl 0
+       add r2=SW(F2)+16,sp             // r2 = &sw->f2
+       ;;
+       st8.spill [r14]=r6,SW(B0)-SW(R6)        // spill r6
+       mov.m r18=ar.fpsr               // preserve fpsr
+       add r3=SW(F3)+16,sp             // r3 = &sw->f3
+       ;;
+       stf.spill [r2]=f2,32
+       mov.m r19=ar.rnat
+       mov r21=b0
+
+       stf.spill [r3]=f3,32
+       st8.spill [r15]=r7,SW(B2)-SW(R7)        // spill r7
+       mov r22=b1
+       ;;
+       // since we're done with the spills, read and save ar.unat:
+       mov.m r29=ar.unat
+       mov.m r20=ar.bspstore
+       mov r23=b2
+       stf.spill [r2]=f4,32
+       stf.spill [r3]=f5,32
+       mov r24=b3
+       ;;
+       st8 [r14]=r21,SW(B1)-SW(B0)             // save b0
+       st8 [r15]=r23,SW(B3)-SW(B2)             // save b2
+       mov r25=b4
+       mov r26=b5
+       ;;
+       st8 [r14]=r22,SW(B4)-SW(B1)             // save b1
+       st8 [r15]=r24,SW(AR_PFS)-SW(B3)         // save b3
+       mov r21=ar.lc           // I-unit
+       stf.spill [r2]=f12,32
+       stf.spill [r3]=f13,32
+       ;;
+       st8 [r14]=r25,SW(B5)-SW(B4)             // save b4
+       st8 [r15]=r16,SW(AR_LC)-SW(AR_PFS)      // save ar.pfs
+       stf.spill [r2]=f14,32
+       stf.spill [r3]=f15,32
+       ;;
+       st8 [r14]=r26                           // save b5
+       st8 [r15]=r21                           // save ar.lc
+       stf.spill [r2]=f16,32
+       stf.spill [r3]=f17,32
+       ;;
+       stf.spill [r2]=f18,32
+       stf.spill [r3]=f19,32
+       ;;
+       stf.spill [r2]=f20,32
+       stf.spill [r3]=f21,32
+       ;;
+       stf.spill [r2]=f22,32
+       stf.spill [r3]=f23,32
+       ;;
+       stf.spill [r2]=f24,32
+       stf.spill [r3]=f25,32
+       ;;
+       stf.spill [r2]=f26,32
+       stf.spill [r3]=f27,32
+       ;;
+       stf.spill [r2]=f28,32
+       stf.spill [r3]=f29,32
+       ;;
+       stf.spill [r2]=f30,SW(AR_UNAT)-SW(F30)
+       stf.spill [r3]=f31,SW(PR)-SW(F31)
+       add r14=SW(CALLER_UNAT)+16,sp
+       ;;
+       st8 [r2]=r29,SW(AR_RNAT)-SW(AR_UNAT)    // save ar.unat
+       st8 [r14]=r17,SW(AR_FPSR)-SW(CALLER_UNAT) // save caller_unat
+       mov r21=pr
+       ;;
+       st8 [r2]=r19,SW(AR_BSPSTORE)-SW(AR_RNAT) // save ar.rnat
+       st8 [r3]=r21                            // save predicate registers
+       ;;
+       st8 [r2]=r20                            // save ar.bspstore
+       st8 [r14]=r18                           // save fpsr
+       mov ar.rsc=3            // put RSE back into eager mode, pl 0
+       br.cond.sptk.many b7
+END(save_switch_stack)
+
+/*
+ * load_switch_stack:
+ *     - "invala" MUST be done at call site (normally in DO_LOAD_SWITCH_STACK)
+ *     - b7 holds address to return to
+ *     - must not touch r8-r11
+ */
+#ifdef XEN
+GLOBAL_ENTRY(load_switch_stack)
+#else
+ENTRY(load_switch_stack)
+#endif
+       .prologue
+       .altrp b7
+
+       .body
+       lfetch.fault.nt1 [sp]
+       adds r2=SW(AR_BSPSTORE)+16,sp
+       adds r3=SW(AR_UNAT)+16,sp
+       mov ar.rsc=0                                            // put RSE into 
enforced lazy mode
+       adds r14=SW(CALLER_UNAT)+16,sp
+       adds r15=SW(AR_FPSR)+16,sp
+       ;;
+       ld8 r27=[r2],(SW(B0)-SW(AR_BSPSTORE))   // bspstore
+       ld8 r29=[r3],(SW(B1)-SW(AR_UNAT))       // unat
+       ;;
+       ld8 r21=[r2],16         // restore b0
+       ld8 r22=[r3],16         // restore b1
+       ;;
+       ld8 r23=[r2],16         // restore b2
+       ld8 r24=[r3],16         // restore b3
+       ;;
+       ld8 r25=[r2],16         // restore b4
+       ld8 r26=[r3],16         // restore b5
+       ;;
+       ld8 r16=[r2],(SW(PR)-SW(AR_PFS))        // ar.pfs
+       ld8 r17=[r3],(SW(AR_RNAT)-SW(AR_LC))    // ar.lc
+       ;;
+       ld8 r28=[r2]            // restore pr
+       ld8 r30=[r3]            // restore rnat
+       ;;
+       ld8 r18=[r14],16        // restore caller's unat
+       ld8 r19=[r15],24        // restore fpsr
+       ;;
+       ldf.fill f2=[r14],32
+       ldf.fill f3=[r15],32
+       ;;
+       ldf.fill f4=[r14],32
+       ldf.fill f5=[r15],32
+       ;;
+       ldf.fill f12=[r14],32
+       ldf.fill f13=[r15],32
+       ;;
+       ldf.fill f14=[r14],32
+       ldf.fill f15=[r15],32
+       ;;
+       ldf.fill f16=[r14],32
+       ldf.fill f17=[r15],32
+       ;;
+       ldf.fill f18=[r14],32
+       ldf.fill f19=[r15],32
+       mov b0=r21
+       ;;
+       ldf.fill f20=[r14],32
+       ldf.fill f21=[r15],32
+       mov b1=r22
+       ;;
+       ldf.fill f22=[r14],32
+       ldf.fill f23=[r15],32
+       mov b2=r23
+       ;;
+       mov ar.bspstore=r27
+       mov ar.unat=r29         // establish unat holding the NaT bits for r4-r7
+       mov b3=r24
+       ;;
+       ldf.fill f24=[r14],32
+       ldf.fill f25=[r15],32
+       mov b4=r25
+       ;;
+       ldf.fill f26=[r14],32
+       ldf.fill f27=[r15],32
+       mov b5=r26
+       ;;
+       ldf.fill f28=[r14],32
+       ldf.fill f29=[r15],32
+       mov ar.pfs=r16
+       ;;
+       ldf.fill f30=[r14],32
+       ldf.fill f31=[r15],24
+       mov ar.lc=r17
+       ;;
+       ld8.fill r4=[r14],16
+       ld8.fill r5=[r15],16
+       mov pr=r28,-1
+       ;;
+       ld8.fill r6=[r14],16
+       ld8.fill r7=[r15],16
+
+       mov ar.unat=r18                         // restore caller's unat
+       mov ar.rnat=r30                         // must restore after bspstore 
but before rsc!
+       mov ar.fpsr=r19                         // restore fpsr
+       mov ar.rsc=3                            // put RSE back into eager 
mode, pl 0
+       br.cond.sptk.many b7
+END(load_switch_stack)
+
+#ifndef XEN
+GLOBAL_ENTRY(__ia64_syscall)
+       .regstk 6,0,0,0
+       mov r15=in5                             // put syscall number in place
+       break __BREAK_SYSCALL
+       movl r2=errno
+       cmp.eq p6,p7=-1,r10
+       ;;
+(p6)   st4 [r2]=r8
+(p6)   mov r8=-1
+       br.ret.sptk.many rp
+END(__ia64_syscall)
+
+GLOBAL_ENTRY(execve)
+       mov r15=__NR_execve                     // put syscall number in place
+       break __BREAK_SYSCALL
+       br.ret.sptk.many rp
+END(execve)
+
+GLOBAL_ENTRY(clone)
+       mov r15=__NR_clone                      // put syscall number in place
+       break __BREAK_SYSCALL
+       br.ret.sptk.many rp
+END(clone)
+
+       /*
+        * Invoke a system call, but do some tracing before and after the call.
+        * We MUST preserve the current register frame throughout this routine
+        * because some system calls (such as ia64_execve) directly
+        * manipulate ar.pfs.
+        */
+GLOBAL_ENTRY(ia64_trace_syscall)
+       PT_REGS_UNWIND_INFO(0)
+       /*
+        * We need to preserve the scratch registers f6-f11 in case the system
+        * call is sigreturn.
+        */
+       adds r16=PT(F6)+16,sp
+       adds r17=PT(F7)+16,sp
+       ;;
+       stf.spill [r16]=f6,32
+       stf.spill [r17]=f7,32
+       ;;
+       stf.spill [r16]=f8,32
+       stf.spill [r17]=f9,32
+       ;;
+       stf.spill [r16]=f10
+       stf.spill [r17]=f11
+       br.call.sptk.many rp=syscall_trace_enter // give parent a chance to 
catch syscall args
+       adds r16=PT(F6)+16,sp
+       adds r17=PT(F7)+16,sp
+       ;;
+       ldf.fill f6=[r16],32
+       ldf.fill f7=[r17],32
+       ;;
+       ldf.fill f8=[r16],32
+       ldf.fill f9=[r17],32
+       ;;
+       ldf.fill f10=[r16]
+       ldf.fill f11=[r17]
+       // the syscall number may have changed, so re-load it and re-calculate 
the
+       // syscall entry-point:
+       adds r15=PT(R15)+16,sp                  // r15 = &pt_regs.r15 (syscall 
#)
+       ;;
+       ld8 r15=[r15]
+       mov r3=NR_syscalls - 1
+       ;;
+       adds r15=-1024,r15
+       movl r16=sys_call_table
+       ;;
+       shladd r20=r15,3,r16                    // r20 = sys_call_table + 
8*(syscall-1024)
+       cmp.leu p6,p7=r15,r3
+       ;;
+(p6)   ld8 r20=[r20]                           // load address of syscall 
entry point
+(p7)   movl r20=sys_ni_syscall
+       ;;
+       mov b6=r20
+       br.call.sptk.many rp=b6                 // do the syscall
+.strace_check_retval:
+       cmp.lt p6,p0=r8,r0                      // syscall failed?
+       adds r2=PT(R8)+16,sp                    // r2 = &pt_regs.r8
+       adds r3=PT(R10)+16,sp                   // r3 = &pt_regs.r10
+       mov r10=0
+(p6)   br.cond.sptk strace_error               // syscall failed ->
+       ;;                                      // avoid RAW on r10
+.strace_save_retval:
+.mem.offset 0,0; st8.spill [r2]=r8             // store return value in slot 
for r8
+.mem.offset 8,0; st8.spill [r3]=r10            // clear error indication in 
slot for r10
+       br.call.sptk.many rp=syscall_trace_leave // give parent a chance to 
catch return value
+.ret3: br.cond.sptk .work_pending_syscall_end
+
+strace_error:
+       ld8 r3=[r2]                             // load pt_regs.r8
+       sub r9=0,r8                             // negate return value to get 
errno value
+       ;;
+       cmp.ne p6,p0=r3,r0                      // is pt_regs.r8!=0?
+       adds r3=16,r2                           // r3=&pt_regs.r10
+       ;;
+(p6)   mov r10=-1
+(p6)   mov r8=r9
+       br.cond.sptk .strace_save_retval
+END(ia64_trace_syscall)
+
+       /*
+        * When traced and returning from sigreturn, we invoke syscall_trace 
but then
+        * go straight to ia64_leave_kernel rather than ia64_leave_syscall.
+        */
+GLOBAL_ENTRY(ia64_strace_leave_kernel)
+       PT_REGS_UNWIND_INFO(0)
+{      /*
+        * Some versions of gas generate bad unwind info if the first 
instruction of a
+        * procedure doesn't go into the first slot of a bundle.  This is a 
workaround.
+        */
+       nop.m 0
+       nop.i 0
+       br.call.sptk.many rp=syscall_trace_leave // give parent a chance to 
catch return value
+}
+.ret4: br.cond.sptk ia64_leave_kernel
+END(ia64_strace_leave_kernel)
+#endif
+
+GLOBAL_ENTRY(ia64_ret_from_clone)
+       PT_REGS_UNWIND_INFO(0)
+{      /*
+        * Some versions of gas generate bad unwind info if the first 
instruction of a
+        * procedure doesn't go into the first slot of a bundle.  This is a 
workaround.
+        */
+       nop.m 0
+       nop.i 0
+       /*
+        * We need to call schedule_tail() to complete the scheduling process.
+        * Called by ia64_switch_to() after do_fork()->copy_thread().  r8 
contains the
+        * address of the previously executing task.
+        */
+       br.call.sptk.many rp=ia64_invoke_schedule_tail
+}
+#ifdef XEN
+       // new domains are cloned but not exec'ed so switch to user mode here
+       cmp.ne pKStk,pUStk=r0,r0
+#ifdef CONFIG_VTI
+       br.cond.spnt ia64_leave_hypervisor
+#else // CONFIG_VTI
+       br.cond.spnt ia64_leave_kernel
+#endif // CONFIG_VTI
+#else
+.ret8:
+       adds r2=TI_FLAGS+IA64_TASK_SIZE,r13
+       ;;
+       ld4 r2=[r2]
+       ;;
+       mov r8=0
+       and r2=_TIF_SYSCALL_TRACEAUDIT,r2
+       ;;
+       cmp.ne p6,p0=r2,r0
+(p6)   br.cond.spnt .strace_check_retval
+#endif
+       ;;                                      // added stop bits to prevent 
r8 dependency
+END(ia64_ret_from_clone)
+       // fall through
+GLOBAL_ENTRY(ia64_ret_from_syscall)
+       PT_REGS_UNWIND_INFO(0)
+       cmp.ge p6,p7=r8,r0                      // syscall executed 
successfully?
+       adds r2=PT(R8)+16,sp                    // r2 = &pt_regs.r8
+       mov r10=r0                              // clear error indication in r10
+(p7)   br.cond.spnt handle_syscall_error       // handle potential syscall 
failure
+END(ia64_ret_from_syscall)
+       // fall through
+/*
+ * ia64_leave_syscall(): Same as ia64_leave_kernel, except that it doesn't
+ *     need to switch to bank 0 and doesn't restore the scratch registers.
+ *     To avoid leaking kernel bits, the scratch registers are set to
+ *     the following known-to-be-safe values:
+ *
+ *               r1: restored (global pointer)
+ *               r2: cleared
+ *               r3: 1 (when returning to user-level)
+ *           r8-r11: restored (syscall return value(s))
+ *              r12: restored (user-level stack pointer)
+ *              r13: restored (user-level thread pointer)
+ *              r14: cleared
+ *              r15: restored (syscall #)
+ *          r16-r17: cleared
+ *              r18: user-level b6
+ *              r19: cleared
+ *              r20: user-level ar.fpsr
+ *              r21: user-level b0
+ *              r22: cleared
+ *              r23: user-level ar.bspstore
+ *              r24: user-level ar.rnat
+ *              r25: user-level ar.unat
+ *              r26: user-level ar.pfs
+ *              r27: user-level ar.rsc
+ *              r28: user-level ip
+ *              r29: user-level psr
+ *              r30: user-level cfm
+ *              r31: user-level pr
+ *           f6-f11: cleared
+ *               pr: restored (user-level pr)
+ *               b0: restored (user-level rp)
+ *               b6: restored
+ *               b7: cleared
+ *          ar.unat: restored (user-level ar.unat)
+ *           ar.pfs: restored (user-level ar.pfs)
+ *           ar.rsc: restored (user-level ar.rsc)
+ *          ar.rnat: restored (user-level ar.rnat)
+ *      ar.bspstore: restored (user-level ar.bspstore)
+ *          ar.fpsr: restored (user-level ar.fpsr)
+ *           ar.ccv: cleared
+ *           ar.csd: cleared
+ *           ar.ssd: cleared
+ */
+ENTRY(ia64_leave_syscall)
+       PT_REGS_UNWIND_INFO(0)
+       /*
+        * work.need_resched etc. mustn't get changed by this CPU before it 
returns to
+        * user- or fsys-mode, hence we disable interrupts early on.
+        *
+        * p6 controls whether current_thread_info()->flags needs to be check 
for
+        * extra work.  We always check for extra work when returning to 
user-level.
+        * With CONFIG_PREEMPT, we also check for extra work when the 
preempt_count
+        * is 0.  After extra work processing has been completed, execution
+        * resumes at .work_processed_syscall with p6 set to 1 if the 
extra-work-check
+        * needs to be redone.
+        */
+#ifdef CONFIG_PREEMPT
+       rsm psr.i                               // disable interrupts
+       cmp.eq pLvSys,p0=r0,r0                  // pLvSys=1: leave from syscall
+(pKStk) adds r20=TI_PRE_COUNT+IA64_TASK_SIZE,r13
+       ;;
+       .pred.rel.mutex pUStk,pKStk
+(pKStk) ld4 r21=[r20]                  // r21 <- preempt_count
+(pUStk)        mov r21=0                       // r21 <- 0
+       ;;
+       cmp.eq p6,p0=r21,r0             // p6 <- pUStk || (preempt_count == 0)
+#else /* !CONFIG_PREEMPT */
+(pUStk)        rsm psr.i
+       cmp.eq pLvSys,p0=r0,r0          // pLvSys=1: leave from syscall
+(pUStk)        cmp.eq.unc p6,p0=r0,r0          // p6 <- pUStk
+#endif
+.work_processed_syscall:
+       adds r2=PT(LOADRS)+16,r12
+       adds r3=PT(AR_BSPSTORE)+16,r12
+#ifdef XEN
+       ;;
+#else
+       adds r18=TI_FLAGS+IA64_TASK_SIZE,r13
+       ;;
+(p6)   ld4 r31=[r18]                           // load 
current_thread_info()->flags
+#endif
+       ld8 r19=[r2],PT(B6)-PT(LOADRS)          // load ar.rsc value for 
"loadrs"
+       mov b7=r0               // clear b7
+       ;;
+       ld8 r23=[r3],PT(R11)-PT(AR_BSPSTORE)    // load ar.bspstore (may be 
garbage)
+       ld8 r18=[r2],PT(R9)-PT(B6)              // load b6
+#ifndef XEN
+(p6)   and r15=TIF_WORK_MASK,r31               // any work other than 
TIF_SYSCALL_TRACE?
+#endif
+       ;;
+       mov r16=ar.bsp                          // M2  get existing backing 
store pointer
+#ifndef XEN
+(p6)   cmp4.ne.unc p6,p0=r15, r0               // any special work pending?
+(p6)   br.cond.spnt .work_pending_syscall
+#endif
+       ;;
+       // start restoring the state saved on the kernel stack (struct pt_regs):
+       ld8 r9=[r2],PT(CR_IPSR)-PT(R9)
+       ld8 r11=[r3],PT(CR_IIP)-PT(R11)
+       mov f6=f0               // clear f6
+       ;;
+       invala                  // M0|1 invalidate ALAT
+       rsm psr.i | psr.ic      // M2 initiate turning off of interrupt and 
interruption collection
+       mov f9=f0               // clear f9
+
+       ld8 r29=[r2],16         // load cr.ipsr
+       ld8 r28=[r3],16                 // load cr.iip
+       mov f8=f0               // clear f8
+       ;;
+       ld8 r30=[r2],16         // M0|1 load cr.ifs
+       mov.m ar.ssd=r0         // M2 clear ar.ssd
+       cmp.eq p9,p0=r0,r0      // set p9 to indicate that we should restore 
cr.ifs
+       ;;
+       ld8 r25=[r3],16         // M0|1 load ar.unat
+       mov.m ar.csd=r0         // M2 clear ar.csd
+       mov r22=r0              // clear r22
+       ;;
+       ld8 r26=[r2],PT(B0)-PT(AR_PFS)  // M0|1 load ar.pfs
+(pKStk)        mov r22=psr             // M2 read PSR now that interrupts are 
disabled
+       mov f10=f0              // clear f10
+       ;;
+       ld8 r21=[r2],PT(AR_RNAT)-PT(B0) // load b0
+       ld8 r27=[r3],PT(PR)-PT(AR_RSC)  // load ar.rsc
+       mov f11=f0              // clear f11
+       ;;
+       ld8 r24=[r2],PT(AR_FPSR)-PT(AR_RNAT)    // load ar.rnat (may be garbage)
+       ld8 r31=[r3],PT(R1)-PT(PR)              // load predicates
+(pUStk) add r14=IA64_TASK_THREAD_ON_USTACK_OFFSET,r13
+       ;;
+       ld8 r20=[r2],PT(R12)-PT(AR_FPSR)        // load ar.fpsr
+       ld8.fill r1=[r3],16     // load r1
+(pUStk) mov r17=1
+       ;;
+       srlz.d                  // M0  ensure interruption collection is off
+       ld8.fill r13=[r3],16
+       mov f7=f0               // clear f7
+       ;;
+       ld8.fill r12=[r2]       // restore r12 (sp)
+       ld8.fill r15=[r3]       // restore r15
+#ifdef XEN
+       movl r3=THIS_CPU(ia64_phys_stacked_size_p8)
+#else
+       addl r3=THIS_CPU(ia64_phys_stacked_size_p8),r0
+#endif
+       ;;
+(pUStk)        ld4 r3=[r3]             // r3 = cpu_data->phys_stacked_size_p8
+(pUStk) st1 [r14]=r17
+       mov b6=r18              // I0  restore b6
+       ;;
+       mov r14=r0              // clear r14
+       shr.u r18=r19,16        // I0|1 get byte size of existing "dirty" 
partition
+(pKStk) br.cond.dpnt.many skip_rbs_switch
+
+       mov.m ar.ccv=r0         // clear ar.ccv
+(pNonSys) br.cond.dpnt.many dont_preserve_current_frame
+       br.cond.sptk.many rbs_switch
+END(ia64_leave_syscall)
+
+#ifdef CONFIG_IA32_SUPPORT
+GLOBAL_ENTRY(ia64_ret_from_ia32_execve)
+       PT_REGS_UNWIND_INFO(0)
+       adds r2=PT(R8)+16,sp                    // r2 = &pt_regs.r8
+       adds r3=PT(R10)+16,sp                   // r3 = &pt_regs.r10
+       ;;
+       .mem.offset 0,0
+       st8.spill [r2]=r8       // store return value in slot for r8 and set 
unat bit
+       .mem.offset 8,0
+       st8.spill [r3]=r0       // clear error indication in slot for r10 and 
set unat bit
+END(ia64_ret_from_ia32_execve_syscall)
+       // fall through
+#endif /* CONFIG_IA32_SUPPORT */
+GLOBAL_ENTRY(ia64_leave_kernel)
+       PT_REGS_UNWIND_INFO(0)
+       /*
+        * work.need_resched etc. mustn't get changed by this CPU before it 
returns to
+        * user- or fsys-mode, hence we disable interrupts early on.
+        *
+        * p6 controls whether current_thread_info()->flags needs to be check 
for
+        * extra work.  We always check for extra work when returning to 
user-level.
+        * With CONFIG_PREEMPT, we also check for extra work when the 
preempt_count
+        * is 0.  After extra work processing has been completed, execution
+        * resumes at .work_processed_syscall with p6 set to 1 if the 
extra-work-check
+        * needs to be redone.
+        */
+#ifdef CONFIG_PREEMPT
+       rsm psr.i                               // disable interrupts
+       cmp.eq p0,pLvSys=r0,r0                  // pLvSys=0: leave from kernel
+(pKStk)        adds r20=TI_PRE_COUNT+IA64_TASK_SIZE,r13
+       ;;
+       .pred.rel.mutex pUStk,pKStk
+(pKStk)        ld4 r21=[r20]                   // r21 <- preempt_count
+(pUStk)        mov r21=0                       // r21 <- 0
+       ;;
+       cmp.eq p6,p0=r21,r0             // p6 <- pUStk || (preempt_count == 0)
+#else
+(pUStk)        rsm psr.i
+       cmp.eq p0,pLvSys=r0,r0          // pLvSys=0: leave from kernel
+(pUStk)        cmp.eq.unc p6,p0=r0,r0          // p6 <- pUStk
+#endif
+.work_processed_kernel:
+#ifdef XEN
+       alloc loc0=ar.pfs,0,1,1,0
+       adds out0=16,r12
+       ;;
+(p6)   br.call.sptk.many b0=deliver_pending_interrupt
+       mov ar.pfs=loc0
+       mov r31=r0
+#else
+       adds r17=TI_FLAGS+IA64_TASK_SIZE,r13
+       ;;
+(p6)   ld4 r31=[r17]                           // load 
current_thread_info()->flags
+#endif
+       adds r21=PT(PR)+16,r12
+       ;;
+
+       lfetch [r21],PT(CR_IPSR)-PT(PR)
+       adds r2=PT(B6)+16,r12
+       adds r3=PT(R16)+16,r12
+       ;;
+       lfetch [r21]
+       ld8 r28=[r2],8          // load b6
+       adds r29=PT(R24)+16,r12
+
+       ld8.fill r16=[r3]
+       adds r30=PT(AR_CCV)+16,r12
+(p6)   and r19=TIF_WORK_MASK,r31               // any work other than 
TIF_SYSCALL_TRACE?
+       ;;
+       adds r3=PT(AR_CSD)-PT(R16),r3
+       ld8.fill r24=[r29]
+       ld8 r15=[r30]           // load ar.ccv
+(p6)   cmp4.ne.unc p6,p0=r19, r0               // any special work pending?
+       ;;
+       ld8 r29=[r2],16         // load b7
+       ld8 r30=[r3],16         // load ar.csd
+#ifndef XEN
+(p6)   br.cond.spnt .work_pending
+#endif
+       ;;
+       ld8 r31=[r2],16         // load ar.ssd
+       ld8.fill r8=[r3],16
+       ;;
+       ld8.fill r9=[r2],16
+       ld8.fill r10=[r3],PT(R17)-PT(R10)
+       ;;
+       ld8.fill r11=[r2],PT(R18)-PT(R11)
+       ld8.fill r17=[r3],16
+       ;;
+       ld8.fill r18=[r2],16
+       ld8.fill r19=[r3],16
+       ;;
+       ld8.fill r20=[r2],16
+       ld8.fill r21=[r3],16
+       mov ar.csd=r30
+       mov ar.ssd=r31
+       ;;
+       rsm psr.i | psr.ic      // initiate turning off of interrupt and 
interruption collection
+       invala                  // invalidate ALAT
+       ;;
+       ld8.fill r22=[r2],24
+       ld8.fill r23=[r3],24
+       mov b6=r28
+       ;;
+       ld8.fill r25=[r2],16
+       ld8.fill r26=[r3],16
+       mov b7=r29
+       ;;
+       ld8.fill r27=[r2],16
+       ld8.fill r28=[r3],16
+       ;;
+       ld8.fill r29=[r2],16
+       ld8.fill r30=[r3],24
+       ;;
+       ld8.fill r31=[r2],PT(F9)-PT(R31)
+       adds r3=PT(F10)-PT(F6),r3
+       ;;
+       ldf.fill f9=[r2],PT(F6)-PT(F9)
+       ldf.fill f10=[r3],PT(F8)-PT(F10)
+       ;;
+       ldf.fill f6=[r2],PT(F7)-PT(F6)
+       ;;
+       ldf.fill f7=[r2],PT(F11)-PT(F7)
+       ldf.fill f8=[r3],32
+       ;;
+       srlz.i                  // ensure interruption collection is off
+       mov ar.ccv=r15
+       ;;
+       ldf.fill f11=[r2]
+       bsw.0                   // switch back to bank 0 (no stop bit required 
beforehand...)
+       ;;
+(pUStk)        mov r18=IA64_KR(CURRENT)// M2 (12 cycle read latency)
+       adds r16=PT(CR_IPSR)+16,r12
+       adds r17=PT(CR_IIP)+16,r12
+
+(pKStk)        mov r22=psr             // M2 read PSR now that interrupts are 
disabled
+       nop.i 0
+       nop.i 0
+       ;;
+       ld8 r29=[r16],16        // load cr.ipsr
+       ld8 r28=[r17],16        // load cr.iip
+       ;;
+       ld8 r30=[r16],16        // load cr.ifs
+       ld8 r25=[r17],16        // load ar.unat
+       ;;
+       ld8 r26=[r16],16        // load ar.pfs
+       ld8 r27=[r17],16        // load ar.rsc
+       cmp.eq p9,p0=r0,r0      // set p9 to indicate that we should restore 
cr.ifs
+       ;;
+       ld8 r24=[r16],16        // load ar.rnat (may be garbage)
+       ld8 r23=[r17],16        // load ar.bspstore (may be garbage)
+       ;;
+       ld8 r31=[r16],16        // load predicates
+       ld8 r21=[r17],16        // load b0
+       ;;
+       ld8 r19=[r16],16        // load ar.rsc value for "loadrs"
+       ld8.fill r1=[r17],16    // load r1
+       ;;
+       ld8.fill r12=[r16],16
+       ld8.fill r13=[r17],16
+(pUStk)        adds r18=IA64_TASK_THREAD_ON_USTACK_OFFSET,r18
+       ;;
+       ld8 r20=[r16],16        // ar.fpsr
+       ld8.fill r15=[r17],16
+       ;;
+       ld8.fill r14=[r16],16
+       ld8.fill r2=[r17]
+(pUStk)        mov r17=1
+       ;;
+       ld8.fill r3=[r16]
+(pUStk)        st1 [r18]=r17           // restore current->thread.on_ustack
+       shr.u r18=r19,16        // get byte size of existing "dirty" partition
+       ;;
+       mov r16=ar.bsp          // get existing backing store pointer
+#ifdef XEN
+       movl r17=THIS_CPU(ia64_phys_stacked_size_p8)
+#else
+       addl r17=THIS_CPU(ia64_phys_stacked_size_p8),r0
+#endif
+       ;;
+       ld4 r17=[r17]           // r17 = cpu_data->phys_stacked_size_p8
+(pKStk)        br.cond.dpnt skip_rbs_switch
+
+       /*
+        * Restore user backing store.
+        *
+        * NOTE: alloc, loadrs, and cover can't be predicated.
+        */
+(pNonSys) br.cond.dpnt dont_preserve_current_frame
+
+rbs_switch:
+       cover                           // add current frame into dirty 
partition and set cr.ifs
+       ;;
+       mov r19=ar.bsp                  // get new backing store pointer
+       sub r16=r16,r18                 // krbs = old bsp - size of dirty 
partition
+       cmp.ne p9,p0=r0,r0              // clear p9 to skip restore of cr.ifs
+       ;;
+       sub r19=r19,r16                 // calculate total byte size of dirty 
partition
+       add r18=64,r18                  // don't force in0-in7 into memory...
+       ;;
+       shl r19=r19,16                  // shift size of dirty partition into 
loadrs position
+       ;;
+dont_preserve_current_frame:
+       /*
+        * To prevent leaking bits between the kernel and user-space,
+        * we must clear the stacked registers in the "invalid" partition here.
+        * Not pretty, but at least it's fast (3.34 registers/cycle on Itanium,
+        * 5 registers/cycle on McKinley).
+        */
+#      define pRecurse p6
+#      define pReturn  p7
+#ifdef CONFIG_ITANIUM
+#      define Nregs    10
+#else
+#      define Nregs    14
+#endif
+       alloc loc0=ar.pfs,2,Nregs-2,2,0
+       shr.u loc1=r18,9                // RNaTslots <= floor(dirtySize / 
(64*8))
+       sub r17=r17,r18                 // r17 = (physStackedSize + 8) - 
dirtySize
+       ;;
+       mov ar.rsc=r19                  // load ar.rsc to be used for "loadrs"
+       shladd in0=loc1,3,r17
+       mov in1=0
+       ;;
+       TEXT_ALIGN(32)
+rse_clear_invalid:
+#ifdef CONFIG_ITANIUM
+       // cycle 0
+ { .mii
+       alloc loc0=ar.pfs,2,Nregs-2,2,0
+       cmp.lt pRecurse,p0=Nregs*8,in0  // if more than Nregs regs left to 
clear, (re)curse
+       add out0=-Nregs*8,in0
+}{ .mfb
+       add out1=1,in1                  // increment recursion count
+       nop.f 0
+       nop.b 0                         // can't do br.call here because of 
alloc (WAW on CFM)
+       ;;
+}{ .mfi        // cycle 1
+       mov loc1=0
+       nop.f 0
+       mov loc2=0
+}{ .mib
+       mov loc3=0
+       mov loc4=0
+(pRecurse) br.call.sptk.many b0=rse_clear_invalid
+
+}{ .mfi        // cycle 2
+       mov loc5=0
+       nop.f 0
+       cmp.ne pReturn,p0=r0,in1        // if recursion count != 0, we need to 
do a br.ret
+}{ .mib
+       mov loc6=0
+       mov loc7=0
+(pReturn) br.ret.sptk.many b0
+}
+#else /* !CONFIG_ITANIUM */
+       alloc loc0=ar.pfs,2,Nregs-2,2,0
+       cmp.lt pRecurse,p0=Nregs*8,in0  // if more than Nregs regs left to 
clear, (re)curse
+       add out0=-Nregs*8,in0
+       add out1=1,in1                  // increment recursion count
+       mov loc1=0
+       mov loc2=0
+       ;;
+       mov loc3=0
+       mov loc4=0
+       mov loc5=0
+       mov loc6=0
+       mov loc7=0
+(pRecurse) br.call.sptk.few b0=rse_clear_invalid
+       ;;
+       mov loc8=0
+       mov loc9=0
+       cmp.ne pReturn,p0=r0,in1        // if recursion count != 0, we need to 
do a br.ret
+       mov loc10=0
+       mov loc11=0
+(pReturn) br.ret.sptk.many b0
+#endif /* !CONFIG_ITANIUM */
+#      undef pRecurse
+#      undef pReturn
+       ;;
+       alloc r17=ar.pfs,0,0,0,0        // drop current register frame
+       ;;
+       loadrs
+       ;;
+skip_rbs_switch:
+       mov ar.unat=r25         // M2
+(pKStk)        extr.u r22=r22,21,1     // I0 extract current value of psr.pp 
from r22
+(pLvSys)mov r19=r0             // A  clear r19 for leave_syscall, no-op 
otherwise
+       ;;
+(pUStk)        mov ar.bspstore=r23     // M2
+(pKStk)        dep r29=r22,r29,21,1    // I0 update ipsr.pp with psr.pp
+(pLvSys)mov r16=r0             // A  clear r16 for leave_syscall, no-op 
otherwise
+       ;;
+       mov cr.ipsr=r29         // M2
+       mov ar.pfs=r26          // I0
+(pLvSys)mov r17=r0             // A  clear r17 for leave_syscall, no-op 
otherwise
+
+(p9)   mov cr.ifs=r30          // M2
+       mov b0=r21              // I0
+(pLvSys)mov r18=r0             // A  clear r18 for leave_syscall, no-op 
otherwise
+
+       mov ar.fpsr=r20         // M2
+       mov cr.iip=r28          // M2
+       nop 0
+       ;;
+(pUStk)        mov ar.rnat=r24         // M2 must happen with RSE in lazy mode
+       nop 0
+(pLvSys)mov r2=r0
+
+       mov ar.rsc=r27          // M2
+       mov pr=r31,-1           // I0
+       rfi                     // B
+
+#ifndef XEN
+       /*
+        * On entry:
+        *      r20 = &current->thread_info->pre_count (if CONFIG_PREEMPT)
+        *      r31 = current->thread_info->flags
+        * On exit:
+        *      p6 = TRUE if work-pending-check needs to be redone
+        */
+.work_pending_syscall:
+       add r2=-8,r2
+       add r3=-8,r3
+       ;;
+       st8 [r2]=r8
+       st8 [r3]=r10
+.work_pending:
+       tbit.nz p6,p0=r31,TIF_SIGDELAYED                // signal delayed from  
MCA/INIT/NMI/PMI context?
+(p6)   br.cond.sptk.few .sigdelayed
+       ;;
+       tbit.z p6,p0=r31,TIF_NEED_RESCHED               // 
current_thread_info()->need_resched==0?
+(p6)   br.cond.sptk.few .notify
+#ifdef CONFIG_PREEMPT
+(pKStk) dep r21=-1,r0,PREEMPT_ACTIVE_BIT,1
+       ;;
+(pKStk) st4 [r20]=r21
+       ssm psr.i               // enable interrupts
+#endif
+       br.call.spnt.many rp=schedule
+.ret9: cmp.eq p6,p0=r0,r0                              // p6 <- 1
+       rsm psr.i               // disable interrupts
+       ;;
+#ifdef CONFIG_PREEMPT
+(pKStk)        adds r20=TI_PRE_COUNT+IA64_TASK_SIZE,r13
+       ;;
+(pKStk)        st4 [r20]=r0            // preempt_count() <- 0
+#endif
+(pLvSys)br.cond.sptk.few  .work_pending_syscall_end
+       br.cond.sptk.many .work_processed_kernel        // re-check
+
+.notify:
+(pUStk)        br.call.spnt.many rp=notify_resume_user
+.ret10:        cmp.ne p6,p0=r0,r0                              // p6 <- 0
+(pLvSys)br.cond.sptk.few  .work_pending_syscall_end
+       br.cond.sptk.many .work_processed_kernel        // don't re-check
+
+// There is a delayed signal that was detected in MCA/INIT/NMI/PMI context 
where
+// it could not be delivered.  Deliver it now.  The signal might be for us and
+// may set TIF_SIGPENDING, so redrive ia64_leave_* after processing the delayed
+// signal.
+
+.sigdelayed:
+       br.call.sptk.many rp=do_sigdelayed
+       cmp.eq p6,p0=r0,r0                              // p6 <- 1, always 
re-check
+(pLvSys)br.cond.sptk.few  .work_pending_syscall_end
+       br.cond.sptk.many .work_processed_kernel        // re-check
+
+.work_pending_syscall_end:
+       adds r2=PT(R8)+16,r12
+       adds r3=PT(R10)+16,r12
+       ;;
+       ld8 r8=[r2]
+       ld8 r10=[r3]
+       br.cond.sptk.many .work_processed_syscall       // re-check
+#endif
+
+END(ia64_leave_kernel)
+
+ENTRY(handle_syscall_error)
+       /*
+        * Some system calls (e.g., ptrace, mmap) can return arbitrary values 
which could
+        * lead us to mistake a negative return value as a failed syscall.  
Those syscall
+        * must deposit a non-zero value in pt_regs.r8 to indicate an error.  If
+        * pt_regs.r8 is zero, we assume that the call completed successfully.
+        */
+       PT_REGS_UNWIND_INFO(0)
+       ld8 r3=[r2]             // load pt_regs.r8
+       ;;
+       cmp.eq p6,p7=r3,r0      // is pt_regs.r8==0?
+       ;;
+(p7)   mov r10=-1
+(p7)   sub r8=0,r8             // negate return value to get errno
+       br.cond.sptk ia64_leave_syscall
+END(handle_syscall_error)
+
+       /*
+        * Invoke schedule_tail(task) while preserving in0-in7, which may be 
needed
+        * in case a system call gets restarted.
+        */
+GLOBAL_ENTRY(ia64_invoke_schedule_tail)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc loc1=ar.pfs,8,2,1,0
+       mov loc0=rp
+       mov out0=r8                             // Address of previous task
+       ;;
+       br.call.sptk.many rp=schedule_tail
+.ret11:        mov ar.pfs=loc1
+       mov rp=loc0
+       br.ret.sptk.many rp
+END(ia64_invoke_schedule_tail)
+
+#ifndef XEN
+       /*
+        * Setup stack and call do_notify_resume_user().  Note that pSys and 
pNonSys need to
+        * be set up by the caller.  We declare 8 input registers so the system 
call
+        * args get preserved, in case we need to restart a system call.
+        */
+ENTRY(notify_resume_user)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc loc1=ar.pfs,8,2,3,0 // preserve all eight input regs in case of 
syscall restart!
+       mov r9=ar.unat
+       mov loc0=rp                             // save return address
+       mov out0=0                              // there is no "oldset"
+       adds out1=8,sp                          // out1=&sigscratch->ar_pfs
+(pSys) mov out2=1                              // out2==1 => we're in a syscall
+       ;;
+(pNonSys) mov out2=0                           // out2==0 => not a syscall
+       .fframe 16
+       .spillpsp ar.unat, 16                   // (note that offset is 
relative to psp+0x10!)
+       st8 [sp]=r9,-16                         // allocate space for ar.unat 
and save it
+       st8 [out1]=loc1,-8                      // save ar.pfs, out1=&sigscratch
+       .body
+       br.call.sptk.many rp=do_notify_resume_user
+.ret15:        .restore sp
+       adds sp=16,sp                           // pop scratch stack space
+       ;;
+       ld8 r9=[sp]                             // load new unat from 
sigscratch->scratch_unat
+       mov rp=loc0
+       ;;
+       mov ar.unat=r9
+       mov ar.pfs=loc1
+       br.ret.sptk.many rp
+END(notify_resume_user)
+
+GLOBAL_ENTRY(sys_rt_sigsuspend)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc loc1=ar.pfs,8,2,3,0 // preserve all eight input regs in case of 
syscall restart!
+       mov r9=ar.unat
+       mov loc0=rp                             // save return address
+       mov out0=in0                            // mask
+       mov out1=in1                            // sigsetsize
+       adds out2=8,sp                          // out2=&sigscratch->ar_pfs
+       ;;
+       .fframe 16
+       .spillpsp ar.unat, 16                   // (note that offset is 
relative to psp+0x10!)
+       st8 [sp]=r9,-16                         // allocate space for ar.unat 
and save it
+       st8 [out2]=loc1,-8                      // save ar.pfs, out2=&sigscratch
+       .body
+       br.call.sptk.many rp=ia64_rt_sigsuspend
+.ret17:        .restore sp
+       adds sp=16,sp                           // pop scratch stack space
+       ;;
+       ld8 r9=[sp]                             // load new unat from 
sw->caller_unat
+       mov rp=loc0
+       ;;
+       mov ar.unat=r9
+       mov ar.pfs=loc1
+       br.ret.sptk.many rp
+END(sys_rt_sigsuspend)
+
+ENTRY(sys_rt_sigreturn)
+       PT_REGS_UNWIND_INFO(0)
+       /*
+        * Allocate 8 input registers since ptrace() may clobber them
+        */
+       alloc r2=ar.pfs,8,0,1,0
+       .prologue
+       PT_REGS_SAVES(16)
+       adds sp=-16,sp
+       .body
+       cmp.eq pNonSys,pSys=r0,r0               // sigreturn isn't a normal 
syscall...
+       ;;
+       /*
+        * leave_kernel() restores f6-f11 from pt_regs, but since the 
streamlined
+        * syscall-entry path does not save them we save them here instead.  
Note: we
+        * don't need to save any other registers that are not saved by the 
stream-lined
+        * syscall path, because restore_sigcontext() restores them.
+        */
+       adds r16=PT(F6)+32,sp
+       adds r17=PT(F7)+32,sp
+       ;;
+       stf.spill [r16]=f6,32
+       stf.spill [r17]=f7,32
+       ;;
+       stf.spill [r16]=f8,32
+       stf.spill [r17]=f9,32
+       ;;
+       stf.spill [r16]=f10
+       stf.spill [r17]=f11
+       adds out0=16,sp                         // out0 = &sigscratch
+       br.call.sptk.many rp=ia64_rt_sigreturn
+.ret19:        .restore sp 0
+       adds sp=16,sp
+       ;;
+       ld8 r9=[sp]                             // load new ar.unat
+       mov.sptk b7=r8,ia64_leave_kernel
+       ;;
+       mov ar.unat=r9
+       br.many b7
+END(sys_rt_sigreturn)
+#endif
+
+GLOBAL_ENTRY(ia64_prepare_handle_unaligned)
+       .prologue
+       /*
+        * r16 = fake ar.pfs, we simply need to make sure privilege is still 0
+        */
+       mov r16=r0
+       DO_SAVE_SWITCH_STACK
+       br.call.sptk.many rp=ia64_handle_unaligned      // stack frame setup in 
ivt
+.ret21:        .body
+       DO_LOAD_SWITCH_STACK
+       br.cond.sptk.many rp                            // goes to 
ia64_leave_kernel
+END(ia64_prepare_handle_unaligned)
+
+#ifndef XEN
+       //
+       // unw_init_running(void (*callback)(info, arg), void *arg)
+       //
+#      define EXTRA_FRAME_SIZE ((UNW_FRAME_INFO_SIZE+15)&~15)
+
+GLOBAL_ENTRY(unw_init_running)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(2)
+       alloc loc1=ar.pfs,2,3,3,0
+       ;;
+       ld8 loc2=[in0],8
+       mov loc0=rp
+       mov r16=loc1
+       DO_SAVE_SWITCH_STACK
+       .body
+
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(2)
+       .fframe IA64_SWITCH_STACK_SIZE+EXTRA_FRAME_SIZE
+       SWITCH_STACK_SAVES(EXTRA_FRAME_SIZE)
+       adds sp=-EXTRA_FRAME_SIZE,sp
+       .body
+       ;;
+       adds out0=16,sp                         // &info
+       mov out1=r13                            // current
+       adds out2=16+EXTRA_FRAME_SIZE,sp        // &switch_stack
+       br.call.sptk.many rp=unw_init_frame_info
+1:     adds out0=16,sp                         // &info
+       mov b6=loc2
+       mov loc2=gp                             // save gp across indirect 
function call
+       ;;
+       ld8 gp=[in0]
+       mov out1=in1                            // arg
+       br.call.sptk.many rp=b6                 // invoke the callback function
+1:     mov gp=loc2                             // restore gp
+
+       // For now, we don't allow changing registers from within
+       // unw_init_running; if we ever want to allow that, we'd
+       // have to do a load_switch_stack here:
+       .restore sp
+       adds sp=IA64_SWITCH_STACK_SIZE+EXTRA_FRAME_SIZE,sp
+
+       mov ar.pfs=loc1
+       mov rp=loc0
+       br.ret.sptk.many rp
+END(unw_init_running)
+
+       .rodata
+       .align 8
+       .globl sys_call_table
+sys_call_table:
+       data8 sys_ni_syscall            //  This must be sys_ni_syscall!  See 
ivt.S.
+       data8 sys_exit                          // 1025
+       data8 sys_read
+       data8 sys_write
+       data8 sys_open
+       data8 sys_close
+       data8 sys_creat                         // 1030
+       data8 sys_link
+       data8 sys_unlink
+       data8 ia64_execve
+       data8 sys_chdir
+       data8 sys_fchdir                        // 1035
+       data8 sys_utimes
+       data8 sys_mknod
+       data8 sys_chmod
+       data8 sys_chown
+       data8 sys_lseek                         // 1040
+       data8 sys_getpid
+       data8 sys_getppid
+       data8 sys_mount
+       data8 sys_umount
+       data8 sys_setuid                        // 1045
+       data8 sys_getuid
+       data8 sys_geteuid
+       data8 sys_ptrace
+       data8 sys_access
+       data8 sys_sync                          // 1050
+       data8 sys_fsync
+       data8 sys_fdatasync
+       data8 sys_kill
+       data8 sys_rename
+       data8 sys_mkdir                         // 1055
+       data8 sys_rmdir
+       data8 sys_dup
+       data8 sys_pipe
+       data8 sys_times
+       data8 ia64_brk                          // 1060
+       data8 sys_setgid
+       data8 sys_getgid
+       data8 sys_getegid
+       data8 sys_acct
+       data8 sys_ioctl                         // 1065
+       data8 sys_fcntl
+       data8 sys_umask
+       data8 sys_chroot
+       data8 sys_ustat
+       data8 sys_dup2                          // 1070
+       data8 sys_setreuid
+       data8 sys_setregid
+       data8 sys_getresuid
+       data8 sys_setresuid
+       data8 sys_getresgid                     // 1075
+       data8 sys_setresgid
+       data8 sys_getgroups
+       data8 sys_setgroups
+       data8 sys_getpgid
+       data8 sys_setpgid                       // 1080
+       data8 sys_setsid
+       data8 sys_getsid
+       data8 sys_sethostname
+       data8 sys_setrlimit
+       data8 sys_getrlimit                     // 1085
+       data8 sys_getrusage
+       data8 sys_gettimeofday
+       data8 sys_settimeofday
+       data8 sys_select
+       data8 sys_poll                          // 1090
+       data8 sys_symlink
+       data8 sys_readlink
+       data8 sys_uselib
+       data8 sys_swapon
+       data8 sys_swapoff                       // 1095
+       data8 sys_reboot
+       data8 sys_truncate
+       data8 sys_ftruncate
+       data8 sys_fchmod
+       data8 sys_fchown                        // 1100
+       data8 ia64_getpriority
+       data8 sys_setpriority
+       data8 sys_statfs
+       data8 sys_fstatfs
+       data8 sys_gettid                        // 1105
+       data8 sys_semget
+       data8 sys_semop
+       data8 sys_semctl
+       data8 sys_msgget
+       data8 sys_msgsnd                        // 1110
+       data8 sys_msgrcv
+       data8 sys_msgctl
+       data8 sys_shmget
+       data8 ia64_shmat
+       data8 sys_shmdt                         // 1115
+       data8 sys_shmctl
+       data8 sys_syslog
+       data8 sys_setitimer
+       data8 sys_getitimer
+       data8 sys_ni_syscall                    // 1120         /* was: 
ia64_oldstat */
+       data8 sys_ni_syscall                                    /* was: 
ia64_oldlstat */
+       data8 sys_ni_syscall                                    /* was: 
ia64_oldfstat */
+       data8 sys_vhangup
+       data8 sys_lchown
+       data8 sys_remap_file_pages              // 1125
+       data8 sys_wait4
+       data8 sys_sysinfo
+       data8 sys_clone
+       data8 sys_setdomainname
+       data8 sys_newuname                      // 1130
+       data8 sys_adjtimex
+       data8 sys_ni_syscall                                    /* was: 
ia64_create_module */
+       data8 sys_init_module
+       data8 sys_delete_module
+       data8 sys_ni_syscall                    // 1135         /* was: 
sys_get_kernel_syms */
+       data8 sys_ni_syscall                                    /* was: 
sys_query_module */
+       data8 sys_quotactl
+       data8 sys_bdflush
+       data8 sys_sysfs
+       data8 sys_personality                   // 1140
+       data8 sys_ni_syscall            // sys_afs_syscall
+       data8 sys_setfsuid
+       data8 sys_setfsgid
+       data8 sys_getdents
+       data8 sys_flock                         // 1145
+       data8 sys_readv
+       data8 sys_writev
+       data8 sys_pread64
+       data8 sys_pwrite64
+       data8 sys_sysctl                        // 1150
+       data8 sys_mmap
+       data8 sys_munmap
+       data8 sys_mlock
+       data8 sys_mlockall
+       data8 sys_mprotect                      // 1155
+       data8 ia64_mremap
+       data8 sys_msync
+       data8 sys_munlock
+       data8 sys_munlockall
+       data8 sys_sched_getparam                // 1160
+       data8 sys_sched_setparam
+       data8 sys_sched_getscheduler
+       data8 sys_sched_setscheduler
+       data8 sys_sched_yield
+       data8 sys_sched_get_priority_max        // 1165
+       data8 sys_sched_get_priority_min
+       data8 sys_sched_rr_get_interval
+       data8 sys_nanosleep
+       data8 sys_nfsservctl
+       data8 sys_prctl                         // 1170
+       data8 sys_getpagesize
+       data8 sys_mmap2
+       data8 sys_pciconfig_read
+       data8 sys_pciconfig_write
+       data8 sys_perfmonctl                    // 1175
+       data8 sys_sigaltstack
+       data8 sys_rt_sigaction
+       data8 sys_rt_sigpending
+       data8 sys_rt_sigprocmask
+       data8 sys_rt_sigqueueinfo               // 1180
+       data8 sys_rt_sigreturn
+       data8 sys_rt_sigsuspend
+       data8 sys_rt_sigtimedwait
+       data8 sys_getcwd
+       data8 sys_capget                        // 1185
+       data8 sys_capset
+       data8 sys_sendfile64
+       data8 sys_ni_syscall            // sys_getpmsg (STREAMS)
+       data8 sys_ni_syscall            // sys_putpmsg (STREAMS)
+       data8 sys_socket                        // 1190
+       data8 sys_bind
+       data8 sys_connect
+       data8 sys_listen
+       data8 sys_accept
+       data8 sys_getsockname                   // 1195
+       data8 sys_getpeername
+       data8 sys_socketpair
+       data8 sys_send
+       data8 sys_sendto
+       data8 sys_recv                          // 1200
+       data8 sys_recvfrom
+       data8 sys_shutdown
+       data8 sys_setsockopt
+       data8 sys_getsockopt
+       data8 sys_sendmsg                       // 1205
+       data8 sys_recvmsg
+       data8 sys_pivot_root
+       data8 sys_mincore
+       data8 sys_madvise
+       data8 sys_newstat                       // 1210
+       data8 sys_newlstat
+       data8 sys_newfstat
+       data8 sys_clone2
+       data8 sys_getdents64
+       data8 sys_getunwind                     // 1215
+       data8 sys_readahead
+       data8 sys_setxattr
+       data8 sys_lsetxattr
+       data8 sys_fsetxattr
+       data8 sys_getxattr                      // 1220
+       data8 sys_lgetxattr
+       data8 sys_fgetxattr
+       data8 sys_listxattr
+       data8 sys_llistxattr
+       data8 sys_flistxattr                    // 1225
+       data8 sys_removexattr
+       data8 sys_lremovexattr
+       data8 sys_fremovexattr
+       data8 sys_tkill
+       data8 sys_futex                         // 1230
+       data8 sys_sched_setaffinity
+       data8 sys_sched_getaffinity
+       data8 sys_set_tid_address
+       data8 sys_fadvise64_64
+       data8 sys_tgkill                        // 1235
+       data8 sys_exit_group
+       data8 sys_lookup_dcookie
+       data8 sys_io_setup
+       data8 sys_io_destroy
+       data8 sys_io_getevents                  // 1240
+       data8 sys_io_submit
+       data8 sys_io_cancel
+       data8 sys_epoll_create
+       data8 sys_epoll_ctl
+       data8 sys_epoll_wait                    // 1245
+       data8 sys_restart_syscall
+       data8 sys_semtimedop
+       data8 sys_timer_create
+       data8 sys_timer_settime
+       data8 sys_timer_gettime                 // 1250
+       data8 sys_timer_getoverrun
+       data8 sys_timer_delete
+       data8 sys_clock_settime
+       data8 sys_clock_gettime
+       data8 sys_clock_getres                  // 1255
+       data8 sys_clock_nanosleep
+       data8 sys_fstatfs64
+       data8 sys_statfs64
+       data8 sys_mbind
+       data8 sys_get_mempolicy                 // 1260
+       data8 sys_set_mempolicy
+       data8 sys_mq_open
+       data8 sys_mq_unlink
+       data8 sys_mq_timedsend
+       data8 sys_mq_timedreceive               // 1265
+       data8 sys_mq_notify
+       data8 sys_mq_getsetattr
+       data8 sys_ni_syscall                    // reserved for kexec_load
+       data8 sys_ni_syscall                    // reserved for vserver
+       data8 sys_waitid                        // 1270
+       data8 sys_add_key
+       data8 sys_request_key
+       data8 sys_keyctl
+       data8 sys_ni_syscall
+       data8 sys_ni_syscall                    // 1275
+       data8 sys_ni_syscall
+       data8 sys_ni_syscall
+       data8 sys_ni_syscall
+       data8 sys_ni_syscall
+
+       .org sys_call_table + 8*NR_syscalls     // guard against failures to 
increase NR_syscalls
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/entry.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/entry.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,97 @@
+#include <linux/config.h>
+
+/*
+ * Preserved registers that are shared between code in ivt.S and
+ * entry.S.  Be careful not to step on these!
+ */
+#define PRED_LEAVE_SYSCALL     1 /* TRUE iff leave from syscall */
+#define PRED_KERNEL_STACK      2 /* returning to kernel-stacks? */
+#define PRED_USER_STACK                3 /* returning to user-stacks? */
+#ifdef CONFIG_VTI
+#define PRED_EMUL              2 /* Need to save r4-r7 for inst emulation */
+#define PRED_NON_EMUL          3 /* No need to save r4-r7 for normal path */
+#define PRED_BN0               6 /* Guest is in bank 0 */
+#define PRED_BN1               7 /* Guest is in bank 1 */
+#endif // CONFIG_VTI
+#define PRED_SYSCALL           4 /* inside a system call? */
+#define PRED_NON_SYSCALL       5 /* complement of PRED_SYSCALL */
+
+#ifdef __ASSEMBLY__
+# define PASTE2(x,y)   x##y
+# define PASTE(x,y)    PASTE2(x,y)
+
+# define pLvSys                PASTE(p,PRED_LEAVE_SYSCALL)
+# define pKStk         PASTE(p,PRED_KERNEL_STACK)
+# define pUStk         PASTE(p,PRED_USER_STACK)
+#ifdef CONFIG_VTI
+# define pEml          PASTE(p,PRED_EMUL)
+# define pNonEml       PASTE(p,PRED_NON_EMUL)
+# define pBN0          PASTE(p,PRED_BN0)
+# define pBN1          PASTE(p,PRED_BN1)
+#endif // CONFIG_VTI
+# define pSys          PASTE(p,PRED_SYSCALL)
+# define pNonSys       PASTE(p,PRED_NON_SYSCALL)
+#endif
+
+#define PT(f)          (IA64_PT_REGS_##f##_OFFSET)
+#define SW(f)          (IA64_SWITCH_STACK_##f##_OFFSET)
+#ifdef CONFIG_VTI
+#define VPD(f)      (VPD_##f##_START_OFFSET)
+#endif // CONFIG_VTI
+
+#define PT_REGS_SAVES(off)                     \
+       .unwabi 3, 'i';                         \
+       .fframe IA64_PT_REGS_SIZE+16+(off);     \
+       .spillsp rp, PT(CR_IIP)+16+(off);       \
+       .spillsp ar.pfs, PT(CR_IFS)+16+(off);   \
+       .spillsp ar.unat, PT(AR_UNAT)+16+(off); \
+       .spillsp ar.fpsr, PT(AR_FPSR)+16+(off); \
+       .spillsp pr, PT(PR)+16+(off);
+
+#define PT_REGS_UNWIND_INFO(off)               \
+       .prologue;                              \
+       PT_REGS_SAVES(off);                     \
+       .body
+
+#define SWITCH_STACK_SAVES(off)                                                
        \
+       .savesp ar.unat,SW(CALLER_UNAT)+16+(off);                               
\
+       .savesp ar.fpsr,SW(AR_FPSR)+16+(off);                                   
\
+       .spillsp f2,SW(F2)+16+(off); .spillsp f3,SW(F3)+16+(off);               
\
+       .spillsp f4,SW(F4)+16+(off); .spillsp f5,SW(F5)+16+(off);               
\
+       .spillsp f16,SW(F16)+16+(off); .spillsp f17,SW(F17)+16+(off);           
\
+       .spillsp f18,SW(F18)+16+(off); .spillsp f19,SW(F19)+16+(off);           
\
+       .spillsp f20,SW(F20)+16+(off); .spillsp f21,SW(F21)+16+(off);           
\
+       .spillsp f22,SW(F22)+16+(off); .spillsp f23,SW(F23)+16+(off);           
\
+       .spillsp f24,SW(F24)+16+(off); .spillsp f25,SW(F25)+16+(off);           
\
+       .spillsp f26,SW(F26)+16+(off); .spillsp f27,SW(F27)+16+(off);           
\
+       .spillsp f28,SW(F28)+16+(off); .spillsp f29,SW(F29)+16+(off);           
\
+       .spillsp f30,SW(F30)+16+(off); .spillsp f31,SW(F31)+16+(off);           
\
+       .spillsp r4,SW(R4)+16+(off); .spillsp r5,SW(R5)+16+(off);               
\
+       .spillsp r6,SW(R6)+16+(off); .spillsp r7,SW(R7)+16+(off);               
\
+       .spillsp b0,SW(B0)+16+(off); .spillsp b1,SW(B1)+16+(off);               
\
+       .spillsp b2,SW(B2)+16+(off); .spillsp b3,SW(B3)+16+(off);               
\
+       .spillsp b4,SW(B4)+16+(off); .spillsp b5,SW(B5)+16+(off);               
\
+       .spillsp ar.pfs,SW(AR_PFS)+16+(off); .spillsp ar.lc,SW(AR_LC)+16+(off); 
\
+       .spillsp @priunat,SW(AR_UNAT)+16+(off);                                 
\
+       .spillsp ar.rnat,SW(AR_RNAT)+16+(off);                                  
\
+       .spillsp ar.bspstore,SW(AR_BSPSTORE)+16+(off);                          
\
+       .spillsp pr,SW(PR)+16+(off))
+
+#define DO_SAVE_SWITCH_STACK                   \
+       movl r28=1f;                            \
+       ;;                                      \
+       .fframe IA64_SWITCH_STACK_SIZE;         \
+       adds sp=-IA64_SWITCH_STACK_SIZE,sp;     \
+       mov.ret.sptk b7=r28,1f;                 \
+       SWITCH_STACK_SAVES(0);                  \
+       br.cond.sptk.many save_switch_stack;    \
+1:
+
+#define DO_LOAD_SWITCH_STACK                   \
+       movl r28=1f;                            \
+       ;;                                      \
+       invala;                                 \
+       mov.ret.sptk b7=r28,1f;                 \
+       br.cond.sptk.many load_switch_stack;    \
+1:     .restore sp;                            \
+       adds sp=IA64_SWITCH_STACK_SIZE,sp
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/head.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/head.S    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1026 @@
+/*
+ * Here is where the ball gets rolling as far as the kernel is concerned.
+ * When control is transferred to _start, the bootload has already
+ * loaded us to the correct address.  All that's left to do here is
+ * to set up the kernel's global pointer and jump to the kernel
+ * entry point.
+ *
+ * Copyright (C) 1998-2001, 2003, 2005 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999 Intel Corp.
+ * Copyright (C) 1999 Asit Mallick <Asit.K.Mallick@xxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <Don.Dugger@xxxxxxxxx>
+ * Copyright (C) 2002 Fenghua Yu <fenghua.yu@xxxxxxxxx>
+ *   -Optimize __ia64_save_fpu() and __ia64_load_fpu() for Itanium 2.
+ */
+
+#include <linux/config.h>
+
+#include <asm/asmmacro.h>
+#include <asm/fpu.h>
+#include <asm/kregs.h>
+#include <asm/mmu_context.h>
+#include <asm/offsets.h>
+#include <asm/pal.h>
+#include <asm/pgtable.h>
+#include <asm/processor.h>
+#include <asm/ptrace.h>
+#include <asm/system.h>
+
+       .section __special_page_section,"ax"
+
+       .global empty_zero_page
+empty_zero_page:
+       .skip PAGE_SIZE
+
+       .global swapper_pg_dir
+swapper_pg_dir:
+       .skip PAGE_SIZE
+
+       .rodata
+halt_msg:
+       stringz "Halting kernel\n"
+
+       .text
+
+       .global start_ap
+
+       /*
+        * Start the kernel.  When the bootloader passes control to _start(), 
r28
+        * points to the address of the boot parameter area.  Execution reaches
+        * here in physical mode.
+        */
+GLOBAL_ENTRY(_start)
+start_ap:
+       .prologue
+       .save rp, r0            // terminate unwind chain with a NULL rp
+       .body
+
+       rsm psr.i | psr.ic
+       ;;
+       srlz.i
+       ;;
+       /*
+        * Initialize kernel region registers:
+        *      rr[0]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[1]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[2]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[3]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[4]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[5]: VHPT enabled, page size = PAGE_SHIFT
+        *      rr[6]: VHPT disabled, page size = IA64_GRANULE_SHIFT
+        *      rr[7]: VHPT disabled, page size = IA64_GRANULE_SHIFT
+        * We initialize all of them to prevent inadvertently assuming
+        * something about the state of address translation early in boot.
+        */
+       movl r6=((ia64_rid(IA64_REGION_ID_KERNEL, (0<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r7=(0<<61)
+       movl r8=((ia64_rid(IA64_REGION_ID_KERNEL, (1<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r9=(1<<61)
+       movl r10=((ia64_rid(IA64_REGION_ID_KERNEL, (2<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r11=(2<<61)
+       movl r12=((ia64_rid(IA64_REGION_ID_KERNEL, (3<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r13=(3<<61)
+       movl r14=((ia64_rid(IA64_REGION_ID_KERNEL, (4<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r15=(4<<61)
+       movl r16=((ia64_rid(IA64_REGION_ID_KERNEL, (5<<61)) << 8) | (PAGE_SHIFT 
<< 2) | 1)
+       movl r17=(5<<61)
+       movl r18=((ia64_rid(IA64_REGION_ID_KERNEL, (6<<61)) << 8) | 
(IA64_GRANULE_SHIFT << 2))
+       movl r19=(6<<61)
+       movl r20=((ia64_rid(IA64_REGION_ID_KERNEL, (7<<61)) << 8) | 
(IA64_GRANULE_SHIFT << 2))
+       movl r21=(7<<61)
+       ;;
+       mov rr[r7]=r6
+       mov rr[r9]=r8
+       mov rr[r11]=r10
+       mov rr[r13]=r12
+       mov rr[r15]=r14
+       mov rr[r17]=r16
+       mov rr[r19]=r18
+       mov rr[r21]=r20
+       ;;
+       /*
+        * Now pin mappings into the TLB for kernel text and data
+        */
+       mov r18=KERNEL_TR_PAGE_SHIFT<<2
+       movl r17=KERNEL_START
+       ;;
+       mov cr.itir=r18
+       mov cr.ifa=r17
+       mov r16=IA64_TR_KERNEL
+       mov r3=ip
+       movl r18=PAGE_KERNEL
+       ;;
+       dep r2=0,r3,0,KERNEL_TR_PAGE_SHIFT
+       ;;
+       or r18=r2,r18
+       ;;
+       srlz.i
+       ;;
+       itr.i itr[r16]=r18
+       ;;
+       itr.d dtr[r16]=r18
+       ;;
+       srlz.i
+
+       /*
+        * Switch into virtual mode:
+        */
+#ifdef CONFIG_VTI
+       movl r16=(IA64_PSR_IT|IA64_PSR_IC|IA64_PSR_DT|IA64_PSR_RT|IA64_PSR_DFH \
+                 |IA64_PSR_DI)
+#else // CONFIG_VTI
+       movl 
r16=(IA64_PSR_IT|IA64_PSR_IC|IA64_PSR_DT|IA64_PSR_RT|IA64_PSR_DFH|IA64_PSR_BN \
+                 |IA64_PSR_DI)
+#endif // CONFIG_VTI
+       ;;
+       mov cr.ipsr=r16
+       movl r17=1f
+       ;;
+       mov cr.iip=r17
+       mov cr.ifs=r0
+       ;;
+       rfi
+       ;;
+1:     // now we are in virtual mode
+
+       // set IVT entry point---can't access I/O ports without it
+#ifdef CONFIG_VTI
+    movl r3=vmx_ia64_ivt
+#else // CONFIG_VTI
+       movl r3=ia64_ivt
+#endif // CONFIG_VTI
+       ;;
+       mov cr.iva=r3
+       movl r2=FPSR_DEFAULT
+       ;;
+       srlz.i
+       movl gp=__gp
+
+       mov ar.fpsr=r2
+       ;;
+
+#define isAP   p2      // are we an Application Processor?
+#define isBP   p3      // are we the Bootstrap Processor?
+
+#ifdef CONFIG_SMP
+       /*
+        * Find the init_task for the currently booting CPU.  At poweron, and in
+        * UP mode, task_for_booting_cpu is NULL.
+        */
+       movl r3=task_for_booting_cpu
+       ;;
+       ld8 r3=[r3]
+       movl r2=init_task
+       ;;
+       cmp.eq isBP,isAP=r3,r0
+       ;;
+(isAP) mov r2=r3
+#else
+       movl r2=init_task
+       cmp.eq isBP,isAP=r0,r0
+#endif
+       ;;
+       tpa r3=r2               // r3 == phys addr of task struct
+       mov r16=-1
+(isBP) br.cond.dpnt .load_current // BP stack is on region 5 --- no need to 
map it
+
+       // load mapping for stack (virtaddr in r2, physaddr in r3)
+       rsm psr.ic
+       movl r17=PAGE_KERNEL
+       ;;
+       srlz.d
+       dep r18=0,r3,0,12
+       ;;
+       or r18=r17,r18
+#ifdef XEN
+       dep r2=-1,r3,60,4       // IMVA of task
+#else
+       dep r2=-1,r3,61,3       // IMVA of task
+#endif
+       ;;
+       mov r17=rr[r2]
+       shr.u r16=r3,IA64_GRANULE_SHIFT
+       ;;
+       dep r17=0,r17,8,24
+       ;;
+       mov cr.itir=r17
+       mov cr.ifa=r2
+
+       mov r19=IA64_TR_CURRENT_STACK
+       ;;
+       itr.d dtr[r19]=r18
+       ;;
+       ssm psr.ic
+       srlz.d
+       ;;
+
+.load_current:
+       // load the "current" pointer (r13) and ar.k6 with the current task
+#ifdef CONFIG_VTI
+       mov r21=r2              // virtual address
+       ;;
+       bsw.1
+       ;;
+#else // CONFIG_VTI
+       mov IA64_KR(CURRENT)=r2         // virtual address
+       mov IA64_KR(CURRENT_STACK)=r16
+#endif // CONFIG_VTI
+       mov r13=r2
+       /*
+        * Reserve space at the top of the stack for "struct pt_regs".  Kernel 
threads
+        * don't store interesting values in that structure, but the space 
still needs
+        * to be there because time-critical stuff such as the context 
switching can
+        * be implemented more efficiently (for example, __switch_to()
+        * always sets the psr.dfh bit of the task it is switching to).
+        */
+       addl r12=IA64_STK_OFFSET-IA64_PT_REGS_SIZE-16,r2
+       addl r2=IA64_RBS_OFFSET,r2      // initialize the RSE
+       mov ar.rsc=0            // place RSE in enforced lazy mode
+       ;;
+       loadrs                  // clear the dirty partition
+       ;;
+       mov ar.bspstore=r2      // establish the new RSE stack
+       ;;
+       mov ar.rsc=0x3          // place RSE in eager mode
+
+#ifdef XEN
+(isBP) dep r28=-1,r28,60,4     // make address virtual
+#else
+(isBP) dep r28=-1,r28,61,3     // make address virtual
+#endif
+(isBP) movl r2=ia64_boot_param
+       ;;
+(isBP) st8 [r2]=r28            // save the address of the boot param area 
passed by the bootloader
+
+#ifdef CONFIG_SMP
+(isAP) br.call.sptk.many rp=start_secondary
+.ret0:
+(isAP) br.cond.sptk self
+#endif
+
+       // This is executed by the bootstrap processor (bsp) only:
+
+#ifdef CONFIG_IA64_FW_EMU
+       // initialize PAL & SAL emulator:
+       br.call.sptk.many rp=sys_fw_init
+.ret1:
+#endif
+       br.call.sptk.many rp=start_kernel
+.ret2: addl r3=@ltoff(halt_msg),gp
+       ;;
+       alloc r2=ar.pfs,8,0,2,0
+       ;;
+       ld8 out0=[r3]
+       br.call.sptk.many b0=console_print
+
+self:  hint @pause
+       ;;
+       br.sptk.many self               // endless loop
+       ;;
+END(_start)
+
+GLOBAL_ENTRY(ia64_save_debug_regs)
+       alloc r16=ar.pfs,1,0,0,0
+       mov r20=ar.lc                   // preserve ar.lc
+       mov ar.lc=IA64_NUM_DBG_REGS-1
+       mov r18=0
+       add r19=IA64_NUM_DBG_REGS*8,in0
+       ;;
+1:     mov r16=dbr[r18]
+#ifdef CONFIG_ITANIUM
+       ;;
+       srlz.d
+#endif
+       mov r17=ibr[r18]
+       add r18=1,r18
+       ;;
+       st8.nta [in0]=r16,8
+       st8.nta [r19]=r17,8
+       br.cloop.sptk.many 1b
+       ;;
+       mov ar.lc=r20                   // restore ar.lc
+       br.ret.sptk.many rp
+END(ia64_save_debug_regs)
+
+GLOBAL_ENTRY(ia64_load_debug_regs)
+       alloc r16=ar.pfs,1,0,0,0
+       lfetch.nta [in0]
+       mov r20=ar.lc                   // preserve ar.lc
+       add r19=IA64_NUM_DBG_REGS*8,in0
+       mov ar.lc=IA64_NUM_DBG_REGS-1
+       mov r18=-1
+       ;;
+1:     ld8.nta r16=[in0],8
+       ld8.nta r17=[r19],8
+       add r18=1,r18
+       ;;
+       mov dbr[r18]=r16
+#ifdef CONFIG_ITANIUM
+       ;;
+       srlz.d                          // Errata 132 (NoFix status)
+#endif
+       mov ibr[r18]=r17
+       br.cloop.sptk.many 1b
+       ;;
+       mov ar.lc=r20                   // restore ar.lc
+       br.ret.sptk.many rp
+END(ia64_load_debug_regs)
+
+GLOBAL_ENTRY(__ia64_save_fpu)
+       alloc r2=ar.pfs,1,4,0,0
+       adds loc0=96*16-16,in0
+       adds loc1=96*16-16-128,in0
+       ;;
+       stf.spill.nta [loc0]=f127,-256
+       stf.spill.nta [loc1]=f119,-256
+       ;;
+       stf.spill.nta [loc0]=f111,-256
+       stf.spill.nta [loc1]=f103,-256
+       ;;
+       stf.spill.nta [loc0]=f95,-256
+       stf.spill.nta [loc1]=f87,-256
+       ;;
+       stf.spill.nta [loc0]=f79,-256
+       stf.spill.nta [loc1]=f71,-256
+       ;;
+       stf.spill.nta [loc0]=f63,-256
+       stf.spill.nta [loc1]=f55,-256
+       adds loc2=96*16-32,in0
+       ;;
+       stf.spill.nta [loc0]=f47,-256
+       stf.spill.nta [loc1]=f39,-256
+       adds loc3=96*16-32-128,in0
+       ;;
+       stf.spill.nta [loc2]=f126,-256
+       stf.spill.nta [loc3]=f118,-256
+       ;;
+       stf.spill.nta [loc2]=f110,-256
+       stf.spill.nta [loc3]=f102,-256
+       ;;
+       stf.spill.nta [loc2]=f94,-256
+       stf.spill.nta [loc3]=f86,-256
+       ;;
+       stf.spill.nta [loc2]=f78,-256
+       stf.spill.nta [loc3]=f70,-256
+       ;;
+       stf.spill.nta [loc2]=f62,-256
+       stf.spill.nta [loc3]=f54,-256
+       adds loc0=96*16-48,in0
+       ;;
+       stf.spill.nta [loc2]=f46,-256
+       stf.spill.nta [loc3]=f38,-256
+       adds loc1=96*16-48-128,in0
+       ;;
+       stf.spill.nta [loc0]=f125,-256
+       stf.spill.nta [loc1]=f117,-256
+       ;;
+       stf.spill.nta [loc0]=f109,-256
+       stf.spill.nta [loc1]=f101,-256
+       ;;
+       stf.spill.nta [loc0]=f93,-256
+       stf.spill.nta [loc1]=f85,-256
+       ;;
+       stf.spill.nta [loc0]=f77,-256
+       stf.spill.nta [loc1]=f69,-256
+       ;;
+       stf.spill.nta [loc0]=f61,-256
+       stf.spill.nta [loc1]=f53,-256
+       adds loc2=96*16-64,in0
+       ;;
+       stf.spill.nta [loc0]=f45,-256
+       stf.spill.nta [loc1]=f37,-256
+       adds loc3=96*16-64-128,in0
+       ;;
+       stf.spill.nta [loc2]=f124,-256
+       stf.spill.nta [loc3]=f116,-256
+       ;;
+       stf.spill.nta [loc2]=f108,-256
+       stf.spill.nta [loc3]=f100,-256
+       ;;
+       stf.spill.nta [loc2]=f92,-256
+       stf.spill.nta [loc3]=f84,-256
+       ;;
+       stf.spill.nta [loc2]=f76,-256
+       stf.spill.nta [loc3]=f68,-256
+       ;;
+       stf.spill.nta [loc2]=f60,-256
+       stf.spill.nta [loc3]=f52,-256
+       adds loc0=96*16-80,in0
+       ;;
+       stf.spill.nta [loc2]=f44,-256
+       stf.spill.nta [loc3]=f36,-256
+       adds loc1=96*16-80-128,in0
+       ;;
+       stf.spill.nta [loc0]=f123,-256
+       stf.spill.nta [loc1]=f115,-256
+       ;;
+       stf.spill.nta [loc0]=f107,-256
+       stf.spill.nta [loc1]=f99,-256
+       ;;
+       stf.spill.nta [loc0]=f91,-256
+       stf.spill.nta [loc1]=f83,-256
+       ;;
+       stf.spill.nta [loc0]=f75,-256
+       stf.spill.nta [loc1]=f67,-256
+       ;;
+       stf.spill.nta [loc0]=f59,-256
+       stf.spill.nta [loc1]=f51,-256
+       adds loc2=96*16-96,in0
+       ;;
+       stf.spill.nta [loc0]=f43,-256
+       stf.spill.nta [loc1]=f35,-256
+       adds loc3=96*16-96-128,in0
+       ;;
+       stf.spill.nta [loc2]=f122,-256
+       stf.spill.nta [loc3]=f114,-256
+       ;;
+       stf.spill.nta [loc2]=f106,-256
+       stf.spill.nta [loc3]=f98,-256
+       ;;
+       stf.spill.nta [loc2]=f90,-256
+       stf.spill.nta [loc3]=f82,-256
+       ;;
+       stf.spill.nta [loc2]=f74,-256
+       stf.spill.nta [loc3]=f66,-256
+       ;;
+       stf.spill.nta [loc2]=f58,-256
+       stf.spill.nta [loc3]=f50,-256
+       adds loc0=96*16-112,in0
+       ;;
+       stf.spill.nta [loc2]=f42,-256
+       stf.spill.nta [loc3]=f34,-256
+       adds loc1=96*16-112-128,in0
+       ;;
+       stf.spill.nta [loc0]=f121,-256
+       stf.spill.nta [loc1]=f113,-256
+       ;;
+       stf.spill.nta [loc0]=f105,-256
+       stf.spill.nta [loc1]=f97,-256
+       ;;
+       stf.spill.nta [loc0]=f89,-256
+       stf.spill.nta [loc1]=f81,-256
+       ;;
+       stf.spill.nta [loc0]=f73,-256
+       stf.spill.nta [loc1]=f65,-256
+       ;;
+       stf.spill.nta [loc0]=f57,-256
+       stf.spill.nta [loc1]=f49,-256
+       adds loc2=96*16-128,in0
+       ;;
+       stf.spill.nta [loc0]=f41,-256
+       stf.spill.nta [loc1]=f33,-256
+       adds loc3=96*16-128-128,in0
+       ;;
+       stf.spill.nta [loc2]=f120,-256
+       stf.spill.nta [loc3]=f112,-256
+       ;;
+       stf.spill.nta [loc2]=f104,-256
+       stf.spill.nta [loc3]=f96,-256
+       ;;
+       stf.spill.nta [loc2]=f88,-256
+       stf.spill.nta [loc3]=f80,-256
+       ;;
+       stf.spill.nta [loc2]=f72,-256
+       stf.spill.nta [loc3]=f64,-256
+       ;;
+       stf.spill.nta [loc2]=f56,-256
+       stf.spill.nta [loc3]=f48,-256
+       ;;
+       stf.spill.nta [loc2]=f40
+       stf.spill.nta [loc3]=f32
+       br.ret.sptk.many rp
+END(__ia64_save_fpu)
+
+GLOBAL_ENTRY(__ia64_load_fpu)
+       alloc r2=ar.pfs,1,2,0,0
+       adds r3=128,in0
+       adds r14=256,in0
+       adds r15=384,in0
+       mov loc0=512
+       mov loc1=-1024+16
+       ;;
+       ldf.fill.nta f32=[in0],loc0
+       ldf.fill.nta f40=[ r3],loc0
+       ldf.fill.nta f48=[r14],loc0
+       ldf.fill.nta f56=[r15],loc0
+       ;;
+       ldf.fill.nta f64=[in0],loc0
+       ldf.fill.nta f72=[ r3],loc0
+       ldf.fill.nta f80=[r14],loc0
+       ldf.fill.nta f88=[r15],loc0
+       ;;
+       ldf.fill.nta f96=[in0],loc1
+       ldf.fill.nta f104=[ r3],loc1
+       ldf.fill.nta f112=[r14],loc1
+       ldf.fill.nta f120=[r15],loc1
+       ;;
+       ldf.fill.nta f33=[in0],loc0
+       ldf.fill.nta f41=[ r3],loc0
+       ldf.fill.nta f49=[r14],loc0
+       ldf.fill.nta f57=[r15],loc0
+       ;;
+       ldf.fill.nta f65=[in0],loc0
+       ldf.fill.nta f73=[ r3],loc0
+       ldf.fill.nta f81=[r14],loc0
+       ldf.fill.nta f89=[r15],loc0
+       ;;
+       ldf.fill.nta f97=[in0],loc1
+       ldf.fill.nta f105=[ r3],loc1
+       ldf.fill.nta f113=[r14],loc1
+       ldf.fill.nta f121=[r15],loc1
+       ;;
+       ldf.fill.nta f34=[in0],loc0
+       ldf.fill.nta f42=[ r3],loc0
+       ldf.fill.nta f50=[r14],loc0
+       ldf.fill.nta f58=[r15],loc0
+       ;;
+       ldf.fill.nta f66=[in0],loc0
+       ldf.fill.nta f74=[ r3],loc0
+       ldf.fill.nta f82=[r14],loc0
+       ldf.fill.nta f90=[r15],loc0
+       ;;
+       ldf.fill.nta f98=[in0],loc1
+       ldf.fill.nta f106=[ r3],loc1
+       ldf.fill.nta f114=[r14],loc1
+       ldf.fill.nta f122=[r15],loc1
+       ;;
+       ldf.fill.nta f35=[in0],loc0
+       ldf.fill.nta f43=[ r3],loc0
+       ldf.fill.nta f51=[r14],loc0
+       ldf.fill.nta f59=[r15],loc0
+       ;;
+       ldf.fill.nta f67=[in0],loc0
+       ldf.fill.nta f75=[ r3],loc0
+       ldf.fill.nta f83=[r14],loc0
+       ldf.fill.nta f91=[r15],loc0
+       ;;
+       ldf.fill.nta f99=[in0],loc1
+       ldf.fill.nta f107=[ r3],loc1
+       ldf.fill.nta f115=[r14],loc1
+       ldf.fill.nta f123=[r15],loc1
+       ;;
+       ldf.fill.nta f36=[in0],loc0
+       ldf.fill.nta f44=[ r3],loc0
+       ldf.fill.nta f52=[r14],loc0
+       ldf.fill.nta f60=[r15],loc0
+       ;;
+       ldf.fill.nta f68=[in0],loc0
+       ldf.fill.nta f76=[ r3],loc0
+       ldf.fill.nta f84=[r14],loc0
+       ldf.fill.nta f92=[r15],loc0
+       ;;
+       ldf.fill.nta f100=[in0],loc1
+       ldf.fill.nta f108=[ r3],loc1
+       ldf.fill.nta f116=[r14],loc1
+       ldf.fill.nta f124=[r15],loc1
+       ;;
+       ldf.fill.nta f37=[in0],loc0
+       ldf.fill.nta f45=[ r3],loc0
+       ldf.fill.nta f53=[r14],loc0
+       ldf.fill.nta f61=[r15],loc0
+       ;;
+       ldf.fill.nta f69=[in0],loc0
+       ldf.fill.nta f77=[ r3],loc0
+       ldf.fill.nta f85=[r14],loc0
+       ldf.fill.nta f93=[r15],loc0
+       ;;
+       ldf.fill.nta f101=[in0],loc1
+       ldf.fill.nta f109=[ r3],loc1
+       ldf.fill.nta f117=[r14],loc1
+       ldf.fill.nta f125=[r15],loc1
+       ;;
+       ldf.fill.nta f38 =[in0],loc0
+       ldf.fill.nta f46 =[ r3],loc0
+       ldf.fill.nta f54 =[r14],loc0
+       ldf.fill.nta f62 =[r15],loc0
+       ;;
+       ldf.fill.nta f70 =[in0],loc0
+       ldf.fill.nta f78 =[ r3],loc0
+       ldf.fill.nta f86 =[r14],loc0
+       ldf.fill.nta f94 =[r15],loc0
+       ;;
+       ldf.fill.nta f102=[in0],loc1
+       ldf.fill.nta f110=[ r3],loc1
+       ldf.fill.nta f118=[r14],loc1
+       ldf.fill.nta f126=[r15],loc1
+       ;;
+       ldf.fill.nta f39 =[in0],loc0
+       ldf.fill.nta f47 =[ r3],loc0
+       ldf.fill.nta f55 =[r14],loc0
+       ldf.fill.nta f63 =[r15],loc0
+       ;;
+       ldf.fill.nta f71 =[in0],loc0
+       ldf.fill.nta f79 =[ r3],loc0
+       ldf.fill.nta f87 =[r14],loc0
+       ldf.fill.nta f95 =[r15],loc0
+       ;;
+       ldf.fill.nta f103=[in0]
+       ldf.fill.nta f111=[ r3]
+       ldf.fill.nta f119=[r14]
+       ldf.fill.nta f127=[r15]
+       br.ret.sptk.many rp
+END(__ia64_load_fpu)
+
+GLOBAL_ENTRY(__ia64_init_fpu)
+       stf.spill [sp]=f0               // M3
+       mov      f32=f0                 // F
+       nop.b    0
+
+       ldfps    f33,f34=[sp]           // M0
+       ldfps    f35,f36=[sp]           // M1
+       mov      f37=f0                 // F
+       ;;
+
+       setf.s   f38=r0                 // M2
+       setf.s   f39=r0                 // M3
+       mov      f40=f0                 // F
+
+       ldfps    f41,f42=[sp]           // M0
+       ldfps    f43,f44=[sp]           // M1
+       mov      f45=f0                 // F
+
+       setf.s   f46=r0                 // M2
+       setf.s   f47=r0                 // M3
+       mov      f48=f0                 // F
+
+       ldfps    f49,f50=[sp]           // M0
+       ldfps    f51,f52=[sp]           // M1
+       mov      f53=f0                 // F
+
+       setf.s   f54=r0                 // M2
+       setf.s   f55=r0                 // M3
+       mov      f56=f0                 // F
+
+       ldfps    f57,f58=[sp]           // M0
+       ldfps    f59,f60=[sp]           // M1
+       mov      f61=f0                 // F
+
+       setf.s   f62=r0                 // M2
+       setf.s   f63=r0                 // M3
+       mov      f64=f0                 // F
+
+       ldfps    f65,f66=[sp]           // M0
+       ldfps    f67,f68=[sp]           // M1
+       mov      f69=f0                 // F
+
+       setf.s   f70=r0                 // M2
+       setf.s   f71=r0                 // M3
+       mov      f72=f0                 // F
+
+       ldfps    f73,f74=[sp]           // M0
+       ldfps    f75,f76=[sp]           // M1
+       mov      f77=f0                 // F
+
+       setf.s   f78=r0                 // M2
+       setf.s   f79=r0                 // M3
+       mov      f80=f0                 // F
+
+       ldfps    f81,f82=[sp]           // M0
+       ldfps    f83,f84=[sp]           // M1
+       mov      f85=f0                 // F
+
+       setf.s   f86=r0                 // M2
+       setf.s   f87=r0                 // M3
+       mov      f88=f0                 // F
+
+       /*
+        * When the instructions are cached, it would be faster to initialize
+        * the remaining registers with simply mov instructions (F-unit).
+        * This gets the time down to ~29 cycles.  However, this would use up
+        * 33 bundles, whereas continuing with the above pattern yields
+        * 10 bundles and ~30 cycles.
+        */
+
+       ldfps    f89,f90=[sp]           // M0
+       ldfps    f91,f92=[sp]           // M1
+       mov      f93=f0                 // F
+
+       setf.s   f94=r0                 // M2
+       setf.s   f95=r0                 // M3
+       mov      f96=f0                 // F
+
+       ldfps    f97,f98=[sp]           // M0
+       ldfps    f99,f100=[sp]          // M1
+       mov      f101=f0                // F
+
+       setf.s   f102=r0                // M2
+       setf.s   f103=r0                // M3
+       mov      f104=f0                // F
+
+       ldfps    f105,f106=[sp]         // M0
+       ldfps    f107,f108=[sp]         // M1
+       mov      f109=f0                // F
+
+       setf.s   f110=r0                // M2
+       setf.s   f111=r0                // M3
+       mov      f112=f0                // F
+
+       ldfps    f113,f114=[sp]         // M0
+       ldfps    f115,f116=[sp]         // M1
+       mov      f117=f0                // F
+
+       setf.s   f118=r0                // M2
+       setf.s   f119=r0                // M3
+       mov      f120=f0                // F
+
+       ldfps    f121,f122=[sp]         // M0
+       ldfps    f123,f124=[sp]         // M1
+       mov      f125=f0                // F
+
+       setf.s   f126=r0                // M2
+       setf.s   f127=r0                // M3
+       br.ret.sptk.many rp             // F
+END(__ia64_init_fpu)
+
+/*
+ * Switch execution mode from virtual to physical
+ *
+ * Inputs:
+ *     r16 = new psr to establish
+ * Output:
+ *     r19 = old virtual address of ar.bsp
+ *     r20 = old virtual address of sp
+ *
+ * Note: RSE must already be in enforced lazy mode
+ */
+GLOBAL_ENTRY(ia64_switch_mode_phys)
+ {
+       alloc r2=ar.pfs,0,0,0,0
+       rsm psr.i | psr.ic              // disable interrupts and interrupt 
collection
+       mov r15=ip
+ }
+       ;;
+ {
+       flushrs                         // must be first insn in group
+       srlz.i
+ }
+       ;;
+       mov cr.ipsr=r16                 // set new PSR
+       add r3=1f-ia64_switch_mode_phys,r15
+
+       mov r19=ar.bsp
+       mov r20=sp
+       mov r14=rp                      // get return address into a general 
register
+       ;;
+
+       // going to physical mode, use tpa to translate virt->phys
+       tpa r17=r19
+       tpa r3=r3
+       tpa sp=sp
+       tpa r14=r14
+       ;;
+
+       mov r18=ar.rnat                 // save ar.rnat
+       mov ar.bspstore=r17             // this steps on ar.rnat
+       mov cr.iip=r3
+       mov cr.ifs=r0
+       ;;
+       mov ar.rnat=r18                 // restore ar.rnat
+       rfi                             // must be last insn in group
+       ;;
+1:     mov rp=r14
+       br.ret.sptk.many rp
+END(ia64_switch_mode_phys)
+
+/*
+ * Switch execution mode from physical to virtual
+ *
+ * Inputs:
+ *     r16 = new psr to establish
+ *     r19 = new bspstore to establish
+ *     r20 = new sp to establish
+ *
+ * Note: RSE must already be in enforced lazy mode
+ */
+GLOBAL_ENTRY(ia64_switch_mode_virt)
+ {
+       alloc r2=ar.pfs,0,0,0,0
+       rsm psr.i | psr.ic              // disable interrupts and interrupt 
collection
+       mov r15=ip
+ }
+       ;;
+ {
+       flushrs                         // must be first insn in group
+       srlz.i
+ }
+       ;;
+       mov cr.ipsr=r16                 // set new PSR
+       add r3=1f-ia64_switch_mode_virt,r15
+
+       mov r14=rp                      // get return address into a general 
register
+       ;;
+
+       // going to virtual
+       //   - for code addresses, set upper bits of addr to KERNEL_START
+       //   - for stack addresses, copy from input argument
+       movl r18=KERNEL_START
+       dep r3=0,r3,KERNEL_TR_PAGE_SHIFT,64-KERNEL_TR_PAGE_SHIFT
+       dep r14=0,r14,KERNEL_TR_PAGE_SHIFT,64-KERNEL_TR_PAGE_SHIFT
+       mov sp=r20
+       ;;
+       or r3=r3,r18
+       or r14=r14,r18
+       ;;
+
+       mov r18=ar.rnat                 // save ar.rnat
+       mov ar.bspstore=r19             // this steps on ar.rnat
+       mov cr.iip=r3
+       mov cr.ifs=r0
+       ;;
+       mov ar.rnat=r18                 // restore ar.rnat
+       rfi                             // must be last insn in group
+       ;;
+1:     mov rp=r14
+       br.ret.sptk.many rp
+END(ia64_switch_mode_virt)
+
+GLOBAL_ENTRY(ia64_delay_loop)
+       .prologue
+{      nop 0                   // work around GAS unwind info generation bug...
+       .save ar.lc,r2
+       mov r2=ar.lc
+       .body
+       ;;
+       mov ar.lc=r32
+}
+       ;;
+       // force loop to be 32-byte aligned (GAS bug means we cannot use .align
+       // inside function body without corrupting unwind info).
+{      nop 0 }
+1:     br.cloop.sptk.few 1b
+       ;;
+       mov ar.lc=r2
+       br.ret.sptk.many rp
+END(ia64_delay_loop)
+
+/*
+ * Return a CPU-local timestamp in nano-seconds.  This timestamp is
+ * NOT synchronized across CPUs its return value must never be
+ * compared against the values returned on another CPU.  The usage in
+ * kernel/sched.c ensures that.
+ *
+ * The return-value of sched_clock() is NOT supposed to wrap-around.
+ * If it did, it would cause some scheduling hiccups (at the worst).
+ * Fortunately, with a 64-bit cycle-counter ticking at 100GHz, even
+ * that would happen only once every 5+ years.
+ *
+ * The code below basically calculates:
+ *
+ *   (ia64_get_itc() * local_cpu_data->nsec_per_cyc) >> IA64_NSEC_PER_CYC_SHIFT
+ *
+ * except that the multiplication and the shift are done with 128-bit
+ * intermediate precision so that we can produce a full 64-bit result.
+ */
+GLOBAL_ENTRY(sched_clock)
+#ifdef XEN
+       movl r8=THIS_CPU(cpu_info) + IA64_CPUINFO_NSEC_PER_CYC_OFFSET
+#else
+       addl r8=THIS_CPU(cpu_info) + IA64_CPUINFO_NSEC_PER_CYC_OFFSET,r0
+#endif
+       mov.m r9=ar.itc         // fetch cycle-counter                          
(35 cyc)
+       ;;
+       ldf8 f8=[r8]
+       ;;
+       setf.sig f9=r9          // certain to stall, so issue it _after_ ldf8...
+       ;;
+       xmpy.lu f10=f9,f8       // calculate low 64 bits of 128-bit product     
(4 cyc)
+       xmpy.hu f11=f9,f8       // calculate high 64 bits of 128-bit product
+       ;;
+       getf.sig r8=f10         //                                              
(5 cyc)
+       getf.sig r9=f11
+       ;;
+       shrp r8=r9,r8,IA64_NSEC_PER_CYC_SHIFT
+       br.ret.sptk.many rp
+END(sched_clock)
+
+GLOBAL_ENTRY(start_kernel_thread)
+       .prologue
+       .save rp, r0                            // this is the end of the 
call-chain
+       .body
+       alloc r2 = ar.pfs, 0, 0, 2, 0
+       mov out0 = r9
+       mov out1 = r11;;
+       br.call.sptk.many rp = kernel_thread_helper;;
+       mov out0 = r8
+       br.call.sptk.many rp = sys_exit;;
+1:     br.sptk.few 1b                          // not reached
+END(start_kernel_thread)
+
+#ifdef CONFIG_IA64_BRL_EMU
+
+/*
+ *  Assembly routines used by brl_emu.c to set preserved register state.
+ */
+
+#define SET_REG(reg)                           \
+ GLOBAL_ENTRY(ia64_set_##reg);                 \
+       alloc r16=ar.pfs,1,0,0,0;               \
+       mov reg=r32;                            \
+       ;;                                      \
+       br.ret.sptk.many rp;                    \
+ END(ia64_set_##reg)
+
+SET_REG(b1);
+SET_REG(b2);
+SET_REG(b3);
+SET_REG(b4);
+SET_REG(b5);
+
+#endif /* CONFIG_IA64_BRL_EMU */
+
+#ifdef CONFIG_SMP
+       /*
+        * This routine handles spinlock contention.  It uses a non-standard 
calling
+        * convention to avoid converting leaf routines into interior routines. 
 Because
+        * of this special convention, there are several restrictions:
+        *
+        * - do not use gp relative variables, this code is called from the 
kernel
+        *   and from modules, r1 is undefined.
+        * - do not use stacked registers, the caller owns them.
+        * - do not use the scratch stack space, the caller owns it.
+        * - do not use any registers other than the ones listed below
+        *
+        * Inputs:
+        *   ar.pfs - saved CFM of caller
+        *   ar.ccv - 0 (and available for use)
+        *   r27    - flags from spin_lock_irqsave or 0.  Must be preserved.
+        *   r28    - available for use.
+        *   r29    - available for use.
+        *   r30    - available for use.
+        *   r31    - address of lock, available for use.
+        *   b6     - return address
+        *   p14    - available for use.
+        *   p15    - used to track flag status.
+        *
+        * If you patch this code to use more registers, do not forget to update
+        * the clobber lists for spin_lock() in include/asm-ia64/spinlock.h.
+        */
+
+#if __GNUC__ < 3 || (__GNUC__ == 3 && __GNUC_MINOR__ < 3)
+
+GLOBAL_ENTRY(ia64_spinlock_contention_pre3_4)
+       .prologue
+       .save ar.pfs, r0        // this code effectively has a zero frame size
+       .save rp, r28
+       .body
+       nop 0
+       tbit.nz p15,p0=r27,IA64_PSR_I_BIT
+       .restore sp             // pop existing prologue after next insn
+       mov b6 = r28
+       .prologue
+       .save ar.pfs, r0
+       .altrp b6
+       .body
+       ;;
+(p15)  ssm psr.i               // reenable interrupts if they were on
+                               // DavidM says that srlz.d is slow and is not 
required in this case
+.wait:
+       // exponential backoff, kdb, lockmeter etc. go in here
+       hint @pause
+       ld4 r30=[r31]           // don't use ld4.bias; if it's contended, we 
won't write the word
+       nop 0
+       ;;
+       cmp4.ne p14,p0=r30,r0
+(p14)  br.cond.sptk.few .wait
+(p15)  rsm psr.i               // disable interrupts if we reenabled them
+       br.cond.sptk.few b6     // lock is now free, try to acquire
+       .global ia64_spinlock_contention_pre3_4_end     // for kernprof
+ia64_spinlock_contention_pre3_4_end:
+END(ia64_spinlock_contention_pre3_4)
+
+#else
+
+GLOBAL_ENTRY(ia64_spinlock_contention)
+       .prologue
+       .altrp b6
+       .body
+       tbit.nz p15,p0=r27,IA64_PSR_I_BIT
+       ;;
+.wait:
+(p15)  ssm psr.i               // reenable interrupts if they were on
+                               // DavidM says that srlz.d is slow and is not 
required in this case
+.wait2:
+       // exponential backoff, kdb, lockmeter etc. go in here
+       hint @pause
+       ld4 r30=[r31]           // don't use ld4.bias; if it's contended, we 
won't write the word
+       ;;
+       cmp4.ne p14,p0=r30,r0
+       mov r30 = 1
+(p14)  br.cond.sptk.few .wait2
+(p15)  rsm psr.i               // disable interrupts if we reenabled them
+       ;;
+       cmpxchg4.acq r30=[r31], r30, ar.ccv
+       ;;
+       cmp4.ne p14,p0=r0,r30
+(p14)  br.cond.sptk.few .wait
+
+       br.ret.sptk.many b6     // lock is now taken
+END(ia64_spinlock_contention)
+
+#endif
+
+#endif /* CONFIG_SMP */
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/irq_ia64.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/irq_ia64.c        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,381 @@
+/*
+ * linux/arch/ia64/kernel/irq.c
+ *
+ * Copyright (C) 1998-2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ *  6/10/99: Updated to bring in sync with x86 version to facilitate
+ *          support for SMP and different interrupt controllers.
+ *
+ * 09/15/00 Goutham Rao <goutham.rao@xxxxxxxxx> Implemented pci_irq_to_vector
+ *                      PCI to vector allocation routine.
+ * 04/14/2004 Ashok Raj <ashok.raj@xxxxxxxxx>
+ *                                             Added CPU Hotplug handling for 
IPF.
+ */
+
+#include <linux/config.h>
+#include <linux/module.h>
+
+#include <linux/jiffies.h>
+#include <linux/errno.h>
+#include <linux/init.h>
+#include <linux/interrupt.h>
+#include <linux/ioport.h>
+#include <linux/kernel_stat.h>
+#include <linux/slab.h>
+#include <linux/ptrace.h>
+#include <linux/random.h>      /* for rand_initialize_irq() */
+#include <linux/signal.h>
+#include <linux/smp.h>
+#include <linux/smp_lock.h>
+#include <linux/threads.h>
+#include <linux/bitops.h>
+
+#include <asm/delay.h>
+#include <asm/intrinsics.h>
+#include <asm/io.h>
+#include <asm/hw_irq.h>
+#include <asm/machvec.h>
+#include <asm/pgtable.h>
+#include <asm/system.h>
+
+#ifdef CONFIG_PERFMON
+# include <asm/perfmon.h>
+#endif
+
+#define IRQ_DEBUG      0
+
+/* default base addr of IPI table */
+void __iomem *ipi_base_addr = ((void __iomem *)
+                              (__IA64_UNCACHED_OFFSET | 
IA64_IPI_DEFAULT_BASE_ADDR));
+
+/*
+ * Legacy IRQ to IA-64 vector translation table.
+ */
+__u8 isa_irq_to_vector_map[16] = {
+       /* 8259 IRQ translation, first 16 entries */
+       0x2f, 0x20, 0x2e, 0x2d, 0x2c, 0x2b, 0x2a, 0x29,
+       0x28, 0x27, 0x26, 0x25, 0x24, 0x23, 0x22, 0x21
+};
+EXPORT_SYMBOL(isa_irq_to_vector_map);
+
+static unsigned long ia64_vector_mask[BITS_TO_LONGS(IA64_NUM_DEVICE_VECTORS)];
+
+int
+assign_irq_vector (int irq)
+{
+       int pos, vector;
+ again:
+       pos = find_first_zero_bit(ia64_vector_mask, IA64_NUM_DEVICE_VECTORS);
+       vector = IA64_FIRST_DEVICE_VECTOR + pos;
+       if (vector > IA64_LAST_DEVICE_VECTOR)
+               /* XXX could look for sharable vectors instead of panic'ing... 
*/
+               panic("assign_irq_vector: out of interrupt vectors!");
+       if (test_and_set_bit(pos, ia64_vector_mask))
+               goto again;
+       return vector;
+}
+
+void
+free_irq_vector (int vector)
+{
+       int pos;
+
+       if (vector < IA64_FIRST_DEVICE_VECTOR || vector > 
IA64_LAST_DEVICE_VECTOR)
+               return;
+
+       pos = vector - IA64_FIRST_DEVICE_VECTOR;
+       if (!test_and_clear_bit(pos, ia64_vector_mask))
+               printk(KERN_WARNING "%s: double free!\n", __FUNCTION__);
+}
+
+#ifdef CONFIG_SMP
+#      define IS_RESCHEDULE(vec)       (vec == IA64_IPI_RESCHEDULE)
+#else
+#      define IS_RESCHEDULE(vec)       (0)
+#endif
+/*
+ * That's where the IVT branches when we get an external
+ * interrupt. This branches to the correct hardware IRQ handler via
+ * function ptr.
+ */
+void
+ia64_handle_irq (ia64_vector vector, struct pt_regs *regs)
+{
+       unsigned long saved_tpr;
+
+#if IRQ_DEBUG
+#ifdef XEN
+       xen_debug_irq(vector, regs);
+#endif
+       {
+               unsigned long bsp, sp;
+
+               /*
+                * Note: if the interrupt happened while executing in
+                * the context switch routine (ia64_switch_to), we may
+                * get a spurious stack overflow here.  This is
+                * because the register and the memory stack are not
+                * switched atomically.
+                */
+               bsp = ia64_getreg(_IA64_REG_AR_BSP);
+               sp = ia64_getreg(_IA64_REG_SP);
+
+               if ((sp - bsp) < 1024) {
+                       static unsigned char count;
+                       static long last_time;
+
+                       if (jiffies - last_time > 5*HZ)
+                               count = 0;
+                       if (++count < 5) {
+                               last_time = jiffies;
+                               printk("ia64_handle_irq: DANGER: less than "
+                                      "1KB of free stack space!!\n"
+                                      "(bsp=0x%lx, sp=%lx)\n", bsp, sp);
+                       }
+               }
+       }
+#endif /* IRQ_DEBUG */
+
+       /*
+        * Always set TPR to limit maximum interrupt nesting depth to
+        * 16 (without this, it would be ~240, which could easily lead
+        * to kernel stack overflows).
+        */
+       irq_enter();
+       saved_tpr = ia64_getreg(_IA64_REG_CR_TPR);
+       ia64_srlz_d();
+       while (vector != IA64_SPURIOUS_INT_VECTOR) {
+               if (!IS_RESCHEDULE(vector)) {
+                       ia64_setreg(_IA64_REG_CR_TPR, vector);
+                       ia64_srlz_d();
+
+#ifdef XEN
+                       if (!xen_do_IRQ(vector))
+#endif
+                       __do_IRQ(local_vector_to_irq(vector), regs);
+
+                       /*
+                        * Disable interrupts and send EOI:
+                        */
+                       local_irq_disable();
+                       ia64_setreg(_IA64_REG_CR_TPR, saved_tpr);
+               }
+               ia64_eoi();
+               vector = ia64_get_ivr();
+       }
+       /*
+        * This must be done *after* the ia64_eoi().  For example, the keyboard 
softirq
+        * handler needs to be able to wait for further keyboard interrupts, 
which can't
+        * come through until ia64_eoi() has been done.
+        */
+       irq_exit();
+}
+
+#ifdef  CONFIG_VTI
+#define vmx_irq_enter()                \
+       add_preempt_count(HARDIRQ_OFFSET);
+
+/* Now softirq will be checked when leaving hypervisor, or else
+ * scheduler irq will be executed too early.
+ */
+#define vmx_irq_exit(void)     \
+       sub_preempt_count(HARDIRQ_OFFSET);
+/*
+ * That's where the IVT branches when we get an external
+ * interrupt. This branches to the correct hardware IRQ handler via
+ * function ptr.
+ */
+void
+vmx_ia64_handle_irq (ia64_vector vector, struct pt_regs *regs)
+{
+       unsigned long saved_tpr;
+       int     wake_dom0 = 0;
+
+
+#if IRQ_DEBUG
+       {
+               unsigned long bsp, sp;
+
+               /*
+                * Note: if the interrupt happened while executing in
+                * the context switch routine (ia64_switch_to), we may
+                * get a spurious stack overflow here.  This is
+                * because the register and the memory stack are not
+                * switched atomically.
+                */
+               bsp = ia64_getreg(_IA64_REG_AR_BSP);
+               sp = ia64_getreg(_IA64_REG_AR_SP);
+
+               if ((sp - bsp) < 1024) {
+                       static unsigned char count;
+                       static long last_time;
+
+                       if (jiffies - last_time > 5*HZ)
+                               count = 0;
+                       if (++count < 5) {
+                               last_time = jiffies;
+                               printk("ia64_handle_irq: DANGER: less than "
+                                      "1KB of free stack space!!\n"
+                                      "(bsp=0x%lx, sp=%lx)\n", bsp, sp);
+                       }
+               }
+       }
+#endif /* IRQ_DEBUG */
+
+       /*
+        * Always set TPR to limit maximum interrupt nesting depth to
+        * 16 (without this, it would be ~240, which could easily lead
+        * to kernel stack overflows).
+        */
+       vmx_irq_enter();
+       saved_tpr = ia64_getreg(_IA64_REG_CR_TPR);
+       ia64_srlz_d();
+       while (vector != IA64_SPURIOUS_INT_VECTOR) {
+           if (!IS_RESCHEDULE(vector)) {
+               ia64_setreg(_IA64_REG_CR_TPR, vector);
+               ia64_srlz_d();
+
+               if (vector != IA64_TIMER_VECTOR) {
+                       /* FIXME: Leave IRQ re-route later */
+                       vmx_vcpu_pend_interrupt(dom0->vcpu[0],vector);
+                       wake_dom0 = 1;
+               }
+               else {  // FIXME: Handle Timer only now
+                       __do_IRQ(local_vector_to_irq(vector), regs);
+               }
+               
+               /*
+                * Disable interrupts and send EOI:
+                */
+               local_irq_disable();
+               ia64_setreg(_IA64_REG_CR_TPR, saved_tpr);
+           }
+           else {
+                printf("Oops: RESCHEDULE IPI absorbed by HV\n");
+            }
+           ia64_eoi();
+           vector = ia64_get_ivr();
+       }
+       /*
+        * This must be done *after* the ia64_eoi().  For example, the keyboard 
softirq
+        * handler needs to be able to wait for further keyboard interrupts, 
which can't
+        * come through until ia64_eoi() has been done.
+        */
+       vmx_irq_exit();
+       if ( wake_dom0 && current != dom0 ) 
+               domain_wake(dom0->vcpu[0]);
+}
+#endif
+
+
+#ifdef CONFIG_HOTPLUG_CPU
+/*
+ * This function emulates a interrupt processing when a cpu is about to be
+ * brought down.
+ */
+void ia64_process_pending_intr(void)
+{
+       ia64_vector vector;
+       unsigned long saved_tpr;
+       extern unsigned int vectors_in_migration[NR_IRQS];
+
+       vector = ia64_get_ivr();
+
+        irq_enter();
+        saved_tpr = ia64_getreg(_IA64_REG_CR_TPR);
+        ia64_srlz_d();
+
+        /*
+         * Perform normal interrupt style processing
+         */
+       while (vector != IA64_SPURIOUS_INT_VECTOR) {
+               if (!IS_RESCHEDULE(vector)) {
+                       ia64_setreg(_IA64_REG_CR_TPR, vector);
+                       ia64_srlz_d();
+
+                       /*
+                        * Now try calling normal ia64_handle_irq as it would 
have got called
+                        * from a real intr handler. Try passing null for 
pt_regs, hopefully
+                        * it will work. I hope it works!.
+                        * Probably could shared code.
+                        */
+                       vectors_in_migration[local_vector_to_irq(vector)]=0;
+                       __do_IRQ(local_vector_to_irq(vector), NULL);
+
+                       /*
+                        * Disable interrupts and send EOI
+                        */
+                       local_irq_disable();
+                       ia64_setreg(_IA64_REG_CR_TPR, saved_tpr);
+               }
+               ia64_eoi();
+               vector = ia64_get_ivr();
+       }
+       irq_exit();
+}
+#endif
+
+
+#ifdef CONFIG_SMP
+extern irqreturn_t handle_IPI (int irq, void *dev_id, struct pt_regs *regs);
+
+static struct irqaction ipi_irqaction = {
+       .handler =      handle_IPI,
+       .flags =        SA_INTERRUPT,
+       .name =         "IPI"
+};
+#endif
+
+void
+register_percpu_irq (ia64_vector vec, struct irqaction *action)
+{
+       irq_desc_t *desc;
+       unsigned int irq;
+
+       for (irq = 0; irq < NR_IRQS; ++irq)
+               if (irq_to_vector(irq) == vec) {
+                       desc = irq_descp(irq);
+                       desc->status |= IRQ_PER_CPU;
+                       desc->handler = &irq_type_ia64_lsapic;
+                       if (action)
+                               setup_irq(irq, action);
+               }
+}
+
+void __init
+init_IRQ (void)
+{
+       register_percpu_irq(IA64_SPURIOUS_INT_VECTOR, NULL);
+#ifdef CONFIG_SMP
+       register_percpu_irq(IA64_IPI_VECTOR, &ipi_irqaction);
+#endif
+#ifdef CONFIG_PERFMON
+       pfm_init_percpu();
+#endif
+       platform_irq_init();
+}
+
+void
+ia64_send_ipi (int cpu, int vector, int delivery_mode, int redirect)
+{
+       void __iomem *ipi_addr;
+       unsigned long ipi_data;
+       unsigned long phys_cpu_id;
+
+#ifdef CONFIG_SMP
+       phys_cpu_id = cpu_physical_id(cpu);
+#else
+       phys_cpu_id = (ia64_getreg(_IA64_REG_CR_LID) >> 16) & 0xffff;
+#endif
+
+       /*
+        * cpu number is in 8bit ID and 8bit EID
+        */
+
+       ipi_data = (delivery_mode << 8) | (vector & 0xff);
+       ipi_addr = ipi_base_addr + ((phys_cpu_id << 4) | ((redirect & 1) << 3));
+
+       writeq(ipi_data, ipi_addr);
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/mm_contig.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/mm_contig.c       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,305 @@
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 2000, Rohit Seth <rohit.seth@xxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 2003 Silicon Graphics, Inc. All rights reserved.
+ *
+ * Routines used by ia64 machines with contiguous (or virtually contiguous)
+ * memory.
+ */
+#include <linux/config.h>
+#include <linux/bootmem.h>
+#include <linux/efi.h>
+#include <linux/mm.h>
+#include <linux/swap.h>
+
+#include <asm/meminit.h>
+#include <asm/pgalloc.h>
+#include <asm/pgtable.h>
+#include <asm/sections.h>
+#include <asm/mca.h>
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+static unsigned long num_dma_physpages;
+#endif
+
+/**
+ * show_mem - display a memory statistics summary
+ *
+ * Just walks the pages in the system and describes where they're allocated.
+ */
+#ifndef XEN
+void
+show_mem (void)
+{
+       int i, total = 0, reserved = 0;
+       int shared = 0, cached = 0;
+
+       printk("Mem-info:\n");
+       show_free_areas();
+
+       printk("Free swap:       %6ldkB\n", nr_swap_pages<<(PAGE_SHIFT-10));
+       i = max_mapnr;
+       while (i-- > 0) {
+               if (!pfn_valid(i))
+                       continue;
+               total++;
+               if (PageReserved(mem_map+i))
+                       reserved++;
+               else if (PageSwapCache(mem_map+i))
+                       cached++;
+               else if (page_count(mem_map + i))
+                       shared += page_count(mem_map + i) - 1;
+       }
+       printk("%d pages of RAM\n", total);
+       printk("%d reserved pages\n", reserved);
+       printk("%d pages shared\n", shared);
+       printk("%d pages swap cached\n", cached);
+       printk("%ld pages in page table cache\n", pgtable_cache_size);
+}
+#endif
+
+/* physical address where the bootmem map is located */
+unsigned long bootmap_start;
+
+/**
+ * find_max_pfn - adjust the maximum page number callback
+ * @start: start of range
+ * @end: end of range
+ * @arg: address of pointer to global max_pfn variable
+ *
+ * Passed as a callback function to efi_memmap_walk() to determine the highest
+ * available page frame number in the system.
+ */
+int
+find_max_pfn (unsigned long start, unsigned long end, void *arg)
+{
+       unsigned long *max_pfnp = arg, pfn;
+
+       pfn = (PAGE_ALIGN(end - 1) - PAGE_OFFSET) >> PAGE_SHIFT;
+       if (pfn > *max_pfnp)
+               *max_pfnp = pfn;
+       return 0;
+}
+
+/**
+ * find_bootmap_location - callback to find a memory area for the bootmap
+ * @start: start of region
+ * @end: end of region
+ * @arg: unused callback data
+ *
+ * Find a place to put the bootmap and return its starting address in
+ * bootmap_start.  This address must be page-aligned.
+ */
+int
+find_bootmap_location (unsigned long start, unsigned long end, void *arg)
+{
+       unsigned long needed = *(unsigned long *)arg;
+       unsigned long range_start, range_end, free_start;
+       int i;
+
+#if IGNORE_PFN0
+       if (start == PAGE_OFFSET) {
+               start += PAGE_SIZE;
+               if (start >= end)
+                       return 0;
+       }
+#endif
+
+       free_start = PAGE_OFFSET;
+
+       for (i = 0; i < num_rsvd_regions; i++) {
+               range_start = max(start, free_start);
+               range_end   = min(end, rsvd_region[i].start & PAGE_MASK);
+
+               free_start = PAGE_ALIGN(rsvd_region[i].end);
+
+               if (range_end <= range_start)
+                       continue; /* skip over empty range */
+
+               if (range_end - range_start >= needed) {
+                       bootmap_start = __pa(range_start);
+                       return -1;      /* done */
+               }
+
+               /* nothing more available in this segment */
+               if (range_end == end)
+                       return 0;
+       }
+       return 0;
+}
+
+/**
+ * find_memory - setup memory map
+ *
+ * Walk the EFI memory map and find usable memory for the system, taking
+ * into account reserved areas.
+ */
+#ifndef XEN
+void
+find_memory (void)
+{
+       unsigned long bootmap_size;
+
+       reserve_memory();
+
+       /* first find highest page frame number */
+       max_pfn = 0;
+       efi_memmap_walk(find_max_pfn, &max_pfn);
+
+       /* how many bytes to cover all the pages */
+       bootmap_size = bootmem_bootmap_pages(max_pfn) << PAGE_SHIFT;
+
+       /* look for a location to hold the bootmap */
+       bootmap_start = ~0UL;
+       efi_memmap_walk(find_bootmap_location, &bootmap_size);
+       if (bootmap_start == ~0UL)
+               panic("Cannot find %ld bytes for bootmap\n", bootmap_size);
+
+       bootmap_size = init_bootmem(bootmap_start >> PAGE_SHIFT, max_pfn);
+
+       /* Free all available memory, then mark bootmem-map as being in use. */
+       efi_memmap_walk(filter_rsvd_memory, free_bootmem);
+       reserve_bootmem(bootmap_start, bootmap_size);
+
+       find_initrd();
+}
+#endif
+
+#ifdef CONFIG_SMP
+/**
+ * per_cpu_init - setup per-cpu variables
+ *
+ * Allocate and setup per-cpu data areas.
+ */
+void *
+per_cpu_init (void)
+{
+       void *cpu_data;
+       int cpu;
+
+       /*
+        * get_free_pages() cannot be used before cpu_init() done.  BSP
+        * allocates "NR_CPUS" pages for all CPUs to avoid that AP calls
+        * get_zeroed_page().
+        */
+       if (smp_processor_id() == 0) {
+               cpu_data = __alloc_bootmem(PERCPU_PAGE_SIZE * NR_CPUS,
+                                          PERCPU_PAGE_SIZE, 
__pa(MAX_DMA_ADDRESS));
+               for (cpu = 0; cpu < NR_CPUS; cpu++) {
+                       memcpy(cpu_data, __phys_per_cpu_start, __per_cpu_end - 
__per_cpu_start);
+                       __per_cpu_offset[cpu] = (char *) cpu_data - 
__per_cpu_start;
+                       cpu_data += PERCPU_PAGE_SIZE;
+                       per_cpu(local_per_cpu_offset, cpu) = 
__per_cpu_offset[cpu];
+               }
+       }
+       return __per_cpu_start + __per_cpu_offset[smp_processor_id()];
+}
+#endif /* CONFIG_SMP */
+
+static int
+count_pages (u64 start, u64 end, void *arg)
+{
+       unsigned long *count = arg;
+
+       *count += (end - start) >> PAGE_SHIFT;
+       return 0;
+}
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+static int
+count_dma_pages (u64 start, u64 end, void *arg)
+{
+       unsigned long *count = arg;
+
+       if (start < MAX_DMA_ADDRESS)
+               *count += (min(end, MAX_DMA_ADDRESS) - start) >> PAGE_SHIFT;
+       return 0;
+}
+#endif
+
+/*
+ * Set up the page tables.
+ */
+
+#ifndef XEN
+void
+paging_init (void)
+{
+       unsigned long max_dma;
+       unsigned long zones_size[MAX_NR_ZONES];
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+       unsigned long zholes_size[MAX_NR_ZONES];
+       unsigned long max_gap;
+#endif
+
+       /* initialize mem_map[] */
+
+       memset(zones_size, 0, sizeof(zones_size));
+
+       num_physpages = 0;
+       efi_memmap_walk(count_pages, &num_physpages);
+
+       max_dma = virt_to_phys((void *) MAX_DMA_ADDRESS) >> PAGE_SHIFT;
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+       memset(zholes_size, 0, sizeof(zholes_size));
+
+       num_dma_physpages = 0;
+       efi_memmap_walk(count_dma_pages, &num_dma_physpages);
+
+       if (max_low_pfn < max_dma) {
+               zones_size[ZONE_DMA] = max_low_pfn;
+               zholes_size[ZONE_DMA] = max_low_pfn - num_dma_physpages;
+       } else {
+               zones_size[ZONE_DMA] = max_dma;
+               zholes_size[ZONE_DMA] = max_dma - num_dma_physpages;
+               if (num_physpages > num_dma_physpages) {
+                       zones_size[ZONE_NORMAL] = max_low_pfn - max_dma;
+                       zholes_size[ZONE_NORMAL] =
+                               ((max_low_pfn - max_dma) -
+                                (num_physpages - num_dma_physpages));
+               }
+       }
+
+       max_gap = 0;
+       efi_memmap_walk(find_largest_hole, (u64 *)&max_gap);
+       if (max_gap < LARGE_GAP) {
+               vmem_map = (struct page *) 0;
+               free_area_init_node(0, &contig_page_data, zones_size, 0,
+                                   zholes_size);
+       } else {
+               unsigned long map_size;
+
+               /* allocate virtual_mem_map */
+
+               map_size = PAGE_ALIGN(max_low_pfn * sizeof(struct page));
+               vmalloc_end -= map_size;
+               vmem_map = (struct page *) vmalloc_end;
+               efi_memmap_walk(create_mem_map_page_table, NULL);
+
+               mem_map = contig_page_data.node_mem_map = vmem_map;
+               free_area_init_node(0, &contig_page_data, zones_size,
+                                   0, zholes_size);
+
+               printk("Virtual mem_map starts at 0x%p\n", mem_map);
+       }
+#else /* !CONFIG_VIRTUAL_MEM_MAP */
+       if (max_low_pfn < max_dma)
+               zones_size[ZONE_DMA] = max_low_pfn;
+       else {
+               zones_size[ZONE_DMA] = max_dma;
+               zones_size[ZONE_NORMAL] = max_low_pfn - max_dma;
+       }
+       free_area_init(zones_size);
+#endif /* !CONFIG_VIRTUAL_MEM_MAP */
+       zero_page_memmap_ptr = virt_to_page(ia64_imva(empty_zero_page));
+}
+#endif /* !CONFIG_XEN */
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/pal.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/pal.S     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,310 @@
+/*
+ * PAL Firmware support
+ * IA-64 Processor Programmers Reference Vol 2
+ *
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999-2001, 2003 Hewlett-Packard Co
+ *     David Mosberger <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * 05/22/2000 eranian Added support for stacked register calls
+ * 05/24/2000 eranian Added support for physical mode static calls
+ */
+
+#include <asm/asmmacro.h>
+#include <asm/processor.h>
+
+       .data
+pal_entry_point:
+       data8 ia64_pal_default_handler
+       .text
+
+/*
+ * Set the PAL entry point address.  This could be written in C code, but we 
do it here
+ * to keep it all in one module (besides, it's so trivial that it's
+ * not a big deal).
+ *
+ * in0         Address of the PAL entry point (text address, NOT a function 
descriptor).
+ */
+GLOBAL_ENTRY(ia64_pal_handler_init)
+       alloc r3=ar.pfs,1,0,0,0
+       movl r2=pal_entry_point
+       ;;
+       st8 [r2]=in0
+       br.ret.sptk.many rp
+END(ia64_pal_handler_init)
+
+/*
+ * Default PAL call handler.  This needs to be coded in assembly because it 
uses
+ * the static calling convention, i.e., the RSE may not be used and calls are
+ * done via "br.cond" (not "br.call").
+ */
+GLOBAL_ENTRY(ia64_pal_default_handler)
+       mov r8=-1
+       br.cond.sptk.many rp
+END(ia64_pal_default_handler)
+
+/*
+ * Make a PAL call using the static calling convention.
+ *
+ * in0         Index of PAL service
+ * in1 - in3   Remaining PAL arguments
+ * in4        1 ==> clear psr.ic,  0 ==> don't clear psr.ic
+ *
+ */
+GLOBAL_ENTRY(ia64_pal_call_static)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(5)
+       alloc loc1 = ar.pfs,5,5,0,0
+       movl loc2 = pal_entry_point
+1:     {
+         mov r28 = in0
+         mov r29 = in1
+         mov r8 = ip
+       }
+       ;;
+       ld8 loc2 = [loc2]               // loc2 <- entry point
+       tbit.nz p6,p7 = in4, 0
+       adds r8 = 1f-1b,r8
+       mov loc4=ar.rsc                 // save RSE configuration
+       ;;
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       mov loc3 = psr
+       mov loc0 = rp
+       .body
+       mov r30 = in2
+
+(p6)   rsm psr.i | psr.ic
+       mov r31 = in3
+       mov b7 = loc2
+
+(p7)   rsm psr.i
+       ;;
+(p6)   srlz.i
+       mov rp = r8
+       br.cond.sptk.many b7
+1:     mov psr.l = loc3
+       mov ar.rsc = loc4               // restore RSE configuration
+       mov ar.pfs = loc1
+       mov rp = loc0
+       ;;
+       srlz.d                          // seralize restoration of psr.l
+       br.ret.sptk.many b0
+END(ia64_pal_call_static)
+
+/*
+ * Make a PAL call using the stacked registers calling convention.
+ *
+ * Inputs:
+ *     in0         Index of PAL service
+ *     in2 - in3   Remaning PAL arguments
+ */
+GLOBAL_ENTRY(ia64_pal_call_stacked)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(4)
+       alloc loc1 = ar.pfs,4,4,4,0
+       movl loc2 = pal_entry_point
+
+       mov r28  = in0                  // Index MUST be copied to r28
+       mov out0 = in0                  // AND in0 of PAL function
+       mov loc0 = rp
+       .body
+       ;;
+       ld8 loc2 = [loc2]               // loc2 <- entry point
+       mov out1 = in1
+       mov out2 = in2
+       mov out3 = in3
+       mov loc3 = psr
+       ;;
+       rsm psr.i
+       mov b7 = loc2
+       ;;
+       br.call.sptk.many rp=b7         // now make the call
+.ret0: mov psr.l  = loc3
+       mov ar.pfs = loc1
+       mov rp = loc0
+       ;;
+       srlz.d                          // serialize restoration of psr.l
+       br.ret.sptk.many b0
+END(ia64_pal_call_stacked)
+
+/*
+ * Make a physical mode PAL call using the static registers calling convention.
+ *
+ * Inputs:
+ *     in0         Index of PAL service
+ *     in2 - in3   Remaning PAL arguments
+ *
+ * PSR_LP, PSR_TB, PSR_ID, PSR_DA are never set by the kernel.
+ * So we don't need to clear them.
+ */
+#define PAL_PSR_BITS_TO_CLEAR                                                  
\
+       (IA64_PSR_I | IA64_PSR_IT | IA64_PSR_DT  | IA64_PSR_DB | IA64_PSR_RT |  
\
+        IA64_PSR_DD | IA64_PSR_SS | IA64_PSR_RI | IA64_PSR_ED |                
\
+        IA64_PSR_DFL | IA64_PSR_DFH)
+
+#define PAL_PSR_BITS_TO_SET                                                    
\
+       (IA64_PSR_BN)
+
+
+GLOBAL_ENTRY(ia64_pal_call_phys_static)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(4)
+       alloc loc1 = ar.pfs,4,7,0,0
+       movl loc2 = pal_entry_point
+1:     {
+         mov r28  = in0                // copy procedure index
+         mov r8   = ip                 // save ip to compute branch
+         mov loc0 = rp                 // save rp
+       }
+       .body
+       ;;
+       ld8 loc2 = [loc2]               // loc2 <- entry point
+       mov r29  = in1                  // first argument
+       mov r30  = in2                  // copy arg2
+       mov r31  = in3                  // copy arg3
+       ;;
+       mov loc3 = psr                  // save psr
+       adds r8  = 1f-1b,r8             // calculate return address for call
+       ;;
+       mov loc4=ar.rsc                 // save RSE configuration
+#ifdef XEN
+       dep.z loc2=loc2,0,60            // convert pal entry point to physical
+#else // XEN
+       dep.z loc2=loc2,0,61            // convert pal entry point to physical
+#endif // XEN
+       tpa r8=r8                       // convert rp to physical
+       ;;
+       mov b7 = loc2                   // install target to branch reg
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       movl r16=PAL_PSR_BITS_TO_CLEAR
+       movl r17=PAL_PSR_BITS_TO_SET
+       ;;
+       or loc3=loc3,r17                // add in psr the bits to set
+       ;;
+       andcm r16=loc3,r16              // removes bits to clear from psr
+       br.call.sptk.many rp=ia64_switch_mode_phys
+.ret1: mov rp = r8                     // install return address (physical)
+       mov loc5 = r19
+       mov loc6 = r20
+       br.cond.sptk.many b7
+1:
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       mov r16=loc3                    // r16= original psr
+       mov r19=loc5
+       mov r20=loc6
+       br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode
+.ret2:
+       mov psr.l = loc3                // restore init PSR
+
+       mov ar.pfs = loc1
+       mov rp = loc0
+       ;;
+       mov ar.rsc=loc4                 // restore RSE configuration
+       srlz.d                          // seralize restoration of psr.l
+       br.ret.sptk.many b0
+END(ia64_pal_call_phys_static)
+
+/*
+ * Make a PAL call using the stacked registers in physical mode.
+ *
+ * Inputs:
+ *     in0         Index of PAL service
+ *     in2 - in3   Remaning PAL arguments
+ */
+GLOBAL_ENTRY(ia64_pal_call_phys_stacked)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(5)
+       alloc   loc1 = ar.pfs,5,7,4,0
+       movl    loc2 = pal_entry_point
+1:     {
+         mov r28  = in0                // copy procedure index
+         mov loc0 = rp         // save rp
+       }
+       .body
+       ;;
+       ld8 loc2 = [loc2]               // loc2 <- entry point
+       mov out0 = in0          // first argument
+       mov out1 = in1          // copy arg2
+       mov out2 = in2          // copy arg3
+       mov out3 = in3          // copy arg3
+       ;;
+       mov loc3 = psr          // save psr
+       ;;
+       mov loc4=ar.rsc                 // save RSE configuration
+#ifdef XEN
+       dep.z loc2=loc2,0,60            // convert pal entry point to physical
+#else // XEN
+       dep.z loc2=loc2,0,61            // convert pal entry point to physical
+#endif // XEN
+       ;;
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       movl r16=PAL_PSR_BITS_TO_CLEAR
+       movl r17=PAL_PSR_BITS_TO_SET
+       ;;
+       or loc3=loc3,r17                // add in psr the bits to set
+       mov b7 = loc2                   // install target to branch reg
+       ;;
+       andcm r16=loc3,r16              // removes bits to clear from psr
+       br.call.sptk.many rp=ia64_switch_mode_phys
+.ret6:
+       mov loc5 = r19
+       mov loc6 = r20
+       br.call.sptk.many rp=b7         // now make the call
+.ret7:
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       mov r16=loc3                    // r16= original psr
+       mov r19=loc5
+       mov r20=loc6
+       br.call.sptk.many rp=ia64_switch_mode_virt      // return to virtual 
mode
+
+.ret8: mov psr.l  = loc3               // restore init PSR
+       mov ar.pfs = loc1
+       mov rp = loc0
+       ;;
+       mov ar.rsc=loc4                 // restore RSE configuration
+       srlz.d                          // seralize restoration of psr.l
+       br.ret.sptk.many b0
+END(ia64_pal_call_phys_stacked)
+
+/*
+ * Save scratch fp scratch regs which aren't saved in pt_regs already 
(fp10-fp15).
+ *
+ * NOTE: We need to do this since firmware (SAL and PAL) may use any of the 
scratch
+ * regs fp-low partition.
+ *
+ * Inputs:
+ *      in0    Address of stack storage for fp regs
+ */
+GLOBAL_ENTRY(ia64_save_scratch_fpregs)
+       alloc r3=ar.pfs,1,0,0,0
+       add r2=16,in0
+       ;;
+       stf.spill [in0] = f10,32
+       stf.spill [r2]  = f11,32
+       ;;
+       stf.spill [in0] = f12,32
+       stf.spill [r2]  = f13,32
+       ;;
+       stf.spill [in0] = f14,32
+       stf.spill [r2]  = f15,32
+       br.ret.sptk.many rp
+END(ia64_save_scratch_fpregs)
+
+/*
+ * Load scratch fp scratch regs (fp10-fp15)
+ *
+ * Inputs:
+ *      in0    Address of stack storage for fp regs
+ */
+GLOBAL_ENTRY(ia64_load_scratch_fpregs)
+       alloc r3=ar.pfs,1,0,0,0
+       add r2=16,in0
+       ;;
+       ldf.fill  f10 = [in0],32
+       ldf.fill  f11 = [r2],32
+       ;;
+       ldf.fill  f12 = [in0],32
+       ldf.fill  f13 = [r2],32
+       ;;
+       ldf.fill  f14 = [in0],32
+       ldf.fill  f15 = [r2],32
+       br.ret.sptk.many rp
+END(ia64_load_scratch_fpregs)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/setup.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/setup.c   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,773 @@
+/*
+ * Architecture-specific setup.
+ *
+ * Copyright (C) 1998-2001, 2003-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 2000, Rohit Seth <rohit.seth@xxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ *
+ * 11/12/01 D.Mosberger Convert get_cpuinfo() to seq_file based show_cpuinfo().
+ * 04/04/00 D.Mosberger renamed cpu_initialized to cpu_online_map
+ * 03/31/00 R.Seth     cpu_initialized and current->processor fixes
+ * 02/04/00 D.Mosberger        some more get_cpuinfo fixes...
+ * 02/01/00 R.Seth     fixed get_cpuinfo for SMP
+ * 01/07/99 S.Eranian  added the support for command line argument
+ * 06/24/99 W.Drummond added boot_cpu_data.
+ */
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/init.h>
+
+#include <linux/acpi.h>
+#include <linux/bootmem.h>
+#include <linux/console.h>
+#include <linux/delay.h>
+#include <linux/kernel.h>
+#include <linux/reboot.h>
+#include <linux/sched.h>
+#include <linux/seq_file.h>
+#include <linux/string.h>
+#include <linux/threads.h>
+#include <linux/tty.h>
+#include <linux/serial.h>
+#include <linux/serial_core.h>
+#include <linux/efi.h>
+#include <linux/initrd.h>
+
+#include <asm/ia32.h>
+#include <asm/machvec.h>
+#include <asm/mca.h>
+#include <asm/meminit.h>
+#include <asm/page.h>
+#include <asm/patch.h>
+#include <asm/pgtable.h>
+#include <asm/processor.h>
+#include <asm/sal.h>
+#include <asm/sections.h>
+#include <asm/serial.h>
+#include <asm/setup.h>
+#include <asm/smp.h>
+#include <asm/system.h>
+#include <asm/unistd.h>
+#ifdef CONFIG_VTI
+#include <asm/vmx.h>
+#endif // CONFIG_VTI
+#include <asm/io.h>
+
+#if defined(CONFIG_SMP) && (IA64_CPU_SIZE > PAGE_SIZE)
+# error "struct cpuinfo_ia64 too big!"
+#endif
+
+#ifdef CONFIG_SMP
+unsigned long __per_cpu_offset[NR_CPUS];
+EXPORT_SYMBOL(__per_cpu_offset);
+#endif
+
+DEFINE_PER_CPU(struct cpuinfo_ia64, cpu_info);
+DEFINE_PER_CPU(unsigned long, local_per_cpu_offset);
+DEFINE_PER_CPU(unsigned long, ia64_phys_stacked_size_p8);
+unsigned long ia64_cycles_per_usec;
+struct ia64_boot_param *ia64_boot_param;
+struct screen_info screen_info;
+
+unsigned long ia64_max_cacheline_size;
+unsigned long ia64_iobase;     /* virtual address for I/O accesses */
+EXPORT_SYMBOL(ia64_iobase);
+struct io_space io_space[MAX_IO_SPACES];
+EXPORT_SYMBOL(io_space);
+unsigned int num_io_spaces;
+
+unsigned char aux_device_present = 0xaa;        /* XXX remove this when legacy 
I/O is gone */
+
+/*
+ * The merge_mask variable needs to be set to (max(iommu_page_size(iommu)) - 
1).  This
+ * mask specifies a mask of address bits that must be 0 in order for two 
buffers to be
+ * mergeable by the I/O MMU (i.e., the end address of the first buffer and the 
start
+ * address of the second buffer must be aligned to (merge_mask+1) in order to 
be
+ * mergeable).  By default, we assume there is no I/O MMU which can merge 
physically
+ * discontiguous buffers, so we set the merge_mask to ~0UL, which corresponds 
to a iommu
+ * page-size of 2^64.
+ */
+unsigned long ia64_max_iommu_merge_mask = ~0UL;
+EXPORT_SYMBOL(ia64_max_iommu_merge_mask);
+
+/*
+ * We use a special marker for the end of memory and it uses the extra (+1) 
slot
+ */
+struct rsvd_region rsvd_region[IA64_MAX_RSVD_REGIONS + 1];
+int num_rsvd_regions;
+
+
+/*
+ * Filter incoming memory segments based on the primitive map created from the 
boot
+ * parameters. Segments contained in the map are removed from the memory 
ranges. A
+ * caller-specified function is called with the memory ranges that remain 
after filtering.
+ * This routine does not assume the incoming segments are sorted.
+ */
+int
+filter_rsvd_memory (unsigned long start, unsigned long end, void *arg)
+{
+       unsigned long range_start, range_end, prev_start;
+       void (*func)(unsigned long, unsigned long, int);
+       int i;
+
+#if IGNORE_PFN0
+       if (start == PAGE_OFFSET) {
+               printk(KERN_WARNING "warning: skipping physical page 0\n");
+               start += PAGE_SIZE;
+               if (start >= end) return 0;
+       }
+#endif
+       /*
+        * lowest possible address(walker uses virtual)
+        */
+       prev_start = PAGE_OFFSET;
+       func = arg;
+
+       for (i = 0; i < num_rsvd_regions; ++i) {
+               range_start = max(start, prev_start);
+               range_end   = min(end, rsvd_region[i].start);
+
+               if (range_start < range_end)
+#ifdef XEN
+               {
+               /* init_boot_pages requires "ps, pe" */
+                       printk("Init boot pages: 0x%lx -> 0x%lx.\n",
+                               __pa(range_start), __pa(range_end));
+                       (*func)(__pa(range_start), __pa(range_end), 0);
+               }
+#else
+                       call_pernode_memory(__pa(range_start), range_end - 
range_start, func);
+#endif
+
+               /* nothing more available in this segment */
+               if (range_end == end) return 0;
+
+               prev_start = rsvd_region[i].end;
+       }
+       /* end of memory marker allows full processing inside loop body */
+       return 0;
+}
+
+static void
+sort_regions (struct rsvd_region *rsvd_region, int max)
+{
+       int j;
+
+       /* simple bubble sorting */
+       while (max--) {
+               for (j = 0; j < max; ++j) {
+                       if (rsvd_region[j].start > rsvd_region[j+1].start) {
+                               struct rsvd_region tmp;
+                               tmp = rsvd_region[j];
+                               rsvd_region[j] = rsvd_region[j + 1];
+                               rsvd_region[j + 1] = tmp;
+                       }
+               }
+       }
+}
+
+/**
+ * reserve_memory - setup reserved memory areas
+ *
+ * Setup the reserved memory areas set aside for the boot parameters,
+ * initrd, etc.  There are currently %IA64_MAX_RSVD_REGIONS defined,
+ * see include/asm-ia64/meminit.h if you need to define more.
+ */
+void
+reserve_memory (void)
+{
+       int n = 0;
+
+       /*
+        * none of the entries in this table overlap
+        */
+       rsvd_region[n].start = (unsigned long) ia64_boot_param;
+       rsvd_region[n].end   = rsvd_region[n].start + sizeof(*ia64_boot_param);
+       n++;
+
+       rsvd_region[n].start = (unsigned long) 
__va(ia64_boot_param->efi_memmap);
+       rsvd_region[n].end   = rsvd_region[n].start + 
ia64_boot_param->efi_memmap_size;
+       n++;
+
+       rsvd_region[n].start = (unsigned long) 
__va(ia64_boot_param->command_line);
+       rsvd_region[n].end   = (rsvd_region[n].start
+                               + strlen(__va(ia64_boot_param->command_line)) + 
1);
+       n++;
+
+       rsvd_region[n].start = (unsigned long) ia64_imva((void *)KERNEL_START);
+#ifdef XEN
+       /* Reserve xen image/bitmap/xen-heap */
+       rsvd_region[n].end   = rsvd_region[n].start + xenheap_size;
+#else
+       rsvd_region[n].end   = (unsigned long) ia64_imva(_end);
+#endif
+       n++;
+
+#ifdef CONFIG_BLK_DEV_INITRD
+       if (ia64_boot_param->initrd_start) {
+               rsvd_region[n].start = (unsigned 
long)__va(ia64_boot_param->initrd_start);
+               rsvd_region[n].end   = rsvd_region[n].start + 
ia64_boot_param->initrd_size;
+               n++;
+       }
+#endif
+
+       /* end of memory marker */
+       rsvd_region[n].start = ~0UL;
+       rsvd_region[n].end   = ~0UL;
+       n++;
+
+       num_rsvd_regions = n;
+
+       sort_regions(rsvd_region, num_rsvd_regions);
+}
+
+/**
+ * find_initrd - get initrd parameters from the boot parameter structure
+ *
+ * Grab the initrd start and end from the boot parameter struct given us by
+ * the boot loader.
+ */
+void
+find_initrd (void)
+{
+#ifdef CONFIG_BLK_DEV_INITRD
+       if (ia64_boot_param->initrd_start) {
+               initrd_start = (unsigned 
long)__va(ia64_boot_param->initrd_start);
+               initrd_end   = initrd_start+ia64_boot_param->initrd_size;
+
+               printk(KERN_INFO "Initial ramdisk at: 0x%lx (%lu bytes)\n",
+                      initrd_start, ia64_boot_param->initrd_size);
+       }
+#endif
+}
+
+static void __init
+io_port_init (void)
+{
+       extern unsigned long ia64_iobase;
+       unsigned long phys_iobase;
+
+       /*
+        *  Set `iobase' to the appropriate address in region 6 (uncached 
access range).
+        *
+        *  The EFI memory map is the "preferred" location to get the I/O port 
space base,
+        *  rather the relying on AR.KR0. This should become more clear in 
future SAL
+        *  specs. We'll fall back to getting it out of AR.KR0 if no 
appropriate entry is
+        *  found in the memory map.
+        */
+       phys_iobase = efi_get_iobase();
+       if (phys_iobase)
+               /* set AR.KR0 since this is all we use it for anyway */
+               ia64_set_kr(IA64_KR_IO_BASE, phys_iobase);
+       else {
+               phys_iobase = ia64_get_kr(IA64_KR_IO_BASE);
+               printk(KERN_INFO "No I/O port range found in EFI memory map, 
falling back "
+                      "to AR.KR0\n");
+               printk(KERN_INFO "I/O port base = 0x%lx\n", phys_iobase);
+       }
+       ia64_iobase = (unsigned long) ioremap(phys_iobase, 0);
+
+       /* setup legacy IO port space */
+       io_space[0].mmio_base = ia64_iobase;
+       io_space[0].sparse = 1;
+       num_io_spaces = 1;
+}
+
+/**
+ * early_console_setup - setup debugging console
+ *
+ * Consoles started here require little enough setup that we can start using
+ * them very early in the boot process, either right after the machine
+ * vector initialization, or even before if the drivers can detect their hw.
+ *
+ * Returns non-zero if a console couldn't be setup.
+ */
+static inline int __init
+early_console_setup (char *cmdline)
+{
+#ifdef CONFIG_SERIAL_SGI_L1_CONSOLE
+       {
+               extern int sn_serial_console_early_setup(void);
+               if (!sn_serial_console_early_setup())
+                       return 0;
+       }
+#endif
+#ifdef CONFIG_EFI_PCDP
+       if (!efi_setup_pcdp_console(cmdline))
+               return 0;
+#endif
+#ifdef CONFIG_SERIAL_8250_CONSOLE
+       if (!early_serial_console_init(cmdline))
+               return 0;
+#endif
+
+       return -1;
+}
+
+static inline void
+mark_bsp_online (void)
+{
+#ifdef CONFIG_SMP
+       /* If we register an early console, allow CPU 0 to printk */
+       cpu_set(smp_processor_id(), cpu_online_map);
+#endif
+}
+
+void __init
+#ifdef XEN
+early_setup_arch (char **cmdline_p)
+#else
+setup_arch (char **cmdline_p)
+#endif
+{
+       unw_init();
+
+       ia64_patch_vtop((u64) __start___vtop_patchlist, (u64) 
__end___vtop_patchlist);
+
+       *cmdline_p = __va(ia64_boot_param->command_line);
+#ifdef XEN
+       efi_init();
+#else
+       strlcpy(saved_command_line, *cmdline_p, COMMAND_LINE_SIZE);
+
+       efi_init();
+       io_port_init();
+#endif
+
+#ifdef CONFIG_IA64_GENERIC
+       {
+               const char *mvec_name = strstr (*cmdline_p, "machvec=");
+               char str[64];
+
+               if (mvec_name) {
+                       const char *end;
+                       size_t len;
+
+                       mvec_name += 8;
+                       end = strchr (mvec_name, ' ');
+                       if (end)
+                               len = end - mvec_name;
+                       else
+                               len = strlen (mvec_name);
+                       len = min(len, sizeof (str) - 1);
+                       strncpy (str, mvec_name, len);
+                       str[len] = '\0';
+                       mvec_name = str;
+               } else
+                       mvec_name = acpi_get_sysname();
+               machvec_init(mvec_name);
+       }
+#endif
+
+#ifdef XEN
+       early_cmdline_parse(cmdline_p);
+       cmdline_parse(*cmdline_p);
+#undef CONFIG_ACPI_BOOT
+#endif
+       if (early_console_setup(*cmdline_p) == 0)
+               mark_bsp_online();
+
+#ifdef CONFIG_ACPI_BOOT
+       /* Initialize the ACPI boot-time table parser */
+       acpi_table_init();
+# ifdef CONFIG_ACPI_NUMA
+       acpi_numa_init();
+# endif
+#else
+# ifdef CONFIG_SMP
+       smp_build_cpu_map();    /* happens, e.g., with the Ski simulator */
+# endif
+#endif /* CONFIG_APCI_BOOT */
+
+#ifndef XEN
+       find_memory();
+#else
+       io_port_init();
+}
+
+void __init
+late_setup_arch (char **cmdline_p)
+{
+#undef CONFIG_ACPI_BOOT
+       acpi_table_init();
+#endif
+       /* process SAL system table: */
+       ia64_sal_init(efi.sal_systab);
+
+#ifdef CONFIG_SMP
+       cpu_physical_id(0) = hard_smp_processor_id();
+#endif
+
+#ifdef CONFIG_VTI
+       identify_vmx_feature();
+#endif // CONFIG_VTI
+
+       cpu_init();     /* initialize the bootstrap CPU */
+
+#ifdef CONFIG_ACPI_BOOT
+       acpi_boot_init();
+#endif
+
+#ifdef CONFIG_VT
+       if (!conswitchp) {
+# if defined(CONFIG_DUMMY_CONSOLE)
+               conswitchp = &dummy_con;
+# endif
+# if defined(CONFIG_VGA_CONSOLE)
+               /*
+                * Non-legacy systems may route legacy VGA MMIO range to system
+                * memory.  vga_con probes the MMIO hole, so memory looks like
+                * a VGA device to it.  The EFI memory map can tell us if it's
+                * memory so we can avoid this problem.
+                */
+               if (efi_mem_type(0xA0000) != EFI_CONVENTIONAL_MEMORY)
+                       conswitchp = &vga_con;
+# endif
+       }
+#endif
+
+       /* enable IA-64 Machine Check Abort Handling unless disabled */
+       if (!strstr(saved_command_line, "nomca"))
+               ia64_mca_init();
+
+       platform_setup(cmdline_p);
+       paging_init();
+}
+
+/*
+ * Display cpu info for all cpu's.
+ */
+static int
+show_cpuinfo (struct seq_file *m, void *v)
+{
+#ifdef CONFIG_SMP
+#      define lpj      c->loops_per_jiffy
+#      define cpunum   c->cpu
+#else
+#      define lpj      loops_per_jiffy
+#      define cpunum   0
+#endif
+       static struct {
+               unsigned long mask;
+               const char *feature_name;
+       } feature_bits[] = {
+               { 1UL << 0, "branchlong" },
+               { 1UL << 1, "spontaneous deferral"},
+               { 1UL << 2, "16-byte atomic ops" }
+       };
+       char family[32], features[128], *cp, sep;
+       struct cpuinfo_ia64 *c = v;
+       unsigned long mask;
+       int i;
+
+       mask = c->features;
+
+       switch (c->family) {
+             case 0x07:        memcpy(family, "Itanium", 8); break;
+             case 0x1f:        memcpy(family, "Itanium 2", 10); break;
+             default:          sprintf(family, "%u", c->family); break;
+       }
+
+       /* build the feature string: */
+       memcpy(features, " standard", 10);
+       cp = features;
+       sep = 0;
+       for (i = 0; i < (int) ARRAY_SIZE(feature_bits); ++i) {
+               if (mask & feature_bits[i].mask) {
+                       if (sep)
+                               *cp++ = sep;
+                       sep = ',';
+                       *cp++ = ' ';
+                       strcpy(cp, feature_bits[i].feature_name);
+                       cp += strlen(feature_bits[i].feature_name);
+                       mask &= ~feature_bits[i].mask;
+               }
+       }
+       if (mask) {
+               /* print unknown features as a hex value: */
+               if (sep)
+                       *cp++ = sep;
+               sprintf(cp, " 0x%lx", mask);
+       }
+
+       seq_printf(m,
+                  "processor  : %d\n"
+                  "vendor     : %s\n"
+                  "arch       : IA-64\n"
+                  "family     : %s\n"
+                  "model      : %u\n"
+                  "revision   : %u\n"
+                  "archrev    : %u\n"
+                  "features   :%s\n"   /* don't change this---it _is_ right! */
+                  "cpu number : %lu\n"
+                  "cpu regs   : %u\n"
+                  "cpu MHz    : %lu.%06lu\n"
+                  "itc MHz    : %lu.%06lu\n"
+                  "BogoMIPS   : %lu.%02lu\n\n",
+                  cpunum, c->vendor, family, c->model, c->revision, c->archrev,
+                  features, c->ppn, c->number,
+                  c->proc_freq / 1000000, c->proc_freq % 1000000,
+                  c->itc_freq / 1000000, c->itc_freq % 1000000,
+                  lpj*HZ/500000, (lpj*HZ/5000) % 100);
+       return 0;
+}
+
+static void *
+c_start (struct seq_file *m, loff_t *pos)
+{
+#ifdef CONFIG_SMP
+       while (*pos < NR_CPUS && !cpu_isset(*pos, cpu_online_map))
+               ++*pos;
+#endif
+       return *pos < NR_CPUS ? cpu_data(*pos) : NULL;
+}
+
+static void *
+c_next (struct seq_file *m, void *v, loff_t *pos)
+{
+       ++*pos;
+       return c_start(m, pos);
+}
+
+static void
+c_stop (struct seq_file *m, void *v)
+{
+}
+
+#ifndef XEN
+struct seq_operations cpuinfo_op = {
+       .start =        c_start,
+       .next =         c_next,
+       .stop =         c_stop,
+       .show =         show_cpuinfo
+};
+#endif
+
+void
+identify_cpu (struct cpuinfo_ia64 *c)
+{
+       union {
+               unsigned long bits[5];
+               struct {
+                       /* id 0 & 1: */
+                       char vendor[16];
+
+                       /* id 2 */
+                       u64 ppn;                /* processor serial number */
+
+                       /* id 3: */
+                       unsigned number         :  8;
+                       unsigned revision       :  8;
+                       unsigned model          :  8;
+                       unsigned family         :  8;
+                       unsigned archrev        :  8;
+                       unsigned reserved       : 24;
+
+                       /* id 4: */
+                       u64 features;
+               } field;
+       } cpuid;
+       pal_vm_info_1_u_t vm1;
+       pal_vm_info_2_u_t vm2;
+       pal_status_t status;
+       unsigned long impl_va_msb = 50, phys_addr_size = 44;    /* Itanium 
defaults */
+       int i;
+
+       for (i = 0; i < 5; ++i)
+               cpuid.bits[i] = ia64_get_cpuid(i);
+
+       memcpy(c->vendor, cpuid.field.vendor, 16);
+#ifdef CONFIG_SMP
+       c->cpu = smp_processor_id();
+#endif
+       c->ppn = cpuid.field.ppn;
+       c->number = cpuid.field.number;
+       c->revision = cpuid.field.revision;
+       c->model = cpuid.field.model;
+       c->family = cpuid.field.family;
+       c->archrev = cpuid.field.archrev;
+       c->features = cpuid.field.features;
+
+       status = ia64_pal_vm_summary(&vm1, &vm2);
+       if (status == PAL_STATUS_SUCCESS) {
+               impl_va_msb = vm2.pal_vm_info_2_s.impl_va_msb;
+               phys_addr_size = vm1.pal_vm_info_1_s.phys_add_size;
+       }
+       c->unimpl_va_mask = ~((7L<<61) | ((1L << (impl_va_msb + 1)) - 1));
+       c->unimpl_pa_mask = ~((1L<<63) | ((1L << phys_addr_size) - 1));
+
+#ifdef CONFIG_VTI
+       /* If vmx feature is on, do necessary initialization for vmx */
+       if (vmx_enabled)
+               vmx_init_env();
+#endif
+}
+
+void
+setup_per_cpu_areas (void)
+{
+       /* start_kernel() requires this... */
+}
+
+static void
+get_max_cacheline_size (void)
+{
+       unsigned long line_size, max = 1;
+       u64 l, levels, unique_caches;
+        pal_cache_config_info_t cci;
+        s64 status;
+
+        status = ia64_pal_cache_summary(&levels, &unique_caches);
+        if (status != 0) {
+                printk(KERN_ERR "%s: ia64_pal_cache_summary() failed 
(status=%ld)\n",
+                       __FUNCTION__, status);
+                max = SMP_CACHE_BYTES;
+               goto out;
+        }
+
+       for (l = 0; l < levels; ++l) {
+               status = ia64_pal_cache_config_info(l, /* cache_type 
(data_or_unified)= */ 2,
+                                                   &cci);
+               if (status != 0) {
+                       printk(KERN_ERR
+                              "%s: ia64_pal_cache_config_info(l=%lu) failed 
(status=%ld)\n",
+                              __FUNCTION__, l, status);
+                       max = SMP_CACHE_BYTES;
+               }
+               line_size = 1 << cci.pcci_line_size;
+               if (line_size > max)
+                       max = line_size;
+        }
+  out:
+       if (max > ia64_max_cacheline_size)
+               ia64_max_cacheline_size = max;
+}
+
+/*
+ * cpu_init() initializes state that is per-CPU.  This function acts
+ * as a 'CPU state barrier', nothing should get across.
+ */
+void
+cpu_init (void)
+{
+       extern void __devinit ia64_mmu_init (void *);
+       unsigned long num_phys_stacked;
+       pal_vm_info_2_u_t vmi;
+       unsigned int max_ctx;
+       struct cpuinfo_ia64 *cpu_info;
+       void *cpu_data;
+
+       cpu_data = per_cpu_init();
+
+       /*
+        * We set ar.k3 so that assembly code in MCA handler can compute
+        * physical addresses of per cpu variables with a simple:
+        *   phys = ar.k3 + &per_cpu_var
+        */
+       ia64_set_kr(IA64_KR_PER_CPU_DATA,
+                   ia64_tpa(cpu_data) - (long) __per_cpu_start);
+
+       get_max_cacheline_size();
+
+       /*
+        * We can't pass "local_cpu_data" to identify_cpu() because we haven't 
called
+        * ia64_mmu_init() yet.  And we can't call ia64_mmu_init() first 
because it
+        * depends on the data returned by identify_cpu().  We break the 
dependency by
+        * accessing cpu_data() through the canonical per-CPU address.
+        */
+       cpu_info = cpu_data + ((char *) &__ia64_per_cpu_var(cpu_info) - 
__per_cpu_start);
+       identify_cpu(cpu_info);
+
+#ifdef CONFIG_MCKINLEY
+       {
+#              define FEATURE_SET 16
+               struct ia64_pal_retval iprv;
+
+               if (cpu_info->family == 0x1f) {
+                       PAL_CALL_PHYS(iprv, PAL_PROC_GET_FEATURES, 0, 
FEATURE_SET, 0);
+                       if ((iprv.status == 0) && (iprv.v0 & 0x80) && (iprv.v2 
& 0x80))
+                               PAL_CALL_PHYS(iprv, PAL_PROC_SET_FEATURES,
+                                             (iprv.v1 | 0x80), FEATURE_SET, 0);
+               }
+       }
+#endif
+
+       /* Clear the stack memory reserved for pt_regs: */
+       memset(ia64_task_regs(current), 0, sizeof(struct pt_regs));
+
+       ia64_set_kr(IA64_KR_FPU_OWNER, 0);
+
+       /*
+        * Initialize default control register to defer all speculative faults. 
 The
+        * kernel MUST NOT depend on a particular setting of these bits (in 
other words,
+        * the kernel must have recovery code for all speculative accesses).  
Turn on
+        * dcr.lc as per recommendation by the architecture team.  Most IA-32 
apps
+        * shouldn't be affected by this (moral: keep your ia32 locks aligned 
and you'll
+        * be fine).
+        */
+       ia64_setreg(_IA64_REG_CR_DCR,  (  IA64_DCR_DP | IA64_DCR_DK | 
IA64_DCR_DX | IA64_DCR_DR
+                                       | IA64_DCR_DA | IA64_DCR_DD | 
IA64_DCR_LC));
+       atomic_inc(&init_mm.mm_count);
+       current->active_mm = &init_mm;
+#ifdef XEN
+       if (current->domain->arch.mm)
+#else
+       if (current->mm)
+#endif
+               BUG();
+
+       ia64_mmu_init(ia64_imva(cpu_data));
+       ia64_mca_cpu_init(ia64_imva(cpu_data));
+
+#ifdef CONFIG_IA32_SUPPORT
+       ia32_cpu_init();
+#endif
+
+       /* Clear ITC to eliminiate sched_clock() overflows in human time.  */
+       ia64_set_itc(0);
+
+       /* disable all local interrupt sources: */
+       ia64_set_itv(1 << 16);
+       ia64_set_lrr0(1 << 16);
+       ia64_set_lrr1(1 << 16);
+       ia64_setreg(_IA64_REG_CR_PMV, 1 << 16);
+       ia64_setreg(_IA64_REG_CR_CMCV, 1 << 16);
+
+       /* clear TPR & XTP to enable all interrupt classes: */
+       ia64_setreg(_IA64_REG_CR_TPR, 0);
+#ifdef CONFIG_SMP
+       normal_xtp();
+#endif
+
+       /* set ia64_ctx.max_rid to the maximum RID that is supported by all 
CPUs: */
+       if (ia64_pal_vm_summary(NULL, &vmi) == 0)
+               max_ctx = (1U << (vmi.pal_vm_info_2_s.rid_size - 3)) - 1;
+       else {
+               printk(KERN_WARNING "cpu_init: PAL VM summary failed, assuming 
18 RID bits\n");
+               max_ctx = (1U << 15) - 1;       /* use architected minimum */
+       }
+       while (max_ctx < ia64_ctx.max_ctx) {
+               unsigned int old = ia64_ctx.max_ctx;
+               if (cmpxchg(&ia64_ctx.max_ctx, old, max_ctx) == old)
+                       break;
+       }
+
+       if (ia64_pal_rse_info(&num_phys_stacked, NULL) != 0) {
+               printk(KERN_WARNING "cpu_init: PAL RSE info failed; assuming 96 
physical "
+                      "stacked regs\n");
+               num_phys_stacked = 96;
+       }
+       /* size of physical stacked register partition plus 8 bytes: */
+       __get_cpu_var(ia64_phys_stacked_size_p8) = num_phys_stacked*8 + 8;
+       platform_cpu_init();
+}
+
+void
+check_bugs (void)
+{
+       ia64_patch_mckinley_e9((unsigned long) __start___mckinley_e9_bundles,
+                              (unsigned long) __end___mckinley_e9_bundles);
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/time.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/time.c    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,264 @@
+/*
+ * linux/arch/ia64/kernel/time.c
+ *
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ * Copyright (C) 1999-2000 VA Linux Systems
+ * Copyright (C) 1999-2000 Walt Drummond <drummond@xxxxxxxxxxx>
+ */
+#include <linux/config.h>
+
+#include <linux/cpu.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/profile.h>
+#include <linux/sched.h>
+#include <linux/time.h>
+#include <linux/interrupt.h>
+#include <linux/efi.h>
+#include <linux/profile.h>
+#include <linux/timex.h>
+
+#include <asm/machvec.h>
+#include <asm/delay.h>
+#include <asm/hw_irq.h>
+#include <asm/ptrace.h>
+#include <asm/sal.h>
+#include <asm/sections.h>
+#include <asm/system.h>
+#ifdef XEN
+#include <linux/jiffies.h>     // not included by xen/sched.h
+#endif
+
+extern unsigned long wall_jiffies;
+
+u64 jiffies_64 __cacheline_aligned_in_smp = INITIAL_JIFFIES;
+
+EXPORT_SYMBOL(jiffies_64);
+
+#define TIME_KEEPER_ID 0       /* smp_processor_id() of time-keeper */
+
+#ifdef CONFIG_IA64_DEBUG_IRQ
+
+unsigned long last_cli_ip;
+EXPORT_SYMBOL(last_cli_ip);
+
+#endif
+
+#ifndef XEN
+static struct time_interpolator itc_interpolator = {
+       .shift = 16,
+       .mask = 0xffffffffffffffffLL,
+       .source = TIME_SOURCE_CPU
+};
+
+static irqreturn_t
+timer_interrupt (int irq, void *dev_id, struct pt_regs *regs)
+{
+       unsigned long new_itm;
+
+       if (unlikely(cpu_is_offline(smp_processor_id()))) {
+               return IRQ_HANDLED;
+       }
+
+       platform_timer_interrupt(irq, dev_id, regs);
+
+       new_itm = local_cpu_data->itm_next;
+
+       if (!time_after(ia64_get_itc(), new_itm))
+               printk(KERN_ERR "Oops: timer tick before it's due 
(itc=%lx,itm=%lx)\n",
+                      ia64_get_itc(), new_itm);
+
+       profile_tick(CPU_PROFILING, regs);
+
+       while (1) {
+               update_process_times(user_mode(regs));
+
+               new_itm += local_cpu_data->itm_delta;
+
+               if (smp_processor_id() == TIME_KEEPER_ID) {
+                       /*
+                        * Here we are in the timer irq handler. We have irqs 
locally
+                        * disabled, but we don't know if the timer_bh is 
running on
+                        * another CPU. We need to avoid to SMP race by 
acquiring the
+                        * xtime_lock.
+                        */
+                       write_seqlock(&xtime_lock);
+                       do_timer(regs);
+                       local_cpu_data->itm_next = new_itm;
+                       write_sequnlock(&xtime_lock);
+               } else
+                       local_cpu_data->itm_next = new_itm;
+
+               if (time_after(new_itm, ia64_get_itc()))
+                       break;
+       }
+
+       do {
+               /*
+                * If we're too close to the next clock tick for
+                * comfort, we increase the safety margin by
+                * intentionally dropping the next tick(s).  We do NOT
+                * update itm.next because that would force us to call
+                * do_timer() which in turn would let our clock run
+                * too fast (with the potentially devastating effect
+                * of losing monotony of time).
+                */
+               while (!time_after(new_itm, ia64_get_itc() + 
local_cpu_data->itm_delta/2))
+                       new_itm += local_cpu_data->itm_delta;
+               ia64_set_itm(new_itm);
+               /* double check, in case we got hit by a (slow) PMI: */
+       } while (time_after_eq(ia64_get_itc(), new_itm));
+       return IRQ_HANDLED;
+}
+#endif
+
+/*
+ * Encapsulate access to the itm structure for SMP.
+ */
+void
+ia64_cpu_local_tick (void)
+{
+       int cpu = smp_processor_id();
+       unsigned long shift = 0, delta;
+
+       /* arrange for the cycle counter to generate a timer interrupt: */
+       ia64_set_itv(IA64_TIMER_VECTOR);
+
+       delta = local_cpu_data->itm_delta;
+       /*
+        * Stagger the timer tick for each CPU so they don't occur all at 
(almost) the
+        * same time:
+        */
+       if (cpu) {
+               unsigned long hi = 1UL << ia64_fls(cpu);
+               shift = (2*(cpu - hi) + 1) * delta/hi/2;
+       }
+       local_cpu_data->itm_next = ia64_get_itc() + delta + shift;
+       ia64_set_itm(local_cpu_data->itm_next);
+}
+
+static int nojitter;
+
+static int __init nojitter_setup(char *str)
+{
+       nojitter = 1;
+       printk("Jitter checking for ITC timers disabled\n");
+       return 1;
+}
+
+__setup("nojitter", nojitter_setup);
+
+
+void __devinit
+ia64_init_itm (void)
+{
+       unsigned long platform_base_freq, itc_freq;
+       struct pal_freq_ratio itc_ratio, proc_ratio;
+       long status, platform_base_drift, itc_drift;
+
+       /*
+        * According to SAL v2.6, we need to use a SAL call to determine the 
platform base
+        * frequency and then a PAL call to determine the frequency ratio 
between the ITC
+        * and the base frequency.
+        */
+       status = ia64_sal_freq_base(SAL_FREQ_BASE_PLATFORM,
+                                   &platform_base_freq, &platform_base_drift);
+       if (status != 0) {
+               printk(KERN_ERR "SAL_FREQ_BASE_PLATFORM failed: %s\n", 
ia64_sal_strerror(status));
+       } else {
+               status = ia64_pal_freq_ratios(&proc_ratio, NULL, &itc_ratio);
+               if (status != 0)
+                       printk(KERN_ERR "PAL_FREQ_RATIOS failed with 
status=%ld\n", status);
+       }
+       if (status != 0) {
+               /* invent "random" values */
+               printk(KERN_ERR
+                      "SAL/PAL failed to obtain frequency info---inventing 
reasonable values\n");
+               platform_base_freq = 100000000;
+               platform_base_drift = -1;       /* no drift info */
+               itc_ratio.num = 3;
+               itc_ratio.den = 1;
+       }
+       if (platform_base_freq < 40000000) {
+               printk(KERN_ERR "Platform base frequency %lu bogus---resetting 
to 75MHz!\n",
+                      platform_base_freq);
+               platform_base_freq = 75000000;
+               platform_base_drift = -1;
+       }
+       if (!proc_ratio.den)
+               proc_ratio.den = 1;     /* avoid division by zero */
+       if (!itc_ratio.den)
+               itc_ratio.den = 1;      /* avoid division by zero */
+
+       itc_freq = (platform_base_freq*itc_ratio.num)/itc_ratio.den;
+
+       local_cpu_data->itm_delta = (itc_freq + HZ/2) / HZ;
+       printk(KERN_DEBUG "CPU %d: base freq=%lu.%03luMHz, ITC ratio=%lu/%lu, "
+              "ITC freq=%lu.%03luMHz", smp_processor_id(),
+              platform_base_freq / 1000000, (platform_base_freq / 1000) % 1000,
+              itc_ratio.num, itc_ratio.den, itc_freq / 1000000, (itc_freq / 
1000) % 1000);
+
+       if (platform_base_drift != -1) {
+               itc_drift = platform_base_drift*itc_ratio.num/itc_ratio.den;
+               printk("+/-%ldppm\n", itc_drift);
+       } else {
+               itc_drift = -1;
+               printk("\n");
+       }
+
+       local_cpu_data->proc_freq = 
(platform_base_freq*proc_ratio.num)/proc_ratio.den;
+       local_cpu_data->itc_freq = itc_freq;
+       local_cpu_data->cyc_per_usec = (itc_freq + USEC_PER_SEC/2) / 
USEC_PER_SEC;
+       local_cpu_data->nsec_per_cyc = ((NSEC_PER_SEC<<IA64_NSEC_PER_CYC_SHIFT)
+                                       + itc_freq/2)/itc_freq;
+
+       if (!(sal_platform_features & IA64_SAL_PLATFORM_FEATURE_ITC_DRIFT)) {
+#ifndef XEN
+               itc_interpolator.frequency = local_cpu_data->itc_freq;
+               itc_interpolator.drift = itc_drift;
+#ifdef CONFIG_SMP
+               /* On IA64 in an SMP configuration ITCs are never accurately 
synchronized.
+                * Jitter compensation requires a cmpxchg which may limit
+                * the scalability of the syscalls for retrieving time.
+                * The ITC synchronization is usually successful to within a few
+                * ITC ticks but this is not a sure thing. If you need to 
improve
+                * timer performance in SMP situations then boot the kernel 
with the
+                * "nojitter" option. However, doing so may result in time 
fluctuating (maybe
+                * even going backward) if the ITC offsets between the 
individual CPUs
+                * are too large.
+                */
+               if (!nojitter) itc_interpolator.jitter = 1;
+#endif
+               register_time_interpolator(&itc_interpolator);
+#endif
+       }
+
+       /* Setup the CPU local timer tick */
+       ia64_cpu_local_tick();
+}
+
+#ifndef XEN
+static struct irqaction timer_irqaction = {
+       .handler =      timer_interrupt,
+       .flags =        SA_INTERRUPT,
+       .name =         "timer"
+};
+
+void __init
+time_init (void)
+{
+       register_percpu_irq(IA64_TIMER_VECTOR, &timer_irqaction);
+       efi_gettimeofday(&xtime);
+       ia64_init_itm();
+
+       /*
+        * Initialize wall_to_monotonic such that adding it to xtime will yield 
zero, the
+        * tv_nsec field must be normalized (i.e., 0 <= nsec < NSEC_PER_SEC).
+        */
+       set_normalized_timespec(&wall_to_monotonic, -xtime.tv_sec, 
-xtime.tv_nsec);
+}
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/tlb.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/tlb.c     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,199 @@
+/*
+ * TLB support routines.
+ *
+ * Copyright (C) 1998-2001, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 08/02/00 A. Mallick <asit.k.mallick@xxxxxxxxx>
+ *             Modified RID allocation for SMP
+ *          Goutham Rao <goutham.rao@xxxxxxxxx>
+ *              IPI based ptc implementation and A-step IPI implementation.
+ */
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/smp.h>
+#include <linux/mm.h>
+
+#include <asm/delay.h>
+#include <asm/mmu_context.h>
+#include <asm/pgalloc.h>
+#include <asm/pal.h>
+#include <asm/tlbflush.h>
+
+static struct {
+       unsigned long mask;     /* mask of supported purge page-sizes */
+       unsigned long max_bits; /* log2() of largest supported purge page-size 
*/
+} purge;
+
+struct ia64_ctx ia64_ctx = {
+       .lock =         SPIN_LOCK_UNLOCKED,
+       .next =         1,
+       .limit =        (1 << 15) - 1,          /* start out with the safe 
(architected) limit */
+       .max_ctx =      ~0U
+};
+
+DEFINE_PER_CPU(u8, ia64_need_tlb_flush);
+
+/*
+ * Acquire the ia64_ctx.lock before calling this function!
+ */
+void
+wrap_mmu_context (struct mm_struct *mm)
+{
+#ifdef XEN
+printf("wrap_mmu_context: called, not implemented\n");
+#else
+       unsigned long tsk_context, max_ctx = ia64_ctx.max_ctx;
+       struct task_struct *tsk;
+       int i;
+
+       if (ia64_ctx.next > max_ctx)
+               ia64_ctx.next = 300;    /* skip daemons */
+       ia64_ctx.limit = max_ctx + 1;
+
+       /*
+        * Scan all the task's mm->context and set proper safe range
+        */
+
+       read_lock(&tasklist_lock);
+  repeat:
+       for_each_process(tsk) {
+               if (!tsk->mm)
+                       continue;
+               tsk_context = tsk->mm->context;
+               if (tsk_context == ia64_ctx.next) {
+                       if (++ia64_ctx.next >= ia64_ctx.limit) {
+                               /* empty range: reset the range limit and start 
over */
+                               if (ia64_ctx.next > max_ctx)
+                                       ia64_ctx.next = 300;
+                               ia64_ctx.limit = max_ctx + 1;
+                               goto repeat;
+                       }
+               }
+               if ((tsk_context > ia64_ctx.next) && (tsk_context < 
ia64_ctx.limit))
+                       ia64_ctx.limit = tsk_context;
+       }
+       read_unlock(&tasklist_lock);
+       /* can't call flush_tlb_all() here because of race condition with O(1) 
scheduler [EF] */
+       {
+               int cpu = get_cpu(); /* prevent preemption/migration */
+               for (i = 0; i < NR_CPUS; ++i)
+                       if (cpu_online(i) && (i != cpu))
+                               per_cpu(ia64_need_tlb_flush, i) = 1;
+               put_cpu();
+       }
+       local_flush_tlb_all();
+#endif
+}
+
+void
+ia64_global_tlb_purge (unsigned long start, unsigned long end, unsigned long 
nbits)
+{
+       static DEFINE_SPINLOCK(ptcg_lock);
+
+       /* HW requires global serialization of ptc.ga.  */
+       spin_lock(&ptcg_lock);
+       {
+               do {
+                       /*
+                        * Flush ALAT entries also.
+                        */
+                       ia64_ptcga(start, (nbits<<2));
+                       ia64_srlz_i();
+                       start += (1UL << nbits);
+               } while (start < end);
+       }
+       spin_unlock(&ptcg_lock);
+}
+
+void
+local_flush_tlb_all (void)
+{
+       unsigned long i, j, flags, count0, count1, stride0, stride1, addr;
+
+       addr    = local_cpu_data->ptce_base;
+       count0  = local_cpu_data->ptce_count[0];
+       count1  = local_cpu_data->ptce_count[1];
+       stride0 = local_cpu_data->ptce_stride[0];
+       stride1 = local_cpu_data->ptce_stride[1];
+
+       local_irq_save(flags);
+       for (i = 0; i < count0; ++i) {
+               for (j = 0; j < count1; ++j) {
+                       ia64_ptce(addr);
+                       addr += stride1;
+               }
+               addr += stride0;
+       }
+       local_irq_restore(flags);
+       ia64_srlz_i();                  /* srlz.i implies srlz.d */
+}
+EXPORT_SYMBOL(local_flush_tlb_all);
+
+void
+flush_tlb_range (struct vm_area_struct *vma, unsigned long start, unsigned 
long end)
+{
+#ifdef XEN
+printf("flush_tlb_range: called, not implemented\n");
+#else
+       struct mm_struct *mm = vma->vm_mm;
+       unsigned long size = end - start;
+       unsigned long nbits;
+
+       if (mm != current->active_mm) {
+               /* this does happen, but perhaps it's not worth optimizing for? 
*/
+#ifdef CONFIG_SMP
+               flush_tlb_all();
+#else
+               mm->context = 0;
+#endif
+               return;
+       }
+
+       nbits = ia64_fls(size + 0xfff);
+       while (unlikely (((1UL << nbits) & purge.mask) == 0) && (nbits < 
purge.max_bits))
+               ++nbits;
+       if (nbits > purge.max_bits)
+               nbits = purge.max_bits;
+       start &= ~((1UL << nbits) - 1);
+
+# ifdef CONFIG_SMP
+       platform_global_tlb_purge(start, end, nbits);
+# else
+       do {
+               ia64_ptcl(start, (nbits<<2));
+               start += (1UL << nbits);
+       } while (start < end);
+# endif
+
+       ia64_srlz_i();                  /* srlz.i implies srlz.d */
+#endif
+}
+EXPORT_SYMBOL(flush_tlb_range);
+
+void __devinit
+ia64_tlb_init (void)
+{
+       ia64_ptce_info_t ptce_info;
+       unsigned long tr_pgbits;
+       long status;
+
+       if ((status = ia64_pal_vm_page_size(&tr_pgbits, &purge.mask)) != 0) {
+               printk(KERN_ERR "PAL_VM_PAGE_SIZE failed with status=%ld;"
+                      "defaulting to architected purge page-sizes.\n", status);
+               purge.mask = 0x115557000UL;
+       }
+       purge.max_bits = ia64_fls(purge.mask);
+
+       ia64_get_ptce(&ptce_info);
+       local_cpu_data->ptce_base = ptce_info.base;
+       local_cpu_data->ptce_count[0] = ptce_info.count[0];
+       local_cpu_data->ptce_count[1] = ptce_info.count[1];
+       local_cpu_data->ptce_stride[0] = ptce_info.stride[0];
+       local_cpu_data->ptce_stride[1] = ptce_info.stride[1];
+
+       local_flush_tlb_all();          /* nuke left overs from 
bootstrapping... */
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux-xen/unaligned.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux-xen/unaligned.c       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1653 @@
+/*
+ * Architecture-specific unaligned trap handling.
+ *
+ * Copyright (C) 1999-2002, 2004 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 2002/12/09   Fix rotating register handling (off-by-1 error, missing 
fr-rotation).  Fix
+ *             get_rse_reg() to not leak kernel bits to user-level (reading an 
out-of-frame
+ *             stacked register returns an undefined value; it does NOT 
trigger a
+ *             "rsvd register fault").
+ * 2001/10/11  Fix unaligned access to rotating registers in s/w pipelined 
loops.
+ * 2001/08/13  Correct size of extended floats (float_fsz) from 16 to 10 bytes.
+ * 2001/01/17  Add support emulation of unaligned kernel accesses.
+ */
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/smp_lock.h>
+#include <linux/tty.h>
+
+#include <asm/intrinsics.h>
+#include <asm/processor.h>
+#include <asm/rse.h>
+#include <asm/uaccess.h>
+#include <asm/unaligned.h>
+
+extern void die_if_kernel(char *str, struct pt_regs *regs, long err) 
__attribute__ ((noreturn));
+
+#undef DEBUG_UNALIGNED_TRAP
+
+#ifdef DEBUG_UNALIGNED_TRAP
+# define DPRINT(a...)  do { printk("%s %u: ", __FUNCTION__, __LINE__); printk 
(a); } while (0)
+# define DDUMP(str,vp,len)     dump(str, vp, len)
+
+static void
+dump (const char *str, void *vp, size_t len)
+{
+       unsigned char *cp = vp;
+       int i;
+
+       printk("%s", str);
+       for (i = 0; i < len; ++i)
+               printk (" %02x", *cp++);
+       printk("\n");
+}
+#else
+# define DPRINT(a...)
+# define DDUMP(str,vp,len)
+#endif
+
+#define IA64_FIRST_STACKED_GR  32
+#define IA64_FIRST_ROTATING_FR 32
+#define SIGN_EXT9              0xffffffffffffff00ul
+
+/*
+ * For M-unit:
+ *
+ *  opcode |   m  |   x6    |
+ * --------|------|---------|
+ * [40-37] | [36] | [35:30] |
+ * --------|------|---------|
+ *     4   |   1  |    6    | = 11 bits
+ * --------------------------
+ * However bits [31:30] are not directly useful to distinguish between
+ * load/store so we can use [35:32] instead, which gives the following
+ * mask ([40:32]) using 9 bits. The 'e' comes from the fact that we defer
+ * checking the m-bit until later in the load/store emulation.
+ */
+#define IA64_OPCODE_MASK       0x1ef
+#define IA64_OPCODE_SHIFT      32
+
+/*
+ * Table C-28 Integer Load/Store
+ *
+ * We ignore [35:32]= 0x6, 0x7, 0xE, 0xF
+ *
+ * ld8.fill, st8.fill  MUST be aligned because the RNATs are based on
+ * the address (bits [8:3]), so we must failed.
+ */
+#define LD_OP            0x080
+#define LDS_OP           0x081
+#define LDA_OP           0x082
+#define LDSA_OP          0x083
+#define LDBIAS_OP        0x084
+#define LDACQ_OP         0x085
+/* 0x086, 0x087 are not relevant */
+#define LDCCLR_OP        0x088
+#define LDCNC_OP         0x089
+#define LDCCLRACQ_OP     0x08a
+#define ST_OP            0x08c
+#define STREL_OP         0x08d
+/* 0x08e,0x8f are not relevant */
+
+/*
+ * Table C-29 Integer Load +Reg
+ *
+ * we use the ld->m (bit [36:36]) field to determine whether or not we have
+ * a load/store of this form.
+ */
+
+/*
+ * Table C-30 Integer Load/Store +Imm
+ *
+ * We ignore [35:32]= 0x6, 0x7, 0xE, 0xF
+ *
+ * ld8.fill, st8.fill  must be aligned because the Nat register are based on
+ * the address, so we must fail and the program must be fixed.
+ */
+#define LD_IMM_OP            0x0a0
+#define LDS_IMM_OP           0x0a1
+#define LDA_IMM_OP           0x0a2
+#define LDSA_IMM_OP          0x0a3
+#define LDBIAS_IMM_OP        0x0a4
+#define LDACQ_IMM_OP         0x0a5
+/* 0x0a6, 0xa7 are not relevant */
+#define LDCCLR_IMM_OP        0x0a8
+#define LDCNC_IMM_OP         0x0a9
+#define LDCCLRACQ_IMM_OP     0x0aa
+#define ST_IMM_OP            0x0ac
+#define STREL_IMM_OP         0x0ad
+/* 0x0ae,0xaf are not relevant */
+
+/*
+ * Table C-32 Floating-point Load/Store
+ */
+#define LDF_OP           0x0c0
+#define LDFS_OP          0x0c1
+#define LDFA_OP          0x0c2
+#define LDFSA_OP         0x0c3
+/* 0x0c6 is irrelevant */
+#define LDFCCLR_OP       0x0c8
+#define LDFCNC_OP        0x0c9
+/* 0x0cb is irrelevant  */
+#define STF_OP           0x0cc
+
+/*
+ * Table C-33 Floating-point Load +Reg
+ *
+ * we use the ld->m (bit [36:36]) field to determine whether or not we have
+ * a load/store of this form.
+ */
+
+/*
+ * Table C-34 Floating-point Load/Store +Imm
+ */
+#define LDF_IMM_OP       0x0e0
+#define LDFS_IMM_OP      0x0e1
+#define LDFA_IMM_OP      0x0e2
+#define LDFSA_IMM_OP     0x0e3
+/* 0x0e6 is irrelevant */
+#define LDFCCLR_IMM_OP   0x0e8
+#define LDFCNC_IMM_OP    0x0e9
+#define STF_IMM_OP       0x0ec
+
+typedef struct {
+       unsigned long    qp:6;  /* [0:5]   */
+       unsigned long    r1:7;  /* [6:12]  */
+       unsigned long   imm:7;  /* [13:19] */
+       unsigned long    r3:7;  /* [20:26] */
+       unsigned long     x:1;  /* [27:27] */
+       unsigned long  hint:2;  /* [28:29] */
+       unsigned long x6_sz:2;  /* [30:31] */
+       unsigned long x6_op:4;  /* [32:35], x6 = x6_sz|x6_op */
+       unsigned long     m:1;  /* [36:36] */
+       unsigned long    op:4;  /* [37:40] */
+       unsigned long   pad:23; /* [41:63] */
+} load_store_t;
+
+
+typedef enum {
+       UPD_IMMEDIATE,  /* ldXZ r1=[r3],imm(9) */
+       UPD_REG         /* ldXZ r1=[r3],r2     */
+} update_t;
+
+/*
+ * We use tables to keep track of the offsets of registers in the saved state.
+ * This way we save having big switch/case statements.
+ *
+ * We use bit 0 to indicate switch_stack or pt_regs.
+ * The offset is simply shifted by 1 bit.
+ * A 2-byte value should be enough to hold any kind of offset
+ *
+ * In case the calling convention changes (and thus pt_regs/switch_stack)
+ * simply use RSW instead of RPT or vice-versa.
+ */
+
+#define RPO(x) ((size_t) &((struct pt_regs *)0)->x)
+#define RSO(x) ((size_t) &((struct switch_stack *)0)->x)
+
+#define RPT(x)         (RPO(x) << 1)
+#define RSW(x)         (1| RSO(x)<<1)
+
+#define GR_OFFS(x)     (gr_info[x]>>1)
+#define GR_IN_SW(x)    (gr_info[x] & 0x1)
+
+#define FR_OFFS(x)     (fr_info[x]>>1)
+#define FR_IN_SW(x)    (fr_info[x] & 0x1)
+
+static u16 gr_info[32]={
+       0,                      /* r0 is read-only : WE SHOULD NEVER GET THIS */
+
+       RPT(r1), RPT(r2), RPT(r3),
+
+#ifdef  CONFIG_VTI
+       RPT(r4), RPT(r5), RPT(r6), RPT(r7),
+#else   //CONFIG_VTI
+       RSW(r4), RSW(r5), RSW(r6), RSW(r7),
+#endif  //CONFIG_VTI
+
+       RPT(r8), RPT(r9), RPT(r10), RPT(r11),
+       RPT(r12), RPT(r13), RPT(r14), RPT(r15),
+
+       RPT(r16), RPT(r17), RPT(r18), RPT(r19),
+       RPT(r20), RPT(r21), RPT(r22), RPT(r23),
+       RPT(r24), RPT(r25), RPT(r26), RPT(r27),
+       RPT(r28), RPT(r29), RPT(r30), RPT(r31)
+};
+
+static u16 fr_info[32]={
+       0,                      /* constant : WE SHOULD NEVER GET THIS */
+       0,                      /* constant : WE SHOULD NEVER GET THIS */
+
+       RSW(f2), RSW(f3), RSW(f4), RSW(f5),
+
+       RPT(f6), RPT(f7), RPT(f8), RPT(f9),
+       RPT(f10), RPT(f11),
+
+       RSW(f12), RSW(f13), RSW(f14),
+       RSW(f15), RSW(f16), RSW(f17), RSW(f18), RSW(f19),
+       RSW(f20), RSW(f21), RSW(f22), RSW(f23), RSW(f24),
+       RSW(f25), RSW(f26), RSW(f27), RSW(f28), RSW(f29),
+       RSW(f30), RSW(f31)
+};
+
+/* Invalidate ALAT entry for integer register REGNO.  */
+static void
+invala_gr (int regno)
+{
+#      define F(reg)   case reg: ia64_invala_gr(reg); break
+
+       switch (regno) {
+               F(  0); F(  1); F(  2); F(  3); F(  4); F(  5); F(  6); F(  7);
+               F(  8); F(  9); F( 10); F( 11); F( 12); F( 13); F( 14); F( 15);
+               F( 16); F( 17); F( 18); F( 19); F( 20); F( 21); F( 22); F( 23);
+               F( 24); F( 25); F( 26); F( 27); F( 28); F( 29); F( 30); F( 31);
+               F( 32); F( 33); F( 34); F( 35); F( 36); F( 37); F( 38); F( 39);
+               F( 40); F( 41); F( 42); F( 43); F( 44); F( 45); F( 46); F( 47);
+               F( 48); F( 49); F( 50); F( 51); F( 52); F( 53); F( 54); F( 55);
+               F( 56); F( 57); F( 58); F( 59); F( 60); F( 61); F( 62); F( 63);
+               F( 64); F( 65); F( 66); F( 67); F( 68); F( 69); F( 70); F( 71);
+               F( 72); F( 73); F( 74); F( 75); F( 76); F( 77); F( 78); F( 79);
+               F( 80); F( 81); F( 82); F( 83); F( 84); F( 85); F( 86); F( 87);
+               F( 88); F( 89); F( 90); F( 91); F( 92); F( 93); F( 94); F( 95);
+               F( 96); F( 97); F( 98); F( 99); F(100); F(101); F(102); F(103);
+               F(104); F(105); F(106); F(107); F(108); F(109); F(110); F(111);
+               F(112); F(113); F(114); F(115); F(116); F(117); F(118); F(119);
+               F(120); F(121); F(122); F(123); F(124); F(125); F(126); F(127);
+       }
+#      undef F
+}
+
+/* Invalidate ALAT entry for floating-point register REGNO.  */
+static void
+invala_fr (int regno)
+{
+#      define F(reg)   case reg: ia64_invala_fr(reg); break
+
+       switch (regno) {
+               F(  0); F(  1); F(  2); F(  3); F(  4); F(  5); F(  6); F(  7);
+               F(  8); F(  9); F( 10); F( 11); F( 12); F( 13); F( 14); F( 15);
+               F( 16); F( 17); F( 18); F( 19); F( 20); F( 21); F( 22); F( 23);
+               F( 24); F( 25); F( 26); F( 27); F( 28); F( 29); F( 30); F( 31);
+               F( 32); F( 33); F( 34); F( 35); F( 36); F( 37); F( 38); F( 39);
+               F( 40); F( 41); F( 42); F( 43); F( 44); F( 45); F( 46); F( 47);
+               F( 48); F( 49); F( 50); F( 51); F( 52); F( 53); F( 54); F( 55);
+               F( 56); F( 57); F( 58); F( 59); F( 60); F( 61); F( 62); F( 63);
+               F( 64); F( 65); F( 66); F( 67); F( 68); F( 69); F( 70); F( 71);
+               F( 72); F( 73); F( 74); F( 75); F( 76); F( 77); F( 78); F( 79);
+               F( 80); F( 81); F( 82); F( 83); F( 84); F( 85); F( 86); F( 87);
+               F( 88); F( 89); F( 90); F( 91); F( 92); F( 93); F( 94); F( 95);
+               F( 96); F( 97); F( 98); F( 99); F(100); F(101); F(102); F(103);
+               F(104); F(105); F(106); F(107); F(108); F(109); F(110); F(111);
+               F(112); F(113); F(114); F(115); F(116); F(117); F(118); F(119);
+               F(120); F(121); F(122); F(123); F(124); F(125); F(126); F(127);
+       }
+#      undef F
+}
+
+static inline unsigned long
+rotate_reg (unsigned long sor, unsigned long rrb, unsigned long reg)
+{
+       reg += rrb;
+       if (reg >= sor)
+               reg -= sor;
+       return reg;
+}
+
+#ifdef CONFIG_VTI
+static void
+set_rse_reg (struct pt_regs *regs, unsigned long r1, unsigned long val, 
unsigned long nat)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long *bsp, *bspstore, *addr, *rnat_addr, *ubs_end;
+       unsigned long *kbs = (void *) current + IA64_RBS_OFFSET;
+       unsigned long rnats, nat_mask;
+    unsigned long old_rsc,new_rsc;
+       unsigned long on_kbs,rnat;
+       long sof = (regs->cr_ifs) & 0x7f;
+       long sor = 8 * ((regs->cr_ifs >> 14) & 0xf);
+       long rrb_gr = (regs->cr_ifs >> 18) & 0x7f;
+       long ridx = r1 - 32;
+
+       if (ridx >= sof) {
+               /* this should never happen, as the "rsvd register fault" has 
higher priority */
+               DPRINT("ignoring write to r%lu; only %lu registers are 
allocated!\n", r1, sof);
+               return;
+       }
+
+       if (ridx < sor)
+               ridx = rotate_reg(sor, rrb_gr, ridx);
+
+    old_rsc=ia64_get_rsc();
+    new_rsc=old_rsc&(~0x3);
+    ia64_set_rsc(new_rsc);
+
+    bspstore = ia64_get_bspstore();
+    bsp =kbs + (regs->loadrs >> 19);//16+3
+
+       addr = ia64_rse_skip_regs(bsp, -sof + ridx);
+    nat_mask = 1UL << ia64_rse_slot_num(addr);
+       rnat_addr = ia64_rse_rnat_addr(addr);
+
+    if(addr >= bspstore){
+
+        ia64_flushrs ();
+        ia64_mf ();
+               *addr = val;
+        bspstore = ia64_get_bspstore();
+       rnat = ia64_get_rnat ();
+        if(bspstore < rnat_addr){
+            rnat=rnat&(~nat_mask);
+        }else{
+            *rnat_addr = (*rnat_addr)&(~nat_mask);
+        }
+        ia64_mf();
+        ia64_loadrs();
+        ia64_set_rnat(rnat);
+    }else{
+
+       rnat = ia64_get_rnat ();
+               *addr = val;
+        if(bspstore < rnat_addr){
+            rnat=rnat&(~nat_mask);
+        }else{
+            *rnat_addr = (*rnat_addr)&(~nat_mask);
+        }
+        ia64_set_bspstore (bspstore);
+        ia64_set_rnat(rnat);
+    }
+    ia64_set_rsc(old_rsc);
+}
+
+
+static void
+get_rse_reg (struct pt_regs *regs, unsigned long r1, unsigned long *val, 
unsigned long *nat)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long *bsp, *addr, *rnat_addr, *ubs_end, *bspstore;
+       unsigned long *kbs = (void *) current + IA64_RBS_OFFSET;
+       unsigned long rnats, nat_mask;
+       unsigned long on_kbs;
+    unsigned long old_rsc, new_rsc;
+       long sof = (regs->cr_ifs) & 0x7f;
+       long sor = 8 * ((regs->cr_ifs >> 14) & 0xf);
+       long rrb_gr = (regs->cr_ifs >> 18) & 0x7f;
+       long ridx = r1 - 32;
+
+       if (ridx >= sof) {
+               /* read of out-of-frame register returns an undefined value; 0 
in our case.  */
+               DPRINT("ignoring read from r%lu; only %lu registers are 
allocated!\n", r1, sof);
+               panic("wrong stack register number");
+       }
+
+       if (ridx < sor)
+               ridx = rotate_reg(sor, rrb_gr, ridx);
+
+    old_rsc=ia64_get_rsc();
+    new_rsc=old_rsc&(~(0x3));
+    ia64_set_rsc(new_rsc);
+
+    bspstore = ia64_get_bspstore();
+    bsp =kbs + (regs->loadrs >> 19); //16+3;
+
+       addr = ia64_rse_skip_regs(bsp, -sof + ridx);
+    nat_mask = 1UL << ia64_rse_slot_num(addr);
+       rnat_addr = ia64_rse_rnat_addr(addr);
+
+    if(addr >= bspstore){
+
+        ia64_flushrs ();
+        ia64_mf ();
+        bspstore = ia64_get_bspstore();
+    }
+       *val=*addr;
+    if(bspstore < rnat_addr){
+        *nat=!!(ia64_get_rnat()&nat_mask);
+    }else{
+        *nat = !!((*rnat_addr)&nat_mask);
+    }
+    ia64_set_rsc(old_rsc);
+}
+#else // CONFIG_VTI
+static void
+set_rse_reg (struct pt_regs *regs, unsigned long r1, unsigned long val, int 
nat)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long *bsp, *bspstore, *addr, *rnat_addr, *ubs_end;
+       unsigned long *kbs = (void *) current + IA64_RBS_OFFSET;
+       unsigned long rnats, nat_mask;
+       unsigned long on_kbs;
+       long sof = (regs->cr_ifs) & 0x7f;
+       long sor = 8 * ((regs->cr_ifs >> 14) & 0xf);
+       long rrb_gr = (regs->cr_ifs >> 18) & 0x7f;
+       long ridx = r1 - 32;
+
+       if (ridx >= sof) {
+               /* this should never happen, as the "rsvd register fault" has 
higher priority */
+               DPRINT("ignoring write to r%lu; only %lu registers are 
allocated!\n", r1, sof);
+               return;
+       }
+
+       if (ridx < sor)
+               ridx = rotate_reg(sor, rrb_gr, ridx);
+
+       DPRINT("r%lu, sw.bspstore=%lx pt.bspstore=%lx sof=%ld sol=%ld 
ridx=%ld\n",
+              r1, sw->ar_bspstore, regs->ar_bspstore, sof, (regs->cr_ifs >> 7) 
& 0x7f, ridx);
+
+       on_kbs = ia64_rse_num_regs(kbs, (unsigned long *) sw->ar_bspstore);
+       addr = ia64_rse_skip_regs((unsigned long *) sw->ar_bspstore, -sof + 
ridx);
+       if (addr >= kbs) {
+               /* the register is on the kernel backing store: easy... */
+               rnat_addr = ia64_rse_rnat_addr(addr);
+               if ((unsigned long) rnat_addr >= sw->ar_bspstore)
+                       rnat_addr = &sw->ar_rnat;
+               nat_mask = 1UL << ia64_rse_slot_num(addr);
+
+               *addr = val;
+               if (nat)
+                       *rnat_addr |=  nat_mask;
+               else
+                       *rnat_addr &= ~nat_mask;
+               return;
+       }
+
+       if (!user_stack(current, regs)) {
+               DPRINT("ignoring kernel write to r%lu; register isn't on the 
kernel RBS!", r1);
+               return;
+       }
+
+       bspstore = (unsigned long *)regs->ar_bspstore;
+       ubs_end = ia64_rse_skip_regs(bspstore, on_kbs);
+       bsp     = ia64_rse_skip_regs(ubs_end, -sof);
+       addr    = ia64_rse_skip_regs(bsp, ridx);
+
+       DPRINT("ubs_end=%p bsp=%p addr=%p\n", (void *) ubs_end, (void *) bsp, 
(void *) addr);
+
+       ia64_poke(current, sw, (unsigned long) ubs_end, (unsigned long) addr, 
val);
+
+       rnat_addr = ia64_rse_rnat_addr(addr);
+
+       ia64_peek(current, sw, (unsigned long) ubs_end, (unsigned long) 
rnat_addr, &rnats);
+       DPRINT("rnat @%p = 0x%lx nat=%d old nat=%ld\n",
+              (void *) rnat_addr, rnats, nat, (rnats >> 
ia64_rse_slot_num(addr)) & 1);
+
+       nat_mask = 1UL << ia64_rse_slot_num(addr);
+       if (nat)
+               rnats |=  nat_mask;
+       else
+               rnats &= ~nat_mask;
+       ia64_poke(current, sw, (unsigned long) ubs_end, (unsigned long) 
rnat_addr, rnats);
+
+       DPRINT("rnat changed to @%p = 0x%lx\n", (void *) rnat_addr, rnats);
+}
+
+
+static void
+get_rse_reg (struct pt_regs *regs, unsigned long r1, unsigned long *val, int 
*nat)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long *bsp, *addr, *rnat_addr, *ubs_end, *bspstore;
+       unsigned long *kbs = (void *) current + IA64_RBS_OFFSET;
+       unsigned long rnats, nat_mask;
+       unsigned long on_kbs;
+       long sof = (regs->cr_ifs) & 0x7f;
+       long sor = 8 * ((regs->cr_ifs >> 14) & 0xf);
+       long rrb_gr = (regs->cr_ifs >> 18) & 0x7f;
+       long ridx = r1 - 32;
+
+       if (ridx >= sof) {
+               /* read of out-of-frame register returns an undefined value; 0 
in our case.  */
+               DPRINT("ignoring read from r%lu; only %lu registers are 
allocated!\n", r1, sof);
+               goto fail;
+       }
+
+       if (ridx < sor)
+               ridx = rotate_reg(sor, rrb_gr, ridx);
+
+       DPRINT("r%lu, sw.bspstore=%lx pt.bspstore=%lx sof=%ld sol=%ld 
ridx=%ld\n",
+              r1, sw->ar_bspstore, regs->ar_bspstore, sof, (regs->cr_ifs >> 7) 
& 0x7f, ridx);
+
+       on_kbs = ia64_rse_num_regs(kbs, (unsigned long *) sw->ar_bspstore);
+       addr = ia64_rse_skip_regs((unsigned long *) sw->ar_bspstore, -sof + 
ridx);
+       if (addr >= kbs) {
+               /* the register is on the kernel backing store: easy... */
+               *val = *addr;
+               if (nat) {
+                       rnat_addr = ia64_rse_rnat_addr(addr);
+                       if ((unsigned long) rnat_addr >= sw->ar_bspstore)
+                               rnat_addr = &sw->ar_rnat;
+                       nat_mask = 1UL << ia64_rse_slot_num(addr);
+                       *nat = (*rnat_addr & nat_mask) != 0;
+               }
+               return;
+       }
+
+       if (!user_stack(current, regs)) {
+               DPRINT("ignoring kernel read of r%lu; register isn't on the 
RBS!", r1);
+               goto fail;
+       }
+
+       bspstore = (unsigned long *)regs->ar_bspstore;
+       ubs_end = ia64_rse_skip_regs(bspstore, on_kbs);
+       bsp     = ia64_rse_skip_regs(ubs_end, -sof);
+       addr    = ia64_rse_skip_regs(bsp, ridx);
+
+       DPRINT("ubs_end=%p bsp=%p addr=%p\n", (void *) ubs_end, (void *) bsp, 
(void *) addr);
+
+       ia64_peek(current, sw, (unsigned long) ubs_end, (unsigned long) addr, 
val);
+
+       if (nat) {
+               rnat_addr = ia64_rse_rnat_addr(addr);
+               nat_mask = 1UL << ia64_rse_slot_num(addr);
+
+               DPRINT("rnat @%p = 0x%lx\n", (void *) rnat_addr, rnats);
+
+               ia64_peek(current, sw, (unsigned long) ubs_end, (unsigned long) 
rnat_addr, &rnats);
+               *nat = (rnats & nat_mask) != 0;
+       }
+       return;
+
+  fail:
+       *val = 0;
+       if (nat)
+               *nat = 0;
+       return;
+}
+#endif // CONFIG_VTI
+
+
+#ifdef XEN
+void
+#else
+static void
+#endif
+setreg (unsigned long regnum, unsigned long val, int nat, struct pt_regs *regs)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long addr;
+       unsigned long bitmask;
+       unsigned long *unat;
+
+       /*
+        * First takes care of stacked registers
+        */
+       if (regnum >= IA64_FIRST_STACKED_GR) {
+               set_rse_reg(regs, regnum, val, nat);
+               return;
+       }
+
+       /*
+        * Using r0 as a target raises a General Exception fault which has 
higher priority
+        * than the Unaligned Reference fault.
+        */
+
+       /*
+        * Now look at registers in [0-31] range and init correct UNAT
+        */
+       if (GR_IN_SW(regnum)) {
+               addr = (unsigned long)sw;
+               unat = &sw->ar_unat;
+       } else {
+               addr = (unsigned long)regs;
+#ifdef CONFIG_VTI
+               unat = &regs->eml_unat;
+#else //CONFIG_VTI
+               unat = &sw->caller_unat;
+#endif  //CONFIG_VTI
+       }
+       DPRINT("tmp_base=%lx switch_stack=%s offset=%d\n",
+              addr, unat==&sw->ar_unat ? "yes":"no", GR_OFFS(regnum));
+       /*
+        * add offset from base of struct
+        * and do it !
+        */
+       addr += GR_OFFS(regnum);
+
+       *(unsigned long *)addr = val;
+
+       /*
+        * We need to clear the corresponding UNAT bit to fully emulate the load
+        * UNAT bit_pos = GR[r3]{8:3} form EAS-2.4
+        */
+       bitmask   = 1UL << (addr >> 3 & 0x3f);
+       DPRINT("*0x%lx=0x%lx NaT=%d prev_unat @%p=%lx\n", addr, val, nat, (void 
*) unat, *unat);
+       if (nat) {
+               *unat |= bitmask;
+       } else {
+               *unat &= ~bitmask;
+       }
+       DPRINT("*0x%lx=0x%lx NaT=%d new unat: %p=%lx\n", addr, val, nat, (void 
*) unat,*unat);
+}
+
+/*
+ * Return the (rotated) index for floating point register REGNUM (REGNUM must 
be in the
+ * range from 32-127, result is in the range from 0-95.
+ */
+static inline unsigned long
+fph_index (struct pt_regs *regs, long regnum)
+{
+       unsigned long rrb_fr = (regs->cr_ifs >> 25) & 0x7f;
+       return rotate_reg(96, rrb_fr, (regnum - IA64_FIRST_ROTATING_FR));
+}
+
+static void
+setfpreg (unsigned long regnum, struct ia64_fpreg *fpval, struct pt_regs *regs)
+{
+       struct switch_stack *sw = (struct switch_stack *)regs - 1;
+       unsigned long addr;
+
+       /*
+        * From EAS-2.5: FPDisableFault has higher priority than Unaligned
+        * Fault. Thus, when we get here, we know the partition is enabled.
+        * To update f32-f127, there are three choices:
+        *
+        *      (1) save f32-f127 to thread.fph and update the values there
+        *      (2) use a gigantic switch statement to directly access the 
registers
+        *      (3) generate code on the fly to update the desired register
+        *
+        * For now, we are using approach (1).
+        */
+       if (regnum >= IA64_FIRST_ROTATING_FR) {
+               ia64_sync_fph(current);
+#ifdef XEN
+               current->arch._thread.fph[fph_index(regs, regnum)] = *fpval;
+#else
+               current->thread.fph[fph_index(regs, regnum)] = *fpval;
+#endif
+       } else {
+               /*
+                * pt_regs or switch_stack ?
+                */
+               if (FR_IN_SW(regnum)) {
+                       addr = (unsigned long)sw;
+               } else {
+                       addr = (unsigned long)regs;
+               }
+
+               DPRINT("tmp_base=%lx offset=%d\n", addr, FR_OFFS(regnum));
+
+               addr += FR_OFFS(regnum);
+               *(struct ia64_fpreg *)addr = *fpval;
+
+               /*
+                * mark the low partition as being used now
+                *
+                * It is highly unlikely that this bit is not already set, but
+                * let's do it for safety.
+                */
+               regs->cr_ipsr |= IA64_PSR_MFL;
+       }
+}
+
+/*
+ * Those 2 inline functions generate the spilled versions of the constant 
floating point
+ * registers which can be used with stfX
+ */
+static inline void
+float_spill_f0 (struct ia64_fpreg *final)
+{
+       ia64_stf_spill(final, 0);
+}
+
+static inline void
+float_spill_f1 (struct ia64_fpreg *final)
+{
+       ia64_stf_spill(final, 1);
+}
+
+static void
+getfpreg (unsigned long regnum, struct ia64_fpreg *fpval, struct pt_regs *regs)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long addr;
+
+       /*
+        * From EAS-2.5: FPDisableFault has higher priority than
+        * Unaligned Fault. Thus, when we get here, we know the partition is
+        * enabled.
+        *
+        * When regnum > 31, the register is still live and we need to force a 
save
+        * to current->thread.fph to get access to it.  See discussion in 
setfpreg()
+        * for reasons and other ways of doing this.
+        */
+       if (regnum >= IA64_FIRST_ROTATING_FR) {
+               ia64_flush_fph(current);
+#ifdef XEN
+               *fpval = current->arch._thread.fph[fph_index(regs, regnum)];
+#else
+               *fpval = current->thread.fph[fph_index(regs, regnum)];
+#endif
+       } else {
+               /*
+                * f0 = 0.0, f1= 1.0. Those registers are constant and are thus
+                * not saved, we must generate their spilled form on the fly
+                */
+               switch(regnum) {
+               case 0:
+                       float_spill_f0(fpval);
+                       break;
+               case 1:
+                       float_spill_f1(fpval);
+                       break;
+               default:
+                       /*
+                        * pt_regs or switch_stack ?
+                        */
+                       addr =  FR_IN_SW(regnum) ? (unsigned long)sw
+                                                : (unsigned long)regs;
+
+                       DPRINT("is_sw=%d tmp_base=%lx offset=0x%x\n",
+                              FR_IN_SW(regnum), addr, FR_OFFS(regnum));
+
+                       addr  += FR_OFFS(regnum);
+                       *fpval = *(struct ia64_fpreg *)addr;
+               }
+       }
+}
+
+
+#ifdef XEN
+void
+#else
+static void
+#endif
+getreg (unsigned long regnum, unsigned long *val, int *nat, struct pt_regs 
*regs)
+{
+       struct switch_stack *sw = (struct switch_stack *) regs - 1;
+       unsigned long addr, *unat;
+
+       if (regnum >= IA64_FIRST_STACKED_GR) {
+               get_rse_reg(regs, regnum, val, nat);
+               return;
+       }
+
+       /*
+        * take care of r0 (read-only always evaluate to 0)
+        */
+       if (regnum == 0) {
+               *val = 0;
+               if (nat)
+                       *nat = 0;
+               return;
+       }
+
+       /*
+        * Now look at registers in [0-31] range and init correct UNAT
+        */
+       if (GR_IN_SW(regnum)) {
+               addr = (unsigned long)sw;
+               unat = &sw->ar_unat;
+       } else {
+               addr = (unsigned long)regs;
+#ifdef  CONFIG_VTI
+               unat = &regs->eml_unat;;
+#else   //CONFIG_VTI
+               unat = &sw->caller_unat;
+#endif  //CONFIG_VTI
+       }
+
+       DPRINT("addr_base=%lx offset=0x%x\n", addr,  GR_OFFS(regnum));
+
+       addr += GR_OFFS(regnum);
+
+       *val  = *(unsigned long *)addr;
+
+       /*
+        * do it only when requested
+        */
+       if (nat)
+               *nat  = (*unat >> (addr >> 3 & 0x3f)) & 0x1UL;
+}
+
+static void
+emulate_load_updates (update_t type, load_store_t ld, struct pt_regs *regs, 
unsigned long ifa)
+{
+       /*
+        * IMPORTANT:
+        * Given the way we handle unaligned speculative loads, we should
+        * not get to this point in the code but we keep this sanity check,
+        * just in case.
+        */
+       if (ld.x6_op == 1 || ld.x6_op == 3) {
+               printk(KERN_ERR "%s: register update on speculative load, 
error\n", __FUNCTION__);
+               die_if_kernel("unaligned reference on speculative load with 
register update\n",
+                             regs, 30);
+       }
+
+
+       /*
+        * at this point, we know that the base register to update is valid 
i.e.,
+        * it's not r0
+        */
+       if (type == UPD_IMMEDIATE) {
+               unsigned long imm;
+
+               /*
+                * Load +Imm: ldXZ r1=[r3],imm(9)
+                *
+                *
+                * form imm9: [13:19] contain the first 7 bits
+                */
+               imm = ld.x << 7 | ld.imm;
+
+               /*
+                * sign extend (1+8bits) if m set
+                */
+               if (ld.m) imm |= SIGN_EXT9;
+
+               /*
+                * ifa == r3 and we know that the NaT bit on r3 was clear so
+                * we can directly use ifa.
+                */
+               ifa += imm;
+
+               setreg(ld.r3, ifa, 0, regs);
+
+               DPRINT("ld.x=%d ld.m=%d imm=%ld r3=0x%lx\n", ld.x, ld.m, imm, 
ifa);
+
+       } else if (ld.m) {
+               unsigned long r2;
+               int nat_r2;
+
+               /*
+                * Load +Reg Opcode: ldXZ r1=[r3],r2
+                *
+                * Note: that we update r3 even in the case of ldfX.a
+                * (where the load does not happen)
+                *
+                * The way the load algorithm works, we know that r3 does not
+                * have its NaT bit set (would have gotten NaT consumption
+                * before getting the unaligned fault). So we can use ifa
+                * which equals r3 at this point.
+                *
+                * IMPORTANT:
+                * The above statement holds ONLY because we know that we
+                * never reach this code when trying to do a ldX.s.
+                * If we ever make it to here on an ldfX.s then
+                */
+               getreg(ld.imm, &r2, &nat_r2, regs);
+
+               ifa += r2;
+
+               /*
+                * propagate Nat r2 -> r3
+                */
+               setreg(ld.r3, ifa, nat_r2, regs);
+
+               DPRINT("imm=%d r2=%ld r3=0x%lx nat_r2=%d\n",ld.imm, r2, ifa, 
nat_r2);
+       }
+}
+
+
+static int
+emulate_load_int (unsigned long ifa, load_store_t ld, struct pt_regs *regs)
+{
+       unsigned int len = 1 << ld.x6_sz;
+       unsigned long val = 0;
+
+       /*
+        * r0, as target, doesn't need to be checked because Illegal Instruction
+        * faults have higher priority than unaligned faults.
+        *
+        * r0 cannot be found as the base as it would never generate an
+        * unaligned reference.
+        */
+
+       /*
+        * ldX.a we will emulate load and also invalidate the ALAT entry.
+        * See comment below for explanation on how we handle ldX.a
+        */
+
+       if (len != 2 && len != 4 && len != 8) {
+               DPRINT("unknown size: x6=%d\n", ld.x6_sz);
+               return -1;
+       }
+       /* this assumes little-endian byte-order: */
+       if (copy_from_user(&val, (void __user *) ifa, len))
+               return -1;
+       setreg(ld.r1, val, 0, regs);
+
+       /*
+        * check for updates on any kind of loads
+        */
+       if (ld.op == 0x5 || ld.m)
+               emulate_load_updates(ld.op == 0x5 ? UPD_IMMEDIATE: UPD_REG, ld, 
regs, ifa);
+
+       /*
+        * handling of various loads (based on EAS2.4):
+        *
+        * ldX.acq (ordered load):
+        *      - acquire semantics would have been used, so force fence 
instead.
+        *
+        * ldX.c.clr (check load and clear):
+        *      - if we get to this handler, it's because the entry was not in 
the ALAT.
+        *        Therefore the operation reverts to a normal load
+        *
+        * ldX.c.nc (check load no clear):
+        *      - same as previous one
+        *
+        * ldX.c.clr.acq (ordered check load and clear):
+        *      - same as above for c.clr part. The load needs to have acquire 
semantics. So
+        *        we use the fence semantics which is stronger and thus ensures 
correctness.
+        *
+        * ldX.a (advanced load):
+        *      - suppose ldX.a r1=[r3]. If we get to the unaligned trap it's 
because the
+        *        address doesn't match requested size alignment. This means 
that we would
+        *        possibly need more than one load to get the result.
+        *
+        *        The load part can be handled just like a normal load, however 
the difficult
+        *        part is to get the right thing into the ALAT. The critical 
piece of information
+        *        in the base address of the load & size. To do that, a ld.a 
must be executed,
+        *        clearly any address can be pushed into the table by using 
ld1.a r1=[r3]. Now
+        *        if we use the same target register, we will be okay for the 
check.a instruction.
+        *        If we look at the store, basically a stX [r3]=r1 checks the 
ALAT  for any entry
+        *        which would overlap within [r3,r3+X] (the size of the load 
was store in the
+        *        ALAT). If such an entry is found the entry is invalidated. 
But this is not good
+        *        enough, take the following example:
+        *              r3=3
+        *              ld4.a r1=[r3]
+        *
+        *        Could be emulated by doing:
+        *              ld1.a r1=[r3],1
+        *              store to temporary;
+        *              ld1.a r1=[r3],1
+        *              store & shift to temporary;
+        *              ld1.a r1=[r3],1
+        *              store & shift to temporary;
+        *              ld1.a r1=[r3]
+        *              store & shift to temporary;
+        *              r1=temporary
+        *
+        *        So in this case, you would get the right value is r1 but the 
wrong info in
+        *        the ALAT.  Notice that you could do it in reverse to finish 
with address 3
+        *        but you would still get the size wrong.  To get the size 
right, one needs to
+        *        execute exactly the same kind of load. You could do it from a 
aligned
+        *        temporary location, but you would get the address wrong.
+        *
+        *        So no matter what, it is not possible to emulate an advanced 
load
+        *        correctly. But is that really critical ?
+        *
+        *        We will always convert ld.a into a normal load with ALAT 
invalidated.  This
+        *        will enable compiler to do optimization where certain code 
path after ld.a
+        *        is not required to have ld.c/chk.a, e.g., code path with no 
intervening stores.
+        *
+        *        If there is a store after the advanced load, one must either 
do a ld.c.* or
+        *        chk.a.* to reuse the value stored in the ALAT. Both can 
"fail" (meaning no
+        *        entry found in ALAT), and that's perfectly ok because:
+        *
+        *              - ld.c.*, if the entry is not present a  normal load is 
executed
+        *              - chk.a.*, if the entry is not present, execution jumps 
to recovery code
+        *
+        *        In either case, the load can be potentially retried in 
another form.
+        *
+        *        ALAT must be invalidated for the register (so that chk.a or 
ld.c don't pick
+        *        up a stale entry later). The register base update MUST also 
be performed.
+        */
+
+       /*
+        * when the load has the .acq completer then
+        * use ordering fence.
+        */
+       if (ld.x6_op == 0x5 || ld.x6_op == 0xa)
+               mb();
+
+       /*
+        * invalidate ALAT entry in case of advanced load
+        */
+       if (ld.x6_op == 0x2)
+               invala_gr(ld.r1);
+
+       return 0;
+}
+
+static int
+emulate_store_int (unsigned long ifa, load_store_t ld, struct pt_regs *regs)
+{
+       unsigned long r2;
+       unsigned int len = 1 << ld.x6_sz;
+
+       /*
+        * if we get to this handler, Nat bits on both r3 and r2 have already
+        * been checked. so we don't need to do it
+        *
+        * extract the value to be stored
+        */
+       getreg(ld.imm, &r2, NULL, regs);
+
+       /*
+        * we rely on the macros in unaligned.h for now i.e.,
+        * we let the compiler figure out how to read memory gracefully.
+        *
+        * We need this switch/case because the way the inline function
+        * works. The code is optimized by the compiler and looks like
+        * a single switch/case.
+        */
+       DPRINT("st%d [%lx]=%lx\n", len, ifa, r2);
+
+       if (len != 2 && len != 4 && len != 8) {
+               DPRINT("unknown size: x6=%d\n", ld.x6_sz);
+               return -1;
+       }
+
+       /* this assumes little-endian byte-order: */
+       if (copy_to_user((void __user *) ifa, &r2, len))
+               return -1;
+
+       /*
+        * stX [r3]=r2,imm(9)
+        *
+        * NOTE:
+        * ld.r3 can never be r0, because r0 would not generate an
+        * unaligned access.
+        */
+       if (ld.op == 0x5) {
+               unsigned long imm;
+
+               /*
+                * form imm9: [12:6] contain first 7bits
+                */
+               imm = ld.x << 7 | ld.r1;
+               /*
+                * sign extend (8bits) if m set
+                */
+               if (ld.m) imm |= SIGN_EXT9;
+               /*
+                * ifa == r3 (NaT is necessarily cleared)
+                */
+               ifa += imm;
+
+               DPRINT("imm=%lx r3=%lx\n", imm, ifa);
+
+               setreg(ld.r3, ifa, 0, regs);
+       }
+       /*
+        * we don't have alat_invalidate_multiple() so we need
+        * to do the complete flush :-<<
+        */
+       ia64_invala();
+
+       /*
+        * stX.rel: use fence instead of release
+        */
+       if (ld.x6_op == 0xd)
+               mb();
+
+       return 0;
+}
+
+/*
+ * floating point operations sizes in bytes
+ */
+static const unsigned char float_fsz[4]={
+       10, /* extended precision (e) */
+       8,  /* integer (8)            */
+       4,  /* single precision (s)   */
+       8   /* double precision (d)   */
+};
+
+static inline void
+mem2float_extended (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldfe(6, init);
+       ia64_stop();
+       ia64_stf_spill(final, 6);
+}
+
+static inline void
+mem2float_integer (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldf8(6, init);
+       ia64_stop();
+       ia64_stf_spill(final, 6);
+}
+
+static inline void
+mem2float_single (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldfs(6, init);
+       ia64_stop();
+       ia64_stf_spill(final, 6);
+}
+
+static inline void
+mem2float_double (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldfd(6, init);
+       ia64_stop();
+       ia64_stf_spill(final, 6);
+}
+
+static inline void
+float2mem_extended (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldf_fill(6, init);
+       ia64_stop();
+       ia64_stfe(final, 6);
+}
+
+static inline void
+float2mem_integer (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldf_fill(6, init);
+       ia64_stop();
+       ia64_stf8(final, 6);
+}
+
+static inline void
+float2mem_single (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldf_fill(6, init);
+       ia64_stop();
+       ia64_stfs(final, 6);
+}
+
+static inline void
+float2mem_double (struct ia64_fpreg *init, struct ia64_fpreg *final)
+{
+       ia64_ldf_fill(6, init);
+       ia64_stop();
+       ia64_stfd(final, 6);
+}
+
+static int
+emulate_load_floatpair (unsigned long ifa, load_store_t ld, struct pt_regs 
*regs)
+{
+       struct ia64_fpreg fpr_init[2];
+       struct ia64_fpreg fpr_final[2];
+       unsigned long len = float_fsz[ld.x6_sz];
+
+       /*
+        * fr0 & fr1 don't need to be checked because Illegal Instruction 
faults have
+        * higher priority than unaligned faults.
+        *
+        * r0 cannot be found as the base as it would never generate an 
unaligned
+        * reference.
+        */
+
+       /*
+        * make sure we get clean buffers
+        */
+       memset(&fpr_init, 0, sizeof(fpr_init));
+       memset(&fpr_final, 0, sizeof(fpr_final));
+
+       /*
+        * ldfpX.a: we don't try to emulate anything but we must
+        * invalidate the ALAT entry and execute updates, if any.
+        */
+       if (ld.x6_op != 0x2) {
+               /*
+                * This assumes little-endian byte-order.  Note that there is 
no "ldfpe"
+                * instruction:
+                */
+               if (copy_from_user(&fpr_init[0], (void __user *) ifa, len)
+                   || copy_from_user(&fpr_init[1], (void __user *) (ifa + 
len), len))
+                       return -1;
+
+               DPRINT("ld.r1=%d ld.imm=%d x6_sz=%d\n", ld.r1, ld.imm, 
ld.x6_sz);
+               DDUMP("frp_init =", &fpr_init, 2*len);
+               /*
+                * XXX fixme
+                * Could optimize inlines by using ldfpX & 2 spills
+                */
+               switch( ld.x6_sz ) {
+                       case 0:
+                               mem2float_extended(&fpr_init[0], &fpr_final[0]);
+                               mem2float_extended(&fpr_init[1], &fpr_final[1]);
+                               break;
+                       case 1:
+                               mem2float_integer(&fpr_init[0], &fpr_final[0]);
+                               mem2float_integer(&fpr_init[1], &fpr_final[1]);
+                               break;
+                       case 2:
+                               mem2float_single(&fpr_init[0], &fpr_final[0]);
+                               mem2float_single(&fpr_init[1], &fpr_final[1]);
+                               break;
+                       case 3:
+                               mem2float_double(&fpr_init[0], &fpr_final[0]);
+                               mem2float_double(&fpr_init[1], &fpr_final[1]);
+                               break;
+               }
+               DDUMP("fpr_final =", &fpr_final, 2*len);
+               /*
+                * XXX fixme
+                *
+                * A possible optimization would be to drop fpr_final and 
directly
+                * use the storage from the saved context i.e., the actual final
+                * destination (pt_regs, switch_stack or thread structure).
+                */
+               setfpreg(ld.r1, &fpr_final[0], regs);
+               setfpreg(ld.imm, &fpr_final[1], regs);
+       }
+
+       /*
+        * Check for updates: only immediate updates are available for this
+        * instruction.
+        */
+       if (ld.m) {
+               /*
+                * the immediate is implicit given the ldsz of the operation:
+                * single: 8 (2x4) and for  all others it's 16 (2x8)
+                */
+               ifa += len<<1;
+
+               /*
+                * IMPORTANT:
+                * the fact that we force the NaT of r3 to zero is ONLY valid
+                * as long as we don't come here with a ldfpX.s.
+                * For this reason we keep this sanity check
+                */
+               if (ld.x6_op == 1 || ld.x6_op == 3)
+                       printk(KERN_ERR "%s: register update on speculative 
load pair, error\n",
+                              __FUNCTION__);
+
+               setreg(ld.r3, ifa, 0, regs);
+       }
+
+       /*
+        * Invalidate ALAT entries, if any, for both registers.
+        */
+       if (ld.x6_op == 0x2) {
+               invala_fr(ld.r1);
+               invala_fr(ld.imm);
+       }
+       return 0;
+}
+
+
+static int
+emulate_load_float (unsigned long ifa, load_store_t ld, struct pt_regs *regs)
+{
+       struct ia64_fpreg fpr_init;
+       struct ia64_fpreg fpr_final;
+       unsigned long len = float_fsz[ld.x6_sz];
+
+       /*
+        * fr0 & fr1 don't need to be checked because Illegal Instruction
+        * faults have higher priority than unaligned faults.
+        *
+        * r0 cannot be found as the base as it would never generate an
+        * unaligned reference.
+        */
+
+       /*
+        * make sure we get clean buffers
+        */
+       memset(&fpr_init,0, sizeof(fpr_init));
+       memset(&fpr_final,0, sizeof(fpr_final));
+
+       /*
+        * ldfX.a we don't try to emulate anything but we must
+        * invalidate the ALAT entry.
+        * See comments in ldX for descriptions on how the various loads are 
handled.
+        */
+       if (ld.x6_op != 0x2) {
+               if (copy_from_user(&fpr_init, (void __user *) ifa, len))
+                       return -1;
+
+               DPRINT("ld.r1=%d x6_sz=%d\n", ld.r1, ld.x6_sz);
+               DDUMP("fpr_init =", &fpr_init, len);
+               /*
+                * we only do something for x6_op={0,8,9}
+                */
+               switch( ld.x6_sz ) {
+                       case 0:
+                               mem2float_extended(&fpr_init, &fpr_final);
+                               break;
+                       case 1:
+                               mem2float_integer(&fpr_init, &fpr_final);
+                               break;
+                       case 2:
+                               mem2float_single(&fpr_init, &fpr_final);
+                               break;
+                       case 3:
+                               mem2float_double(&fpr_init, &fpr_final);
+                               break;
+               }
+               DDUMP("fpr_final =", &fpr_final, len);
+               /*
+                * XXX fixme
+                *
+                * A possible optimization would be to drop fpr_final and 
directly
+                * use the storage from the saved context i.e., the actual final
+                * destination (pt_regs, switch_stack or thread structure).
+                */
+               setfpreg(ld.r1, &fpr_final, regs);
+       }
+
+       /*
+        * check for updates on any loads
+        */
+       if (ld.op == 0x7 || ld.m)
+               emulate_load_updates(ld.op == 0x7 ? UPD_IMMEDIATE: UPD_REG, ld, 
regs, ifa);
+
+       /*
+        * invalidate ALAT entry in case of advanced floating point loads
+        */
+       if (ld.x6_op == 0x2)
+               invala_fr(ld.r1);
+
+       return 0;
+}
+
+
+static int
+emulate_store_float (unsigned long ifa, load_store_t ld, struct pt_regs *regs)
+{
+       struct ia64_fpreg fpr_init;
+       struct ia64_fpreg fpr_final;
+       unsigned long len = float_fsz[ld.x6_sz];
+
+       /*
+        * make sure we get clean buffers
+        */
+       memset(&fpr_init,0, sizeof(fpr_init));
+       memset(&fpr_final,0, sizeof(fpr_final));
+
+       /*
+        * if we get to this handler, Nat bits on both r3 and r2 have already
+        * been checked. so we don't need to do it
+        *
+        * extract the value to be stored
+        */
+       getfpreg(ld.imm, &fpr_init, regs);
+       /*
+        * during this step, we extract the spilled registers from the saved
+        * context i.e., we refill. Then we store (no spill) to temporary
+        * aligned location
+        */
+       switch( ld.x6_sz ) {
+               case 0:
+                       float2mem_extended(&fpr_init, &fpr_final);
+                       break;
+               case 1:
+                       float2mem_integer(&fpr_init, &fpr_final);
+                       break;
+               case 2:
+                       float2mem_single(&fpr_init, &fpr_final);
+                       break;
+               case 3:
+                       float2mem_double(&fpr_init, &fpr_final);
+                       break;
+       }
+       DPRINT("ld.r1=%d x6_sz=%d\n", ld.r1, ld.x6_sz);
+       DDUMP("fpr_init =", &fpr_init, len);
+       DDUMP("fpr_final =", &fpr_final, len);
+
+       if (copy_to_user((void __user *) ifa, &fpr_final, len))
+               return -1;
+
+       /*
+        * stfX [r3]=r2,imm(9)
+        *
+        * NOTE:
+        * ld.r3 can never be r0, because r0 would not generate an
+        * unaligned access.
+        */
+       if (ld.op == 0x7) {
+               unsigned long imm;
+
+               /*
+                * form imm9: [12:6] contain first 7bits
+                */
+               imm = ld.x << 7 | ld.r1;
+               /*
+                * sign extend (8bits) if m set
+                */
+               if (ld.m)
+                       imm |= SIGN_EXT9;
+               /*
+                * ifa == r3 (NaT is necessarily cleared)
+                */
+               ifa += imm;
+
+               DPRINT("imm=%lx r3=%lx\n", imm, ifa);
+
+               setreg(ld.r3, ifa, 0, regs);
+       }
+       /*
+        * we don't have alat_invalidate_multiple() so we need
+        * to do the complete flush :-<<
+        */
+       ia64_invala();
+
+       return 0;
+}
+
+/*
+ * Make sure we log the unaligned access, so that user/sysadmin can notice it 
and
+ * eventually fix the program.  However, we don't want to do that for every 
access so we
+ * pace it with jiffies.  This isn't really MP-safe, but it doesn't really 
have to be
+ * either...
+ */
+static int
+within_logging_rate_limit (void)
+{
+       static unsigned long count, last_time;
+
+       if (jiffies - last_time > 5*HZ)
+               count = 0;
+       if (++count < 5) {
+               last_time = jiffies;
+               return 1;
+       }
+       return 0;
+
+}
+
+void
+ia64_handle_unaligned (unsigned long ifa, struct pt_regs *regs)
+{
+#ifdef XEN
+printk("ia64_handle_unaligned: called, not working yet\n");
+#else
+       struct ia64_psr *ipsr = ia64_psr(regs);
+       mm_segment_t old_fs = get_fs();
+       unsigned long bundle[2];
+       unsigned long opcode;
+       struct siginfo si;
+       const struct exception_table_entry *eh = NULL;
+       union {
+               unsigned long l;
+               load_store_t insn;
+       } u;
+       int ret = -1;
+
+       if (ia64_psr(regs)->be) {
+               /* we don't support big-endian accesses */
+               die_if_kernel("big-endian unaligned accesses are not 
supported", regs, 0);
+               goto force_sigbus;
+       }
+
+       /*
+        * Treat kernel accesses for which there is an exception handler entry 
the same as
+        * user-level unaligned accesses.  Otherwise, a clever program could 
trick this
+        * handler into reading an arbitrary kernel addresses...
+        */
+       if (!user_mode(regs))
+               eh = search_exception_tables(regs->cr_iip + ia64_psr(regs)->ri);
+       if (user_mode(regs) || eh) {
+               if ((current->thread.flags & IA64_THREAD_UAC_SIGBUS) != 0)
+                       goto force_sigbus;
+
+               if (!(current->thread.flags & IA64_THREAD_UAC_NOPRINT)
+                   && within_logging_rate_limit())
+               {
+                       char buf[200];  /* comm[] is at most 16 bytes... */
+                       size_t len;
+
+                       len = sprintf(buf, "%s(%d): unaligned access to 
0x%016lx, "
+                                     "ip=0x%016lx\n\r", current->comm, 
current->pid,
+                                     ifa, regs->cr_iip + ipsr->ri);
+                       /*
+                        * Don't call tty_write_message() if we're in the 
kernel; we might
+                        * be holding locks...
+                        */
+                       if (user_mode(regs))
+                               tty_write_message(current->signal->tty, buf);
+                       buf[len-1] = '\0';      /* drop '\r' */
+                       printk(KERN_WARNING "%s", buf); /* watch for command 
names containing %s */
+               }
+       } else {
+               if (within_logging_rate_limit())
+                       printk(KERN_WARNING "kernel unaligned access to 
0x%016lx, ip=0x%016lx\n",
+                              ifa, regs->cr_iip + ipsr->ri);
+               set_fs(KERNEL_DS);
+       }
+
+       DPRINT("iip=%lx ifa=%lx isr=%lx (ei=%d, sp=%d)\n",
+              regs->cr_iip, ifa, regs->cr_ipsr, ipsr->ri, ipsr->it);
+
+       if (__copy_from_user(bundle, (void __user *) regs->cr_iip, 16))
+               goto failure;
+
+       /*
+        * extract the instruction from the bundle given the slot number
+        */
+       switch (ipsr->ri) {
+             case 0: u.l = (bundle[0] >>  5); break;
+             case 1: u.l = (bundle[0] >> 46) | (bundle[1] << 18); break;
+             case 2: u.l = (bundle[1] >> 23); break;
+       }
+       opcode = (u.l >> IA64_OPCODE_SHIFT) & IA64_OPCODE_MASK;
+
+       DPRINT("opcode=%lx ld.qp=%d ld.r1=%d ld.imm=%d ld.r3=%d ld.x=%d 
ld.hint=%d "
+              "ld.x6=0x%x ld.m=%d ld.op=%d\n", opcode, u.insn.qp, u.insn.r1, 
u.insn.imm,
+              u.insn.r3, u.insn.x, u.insn.hint, u.insn.x6_sz, u.insn.m, 
u.insn.op);
+
+       /*
+        * IMPORTANT:
+        * Notice that the switch statement DOES not cover all possible 
instructions
+        * that DO generate unaligned references. This is made on purpose 
because for some
+        * instructions it DOES NOT make sense to try and emulate the access. 
Sometimes it
+        * is WRONG to try and emulate. Here is a list of instruction we don't 
emulate i.e.,
+        * the program will get a signal and die:
+        *
+        *      load/store:
+        *              - ldX.spill
+        *              - stX.spill
+        *      Reason: RNATs are based on addresses
+        *
+        *      synchronization:
+        *              - cmpxchg
+        *              - fetchadd
+        *              - xchg
+        *      Reason: ATOMIC operations cannot be emulated properly using 
multiple
+        *              instructions.
+        *
+        *      speculative loads:
+        *              - ldX.sZ
+        *      Reason: side effects, code must be ready to deal with failure 
so simpler
+        *              to let the load fail.
+        * 
---------------------------------------------------------------------------------
+        * XXX fixme
+        *
+        * I would like to get rid of this switch case and do something
+        * more elegant.
+        */
+       switch (opcode) {
+             case LDS_OP:
+             case LDSA_OP:
+             case LDS_IMM_OP:
+             case LDSA_IMM_OP:
+             case LDFS_OP:
+             case LDFSA_OP:
+             case LDFS_IMM_OP:
+               /*
+                * The instruction will be retried with deferred exceptions 
turned on, and
+                * we should get Nat bit installed
+                *
+                * IMPORTANT: When PSR_ED is set, the register & immediate 
update forms
+                * are actually executed even though the operation failed. So 
we don't
+                * need to take care of this.
+                */
+               DPRINT("forcing PSR_ED\n");
+               regs->cr_ipsr |= IA64_PSR_ED;
+               goto done;
+
+             case LD_OP:
+             case LDA_OP:
+             case LDBIAS_OP:
+             case LDACQ_OP:
+             case LDCCLR_OP:
+             case LDCNC_OP:
+             case LDCCLRACQ_OP:
+             case LD_IMM_OP:
+             case LDA_IMM_OP:
+             case LDBIAS_IMM_OP:
+             case LDACQ_IMM_OP:
+             case LDCCLR_IMM_OP:
+             case LDCNC_IMM_OP:
+             case LDCCLRACQ_IMM_OP:
+               ret = emulate_load_int(ifa, u.insn, regs);
+               break;
+
+             case ST_OP:
+             case STREL_OP:
+             case ST_IMM_OP:
+             case STREL_IMM_OP:
+               ret = emulate_store_int(ifa, u.insn, regs);
+               break;
+
+             case LDF_OP:
+             case LDFA_OP:
+             case LDFCCLR_OP:
+             case LDFCNC_OP:
+             case LDF_IMM_OP:
+             case LDFA_IMM_OP:
+             case LDFCCLR_IMM_OP:
+             case LDFCNC_IMM_OP:
+               if (u.insn.x)
+                       ret = emulate_load_floatpair(ifa, u.insn, regs);
+               else
+                       ret = emulate_load_float(ifa, u.insn, regs);
+               break;
+
+             case STF_OP:
+             case STF_IMM_OP:
+               ret = emulate_store_float(ifa, u.insn, regs);
+               break;
+
+             default:
+               goto failure;
+       }
+       DPRINT("ret=%d\n", ret);
+       if (ret)
+               goto failure;
+
+       if (ipsr->ri == 2)
+               /*
+                * given today's architecture this case is not likely to happen 
because a
+                * memory access instruction (M) can never be in the last slot 
of a
+                * bundle. But let's keep it for now.
+                */
+               regs->cr_iip += 16;
+       ipsr->ri = (ipsr->ri + 1) & 0x3;
+
+       DPRINT("ipsr->ri=%d iip=%lx\n", ipsr->ri, regs->cr_iip);
+  done:
+       set_fs(old_fs);         /* restore original address limit */
+       return;
+
+  failure:
+       /* something went wrong... */
+       if (!user_mode(regs)) {
+               if (eh) {
+                       ia64_handle_exception(regs, eh);
+                       goto done;
+               }
+               die_if_kernel("error during unaligned kernel access\n", regs, 
ret);
+               /* NOT_REACHED */
+       }
+  force_sigbus:
+       si.si_signo = SIGBUS;
+       si.si_errno = 0;
+       si.si_code = BUS_ADRALN;
+       si.si_addr = (void __user *) ifa;
+       si.si_flags = 0;
+       si.si_isr = 0;
+       si.si_imm = 0;
+       force_sig_info(SIGBUS, &si, current);
+       goto done;
+#endif
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/cmdline.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/cmdline.c     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,120 @@
+/*
+ * linux/lib/cmdline.c
+ * Helper functions generally used for parsing kernel command line
+ * and module options.
+ *
+ * Code and copyrights come from init/main.c and arch/i386/kernel/setup.c.
+ *
+ * This source code is licensed under the GNU General Public License,
+ * Version 2.  See the file COPYING for more details.
+ *
+ * GNU Indent formatting options for this file: -kr -i8 -npsl -pcs
+ *
+ */
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/string.h>
+
+
+/**
+ *     get_option - Parse integer from an option string
+ *     @str: option string
+ *     @pint: (output) integer value parsed from @str
+ *
+ *     Read an int from an option string; if available accept a subsequent
+ *     comma as well.
+ *
+ *     Return values:
+ *     0 : no int in string
+ *     1 : int found, no subsequent comma
+ *     2 : int found including a subsequent comma
+ */
+
+int get_option (char **str, int *pint)
+{
+       char *cur = *str;
+
+       if (!cur || !(*cur))
+               return 0;
+       *pint = simple_strtol (cur, str, 0);
+       if (cur == *str)
+               return 0;
+       if (**str == ',') {
+               (*str)++;
+               return 2;
+       }
+
+       return 1;
+}
+
+/**
+ *     get_options - Parse a string into a list of integers
+ *     @str: String to be parsed
+ *     @nints: size of integer array
+ *     @ints: integer array
+ *
+ *     This function parses a string containing a comma-separated
+ *     list of integers.  The parse halts when the array is
+ *     full, or when no more numbers can be retrieved from the
+ *     string.
+ *
+ *     Return value is the character in the string which caused
+ *     the parse to end (typically a null terminator, if @str is
+ *     completely parseable).
+ */
+ 
+char *get_options(const char *str, int nints, int *ints)
+{
+       int res, i = 1;
+
+       while (i < nints) {
+               res = get_option ((char **)&str, ints + i);
+               if (res == 0)
+                       break;
+               i++;
+               if (res == 1)
+                       break;
+       }
+       ints[0] = i - 1;
+       return (char *)str;
+}
+
+/**
+ *     memparse - parse a string with mem suffixes into a number
+ *     @ptr: Where parse begins
+ *     @retptr: (output) Pointer to next char after parse completes
+ *
+ *     Parses a string into a number.  The number stored at @ptr is
+ *     potentially suffixed with %K (for kilobytes, or 1024 bytes),
+ *     %M (for megabytes, or 1048576 bytes), or %G (for gigabytes, or
+ *     1073741824).  If the number is suffixed with K, M, or G, then
+ *     the return value is the number multiplied by one kilobyte, one
+ *     megabyte, or one gigabyte, respectively.
+ */
+
+unsigned long long memparse (char *ptr, char **retptr)
+{
+       unsigned long long ret = simple_strtoull (ptr, retptr, 0);
+
+       switch (**retptr) {
+       case 'G':
+       case 'g':
+               ret <<= 10;
+       case 'M':
+       case 'm':
+               ret <<= 10;
+       case 'K':
+       case 'k':
+               ret <<= 10;
+               (*retptr)++;
+       default:
+               break;
+       }
+       return ret;
+}
+
+
+EXPORT_SYMBOL(memparse);
+EXPORT_SYMBOL(get_option);
+EXPORT_SYMBOL(get_options);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/efi_stub.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/efi_stub.S    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,86 @@
+/*
+ * EFI call stub.
+ *
+ * Copyright (C) 1999-2001 Hewlett-Packard Co
+ *     David Mosberger <davidm@xxxxxxxxxx>
+ *
+ * This stub allows us to make EFI calls in physical mode with interrupts
+ * turned off.  We need this because we can't call SetVirtualMap() until
+ * the kernel has booted far enough to allow allocation of struct vma_struct
+ * entries (which we would need to map stuff with memory attributes other
+ * than uncached or writeback...).  Since the GetTime() service gets called
+ * earlier than that, we need to be able to make physical mode EFI calls from
+ * the kernel.
+ */
+
+/*
+ * PSR settings as per SAL spec (Chapter 8 in the "IA-64 System
+ * Abstraction Layer Specification", revision 2.6e).  Note that
+ * psr.dfl and psr.dfh MUST be cleared, despite what this manual says.
+ * Otherwise, SAL dies whenever it's trying to do an IA-32 BIOS call
+ * (the br.ia instruction fails unless psr.dfl and psr.dfh are
+ * cleared).  Fortunately, SAL promises not to touch the floating
+ * point regs, so at least we don't have to save f2-f127.
+ */
+#define PSR_BITS_TO_CLEAR                                              \
+       (IA64_PSR_I | IA64_PSR_IT | IA64_PSR_DT | IA64_PSR_RT |         \
+        IA64_PSR_DD | IA64_PSR_SS | IA64_PSR_RI | IA64_PSR_ED |        \
+        IA64_PSR_DFL | IA64_PSR_DFH)
+
+#define PSR_BITS_TO_SET                                                        
\
+       (IA64_PSR_BN)
+
+#include <asm/processor.h>
+#include <asm/asmmacro.h>
+
+/*
+ * Inputs:
+ *     in0 = address of function descriptor of EFI routine to call
+ *     in1..in7 = arguments to routine
+ *
+ * Outputs:
+ *     r8 = EFI_STATUS returned by called function
+ */
+
+GLOBAL_ENTRY(efi_call_phys)
+       .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(8)
+       alloc loc1=ar.pfs,8,7,7,0
+       ld8 r2=[in0],8                  // load EFI function's entry point
+       mov loc0=rp
+       .body
+       ;;
+       mov loc2=gp                     // save global pointer
+       mov loc4=ar.rsc                 // save RSE configuration
+       mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       ;;
+       ld8 gp=[in0]                    // load EFI function's global pointer
+       movl r16=PSR_BITS_TO_CLEAR
+       mov loc3=psr                    // save processor status word
+       movl r17=PSR_BITS_TO_SET
+       ;;
+       or loc3=loc3,r17
+       mov b6=r2
+       ;;
+       andcm r16=loc3,r16              // get psr with IT, DT, and RT bits 
cleared
+       br.call.sptk.many rp=ia64_switch_mode_phys
+.ret0: mov out4=in5
+       mov out0=in1
+       mov out1=in2
+       mov out2=in3
+       mov out3=in4
+       mov out5=in6
+       mov out6=in7
+       mov loc5=r19
+       mov loc6=r20
+       br.call.sptk.many rp=b6         // call the EFI function
+.ret1: mov ar.rsc=0                    // put RSE in enforced lazy, LE mode
+       mov r16=loc3
+       mov r19=loc5
+       mov r20=loc6
+       br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode
+.ret2: mov ar.rsc=loc4                 // restore RSE configuration
+       mov ar.pfs=loc1
+       mov rp=loc0
+       mov gp=loc2
+       br.ret.sptk.many rp
+END(efi_call_phys)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/extable.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/extable.c     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,93 @@
+/*
+ * Kernel exception handling table support.  Derived from 
arch/alpha/mm/extable.c.
+ *
+ * Copyright (C) 1998, 1999, 2001-2002, 2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <asm/uaccess.h>
+#include <asm/module.h>
+
+static inline int
+compare_entries (struct exception_table_entry *l, struct exception_table_entry 
*r)
+{
+       u64 lip = (u64) &l->addr + l->addr;
+       u64 rip = (u64) &r->addr + r->addr;
+
+       if (lip < rip)
+               return -1;
+       if (lip == rip)
+               return 0;
+       else
+               return 1;
+}
+
+static inline void
+swap_entries (struct exception_table_entry *l, struct exception_table_entry *r)
+{
+       u64 delta = (u64) r - (u64) l;
+       struct exception_table_entry tmp;
+
+       tmp = *l;
+       l->addr = r->addr + delta;
+       l->cont = r->cont + delta;
+       r->addr = tmp.addr - delta;
+       r->cont = tmp.cont - delta;
+}
+
+/*
+ * Sort the exception table.  It's usually already sorted, but there may be 
unordered
+ * entries due to multiple text sections (such as the .init text section).  
Note that the
+ * exception-table-entries contain location-relative addresses, which requires 
a bit of
+ * care during sorting to avoid overflows in the offset members (e.g., it 
would not be
+ * safe to make a temporary copy of an exception-table entry on the stack, 
because the
+ * stack may be more than 2GB away from the exception-table).
+ */
+void
+sort_extable (struct exception_table_entry *start, struct 
exception_table_entry *finish)
+{
+       struct exception_table_entry *p, *q;
+
+       /* insertion sort */
+       for (p = start + 1; p < finish; ++p)
+               /* start .. p-1 is sorted; push p down to it's proper place */
+               for (q = p; q > start && compare_entries(&q[0], &q[-1]) < 0; 
--q)
+                       swap_entries(&q[0], &q[-1]);
+}
+
+const struct exception_table_entry *
+search_extable (const struct exception_table_entry *first,
+               const struct exception_table_entry *last,
+               unsigned long ip)
+{
+       const struct exception_table_entry *mid;
+       unsigned long mid_ip;
+       long diff;
+
+        while (first <= last) {
+               mid = &first[(last - first)/2];
+               mid_ip = (u64) &mid->addr + mid->addr;
+               diff = mid_ip - ip;
+                if (diff == 0)
+                        return mid;
+                else if (diff < 0)
+                        first = mid + 1;
+                else
+                        last = mid - 1;
+        }
+        return NULL;
+}
+
+void
+ia64_handle_exception (struct pt_regs *regs, const struct 
exception_table_entry *e)
+{
+       long fix = (u64) &e->cont + e->cont;
+
+       regs->r8 = -EFAULT;
+       if (fix & 4)
+               regs->r9 = 0;
+       regs->cr_iip = fix & ~0xf;
+       ia64_psr(regs)->ri = fix & 0x3;         /* set continuation slot number 
*/
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/hpsim.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/hpsim.S       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,10 @@
+#include <asm/asmmacro.h>
+
+/*
+ * Simulator system call.
+ */
+GLOBAL_ENTRY(ia64_ssc)
+       mov r15=r36
+       break 0x80001
+       br.ret.sptk.many rp
+END(ia64_ssc)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/ia64_ksyms.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/ia64_ksyms.c  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,127 @@
+/*
+ * Architecture-specific kernel symbols
+ *
+ * Don't put any exports here unless it's defined in an assembler file.
+ * All other exports should be put directly after the definition.
+ */
+
+#include <linux/config.h>
+#include <linux/module.h>
+
+#include <linux/string.h>
+EXPORT_SYMBOL(memset);
+EXPORT_SYMBOL(memchr);
+EXPORT_SYMBOL(memcmp);
+EXPORT_SYMBOL(memcpy);
+EXPORT_SYMBOL(memmove);
+EXPORT_SYMBOL(memscan);
+EXPORT_SYMBOL(strcat);
+EXPORT_SYMBOL(strchr);
+EXPORT_SYMBOL(strcmp);
+EXPORT_SYMBOL(strcpy);
+EXPORT_SYMBOL(strlen);
+EXPORT_SYMBOL(strncat);
+EXPORT_SYMBOL(strncmp);
+EXPORT_SYMBOL(strncpy);
+EXPORT_SYMBOL(strnlen);
+EXPORT_SYMBOL(strrchr);
+EXPORT_SYMBOL(strstr);
+EXPORT_SYMBOL(strpbrk);
+
+#include <asm/checksum.h>
+EXPORT_SYMBOL(ip_fast_csum);           /* hand-coded assembly */
+
+#include <asm/semaphore.h>
+EXPORT_SYMBOL(__down);
+EXPORT_SYMBOL(__down_interruptible);
+EXPORT_SYMBOL(__down_trylock);
+EXPORT_SYMBOL(__up);
+
+#include <asm/page.h>
+EXPORT_SYMBOL(clear_page);
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+#include <linux/bootmem.h>
+EXPORT_SYMBOL(max_low_pfn);    /* defined by bootmem.c, but not exported by 
generic code */
+#endif
+
+#include <asm/processor.h>
+EXPORT_SYMBOL(per_cpu__cpu_info);
+#ifdef CONFIG_SMP
+EXPORT_SYMBOL(per_cpu__local_per_cpu_offset);
+#endif
+
+#include <asm/uaccess.h>
+EXPORT_SYMBOL(__copy_user);
+EXPORT_SYMBOL(__do_clear_user);
+EXPORT_SYMBOL(__strlen_user);
+EXPORT_SYMBOL(__strncpy_from_user);
+EXPORT_SYMBOL(__strnlen_user);
+
+#include <asm/unistd.h>
+EXPORT_SYMBOL(__ia64_syscall);
+
+/* from arch/ia64/lib */
+extern void __divsi3(void);
+extern void __udivsi3(void);
+extern void __modsi3(void);
+extern void __umodsi3(void);
+extern void __divdi3(void);
+extern void __udivdi3(void);
+extern void __moddi3(void);
+extern void __umoddi3(void);
+
+EXPORT_SYMBOL(__divsi3);
+EXPORT_SYMBOL(__udivsi3);
+EXPORT_SYMBOL(__modsi3);
+EXPORT_SYMBOL(__umodsi3);
+EXPORT_SYMBOL(__divdi3);
+EXPORT_SYMBOL(__udivdi3);
+EXPORT_SYMBOL(__moddi3);
+EXPORT_SYMBOL(__umoddi3);
+
+#if defined(CONFIG_MD_RAID5) || defined(CONFIG_MD_RAID5_MODULE)
+extern void xor_ia64_2(void);
+extern void xor_ia64_3(void);
+extern void xor_ia64_4(void);
+extern void xor_ia64_5(void);
+
+EXPORT_SYMBOL(xor_ia64_2);
+EXPORT_SYMBOL(xor_ia64_3);
+EXPORT_SYMBOL(xor_ia64_4);
+EXPORT_SYMBOL(xor_ia64_5);
+#endif
+
+#include <asm/pal.h>
+EXPORT_SYMBOL(ia64_pal_call_phys_stacked);
+EXPORT_SYMBOL(ia64_pal_call_phys_static);
+EXPORT_SYMBOL(ia64_pal_call_stacked);
+EXPORT_SYMBOL(ia64_pal_call_static);
+EXPORT_SYMBOL(ia64_load_scratch_fpregs);
+EXPORT_SYMBOL(ia64_save_scratch_fpregs);
+
+#include <asm/unwind.h>
+EXPORT_SYMBOL(unw_init_running);
+
+#ifdef ASM_SUPPORTED
+# ifdef CONFIG_SMP
+#  if __GNUC__ < 3 || (__GNUC__ == 3 && __GNUC_MINOR__ < 3)
+/*
+ * This is not a normal routine and we don't want a function descriptor for 
it, so we use
+ * a fake declaration here.
+ */
+extern char ia64_spinlock_contention_pre3_4;
+EXPORT_SYMBOL(ia64_spinlock_contention_pre3_4);
+#  else
+/*
+ * This is not a normal routine and we don't want a function descriptor for 
it, so we use
+ * a fake declaration here.
+ */
+extern char ia64_spinlock_contention;
+EXPORT_SYMBOL(ia64_spinlock_contention);
+#  endif
+# endif
+#endif
+
+extern char ia64_ivt[];
+EXPORT_SYMBOL(ia64_ivt);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/irq_lsapic.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/irq_lsapic.c  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,37 @@
+/*
+ * LSAPIC Interrupt Controller
+ *
+ * This takes care of interrupts that are generated by the CPU's
+ * internal Streamlined Advanced Programmable Interrupt Controller
+ * (LSAPIC), such as the ITC and IPI interrupts.
+    *
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 2000 Hewlett-Packard Co
+ * Copyright (C) 2000 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/sched.h>
+#include <linux/irq.h>
+
+static unsigned int
+lsapic_noop_startup (unsigned int irq)
+{
+       return 0;
+}
+
+static void
+lsapic_noop (unsigned int irq)
+{
+       /* nuthing to do... */
+}
+
+struct hw_interrupt_type irq_type_ia64_lsapic = {
+       .typename =     "LSAPIC",
+       .startup =      lsapic_noop_startup,
+       .shutdown =     lsapic_noop,
+       .enable =       lsapic_noop,
+       .disable =      lsapic_noop,
+       .ack =          lsapic_noop,
+       .end =          lsapic_noop
+};
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/Makefile
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/Makefile  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,44 @@
+#
+# Makefile for ia64-specific library routines..
+#
+
+include $(BASEDIR)/Rules.mk
+
+OBJS := __divsi3.o __udivsi3.o __modsi3.o __umodsi3.o                  \
+       __divdi3.o __udivdi3.o __moddi3.o __umoddi3.o                   \
+       bitop.o checksum.o clear_page.o csum_partial_copy.o copy_page.o \
+       clear_user.o strncpy_from_user.o strlen_user.o strnlen_user.o   \
+       flush.o ip_fast_csum.o do_csum.o copy_user.o                    \
+       memset.o strlen.o memcpy.o 
+
+default: $(OBJS)
+       $(LD) -r -o ia64lib.o $(OBJS)
+
+AFLAGS += -I$(BASEDIR)/include -D__ASSEMBLY__
+
+__divdi3.o: idiv64.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -o $@ $<
+
+__udivdi3.o: idiv64.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DUNSIGNED -c -o $@ $<
+
+__moddi3.o: idiv64.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DMODULO -c -o $@ $<
+
+__umoddi3.o: idiv64.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DMODULO -DUNSIGNED -c -o $@ $<
+
+__divsi3.o: idiv32.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -o $@ $<
+
+__udivsi3.o: idiv32.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DUNSIGNED -c -o $@ $<
+
+__modsi3.o: idiv32.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DMODULO -c -o $@ $<
+
+__umodsi3.o: idiv32.S
+       $(CC) $(AFLAGS) $(AFLAGS_KERNEL) -c -DMODULO -DUNSIGNED -c -o $@ $<
+
+clean:
+       rm -f *.o *~
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/bitop.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/bitop.c   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,88 @@
+#include <linux/compiler.h>
+#include <linux/types.h>
+#include <asm/intrinsics.h>
+#include <linux/module.h>
+#include <linux/bitops.h>
+
+/*
+ * Find next zero bit in a bitmap reasonably efficiently..
+ */
+
+int __find_next_zero_bit (const void *addr, unsigned long size, unsigned long 
offset)
+{
+       unsigned long *p = ((unsigned long *) addr) + (offset >> 6);
+       unsigned long result = offset & ~63UL;
+       unsigned long tmp;
+
+       if (offset >= size)
+               return size;
+       size -= result;
+       offset &= 63UL;
+       if (offset) {
+               tmp = *(p++);
+               tmp |= ~0UL >> (64-offset);
+               if (size < 64)
+                       goto found_first;
+               if (~tmp)
+                       goto found_middle;
+               size -= 64;
+               result += 64;
+       }
+       while (size & ~63UL) {
+               if (~(tmp = *(p++)))
+                       goto found_middle;
+               result += 64;
+               size -= 64;
+       }
+       if (!size)
+               return result;
+       tmp = *p;
+found_first:
+       tmp |= ~0UL << size;
+       if (tmp == ~0UL)                /* any bits zero? */
+               return result + size;   /* nope */
+found_middle:
+       return result + ffz(tmp);
+}
+EXPORT_SYMBOL(__find_next_zero_bit);
+
+/*
+ * Find next bit in a bitmap reasonably efficiently..
+ */
+int __find_next_bit(const void *addr, unsigned long size, unsigned long offset)
+{
+       unsigned long *p = ((unsigned long *) addr) + (offset >> 6);
+       unsigned long result = offset & ~63UL;
+       unsigned long tmp;
+
+       if (offset >= size)
+               return size;
+       size -= result;
+       offset &= 63UL;
+       if (offset) {
+               tmp = *(p++);
+               tmp &= ~0UL << offset;
+               if (size < 64)
+                       goto found_first;
+               if (tmp)
+                       goto found_middle;
+               size -= 64;
+               result += 64;
+       }
+       while (size & ~63UL) {
+               if ((tmp = *(p++)))
+                       goto found_middle;
+               result += 64;
+               size -= 64;
+       }
+       if (!size)
+               return result;
+       tmp = *p;
+  found_first:
+       tmp &= ~0UL >> (64-size);
+       if (tmp == 0UL)         /* Are any bits set? */
+               return result + size; /* Nope. */
+  found_middle:
+       return result + __ffs(tmp);
+}
+EXPORT_SYMBOL(__find_next_bit);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/carta_random.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/carta_random.S    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,54 @@
+/*
+ * Fast, simple, yet decent quality random number generator based on
+ * a paper by David G. Carta ("Two Fast Implementations of the
+ * `Minimal Standard' Random Number Generator," Communications of the
+ * ACM, January, 1990).
+ *
+ * Copyright (C) 2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm/asmmacro.h>
+
+#define a      r2
+#define m      r3
+#define lo     r8
+#define hi     r9
+#define t0     r16
+#define t1     r17
+#define        seed    r32
+
+GLOBAL_ENTRY(carta_random32)
+       movl    a = (16807 << 16) | 16807
+       ;;
+       pmpyshr2.u t0 = a, seed, 0
+       pmpyshr2.u t1 = a, seed, 16
+       ;;
+       unpack2.l t0 = t1, t0
+       dep     m = -1, r0, 0, 31
+       ;;
+       zxt4    lo = t0
+       shr.u   hi = t0, 32
+       ;;
+       dep     t0 = 0, hi, 15, 49      // t0 = (hi & 0x7fff)
+       ;;
+       shl     t0 = t0, 16             // t0 = (hi & 0x7fff) << 16
+       shr     t1 = hi, 15             // t1 = (hi >> 15)
+       ;;
+       add     lo = lo, t0
+       ;;
+       cmp.gtu p6, p0 = lo, m
+       ;;
+(p6)   and     lo = lo, m
+       ;;
+(p6)   add     lo = 1, lo
+       ;;
+       add     lo = lo, t1
+       ;;
+       cmp.gtu p6, p0 = lo, m
+       ;;
+(p6)   and     lo = lo, m
+       ;;
+(p6)   add     lo = 1, lo
+       br.ret.sptk.many rp
+END(carta_random32)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/checksum.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/checksum.c        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,102 @@
+/*
+ * Network checksum routines
+ *
+ * Copyright (C) 1999, 2003 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * Most of the code coming from arch/alpha/lib/checksum.c
+ *
+ * This file contains network checksum routines that are better done
+ * in an architecture-specific manner due to speed..
+ */
+
+#include <linux/module.h>
+#include <linux/string.h>
+
+#include <asm/byteorder.h>
+
+static inline unsigned short
+from64to16 (unsigned long x)
+{
+       /* add up 32-bit words for 33 bits */
+       x = (x & 0xffffffff) + (x >> 32);
+       /* add up 16-bit and 17-bit words for 17+c bits */
+       x = (x & 0xffff) + (x >> 16);
+       /* add up 16-bit and 2-bit for 16+c bit */
+       x = (x & 0xffff) + (x >> 16);
+       /* add up carry.. */
+       x = (x & 0xffff) + (x >> 16);
+       return x;
+}
+
+/*
+ * computes the checksum of the TCP/UDP pseudo-header
+ * returns a 16-bit checksum, already complemented.
+ */
+unsigned short int
+csum_tcpudp_magic (unsigned long saddr, unsigned long daddr, unsigned short 
len,
+                  unsigned short proto, unsigned int sum)
+{
+       return ~from64to16(saddr + daddr + sum + ((unsigned long) ntohs(len) << 
16) +
+                          ((unsigned long) proto << 8));
+}
+
+EXPORT_SYMBOL(csum_tcpudp_magic);
+
+unsigned int
+csum_tcpudp_nofold (unsigned long saddr, unsigned long daddr, unsigned short 
len,
+                   unsigned short proto, unsigned int sum)
+{
+       unsigned long result;
+
+       result = (saddr + daddr + sum +
+                 ((unsigned long) ntohs(len) << 16) +
+                 ((unsigned long) proto << 8));
+
+       /* Fold down to 32-bits so we don't lose in the typedef-less network 
stack.  */
+       /* 64 to 33 */
+       result = (result & 0xffffffff) + (result >> 32);
+       /* 33 to 32 */
+       result = (result & 0xffffffff) + (result >> 32);
+       return result;
+}
+
+extern unsigned long do_csum (const unsigned char *, long);
+
+/*
+ * computes the checksum of a memory block at buff, length len,
+ * and adds in "sum" (32-bit)
+ *
+ * returns a 32-bit number suitable for feeding into itself
+ * or csum_tcpudp_magic
+ *
+ * this function must be called with even lengths, except
+ * for the last fragment, which may be odd
+ *
+ * it's best to have buff aligned on a 32-bit boundary
+ */
+unsigned int
+csum_partial (const unsigned char * buff, int len, unsigned int sum)
+{
+       unsigned long result = do_csum(buff, len);
+
+       /* add in old sum, and carry.. */
+       result += sum;
+       /* 32+c bits -> 32 bits */
+       result = (result & 0xffffffff) + (result >> 32);
+       return result;
+}
+
+EXPORT_SYMBOL(csum_partial);
+
+/*
+ * this routine is used for miscellaneous IP-like checksums, mainly
+ * in icmp.c
+ */
+unsigned short
+ip_compute_csum (unsigned char * buff, int len)
+{
+       return ~do_csum(buff,len);
+}
+
+EXPORT_SYMBOL(ip_compute_csum);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/clear_page.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/clear_page.S      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,77 @@
+/*
+ * Copyright (C) 1999-2002 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 2002 Ken Chen <kenneth.w.chen@xxxxxxxxx>
+ *
+ * 1/06/01 davidm      Tuned for Itanium.
+ * 2/12/02 kchen       Tuned for both Itanium and McKinley
+ * 3/08/02 davidm      Some more tweaking
+ */
+#include <linux/config.h>
+
+#include <asm/asmmacro.h>
+#include <asm/page.h>
+
+#ifdef CONFIG_ITANIUM
+# define L3_LINE_SIZE  64      // Itanium L3 line size
+# define PREFETCH_LINES        9       // magic number
+#else
+# define L3_LINE_SIZE  128     // McKinley L3 line size
+# define PREFETCH_LINES        12      // magic number
+#endif
+
+#define saved_lc       r2
+#define dst_fetch      r3
+#define dst1           r8
+#define dst2           r9
+#define dst3           r10
+#define dst4           r11
+
+#define dst_last       r31
+
+GLOBAL_ENTRY(clear_page)
+       .prologue
+       .regstk 1,0,0,0
+       mov r16 = PAGE_SIZE/L3_LINE_SIZE-1      // main loop count, 
-1=repeat/until
+       .save ar.lc, saved_lc
+       mov saved_lc = ar.lc
+
+       .body
+       mov ar.lc = (PREFETCH_LINES - 1)
+       mov dst_fetch = in0
+       adds dst1 = 16, in0
+       adds dst2 = 32, in0
+       ;;
+.fetch:        stf.spill.nta [dst_fetch] = f0, L3_LINE_SIZE
+       adds dst3 = 48, in0             // executing this multiple times is 
harmless
+       br.cloop.sptk.few .fetch
+       ;;
+       addl dst_last = (PAGE_SIZE - PREFETCH_LINES*L3_LINE_SIZE), dst_fetch
+       mov ar.lc = r16                 // one L3 line per iteration
+       adds dst4 = 64, in0
+       ;;
+#ifdef CONFIG_ITANIUM
+       // Optimized for Itanium
+1:     stf.spill.nta [dst1] = f0, 64
+       stf.spill.nta [dst2] = f0, 64
+       cmp.lt p8,p0=dst_fetch, dst_last
+       ;;
+#else
+       // Optimized for McKinley
+1:     stf.spill.nta [dst1] = f0, 64
+       stf.spill.nta [dst2] = f0, 64
+       stf.spill.nta [dst3] = f0, 64
+       stf.spill.nta [dst4] = f0, 128
+       cmp.lt p8,p0=dst_fetch, dst_last
+       ;;
+       stf.spill.nta [dst1] = f0, 64
+       stf.spill.nta [dst2] = f0, 64
+#endif
+       stf.spill.nta [dst3] = f0, 64
+(p8)   stf.spill.nta [dst_fetch] = f0, L3_LINE_SIZE
+       br.cloop.sptk.few 1b
+       ;;
+       mov ar.lc = saved_lc            // restore lc
+       br.ret.sptk.many rp
+END(clear_page)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/clear_user.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/clear_user.S      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,209 @@
+/*
+ * This routine clears to zero a linear memory buffer in user space.
+ *
+ * Inputs:
+ *     in0:    address of buffer
+ *     in1:    length of buffer in bytes
+ * Outputs:
+ *     r8:     number of bytes that didn't get cleared due to a fault
+ *
+ * Copyright (C) 1998, 1999, 2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ */
+
+#include <asm/asmmacro.h>
+
+//
+// arguments
+//
+#define buf            r32
+#define len            r33
+
+//
+// local registers
+//
+#define cnt            r16
+#define buf2           r17
+#define saved_lc       r18
+#define saved_pfs      r19
+#define tmp            r20
+#define len2           r21
+#define len3           r22
+
+//
+// Theory of operations:
+//     - we check whether or not the buffer is small, i.e., less than 17
+//       in which case we do the byte by byte loop.
+//
+//     - Otherwise we go progressively from 1 byte store to 8byte store in
+//       the head part, the body is a 16byte store loop and we finish we the
+//       tail for the last 15 bytes.
+//       The good point about this breakdown is that the long buffer handling
+//       contains only 2 branches.
+//
+//     The reason for not using shifting & masking for both the head and the
+//     tail is to stay semantically correct. This routine is not supposed
+//     to write bytes outside of the buffer. While most of the time this would
+//     be ok, we can't tolerate a mistake. A classical example is the case
+//     of multithreaded code were to the extra bytes touched is actually owned
+//     by another thread which runs concurrently to ours. Another, less likely,
+//     example is with device drivers where reading an I/O mapped location may
+//     have side effects (same thing for writing).
+//
+
+GLOBAL_ENTRY(__do_clear_user)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc   saved_pfs=ar.pfs,2,0,0,0
+       cmp.eq p6,p0=r0,len             // check for zero length
+       .save ar.lc, saved_lc
+       mov saved_lc=ar.lc              // preserve ar.lc (slow)
+       .body
+       ;;                              // avoid WAW on CFM
+       adds tmp=-1,len                 // br.ctop is repeat/until
+       mov ret0=len                    // return value is length at this point
+(p6)   br.ret.spnt.many rp
+       ;;
+       cmp.lt p6,p0=16,len             // if len > 16 then long memset
+       mov ar.lc=tmp                   // initialize lc for small count
+(p6)   br.cond.dptk .long_do_clear
+       ;;                              // WAR on ar.lc
+       //
+       // worst case 16 iterations, avg 8 iterations
+       //
+       // We could have played with the predicates to use the extra
+       // M slot for 2 stores/iteration but the cost the initialization
+       // the various counters compared to how long the loop is supposed
+       // to last on average does not make this solution viable.
+       //
+1:
+       EX( .Lexit1, st1 [buf]=r0,1 )
+       adds len=-1,len                 // countdown length using len
+       br.cloop.dptk 1b
+       ;;                              // avoid RAW on ar.lc
+       //
+       // .Lexit4: comes from byte by byte loop
+       //          len contains bytes left
+.Lexit1:
+       mov ret0=len                    // faster than using ar.lc
+       mov ar.lc=saved_lc
+       br.ret.sptk.many rp             // end of short clear_user
+
+
+       //
+       // At this point we know we have more than 16 bytes to copy
+       // so we focus on alignment (no branches required)
+       //
+       // The use of len/len2 for countdown of the number of bytes left
+       // instead of ret0 is due to the fact that the exception code
+       // changes the values of r8.
+       //
+.long_do_clear:
+       tbit.nz p6,p0=buf,0             // odd alignment (for long_do_clear)
+       ;;
+       EX( .Lexit3, (p6) st1 [buf]=r0,1 )      // 1-byte aligned
+(p6)   adds len=-1,len;;               // sync because buf is modified
+       tbit.nz p6,p0=buf,1
+       ;;
+       EX( .Lexit3, (p6) st2 [buf]=r0,2 )      // 2-byte aligned
+(p6)   adds len=-2,len;;
+       tbit.nz p6,p0=buf,2
+       ;;
+       EX( .Lexit3, (p6) st4 [buf]=r0,4 )      // 4-byte aligned
+(p6)   adds len=-4,len;;
+       tbit.nz p6,p0=buf,3
+       ;;
+       EX( .Lexit3, (p6) st8 [buf]=r0,8 )      // 8-byte aligned
+(p6)   adds len=-8,len;;
+       shr.u cnt=len,4         // number of 128-bit (2x64bit) words
+       ;;
+       cmp.eq p6,p0=r0,cnt
+       adds tmp=-1,cnt
+(p6)   br.cond.dpnt .dotail            // we have less than 16 bytes left
+       ;;
+       adds buf2=8,buf                 // setup second base pointer
+       mov ar.lc=tmp
+       ;;
+
+       //
+       // 16bytes/iteration core loop
+       //
+       // The second store can never generate a fault because
+       // we come into the loop only when we are 16-byte aligned.
+       // This means that if we cross a page then it will always be
+       // in the first store and never in the second.
+       //
+       //
+       // We need to keep track of the remaining length. A possible 
(optimistic)
+       // way would be to use ar.lc and derive how many byte were left by
+       // doing : left= 16*ar.lc + 16.  this would avoid the addition at
+       // every iteration.
+       // However we need to keep the synchronization point. A template
+       // M;;MB does not exist and thus we can keep the addition at no
+       // extra cycle cost (use a nop slot anyway). It also simplifies the
+       // (unlikely)  error recovery code
+       //
+
+2:     EX(.Lexit3, st8 [buf]=r0,16 )
+       ;;                              // needed to get len correct when error
+       st8 [buf2]=r0,16
+       adds len=-16,len
+       br.cloop.dptk 2b
+       ;;
+       mov ar.lc=saved_lc
+       //
+       // tail correction based on len only
+       //
+       // We alternate the use of len3,len2 to allow parallelism and correct
+       // error handling. We also reuse p6/p7 to return correct value.
+       // The addition of len2/len3 does not cost anything more compared to
+       // the regular memset as we had empty slots.
+       //
+.dotail:
+       mov len2=len                    // for parallelization of error handling
+       mov len3=len
+       tbit.nz p6,p0=len,3
+       ;;
+       EX( .Lexit2, (p6) st8 [buf]=r0,8 )      // at least 8 bytes
+(p6)   adds len3=-8,len2
+       tbit.nz p7,p6=len,2
+       ;;
+       EX( .Lexit2, (p7) st4 [buf]=r0,4 )      // at least 4 bytes
+(p7)   adds len2=-4,len3
+       tbit.nz p6,p7=len,1
+       ;;
+       EX( .Lexit2, (p6) st2 [buf]=r0,2 )      // at least 2 bytes
+(p6)   adds len3=-2,len2
+       tbit.nz p7,p6=len,0
+       ;;
+       EX( .Lexit2, (p7) st1 [buf]=r0 )        // only 1 byte left
+       mov ret0=r0                             // success
+       br.ret.sptk.many rp                     // end of most likely path
+
+       //
+       // Outlined error handling code
+       //
+
+       //
+       // .Lexit3: comes from core loop, need restore pr/lc
+       //          len contains bytes left
+       //
+       //
+       // .Lexit2:
+       //      if p6 -> coming from st8 or st2 : len2 contains what's left
+       //      if p7 -> coming from st4 or st1 : len3 contains what's left
+       // We must restore lc/pr even though might not have been used.
+.Lexit2:
+       .pred.rel "mutex", p6, p7
+(p6)   mov len=len2
+(p7)   mov len=len3
+       ;;
+       //
+       // .Lexit4: comes from head, need not restore pr/lc
+       //          len contains bytes left
+       //
+.Lexit3:
+       mov ret0=len
+       mov ar.lc=saved_lc
+       br.ret.sptk.many rp
+END(__do_clear_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/copy_page.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/copy_page.S       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,98 @@
+/*
+ *
+ * Optimized version of the standard copy_page() function
+ *
+ * Inputs:
+ *     in0:    address of target page
+ *     in1:    address of source page
+ * Output:
+ *     no return value
+ *
+ * Copyright (C) 1999, 2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger <davidm@xxxxxxxxxx>
+ *
+ * 4/06/01 davidm      Tuned to make it perform well both for cached and 
uncached copies.
+ */
+#include <asm/asmmacro.h>
+#include <asm/page.h>
+
+#define PIPE_DEPTH     3
+#define EPI            p[PIPE_DEPTH-1]
+
+#define lcount         r16
+#define saved_pr       r17
+#define saved_lc       r18
+#define saved_pfs      r19
+#define src1           r20
+#define src2           r21
+#define tgt1           r22
+#define tgt2           r23
+#define srcf           r24
+#define tgtf           r25
+#define tgt_last       r26
+
+#define Nrot           ((8*PIPE_DEPTH+7)&~7)
+
+GLOBAL_ENTRY(copy_page)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,3,Nrot-3,0,Nrot
+
+       .rotr t1[PIPE_DEPTH], t2[PIPE_DEPTH], t3[PIPE_DEPTH], t4[PIPE_DEPTH], \
+             t5[PIPE_DEPTH], t6[PIPE_DEPTH], t7[PIPE_DEPTH], t8[PIPE_DEPTH]
+       .rotp p[PIPE_DEPTH]
+
+       .save ar.lc, saved_lc
+       mov saved_lc=ar.lc
+       mov ar.ec=PIPE_DEPTH
+
+       mov lcount=PAGE_SIZE/64-1
+       .save pr, saved_pr
+       mov saved_pr=pr
+       mov pr.rot=1<<16
+
+       .body
+
+       mov src1=in1
+       adds src2=8,in1
+       mov tgt_last = PAGE_SIZE
+       ;;
+       adds tgt2=8,in0
+       add srcf=512,in1
+       mov ar.lc=lcount
+       mov tgt1=in0
+       add tgtf=512,in0
+       add tgt_last = tgt_last, in0
+       ;;
+1:
+(p[0]) ld8 t1[0]=[src1],16
+(EPI)  st8 [tgt1]=t1[PIPE_DEPTH-1],16
+(p[0]) ld8 t2[0]=[src2],16
+(EPI)  st8 [tgt2]=t2[PIPE_DEPTH-1],16
+       cmp.ltu p6,p0 = tgtf, tgt_last
+       ;;
+(p[0]) ld8 t3[0]=[src1],16
+(EPI)  st8 [tgt1]=t3[PIPE_DEPTH-1],16
+(p[0]) ld8 t4[0]=[src2],16
+(EPI)  st8 [tgt2]=t4[PIPE_DEPTH-1],16
+       ;;
+(p[0]) ld8 t5[0]=[src1],16
+(EPI)  st8 [tgt1]=t5[PIPE_DEPTH-1],16
+(p[0]) ld8 t6[0]=[src2],16
+(EPI)  st8 [tgt2]=t6[PIPE_DEPTH-1],16
+       ;;
+(p[0]) ld8 t7[0]=[src1],16
+(EPI)  st8 [tgt1]=t7[PIPE_DEPTH-1],16
+(p[0]) ld8 t8[0]=[src2],16
+(EPI)  st8 [tgt2]=t8[PIPE_DEPTH-1],16
+
+(p6)   lfetch [srcf], 64
+(p6)   lfetch [tgtf], 64
+       br.ctop.sptk.few 1b
+       ;;
+       mov pr=saved_pr,0xffffffffffff0000      // restore predicates
+       mov ar.pfs=saved_pfs
+       mov ar.lc=saved_lc
+       br.ret.sptk.many rp
+END(copy_page)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/copy_page_mck.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/copy_page_mck.S   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,185 @@
+/*
+ * McKinley-optimized version of copy_page().
+ *
+ * Copyright (C) 2002 Hewlett-Packard Co
+ *     David Mosberger <davidm@xxxxxxxxxx>
+ *
+ * Inputs:
+ *     in0:    address of target page
+ *     in1:    address of source page
+ * Output:
+ *     no return value
+ *
+ * General idea:
+ *     - use regular loads and stores to prefetch data to avoid consuming 
M-slot just for
+ *       lfetches => good for in-cache performance
+ *     - avoid l2 bank-conflicts by not storing into the same 16-byte bank 
within a single
+ *       cycle
+ *
+ * Principle of operation:
+ *     First, note that L1 has a line-size of 64 bytes and L2 a line-size of 
128 bytes.
+ *     To avoid secondary misses in L2, we prefetch both source and 
destination with a line-size
+ *     of 128 bytes.  When both of these lines are in the L2 and the first 
half of the
+ *     source line is in L1, we start copying the remaining words.  The second 
half of the
+ *     source line is prefetched in an earlier iteration, so that by the time 
we start
+ *     accessing it, it's also present in the L1.
+ *
+ *     We use a software-pipelined loop to control the overall operation.  The 
pipeline
+ *     has 2*PREFETCH_DIST+K stages.  The first PREFETCH_DIST stages are used 
for prefetching
+ *     source cache-lines.  The second PREFETCH_DIST stages are used for 
prefetching destination
+ *     cache-lines, the last K stages are used to copy the cache-line words 
not copied by
+ *     the prefetches.  The four relevant points in the pipelined are called 
A, B, C, D:
+ *     p[A] is TRUE if a source-line should be prefetched, p[B] is TRUE if a 
destination-line
+ *     should be prefetched, p[C] is TRUE if the second half of an L2 line 
should be brought
+ *     into L1D and p[D] is TRUE if a cacheline needs to be copied.
+ *
+ *     This all sounds very complicated, but thanks to the modulo-scheduled 
loop support,
+ *     the resulting code is very regular and quite easy to follow (once you 
get the idea).
+ *
+ *     As a secondary optimization, the first 2*PREFETCH_DIST iterations are 
implemented
+ *     as the separate .prefetch_loop.  Logically, this loop performs exactly 
like the
+ *     main-loop (.line_copy), but has all known-to-be-predicated-off 
instructions removed,
+ *     so that each loop iteration is faster (again, good for cached case).
+ *
+ *     When reading the code, it helps to keep the following picture in mind:
+ *
+ *            word 0 word 1
+ *            +------+------+---
+ *           | v[x] |  t1  | ^
+ *           | t2   |  t3  | |
+ *           | t4   |  t5  | |
+ *           | t6   |  t7  | | 128 bytes
+ *                   | n[y] |  t9  | | (L2 cache line)
+ *           | t10  |  t11 | |
+ *           | t12  |  t13 | |
+ *           | t14  |  t15 | v
+ *           +------+------+---
+ *
+ *     Here, v[x] is copied by the (memory) prefetch.  n[y] is loaded at p[C]
+ *     to fetch the second-half of the L2 cache line into L1, and the tX words 
are copied in
+ *     an order that avoids bank conflicts.
+ */
+#include <asm/asmmacro.h>
+#include <asm/page.h>
+
+#define PREFETCH_DIST  8               // McKinley sustains 16 outstanding L2 
misses (8 ld, 8 st)
+
+#define src0           r2
+#define src1           r3
+#define dst0           r9
+#define dst1           r10
+#define src_pre_mem    r11
+#define dst_pre_mem    r14
+#define src_pre_l2     r15
+#define dst_pre_l2     r16
+#define t1             r17
+#define t2             r18
+#define t3             r19
+#define t4             r20
+#define t5             t1      // alias!
+#define t6             t2      // alias!
+#define t7             t3      // alias!
+#define t9             t5      // alias!
+#define t10            t4      // alias!
+#define t11            t7      // alias!
+#define t12            t6      // alias!
+#define t14            t10     // alias!
+#define t13            r21
+#define t15            r22
+
+#define saved_lc       r23
+#define saved_pr       r24
+
+#define        A       0
+#define B      (PREFETCH_DIST)
+#define C      (B + PREFETCH_DIST)
+#define D      (C + 3)
+#define N      (D + 1)
+#define Nrot   ((N + 7) & ~7)
+
+GLOBAL_ENTRY(copy_page)
+       .prologue
+       alloc r8 = ar.pfs, 2, Nrot-2, 0, Nrot
+
+       .rotr v[2*PREFETCH_DIST], n[D-C+1]
+       .rotp p[N]
+
+       .save ar.lc, saved_lc
+       mov saved_lc = ar.lc
+       .save pr, saved_pr
+       mov saved_pr = pr
+       .body
+
+       mov src_pre_mem = in1
+       mov pr.rot = 0x10000
+       mov ar.ec = 1                           // special unrolled loop
+
+       mov dst_pre_mem = in0
+       mov ar.lc = 2*PREFETCH_DIST - 1
+
+       add src_pre_l2 = 8*8, in1
+       add dst_pre_l2 = 8*8, in0
+       add src0 = 8, in1                       // first t1 src
+       add src1 = 3*8, in1                     // first t3 src
+       add dst0 = 8, in0                       // first t1 dst
+       add dst1 = 3*8, in0                     // first t3 dst
+       mov t1 = (PAGE_SIZE/128) - (2*PREFETCH_DIST) - 1
+       nop.m 0
+       nop.i 0
+       ;;
+       // same as .line_copy loop, but with all predicated-off instructions 
removed:
+.prefetch_loop:
+(p[A]) ld8 v[A] = [src_pre_mem], 128           // M0
+(p[B]) st8 [dst_pre_mem] = v[B], 128           // M2
+       br.ctop.sptk .prefetch_loop
+       ;;
+       cmp.eq p16, p0 = r0, r0                 // reset p16 to 1 (br.ctop 
cleared it to zero)
+       mov ar.lc = t1                          // with 64KB pages, t1 is too 
big to fit in 8 bits!
+       mov ar.ec = N                           // # of stages in pipeline
+       ;;
+.line_copy:
+(p[D]) ld8 t2 = [src0], 3*8                    // M0
+(p[D]) ld8 t4 = [src1], 3*8                    // M1
+(p[B]) st8 [dst_pre_mem] = v[B], 128           // M2 prefetch dst from memory
+(p[D]) st8 [dst_pre_l2] = n[D-C], 128          // M3 prefetch dst from L2
+       ;;
+(p[A]) ld8 v[A] = [src_pre_mem], 128           // M0 prefetch src from memory
+(p[C]) ld8 n[0] = [src_pre_l2], 128            // M1 prefetch src from L2
+(p[D]) st8 [dst0] =  t1, 8                     // M2
+(p[D]) st8 [dst1] =  t3, 8                     // M3
+       ;;
+(p[D]) ld8  t5 = [src0], 8
+(p[D]) ld8  t7 = [src1], 3*8
+(p[D]) st8 [dst0] =  t2, 3*8
+(p[D]) st8 [dst1] =  t4, 3*8
+       ;;
+(p[D]) ld8  t6 = [src0], 3*8
+(p[D]) ld8 t10 = [src1], 8
+(p[D]) st8 [dst0] =  t5, 8
+(p[D]) st8 [dst1] =  t7, 3*8
+       ;;
+(p[D]) ld8  t9 = [src0], 3*8
+(p[D]) ld8 t11 = [src1], 3*8
+(p[D]) st8 [dst0] =  t6, 3*8
+(p[D]) st8 [dst1] = t10, 8
+       ;;
+(p[D]) ld8 t12 = [src0], 8
+(p[D]) ld8 t14 = [src1], 8
+(p[D]) st8 [dst0] =  t9, 3*8
+(p[D]) st8 [dst1] = t11, 3*8
+       ;;
+(p[D]) ld8 t13 = [src0], 4*8
+(p[D]) ld8 t15 = [src1], 4*8
+(p[D]) st8 [dst0] = t12, 8
+(p[D]) st8 [dst1] = t14, 8
+       ;;
+(p[D-1])ld8  t1 = [src0], 8
+(p[D-1])ld8  t3 = [src1], 8
+(p[D]) st8 [dst0] = t13, 4*8
+(p[D]) st8 [dst1] = t15, 4*8
+       br.ctop.sptk .line_copy
+       ;;
+       mov ar.lc = saved_lc
+       mov pr = saved_pr, -1
+       br.ret.sptk.many rp
+END(copy_page)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/copy_user.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/copy_user.S       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,610 @@
+/*
+ *
+ * Optimized version of the copy_user() routine.
+ * It is used to copy date across the kernel/user boundary.
+ *
+ * The source and destination are always on opposite side of
+ * the boundary. When reading from user space we must catch
+ * faults on loads. When writing to user space we must catch
+ * errors on stores. Note that because of the nature of the copy
+ * we don't need to worry about overlapping regions.
+ *
+ *
+ * Inputs:
+ *     in0     address of source buffer
+ *     in1     address of destination buffer
+ *     in2     number of bytes to copy
+ *
+ * Outputs:
+ *     ret0    0 in case of success. The number of bytes NOT copied in
+ *             case of error.
+ *
+ * Copyright (C) 2000-2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * Fixme:
+ *     - handle the case where we have more than 16 bytes and the alignment
+ *       are different.
+ *     - more benchmarking
+ *     - fix extraneous stop bit introduced by the EX() macro.
+ */
+
+#include <asm/asmmacro.h>
+
+//
+// Tuneable parameters
+//
+#define COPY_BREAK     16      // we do byte copy below (must be >=16)
+#define PIPE_DEPTH     21      // pipe depth
+
+#define EPI            p[PIPE_DEPTH-1]
+
+//
+// arguments
+//
+#define dst            in0
+#define src            in1
+#define len            in2
+
+//
+// local registers
+//
+#define t1             r2      // rshift in bytes
+#define t2             r3      // lshift in bytes
+#define rshift         r14     // right shift in bits
+#define lshift         r15     // left shift in bits
+#define word1          r16
+#define word2          r17
+#define cnt            r18
+#define len2           r19
+#define saved_lc       r20
+#define saved_pr       r21
+#define tmp            r22
+#define val            r23
+#define src1           r24
+#define dst1           r25
+#define src2           r26
+#define dst2           r27
+#define len1           r28
+#define enddst         r29
+#define endsrc         r30
+#define saved_pfs      r31
+
+GLOBAL_ENTRY(__copy_user)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,3,((2*PIPE_DEPTH+7)&~7),0,((2*PIPE_DEPTH+7)&~7)
+
+       .rotr val1[PIPE_DEPTH],val2[PIPE_DEPTH]
+       .rotp p[PIPE_DEPTH]
+
+       adds len2=-1,len        // br.ctop is repeat/until
+       mov ret0=r0
+
+       ;;                      // RAW of cfm when len=0
+       cmp.eq p8,p0=r0,len     // check for zero length
+       .save ar.lc, saved_lc
+       mov saved_lc=ar.lc      // preserve ar.lc (slow)
+(p8)   br.ret.spnt.many rp     // empty mempcy()
+       ;;
+       add enddst=dst,len      // first byte after end of source
+       add endsrc=src,len      // first byte after end of destination
+       .save pr, saved_pr
+       mov saved_pr=pr         // preserve predicates
+
+       .body
+
+       mov dst1=dst            // copy because of rotation
+       mov ar.ec=PIPE_DEPTH
+       mov pr.rot=1<<16        // p16=true all others are false
+
+       mov src1=src            // copy because of rotation
+       mov ar.lc=len2          // initialize lc for small count
+       cmp.lt p10,p7=COPY_BREAK,len    // if len > COPY_BREAK then long copy
+
+       xor tmp=src,dst         // same alignment test prepare
+(p10)  br.cond.dptk .long_copy_user
+       ;;                      // RAW pr.rot/p16 ?
+       //
+       // Now we do the byte by byte loop with software pipeline
+       //
+       // p7 is necessarily false by now
+1:
+       EX(.failure_in_pipe1,(p16) ld1 val1[0]=[src1],1)
+       EX(.failure_out,(EPI) st1 [dst1]=val1[PIPE_DEPTH-1],1)
+       br.ctop.dptk.few 1b
+       ;;
+       mov ar.lc=saved_lc
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.pfs=saved_pfs            // restore ar.ec
+       br.ret.sptk.many rp             // end of short memcpy
+
+       //
+       // Not 8-byte aligned
+       //
+.diff_align_copy_user:
+       // At this point we know we have more than 16 bytes to copy
+       // and also that src and dest do _not_ have the same alignment.
+       and src2=0x7,src1                               // src offset
+       and dst2=0x7,dst1                               // dst offset
+       ;;
+       // The basic idea is that we copy byte-by-byte at the head so
+       // that we can reach 8-byte alignment for both src1 and dst1.
+       // Then copy the body using software pipelined 8-byte copy,
+       // shifting the two back-to-back words right and left, then copy
+       // the tail by copying byte-by-byte.
+       //
+       // Fault handling. If the byte-by-byte at the head fails on the
+       // load, then restart and finish the pipleline by copying zeros
+       // to the dst1. Then copy zeros for the rest of dst1.
+       // If 8-byte software pipeline fails on the load, do the same as
+       // failure_in3 does. If the byte-by-byte at the tail fails, it is
+       // handled simply by failure_in_pipe1.
+       //
+       // The case p14 represents the source has more bytes in the
+       // the first word (by the shifted part), whereas the p15 needs to
+       // copy some bytes from the 2nd word of the source that has the
+       // tail of the 1st of the destination.
+       //
+
+       //
+       // Optimization. If dst1 is 8-byte aligned (quite common), we don't need
+       // to copy the head to dst1, to start 8-byte copy software pipeline.
+       // We know src1 is not 8-byte aligned in this case.
+       //
+       cmp.eq p14,p15=r0,dst2
+(p15)  br.cond.spnt 1f
+       ;;
+       sub t1=8,src2
+       mov t2=src2
+       ;;
+       shl rshift=t2,3
+       sub len1=len,t1                                 // set len1
+       ;;
+       sub lshift=64,rshift
+       ;;
+       br.cond.spnt .word_copy_user
+       ;;
+1:
+       cmp.leu p14,p15=src2,dst2
+       sub t1=dst2,src2
+       ;;
+       .pred.rel "mutex", p14, p15
+(p14)  sub word1=8,src2                                // (8 - src offset)
+(p15)  sub t1=r0,t1                                    // absolute value
+(p15)  sub word1=8,dst2                                // (8 - dst offset)
+       ;;
+       // For the case p14, we don't need to copy the shifted part to
+       // the 1st word of destination.
+       sub t2=8,t1
+(p14)  sub word1=word1,t1
+       ;;
+       sub len1=len,word1                              // resulting len
+(p15)  shl rshift=t1,3                                 // in bits
+(p14)  shl rshift=t2,3
+       ;;
+(p14)  sub len1=len1,t1
+       adds cnt=-1,word1
+       ;;
+       sub lshift=64,rshift
+       mov ar.ec=PIPE_DEPTH
+       mov pr.rot=1<<16        // p16=true all others are false
+       mov ar.lc=cnt
+       ;;
+2:
+       EX(.failure_in_pipe2,(p16) ld1 val1[0]=[src1],1)
+       EX(.failure_out,(EPI) st1 [dst1]=val1[PIPE_DEPTH-1],1)
+       br.ctop.dptk.few 2b
+       ;;
+       clrrrb
+       ;;
+.word_copy_user:
+       cmp.gtu p9,p0=16,len1
+(p9)   br.cond.spnt 4f                 // if (16 > len1) skip 8-byte copy
+       ;;
+       shr.u cnt=len1,3                // number of 64-bit words
+       ;;
+       adds cnt=-1,cnt
+       ;;
+       .pred.rel "mutex", p14, p15
+(p14)  sub src1=src1,t2
+(p15)  sub src1=src1,t1
+       //
+       // Now both src1 and dst1 point to an 8-byte aligned address. And
+       // we have more than 8 bytes to copy.
+       //
+       mov ar.lc=cnt
+       mov ar.ec=PIPE_DEPTH
+       mov pr.rot=1<<16        // p16=true all others are false
+       ;;
+3:
+       //
+       // The pipleline consists of 3 stages:
+       // 1 (p16):     Load a word from src1
+       // 2 (EPI_1):   Shift right pair, saving to tmp
+       // 3 (EPI):     Store tmp to dst1
+       //
+       // To make it simple, use at least 2 (p16) loops to set up val1[n]
+       // because we need 2 back-to-back val1[] to get tmp.
+       // Note that this implies EPI_2 must be p18 or greater.
+       //
+
+#define EPI_1          p[PIPE_DEPTH-2]
+#define SWITCH(pred, shift)    cmp.eq pred,p0=shift,rshift
+#define CASE(pred, shift)      \
+       (pred)  br.cond.spnt .copy_user_bit##shift
+#define BODY(rshift)                                           \
+.copy_user_bit##rshift:                                                \
+1:                                                             \
+       EX(.failure_out,(EPI) st8 [dst1]=tmp,8);                \
+(EPI_1) shrp tmp=val1[PIPE_DEPTH-2],val1[PIPE_DEPTH-1],rshift; \
+       EX(3f,(p16) ld8 val1[1]=[src1],8);                      \
+(p16)  mov val1[0]=r0;                                         \
+       br.ctop.dptk 1b;                                        \
+       ;;                                                      \
+       br.cond.sptk.many .diff_align_do_tail;                  \
+2:                                                             \
+(EPI)  st8 [dst1]=tmp,8;                                       \
+(EPI_1)        shrp tmp=val1[PIPE_DEPTH-2],val1[PIPE_DEPTH-1],rshift;  \
+3:                                                             \
+(p16)  mov val1[1]=r0;                                         \
+(p16)  mov val1[0]=r0;                                         \
+       br.ctop.dptk 2b;                                        \
+       ;;                                                      \
+       br.cond.sptk.many .failure_in2
+
+       //
+       // Since the instruction 'shrp' requires a fixed 128-bit value
+       // specifying the bits to shift, we need to provide 7 cases
+       // below.
+       //
+       SWITCH(p6, 8)
+       SWITCH(p7, 16)
+       SWITCH(p8, 24)
+       SWITCH(p9, 32)
+       SWITCH(p10, 40)
+       SWITCH(p11, 48)
+       SWITCH(p12, 56)
+       ;;
+       CASE(p6, 8)
+       CASE(p7, 16)
+       CASE(p8, 24)
+       CASE(p9, 32)
+       CASE(p10, 40)
+       CASE(p11, 48)
+       CASE(p12, 56)
+       ;;
+       BODY(8)
+       BODY(16)
+       BODY(24)
+       BODY(32)
+       BODY(40)
+       BODY(48)
+       BODY(56)
+       ;;
+.diff_align_do_tail:
+       .pred.rel "mutex", p14, p15
+(p14)  sub src1=src1,t1
+(p14)  adds dst1=-8,dst1
+(p15)  sub dst1=dst1,t1
+       ;;
+4:
+       // Tail correction.
+       //
+       // The problem with this piplelined loop is that the last word is not
+       // loaded and thus parf of the last word written is not correct.
+       // To fix that, we simply copy the tail byte by byte.
+
+       sub len1=endsrc,src1,1
+       clrrrb
+       ;;
+       mov ar.ec=PIPE_DEPTH
+       mov pr.rot=1<<16        // p16=true all others are false
+       mov ar.lc=len1
+       ;;
+5:
+       EX(.failure_in_pipe1,(p16) ld1 val1[0]=[src1],1)
+       EX(.failure_out,(EPI) st1 [dst1]=val1[PIPE_DEPTH-1],1)
+       br.ctop.dptk.few 5b
+       ;;
+       mov ar.lc=saved_lc
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       //
+       // Beginning of long mempcy (i.e. > 16 bytes)
+       //
+.long_copy_user:
+       tbit.nz p6,p7=src1,0    // odd alignment
+       and tmp=7,tmp
+       ;;
+       cmp.eq p10,p8=r0,tmp
+       mov len1=len            // copy because of rotation
+(p8)   br.cond.dpnt .diff_align_copy_user
+       ;;
+       // At this point we know we have more than 16 bytes to copy
+       // and also that both src and dest have the same alignment
+       // which may not be the one we want. So for now we must move
+       // forward slowly until we reach 16byte alignment: no need to
+       // worry about reaching the end of buffer.
+       //
+       EX(.failure_in1,(p6) ld1 val1[0]=[src1],1)      // 1-byte aligned
+(p6)   adds len1=-1,len1;;
+       tbit.nz p7,p0=src1,1
+       ;;
+       EX(.failure_in1,(p7) ld2 val1[1]=[src1],2)      // 2-byte aligned
+(p7)   adds len1=-2,len1;;
+       tbit.nz p8,p0=src1,2
+       ;;
+       //
+       // Stop bit not required after ld4 because if we fail on ld4
+       // we have never executed the ld1, therefore st1 is not executed.
+       //
+       EX(.failure_in1,(p8) ld4 val2[0]=[src1],4)      // 4-byte aligned
+       ;;
+       EX(.failure_out,(p6) st1 [dst1]=val1[0],1)
+       tbit.nz p9,p0=src1,3
+       ;;
+       //
+       // Stop bit not required after ld8 because if we fail on ld8
+       // we have never executed the ld2, therefore st2 is not executed.
+       //
+       EX(.failure_in1,(p9) ld8 val2[1]=[src1],8)      // 8-byte aligned
+       EX(.failure_out,(p7) st2 [dst1]=val1[1],2)
+(p8)   adds len1=-4,len1
+       ;;
+       EX(.failure_out, (p8) st4 [dst1]=val2[0],4)
+(p9)   adds len1=-8,len1;;
+       shr.u cnt=len1,4                // number of 128-bit (2x64bit) words
+       ;;
+       EX(.failure_out, (p9) st8 [dst1]=val2[1],8)
+       tbit.nz p6,p0=len1,3
+       cmp.eq p7,p0=r0,cnt
+       adds tmp=-1,cnt                 // br.ctop is repeat/until
+(p7)   br.cond.dpnt .dotail            // we have less than 16 bytes left
+       ;;
+       adds src2=8,src1
+       adds dst2=8,dst1
+       mov ar.lc=tmp
+       ;;
+       //
+       // 16bytes/iteration
+       //
+2:
+       EX(.failure_in3,(p16) ld8 val1[0]=[src1],16)
+(p16)  ld8 val2[0]=[src2],16
+
+       EX(.failure_out, (EPI)  st8 [dst1]=val1[PIPE_DEPTH-1],16)
+(EPI)  st8 [dst2]=val2[PIPE_DEPTH-1],16
+       br.ctop.dptk 2b
+       ;;                      // RAW on src1 when fall through from loop
+       //
+       // Tail correction based on len only
+       //
+       // No matter where we come from (loop or test) the src1 pointer
+       // is 16 byte aligned AND we have less than 16 bytes to copy.
+       //
+.dotail:
+       EX(.failure_in1,(p6) ld8 val1[0]=[src1],8)      // at least 8 bytes
+       tbit.nz p7,p0=len1,2
+       ;;
+       EX(.failure_in1,(p7) ld4 val1[1]=[src1],4)      // at least 4 bytes
+       tbit.nz p8,p0=len1,1
+       ;;
+       EX(.failure_in1,(p8) ld2 val2[0]=[src1],2)      // at least 2 bytes
+       tbit.nz p9,p0=len1,0
+       ;;
+       EX(.failure_out, (p6) st8 [dst1]=val1[0],8)
+       ;;
+       EX(.failure_in1,(p9) ld1 val2[1]=[src1])        // only 1 byte left
+       mov ar.lc=saved_lc
+       ;;
+       EX(.failure_out,(p7) st4 [dst1]=val1[1],4)
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       EX(.failure_out, (p8)   st2 [dst1]=val2[0],2)
+       mov ar.pfs=saved_pfs
+       ;;
+       EX(.failure_out, (p9)   st1 [dst1]=val2[1])
+       br.ret.sptk.many rp
+
+
+       //
+       // Here we handle the case where the byte by byte copy fails
+       // on the load.
+       // Several factors make the zeroing of the rest of the buffer kind of
+       // tricky:
+       //      - the pipeline: loads/stores are not in sync (pipeline)
+       //
+       //        In the same loop iteration, the dst1 pointer does not directly
+       //        reflect where the faulty load was.
+       //
+       //      - pipeline effect
+       //        When you get a fault on load, you may have valid data from
+       //        previous loads not yet store in transit. Such data must be
+       //        store normally before moving onto zeroing the rest.
+       //
+       //      - single/multi dispersal independence.
+       //
+       // solution:
+       //      - we don't disrupt the pipeline, i.e. data in transit in
+       //        the software pipeline will be eventually move to memory.
+       //        We simply replace the load with a simple mov and keep the
+       //        pipeline going. We can't really do this inline because
+       //        p16 is always reset to 1 when lc > 0.
+       //
+.failure_in_pipe1:
+       sub ret0=endsrc,src1    // number of bytes to zero, i.e. not copied
+1:
+(p16)  mov val1[0]=r0
+(EPI)  st1 [dst1]=val1[PIPE_DEPTH-1],1
+       br.ctop.dptk 1b
+       ;;
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.lc=saved_lc
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       //
+       // This is the case where the byte by byte copy fails on the load
+       // when we copy the head. We need to finish the pipeline and copy
+       // zeros for the rest of the destination. Since this happens
+       // at the top we still need to fill the body and tail.
+.failure_in_pipe2:
+       sub ret0=endsrc,src1    // number of bytes to zero, i.e. not copied
+2:
+(p16)  mov val1[0]=r0
+(EPI)  st1 [dst1]=val1[PIPE_DEPTH-1],1
+       br.ctop.dptk 2b
+       ;;
+       sub len=enddst,dst1,1           // precompute len
+       br.cond.dptk.many .failure_in1bis
+       ;;
+
+       //
+       // Here we handle the head & tail part when we check for alignment.
+       // The following code handles only the load failures. The
+       // main diffculty comes from the fact that loads/stores are
+       // scheduled. So when you fail on a load, the stores corresponding
+       // to previous successful loads must be executed.
+       //
+       // However some simplifications are possible given the way
+       // things work.
+       //
+       // 1) HEAD
+       // Theory of operation:
+       //
+       //  Page A   | Page B
+       //  ---------|-----
+       //          1|8 x
+       //        1 2|8 x
+       //          4|8 x
+       //        1 4|8 x
+       //        2 4|8 x
+       //      1 2 4|8 x
+       //           |1
+       //           |2 x
+       //           |4 x
+       //
+       // page_size >= 4k (2^12).  (x means 4, 2, 1)
+       // Here we suppose Page A exists and Page B does not.
+       //
+       // As we move towards eight byte alignment we may encounter faults.
+       // The numbers on each page show the size of the load (current 
alignment).
+       //
+       // Key point:
+       //      - if you fail on 1, 2, 4 then you have never executed any 
smaller
+       //        size loads, e.g. failing ld4 means no ld1 nor ld2 executed
+       //        before.
+       //
+       // This allows us to simplify the cleanup code, because basically you
+       // only have to worry about "pending" stores in the case of a failing
+       // ld8(). Given the way the code is written today, this means only
+       // worry about st2, st4. There we can use the information encapsulated
+       // into the predicates.
+       //
+       // Other key point:
+       //      - if you fail on the ld8 in the head, it means you went straight
+       //        to it, i.e. 8byte alignment within an unexisting page.
+       // Again this comes from the fact that if you crossed just for the ld8 
then
+       // you are 8byte aligned but also 16byte align, therefore you would
+       // either go for the 16byte copy loop OR the ld8 in the tail part.
+       // The combination ld1, ld2, ld4, ld8 where you fail on ld8 is 
impossible
+       // because it would mean you had 15bytes to copy in which case you
+       // would have defaulted to the byte by byte copy.
+       //
+       //
+       // 2) TAIL
+       // Here we now we have less than 16 bytes AND we are either 8 or 16 byte
+       // aligned.
+       //
+       // Key point:
+       // This means that we either:
+       //              - are right on a page boundary
+       //      OR
+       //              - are at more than 16 bytes from a page boundary with
+       //                at most 15 bytes to copy: no chance of crossing.
+       //
+       // This allows us to assume that if we fail on a load we haven't 
possibly
+       // executed any of the previous (tail) ones, so we don't need to do
+       // any stores. For instance, if we fail on ld2, this means we had
+       // 2 or 3 bytes left to copy and we did not execute the ld8 nor ld4.
+       //
+       // This means that we are in a situation similar the a fault in the
+       // head part. That's nice!
+       //
+.failure_in1:
+       sub ret0=endsrc,src1    // number of bytes to zero, i.e. not copied
+       sub len=endsrc,src1,1
+       //
+       // we know that ret0 can never be zero at this point
+       // because we failed why trying to do a load, i.e. there is still
+       // some work to do.
+       // The failure_in1bis and length problem is taken care of at the
+       // calling side.
+       //
+       ;;
+.failure_in1bis:               // from (.failure_in3)
+       mov ar.lc=len           // Continue with a stupid byte store.
+       ;;
+5:
+       st1 [dst1]=r0,1
+       br.cloop.dptk 5b
+       ;;
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.lc=saved_lc
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       //
+       // Here we simply restart the loop but instead
+       // of doing loads we fill the pipeline with zeroes
+       // We can't simply store r0 because we may have valid
+       // data in transit in the pipeline.
+       // ar.lc and ar.ec are setup correctly at this point
+       //
+       // we MUST use src1/endsrc here and not dst1/enddst because
+       // of the pipeline effect.
+       //
+.failure_in3:
+       sub ret0=endsrc,src1    // number of bytes to zero, i.e. not copied
+       ;;
+2:
+(p16)  mov val1[0]=r0
+(p16)  mov val2[0]=r0
+(EPI)  st8 [dst1]=val1[PIPE_DEPTH-1],16
+(EPI)  st8 [dst2]=val2[PIPE_DEPTH-1],16
+       br.ctop.dptk 2b
+       ;;
+       cmp.ne p6,p0=dst1,enddst        // Do we need to finish the tail ?
+       sub len=enddst,dst1,1           // precompute len
+(p6)   br.cond.dptk .failure_in1bis
+       ;;
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.lc=saved_lc
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+.failure_in2:
+       sub ret0=endsrc,src1
+       cmp.ne p6,p0=dst1,enddst        // Do we need to finish the tail ?
+       sub len=enddst,dst1,1           // precompute len
+(p6)   br.cond.dptk .failure_in1bis
+       ;;
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.lc=saved_lc
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       //
+       // handling of failures on stores: that's the easy part
+       //
+.failure_out:
+       sub ret0=enddst,dst1
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.lc=saved_lc
+
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+END(__copy_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/csum_partial_copy.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/csum_partial_copy.c       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,151 @@
+/*
+ * Network Checksum & Copy routine
+ *
+ * Copyright (C) 1999, 2003-2004 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * Most of the code has been imported from Linux/Alpha
+ */
+
+#include <linux/module.h>
+#include <linux/types.h>
+#include <linux/string.h>
+
+#include <asm/uaccess.h>
+
+/*
+ * XXX Fixme: those 2 inlines are meant for debugging and will go away
+ */
+static inline unsigned
+short from64to16(unsigned long x)
+{
+       /* add up 32-bit words for 33 bits */
+       x = (x & 0xffffffff) + (x >> 32);
+       /* add up 16-bit and 17-bit words for 17+c bits */
+       x = (x & 0xffff) + (x >> 16);
+       /* add up 16-bit and 2-bit for 16+c bit */
+       x = (x & 0xffff) + (x >> 16);
+       /* add up carry.. */
+       x = (x & 0xffff) + (x >> 16);
+       return x;
+}
+
+static inline
+unsigned long do_csum_c(const unsigned char * buff, int len, unsigned int psum)
+{
+       int odd, count;
+       unsigned long result = (unsigned long)psum;
+
+       if (len <= 0)
+               goto out;
+       odd = 1 & (unsigned long) buff;
+       if (odd) {
+               result = *buff << 8;
+               len--;
+               buff++;
+       }
+       count = len >> 1;               /* nr of 16-bit words.. */
+       if (count) {
+               if (2 & (unsigned long) buff) {
+                       result += *(unsigned short *) buff;
+                       count--;
+                       len -= 2;
+                       buff += 2;
+               }
+               count >>= 1;            /* nr of 32-bit words.. */
+               if (count) {
+                       if (4 & (unsigned long) buff) {
+                               result += *(unsigned int *) buff;
+                               count--;
+                               len -= 4;
+                               buff += 4;
+                       }
+                       count >>= 1;    /* nr of 64-bit words.. */
+                       if (count) {
+                               unsigned long carry = 0;
+                               do {
+                                       unsigned long w = *(unsigned long *) 
buff;
+                                       count--;
+                                       buff += 8;
+                                       result += carry;
+                                       result += w;
+                                       carry = (w > result);
+                               } while (count);
+                               result += carry;
+                               result = (result & 0xffffffff) + (result >> 32);
+                       }
+                       if (len & 4) {
+                               result += *(unsigned int *) buff;
+                               buff += 4;
+                       }
+               }
+               if (len & 2) {
+                       result += *(unsigned short *) buff;
+                       buff += 2;
+               }
+       }
+       if (len & 1)
+               result += *buff;
+
+       result = from64to16(result);
+
+       if (odd)
+               result = ((result >> 8) & 0xff) | ((result & 0xff) << 8);
+
+out:
+       return result;
+}
+
+/*
+ * XXX Fixme
+ *
+ * This is very ugly but temporary. THIS NEEDS SERIOUS ENHANCEMENTS.
+ * But it's very tricky to get right even in C.
+ */
+extern unsigned long do_csum(const unsigned char *, long);
+
+static unsigned int
+do_csum_partial_copy_from_user (const unsigned char __user *src, unsigned char 
*dst,
+                               int len, unsigned int psum, int *errp)
+{
+       unsigned long result;
+
+       /* XXX Fixme
+        * for now we separate the copy from checksum for obvious
+        * alignment difficulties. Look at the Alpha code and you'll be
+        * scared.
+        */
+
+       if (__copy_from_user(dst, src, len) != 0 && errp)
+               *errp = -EFAULT;
+
+       result = do_csum(dst, len);
+
+       /* add in old sum, and carry.. */
+       result += psum;
+       /* 32+c bits -> 32 bits */
+       result = (result & 0xffffffff) + (result >> 32);
+       return result;
+}
+
+unsigned int
+csum_partial_copy_from_user (const unsigned char __user *src, unsigned char 
*dst,
+                            int len, unsigned int sum, int *errp)
+{
+       if (!access_ok(VERIFY_READ, src, len)) {
+               *errp = -EFAULT;
+               memset(dst, 0, len);
+               return sum;
+       }
+
+       return do_csum_partial_copy_from_user(src, dst, len, sum, errp);
+}
+
+unsigned int
+csum_partial_copy_nocheck(const unsigned char __user *src, unsigned char *dst,
+                         int len, unsigned int sum)
+{
+       return do_csum_partial_copy_from_user(src, dst, len, sum, NULL);
+}
+
+EXPORT_SYMBOL(csum_partial_copy_nocheck);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/dec_and_lock.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/dec_and_lock.c    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2003 Jerome Marchand, Bull S.A.
+ *     Cleaned up by David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * This file is released under the GPLv2, or at your option any later version.
+ *
+ * ia64 version of "atomic_dec_and_lock()" using the atomic "cmpxchg" 
instruction.  This
+ * code is an adaptation of the x86 version of "atomic_dec_and_lock()".
+ */
+
+#include <linux/compiler.h>
+#include <linux/module.h>
+#include <linux/spinlock.h>
+#include <asm/atomic.h>
+
+/*
+ * Decrement REFCOUNT and if the count reaches zero, acquire the spinlock.  
Both of these
+ * operations have to be done atomically, so that the count doesn't drop to 
zero without
+ * acquiring the spinlock first.
+ */
+int
+_atomic_dec_and_lock (atomic_t *refcount, spinlock_t *lock)
+{
+       int old, new;
+
+       do {
+               old = atomic_read(refcount);
+               new = old - 1;
+
+               if (unlikely (old == 1)) {
+                       /* oops, we may be decrementing to zero, do it the slow 
way... */
+                       spin_lock(lock);
+                       if (atomic_dec_and_test(refcount))
+                               return 1;
+                       spin_unlock(lock);
+                       return 0;
+               }
+       } while (cmpxchg(&refcount->counter, old, new) != old);
+       return 0;
+}
+
+EXPORT_SYMBOL(_atomic_dec_and_lock);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/do_csum.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/do_csum.S Tue Aug 16 04:15:23 2005
@@ -0,0 +1,323 @@
+/*
+ *
+ * Optmized version of the standard do_csum() function
+ *
+ * Return: a 64bit quantity containing the 16bit Internet checksum
+ *
+ * Inputs:
+ *     in0: address of buffer to checksum (char *)
+ *     in1: length of the buffer (int)
+ *
+ * Copyright (C) 1999, 2001-2002 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * 02/04/22    Ken Chen <kenneth.w.chen@xxxxxxxxx>
+ *             Data locality study on the checksum buffer.
+ *             More optimization cleanup - remove excessive stop bits.
+ * 02/04/08    David Mosberger <davidm@xxxxxxxxxx>
+ *             More cleanup and tuning.
+ * 01/04/18    Jun Nakajima <jun.nakajima@xxxxxxxxx>
+ *             Clean up and optimize and the software pipeline, loading two
+ *             back-to-back 8-byte words per loop. Clean up the initialization
+ *             for the loop. Support the cases where load latency = 1 or 2.
+ *             Set CONFIG_IA64_LOAD_LATENCY to 1 or 2 (default).
+ */
+
+#include <asm/asmmacro.h>
+
+//
+// Theory of operations:
+//     The goal is to go as quickly as possible to the point where
+//     we can checksum 16 bytes/loop. Before reaching that point we must
+//     take care of incorrect alignment of first byte.
+//
+//     The code hereafter also takes care of the "tail" part of the buffer
+//     before entering the core loop, if any. The checksum is a sum so it
+//     allows us to commute operations. So we do the "head" and "tail"
+//     first to finish at full speed in the body. Once we get the head and
+//     tail values, we feed them into the pipeline, very handy initialization.
+//
+//     Of course we deal with the special case where the whole buffer fits
+//     into one 8 byte word. In this case we have only one entry in the 
pipeline.
+//
+//     We use a (LOAD_LATENCY+2)-stage pipeline in the loop to account for
+//     possible load latency and also to accommodate for head and tail.
+//
+//     The end of the function deals with folding the checksum from 64bits
+//     down to 16bits taking care of the carry.
+//
+//     This version avoids synchronization in the core loop by also using a
+//     pipeline for the accumulation of the checksum in resultx[] (x=1,2).
+//
+//      wordx[] (x=1,2)
+//     |---|
+//      |   | 0                        : new value loaded in pipeline
+//     |---|
+//      |   | -                        : in transit data
+//     |---|
+//      |   | LOAD_LATENCY     : current value to add to checksum
+//     |---|
+//      |   | LOAD_LATENCY+1   : previous value added to checksum
+//      |---|                  (previous iteration)
+//
+//     resultx[] (x=1,2)
+//     |---|
+//      |   | 0                        : initial value
+//     |---|
+//      |   | LOAD_LATENCY-1   : new checksum
+//     |---|
+//      |   | LOAD_LATENCY     : previous value of checksum
+//     |---|
+//      |   | LOAD_LATENCY+1   : final checksum when out of the loop
+//      |---|
+//
+//
+//     See RFC1071 "Computing the Internet Checksum" for various techniques for
+//     calculating the Internet checksum.
+//
+// NOT YET DONE:
+//     - Maybe another algorithm which would take care of the folding at the
+//       end in a different manner
+//     - Work with people more knowledgeable than me on the network stack
+//       to figure out if we could not split the function depending on the
+//       type of packet or alignment we get. Like the ip_fast_csum() routine
+//       where we know we have at least 20bytes worth of data to checksum.
+//     - Do a better job of handling small packets.
+//     - Note on prefetching: it was found that under various load, i.e. ftp 
read/write,
+//       nfs read/write, the L1 cache hit rate is at 60% and L2 cache hit rate 
is at 99.8%
+//       on the data that buffer points to (partly because the checksum is 
often preceded by
+//       a copy_from_user()).  This finding indiate that lfetch will not be 
beneficial since
+//       the data is already in the cache.
+//
+
+#define saved_pfs      r11
+#define hmask          r16
+#define tmask          r17
+#define first1         r18
+#define firstval       r19
+#define firstoff       r20
+#define last           r21
+#define lastval                r22
+#define lastoff                r23
+#define saved_lc       r24
+#define saved_pr       r25
+#define tmp1           r26
+#define tmp2           r27
+#define tmp3           r28
+#define carry1         r29
+#define carry2         r30
+#define first2         r31
+
+#define buf            in0
+#define len            in1
+
+#define LOAD_LATENCY   2       // XXX fix me
+
+#if (LOAD_LATENCY != 1) && (LOAD_LATENCY != 2)
+# error "Only 1 or 2 is supported/tested for LOAD_LATENCY."
+#endif
+
+#define PIPE_DEPTH                     (LOAD_LATENCY+2)
+#define ELD    p[LOAD_LATENCY]         // end of load
+#define ELD_1  p[LOAD_LATENCY+1]       // and next stage
+
+// unsigned long do_csum(unsigned char *buf,long len)
+
+GLOBAL_ENTRY(do_csum)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,2,16,0,16
+       .rotr word1[4], word2[4],result1[LOAD_LATENCY+2],result2[LOAD_LATENCY+2]
+       .rotp p[PIPE_DEPTH], pC1[2], pC2[2]
+       mov ret0=r0             // in case we have zero length
+       cmp.lt p0,p6=r0,len     // check for zero length or negative (32bit len)
+       ;;
+       add tmp1=buf,len        // last byte's address
+       .save pr, saved_pr
+       mov saved_pr=pr         // preserve predicates (rotation)
+(p6)   br.ret.spnt.many rp     // return if zero or negative length
+
+       mov hmask=-1            // initialize head mask
+       tbit.nz p15,p0=buf,0    // is buf an odd address?
+       and first1=-8,buf       // 8-byte align down address of first1 element
+
+       and firstoff=7,buf      // how many bytes off for first1 element
+       mov tmask=-1            // initialize tail mask
+
+       ;;
+       adds tmp2=-1,tmp1       // last-1
+       and lastoff=7,tmp1      // how many bytes off for last element
+       ;;
+       sub tmp1=8,lastoff      // complement to lastoff
+       and last=-8,tmp2        // address of word containing last byte
+       ;;
+       sub tmp3=last,first1    // tmp3=distance from first1 to last
+       .save ar.lc, saved_lc
+       mov saved_lc=ar.lc      // save lc
+       cmp.eq p8,p9=last,first1        // everything fits in one word ?
+
+       ld8 firstval=[first1],8 // load, ahead of time, "first1" word
+       and tmp1=7, tmp1        // make sure that if tmp1==8 -> tmp1=0
+       shl tmp2=firstoff,3     // number of bits
+       ;;
+(p9)   ld8 lastval=[last]      // load, ahead of time, "last" word, if needed
+       shl tmp1=tmp1,3         // number of bits
+(p9)   adds tmp3=-8,tmp3       // effectively loaded
+       ;;
+(p8)   mov lastval=r0          // we don't need lastval if first1==last
+       shl hmask=hmask,tmp2    // build head mask, mask off [0,first1off[
+       shr.u tmask=tmask,tmp1  // build tail mask, mask off ]8,lastoff]
+       ;;
+       .body
+#define count tmp3
+
+(p8)   and hmask=hmask,tmask   // apply tail mask to head mask if 1 word only
+(p9)   and word2[0]=lastval,tmask      // mask last it as appropriate
+       shr.u count=count,3     // how many 8-byte?
+       ;;
+       // If count is odd, finish this 8-byte word so that we can
+       // load two back-to-back 8-byte words per loop thereafter.
+       and word1[0]=firstval,hmask     // and mask it as appropriate
+       tbit.nz p10,p11=count,0         // if (count is odd)
+       ;;
+(p8)   mov result1[0]=word1[0]
+(p9)   add result1[0]=word1[0],word2[0]
+       ;;
+       cmp.ltu p6,p0=result1[0],word1[0]       // check the carry
+       cmp.eq.or.andcm p8,p0=0,count           // exit if zero 8-byte
+       ;;
+(p6)   adds result1[0]=1,result1[0]
+(p8)   br.cond.dptk .do_csum_exit      // if (within an 8-byte word)
+(p11)  br.cond.dptk .do_csum16         // if (count is even)
+
+       // Here count is odd.
+       ld8 word1[1]=[first1],8         // load an 8-byte word
+       cmp.eq p9,p10=1,count           // if (count == 1)
+       adds count=-1,count             // loaded an 8-byte word
+       ;;
+       add result1[0]=result1[0],word1[1]
+       ;;
+       cmp.ltu p6,p0=result1[0],word1[1]
+       ;;
+(p6)   adds result1[0]=1,result1[0]
+(p9)   br.cond.sptk .do_csum_exit      // if (count == 1) exit
+       // Fall through to caluculate the checksum, feeding result1[0] as
+       // the initial value in result1[0].
+       //
+       // Calculate the checksum loading two 8-byte words per loop.
+       //
+.do_csum16:
+       add first2=8,first1
+       shr.u count=count,1     // we do 16 bytes per loop
+       ;;
+       adds count=-1,count
+       mov carry1=r0
+       mov carry2=r0
+       brp.loop.imp 1f,2f
+       ;;
+       mov ar.ec=PIPE_DEPTH
+       mov ar.lc=count // set lc
+       mov pr.rot=1<<16
+       // result1[0] must be initialized in advance.
+       mov result2[0]=r0
+       ;;
+       .align 32
+1:
+(ELD_1)        cmp.ltu pC1[0],p0=result1[LOAD_LATENCY],word1[LOAD_LATENCY+1]
+(pC1[1])adds carry1=1,carry1
+(ELD_1)        cmp.ltu pC2[0],p0=result2[LOAD_LATENCY],word2[LOAD_LATENCY+1]
+(pC2[1])adds carry2=1,carry2
+(ELD)  add result1[LOAD_LATENCY-1]=result1[LOAD_LATENCY],word1[LOAD_LATENCY]
+(ELD)  add result2[LOAD_LATENCY-1]=result2[LOAD_LATENCY],word2[LOAD_LATENCY]
+2:
+(p[0]) ld8 word1[0]=[first1],16
+(p[0]) ld8 word2[0]=[first2],16
+       br.ctop.sptk 1b
+       ;;
+       // Since len is a 32-bit value, carry cannot be larger than a 64-bit 
value.
+(pC1[1])adds carry1=1,carry1   // since we miss the last one
+(pC2[1])adds carry2=1,carry2
+       ;;
+       add result1[LOAD_LATENCY+1]=result1[LOAD_LATENCY+1],carry1
+       add result2[LOAD_LATENCY+1]=result2[LOAD_LATENCY+1],carry2
+       ;;
+       cmp.ltu p6,p0=result1[LOAD_LATENCY+1],carry1
+       cmp.ltu p7,p0=result2[LOAD_LATENCY+1],carry2
+       ;;
+(p6)   adds result1[LOAD_LATENCY+1]=1,result1[LOAD_LATENCY+1]
+(p7)   adds result2[LOAD_LATENCY+1]=1,result2[LOAD_LATENCY+1]
+       ;;
+       add result1[0]=result1[LOAD_LATENCY+1],result2[LOAD_LATENCY+1]
+       ;;
+       cmp.ltu p6,p0=result1[0],result2[LOAD_LATENCY+1]
+       ;;
+(p6)   adds result1[0]=1,result1[0]
+       ;;
+.do_csum_exit:
+       //
+       // now fold 64 into 16 bits taking care of carry
+       // that's not very good because it has lots of sequentiality
+       //
+       mov tmp3=0xffff
+       zxt4 tmp1=result1[0]
+       shr.u tmp2=result1[0],32
+       ;;
+       add result1[0]=tmp1,tmp2
+       ;;
+       and tmp1=result1[0],tmp3
+       shr.u tmp2=result1[0],16
+       ;;
+       add result1[0]=tmp1,tmp2
+       ;;
+       and tmp1=result1[0],tmp3
+       shr.u tmp2=result1[0],16
+       ;;
+       add result1[0]=tmp1,tmp2
+       ;;
+       and tmp1=result1[0],tmp3
+       shr.u tmp2=result1[0],16
+       ;;
+       add ret0=tmp1,tmp2
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       // if buf was odd then swap bytes
+       mov ar.pfs=saved_pfs            // restore ar.ec
+(p15)  mux1 ret0=ret0,@rev             // reverse word
+       ;;
+       mov ar.lc=saved_lc
+(p15)  shr.u ret0=ret0,64-16   // + shift back to position = swap bytes
+       br.ret.sptk.many rp
+
+//     I (Jun Nakajima) wrote an equivalent code (see below), but it was
+//     not much better than the original. So keep the original there so that
+//     someone else can challenge.
+//
+//     shr.u word1[0]=result1[0],32
+//     zxt4 result1[0]=result1[0]
+//     ;;
+//     add result1[0]=result1[0],word1[0]
+//     ;;
+//     zxt2 result2[0]=result1[0]
+//     extr.u word1[0]=result1[0],16,16
+//     shr.u carry1=result1[0],32
+//     ;;
+//     add result2[0]=result2[0],word1[0]
+//     ;;
+//     add result2[0]=result2[0],carry1
+//     ;;
+//     extr.u ret0=result2[0],16,16
+//     ;;
+//     add ret0=ret0,result2[0]
+//     ;;
+//     zxt2 ret0=ret0
+//     mov ar.pfs=saved_pfs             // restore ar.ec
+//     mov pr=saved_pr,0xffffffffffff0000
+//     ;;
+//     // if buf was odd then swap bytes
+//     mov ar.lc=saved_lc
+//(p15)        mux1 ret0=ret0,@rev             // reverse word
+//     ;;
+//(p15)        shr.u ret0=ret0,64-16   // + shift back to position = swap bytes
+//     br.ret.sptk.many rp
+
+END(do_csum)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/flush.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/flush.S   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,39 @@
+/*
+ * Cache flushing routines.
+ *
+ * Copyright (C) 1999-2001 Hewlett-Packard Co
+ * Copyright (C) 1999-2001 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#include <asm/asmmacro.h>
+#include <asm/page.h>
+
+       /*
+        * flush_icache_range(start,end)
+        *      Must flush range from start to end-1 but nothing else (need to
+        *      be careful not to touch addresses that may be unmapped).
+        */
+GLOBAL_ENTRY(flush_icache_range)
+       .prologue
+       alloc r2=ar.pfs,2,0,0,0
+       sub r8=in1,in0,1
+       ;;
+       shr.u r8=r8,5                   // we flush 32 bytes per iteration
+       .save ar.lc, r3
+       mov r3=ar.lc                    // save ar.lc
+       ;;
+
+       .body
+
+       mov ar.lc=r8
+       ;;
+.Loop: fc in0                          // issuable on M0 only
+       add in0=32,in0
+       br.cloop.sptk.few .Loop
+       ;;
+       sync.i
+       ;;
+       srlz.i
+       ;;
+       mov ar.lc=r3                    // restore ar.lc
+       br.ret.sptk.many rp
+END(flush_icache_range)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/idiv32.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/idiv32.S  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,83 @@
+/*
+ * Copyright (C) 2000 Hewlett-Packard Co
+ * Copyright (C) 2000 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 32-bit integer division.
+ *
+ * This code is based on the application note entitled "Divide, Square Root
+ * and Remainder Algorithms for the IA-64 Architecture".  This document
+ * is available as Intel document number 248725-002 or via the web at
+ * http://developer.intel.com/software/opensource/numerics/
+ *
+ * For more details on the theory behind these algorithms, see "IA-64
+ * and Elementary Functions" by Peter Markstein; HP Professional Books
+ * (http://www.hp.com/go/retailbooks/)
+ */
+
+#include <asm/asmmacro.h>
+
+#ifdef MODULO
+# define OP    mod
+#else
+# define OP    div
+#endif
+
+#ifdef UNSIGNED
+# define SGN   u
+# define EXTEND        zxt4
+# define INT_TO_FP(a,b)        fcvt.xuf.s1 a=b
+# define FP_TO_INT(a,b)        fcvt.fxu.trunc.s1 a=b
+#else
+# define SGN
+# define EXTEND        sxt4
+# define INT_TO_FP(a,b)        fcvt.xf a=b
+# define FP_TO_INT(a,b)        fcvt.fx.trunc.s1 a=b
+#endif
+
+#define PASTE1(a,b)    a##b
+#define PASTE(a,b)     PASTE1(a,b)
+#define NAME           PASTE(PASTE(__,SGN),PASTE(OP,si3))
+
+GLOBAL_ENTRY(NAME)
+       .regstk 2,0,0,0
+       // Transfer inputs to FP registers.
+       mov r2 = 0xffdd                 // r2 = -34 + 65535 (fp reg format bias)
+       EXTEND in0 = in0                // in0 = a
+       EXTEND in1 = in1                // in1 = b
+       ;;
+       setf.sig f8 = in0
+       setf.sig f9 = in1
+#ifdef MODULO
+       sub in1 = r0, in1               // in1 = -b
+#endif
+       ;;
+       // Convert the inputs to FP, to avoid FP software-assist faults.
+       INT_TO_FP(f8, f8)
+       INT_TO_FP(f9, f9)
+       ;;
+       setf.exp f7 = r2                // f7 = 2^-34
+       frcpa.s1 f6, p6 = f8, f9        // y0 = frcpa(b)
+       ;;
+(p6)   fmpy.s1 f8 = f8, f6             // q0 = a*y0
+(p6)   fnma.s1 f6 = f9, f6, f1         // e0 = -b*y0 + 1 
+       ;;
+#ifdef MODULO
+       setf.sig f9 = in1               // f9 = -b
+#endif
+(p6)   fma.s1 f8 = f6, f8, f8          // q1 = e0*q0 + q0
+(p6)   fma.s1 f6 = f6, f6, f7          // e1 = e0*e0 + 2^-34
+       ;;
+#ifdef MODULO
+       setf.sig f7 = in0
+#endif
+(p6)   fma.s1 f6 = f6, f8, f8          // q2 = e1*q1 + q1
+       ;;
+       FP_TO_INT(f6, f6)               // q = trunc(q2)
+       ;;
+#ifdef MODULO
+       xma.l f6 = f6, f9, f7           // r = q*(-b) + a
+       ;;
+#endif
+       getf.sig r8 = f6                // transfer result to result register
+       br.ret.sptk.many rp
+END(NAME)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/idiv64.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/idiv64.S  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 1999-2000 Hewlett-Packard Co
+ * Copyright (C) 1999-2000 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 64-bit integer division.
+ *
+ * This code is based on the application note entitled "Divide, Square Root
+ * and Remainder Algorithms for the IA-64 Architecture".  This document
+ * is available as Intel document number 248725-002 or via the web at
+ * http://developer.intel.com/software/opensource/numerics/
+ *
+ * For more details on the theory behind these algorithms, see "IA-64
+ * and Elementary Functions" by Peter Markstein; HP Professional Books
+ * (http://www.hp.com/go/retailbooks/)
+ */
+
+#include <asm/asmmacro.h>
+
+#ifdef MODULO
+# define OP    mod
+#else
+# define OP    div
+#endif
+
+#ifdef UNSIGNED
+# define SGN   u
+# define INT_TO_FP(a,b)        fcvt.xuf.s1 a=b
+# define FP_TO_INT(a,b)        fcvt.fxu.trunc.s1 a=b
+#else
+# define SGN
+# define INT_TO_FP(a,b)        fcvt.xf a=b
+# define FP_TO_INT(a,b)        fcvt.fx.trunc.s1 a=b
+#endif
+
+#define PASTE1(a,b)    a##b
+#define PASTE(a,b)     PASTE1(a,b)
+#define NAME           PASTE(PASTE(__,SGN),PASTE(OP,di3))
+
+GLOBAL_ENTRY(NAME)
+       .regstk 2,0,0,0
+       // Transfer inputs to FP registers.
+       setf.sig f8 = in0
+       setf.sig f9 = in1
+       ;;
+       // Convert the inputs to FP, to avoid FP software-assist faults.
+       INT_TO_FP(f8, f8)
+       INT_TO_FP(f9, f9)
+       ;;
+       frcpa.s1 f11, p6 = f8, f9       // y0 = frcpa(b)
+       ;;
+(p6)   fmpy.s1 f7 = f8, f11            // q0 = a*y0
+(p6)   fnma.s1 f6 = f9, f11, f1        // e0 = -b*y0 + 1
+       ;;
+(p6)   fma.s1 f10 = f7, f6, f7         // q1 = q0*e0 + q0
+(p6)   fmpy.s1 f7 = f6, f6             // e1 = e0*e0
+       ;;
+#ifdef MODULO
+       sub in1 = r0, in1               // in1 = -b
+#endif
+(p6)   fma.s1 f10 = f10, f7, f10       // q2 = q1*e1 + q1
+(p6)   fma.s1 f6 = f11, f6, f11        // y1 = y0*e0 + y0
+       ;;
+(p6)   fma.s1 f6 = f6, f7, f6          // y2 = y1*e1 + y1
+(p6)   fnma.s1 f7 = f9, f10, f8        // r = -b*q2 + a
+       ;;
+#ifdef MODULO
+       setf.sig f8 = in0               // f8 = a
+       setf.sig f9 = in1               // f9 = -b
+#endif
+(p6)   fma.s1 f11 = f7, f6, f10        // q3 = r*y2 + q2
+       ;;
+       FP_TO_INT(f11, f11)             // q = trunc(q3)
+       ;;
+#ifdef MODULO
+       xma.l f11 = f11, f9, f8         // r = q*(-b) + a
+       ;;
+#endif
+       getf.sig r8 = f11               // transfer result to result register
+       br.ret.sptk.many rp
+END(NAME)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/io.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/io.c      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,165 @@
+#include <linux/config.h>
+#include <linux/module.h>
+#include <linux/types.h>
+
+#include <asm/io.h>
+
+/*
+ * Copy data from IO memory space to "real" memory space.
+ * This needs to be optimized.
+ */
+void memcpy_fromio(void *to, const volatile void __iomem *from, long count)
+{
+       char *dst = to;
+
+       while (count) {
+               count--;
+               *dst++ = readb(from++);
+       }
+}
+EXPORT_SYMBOL(memcpy_fromio);
+
+/*
+ * Copy data from "real" memory space to IO memory space.
+ * This needs to be optimized.
+ */
+void memcpy_toio(volatile void __iomem *to, const void *from, long count)
+{
+       const char *src = from;
+
+       while (count) {
+               count--;
+               writeb(*src++, to++);
+       }
+}
+EXPORT_SYMBOL(memcpy_toio);
+
+/*
+ * "memset" on IO memory space.
+ * This needs to be optimized.
+ */
+void memset_io(volatile void __iomem *dst, int c, long count)
+{
+       unsigned char ch = (char)(c & 0xff);
+
+       while (count) {
+               count--;
+               writeb(ch, dst);
+               dst++;
+       }
+}
+EXPORT_SYMBOL(memset_io);
+
+#ifdef CONFIG_IA64_GENERIC
+
+#undef __ia64_inb
+#undef __ia64_inw
+#undef __ia64_inl
+#undef __ia64_outb
+#undef __ia64_outw
+#undef __ia64_outl
+#undef __ia64_readb
+#undef __ia64_readw
+#undef __ia64_readl
+#undef __ia64_readq
+#undef __ia64_readb_relaxed
+#undef __ia64_readw_relaxed
+#undef __ia64_readl_relaxed
+#undef __ia64_readq_relaxed
+#undef __ia64_writeb
+#undef __ia64_writew
+#undef __ia64_writel
+#undef __ia64_writeq
+#undef __ia64_mmiowb
+
+unsigned int
+__ia64_inb (unsigned long port)
+{
+       return ___ia64_inb(port);
+}
+
+unsigned int
+__ia64_inw (unsigned long port)
+{
+       return ___ia64_inw(port);
+}
+
+unsigned int
+__ia64_inl (unsigned long port)
+{
+       return ___ia64_inl(port);
+}
+
+void
+__ia64_outb (unsigned char val, unsigned long port)
+{
+       ___ia64_outb(val, port);
+}
+
+void
+__ia64_outw (unsigned short val, unsigned long port)
+{
+       ___ia64_outw(val, port);
+}
+
+void
+__ia64_outl (unsigned int val, unsigned long port)
+{
+       ___ia64_outl(val, port);
+}
+
+unsigned char
+__ia64_readb (void __iomem *addr)
+{
+       return ___ia64_readb (addr);
+}
+
+unsigned short
+__ia64_readw (void __iomem *addr)
+{
+       return ___ia64_readw (addr);
+}
+
+unsigned int
+__ia64_readl (void __iomem *addr)
+{
+       return ___ia64_readl (addr);
+}
+
+unsigned long
+__ia64_readq (void __iomem *addr)
+{
+       return ___ia64_readq (addr);
+}
+
+unsigned char
+__ia64_readb_relaxed (void __iomem *addr)
+{
+       return ___ia64_readb (addr);
+}
+
+unsigned short
+__ia64_readw_relaxed (void __iomem *addr)
+{
+       return ___ia64_readw (addr);
+}
+
+unsigned int
+__ia64_readl_relaxed (void __iomem *addr)
+{
+       return ___ia64_readl (addr);
+}
+
+unsigned long
+__ia64_readq_relaxed (void __iomem *addr)
+{
+       return ___ia64_readq (addr);
+}
+
+void
+__ia64_mmiowb(void)
+{
+       ___ia64_mmiowb();
+}
+
+#endif /* CONFIG_IA64_GENERIC */
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/ip_fast_csum.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/ip_fast_csum.S    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,90 @@
+/*
+ * Optmized version of the ip_fast_csum() function
+ * Used for calculating IP header checksum
+ *
+ * Return: 16bit checksum, complemented
+ *
+ * Inputs:
+ *      in0: address of buffer to checksum (char *)
+ *      in1: length of the buffer (int)
+ *
+ * Copyright (C) 2002 Intel Corp.
+ * Copyright (C) 2002 Ken Chen <kenneth.w.chen@xxxxxxxxx>
+ */
+
+#include <asm/asmmacro.h>
+
+/*
+ * Since we know that most likely this function is called with buf aligned
+ * on 4-byte boundary and 20 bytes in length, we can execution rather quickly
+ * versus calling generic version of do_csum, which has lots of overhead in
+ * handling various alignments and sizes.  However, due to lack of constrains
+ * put on the function input argument, cases with alignment not on 4-byte or
+ * size not equal to 20 bytes will be handled by the generic do_csum function.
+ */
+
+#define in0    r32
+#define in1    r33
+#define ret0   r8
+
+GLOBAL_ENTRY(ip_fast_csum)
+       .prologue
+       .body
+       cmp.ne  p6,p7=5,in1     // size other than 20 byte?
+       and     r14=3,in0       // is it aligned on 4-byte?
+       add     r15=4,in0       // second source pointer
+       ;;
+       cmp.ne.or.andcm p6,p7=r14,r0
+       ;;
+(p7)   ld4     r20=[in0],8
+(p7)   ld4     r21=[r15],8
+(p6)   br.spnt .generic
+       ;;
+       ld4     r22=[in0],8
+       ld4     r23=[r15],8
+       ;;
+       ld4     r24=[in0]
+       add     r20=r20,r21
+       add     r22=r22,r23
+       ;;
+       add     r20=r20,r22
+       ;;
+       add     r20=r20,r24
+       ;;
+       shr.u   ret0=r20,16     // now need to add the carry
+       zxt2    r20=r20
+       ;;
+       add     r20=ret0,r20
+       ;;
+       shr.u   ret0=r20,16     // add carry again
+       zxt2    r20=r20
+       ;;
+       add     r20=ret0,r20
+       ;;
+       shr.u   ret0=r20,16
+       zxt2    r20=r20
+       ;;
+       add     r20=ret0,r20
+       ;;
+       andcm   ret0=-1,r20
+       .restore sp             // reset frame state
+       br.ret.sptk.many b0
+       ;;
+
+.generic:
+       .prologue
+       .save ar.pfs, r35
+       alloc   r35=ar.pfs,2,2,2,0
+       .save rp, r34
+       mov     r34=b0
+       .body
+       dep.z   out1=in1,2,30
+       mov     out0=in0
+       ;;
+       br.call.sptk.many b0=do_csum
+       ;;
+       andcm   ret0=-1,ret0
+       mov     ar.pfs=r35
+       mov     b0=r34
+       br.ret.sptk.many b0
+END(ip_fast_csum)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/memcpy.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/memcpy.S  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,301 @@
+/*
+ *
+ * Optimized version of the standard memcpy() function
+ *
+ * Inputs:
+ *     in0:    destination address
+ *     in1:    source address
+ *     in2:    number of bytes to copy
+ * Output:
+ *     no return value
+ *
+ * Copyright (C) 2000-2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#include <asm/asmmacro.h>
+
+GLOBAL_ENTRY(memcpy)
+
+#      define MEM_LAT  21              /* latency to memory */
+
+#      define dst      r2
+#      define src      r3
+#      define retval   r8
+#      define saved_pfs r9
+#      define saved_lc r10
+#      define saved_pr r11
+#      define cnt      r16
+#      define src2     r17
+#      define t0       r18
+#      define t1       r19
+#      define t2       r20
+#      define t3       r21
+#      define t4       r22
+#      define src_end  r23
+
+#      define N        (MEM_LAT + 4)
+#      define Nrot     ((N + 7) & ~7)
+
+       /*
+        * First, check if everything (src, dst, len) is a multiple of eight.  
If
+        * so, we handle everything with no taken branches (other than the loop
+        * itself) and a small icache footprint.  Otherwise, we jump off to
+        * the more general copy routine handling arbitrary
+        * sizes/alignment etc.
+        */
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,3,Nrot,0,Nrot
+       .save ar.lc, saved_lc
+       mov saved_lc=ar.lc
+       or t0=in0,in1
+       ;;
+
+       or t0=t0,in2
+       .save pr, saved_pr
+       mov saved_pr=pr
+
+       .body
+
+       cmp.eq p6,p0=in2,r0     // zero length?
+       mov retval=in0          // return dst
+(p6)   br.ret.spnt.many rp     // zero length, return immediately
+       ;;
+
+       mov dst=in0             // copy because of rotation
+       shr.u cnt=in2,3         // number of 8-byte words to copy
+       mov pr.rot=1<<16
+       ;;
+
+       adds cnt=-1,cnt         // br.ctop is repeat/until
+       cmp.gtu p7,p0=16,in2    // copying less than 16 bytes?
+       mov ar.ec=N
+       ;;
+
+       and t0=0x7,t0
+       mov ar.lc=cnt
+       ;;
+       cmp.ne p6,p0=t0,r0
+
+       mov src=in1             // copy because of rotation
+(p7)   br.cond.spnt.few .memcpy_short
+(p6)   br.cond.spnt.few .memcpy_long
+       ;;
+       nop.m   0
+       ;;
+       nop.m   0
+       nop.i   0
+       ;;
+       nop.m   0
+       ;;
+       .rotr val[N]
+       .rotp p[N]
+       .align 32
+1: { .mib
+(p[0]) ld8 val[0]=[src],8
+       nop.i 0
+       brp.loop.imp 1b, 2f
+}
+2: { .mfb
+(p[N-1])st8 [dst]=val[N-1],8
+       nop.f 0
+       br.ctop.dptk.few 1b
+}
+       ;;
+       mov ar.lc=saved_lc
+       mov pr=saved_pr,-1
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       /*
+        * Small (<16 bytes) unaligned copying is done via a simple 
byte-at-the-time
+        * copy loop.  This performs relatively poorly on Itanium, but it 
doesn't
+        * get used very often (gcc inlines small copies) and due to atomicity
+        * issues, we want to avoid read-modify-write of entire words.
+        */
+       .align 32
+.memcpy_short:
+       adds cnt=-1,in2         // br.ctop is repeat/until
+       mov ar.ec=MEM_LAT
+       brp.loop.imp 1f, 2f
+       ;;
+       mov ar.lc=cnt
+       ;;
+       nop.m   0
+       ;;
+       nop.m   0
+       nop.i   0
+       ;;
+       nop.m   0
+       ;;
+       nop.m   0
+       ;;
+       /*
+        * It is faster to put a stop bit in the loop here because it makes
+        * the pipeline shorter (and latency is what matters on short copies).
+        */
+       .align 32
+1: { .mib
+(p[0]) ld1 val[0]=[src],1
+       nop.i 0
+       brp.loop.imp 1b, 2f
+} ;;
+2: { .mfb
+(p[MEM_LAT-1])st1 [dst]=val[MEM_LAT-1],1
+       nop.f 0
+       br.ctop.dptk.few 1b
+} ;;
+       mov ar.lc=saved_lc
+       mov pr=saved_pr,-1
+       mov ar.pfs=saved_pfs
+       br.ret.sptk.many rp
+
+       /*
+        * Large (>= 16 bytes) copying is done in a fancy way.  Latency isn't
+        * an overriding concern here, but throughput is.  We first do
+        * sub-word copying until the destination is aligned, then we check
+        * if the source is also aligned.  If so, we do a simple load/store-loop
+        * until there are less than 8 bytes left over and then we do the tail,
+        * by storing the last few bytes using sub-word copying.  If the source
+        * is not aligned, we branch off to the non-congruent loop.
+        *
+        *   stage:   op:
+        *         0  ld
+        *         :
+        * MEM_LAT+3  shrp
+        * MEM_LAT+4  st
+        *
+        * On Itanium, the pipeline itself runs without stalls.  However,  
br.ctop
+        * seems to introduce an unavoidable bubble in the pipeline so the 
overall
+        * latency is 2 cycles/iteration.  This gives us a _copy_ throughput
+        * of 4 byte/cycle.  Still not bad.
+        */
+#      undef N
+#      undef Nrot
+#      define N        (MEM_LAT + 5)           /* number of stages */
+#      define Nrot     ((N+1 + 2 + 7) & ~7)    /* number of rotating regs */
+
+#define LOG_LOOP_SIZE  6
+
+.memcpy_long:
+       alloc t3=ar.pfs,3,Nrot,0,Nrot   // resize register frame
+       and t0=-8,src           // t0 = src & ~7
+       and t2=7,src            // t2 = src & 7
+       ;;
+       ld8 t0=[t0]             // t0 = 1st source word
+       adds src2=7,src         // src2 = (src + 7)
+       sub t4=r0,dst           // t4 = -dst
+       ;;
+       and src2=-8,src2        // src2 = (src + 7) & ~7
+       shl t2=t2,3             // t2 = 8*(src & 7)
+       shl t4=t4,3             // t4 = 8*(dst & 7)
+       ;;
+       ld8 t1=[src2]           // t1 = 1st source word if src is 8-byte 
aligned, 2nd otherwise
+       sub t3=64,t2            // t3 = 64-8*(src & 7)
+       shr.u t0=t0,t2
+       ;;
+       add src_end=src,in2
+       shl t1=t1,t3
+       mov pr=t4,0x38          // (p5,p4,p3)=(dst & 7)
+       ;;
+       or t0=t0,t1
+       mov cnt=r0
+       adds src_end=-1,src_end
+       ;;
+(p3)   st1 [dst]=t0,1
+(p3)   shr.u t0=t0,8
+(p3)   adds cnt=1,cnt
+       ;;
+(p4)   st2 [dst]=t0,2
+(p4)   shr.u t0=t0,16
+(p4)   adds cnt=2,cnt
+       ;;
+(p5)   st4 [dst]=t0,4
+(p5)   adds cnt=4,cnt
+       and src_end=-8,src_end  // src_end = last word of source buffer
+       ;;
+
+       // At this point, dst is aligned to 8 bytes and there at least 16-7=9 
bytes left to copy:
+
+1:{    add src=cnt,src                 // make src point to remainder of 
source buffer
+       sub cnt=in2,cnt                 // cnt = number of bytes left to copy
+       mov t4=ip
+  }    ;;
+       and src2=-8,src                 // align source pointer
+       adds t4=.memcpy_loops-1b,t4
+       mov ar.ec=N
+
+       and t0=7,src                    // t0 = src & 7
+       shr.u t2=cnt,3                  // t2 = number of 8-byte words left to 
copy
+       shl cnt=cnt,3                   // move bits 0-2 to 3-5
+       ;;
+
+       .rotr val[N+1], w[2]
+       .rotp p[N]
+
+       cmp.ne p6,p0=t0,r0              // is src aligned, too?
+       shl t0=t0,LOG_LOOP_SIZE         // t0 = 8*(src & 7)
+       adds t2=-1,t2                   // br.ctop is repeat/until
+       ;;
+       add t4=t0,t4
+       mov pr=cnt,0x38                 // set (p5,p4,p3) to # of bytes 
last-word bytes to copy
+       mov ar.lc=t2
+       ;;
+       nop.m   0
+       ;;
+       nop.m   0
+       nop.i   0
+       ;;
+       nop.m   0
+       ;;
+(p6)   ld8 val[1]=[src2],8             // prime the pump...
+       mov b6=t4
+       br.sptk.few b6
+       ;;
+
+.memcpy_tail:
+       // At this point, (p5,p4,p3) are set to the number of bytes left to 
copy (which is
+       // less than 8) and t0 contains the last few bytes of the src buffer:
+(p5)   st4 [dst]=t0,4
+(p5)   shr.u t0=t0,32
+       mov ar.lc=saved_lc
+       ;;
+(p4)   st2 [dst]=t0,2
+(p4)   shr.u t0=t0,16
+       mov ar.pfs=saved_pfs
+       ;;
+(p3)   st1 [dst]=t0
+       mov pr=saved_pr,-1
+       br.ret.sptk.many rp
+
+///////////////////////////////////////////////////////
+       .align 64
+
+#define COPY(shift,index)                                                      
                \
+ 1: { .mib                                                                     
                \
+       (p[0])          ld8 val[0]=[src2],8;                                    
                \
+       (p[MEM_LAT+3])  shrp w[0]=val[MEM_LAT+3],val[MEM_LAT+4-index],shift;    
                \
+                       brp.loop.imp 1b, 2f                                     
                \
+    };                                                                         
                \
+ 2: { .mfb                                                                     
                \
+       (p[MEM_LAT+4])  st8 [dst]=w[1],8;                                       
                \
+                       nop.f 0;                                                
                \
+                       br.ctop.dptk.few 1b;                                    
                \
+    };                                                                         
                \
+                       ;;                                                      
                \
+                       ld8 val[N-1]=[src_end]; /* load last word (may be same 
as val[N]) */    \
+                       ;;                                                      
                \
+                       shrp t0=val[N-1],val[N-index],shift;                    
                \
+                       br .memcpy_tail
+.memcpy_loops:
+       COPY(0, 1) /* no point special casing this---it doesn't go any faster 
without shrp */
+       COPY(8, 0)
+       COPY(16, 0)
+       COPY(24, 0)
+       COPY(32, 0)
+       COPY(40, 0)
+       COPY(48, 0)
+       COPY(56, 0)
+
+END(memcpy)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/memcpy_mck.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/memcpy_mck.S      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,661 @@
+/*
+ * Itanium 2-optimized version of memcpy and copy_user function
+ *
+ * Inputs:
+ *     in0:    destination address
+ *     in1:    source address
+ *     in2:    number of bytes to copy
+ * Output:
+ *     0 if success, or number of byte NOT copied if error occurred.
+ *
+ * Copyright (C) 2002 Intel Corp.
+ * Copyright (C) 2002 Ken Chen <kenneth.w.chen@xxxxxxxxx>
+ */
+#include <linux/config.h>
+#include <asm/asmmacro.h>
+#include <asm/page.h>
+
+#define EK(y...) EX(y)
+
+/* McKinley specific optimization */
+
+#define retval         r8
+#define saved_pfs      r31
+#define saved_lc       r10
+#define saved_pr       r11
+#define saved_in0      r14
+#define saved_in1      r15
+#define saved_in2      r16
+
+#define src0           r2
+#define src1           r3
+#define dst0           r17
+#define dst1           r18
+#define cnt            r9
+
+/* r19-r30 are temp for each code section */
+#define PREFETCH_DIST  8
+#define src_pre_mem    r19
+#define dst_pre_mem    r20
+#define src_pre_l2     r21
+#define dst_pre_l2     r22
+#define t1             r23
+#define t2             r24
+#define t3             r25
+#define t4             r26
+#define t5             t1      // alias!
+#define t6             t2      // alias!
+#define t7             t3      // alias!
+#define n8             r27
+#define t9             t5      // alias!
+#define t10            t4      // alias!
+#define t11            t7      // alias!
+#define t12            t6      // alias!
+#define t14            t10     // alias!
+#define t13            r28
+#define t15            r29
+#define tmp            r30
+
+/* defines for long_copy block */
+#define        A       0
+#define B      (PREFETCH_DIST)
+#define C      (B + PREFETCH_DIST)
+#define D      (C + 1)
+#define N      (D + 1)
+#define Nrot   ((N + 7) & ~7)
+
+/* alias */
+#define in0            r32
+#define in1            r33
+#define in2            r34
+
+GLOBAL_ENTRY(memcpy)
+       and     r28=0x7,in0
+       and     r29=0x7,in1
+       mov     f6=f0
+       br.cond.sptk .common_code
+       ;;
+GLOBAL_ENTRY(__copy_user)
+       .prologue
+// check dest alignment
+       and     r28=0x7,in0
+       and     r29=0x7,in1
+       mov     f6=f1
+       mov     saved_in0=in0   // save dest pointer
+       mov     saved_in1=in1   // save src pointer
+       mov     saved_in2=in2   // save len
+       ;;
+.common_code:
+       cmp.gt  p15,p0=8,in2    // check for small size
+       cmp.ne  p13,p0=0,r28    // check dest alignment
+       cmp.ne  p14,p0=0,r29    // check src alignment
+       add     src0=0,in1
+       sub     r30=8,r28       // for .align_dest
+       mov     retval=r0       // initialize return value
+       ;;
+       add     dst0=0,in0
+       add     dst1=1,in0      // dest odd index
+       cmp.le  p6,p0 = 1,r30   // for .align_dest
+(p15)  br.cond.dpnt .memcpy_short
+(p13)  br.cond.dpnt .align_dest
+(p14)  br.cond.dpnt .unaligned_src
+       ;;
+
+// both dest and src are aligned on 8-byte boundary
+.aligned_src:
+       .save ar.pfs, saved_pfs
+       alloc   saved_pfs=ar.pfs,3,Nrot-3,0,Nrot
+       .save pr, saved_pr
+       mov     saved_pr=pr
+
+       shr.u   cnt=in2,7       // this much cache line
+       ;;
+       cmp.lt  p6,p0=2*PREFETCH_DIST,cnt
+       cmp.lt  p7,p8=1,cnt
+       .save ar.lc, saved_lc
+       mov     saved_lc=ar.lc
+       .body
+       add     cnt=-1,cnt
+       add     src_pre_mem=0,in1       // prefetch src pointer
+       add     dst_pre_mem=0,in0       // prefetch dest pointer
+       ;;
+(p7)   mov     ar.lc=cnt       // prefetch count
+(p8)   mov     ar.lc=r0
+(p6)   br.cond.dpnt .long_copy
+       ;;
+
+.prefetch:
+       lfetch.fault      [src_pre_mem], 128
+       lfetch.fault.excl [dst_pre_mem], 128
+       br.cloop.dptk.few .prefetch
+       ;;
+
+.medium_copy:
+       and     tmp=31,in2      // copy length after iteration
+       shr.u   r29=in2,5       // number of 32-byte iteration
+       add     dst1=8,dst0     // 2nd dest pointer
+       ;;
+       add     cnt=-1,r29      // ctop iteration adjustment
+       cmp.eq  p10,p0=r29,r0   // do we really need to loop?
+       add     src1=8,src0     // 2nd src pointer
+       cmp.le  p6,p0=8,tmp
+       ;;
+       cmp.le  p7,p0=16,tmp
+       mov     ar.lc=cnt       // loop setup
+       cmp.eq  p16,p17 = r0,r0
+       mov     ar.ec=2
+(p10)  br.dpnt.few .aligned_src_tail
+       ;;
+       TEXT_ALIGN(32)
+1:
+EX(.ex_handler, (p16)  ld8     r34=[src0],16)
+EK(.ex_handler, (p16)  ld8     r38=[src1],16)
+EX(.ex_handler, (p17)  st8     [dst0]=r33,16)
+EK(.ex_handler, (p17)  st8     [dst1]=r37,16)
+       ;;
+EX(.ex_handler, (p16)  ld8     r32=[src0],16)
+EK(.ex_handler, (p16)  ld8     r36=[src1],16)
+EX(.ex_handler, (p16)  st8     [dst0]=r34,16)
+EK(.ex_handler, (p16)  st8     [dst1]=r38,16)
+       br.ctop.dptk.few 1b
+       ;;
+
+.aligned_src_tail:
+EX(.ex_handler, (p6)   ld8     t1=[src0])
+       mov     ar.lc=saved_lc
+       mov     ar.pfs=saved_pfs
+EX(.ex_hndlr_s, (p7)   ld8     t2=[src1],8)
+       cmp.le  p8,p0=24,tmp
+       and     r21=-8,tmp
+       ;;
+EX(.ex_hndlr_s, (p8)   ld8     t3=[src1])
+EX(.ex_handler, (p6)   st8     [dst0]=t1)      // store byte 1
+       and     in2=7,tmp       // remaining length
+EX(.ex_hndlr_d, (p7)   st8     [dst1]=t2,8)    // store byte 2
+       add     src0=src0,r21   // setting up src pointer
+       add     dst0=dst0,r21   // setting up dest pointer
+       ;;
+EX(.ex_handler, (p8)   st8     [dst1]=t3)      // store byte 3
+       mov     pr=saved_pr,-1
+       br.dptk.many .memcpy_short
+       ;;
+
+/* code taken from copy_page_mck */
+.long_copy:
+       .rotr v[2*PREFETCH_DIST]
+       .rotp p[N]
+
+       mov src_pre_mem = src0
+       mov pr.rot = 0x10000
+       mov ar.ec = 1                           // special unrolled loop
+
+       mov dst_pre_mem = dst0
+
+       add src_pre_l2 = 8*8, src0
+       add dst_pre_l2 = 8*8, dst0
+       ;;
+       add src0 = 8, src_pre_mem               // first t1 src
+       mov ar.lc = 2*PREFETCH_DIST - 1
+       shr.u cnt=in2,7                         // number of lines
+       add src1 = 3*8, src_pre_mem             // first t3 src
+       add dst0 = 8, dst_pre_mem               // first t1 dst
+       add dst1 = 3*8, dst_pre_mem             // first t3 dst
+       ;;
+       and tmp=127,in2                         // remaining bytes after this 
block
+       add cnt = -(2*PREFETCH_DIST) - 1, cnt
+       // same as .line_copy loop, but with all predicated-off instructions 
removed:
+.prefetch_loop:
+EX(.ex_hndlr_lcpy_1, (p[A])    ld8 v[A] = [src_pre_mem], 128)          // M0
+EK(.ex_hndlr_lcpy_1, (p[B])    st8 [dst_pre_mem] = v[B], 128)          // M2
+       br.ctop.sptk .prefetch_loop
+       ;;
+       cmp.eq p16, p0 = r0, r0                 // reset p16 to 1
+       mov ar.lc = cnt
+       mov ar.ec = N                           // # of stages in pipeline
+       ;;
+.line_copy:
+EX(.ex_handler,        (p[D])  ld8 t2 = [src0], 3*8)                   // M0
+EK(.ex_handler,        (p[D])  ld8 t4 = [src1], 3*8)                   // M1
+EX(.ex_handler_lcpy,   (p[B])  st8 [dst_pre_mem] = v[B], 128)          // M2 
prefetch dst from memory
+EK(.ex_handler_lcpy,   (p[D])  st8 [dst_pre_l2] = n8, 128)             // M3 
prefetch dst from L2
+       ;;
+EX(.ex_handler_lcpy,   (p[A])  ld8 v[A] = [src_pre_mem], 128)          // M0 
prefetch src from memory
+EK(.ex_handler_lcpy,   (p[C])  ld8 n8 = [src_pre_l2], 128)             // M1 
prefetch src from L2
+EX(.ex_handler,        (p[D])  st8 [dst0] =  t1, 8)                    // M2
+EK(.ex_handler,        (p[D])  st8 [dst1] =  t3, 8)                    // M3
+       ;;
+EX(.ex_handler,        (p[D])  ld8  t5 = [src0], 8)
+EK(.ex_handler,        (p[D])  ld8  t7 = [src1], 3*8)
+EX(.ex_handler,        (p[D])  st8 [dst0] =  t2, 3*8)
+EK(.ex_handler,        (p[D])  st8 [dst1] =  t4, 3*8)
+       ;;
+EX(.ex_handler,        (p[D])  ld8  t6 = [src0], 3*8)
+EK(.ex_handler,        (p[D])  ld8 t10 = [src1], 8)
+EX(.ex_handler,        (p[D])  st8 [dst0] =  t5, 8)
+EK(.ex_handler,        (p[D])  st8 [dst1] =  t7, 3*8)
+       ;;
+EX(.ex_handler,        (p[D])  ld8  t9 = [src0], 3*8)
+EK(.ex_handler,        (p[D])  ld8 t11 = [src1], 3*8)
+EX(.ex_handler,        (p[D])  st8 [dst0] =  t6, 3*8)
+EK(.ex_handler,        (p[D])  st8 [dst1] = t10, 8)
+       ;;
+EX(.ex_handler,        (p[D])  ld8 t12 = [src0], 8)
+EK(.ex_handler,        (p[D])  ld8 t14 = [src1], 8)
+EX(.ex_handler,        (p[D])  st8 [dst0] =  t9, 3*8)
+EK(.ex_handler,        (p[D])  st8 [dst1] = t11, 3*8)
+       ;;
+EX(.ex_handler,        (p[D])  ld8 t13 = [src0], 4*8)
+EK(.ex_handler,        (p[D])  ld8 t15 = [src1], 4*8)
+EX(.ex_handler,        (p[D])  st8 [dst0] = t12, 8)
+EK(.ex_handler,        (p[D])  st8 [dst1] = t14, 8)
+       ;;
+EX(.ex_handler,        (p[C])  ld8  t1 = [src0], 8)
+EK(.ex_handler,        (p[C])  ld8  t3 = [src1], 8)
+EX(.ex_handler,        (p[D])  st8 [dst0] = t13, 4*8)
+EK(.ex_handler,        (p[D])  st8 [dst1] = t15, 4*8)
+       br.ctop.sptk .line_copy
+       ;;
+
+       add dst0=-8,dst0
+       add src0=-8,src0
+       mov in2=tmp
+       .restore sp
+       br.sptk.many .medium_copy
+       ;;
+
+#define BLOCK_SIZE     128*32
+#define blocksize      r23
+#define curlen         r24
+
+// dest is on 8-byte boundary, src is not. We need to do
+// ld8-ld8, shrp, then st8.  Max 8 byte copy per cycle.
+.unaligned_src:
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc   saved_pfs=ar.pfs,3,5,0,8
+       .save ar.lc, saved_lc
+       mov     saved_lc=ar.lc
+       .save pr, saved_pr
+       mov     saved_pr=pr
+       .body
+.4k_block:
+       mov     saved_in0=dst0  // need to save all input arguments
+       mov     saved_in2=in2
+       mov     blocksize=BLOCK_SIZE
+       ;;
+       cmp.lt  p6,p7=blocksize,in2
+       mov     saved_in1=src0
+       ;;
+(p6)   mov     in2=blocksize
+       ;;
+       shr.u   r21=in2,7       // this much cache line
+       shr.u   r22=in2,4       // number of 16-byte iteration
+       and     curlen=15,in2   // copy length after iteration
+       and     r30=7,src0      // source alignment
+       ;;
+       cmp.lt  p7,p8=1,r21
+       add     cnt=-1,r21
+       ;;
+
+       add     src_pre_mem=0,src0      // prefetch src pointer
+       add     dst_pre_mem=0,dst0      // prefetch dest pointer
+       and     src0=-8,src0            // 1st src pointer
+(p7)   mov     ar.lc = r21
+(p8)   mov     ar.lc = r0
+       ;;
+       TEXT_ALIGN(32)
+1:     lfetch.fault      [src_pre_mem], 128
+       lfetch.fault.excl [dst_pre_mem], 128
+       br.cloop.dptk.few 1b
+       ;;
+
+       shladd  dst1=r22,3,dst0 // 2nd dest pointer
+       shladd  src1=r22,3,src0 // 2nd src pointer
+       cmp.eq  p8,p9=r22,r0    // do we really need to loop?
+       cmp.le  p6,p7=8,curlen; // have at least 8 byte remaining?
+       add     cnt=-1,r22      // ctop iteration adjustment
+       ;;
+EX(.ex_handler, (p9)   ld8     r33=[src0],8)   // loop primer
+EK(.ex_handler, (p9)   ld8     r37=[src1],8)
+(p8)   br.dpnt.few .noloop
+       ;;
+
+// The jump address is calculated based on src alignment. The COPYU
+// macro below need to confine its size to power of two, so an entry
+// can be caulated using shl instead of an expensive multiply. The
+// size is then hard coded by the following #define to match the
+// actual size.  This make it somewhat tedious when COPYU macro gets
+// changed and this need to be adjusted to match.
+#define LOOP_SIZE 6
+1:
+       mov     r29=ip          // jmp_table thread
+       mov     ar.lc=cnt
+       ;;
+       add     r29=.jump_table - 1b - (.jmp1-.jump_table), r29
+       shl     r28=r30, LOOP_SIZE      // jmp_table thread
+       mov     ar.ec=2         // loop setup
+       ;;
+       add     r29=r29,r28             // jmp_table thread
+       cmp.eq  p16,p17=r0,r0
+       ;;
+       mov     b6=r29                  // jmp_table thread
+       ;;
+       br.cond.sptk.few b6
+
+// for 8-15 byte case
+// We will skip the loop, but need to replicate the side effect
+// that the loop produces.
+.noloop:
+EX(.ex_handler, (p6)   ld8     r37=[src1],8)
+       add     src0=8,src0
+(p6)   shl     r25=r30,3
+       ;;
+EX(.ex_handler, (p6)   ld8     r27=[src1])
+(p6)   shr.u   r28=r37,r25
+(p6)   sub     r26=64,r25
+       ;;
+(p6)   shl     r27=r27,r26
+       ;;
+(p6)   or      r21=r28,r27
+
+.unaligned_src_tail:
+/* check if we have more than blocksize to copy, if so go back */
+       cmp.gt  p8,p0=saved_in2,blocksize
+       ;;
+(p8)   add     dst0=saved_in0,blocksize
+(p8)   add     src0=saved_in1,blocksize
+(p8)   sub     in2=saved_in2,blocksize
+(p8)   br.dpnt .4k_block
+       ;;
+
+/* we have up to 15 byte to copy in the tail.
+ * part of work is already done in the jump table code
+ * we are at the following state.
+ * src side:
+ * 
+ *   xxxxxx xx                   <----- r21 has xxxxxxxx already
+ * -------- -------- --------
+ * 0        8        16
+ *          ^
+ *          |
+ *          src1
+ * 
+ * dst
+ * -------- -------- --------
+ * ^
+ * |
+ * dst1
+ */
+EX(.ex_handler, (p6)   st8     [dst1]=r21,8)   // more than 8 byte to copy
+(p6)   add     curlen=-8,curlen        // update length
+       mov     ar.pfs=saved_pfs
+       ;;
+       mov     ar.lc=saved_lc
+       mov     pr=saved_pr,-1
+       mov     in2=curlen      // remaining length
+       mov     dst0=dst1       // dest pointer
+       add     src0=src1,r30   // forward by src alignment
+       ;;
+
+// 7 byte or smaller.
+.memcpy_short:
+       cmp.le  p8,p9   = 1,in2
+       cmp.le  p10,p11 = 2,in2
+       cmp.le  p12,p13 = 3,in2
+       cmp.le  p14,p15 = 4,in2
+       add     src1=1,src0     // second src pointer
+       add     dst1=1,dst0     // second dest pointer
+       ;;
+
+EX(.ex_handler_short, (p8)     ld1     t1=[src0],2)
+EK(.ex_handler_short, (p10)    ld1     t2=[src1],2)
+(p9)   br.ret.dpnt rp          // 0 byte copy
+       ;;
+
+EX(.ex_handler_short, (p8)     st1     [dst0]=t1,2)
+EK(.ex_handler_short, (p10)    st1     [dst1]=t2,2)
+(p11)  br.ret.dpnt rp          // 1 byte copy
+
+EX(.ex_handler_short, (p12)    ld1     t3=[src0],2)
+EK(.ex_handler_short, (p14)    ld1     t4=[src1],2)
+(p13)  br.ret.dpnt rp          // 2 byte copy
+       ;;
+
+       cmp.le  p6,p7   = 5,in2
+       cmp.le  p8,p9   = 6,in2
+       cmp.le  p10,p11 = 7,in2
+
+EX(.ex_handler_short, (p12)    st1     [dst0]=t3,2)
+EK(.ex_handler_short, (p14)    st1     [dst1]=t4,2)
+(p15)  br.ret.dpnt rp          // 3 byte copy
+       ;;
+
+EX(.ex_handler_short, (p6)     ld1     t5=[src0],2)
+EK(.ex_handler_short, (p8)     ld1     t6=[src1],2)
+(p7)   br.ret.dpnt rp          // 4 byte copy
+       ;;
+
+EX(.ex_handler_short, (p6)     st1     [dst0]=t5,2)
+EK(.ex_handler_short, (p8)     st1     [dst1]=t6,2)
+(p9)   br.ret.dptk rp          // 5 byte copy
+
+EX(.ex_handler_short, (p10)    ld1     t7=[src0],2)
+(p11)  br.ret.dptk rp          // 6 byte copy
+       ;;
+
+EX(.ex_handler_short, (p10)    st1     [dst0]=t7,2)
+       br.ret.dptk rp          // done all cases
+
+
+/* Align dest to nearest 8-byte boundary. We know we have at
+ * least 7 bytes to copy, enough to crawl to 8-byte boundary.
+ * Actual number of byte to crawl depend on the dest alignment.
+ * 7 byte or less is taken care at .memcpy_short
+
+ * src0 - source even index
+ * src1 - source  odd index
+ * dst0 - dest even index
+ * dst1 - dest  odd index
+ * r30  - distance to 8-byte boundary
+ */
+
+.align_dest:
+       add     src1=1,in1      // source odd index
+       cmp.le  p7,p0 = 2,r30   // for .align_dest
+       cmp.le  p8,p0 = 3,r30   // for .align_dest
+EX(.ex_handler_short, (p6)     ld1     t1=[src0],2)
+       cmp.le  p9,p0 = 4,r30   // for .align_dest
+       cmp.le  p10,p0 = 5,r30
+       ;;
+EX(.ex_handler_short, (p7)     ld1     t2=[src1],2)
+EK(.ex_handler_short, (p8)     ld1     t3=[src0],2)
+       cmp.le  p11,p0 = 6,r30
+EX(.ex_handler_short, (p6)     st1     [dst0] = t1,2)
+       cmp.le  p12,p0 = 7,r30
+       ;;
+EX(.ex_handler_short, (p9)     ld1     t4=[src1],2)
+EK(.ex_handler_short, (p10)    ld1     t5=[src0],2)
+EX(.ex_handler_short, (p7)     st1     [dst1] = t2,2)
+EK(.ex_handler_short, (p8)     st1     [dst0] = t3,2)
+       ;;
+EX(.ex_handler_short, (p11)    ld1     t6=[src1],2)
+EK(.ex_handler_short, (p12)    ld1     t7=[src0],2)
+       cmp.eq  p6,p7=r28,r29
+EX(.ex_handler_short, (p9)     st1     [dst1] = t4,2)
+EK(.ex_handler_short, (p10)    st1     [dst0] = t5,2)
+       sub     in2=in2,r30
+       ;;
+EX(.ex_handler_short, (p11)    st1     [dst1] = t6,2)
+EK(.ex_handler_short, (p12)    st1     [dst0] = t7)
+       add     dst0=in0,r30    // setup arguments
+       add     src0=in1,r30
+(p6)   br.cond.dptk .aligned_src
+(p7)   br.cond.dpnt .unaligned_src
+       ;;
+
+/* main loop body in jump table format */
+#define COPYU(shift)                                                           
        \
+1:                                                                             
        \
+EX(.ex_handler,  (p16) ld8     r32=[src0],8);          /* 1 */                 
        \
+EK(.ex_handler,  (p16) ld8     r36=[src1],8);                                  
        \
+                (p17)  shrp    r35=r33,r34,shift;;     /* 1 */                 
        \
+EX(.ex_handler,  (p6)  ld8     r22=[src1]);    /* common, prime for tail 
section */    \
+                nop.m  0;                                                      
        \
+                (p16)  shrp    r38=r36,r37,shift;                              
        \
+EX(.ex_handler,  (p17) st8     [dst0]=r35,8);          /* 1 */                 
        \
+EK(.ex_handler,  (p17) st8     [dst1]=r39,8);                                  
        \
+                br.ctop.dptk.few 1b;;                                          
        \
+                (p7)   add     src1=-8,src1;   /* back out for <8 byte case */ 
        \
+                shrp   r21=r22,r38,shift;      /* speculative work */          
        \
+                br.sptk.few .unaligned_src_tail /* branch out of jump table */ 
        \
+                ;;
+       TEXT_ALIGN(32)
+.jump_table:
+       COPYU(8)        // unaligned cases
+.jmp1:
+       COPYU(16)
+       COPYU(24)
+       COPYU(32)
+       COPYU(40)
+       COPYU(48)
+       COPYU(56)
+
+#undef A
+#undef B
+#undef C
+#undef D
+END(memcpy)
+
+/*
+ * Due to lack of local tag support in gcc 2.x assembler, it is not clear which
+ * instruction failed in the bundle.  The exception algorithm is that we
+ * first figure out the faulting address, then detect if there is any
+ * progress made on the copy, if so, redo the copy from last known copied
+ * location up to the faulting address (exclusive). In the copy_from_user
+ * case, remaining byte in kernel buffer will be zeroed.
+ *
+ * Take copy_from_user as an example, in the code there are multiple loads
+ * in a bundle and those multiple loads could span over two pages, the
+ * faulting address is calculated as page_round_down(max(src0, src1)).
+ * This is based on knowledge that if we can access one byte in a page, we
+ * can access any byte in that page.
+ *
+ * predicate used in the exception handler:
+ * p6-p7: direction
+ * p10-p11: src faulting addr calculation
+ * p12-p13: dst faulting addr calculation
+ */
+
+#define A      r19
+#define B      r20
+#define C      r21
+#define D      r22
+#define F      r28
+
+#define memset_arg0    r32
+#define memset_arg2    r33
+
+#define saved_retval   loc0
+#define saved_rtlink   loc1
+#define saved_pfs_stack        loc2
+
+.ex_hndlr_s:
+       add     src0=8,src0
+       br.sptk .ex_handler
+       ;;
+.ex_hndlr_d:
+       add     dst0=8,dst0
+       br.sptk .ex_handler
+       ;;
+.ex_hndlr_lcpy_1:
+       mov     src1=src_pre_mem
+       mov     dst1=dst_pre_mem
+       cmp.gtu p10,p11=src_pre_mem,saved_in1
+       cmp.gtu p12,p13=dst_pre_mem,saved_in0
+       ;;
+(p10)  add     src0=8,saved_in1
+(p11)  mov     src0=saved_in1
+(p12)  add     dst0=8,saved_in0
+(p13)  mov     dst0=saved_in0
+       br.sptk .ex_handler
+.ex_handler_lcpy:
+       // in line_copy block, the preload addresses should always ahead
+       // of the other two src/dst pointers.  Furthermore, src1/dst1 should
+       // always ahead of src0/dst0.
+       mov     src1=src_pre_mem
+       mov     dst1=dst_pre_mem
+.ex_handler:
+       mov     pr=saved_pr,-1          // first restore pr, lc, and pfs
+       mov     ar.lc=saved_lc
+       mov     ar.pfs=saved_pfs
+       ;;
+.ex_handler_short: // fault occurred in these sections didn't change pr, lc, 
pfs
+       cmp.ltu p6,p7=saved_in0, saved_in1      // get the copy direction
+       cmp.ltu p10,p11=src0,src1
+       cmp.ltu p12,p13=dst0,dst1
+       fcmp.eq p8,p0=f6,f0             // is it memcpy?
+       mov     tmp = dst0
+       ;;
+(p11)  mov     src1 = src0             // pick the larger of the two
+(p13)  mov     dst0 = dst1             // make dst0 the smaller one
+(p13)  mov     dst1 = tmp              // and dst1 the larger one
+       ;;
+(p6)   dep     F = r0,dst1,0,PAGE_SHIFT // usr dst round down to page boundary
+(p7)   dep     F = r0,src1,0,PAGE_SHIFT // usr src round down to page boundary
+       ;;
+(p6)   cmp.le  p14,p0=dst0,saved_in0   // no progress has been made on store
+(p7)   cmp.le  p14,p0=src0,saved_in1   // no progress has been made on load
+       mov     retval=saved_in2
+(p8)   ld1     tmp=[src1]              // force an oops for memcpy call
+(p8)   st1     [dst1]=r0               // force an oops for memcpy call
+(p14)  br.ret.sptk.many rp
+
+/*
+ * The remaining byte to copy is calculated as:
+ *
+ * A = (faulting_addr - orig_src)      -> len to faulting ld address
+ *     or 
+ *     (faulting_addr - orig_dst)      -> len to faulting st address
+ * B = (cur_dst - orig_dst)            -> len copied so far
+ * C = A - B                           -> len need to be copied
+ * D = orig_len - A                    -> len need to be zeroed
+ */
+(p6)   sub     A = F, saved_in0
+(p7)   sub     A = F, saved_in1
+       clrrrb
+       ;;
+       alloc   saved_pfs_stack=ar.pfs,3,3,3,0
+       sub     B = dst0, saved_in0     // how many byte copied so far
+       ;;
+       sub     C = A, B
+       sub     D = saved_in2, A
+       ;;
+       cmp.gt  p8,p0=C,r0              // more than 1 byte?
+       add     memset_arg0=saved_in0, A
+(p6)   mov     memset_arg2=0           // copy_to_user should not call memset
+(p7)   mov     memset_arg2=D           // copy_from_user need to have kbuf 
zeroed
+       mov     r8=0
+       mov     saved_retval = D
+       mov     saved_rtlink = b0
+
+       add     out0=saved_in0, B
+       add     out1=saved_in1, B
+       mov     out2=C
+(p8)   br.call.sptk.few b0=__copy_user // recursive call
+       ;;
+
+       add     saved_retval=saved_retval,r8    // above might return non-zero 
value
+       cmp.gt  p8,p0=memset_arg2,r0    // more than 1 byte?
+       mov     out0=memset_arg0        // *s
+       mov     out1=r0                 // c
+       mov     out2=memset_arg2        // n
+(p8)   br.call.sptk.few b0=memset
+       ;;
+
+       mov     retval=saved_retval
+       mov     ar.pfs=saved_pfs_stack
+       mov     b0=saved_rtlink
+       br.ret.sptk.many rp
+
+/* end of McKinley specific optimization */
+END(__copy_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/memset.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/memset.S  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,362 @@
+/* Optimized version of the standard memset() function.
+
+   Copyright (c) 2002 Hewlett-Packard Co/CERN
+       Sverre Jarp <Sverre.Jarp@xxxxxxx>
+
+   Return: dest
+
+   Inputs:
+        in0:    dest
+        in1:    value
+        in2:    count
+
+   The algorithm is fairly straightforward: set byte by byte until we
+   we get to a 16B-aligned address, then loop on 128 B chunks using an
+   early store as prefetching, then loop on 32B chucks, then clear remaining
+   words, finally clear remaining bytes.
+   Since a stf.spill f0 can store 16B in one go, we use this instruction
+   to get peak speed when value = 0.  */
+
+#include <asm/asmmacro.h>
+#undef ret
+
+#define dest           in0
+#define value          in1
+#define        cnt             in2
+
+#define tmp            r31
+#define save_lc                r30
+#define ptr0           r29
+#define ptr1           r28
+#define ptr2           r27
+#define ptr3           r26
+#define ptr9           r24
+#define        loopcnt         r23
+#define linecnt                r22
+#define bytecnt                r21
+
+#define fvalue         f6
+
+// This routine uses only scratch predicate registers (p6 - p15)
+#define p_scr          p6                      // default register for 
same-cycle branches
+#define p_nz           p7
+#define p_zr           p8
+#define p_unalgn       p9
+#define p_y            p11
+#define p_n            p12
+#define p_yy           p13
+#define p_nn           p14
+
+#define MIN1           15
+#define MIN1P1HALF     8
+#define LINE_SIZE      128
+#define LSIZE_SH        7                      // shift amount
+#define PREF_AHEAD     8
+
+GLOBAL_ENTRY(memset)
+{ .mmi
+       .prologue
+       alloc   tmp = ar.pfs, 3, 0, 0, 0
+       .body
+       lfetch.nt1 [dest]                       //
+       .save   ar.lc, save_lc
+       mov.i   save_lc = ar.lc
+} { .mmi
+       mov     ret0 = dest                     // return value
+       cmp.ne  p_nz, p_zr = value, r0          // use stf.spill if value is 
zero
+       cmp.eq  p_scr, p0 = cnt, r0
+;; }
+{ .mmi
+       and     ptr2 = -(MIN1+1), dest          // aligned address
+       and     tmp = MIN1, dest                // prepare to check for correct 
alignment
+       tbit.nz p_y, p_n = dest, 0              // Do we have an odd address? 
(M_B_U)
+} { .mib
+       mov     ptr1 = dest
+       mux1    value = value, @brcst           // create 8 identical bytes in 
word
+(p_scr)        br.ret.dpnt.many rp                     // return immediately 
if count = 0
+;; }
+{ .mib
+       cmp.ne  p_unalgn, p0 = tmp, r0          //
+} { .mib
+       sub     bytecnt = (MIN1+1), tmp         // NB: # of bytes to move is 1 
higher than loopcnt
+       cmp.gt  p_scr, p0 = 16, cnt             // is it a minimalistic task?
+(p_scr)        br.cond.dptk.many .move_bytes_unaligned // go move just a few 
(M_B_U)
+;; }
+{ .mmi
+(p_unalgn) add ptr1 = (MIN1+1), ptr2           // after alignment
+(p_unalgn) add ptr2 = MIN1P1HALF, ptr2         // after alignment
+(p_unalgn) tbit.nz.unc p_y, p_n = bytecnt, 3   // should we do a st8 ?
+;; }
+{ .mib
+(p_y)  add     cnt = -8, cnt                   //
+(p_unalgn) tbit.nz.unc p_yy, p_nn = bytecnt, 2 // should we do a st4 ?
+} { .mib
+(p_y)  st8     [ptr2] = value,-4               //
+(p_n)  add     ptr2 = 4, ptr2                  //
+;; }
+{ .mib
+(p_yy) add     cnt = -4, cnt                   //
+(p_unalgn) tbit.nz.unc p_y, p_n = bytecnt, 1   // should we do a st2 ?
+} { .mib
+(p_yy) st4     [ptr2] = value,-2               //
+(p_nn) add     ptr2 = 2, ptr2                  //
+;; }
+{ .mmi
+       mov     tmp = LINE_SIZE+1               // for compare
+(p_y)  add     cnt = -2, cnt                   //
+(p_unalgn) tbit.nz.unc p_yy, p_nn = bytecnt, 0 // should we do a st1 ?
+} { .mmi
+       setf.sig fvalue=value                   // transfer value to FLP side
+(p_y)  st2     [ptr2] = value,-1               //
+(p_n)  add     ptr2 = 1, ptr2                  //
+;; }
+
+{ .mmi
+(p_yy) st1     [ptr2] = value                  //
+       cmp.gt  p_scr, p0 = tmp, cnt            // is it a minimalistic task?
+} { .mbb
+(p_yy) add     cnt = -1, cnt                   //
+(p_scr)        br.cond.dpnt.many .fraction_of_line     // go move just a few
+;; }
+
+{ .mib
+       nop.m 0
+       shr.u   linecnt = cnt, LSIZE_SH
+(p_zr) br.cond.dptk.many .l1b                  // Jump to use stf.spill
+;; }
+
+       TEXT_ALIGN(32) // --------------------- //  L1A: store ahead into cache 
lines; fill later
+{ .mmi
+       and     tmp = -(LINE_SIZE), cnt         // compute end of range
+       mov     ptr9 = ptr1                     // used for prefetching
+       and     cnt = (LINE_SIZE-1), cnt        // remainder
+} { .mmi
+       mov     loopcnt = PREF_AHEAD-1          // default prefetch loop
+       cmp.gt  p_scr, p0 = PREF_AHEAD, linecnt // check against actual value
+;; }
+{ .mmi
+(p_scr)        add     loopcnt = -1, linecnt           //
+       add     ptr2 = 8, ptr1                  // start of stores (beyond 
prefetch stores)
+       add     ptr1 = tmp, ptr1                // first address beyond total 
range
+;; }
+{ .mmi
+       add     tmp = -1, linecnt               // next loop count
+       mov.i   ar.lc = loopcnt                 //
+;; }
+.pref_l1a:
+{ .mib
+       stf8 [ptr9] = fvalue, 128               // Do stores one cache line 
apart
+       nop.i   0
+       br.cloop.dptk.few .pref_l1a
+;; }
+{ .mmi
+       add     ptr0 = 16, ptr2                 // Two stores in parallel
+       mov.i   ar.lc = tmp                     //
+;; }
+.l1ax:
+ { .mmi
+       stf8 [ptr2] = fvalue, 8
+       stf8 [ptr0] = fvalue, 8
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 24
+       stf8 [ptr0] = fvalue, 24
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 8
+       stf8 [ptr0] = fvalue, 8
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 24
+       stf8 [ptr0] = fvalue, 24
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 8
+       stf8 [ptr0] = fvalue, 8
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 24
+       stf8 [ptr0] = fvalue, 24
+ ;; }
+ { .mmi
+       stf8 [ptr2] = fvalue, 8
+       stf8 [ptr0] = fvalue, 32
+       cmp.lt  p_scr, p0 = ptr9, ptr1          // do we need more prefetching?
+ ;; }
+{ .mmb
+       stf8 [ptr2] = fvalue, 24
+(p_scr)        stf8 [ptr9] = fvalue, 128
+       br.cloop.dptk.few .l1ax
+;; }
+{ .mbb
+       cmp.le  p_scr, p0 = 8, cnt              // just a few bytes left ?
+(p_scr) br.cond.dpnt.many  .fraction_of_line   // Branch no. 2
+       br.cond.dpnt.many  .move_bytes_from_alignment   // Branch no. 3
+;; }
+
+       TEXT_ALIGN(32)
+.l1b:  // ------------------------------------ //  L1B: store ahead into cache 
lines; fill later
+{ .mmi
+       and     tmp = -(LINE_SIZE), cnt         // compute end of range
+       mov     ptr9 = ptr1                     // used for prefetching
+       and     cnt = (LINE_SIZE-1), cnt        // remainder
+} { .mmi
+       mov     loopcnt = PREF_AHEAD-1          // default prefetch loop
+       cmp.gt  p_scr, p0 = PREF_AHEAD, linecnt // check against actual value
+;; }
+{ .mmi
+(p_scr)        add     loopcnt = -1, linecnt
+       add     ptr2 = 16, ptr1                 // start of stores (beyond 
prefetch stores)
+       add     ptr1 = tmp, ptr1                // first address beyond total 
range
+;; }
+{ .mmi
+       add     tmp = -1, linecnt               // next loop count
+       mov.i   ar.lc = loopcnt
+;; }
+.pref_l1b:
+{ .mib
+       stf.spill [ptr9] = f0, 128              // Do stores one cache line 
apart
+       nop.i   0
+       br.cloop.dptk.few .pref_l1b
+;; }
+{ .mmi
+       add     ptr0 = 16, ptr2                 // Two stores in parallel
+       mov.i   ar.lc = tmp
+;; }
+.l1bx:
+ { .mmi
+       stf.spill [ptr2] = f0, 32
+       stf.spill [ptr0] = f0, 32
+ ;; }
+ { .mmi
+       stf.spill [ptr2] = f0, 32
+       stf.spill [ptr0] = f0, 32
+ ;; }
+ { .mmi
+       stf.spill [ptr2] = f0, 32
+       stf.spill [ptr0] = f0, 64
+       cmp.lt  p_scr, p0 = ptr9, ptr1          // do we need more prefetching?
+ ;; }
+{ .mmb
+       stf.spill [ptr2] = f0, 32
+(p_scr)        stf.spill [ptr9] = f0, 128
+       br.cloop.dptk.few .l1bx
+;; }
+{ .mib
+       cmp.gt  p_scr, p0 = 8, cnt              // just a few bytes left ?
+(p_scr)        br.cond.dpnt.many  .move_bytes_from_alignment   //
+;; }
+
+.fraction_of_line:
+{ .mib
+       add     ptr2 = 16, ptr1
+       shr.u   loopcnt = cnt, 5                // loopcnt = cnt / 32
+;; }
+{ .mib
+       cmp.eq  p_scr, p0 = loopcnt, r0
+       add     loopcnt = -1, loopcnt
+(p_scr)        br.cond.dpnt.many .store_words
+;; }
+{ .mib
+       and     cnt = 0x1f, cnt                 // compute the remaining cnt
+       mov.i   ar.lc = loopcnt
+;; }
+       TEXT_ALIGN(32)
+.l2:   // ------------------------------------ //  L2A:  store 32B in 2 cycles
+{ .mmb
+       stf8    [ptr1] = fvalue, 8
+       stf8    [ptr2] = fvalue, 8
+;; } { .mmb
+       stf8    [ptr1] = fvalue, 24
+       stf8    [ptr2] = fvalue, 24
+       br.cloop.dptk.many .l2
+;; }
+.store_words:
+{ .mib
+       cmp.gt  p_scr, p0 = 8, cnt              // just a few bytes left ?
+(p_scr)        br.cond.dpnt.many .move_bytes_from_alignment    // Branch
+;; }
+
+{ .mmi
+       stf8    [ptr1] = fvalue, 8              // store
+       cmp.le  p_y, p_n = 16, cnt
+       add     cnt = -8, cnt                   // subtract
+;; }
+{ .mmi
+(p_y)  stf8    [ptr1] = fvalue, 8              // store
+(p_y)  cmp.le.unc p_yy, p_nn = 16, cnt
+(p_y)  add     cnt = -8, cnt                   // subtract
+;; }
+{ .mmi                                         // store
+(p_yy) stf8    [ptr1] = fvalue, 8
+(p_yy) add     cnt = -8, cnt                   // subtract
+;; }
+
+.move_bytes_from_alignment:
+{ .mib
+       cmp.eq  p_scr, p0 = cnt, r0
+       tbit.nz.unc p_y, p0 = cnt, 2            // should we terminate with a 
st4 ?
+(p_scr)        br.cond.dpnt.few .restore_and_exit
+;; }
+{ .mib
+(p_y)  st4     [ptr1] = value,4
+       tbit.nz.unc p_yy, p0 = cnt, 1           // should we terminate with a 
st2 ?
+;; }
+{ .mib
+(p_yy) st2     [ptr1] = value,2
+       tbit.nz.unc p_y, p0 = cnt, 0            // should we terminate with a 
st1 ?
+;; }
+
+{ .mib
+(p_y)  st1     [ptr1] = value
+;; }
+.restore_and_exit:
+{ .mib
+       nop.m   0
+       mov.i   ar.lc = save_lc
+       br.ret.sptk.many rp
+;; }
+
+.move_bytes_unaligned:
+{ .mmi
+       .pred.rel "mutex",p_y, p_n
+       .pred.rel "mutex",p_yy, p_nn
+(p_n)  cmp.le  p_yy, p_nn = 4, cnt
+(p_y)  cmp.le  p_yy, p_nn = 5, cnt
+(p_n)  add     ptr2 = 2, ptr1
+} { .mmi
+(p_y)  add     ptr2 = 3, ptr1
+(p_y)  st1     [ptr1] = value, 1               // fill 1 (odd-aligned) byte 
[15, 14 (or less) left]
+(p_y)  add     cnt = -1, cnt
+;; }
+{ .mmi
+(p_yy) cmp.le.unc p_y, p0 = 8, cnt
+       add     ptr3 = ptr1, cnt                // prepare last store
+       mov.i   ar.lc = save_lc
+} { .mmi
+(p_yy) st2     [ptr1] = value, 4               // fill 2 (aligned) bytes
+(p_yy) st2     [ptr2] = value, 4               // fill 2 (aligned) bytes [11, 
10 (o less) left]
+(p_yy) add     cnt = -4, cnt
+;; }
+{ .mmi
+(p_y)  cmp.le.unc p_yy, p0 = 8, cnt
+       add     ptr3 = -1, ptr3                 // last store
+       tbit.nz p_scr, p0 = cnt, 1              // will there be a st2 at the 
end ?
+} { .mmi
+(p_y)  st2     [ptr1] = value, 4               // fill 2 (aligned) bytes
+(p_y)  st2     [ptr2] = value, 4               // fill 2 (aligned) bytes [7, 6 
(or less) left]
+(p_y)  add     cnt = -4, cnt
+;; }
+{ .mmi
+(p_yy) st2     [ptr1] = value, 4               // fill 2 (aligned) bytes
+(p_yy) st2     [ptr2] = value, 4               // fill 2 (aligned) bytes [3, 2 
(or less) left]
+       tbit.nz p_y, p0 = cnt, 0                // will there be a st1 at the 
end ?
+} { .mmi
+(p_yy) add     cnt = -4, cnt
+;; }
+{ .mmb
+(p_scr)        st2     [ptr1] = value                  // fill 2 (aligned) 
bytes
+(p_y)  st1     [ptr3] = value                  // fill last byte (using ptr3)
+       br.ret.sptk.many rp
+}
+END(memset)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/strlen.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/strlen.S  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,192 @@
+/*
+ *
+ * Optimized version of the standard strlen() function
+ *
+ *
+ * Inputs:
+ *     in0     address of string
+ *
+ * Outputs:
+ *     ret0    the number of characters in the string (0 if empty string)
+ *     does not count the \0
+ *
+ * Copyright (C) 1999, 2001 Hewlett-Packard Co
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * 09/24/99 S.Eranian add speculation recovery code
+ */
+
+#include <asm/asmmacro.h>
+
+//
+//
+// This is an enhanced version of the basic strlen. it includes a combination
+// of compute zero index (czx), parallel comparisons, speculative loads and
+// loop unroll using rotating registers.
+//
+// General Ideas about the algorithm:
+//       The goal is to look at the string in chunks of 8 bytes.
+//       so we need to do a few extra checks at the beginning because the
+//       string may not be 8-byte aligned. In this case we load the 8byte
+//       quantity which includes the start of the string and mask the unused
+//       bytes with 0xff to avoid confusing czx.
+//       We use speculative loads and software pipelining to hide memory
+//       latency and do read ahead safely. This way we defer any exception.
+//
+//       Because we don't want the kernel to be relying on particular
+//       settings of the DCR register, we provide recovery code in case
+//       speculation fails. The recovery code is going to "redo" the work using
+//       only normal loads. If we still get a fault then we generate a
+//       kernel panic. Otherwise we return the strlen as usual.
+//
+//       The fact that speculation may fail can be caused, for instance, by
+//       the DCR.dm bit being set. In this case TLB misses are deferred, i.e.,
+//       a NaT bit will be set if the translation is not present. The normal
+//       load, on the other hand, will cause the translation to be inserted
+//       if the mapping exists.
+//
+//       It should be noted that we execute recovery code only when we need
+//       to use the data that has been speculatively loaded: we don't execute
+//       recovery code on pure read ahead data.
+//
+// Remarks:
+//     - the cmp r0,r0 is used as a fast way to initialize a predicate
+//       register to 1. This is required to make sure that we get the parallel
+//       compare correct.
+//
+//     - we don't use the epilogue counter to exit the loop but we need to set
+//       it to zero beforehand.
+//
+//     - after the loop we must test for Nat values because neither the
+//       czx nor cmp instruction raise a NaT consumption fault. We must be
+//       careful not to look too far for a Nat for which we don't care.
+//       For instance we don't need to look at a NaT in val2 if the zero byte
+//       was in val1.
+//
+//     - Clearly performance tuning is required.
+//
+//
+//
+#define saved_pfs      r11
+#define        tmp             r10
+#define base           r16
+#define orig           r17
+#define saved_pr       r18
+#define src            r19
+#define mask           r20
+#define val            r21
+#define val1           r22
+#define val2           r23
+
+GLOBAL_ENTRY(strlen)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,11,0,0,8 // rotating must be multiple of 8
+
+       .rotr v[2], w[2]        // declares our 4 aliases
+
+       extr.u tmp=in0,0,3      // tmp=least significant 3 bits
+       mov orig=in0            // keep trackof initial byte address
+       dep src=0,in0,0,3       // src=8byte-aligned in0 address
+       .save pr, saved_pr
+       mov saved_pr=pr         // preserve predicates (rotation)
+       ;;
+
+       .body
+
+       ld8 v[1]=[src],8        // must not speculate: can fail here
+       shl tmp=tmp,3           // multiply by 8bits/byte
+       mov mask=-1             // our mask
+       ;;
+       ld8.s w[1]=[src],8      // speculatively load next
+       cmp.eq p6,p0=r0,r0      // sets p6 to true for cmp.and
+       sub tmp=64,tmp          // how many bits to shift our mask on the right
+       ;;
+       shr.u   mask=mask,tmp   // zero enough bits to hold v[1] valuable part
+       mov ar.ec=r0            // clear epilogue counter (saved in ar.pfs)
+       ;;
+       add base=-16,src        // keep track of aligned base
+       or v[1]=v[1],mask       // now we have a safe initial byte pattern
+       ;;
+1:
+       ld8.s v[0]=[src],8      // speculatively load next
+       czx1.r val1=v[1]        // search 0 byte from right
+       czx1.r val2=w[1]        // search 0 byte from right following 8bytes
+       ;;
+       ld8.s w[0]=[src],8      // speculatively load next to next
+       cmp.eq.and p6,p0=8,val1 // p6 = p6 and val1==8
+       cmp.eq.and p6,p0=8,val2 // p6 = p6 and mask==8
+(p6)   br.wtop.dptk 1b         // loop until p6 == 0
+       ;;
+       //
+       // We must return try the recovery code iff
+       // val1_is_nat || (val1==8 && val2_is_nat)
+       //
+       // XXX Fixme
+       //      - there must be a better way of doing the test
+       //
+       cmp.eq  p8,p9=8,val1    // p6 = val1 had zero (disambiguate)
+       tnat.nz p6,p7=val1      // test NaT on val1
+(p6)   br.cond.spnt .recover   // jump to recovery if val1 is NaT
+       ;;
+       //
+       // if we come here p7 is true, i.e., initialized for // cmp
+       //
+       cmp.eq.and  p7,p0=8,val1// val1==8?
+       tnat.nz.and p7,p0=val2  // test NaT if val2
+(p7)   br.cond.spnt .recover   // jump to recovery if val2 is NaT
+       ;;
+(p8)   mov val1=val2           // the other test got us out of the loop
+(p8)   adds src=-16,src        // correct position when 3 ahead
+(p9)   adds src=-24,src        // correct position when 4 ahead
+       ;;
+       sub ret0=src,orig       // distance from base
+       sub tmp=8,val1          // which byte in word
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       sub ret0=ret0,tmp       // adjust
+       mov ar.pfs=saved_pfs    // because of ar.ec, restore no matter what
+       br.ret.sptk.many rp     // end of normal execution
+
+       //
+       // Outlined recovery code when speculation failed
+       //
+       // This time we don't use speculation and rely on the normal exception
+       // mechanism. that's why the loop is not as good as the previous one
+       // because read ahead is not possible
+       //
+       // IMPORTANT:
+       // Please note that in the case of strlen() as opposed to strlen_user()
+       // we don't use the exception mechanism, as this function is not
+       // supposed to fail. If that happens it means we have a bug and the
+       // code will cause of kernel fault.
+       //
+       // XXX Fixme
+       //      - today we restart from the beginning of the string instead
+       //        of trying to continue where we left off.
+       //
+.recover:
+       ld8 val=[base],8        // will fail if unrecoverable fault
+       ;;
+       or val=val,mask         // remask first bytes
+       cmp.eq p0,p6=r0,r0      // nullify first ld8 in loop
+       ;;
+       //
+       // ar.ec is still zero here
+       //
+2:
+(p6)   ld8 val=[base],8        // will fail if unrecoverable fault
+       ;;
+       czx1.r val1=val         // search 0 byte from right
+       ;;
+       cmp.eq p6,p0=8,val1     // val1==8 ?
+(p6)   br.wtop.dptk 2b         // loop until p6 == 0
+       ;;                      // (avoid WAW on p63)
+       sub ret0=base,orig      // distance from base
+       sub tmp=8,val1
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       sub ret0=ret0,tmp       // length=now - back -1
+       mov ar.pfs=saved_pfs    // because of ar.ec, restore no matter what
+       br.ret.sptk.many rp     // end of successful recovery code
+END(strlen)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/strlen_user.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/strlen_user.S     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,198 @@
+/*
+ * Optimized version of the strlen_user() function
+ *
+ * Inputs:
+ *     in0     address of buffer
+ *
+ * Outputs:
+ *     ret0    0 in case of fault, strlen(buffer)+1 otherwise
+ *
+ * Copyright (C) 1998, 1999, 2001 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * 01/19/99 S.Eranian heavily enhanced version (see details below)
+ * 09/24/99 S.Eranian added speculation recovery code
+ */
+
+#include <asm/asmmacro.h>
+
+//
+// int strlen_user(char *)
+// ------------------------
+// Returns:
+//     - length of string + 1
+//     - 0 in case an exception is raised
+//
+// This is an enhanced version of the basic strlen_user. it includes a
+// combination of compute zero index (czx), parallel comparisons, speculative
+// loads and loop unroll using rotating registers.
+//
+// General Ideas about the algorithm:
+//       The goal is to look at the string in chunks of 8 bytes.
+//       so we need to do a few extra checks at the beginning because the
+//       string may not be 8-byte aligned. In this case we load the 8byte
+//       quantity which includes the start of the string and mask the unused
+//       bytes with 0xff to avoid confusing czx.
+//       We use speculative loads and software pipelining to hide memory
+//       latency and do read ahead safely. This way we defer any exception.
+//
+//       Because we don't want the kernel to be relying on particular
+//       settings of the DCR register, we provide recovery code in case
+//       speculation fails. The recovery code is going to "redo" the work using
+//       only normal loads. If we still get a fault then we return an
+//       error (ret0=0). Otherwise we return the strlen+1 as usual.
+//       The fact that speculation may fail can be caused, for instance, by
+//       the DCR.dm bit being set. In this case TLB misses are deferred, i.e.,
+//       a NaT bit will be set if the translation is not present. The normal
+//       load, on the other hand, will cause the translation to be inserted
+//       if the mapping exists.
+//
+//       It should be noted that we execute recovery code only when we need
+//       to use the data that has been speculatively loaded: we don't execute
+//       recovery code on pure read ahead data.
+//
+// Remarks:
+//     - the cmp r0,r0 is used as a fast way to initialize a predicate
+//       register to 1. This is required to make sure that we get the parallel
+//       compare correct.
+//
+//     - we don't use the epilogue counter to exit the loop but we need to set
+//       it to zero beforehand.
+//
+//     - after the loop we must test for Nat values because neither the
+//       czx nor cmp instruction raise a NaT consumption fault. We must be
+//       careful not to look too far for a Nat for which we don't care.
+//       For instance we don't need to look at a NaT in val2 if the zero byte
+//       was in val1.
+//
+//     - Clearly performance tuning is required.
+//
+
+#define saved_pfs      r11
+#define        tmp             r10
+#define base           r16
+#define orig           r17
+#define saved_pr       r18
+#define src            r19
+#define mask           r20
+#define val            r21
+#define val1           r22
+#define val2           r23
+
+GLOBAL_ENTRY(__strlen_user)
+       .prologue
+       .save ar.pfs, saved_pfs
+       alloc saved_pfs=ar.pfs,11,0,0,8
+
+       .rotr v[2], w[2]        // declares our 4 aliases
+
+       extr.u tmp=in0,0,3      // tmp=least significant 3 bits
+       mov orig=in0            // keep trackof initial byte address
+       dep src=0,in0,0,3       // src=8byte-aligned in0 address
+       .save pr, saved_pr
+       mov saved_pr=pr         // preserve predicates (rotation)
+       ;;
+
+       .body
+
+       ld8.s v[1]=[src],8      // load the initial 8bytes (must speculate)
+       shl tmp=tmp,3           // multiply by 8bits/byte
+       mov mask=-1             // our mask
+       ;;
+       ld8.s w[1]=[src],8      // load next 8 bytes in 2nd pipeline
+       cmp.eq p6,p0=r0,r0      // sets p6 (required because of // cmp.and)
+       sub tmp=64,tmp          // how many bits to shift our mask on the right
+       ;;
+       shr.u   mask=mask,tmp   // zero enough bits to hold v[1] valuable part
+       mov ar.ec=r0            // clear epilogue counter (saved in ar.pfs)
+       ;;
+       add base=-16,src        // keep track of aligned base
+       chk.s v[1], .recover    // if already NaT, then directly skip to recover
+       or v[1]=v[1],mask       // now we have a safe initial byte pattern
+       ;;
+1:
+       ld8.s v[0]=[src],8      // speculatively load next
+       czx1.r val1=v[1]        // search 0 byte from right
+       czx1.r val2=w[1]        // search 0 byte from right following 8bytes
+       ;;
+       ld8.s w[0]=[src],8      // speculatively load next to next
+       cmp.eq.and p6,p0=8,val1 // p6 = p6 and val1==8
+       cmp.eq.and p6,p0=8,val2 // p6 = p6 and mask==8
+(p6)   br.wtop.dptk.few 1b     // loop until p6 == 0
+       ;;
+       //
+       // We must return try the recovery code iff
+       // val1_is_nat || (val1==8 && val2_is_nat)
+       //
+       // XXX Fixme
+       //      - there must be a better way of doing the test
+       //
+       cmp.eq  p8,p9=8,val1    // p6 = val1 had zero (disambiguate)
+       tnat.nz p6,p7=val1      // test NaT on val1
+(p6)   br.cond.spnt .recover   // jump to recovery if val1 is NaT
+       ;;
+       //
+       // if we come here p7 is true, i.e., initialized for // cmp
+       //
+       cmp.eq.and  p7,p0=8,val1// val1==8?
+       tnat.nz.and p7,p0=val2  // test NaT if val2
+(p7)   br.cond.spnt .recover   // jump to recovery if val2 is NaT
+       ;;
+(p8)   mov val1=val2           // val2 contains the value
+(p8)   adds src=-16,src        // correct position when 3 ahead
+(p9)   adds src=-24,src        // correct position when 4 ahead
+       ;;
+       sub ret0=src,orig       // distance from origin
+       sub tmp=7,val1          // 7=8-1 because this strlen returns strlen+1
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       sub ret0=ret0,tmp       // length=now - back -1
+       mov ar.pfs=saved_pfs    // because of ar.ec, restore no matter what
+       br.ret.sptk.many rp     // end of normal execution
+
+       //
+       // Outlined recovery code when speculation failed
+       //
+       // This time we don't use speculation and rely on the normal exception
+       // mechanism. that's why the loop is not as good as the previous one
+       // because read ahead is not possible
+       //
+       // XXX Fixme
+       //      - today we restart from the beginning of the string instead
+       //        of trying to continue where we left off.
+       //
+.recover:
+       EX(.Lexit1, ld8 val=[base],8)   // load the initial bytes
+       ;;
+       or val=val,mask                 // remask first bytes
+       cmp.eq p0,p6=r0,r0              // nullify first ld8 in loop
+       ;;
+       //
+       // ar.ec is still zero here
+       //
+2:
+       EX(.Lexit1, (p6) ld8 val=[base],8)
+       ;;
+       czx1.r val1=val         // search 0 byte from right
+       ;;
+       cmp.eq p6,p0=8,val1     // val1==8 ?
+(p6)   br.wtop.dptk.few 2b     // loop until p6 == 0
+       ;;
+       sub ret0=base,orig      // distance from base
+       sub tmp=7,val1          // 7=8-1 because this strlen returns strlen+1
+       mov pr=saved_pr,0xffffffffffff0000
+       ;;
+       sub ret0=ret0,tmp       // length=now - back -1
+       mov ar.pfs=saved_pfs    // because of ar.ec, restore no matter what
+       br.ret.sptk.many rp     // end of successful recovery code
+
+       //
+       // We failed even on the normal load (called from exception handler)
+       //
+.Lexit1:
+       mov ret0=0
+       mov pr=saved_pr,0xffffffffffff0000
+       mov ar.pfs=saved_pfs    // because of ar.ec, restore no matter what
+       br.ret.sptk.many rp
+END(__strlen_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/strncpy_from_user.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/strncpy_from_user.S       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,44 @@
+/*
+ * Just like strncpy() except that if a fault occurs during copying,
+ * -EFAULT is returned.
+ *
+ * Inputs:
+ *     in0:    address of destination buffer
+ *     in1:    address of string to be copied
+ *     in2:    length of buffer in bytes
+ * Outputs:
+ *     r8:     -EFAULT in case of fault or number of bytes copied if no fault
+ *
+ * Copyright (C) 1998-2001 Hewlett-Packard Co
+ * Copyright (C) 1998-2001 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 00/03/06 D. Mosberger Fixed to return proper return value (bug found by
+ *                      by Andreas Schwab <schwab@xxxxxxx>).
+ */
+
+#include <asm/asmmacro.h>
+
+GLOBAL_ENTRY(__strncpy_from_user)
+       alloc r2=ar.pfs,3,0,0,0
+       mov r8=0
+       mov r9=in1
+       ;;
+       add r10=in1,in2
+       cmp.eq p6,p0=r0,in2
+(p6)   br.ret.spnt.many rp
+
+       // XXX braindead copy loop---this needs to be optimized
+.Loop1:
+       EX(.Lexit, ld1 r8=[in1],1)
+       ;;
+       EX(.Lexit, st1 [in0]=r8,1)
+       cmp.ne p6,p7=r8,r0
+       ;;
+(p6)   cmp.ne.unc p8,p0=in1,r10
+(p8)   br.cond.dpnt.few .Loop1
+       ;;
+(p6)   mov r8=in2              // buffer filled up---return buffer length
+(p7)   sub r8=in1,r9,1         // return string length (excluding NUL 
character)
+[.Lexit:]
+       br.ret.sptk.many rp
+END(__strncpy_from_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/strnlen_user.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/strnlen_user.S    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,45 @@
+/*
+ * Returns 0 if exception before NUL or reaching the supplied limit (N),
+ * a value greater than N if the string is longer than the limit, else
+ * strlen.
+ *
+ * Inputs:
+ *     in0:    address of buffer
+ *     in1:    string length limit N
+ * Outputs:
+ *     r8:     0 in case of fault, strlen(buffer)+1 otherwise
+ *
+ * Copyright (C) 1999, 2001 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm/asmmacro.h>
+
+GLOBAL_ENTRY(__strnlen_user)
+       .prologue
+       alloc r2=ar.pfs,2,0,0,0
+       .save ar.lc, r16
+       mov r16=ar.lc                   // preserve ar.lc
+
+       .body
+
+       add r3=-1,in1
+       ;;
+       mov ar.lc=r3
+       mov r9=0
+       ;;
+       // XXX braindead strlen loop---this needs to be optimized
+.Loop1:
+       EXCLR(.Lexit, ld1 r8=[in0],1)
+       add r9=1,r9
+       ;;
+       cmp.eq p6,p0=r8,r0
+(p6)   br.cond.dpnt .Lexit
+       br.cloop.dptk.few .Loop1
+
+       add r9=1,in1                    // NUL not found---return N+1
+       ;;
+.Lexit:
+       mov r8=r9
+       mov ar.lc=r16                   // restore ar.lc
+       br.ret.sptk.many rp
+END(__strnlen_user)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/lib/xor.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/lib/xor.S     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,184 @@
+/*
+ * arch/ia64/lib/xor.S
+ *
+ * Optimized RAID-5 checksumming functions for IA-64.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * You should have received a copy of the GNU General Public License
+ * (for example /usr/src/linux/COPYING); if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#include <asm/asmmacro.h>
+
+GLOBAL_ENTRY(xor_ia64_2)
+       .prologue
+       .fframe 0
+       .save ar.pfs, r31
+       alloc r31 = ar.pfs, 3, 0, 13, 16
+       .save ar.lc, r30
+       mov r30 = ar.lc
+       .save pr, r29
+       mov r29 = pr
+       ;;
+       .body
+       mov r8 = in1
+       mov ar.ec = 6 + 2
+       shr in0 = in0, 3
+       ;;
+       adds in0 = -1, in0
+       mov r16 = in1
+       mov r17 = in2
+       ;;
+       mov ar.lc = in0
+       mov pr.rot = 1 << 16
+       ;;
+       .rotr s1[6+1], s2[6+1], d[2]
+       .rotp p[6+2]
+0:
+(p[0]) ld8.nta s1[0] = [r16], 8
+(p[0]) ld8.nta s2[0] = [r17], 8
+(p[6]) xor d[0] = s1[6], s2[6]
+(p[6+1])st8.nta [r8] = d[1], 8
+       nop.f 0
+       br.ctop.dptk.few 0b
+       ;;
+       mov ar.lc = r30
+       mov pr = r29, -1
+       br.ret.sptk.few rp
+END(xor_ia64_2)
+
+GLOBAL_ENTRY(xor_ia64_3)
+       .prologue
+       .fframe 0
+       .save ar.pfs, r31
+       alloc r31 = ar.pfs, 4, 0, 20, 24
+       .save ar.lc, r30
+       mov r30 = ar.lc
+       .save pr, r29
+       mov r29 = pr
+       ;;
+       .body
+       mov r8 = in1
+       mov ar.ec = 6 + 2
+       shr in0 = in0, 3
+       ;;
+       adds in0 = -1, in0
+       mov r16 = in1
+       mov r17 = in2
+       ;;
+       mov r18 = in3
+       mov ar.lc = in0
+       mov pr.rot = 1 << 16
+       ;;
+       .rotr s1[6+1], s2[6+1], s3[6+1], d[2]
+       .rotp p[6+2]
+0:
+(p[0]) ld8.nta s1[0] = [r16], 8
+(p[0]) ld8.nta s2[0] = [r17], 8
+(p[6]) xor d[0] = s1[6], s2[6]
+       ;;
+(p[0]) ld8.nta s3[0] = [r18], 8
+(p[6+1])st8.nta [r8] = d[1], 8
+(p[6]) xor d[0] = d[0], s3[6]
+       br.ctop.dptk.few 0b
+       ;;
+       mov ar.lc = r30
+       mov pr = r29, -1
+       br.ret.sptk.few rp
+END(xor_ia64_3)
+
+GLOBAL_ENTRY(xor_ia64_4)
+       .prologue
+       .fframe 0
+       .save ar.pfs, r31
+       alloc r31 = ar.pfs, 5, 0, 27, 32
+       .save ar.lc, r30
+       mov r30 = ar.lc
+       .save pr, r29
+       mov r29 = pr
+       ;;
+       .body
+       mov r8 = in1
+       mov ar.ec = 6 + 2
+       shr in0 = in0, 3
+       ;;
+       adds in0 = -1, in0
+       mov r16 = in1
+       mov r17 = in2
+       ;;
+       mov r18 = in3
+       mov ar.lc = in0
+       mov pr.rot = 1 << 16
+       mov r19 = in4
+       ;;
+       .rotr s1[6+1], s2[6+1], s3[6+1], s4[6+1], d[2]
+       .rotp p[6+2]
+0:
+(p[0]) ld8.nta s1[0] = [r16], 8
+(p[0]) ld8.nta s2[0] = [r17], 8
+(p[6]) xor d[0] = s1[6], s2[6]
+(p[0]) ld8.nta s3[0] = [r18], 8
+(p[0]) ld8.nta s4[0] = [r19], 8
+(p[6]) xor r20 = s3[6], s4[6]
+       ;;
+(p[6+1])st8.nta [r8] = d[1], 8
+(p[6]) xor d[0] = d[0], r20
+       br.ctop.dptk.few 0b
+       ;;
+       mov ar.lc = r30
+       mov pr = r29, -1
+       br.ret.sptk.few rp
+END(xor_ia64_4)
+
+GLOBAL_ENTRY(xor_ia64_5)
+       .prologue
+       .fframe 0
+       .save ar.pfs, r31
+       alloc r31 = ar.pfs, 6, 0, 34, 40
+       .save ar.lc, r30
+       mov r30 = ar.lc
+       .save pr, r29
+       mov r29 = pr
+       ;;
+       .body
+       mov r8 = in1
+       mov ar.ec = 6 + 2
+       shr in0 = in0, 3
+       ;;
+       adds in0 = -1, in0
+       mov r16 = in1
+       mov r17 = in2
+       ;;
+       mov r18 = in3
+       mov ar.lc = in0
+       mov pr.rot = 1 << 16
+       mov r19 = in4
+       mov r20 = in5
+       ;;
+       .rotr s1[6+1], s2[6+1], s3[6+1], s4[6+1], s5[6+1], d[2]
+       .rotp p[6+2]
+0:
+(p[0]) ld8.nta s1[0] = [r16], 8
+(p[0]) ld8.nta s2[0] = [r17], 8
+(p[6]) xor d[0] = s1[6], s2[6]
+(p[0]) ld8.nta s3[0] = [r18], 8
+(p[0]) ld8.nta s4[0] = [r19], 8
+(p[6]) xor r21 = s3[6], s4[6]
+       ;;
+(p[0]) ld8.nta s5[0] = [r20], 8
+(p[6+1])st8.nta [r8] = d[1], 8
+(p[6]) xor d[0] = d[0], r21
+       ;;
+(p[6])   xor d[0] = d[0], s5[6]
+       nop.f 0
+       br.ctop.dptk.few 0b
+       ;;
+       mov ar.lc = r30
+       mov pr = r29, -1
+       br.ret.sptk.few rp
+END(xor_ia64_5)
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/linuxextable.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/linuxextable.c        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,67 @@
+/* Rewritten by Rusty Russell, on the backs of many others...
+   Copyright (C) 2001 Rusty Russell, 2002 Rusty Russell IBM.
+
+    This program is free software; you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation; either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program; if not, write to the Free Software
+    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+*/
+#include <linux/module.h>
+#include <linux/init.h>
+#include <asm/uaccess.h>
+#include <asm/sections.h>
+
+extern struct exception_table_entry __start___ex_table[];
+extern struct exception_table_entry __stop___ex_table[];
+
+/* Sort the kernel's built-in exception table */
+void __init sort_main_extable(void)
+{
+       sort_extable(__start___ex_table, __stop___ex_table);
+}
+
+/* Given an address, look for it in the exception tables. */
+const struct exception_table_entry *search_exception_tables(unsigned long addr)
+{
+       const struct exception_table_entry *e;
+
+       e = search_extable(__start___ex_table, __stop___ex_table-1, addr);
+       if (!e)
+               e = search_module_extables(addr);
+       return e;
+}
+
+static int core_kernel_text(unsigned long addr)
+{
+       if (addr >= (unsigned long)_stext &&
+           addr <= (unsigned long)_etext)
+               return 1;
+
+       if (addr >= (unsigned long)_sinittext &&
+           addr <= (unsigned long)_einittext)
+               return 1;
+       return 0;
+}
+
+int __kernel_text_address(unsigned long addr)
+{
+       if (core_kernel_text(addr))
+               return 1;
+       return __module_text_address(addr) != NULL;
+}
+
+int kernel_text_address(unsigned long addr)
+{
+       if (core_kernel_text(addr))
+               return 1;
+       return module_text_address(addr) != NULL;
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/machvec.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/machvec.c     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,70 @@
+#include <linux/config.h>
+#include <linux/module.h>
+
+#include <asm/machvec.h>
+#include <asm/system.h>
+
+#ifdef CONFIG_IA64_GENERIC
+
+#include <linux/kernel.h>
+#include <linux/string.h>
+
+#include <asm/page.h>
+
+struct ia64_machine_vector ia64_mv;
+EXPORT_SYMBOL(ia64_mv);
+
+static struct ia64_machine_vector *
+lookup_machvec (const char *name)
+{
+       extern struct ia64_machine_vector machvec_start[];
+       extern struct ia64_machine_vector machvec_end[];
+       struct ia64_machine_vector *mv;
+
+       for (mv = machvec_start; mv < machvec_end; ++mv)
+               if (strcmp (mv->name, name) == 0)
+                       return mv;
+
+       return 0;
+}
+
+void
+machvec_init (const char *name)
+{
+       struct ia64_machine_vector *mv;
+
+       mv = lookup_machvec(name);
+       if (!mv) {
+               panic("generic kernel failed to find machine vector for 
platform %s!", name);
+       }
+       ia64_mv = *mv;
+       printk(KERN_INFO "booting generic kernel on platform %s\n", name);
+}
+
+#endif /* CONFIG_IA64_GENERIC */
+
+void
+machvec_setup (char **arg)
+{
+}
+EXPORT_SYMBOL(machvec_setup);
+
+void
+machvec_timer_interrupt (int irq, void *dev_id, struct pt_regs *regs)
+{
+}
+EXPORT_SYMBOL(machvec_timer_interrupt);
+
+void
+machvec_dma_sync_single (struct device *hwdev, dma_addr_t dma_handle, size_t 
size, int dir)
+{
+       mb();
+}
+EXPORT_SYMBOL(machvec_dma_sync_single);
+
+void
+machvec_dma_sync_sg (struct device *hwdev, struct scatterlist *sg, int n, int 
dir)
+{
+       mb();
+}
+EXPORT_SYMBOL(machvec_dma_sync_sg);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/minstate.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/minstate.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,251 @@
+#include <linux/config.h>
+
+#include <asm/cache.h>
+
+#include "entry.h"
+
+/*
+ * For ivt.s we want to access the stack virtually so we don't have to disable 
translation
+ * on interrupts.
+ *
+ *  On entry:
+ *     r1:     pointer to current task (ar.k6)
+ */
+#define MINSTATE_START_SAVE_MIN_VIRT                                           
                \
+(pUStk)        mov ar.rsc=0;           /* set enforced lazy mode, pl 0, 
little-endian, loadrs=0 */     \
+       ;;                                                                      
                \
+(pUStk)        mov.m r24=ar.rnat;                                              
                        \
+(pUStk)        addl r22=IA64_RBS_OFFSET,r1;                    /* compute base 
of RBS */               \
+(pKStk) mov r1=sp;                                     /* get sp  */           
                \
+       ;;                                                                      
                \
+(pUStk) lfetch.fault.excl.nt1 [r22];                                           
                \
+(pUStk)        addl r1=IA64_STK_OFFSET-IA64_PT_REGS_SIZE,r1;   /* compute base 
of memory stack */      \
+(pUStk)        mov r23=ar.bspstore;                            /* save 
ar.bspstore */                  \
+       ;;                                                                      
                \
+(pUStk)        mov ar.bspstore=r22;                            /* switch to 
kernel RBS */              \
+(pKStk) addl r1=-IA64_PT_REGS_SIZE,r1;                 /* if in kernel mode, 
use sp (r12) */   \
+       ;;                                                                      
                \
+(pUStk)        mov r18=ar.bsp;                                                 
                        \
+(pUStk)        mov ar.rsc=0x3;         /* set eager mode, pl 0, little-endian, 
loadrs=0 */             \
+
+#define MINSTATE_END_SAVE_MIN_VIRT                                             
                \
+       bsw.1;                  /* switch back to bank 1 (must be last in insn 
group) */        \
+       ;;
+
+/*
+ * For mca_asm.S we want to access the stack physically since the state is 
saved before we
+ * go virtual and don't want to destroy the iip or ipsr.
+ */
+#define MINSTATE_START_SAVE_MIN_PHYS                                           
                \
+(pKStk) mov r3=IA64_KR(PER_CPU_DATA);;                                         
                \
+(pKStk) addl r3=THIS_CPU(ia64_mca_data),r3;;                                   
                \
+(pKStk) ld8 r3 = [r3];;                                                        
                        \
+(pKStk) addl r3=IA64_MCA_CPU_INIT_STACK_OFFSET,r3;;                            
                \
+(pKStk) addl sp=IA64_STK_OFFSET-IA64_PT_REGS_SIZE,r3;                          
                \
+(pUStk)        mov ar.rsc=0;           /* set enforced lazy mode, pl 0, 
little-endian, loadrs=0 */     \
+(pUStk)        addl r22=IA64_RBS_OFFSET,r1;            /* compute base of 
register backing store */    \
+       ;;                                                                      
                \
+(pUStk)        mov r24=ar.rnat;                                                
                        \
+(pUStk)        addl r1=IA64_STK_OFFSET-IA64_PT_REGS_SIZE,r1;   /* compute base 
of memory stack */      \
+(pUStk)        mov r23=ar.bspstore;                            /* save 
ar.bspstore */                  \
+(pUStk)        dep r22=-1,r22,61,3;                    /* compute kernel 
virtual addr of RBS */        \
+       ;;                                                                      
                \
+(pKStk) addl r1=-IA64_PT_REGS_SIZE,r1;         /* if in kernel mode, use sp 
(r12) */           \
+(pUStk)        mov ar.bspstore=r22;                    /* switch to kernel RBS 
*/                      \
+       ;;                                                                      
                \
+(pUStk)        mov r18=ar.bsp;                                                 
                        \
+(pUStk)        mov ar.rsc=0x3;         /* set eager mode, pl 0, little-endian, 
loadrs=0 */             \
+
+#define MINSTATE_END_SAVE_MIN_PHYS                                             
                \
+       dep r12=-1,r12,61,3;            /* make sp a kernel virtual address */  
                \
+       ;;
+
+#ifdef MINSTATE_VIRT
+# define MINSTATE_GET_CURRENT(reg)     mov reg=IA64_KR(CURRENT)
+# define MINSTATE_START_SAVE_MIN       MINSTATE_START_SAVE_MIN_VIRT
+# define MINSTATE_END_SAVE_MIN         MINSTATE_END_SAVE_MIN_VIRT
+#endif
+
+#ifdef MINSTATE_PHYS
+# define MINSTATE_GET_CURRENT(reg)     mov reg=IA64_KR(CURRENT);; tpa reg=reg
+# define MINSTATE_START_SAVE_MIN       MINSTATE_START_SAVE_MIN_PHYS
+# define MINSTATE_END_SAVE_MIN         MINSTATE_END_SAVE_MIN_PHYS
+#endif
+
+/*
+ * DO_SAVE_MIN switches to the kernel stacks (if necessary) and saves
+ * the minimum state necessary that allows us to turn psr.ic back
+ * on.
+ *
+ * Assumed state upon entry:
+ *     psr.ic: off
+ *     r31:    contains saved predicates (pr)
+ *
+ * Upon exit, the state is as follows:
+ *     psr.ic: off
+ *      r2 = points to &pt_regs.r16
+ *      r8 = contents of ar.ccv
+ *      r9 = contents of ar.csd
+ *     r10 = contents of ar.ssd
+ *     r11 = FPSR_DEFAULT
+ *     r12 = kernel sp (kernel virtual address)
+ *     r13 = points to current task_struct (kernel virtual address)
+ *     p15 = TRUE if psr.i is set in cr.ipsr
+ *     predicate registers (other than p2, p3, and p15), b6, r3, r14, r15:
+ *             preserved
+ *
+ * Note that psr.ic is NOT turned on by this macro.  This is so that
+ * we can pass interruption state as arguments to a handler.
+ */
+#define DO_SAVE_MIN(COVER,SAVE_IFS,EXTRA)                                      
                \
+       MINSTATE_GET_CURRENT(r16);      /* M (or M;;I) */                       
                \
+       mov r27=ar.rsc;                 /* M */                                 
                \
+       mov r20=r1;                     /* A */                                 
                \
+       mov r25=ar.unat;                /* M */                                 
                \
+       mov r29=cr.ipsr;                /* M */                                 
                \
+       mov r26=ar.pfs;                 /* I */                                 
                \
+       mov r28=cr.iip;                 /* M */                                 
                \
+       mov r21=ar.fpsr;                /* M */                                 
                \
+       COVER;                          /* B;; (or nothing) */                  
                \
+       ;;                                                                      
                \
+       adds r16=IA64_TASK_THREAD_ON_USTACK_OFFSET,r16;                         
                \
+       ;;                                                                      
                \
+       ld1 r17=[r16];                          /* load 
current->thread.on_ustack flag */       \
+       st1 [r16]=r0;                           /* clear 
current->thread.on_ustack flag */      \
+       adds r1=-IA64_TASK_THREAD_ON_USTACK_OFFSET,r16                          
                \
+       /* switch from user to kernel RBS: */                                   
                \
+       ;;                                                                      
                \
+       invala;                         /* M */                                 
                \
+       SAVE_IFS;                                                               
                \
+       cmp.eq pKStk,pUStk=r0,r17;              /* are we in kernel mode 
already? */            \
+       ;;                                                                      
                \
+       MINSTATE_START_SAVE_MIN                                                 
                \
+       adds r17=2*L1_CACHE_BYTES,r1;           /* really: biggest cache-line 
size */           \
+       adds r16=PT(CR_IPSR),r1;                                                
                \
+       ;;                                                                      
                \
+       lfetch.fault.excl.nt1 [r17],L1_CACHE_BYTES;                             
                \
+       st8 [r16]=r29;          /* save cr.ipsr */                              
                \
+       ;;                                                                      
                \
+       lfetch.fault.excl.nt1 [r17];                                            
                \
+       tbit.nz p15,p0=r29,IA64_PSR_I_BIT;                                      
                \
+       mov r29=b0                                                              
                \
+       ;;                                                                      
                \
+       adds r16=PT(R8),r1;     /* initialize first base pointer */             
                \
+       adds r17=PT(R9),r1;     /* initialize second base pointer */            
                \
+(pKStk)        mov r18=r0;             /* make sure r18 isn't NaT */           
                        \
+       ;;                                                                      
                \
+.mem.offset 0,0; st8.spill [r16]=r8,16;                                        
                        \
+.mem.offset 8,0; st8.spill [r17]=r9,16;                                        
                        \
+        ;;                                                                     
                \
+.mem.offset 0,0; st8.spill [r16]=r10,24;                                       
                \
+.mem.offset 8,0; st8.spill [r17]=r11,24;                                       
                \
+        ;;                                                                     
                \
+       st8 [r16]=r28,16;       /* save cr.iip */                               
                \
+       st8 [r17]=r30,16;       /* save cr.ifs */                               
                \
+(pUStk)        sub r18=r18,r22;        /* r18=RSE.ndirty*8 */                  
                        \
+       mov r8=ar.ccv;                                                          
                \
+       mov r9=ar.csd;                                                          
                \
+       mov r10=ar.ssd;                                                         
                \
+       movl r11=FPSR_DEFAULT;   /* L-unit */                                   
                \
+       ;;                                                                      
                \
+       st8 [r16]=r25,16;       /* save ar.unat */                              
                \
+       st8 [r17]=r26,16;       /* save ar.pfs */                               
                \
+       shl r18=r18,16;         /* compute ar.rsc to be used for "loadrs" */    
                \
+       ;;                                                                      
                \
+       st8 [r16]=r27,16;       /* save ar.rsc */                               
                \
+(pUStk)        st8 [r17]=r24,16;       /* save ar.rnat */                      
                        \
+(pKStk)        adds r17=16,r17;        /* skip over ar_rnat field */           
                        \
+       ;;                      /* avoid RAW on r16 & r17 */                    
                \
+(pUStk)        st8 [r16]=r23,16;       /* save ar.bspstore */                  
                        \
+       st8 [r17]=r31,16;       /* save predicates */                           
                \
+(pKStk)        adds r16=16,r16;        /* skip over ar_bspstore field */       
                        \
+       ;;                                                                      
                \
+       st8 [r16]=r29,16;       /* save b0 */                                   
                \
+       st8 [r17]=r18,16;       /* save ar.rsc value for "loadrs" */            
                \
+       cmp.eq pNonSys,pSys=r0,r0       /* initialize pSys=0, pNonSys=1 */      
                \
+       ;;                                                                      
                \
+.mem.offset 0,0; st8.spill [r16]=r20,16;       /* save original r1 */          
                \
+.mem.offset 8,0; st8.spill [r17]=r12,16;                                       
                \
+       adds r12=-16,r1;        /* switch to kernel memory stack (with 16 bytes 
of scratch) */  \
+       ;;                                                                      
                \
+.mem.offset 0,0; st8.spill [r16]=r13,16;                                       
                \
+.mem.offset 8,0; st8.spill [r17]=r21,16;       /* save ar.fpsr */              
                \
+       mov r13=IA64_KR(CURRENT);       /* establish `current' */               
                \
+       ;;                                                                      
                \
+.mem.offset 0,0; st8.spill [r16]=r15,16;                                       
                \
+.mem.offset 8,0; st8.spill [r17]=r14,16;                                       
                \
+       ;;                                                                      
                \
+.mem.offset 0,0; st8.spill [r16]=r2,16;                                        
                        \
+.mem.offset 8,0; st8.spill [r17]=r3,16;                                        
                        \
+       adds r2=IA64_PT_REGS_R16_OFFSET,r1;                                     
                \
+       ;;                                                                      
                \
+       EXTRA;                                                                  
                \
+       movl r1=__gp;           /* establish kernel global pointer */           
                \
+       ;;                                                                      
                \
+       MINSTATE_END_SAVE_MIN
+
+/*
+ * SAVE_REST saves the remainder of pt_regs (with psr.ic on).
+ *
+ * Assumed state upon entry:
+ *     psr.ic: on
+ *     r2:     points to &pt_regs.r16
+ *     r3:     points to &pt_regs.r17
+ *     r8:     contents of ar.ccv
+ *     r9:     contents of ar.csd
+ *     r10:    contents of ar.ssd
+ *     r11:    FPSR_DEFAULT
+ *
+ * Registers r14 and r15 are guaranteed not to be touched by SAVE_REST.
+ */
+#define SAVE_REST                              \
+.mem.offset 0,0; st8.spill [r2]=r16,16;                \
+.mem.offset 8,0; st8.spill [r3]=r17,16;                \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r18,16;                \
+.mem.offset 8,0; st8.spill [r3]=r19,16;                \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r20,16;                \
+.mem.offset 8,0; st8.spill [r3]=r21,16;                \
+       mov r18=b6;                             \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r22,16;                \
+.mem.offset 8,0; st8.spill [r3]=r23,16;                \
+       mov r19=b7;                             \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r24,16;                \
+.mem.offset 8,0; st8.spill [r3]=r25,16;                \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r26,16;                \
+.mem.offset 8,0; st8.spill [r3]=r27,16;                \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r28,16;                \
+.mem.offset 8,0; st8.spill [r3]=r29,16;                \
+       ;;                                      \
+.mem.offset 0,0; st8.spill [r2]=r30,16;                \
+.mem.offset 8,0; st8.spill [r3]=r31,32;                \
+       ;;                                      \
+       mov ar.fpsr=r11;        /* M-unit */    \
+       st8 [r2]=r8,8;          /* ar.ccv */    \
+       adds r24=PT(B6)-PT(F7),r3;              \
+       ;;                                      \
+       stf.spill [r2]=f6,32;                   \
+       stf.spill [r3]=f7,32;                   \
+       ;;                                      \
+       stf.spill [r2]=f8,32;                   \
+       stf.spill [r3]=f9,32;                   \
+       ;;                                      \
+       stf.spill [r2]=f10;                     \
+       stf.spill [r3]=f11;                     \
+       adds r25=PT(B7)-PT(F11),r3;             \
+       ;;                                      \
+       st8 [r24]=r18,16;       /* b6 */        \
+       st8 [r25]=r19,16;       /* b7 */        \
+       ;;                                      \
+       st8 [r24]=r9;           /* ar.csd */    \
+       st8 [r25]=r10;          /* ar.ssd */    \
+       ;;
+
+#define SAVE_MIN_WITH_COVER    DO_SAVE_MIN(cover, mov r30=cr.ifs,)
+#define SAVE_MIN_WITH_COVER_R19        DO_SAVE_MIN(cover, mov r30=cr.ifs, mov 
r15=r19)
+#define SAVE_MIN               DO_SAVE_MIN(     , mov r30=r0, )
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/patch.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/patch.c       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,189 @@
+/*
+ * Instruction-patching support.
+ *
+ * Copyright (C) 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#include <linux/init.h>
+#include <linux/string.h>
+
+#include <asm/patch.h>
+#include <asm/processor.h>
+#include <asm/sections.h>
+#include <asm/system.h>
+#include <asm/unistd.h>
+
+/*
+ * This was adapted from code written by Tony Luck:
+ *
+ * The 64-bit value in a "movl reg=value" is scattered between the two words 
of the bundle
+ * like this:
+ *
+ * 6  6         5         4         3         2         1
+ * 3210987654321098765432109876543210987654321098765432109876543210
+ * ABBBBBBBBBBBBBBBBBBBBBBBCCCCCCCCCCCCCCCCCCDEEEEEFFFFFFFFFGGGGGGG
+ *
+ * CCCCCCCCCCCCCCCCCCxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
+ * xxxxAFFFFFFFFFEEEEEDxGGGGGGGxxxxxxxxxxxxxBBBBBBBBBBBBBBBBBBBBBBB
+ */
+static u64
+get_imm64 (u64 insn_addr)
+{
+       u64 *p = (u64 *) (insn_addr & -16);     /* mask out slot number */
+
+       return ( (p[1] & 0x0800000000000000UL) << 4)  | /*A*/
+               ((p[1] & 0x00000000007fffffUL) << 40) | /*B*/
+               ((p[0] & 0xffffc00000000000UL) >> 24) | /*C*/
+               ((p[1] & 0x0000100000000000UL) >> 23) | /*D*/
+               ((p[1] & 0x0003e00000000000UL) >> 29) | /*E*/
+               ((p[1] & 0x07fc000000000000UL) >> 43) | /*F*/
+               ((p[1] & 0x000007f000000000UL) >> 36);  /*G*/
+}
+
+/* Patch instruction with "val" where "mask" has 1 bits. */
+void
+ia64_patch (u64 insn_addr, u64 mask, u64 val)
+{
+       u64 m0, m1, v0, v1, b0, b1, *b = (u64 *) (insn_addr & -16);
+#      define insn_mask ((1UL << 41) - 1)
+       unsigned long shift;
+
+       b0 = b[0]; b1 = b[1];
+       shift = 5 + 41 * (insn_addr % 16); /* 5 bits of template, then 3 x 
41-bit instructions */
+       if (shift >= 64) {
+               m1 = mask << (shift - 64);
+               v1 = val << (shift - 64);
+       } else {
+               m0 = mask << shift; m1 = mask >> (64 - shift);
+               v0 = val  << shift; v1 = val >> (64 - shift);
+               b[0] = (b0 & ~m0) | (v0 & m0);
+       }
+       b[1] = (b1 & ~m1) | (v1 & m1);
+}
+
+void
+ia64_patch_imm64 (u64 insn_addr, u64 val)
+{
+       ia64_patch(insn_addr,
+                  0x01fffefe000UL, (  ((val & 0x8000000000000000UL) >> 27) /* 
bit 63 -> 36 */
+                                    | ((val & 0x0000000000200000UL) <<  0) /* 
bit 21 -> 21 */
+                                    | ((val & 0x00000000001f0000UL) <<  6) /* 
bit 16 -> 22 */
+                                    | ((val & 0x000000000000ff80UL) << 20) /* 
bit  7 -> 27 */
+                                    | ((val & 0x000000000000007fUL) << 13) /* 
bit  0 -> 13 */));
+       ia64_patch(insn_addr - 1, 0x1ffffffffffUL, val >> 22);
+}
+
+void
+ia64_patch_imm60 (u64 insn_addr, u64 val)
+{
+       ia64_patch(insn_addr,
+                  0x011ffffe000UL, (  ((val & 0x0800000000000000UL) >> 23) /* 
bit 59 -> 36 */
+                                    | ((val & 0x00000000000fffffUL) << 13) /* 
bit  0 -> 13 */));
+       ia64_patch(insn_addr - 1, 0x1fffffffffcUL, val >> 18);
+}
+
+/*
+ * We need sometimes to load the physical address of a kernel
+ * object.  Often we can convert the virtual address to physical
+ * at execution time, but sometimes (either for performance reasons
+ * or during error recovery) we cannot to this.  Patch the marked
+ * bundles to load the physical address.
+ */
+void __init
+ia64_patch_vtop (unsigned long start, unsigned long end)
+{
+       s32 *offp = (s32 *) start;
+       u64 ip;
+
+       while (offp < (s32 *) end) {
+               ip = (u64) offp + *offp;
+
+               /* replace virtual address with corresponding physical address: 
*/
+               ia64_patch_imm64(ip, ia64_tpa(get_imm64(ip)));
+               ia64_fc((void *) ip);
+               ++offp;
+       }
+       ia64_sync_i();
+       ia64_srlz_i();
+}
+
+void
+ia64_patch_mckinley_e9 (unsigned long start, unsigned long end)
+{
+       static int first_time = 1;
+       int need_workaround;
+       s32 *offp = (s32 *) start;
+       u64 *wp;
+
+       need_workaround = (local_cpu_data->family == 0x1f && 
local_cpu_data->model == 0);
+
+       if (first_time) {
+               first_time = 0;
+               if (need_workaround)
+                       printk(KERN_INFO "Leaving McKinley Errata 9 workaround 
enabled\n");
+               else
+                       printk(KERN_INFO "McKinley Errata 9 workaround not 
needed; "
+                              "disabling it\n");
+       }
+       if (need_workaround)
+               return;
+
+       while (offp < (s32 *) end) {
+               wp = (u64 *) ia64_imva((char *) offp + *offp);
+               wp[0] = 0x0000000100000000UL; /* nop.m 0; nop.i 0; nop.i 0 */
+               wp[1] = 0x0004000000000200UL;
+               wp[2] = 0x0000000100000011UL; /* nop.m 0; nop.i 0; 
br.ret.sptk.many b6 */
+               wp[3] = 0x0084006880000200UL;
+               ia64_fc(wp); ia64_fc(wp + 2);
+               ++offp;
+       }
+       ia64_sync_i();
+       ia64_srlz_i();
+}
+
+static void
+patch_fsyscall_table (unsigned long start, unsigned long end)
+{
+       extern unsigned long fsyscall_table[NR_syscalls];
+       s32 *offp = (s32 *) start;
+       u64 ip;
+
+       while (offp < (s32 *) end) {
+               ip = (u64) ia64_imva((char *) offp + *offp);
+               ia64_patch_imm64(ip, (u64) fsyscall_table);
+               ia64_fc((void *) ip);
+               ++offp;
+       }
+       ia64_sync_i();
+       ia64_srlz_i();
+}
+
+static void
+patch_brl_fsys_bubble_down (unsigned long start, unsigned long end)
+{
+       extern char fsys_bubble_down[];
+       s32 *offp = (s32 *) start;
+       u64 ip;
+
+       while (offp < (s32 *) end) {
+               ip = (u64) offp + *offp;
+               ia64_patch_imm60((u64) ia64_imva((void *) ip),
+                                (u64) (fsys_bubble_down - (ip & -16)) / 16);
+               ia64_fc((void *) ip);
+               ++offp;
+       }
+       ia64_sync_i();
+       ia64_srlz_i();
+}
+
+void
+ia64_patch_gate (void)
+{
+#      define START(name)      ((unsigned long) 
__start_gate_##name##_patchlist)
+#      define END(name)        ((unsigned long)__end_gate_##name##_patchlist)
+
+       patch_fsyscall_table(START(fsyscall), END(fsyscall));
+       patch_brl_fsys_bubble_down(START(brl_fsys_bubble_down), 
END(brl_fsys_bubble_down));
+       ia64_patch_vtop(START(vtop), END(vtop));
+       ia64_patch_mckinley_e9(START(mckinley_e9), END(mckinley_e9));
+}
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/pcdp.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/pcdp.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,84 @@
+/*
+ * Definitions for PCDP-defined console devices
+ *
+ * v1.0a: http://www.dig64.org/specifications/DIG64_HCDPv10a_01.pdf
+ * v2.0:  http://www.dig64.org/specifications/DIG64_HCDPv20_042804.pdf
+ *
+ * (c) Copyright 2002, 2004 Hewlett-Packard Development Company, L.P.
+ *     Khalid Aziz <khalid.aziz@xxxxxx>
+ *     Bjorn Helgaas <bjorn.helgaas@xxxxxx>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#define PCDP_CONSOLE                   0
+#define PCDP_DEBUG                     1
+#define PCDP_CONSOLE_OUTPUT            2
+#define PCDP_CONSOLE_INPUT             3
+
+#define PCDP_UART                      (0 << 3)
+#define PCDP_VGA                       (1 << 3)
+#define PCDP_USB                       (2 << 3)
+
+/* pcdp_uart.type and pcdp_device.type */
+#define PCDP_CONSOLE_UART              (PCDP_UART | PCDP_CONSOLE)
+#define PCDP_DEBUG_UART                        (PCDP_UART | PCDP_DEBUG)
+#define PCDP_CONSOLE_VGA               (PCDP_VGA  | PCDP_CONSOLE_OUTPUT)
+#define PCDP_CONSOLE_USB               (PCDP_USB  | PCDP_CONSOLE_INPUT)
+
+/* pcdp_uart.flags */
+#define PCDP_UART_EDGE_SENSITIVE       (1 << 0)
+#define PCDP_UART_ACTIVE_LOW           (1 << 1)
+#define PCDP_UART_PRIMARY_CONSOLE      (1 << 2)
+#define PCDP_UART_IRQ                  (1 << 6) /* in pci_func for rev < 3 */
+#define PCDP_UART_PCI                  (1 << 7) /* in pci_func for rev < 3 */
+
+struct pcdp_uart {
+       u8                              type;
+       u8                              bits;
+       u8                              parity;
+       u8                              stop_bits;
+       u8                              pci_seg;
+       u8                              pci_bus;
+       u8                              pci_dev;
+       u8                              pci_func;
+       u64                             baud;
+       struct acpi_generic_address     addr;
+       u16                             pci_dev_id;
+       u16                             pci_vendor_id;
+       u32                             gsi;
+       u32                             clock_rate;
+       u8                              pci_prog_intfc;
+       u8                              flags;
+};
+
+struct pcdp_vga {
+       u8                      count;          /* address space descriptors */
+};
+
+/* pcdp_device.flags */
+#define PCDP_PRIMARY_CONSOLE   1
+
+struct pcdp_device {
+       u8                      type;
+       u8                      flags;
+       u16                     length;
+       u16                     efi_index;
+};
+
+struct pcdp {
+       u8                      signature[4];
+       u32                     length;
+       u8                      rev;            /* PCDP v2.0 is rev 3 */
+       u8                      chksum;
+       u8                      oemid[6];
+       u8                      oem_tabid[8];
+       u32                     oem_rev;
+       u8                      creator_id[4];
+       u32                     creator_rev;
+       u32                     num_uarts;
+       struct pcdp_uart        uart[0];        /* actual size is num_uarts */
+       /* remainder of table is pcdp_device structures */
+};
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/linux/sal.c
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/linux/sal.c Tue Aug 16 04:15:23 2005
@@ -0,0 +1,302 @@
+/*
+ * System Abstraction Layer (SAL) interface routines.
+ *
+ * Copyright (C) 1998, 1999, 2001, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ */
+#include <linux/config.h>
+
+#include <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/module.h>
+#include <linux/spinlock.h>
+#include <linux/string.h>
+
+#include <asm/page.h>
+#include <asm/sal.h>
+#include <asm/pal.h>
+
+ __cacheline_aligned DEFINE_SPINLOCK(sal_lock);
+unsigned long sal_platform_features;
+
+unsigned short sal_revision;
+unsigned short sal_version;
+
+#define SAL_MAJOR(x) ((x) >> 8)
+#define SAL_MINOR(x) ((x) & 0xff)
+
+static struct {
+       void *addr;     /* function entry point */
+       void *gpval;    /* gp value to use */
+} pdesc;
+
+static long
+default_handler (void)
+{
+       return -1;
+}
+
+ia64_sal_handler ia64_sal = (ia64_sal_handler) default_handler;
+ia64_sal_desc_ptc_t *ia64_ptc_domain_info;
+
+const char *
+ia64_sal_strerror (long status)
+{
+       const char *str;
+       switch (status) {
+             case 0: str = "Call completed without error"; break;
+             case 1: str = "Effect a warm boot of the system to complete "
+                             "the update"; break;
+             case -1: str = "Not implemented"; break;
+             case -2: str = "Invalid argument"; break;
+             case -3: str = "Call completed with error"; break;
+             case -4: str = "Virtual address not registered"; break;
+             case -5: str = "No information available"; break;
+             case -6: str = "Insufficient space to add the entry"; break;
+             case -7: str = "Invalid entry_addr value"; break;
+             case -8: str = "Invalid interrupt vector"; break;
+             case -9: str = "Requested memory not available"; break;
+             case -10: str = "Unable to write to the NVM device"; break;
+             case -11: str = "Invalid partition type specified"; break;
+             case -12: str = "Invalid NVM_Object id specified"; break;
+             case -13: str = "NVM_Object already has the maximum number "
+                               "of partitions"; break;
+             case -14: str = "Insufficient space in partition for the "
+                               "requested write sub-function"; break;
+             case -15: str = "Insufficient data buffer space for the "
+                               "requested read record sub-function"; break;
+             case -16: str = "Scratch buffer required for the write/delete "
+                               "sub-function"; break;
+             case -17: str = "Insufficient space in the NVM_Object for the "
+                               "requested create sub-function"; break;
+             case -18: str = "Invalid value specified in the partition_rec "
+                               "argument"; break;
+             case -19: str = "Record oriented I/O not supported for this "
+                               "partition"; break;
+             case -20: str = "Bad format of record to be written or "
+                               "required keyword variable not "
+                               "specified"; break;
+             default: str = "Unknown SAL status code"; break;
+       }
+       return str;
+}
+
+void __init
+ia64_sal_handler_init (void *entry_point, void *gpval)
+{
+       /* fill in the SAL procedure descriptor and point ia64_sal to it: */
+       pdesc.addr = entry_point;
+       pdesc.gpval = gpval;
+       ia64_sal = (ia64_sal_handler) &pdesc;
+}
+
+static void __init
+check_versions (struct ia64_sal_systab *systab)
+{
+       sal_revision = (systab->sal_rev_major << 8) | systab->sal_rev_minor;
+       sal_version = (systab->sal_b_rev_major << 8) | systab->sal_b_rev_minor;
+
+       /* Check for broken firmware */
+       if ((sal_revision == SAL_VERSION_CODE(49, 29))
+           && (sal_version == SAL_VERSION_CODE(49, 29)))
+       {
+               /*
+                * Old firmware for zx2000 prototypes have this weird version 
number,
+                * reset it to something sane.
+                */
+               sal_revision = SAL_VERSION_CODE(2, 8);
+               sal_version = SAL_VERSION_CODE(0, 0);
+       }
+}
+
+static void __init
+sal_desc_entry_point (void *p)
+{
+       struct ia64_sal_desc_entry_point *ep = p;
+       ia64_pal_handler_init(__va(ep->pal_proc));
+       ia64_sal_handler_init(__va(ep->sal_proc), __va(ep->gp));
+}
+
+#ifdef CONFIG_SMP
+static void __init
+set_smp_redirect (int flag)
+{
+#ifndef CONFIG_HOTPLUG_CPU
+       if (no_int_routing)
+               smp_int_redirect &= ~flag;
+       else
+               smp_int_redirect |= flag;
+#else
+       /*
+        * For CPU Hotplug we dont want to do any chipset supported
+        * interrupt redirection. The reason is this would require that
+        * All interrupts be stopped and hard bind the irq to a cpu.
+        * Later when the interrupt is fired we need to set the redir hint
+        * on again in the vector. This is combersome for something that the
+        * user mode irq balancer will solve anyways.
+        */
+       no_int_routing=1;
+       smp_int_redirect &= ~flag;
+#endif
+}
+#else
+#define set_smp_redirect(flag) do { } while (0)
+#endif
+
+static void __init
+sal_desc_platform_feature (void *p)
+{
+       struct ia64_sal_desc_platform_feature *pf = p;
+       sal_platform_features = pf->feature_mask;
+
+       printk(KERN_INFO "SAL Platform features:");
+       if (!sal_platform_features) {
+               printk(" None\n");
+               return;
+       }
+
+       if (sal_platform_features & IA64_SAL_PLATFORM_FEATURE_BUS_LOCK)
+               printk(" BusLock");
+       if (sal_platform_features & IA64_SAL_PLATFORM_FEATURE_IRQ_REDIR_HINT) {
+               printk(" IRQ_Redirection");
+               set_smp_redirect(SMP_IRQ_REDIRECTION);
+       }
+       if (sal_platform_features & IA64_SAL_PLATFORM_FEATURE_IPI_REDIR_HINT) {
+               printk(" IPI_Redirection");
+               set_smp_redirect(SMP_IPI_REDIRECTION);
+       }
+       if (sal_platform_features & IA64_SAL_PLATFORM_FEATURE_ITC_DRIFT)
+               printk(" ITC_Drift");
+       printk("\n");
+}
+
+#ifdef CONFIG_SMP
+static void __init
+sal_desc_ap_wakeup (void *p)
+{
+       struct ia64_sal_desc_ap_wakeup *ap = p;
+
+       switch (ap->mechanism) {
+       case IA64_SAL_AP_EXTERNAL_INT:
+               ap_wakeup_vector = ap->vector;
+               printk(KERN_INFO "SAL: AP wakeup using external interrupt "
+                               "vector 0x%lx\n", ap_wakeup_vector);
+               break;
+       default:
+               printk(KERN_ERR "SAL: AP wakeup mechanism unsupported!\n");
+               break;
+       }
+}
+
+static void __init
+chk_nointroute_opt(void)
+{
+       char *cp;
+       extern char saved_command_line[];
+
+       for (cp = saved_command_line; *cp; ) {
+               if (memcmp(cp, "nointroute", 10) == 0) {
+                       no_int_routing = 1;
+                       printk ("no_int_routing on\n");
+                       break;
+               } else {
+                       while (*cp != ' ' && *cp)
+                               ++cp;
+                       while (*cp == ' ')
+                               ++cp;
+               }
+       }
+}
+
+#else
+static void __init sal_desc_ap_wakeup(void *p) { }
+#endif
+
+void __init
+ia64_sal_init (struct ia64_sal_systab *systab)
+{
+       char *p;
+       int i;
+
+       if (!systab) {
+               printk(KERN_WARNING "Hmm, no SAL System Table.\n");
+               return;
+       }
+
+       if (strncmp(systab->signature, "SST_", 4) != 0)
+               printk(KERN_ERR "bad signature in system table!");
+
+       check_versions(systab);
+#ifdef CONFIG_SMP
+       chk_nointroute_opt();
+#endif
+
+       /* revisions are coded in BCD, so %x does the job for us */
+       printk(KERN_INFO "SAL %x.%x: %.32s %.32s%sversion %x.%x\n",
+                       SAL_MAJOR(sal_revision), SAL_MINOR(sal_revision),
+                       systab->oem_id, systab->product_id,
+                       systab->product_id[0] ? " " : "",
+                       SAL_MAJOR(sal_version), SAL_MINOR(sal_version));
+
+       p = (char *) (systab + 1);
+       for (i = 0; i < systab->entry_count; i++) {
+               /*
+                * The first byte of each entry type contains the type
+                * descriptor.
+                */
+               switch (*p) {
+               case SAL_DESC_ENTRY_POINT:
+                       sal_desc_entry_point(p);
+                       break;
+               case SAL_DESC_PLATFORM_FEATURE:
+                       sal_desc_platform_feature(p);
+                       break;
+               case SAL_DESC_PTC:
+                       ia64_ptc_domain_info = (ia64_sal_desc_ptc_t *)p;
+                       break;
+               case SAL_DESC_AP_WAKEUP:
+                       sal_desc_ap_wakeup(p);
+                       break;
+               }
+               p += SAL_DESC_SIZE(*p);
+       }
+}
+
+int
+ia64_sal_oemcall(struct ia64_sal_retval *isrvp, u64 oemfunc, u64 arg1,
+                u64 arg2, u64 arg3, u64 arg4, u64 arg5, u64 arg6, u64 arg7)
+{
+       if (oemfunc < IA64_SAL_OEMFUNC_MIN || oemfunc > IA64_SAL_OEMFUNC_MAX)
+               return -1;
+       SAL_CALL(*isrvp, oemfunc, arg1, arg2, arg3, arg4, arg5, arg6, arg7);
+       return 0;
+}
+EXPORT_SYMBOL(ia64_sal_oemcall);
+
+int
+ia64_sal_oemcall_nolock(struct ia64_sal_retval *isrvp, u64 oemfunc, u64 arg1,
+                       u64 arg2, u64 arg3, u64 arg4, u64 arg5, u64 arg6,
+                       u64 arg7)
+{
+       if (oemfunc < IA64_SAL_OEMFUNC_MIN || oemfunc > IA64_SAL_OEMFUNC_MAX)
+               return -1;
+       SAL_CALL_NOLOCK(*isrvp, oemfunc, arg1, arg2, arg3, arg4, arg5, arg6,
+                       arg7);
+       return 0;
+}
+EXPORT_SYMBOL(ia64_sal_oemcall_nolock);
+
+int
+ia64_sal_oemcall_reentrant(struct ia64_sal_retval *isrvp, u64 oemfunc,
+                          u64 arg1, u64 arg2, u64 arg3, u64 arg4, u64 arg5,
+                          u64 arg6, u64 arg7)
+{
+       if (oemfunc < IA64_SAL_OEMFUNC_MIN || oemfunc > IA64_SAL_OEMFUNC_MAX)
+               return -1;
+       SAL_CALL_REENTRANT(*isrvp, oemfunc, arg1, arg2, arg3, arg4, arg5, arg6,
+                          arg7);
+       return 0;
+}
+EXPORT_SYMBOL(ia64_sal_oemcall_reentrant);
diff -r b5196e075602 -r e3d811cca4e1 xen/arch/ia64/xen.lds.S
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/arch/ia64/xen.lds.S   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,251 @@
+#include <linux/config.h>
+
+#include <asm/cache.h>
+#include <asm/ptrace.h>
+#include <asm/system.h>
+#include <asm/pgtable.h>
+
+#define LOAD_OFFSET    (KERNEL_START - KERNEL_TR_PAGE_SIZE)
+#include <asm-generic/vmlinux.lds.h>
+
+OUTPUT_FORMAT("elf64-ia64-little")
+OUTPUT_ARCH(ia64)
+ENTRY(phys_start)
+jiffies = jiffies_64;
+PHDRS {
+  code   PT_LOAD;
+  percpu PT_LOAD;
+  data   PT_LOAD;
+}
+SECTIONS
+{
+  /* Sections to be discarded */
+  /DISCARD/ : {
+       *(.exit.text)
+       *(.exit.data)
+       *(.exitcall.exit)
+       *(.IA_64.unwind.exit.text)
+       *(.IA_64.unwind_info.exit.text)
+       }
+
+  v = PAGE_OFFSET;     /* this symbol is here to make debugging easier... */
+  phys_start = _start - LOAD_OFFSET;
+
+  code : { } :code
+  . = KERNEL_START;
+
+  _text = .;
+  _stext = .;
+
+  .text : AT(ADDR(.text) - LOAD_OFFSET)
+    {
+       *(.text.ivt)
+       *(.text)
+       SCHED_TEXT
+       LOCK_TEXT
+       *(.gnu.linkonce.t*)
+    }
+  .text2 : AT(ADDR(.text2) - LOAD_OFFSET)
+       { *(.text2) }
+#ifdef CONFIG_SMP
+  .text.lock : AT(ADDR(.text.lock) - LOAD_OFFSET)
+       { *(.text.lock) }
+#endif
+  _etext = .;
+
+  /* Read-only data */
+
+  /* Exception table */
+  . = ALIGN(16);
+  __ex_table : AT(ADDR(__ex_table) - LOAD_OFFSET)
+       {
+         __start___ex_table = .;
+         *(__ex_table)
+         __stop___ex_table = .;
+       }
+
+  .data.patch.vtop : AT(ADDR(.data.patch.vtop) - LOAD_OFFSET)
+       {
+         __start___vtop_patchlist = .;
+         *(.data.patch.vtop)
+         __end___vtop_patchlist = .;
+       }
+
+  .data.patch.mckinley_e9 : AT(ADDR(.data.patch.mckinley_e9) - LOAD_OFFSET)
+       {
+         __start___mckinley_e9_bundles = .;
+         *(.data.patch.mckinley_e9)
+         __end___mckinley_e9_bundles = .;
+       }
+
+  /* Global data */
+  _data = .;
+
+#if defined(CONFIG_IA64_GENERIC)
+  /* Machine Vector */
+  . = ALIGN(16);
+  .machvec : AT(ADDR(.machvec) - LOAD_OFFSET)
+       {
+         machvec_start = .;
+         *(.machvec)
+         machvec_end = .;
+       }
+#endif
+
+  /* Unwind info & table: */
+  . = ALIGN(8);
+  .IA_64.unwind_info : AT(ADDR(.IA_64.unwind_info) - LOAD_OFFSET)
+       { *(.IA_64.unwind_info*) }
+  .IA_64.unwind : AT(ADDR(.IA_64.unwind) - LOAD_OFFSET)
+       {
+         __start_unwind = .;
+         *(.IA_64.unwind*)
+         __end_unwind = .;
+       }
+
+  RODATA
+
+  .opd : AT(ADDR(.opd) - LOAD_OFFSET)
+       { *(.opd) }
+
+  /* Initialization code and data: */
+
+  . = ALIGN(PAGE_SIZE);
+  __init_begin = .;
+  .init.text : AT(ADDR(.init.text) - LOAD_OFFSET)
+       {
+         _sinittext = .;
+         *(.init.text)
+         _einittext = .;
+       }
+
+  .init.data : AT(ADDR(.init.data) - LOAD_OFFSET)
+       { *(.init.data) }
+
+  .init.ramfs : AT(ADDR(.init.ramfs) - LOAD_OFFSET)
+       {
+         __initramfs_start = .;
+         *(.init.ramfs)
+         __initramfs_end = .;
+       }
+
+   . = ALIGN(16);
+  .init.setup : AT(ADDR(.init.setup) - LOAD_OFFSET)
+        {
+         __setup_start = .;
+         *(.init.setup)
+         __setup_end = .;
+       }
+  .initcall.init : AT(ADDR(.initcall.init) - LOAD_OFFSET)
+       {
+         __initcall_start = .;
+         *(.initcall1.init)
+         *(.initcall2.init)
+         *(.initcall3.init)
+         *(.initcall4.init)
+         *(.initcall5.init)
+         *(.initcall6.init)
+         *(.initcall7.init)
+         __initcall_end = .;
+       }
+   __con_initcall_start = .;
+  .con_initcall.init : AT(ADDR(.con_initcall.init) - LOAD_OFFSET)
+       { *(.con_initcall.init) }
+  __con_initcall_end = .;
+  __security_initcall_start = .;
+  .security_initcall.init : AT(ADDR(.security_initcall.init) - LOAD_OFFSET)
+       { *(.security_initcall.init) }
+  __security_initcall_end = .;
+  . = ALIGN(PAGE_SIZE);
+  __init_end = .;
+
+  /* The initial task and kernel stack */
+  .data.init_task : AT(ADDR(.data.init_task) - LOAD_OFFSET)
+       { *(.data.init_task) }
+
+  .data.page_aligned : AT(ADDR(.data.page_aligned) - LOAD_OFFSET)
+        { *(__special_page_section)
+         __start_gate_section = .;
+         *(.data.gate)
+         __stop_gate_section = .;
+       }
+  . = ALIGN(PAGE_SIZE);                /* make sure the gate page doesn't 
expose kernel data */
+
+  .data.cacheline_aligned : AT(ADDR(.data.cacheline_aligned) - LOAD_OFFSET)
+        { *(.data.cacheline_aligned) }
+
+  /* Per-cpu data: */
+  percpu : { } :percpu
+  . = ALIGN(PERCPU_PAGE_SIZE);
+  __phys_per_cpu_start = .;
+  .data.percpu PERCPU_ADDR : AT(__phys_per_cpu_start - LOAD_OFFSET)
+       {
+               __per_cpu_start = .;
+               *(.data.percpu)
+               __per_cpu_end = .;
+       }
+  . = __phys_per_cpu_start + PERCPU_PAGE_SIZE; /* ensure percpu data fits into 
percpu page size */
+
+  data : { } :data
+  .data : AT(ADDR(.data) - LOAD_OFFSET)
+       { *(.data) *(.data1) *(.gnu.linkonce.d*) CONSTRUCTORS }
+
+  . = ALIGN(16);       /* gp must be 16-byte aligned for exc. table */
+  .got : AT(ADDR(.got) - LOAD_OFFSET)
+       { *(.got.plt) *(.got) }
+  __gp = ADDR(.got) + 0x200000;
+  /* We want the small data sections together, so single-instruction offsets
+     can access them all, and initialized data all before uninitialized, so
+     we can shorten the on-disk segment size.  */
+  .sdata : AT(ADDR(.sdata) - LOAD_OFFSET)
+       { *(.sdata) *(.sdata1) *(.srdata) }
+  _edata  =  .;
+  _bss = .;
+  .sbss : AT(ADDR(.sbss) - LOAD_OFFSET)
+       { *(.sbss) *(.scommon) }
+  .bss : AT(ADDR(.bss) - LOAD_OFFSET)
+       { *(.bss) *(COMMON) }
+
+  _end = .;
+
+  code : { } :code
+  /* Stabs debugging sections.  */
+  .stab 0 : { *(.stab) }
+  .stabstr 0 : { *(.stabstr) }
+  .stab.excl 0 : { *(.stab.excl) }
+  .stab.exclstr 0 : { *(.stab.exclstr) }
+  .stab.index 0 : { *(.stab.index) }
+  .stab.indexstr 0 : { *(.stab.indexstr) }
+  /* DWARF debug sections.
+     Symbols in the DWARF debugging sections are relative to the beginning
+     of the section so we begin them at 0.  */
+  /* DWARF 1 */
+  .debug          0 : { *(.debug) }
+  .line           0 : { *(.line) }
+  /* GNU DWARF 1 extensions */
+  .debug_srcinfo  0 : { *(.debug_srcinfo) }
+  .debug_sfnames  0 : { *(.debug_sfnames) }
+  /* DWARF 1.1 and DWARF 2 */
+  .debug_aranges  0 : { *(.debug_aranges) }
+  .debug_pubnames 0 : { *(.debug_pubnames) }
+  /* DWARF 2 */
+  .debug_info     0 : { *(.debug_info) }
+  .debug_abbrev   0 : { *(.debug_abbrev) }
+  .debug_line     0 : { *(.debug_line) }
+  .debug_frame    0 : { *(.debug_frame) }
+  .debug_str      0 : { *(.debug_str) }
+  .debug_loc      0 : { *(.debug_loc) }
+  .debug_macinfo  0 : { *(.debug_macinfo) }
+  /* SGI/MIPS DWARF 2 extensions */
+  .debug_weaknames 0 : { *(.debug_weaknames) }
+  .debug_funcnames 0 : { *(.debug_funcnames) }
+  .debug_typenames 0 : { *(.debug_typenames) }
+  .debug_varnames  0 : { *(.debug_varnames) }
+  /* These must appear regardless of  .  */
+  /* Discard them for now since Intel SoftSDV cannot handle them.
+  .comment 0 : { *(.comment) }
+  .note 0 : { *(.note) }
+  */
+  /DISCARD/ : { *(.comment) }
+  /DISCARD/ : { *(.note) }
+}
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/gcc_intrin.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/gcc_intrin.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,657 @@
+#ifndef _ASM_IA64_GCC_INTRIN_H
+#define _ASM_IA64_GCC_INTRIN_H
+/*
+ *
+ * Copyright (C) 2002,2003 Jun Nakajima <jun.nakajima@xxxxxxxxx>
+ * Copyright (C) 2002,2003 Suresh Siddha <suresh.b.siddha@xxxxxxxxx>
+ */
+
+#include <linux/compiler.h>
+
+/* define this macro to get some asm stmts included in 'c' files */
+#define ASM_SUPPORTED
+
+/* Optimization barrier */
+/* The "volatile" is due to gcc bugs */
+#define ia64_barrier() asm volatile ("":::"memory")
+
+#define ia64_stop()    asm volatile (";;"::)
+
+#define ia64_invala_gr(regnum) asm volatile ("invala.e r%0" :: "i"(regnum))
+
+#define ia64_invala_fr(regnum) asm volatile ("invala.e f%0" :: "i"(regnum))
+
+extern void ia64_bad_param_for_setreg (void);
+extern void ia64_bad_param_for_getreg (void);
+
+register unsigned long ia64_r13 asm ("r13") __attribute_used__;
+
+#define ia64_setreg(regnum, val)                                               
\
+({                                                                             
\
+       switch (regnum) {                                                       
\
+           case _IA64_REG_PSR_L:                                               
\
+                   asm volatile ("mov psr.l=%0" :: "r"(val) : "memory");       
\
+                   break;                                                      
\
+           case _IA64_REG_AR_KR0 ... _IA64_REG_AR_EC:                          
\
+                   asm volatile ("mov ar%0=%1" ::                              
\
+                                         "i" (regnum - _IA64_REG_AR_KR0),      
\
+                                         "r"(val): "memory");                  
\
+                   break;                                                      
\
+           case _IA64_REG_CR_DCR ... _IA64_REG_CR_LRR1:                        
\
+                   asm volatile ("mov cr%0=%1" ::                              
\
+                                         "i" (regnum - _IA64_REG_CR_DCR),      
\
+                                         "r"(val): "memory" );                 
\
+                   break;                                                      
\
+           case _IA64_REG_SP:                                                  
\
+                   asm volatile ("mov r12=%0" ::                               
\
+                                         "r"(val): "memory");                  
\
+                   break;                                                      
\
+           case _IA64_REG_GP:                                                  
\
+                   asm volatile ("mov gp=%0" :: "r"(val) : "memory");          
\
+               break;                                                          
\
+           default:                                                            
\
+                   ia64_bad_param_for_setreg();                                
\
+                   break;                                                      
\
+       }                                                                       
\
+})
+
+#define ia64_getreg(regnum)                                                    
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+                                                                               
\
+       switch (regnum) {                                                       
\
+       case _IA64_REG_GP:                                                      
\
+               asm volatile ("mov %0=gp" : "=r"(ia64_intri_res));              
\
+               break;                                                          
\
+       case _IA64_REG_IP:                                                      
\
+               asm volatile ("mov %0=ip" : "=r"(ia64_intri_res));              
\
+               break;                                                          
\
+       case _IA64_REG_PSR:                                                     
\
+               asm volatile ("mov %0=psr" : "=r"(ia64_intri_res));             
\
+               break;                                                          
\
+       case _IA64_REG_TP:      /* for current() */                             
\
+               ia64_intri_res = ia64_r13;                                      
\
+               break;                                                          
\
+       case _IA64_REG_AR_KR0 ... _IA64_REG_AR_EC:                              
\
+               asm volatile ("mov %0=ar%1" : "=r" (ia64_intri_res)             
\
+                                     : "i"(regnum - _IA64_REG_AR_KR0));        
\
+               break;                                                          
\
+       case _IA64_REG_CR_DCR ... _IA64_REG_CR_LRR1:                            
\
+               asm volatile ("mov %0=cr%1" : "=r" (ia64_intri_res)             
\
+                                     : "i" (regnum - _IA64_REG_CR_DCR));       
\
+               break;                                                          
\
+       case _IA64_REG_SP:                                                      
\
+               asm volatile ("mov %0=sp" : "=r" (ia64_intri_res));             
\
+               break;                                                          
\
+       default:                                                                
\
+               ia64_bad_param_for_getreg();                                    
\
+               break;                                                          
\
+       }                                                                       
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_hint_pause 0
+
+#define ia64_hint(mode)                                                \
+({                                                             \
+       switch (mode) {                                         \
+       case ia64_hint_pause:                                   \
+               asm volatile ("hint @pause" ::: "memory");      \
+               break;                                          \
+       }                                                       \
+})
+
+
+/* Integer values for mux1 instruction */
+#define ia64_mux1_brcst 0
+#define ia64_mux1_mix   8
+#define ia64_mux1_shuf  9
+#define ia64_mux1_alt  10
+#define ia64_mux1_rev  11
+
+#define ia64_mux1(x, mode)                                                     
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+                                                                               
\
+       switch (mode) {                                                         
\
+       case ia64_mux1_brcst:                                                   
\
+               asm ("mux1 %0=%1,@brcst" : "=r" (ia64_intri_res) : "r" (x));    
\
+               break;                                                          
\
+       case ia64_mux1_mix:                                                     
\
+               asm ("mux1 %0=%1,@mix" : "=r" (ia64_intri_res) : "r" (x));      
\
+               break;                                                          
\
+       case ia64_mux1_shuf:                                                    
\
+               asm ("mux1 %0=%1,@shuf" : "=r" (ia64_intri_res) : "r" (x));     
\
+               break;                                                          
\
+       case ia64_mux1_alt:                                                     
\
+               asm ("mux1 %0=%1,@alt" : "=r" (ia64_intri_res) : "r" (x));      
\
+               break;                                                          
\
+       case ia64_mux1_rev:                                                     
\
+               asm ("mux1 %0=%1,@rev" : "=r" (ia64_intri_res) : "r" (x));      
\
+               break;                                                          
\
+       }                                                                       
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_popcnt(x)                                         \
+({                                                             \
+       __u64 ia64_intri_res;                                   \
+       asm ("popcnt %0=%1" : "=r" (ia64_intri_res) : "r" (x)); \
+                                                               \
+       ia64_intri_res;                                         \
+})
+
+#define ia64_getf_exp(x)                                       \
+({                                                             \
+       long ia64_intri_res;                                    \
+                                                               \
+       asm ("getf.exp %0=%1" : "=r"(ia64_intri_res) : "f"(x)); \
+                                                               \
+       ia64_intri_res;                                         \
+})
+
+#define ia64_shrp(a, b, count)                                                 
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm ("shrp %0=%1,%2,%3" : "=r"(ia64_intri_res) : "r"(a), "r"(b), 
"i"(count));   \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_ldfs(regnum, x)                                   \
+({                                                             \
+       register double __f__ asm ("f"#regnum);                 \
+       asm volatile ("ldfs %0=[%1]" :"=f"(__f__): "r"(x));     \
+})
+
+#define ia64_ldfd(regnum, x)                                   \
+({                                                             \
+       register double __f__ asm ("f"#regnum);                 \
+       asm volatile ("ldfd %0=[%1]" :"=f"(__f__): "r"(x));     \
+})
+
+#define ia64_ldfe(regnum, x)                                   \
+({                                                             \
+       register double __f__ asm ("f"#regnum);                 \
+       asm volatile ("ldfe %0=[%1]" :"=f"(__f__): "r"(x));     \
+})
+
+#define ia64_ldf8(regnum, x)                                   \
+({                                                             \
+       register double __f__ asm ("f"#regnum);                 \
+       asm volatile ("ldf8 %0=[%1]" :"=f"(__f__): "r"(x));     \
+})
+
+#define ia64_ldf_fill(regnum, x)                               \
+({                                                             \
+       register double __f__ asm ("f"#regnum);                 \
+       asm volatile ("ldf.fill %0=[%1]" :"=f"(__f__): "r"(x)); \
+})
+
+#define ia64_stfs(x, regnum)                                           \
+({                                                                     \
+       register double __f__ asm ("f"#regnum);                         \
+       asm volatile ("stfs [%0]=%1" :: "r"(x), "f"(__f__) : "memory"); \
+})
+
+#define ia64_stfd(x, regnum)                                           \
+({                                                                     \
+       register double __f__ asm ("f"#regnum);                         \
+       asm volatile ("stfd [%0]=%1" :: "r"(x), "f"(__f__) : "memory"); \
+})
+
+#define ia64_stfe(x, regnum)                                           \
+({                                                                     \
+       register double __f__ asm ("f"#regnum);                         \
+       asm volatile ("stfe [%0]=%1" :: "r"(x), "f"(__f__) : "memory"); \
+})
+
+#define ia64_stf8(x, regnum)                                           \
+({                                                                     \
+       register double __f__ asm ("f"#regnum);                         \
+       asm volatile ("stf8 [%0]=%1" :: "r"(x), "f"(__f__) : "memory"); \
+})
+
+#define ia64_stf_spill(x, regnum)                                              
\
+({                                                                             
\
+       register double __f__ asm ("f"#regnum);                                 
\
+       asm volatile ("stf.spill [%0]=%1" :: "r"(x), "f"(__f__) : "memory");    
\
+})
+
+#define ia64_fetchadd4_acq(p, inc)                                             
\
+({                                                                             
\
+                                                                               
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("fetchadd4.acq %0=[%1],%2"                                
\
+                               : "=r"(ia64_intri_res) : "r"(p), "i" (inc)      
\
+                               : "memory");                                    
\
+                                                                               
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_fetchadd4_rel(p, inc)                                             
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("fetchadd4.rel %0=[%1],%2"                                
\
+                               : "=r"(ia64_intri_res) : "r"(p), "i" (inc)      
\
+                               : "memory");                                    
\
+                                                                               
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_fetchadd8_acq(p, inc)                                             
\
+({                                                                             
\
+                                                                               
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("fetchadd8.acq %0=[%1],%2"                                
\
+                               : "=r"(ia64_intri_res) : "r"(p), "i" (inc)      
\
+                               : "memory");                                    
\
+                                                                               
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_fetchadd8_rel(p, inc)                                             
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("fetchadd8.rel %0=[%1],%2"                                
\
+                               : "=r"(ia64_intri_res) : "r"(p), "i" (inc)      
\
+                               : "memory");                                    
\
+                                                                               
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_xchg1(ptr,x)                                                      
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("xchg1 %0=[%1],%2"                                        
\
+                     : "=r" (ia64_intri_res) : "r" (ptr), "r" (x) : "memory"); 
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_xchg2(ptr,x)                                              \
+({                                                                     \
+       __u64 ia64_intri_res;                                           \
+       asm volatile ("xchg2 %0=[%1],%2" : "=r" (ia64_intri_res)        \
+                     : "r" (ptr), "r" (x) : "memory");                 \
+       ia64_intri_res;                                                 \
+})
+
+#define ia64_xchg4(ptr,x)                                              \
+({                                                                     \
+       __u64 ia64_intri_res;                                           \
+       asm volatile ("xchg4 %0=[%1],%2" : "=r" (ia64_intri_res)        \
+                     : "r" (ptr), "r" (x) : "memory");                 \
+       ia64_intri_res;                                                 \
+})
+
+#define ia64_xchg8(ptr,x)                                              \
+({                                                                     \
+       __u64 ia64_intri_res;                                           \
+       asm volatile ("xchg8 %0=[%1],%2" : "=r" (ia64_intri_res)        \
+                     : "r" (ptr), "r" (x) : "memory");                 \
+       ia64_intri_res;                                                 \
+})
+
+#define ia64_cmpxchg1_acq(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg1.acq %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg1_rel(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg1.rel %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg2_acq(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg2.acq %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg2_rel(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+                                                                               
        \
+       asm volatile ("cmpxchg2.rel %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg4_acq(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg4.acq %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg4_rel(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg4.rel %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg8_acq(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+       asm volatile ("cmpxchg8.acq %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_cmpxchg8_rel(ptr, new, old)                                       
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov ar.ccv=%0;;" :: "rO"(old));                          
        \
+                                                                               
        \
+       asm volatile ("cmpxchg8.rel %0=[%1],%2,ar.ccv":                         
        \
+                             "=r"(ia64_intri_res) : "r"(ptr), "r"(new) : 
"memory");    \
+       ia64_intri_res;                                                         
        \
+})
+
+#define ia64_mf()      asm volatile ("mf" ::: "memory")
+#define ia64_mfa()     asm volatile ("mf.a" ::: "memory")
+
+#ifdef CONFIG_VTI
+/*
+ * Flushrs instruction stream.
+ */
+#define ia64_flushrs() asm volatile ("flushrs;;":::"memory")
+
+#define ia64_loadrs() asm volatile ("loadrs;;":::"memory")
+
+#define ia64_get_rsc()                          \
+({                                  \
+    unsigned long val;                     \
+    asm volatile ("mov %0=ar.rsc;;" : "=r"(val) :: "memory");  \
+    val;                               \
+})
+
+#define ia64_set_rsc(val)                       \
+    asm volatile ("mov ar.rsc=%0;;" :: "r"(val) : "memory")
+
+#define ia64_get_bspstore()     \
+({                                  \
+    unsigned long val;                     \
+    asm volatile ("mov %0=ar.bspstore;;" : "=r"(val) :: "memory");  \
+    val;                               \
+})
+
+#define ia64_set_bspstore(val)                       \
+    asm volatile ("mov ar.bspstore=%0;;" :: "r"(val) : "memory")
+
+#define ia64_get_rnat()     \
+({                                  \
+    unsigned long val;                     \
+    asm volatile ("mov %0=ar.rnat;" : "=r"(val) :: "memory");  \
+    val;                               \
+})
+
+#define ia64_set_rnat(val)                       \
+    asm volatile ("mov ar.rnat=%0;;" :: "r"(val) : "memory")
+
+#define ia64_ttag(addr)                                                        
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("ttag %0=%1" : "=r"(ia64_intri_res) : "r" (addr));        
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_get_dcr()                          \
+({                                      \
+    __u64 result;                               \
+    asm volatile ("mov %0=cr.dcr" : "=r"(result) : );           \
+    result;                                 \
+})
+
+#define ia64_set_dcr(val)                           \
+({                                      \
+    asm volatile ("mov cr.dcr=%0" :: "r"(val) );            \
+})
+
+#endif // CONFIG_VTI
+
+
+#define ia64_invala() asm volatile ("invala" ::: "memory")
+
+#define ia64_thash(addr)                                                       
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("thash %0=%1" : "=r"(ia64_intri_res) : "r" (addr));       
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_srlz_i()  asm volatile (";; srlz.i ;;" ::: "memory")
+#define ia64_srlz_d()  asm volatile (";; srlz.d" ::: "memory");
+
+#ifdef HAVE_SERIALIZE_DIRECTIVE
+# define ia64_dv_serialize_data()              asm volatile 
(".serialize.data");
+# define ia64_dv_serialize_instruction()       asm volatile 
(".serialize.instruction");
+#else
+# define ia64_dv_serialize_data()
+# define ia64_dv_serialize_instruction()
+#endif
+
+#define ia64_nop(x)    asm volatile ("nop %0"::"i"(x));
+
+#define ia64_itci(addr)        asm volatile ("itc.i %0;;" :: "r"(addr) : 
"memory")
+
+#define ia64_itcd(addr)        asm volatile ("itc.d %0;;" :: "r"(addr) : 
"memory")
+
+
+#define ia64_itri(trnum, addr) asm volatile ("itr.i itr[%0]=%1"                
                \
+                                            :: "r"(trnum), "r"(addr) : 
"memory")
+
+#define ia64_itrd(trnum, addr) asm volatile ("itr.d dtr[%0]=%1"                
                \
+                                            :: "r"(trnum), "r"(addr) : 
"memory")
+
+#define ia64_tpa(addr)                                                         
\
+({                                                                             
\
+       __u64 ia64_pa;                                                          
\
+       asm volatile ("tpa %0 = %1" : "=r"(ia64_pa) : "r"(addr) : "memory");    
\
+       ia64_pa;                                                                
\
+})
+
+#define __ia64_set_dbr(index, val)                                             
\
+       asm volatile ("mov dbr[%0]=%1" :: "r"(index), "r"(val) : "memory")
+
+#define ia64_set_ibr(index, val)                                               
\
+       asm volatile ("mov ibr[%0]=%1" :: "r"(index), "r"(val) : "memory")
+
+#define ia64_set_pkr(index, val)                                               
\
+       asm volatile ("mov pkr[%0]=%1" :: "r"(index), "r"(val) : "memory")
+
+#define ia64_set_pmc(index, val)                                               
\
+       asm volatile ("mov pmc[%0]=%1" :: "r"(index), "r"(val) : "memory")
+
+#define ia64_set_pmd(index, val)                                               
\
+       asm volatile ("mov pmd[%0]=%1" :: "r"(index), "r"(val) : "memory")
+
+#define ia64_set_rr(index, val)                                                
        \
+       asm volatile ("mov rr[%0]=%1" :: "r"(index), "r"(val) : "memory");
+
+#define ia64_get_cpuid(index)                                                  
        \
+({                                                                             
        \
+       __u64 ia64_intri_res;                                                   
        \
+       asm volatile ("mov %0=cpuid[%r1]" : "=r"(ia64_intri_res) : 
"rO"(index));        \
+       ia64_intri_res;                                                         
        \
+})
+
+#define __ia64_get_dbr(index)                                                  
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=dbr[%1]" : "=r"(ia64_intri_res) : "r"(index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_get_ibr(index)                                                    
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=ibr[%1]" : "=r"(ia64_intri_res) : "r"(index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_get_pkr(index)                                                    
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=pkr[%1]" : "=r"(ia64_intri_res) : "r"(index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_get_pmc(index)                                                    
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=pmc[%1]" : "=r"(ia64_intri_res) : "r"(index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+
+#define ia64_get_pmd(index)                                                    
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=pmd[%1]" : "=r"(ia64_intri_res) : "r"(index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_get_rr(index)                                                     
\
+({                                                                             
\
+       __u64 ia64_intri_res;                                                   
\
+       asm volatile ("mov %0=rr[%1]" : "=r"(ia64_intri_res) : "r" (index));    
\
+       ia64_intri_res;                                                         
\
+})
+
+#define ia64_fc(addr)  asm volatile ("fc %0" :: "r"(addr) : "memory")
+
+
+#define ia64_sync_i()  asm volatile (";; sync.i" ::: "memory")
+
+#define ia64_ssm(mask) asm volatile ("ssm %0":: "i"((mask)) : "memory")
+#define ia64_rsm(mask) asm volatile ("rsm %0":: "i"((mask)) : "memory")
+#define ia64_sum(mask) asm volatile ("sum %0":: "i"((mask)) : "memory")
+#define ia64_rum(mask) asm volatile ("rum %0":: "i"((mask)) : "memory")
+
+#define ia64_ptce(addr)        asm volatile ("ptc.e %0" :: "r"(addr))
+
+#define ia64_ptcga(addr, size)                                                 
\
+do {                                                                           
\
+       asm volatile ("ptc.ga %0,%1" :: "r"(addr), "r"(size) : "memory");       
\
+       ia64_dv_serialize_data();                                               
\
+} while (0)
+
+#define ia64_ptcl(addr, size)                                                  
\
+do {                                                                           
\
+       asm volatile ("ptc.l %0,%1" :: "r"(addr), "r"(size) : "memory");        
\
+       ia64_dv_serialize_data();                                               
\
+} while (0)
+
+#define ia64_ptri(addr, size)                                          \
+       asm volatile ("ptr.i %0,%1" :: "r"(addr), "r"(size) : "memory")
+
+#define ia64_ptrd(addr, size)                                          \
+       asm volatile ("ptr.d %0,%1" :: "r"(addr), "r"(size) : "memory")
+
+/* Values for lfhint in ia64_lfetch and ia64_lfetch_fault */
+
+#define ia64_lfhint_none   0
+#define ia64_lfhint_nt1    1
+#define ia64_lfhint_nt2    2
+#define ia64_lfhint_nta    3
+
+#define ia64_lfetch(lfhint, y)                                 \
+({                                                             \
+        switch (lfhint) {                                      \
+        case ia64_lfhint_none:                                 \
+                asm volatile ("lfetch [%0]" : : "r"(y));       \
+                break;                                         \
+        case ia64_lfhint_nt1:                                  \
+                asm volatile ("lfetch.nt1 [%0]" : : "r"(y));   \
+                break;                                         \
+        case ia64_lfhint_nt2:                                  \
+                asm volatile ("lfetch.nt2 [%0]" : : "r"(y));   \
+                break;                                         \
+        case ia64_lfhint_nta:                                  \
+                asm volatile ("lfetch.nta [%0]" : : "r"(y));   \
+                break;                                         \
+        }                                                      \
+})
+
+#define ia64_lfetch_excl(lfhint, y)                                    \
+({                                                                     \
+        switch (lfhint) {                                              \
+        case ia64_lfhint_none:                                         \
+                asm volatile ("lfetch.excl [%0]" :: "r"(y));           \
+                break;                                                 \
+        case ia64_lfhint_nt1:                                          \
+                asm volatile ("lfetch.excl.nt1 [%0]" :: "r"(y));       \
+                break;                                                 \
+        case ia64_lfhint_nt2:                                          \
+                asm volatile ("lfetch.excl.nt2 [%0]" :: "r"(y));       \
+                break;                                                 \
+        case ia64_lfhint_nta:                                          \
+                asm volatile ("lfetch.excl.nta [%0]" :: "r"(y));       \
+                break;                                                 \
+        }                                                              \
+})
+
+#define ia64_lfetch_fault(lfhint, y)                                   \
+({                                                                     \
+        switch (lfhint) {                                              \
+        case ia64_lfhint_none:                                         \
+                asm volatile ("lfetch.fault [%0]" : : "r"(y));         \
+                break;                                                 \
+        case ia64_lfhint_nt1:                                          \
+                asm volatile ("lfetch.fault.nt1 [%0]" : : "r"(y));     \
+                break;                                                 \
+        case ia64_lfhint_nt2:                                          \
+                asm volatile ("lfetch.fault.nt2 [%0]" : : "r"(y));     \
+                break;                                                 \
+        case ia64_lfhint_nta:                                          \
+                asm volatile ("lfetch.fault.nta [%0]" : : "r"(y));     \
+                break;                                                 \
+        }                                                              \
+})
+
+#define ia64_lfetch_fault_excl(lfhint, y)                              \
+({                                                                     \
+        switch (lfhint) {                                              \
+        case ia64_lfhint_none:                                         \
+                asm volatile ("lfetch.fault.excl [%0]" :: "r"(y));     \
+                break;                                                 \
+        case ia64_lfhint_nt1:                                          \
+                asm volatile ("lfetch.fault.excl.nt1 [%0]" :: "r"(y)); \
+                break;                                                 \
+        case ia64_lfhint_nt2:                                          \
+                asm volatile ("lfetch.fault.excl.nt2 [%0]" :: "r"(y)); \
+                break;                                                 \
+        case ia64_lfhint_nta:                                          \
+                asm volatile ("lfetch.fault.excl.nta [%0]" :: "r"(y)); \
+                break;                                                 \
+        }                                                              \
+})
+
+#define ia64_intrin_local_irq_restore(x)                       \
+do {                                                           \
+       asm volatile (";;   cmp.ne p6,p7=%0,r0;;"               \
+                     "(p6) ssm psr.i;"                         \
+                     "(p7) rsm psr.i;;"                        \
+                     "(p6) srlz.d"                             \
+                     :: "r"((x)) : "p6", "p7", "memory");      \
+} while (0)
+
+#endif /* _ASM_IA64_GCC_INTRIN_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/hpsim_ssc.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/hpsim_ssc.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,55 @@
+/*
+ * Platform dependent support for HP simulator.
+ *
+ * Copyright (C) 1998, 1999 Hewlett-Packard Co
+ * Copyright (C) 1998, 1999 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Vijay Chander <vijay@xxxxxxxxxxxx>
+ */
+#ifndef _IA64_PLATFORM_HPSIM_SSC_H
+#define _IA64_PLATFORM_HPSIM_SSC_H
+
+/* Simulator system calls: */
+
+#define SSC_CONSOLE_INIT               20
+#define SSC_GETCHAR                    21
+#define SSC_PUTCHAR                    31
+#define SSC_CONNECT_INTERRUPT          58
+#define SSC_GENERATE_INTERRUPT         59
+#define SSC_SET_PERIODIC_INTERRUPT     60
+#define SSC_GET_RTC                    65
+#define SSC_EXIT                       66
+#define SSC_LOAD_SYMBOLS               69
+#define SSC_GET_TOD                    74
+#define SSC_CTL_TRACE                  76
+
+#define SSC_NETDEV_PROBE               100
+#define SSC_NETDEV_SEND                        101
+#define SSC_NETDEV_RECV                        102
+#define SSC_NETDEV_ATTACH              103
+#define SSC_NETDEV_DETACH              104
+
+/*
+ * Simulator system call.
+ */
+extern long ia64_ssc (long arg0, long arg1, long arg2, long arg3, int nr);
+
+#ifdef XEN
+/* Note: These are declared in linux/arch/ia64/hp/sim/simscsi.c but belong
+ * in linux/include/asm-ia64/hpsim_ssc.h, hence their addition here */
+#define SSC_OPEN                       50
+#define SSC_CLOSE                      51
+#define SSC_READ                       52
+#define SSC_WRITE                      53
+#define SSC_GET_COMPLETION             54
+#define SSC_WAIT_COMPLETION            55
+
+#define SSC_WRITE_ACCESS               2
+#define SSC_READ_ACCESS                        1
+
+struct ssc_disk_req {
+       unsigned long addr;
+       unsigned long len;
+};
+#endif
+
+#endif /* _IA64_PLATFORM_HPSIM_SSC_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/ia64regs.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/ia64regs.h     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,129 @@
+/*
+ * Copyright (C) 2002,2003 Intel Corp.
+ *      Jun Nakajima <jun.nakajima@xxxxxxxxx>
+ *      Suresh Siddha <suresh.b.siddha@xxxxxxxxx>
+ */
+
+#ifndef _ASM_IA64_IA64REGS_H
+#define _ASM_IA64_IA64REGS_H
+
+/*
+ * Register Names for getreg() and setreg().
+ *
+ * The "magic" numbers happen to match the values used by the Intel compiler's
+ * getreg()/setreg() intrinsics.
+ */
+
+/* Special Registers */
+
+#define _IA64_REG_IP           1016    /* getreg only */
+#define _IA64_REG_PSR          1019
+#define _IA64_REG_PSR_L                1019
+
+/* General Integer Registers */
+
+#define _IA64_REG_GP           1025    /* R1 */
+#define _IA64_REG_R8           1032    /* R8 */
+#define _IA64_REG_R9           1033    /* R9 */
+#define _IA64_REG_SP           1036    /* R12 */
+#define _IA64_REG_TP           1037    /* R13 */
+
+/* Application Registers */
+
+#define _IA64_REG_AR_KR0       3072
+#define _IA64_REG_AR_KR1       3073
+#define _IA64_REG_AR_KR2       3074
+#define _IA64_REG_AR_KR3       3075
+#define _IA64_REG_AR_KR4       3076
+#define _IA64_REG_AR_KR5       3077
+#define _IA64_REG_AR_KR6       3078
+#define _IA64_REG_AR_KR7       3079
+#define _IA64_REG_AR_RSC       3088
+#define _IA64_REG_AR_BSP       3089
+#define _IA64_REG_AR_BSPSTORE  3090
+#define _IA64_REG_AR_RNAT      3091
+#define _IA64_REG_AR_FCR       3093
+#define _IA64_REG_AR_EFLAG     3096
+#define _IA64_REG_AR_CSD       3097
+#define _IA64_REG_AR_SSD       3098
+#define _IA64_REG_AR_CFLAG     3099
+#define _IA64_REG_AR_FSR       3100
+#define _IA64_REG_AR_FIR       3101
+#define _IA64_REG_AR_FDR       3102
+#define _IA64_REG_AR_CCV       3104
+#define _IA64_REG_AR_UNAT      3108
+#define _IA64_REG_AR_FPSR      3112
+#define _IA64_REG_AR_ITC       3116
+#define _IA64_REG_AR_PFS       3136
+#define _IA64_REG_AR_LC                3137
+#define _IA64_REG_AR_EC                3138
+
+/* Control Registers */
+
+#define _IA64_REG_CR_DCR       4096
+#define _IA64_REG_CR_ITM       4097
+#define _IA64_REG_CR_IVA       4098
+#define _IA64_REG_CR_PTA       4104
+#define _IA64_REG_CR_IPSR      4112
+#define _IA64_REG_CR_ISR       4113
+#define _IA64_REG_CR_IIP       4115
+#define _IA64_REG_CR_IFA       4116
+#define _IA64_REG_CR_ITIR      4117
+#define _IA64_REG_CR_IIPA      4118
+#define _IA64_REG_CR_IFS       4119
+#define _IA64_REG_CR_IIM       4120
+#define _IA64_REG_CR_IHA       4121
+#define _IA64_REG_CR_LID       4160
+#define _IA64_REG_CR_IVR       4161    /* getreg only */
+#define _IA64_REG_CR_TPR       4162
+#define _IA64_REG_CR_EOI       4163
+#define _IA64_REG_CR_IRR0      4164    /* getreg only */
+#define _IA64_REG_CR_IRR1      4165    /* getreg only */
+#define _IA64_REG_CR_IRR2      4166    /* getreg only */
+#define _IA64_REG_CR_IRR3      4167    /* getreg only */
+#define _IA64_REG_CR_ITV       4168
+#define _IA64_REG_CR_PMV       4169
+#define _IA64_REG_CR_CMCV      4170
+#define _IA64_REG_CR_LRR0      4176
+#define _IA64_REG_CR_LRR1      4177
+
+#ifdef  CONFIG_VTI
+#define IA64_REG_CR_DCR   0
+#define IA64_REG_CR_ITM   1
+#define IA64_REG_CR_IVA   2
+#define IA64_REG_CR_PTA   8
+#define IA64_REG_CR_IPSR  16
+#define IA64_REG_CR_ISR   17
+#define IA64_REG_CR_IIP   19
+#define IA64_REG_CR_IFA   20
+#define IA64_REG_CR_ITIR  21
+#define IA64_REG_CR_IIPA  22
+#define IA64_REG_CR_IFS   23
+#define IA64_REG_CR_IIM   24
+#define IA64_REG_CR_IHA   25
+#define IA64_REG_CR_LID   64
+#define IA64_REG_CR_IVR   65
+#define IA64_REG_CR_TPR   66
+#define IA64_REG_CR_EOI   67
+#define IA64_REG_CR_IRR0  68
+#define IA64_REG_CR_IRR1  69
+#define IA64_REG_CR_IRR2  70
+#define IA64_REG_CR_IRR3  71
+#define IA64_REG_CR_ITV   72
+#define IA64_REG_CR_PMV   73
+#define IA64_REG_CR_CMCV  74
+#define IA64_REG_CR_LRR0  80
+#define IA64_REG_CR_LRR1  81
+#endif  //  CONFIG_VTI
+
+/* Indirect Registers for getindreg() and setindreg() */
+
+#define _IA64_REG_INDR_CPUID   9000    /* getindreg only */
+#define _IA64_REG_INDR_DBR     9001
+#define _IA64_REG_INDR_IBR     9002
+#define _IA64_REG_INDR_PKR     9003
+#define _IA64_REG_INDR_PMC     9004
+#define _IA64_REG_INDR_PMD     9005
+#define _IA64_REG_INDR_RR      9006
+
+#endif /* _ASM_IA64_IA64REGS_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/io.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/io.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,488 @@
+#ifndef _ASM_IA64_IO_H
+#define _ASM_IA64_IO_H
+
+/*
+ * This file contains the definitions for the emulated IO instructions
+ * inb/inw/inl/outb/outw/outl and the "string versions" of the same
+ * (insb/insw/insl/outsb/outsw/outsl). You can also use "pausing"
+ * versions of the single-IO instructions (inb_p/inw_p/..).
+ *
+ * This file is not meant to be obfuscating: it's just complicated to
+ * (a) handle it all in a way that makes gcc able to optimize it as
+ * well as possible and (b) trying to avoid writing the same thing
+ * over and over again with slight variations and possibly making a
+ * mistake somewhere.
+ *
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Asit Mallick <asit.k.mallick@xxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ */
+
+/* We don't use IO slowdowns on the ia64, but.. */
+#define __SLOW_DOWN_IO do { } while (0)
+#define SLOW_DOWN_IO   do { } while (0)
+
+#ifdef XEN
+#define __IA64_UNCACHED_OFFSET 0xe800000000000000UL
+#else
+#define __IA64_UNCACHED_OFFSET 0xc000000000000000UL    /* region 6 */
+#endif
+
+/*
+ * The legacy I/O space defined by the ia64 architecture supports only 65536 
ports, but
+ * large machines may have multiple other I/O spaces so we can't place any a 
priori limit
+ * on IO_SPACE_LIMIT.  These additional spaces are described in ACPI.
+ */
+#define IO_SPACE_LIMIT         0xffffffffffffffffUL
+
+#define MAX_IO_SPACES_BITS             4
+#define MAX_IO_SPACES                  (1UL << MAX_IO_SPACES_BITS)
+#define IO_SPACE_BITS                  24
+#define IO_SPACE_SIZE                  (1UL << IO_SPACE_BITS)
+
+#define IO_SPACE_NR(port)              ((port) >> IO_SPACE_BITS)
+#define IO_SPACE_BASE(space)           ((space) << IO_SPACE_BITS)
+#define IO_SPACE_PORT(port)            ((port) & (IO_SPACE_SIZE - 1))
+
+#define IO_SPACE_SPARSE_ENCODING(p)    ((((p) >> 2) << 12) | (p & 0xfff))
+
+struct io_space {
+       unsigned long mmio_base;        /* base in MMIO space */
+       int sparse;
+};
+
+extern struct io_space io_space[];
+extern unsigned int num_io_spaces;
+
+# ifdef __KERNEL__
+
+/*
+ * All MMIO iomem cookies are in region 6; anything less is a PIO cookie:
+ *     0xCxxxxxxxxxxxxxxx      MMIO cookie (return from ioremap)
+ *     0x000000001SPPPPPP      PIO cookie (S=space number, P..P=port)
+ *
+ * ioread/writeX() uses the leading 1 in PIO cookies (PIO_OFFSET) to catch
+ * code that uses bare port numbers without the prerequisite pci_iomap().
+ */
+#define PIO_OFFSET             (1UL << (MAX_IO_SPACES_BITS + IO_SPACE_BITS))
+#define PIO_MASK               (PIO_OFFSET - 1)
+#define PIO_RESERVED           __IA64_UNCACHED_OFFSET
+#define HAVE_ARCH_PIO_SIZE
+
+#include <asm/intrinsics.h>
+#include <asm/machvec.h>
+#include <asm/page.h>
+#include <asm/system.h>
+#include <asm-generic/iomap.h>
+
+/*
+ * Change virtual addresses to physical addresses and vv.
+ */
+static inline unsigned long
+virt_to_phys (volatile void *address)
+{
+       return (unsigned long) address - PAGE_OFFSET;
+}
+
+static inline void*
+phys_to_virt (unsigned long address)
+{
+       return (void *) (address + PAGE_OFFSET);
+}
+
+#define ARCH_HAS_VALID_PHYS_ADDR_RANGE
+extern int valid_phys_addr_range (unsigned long addr, size_t *count); /* efi.c 
*/
+
+/*
+ * The following two macros are deprecated and scheduled for removal.
+ * Please use the PCI-DMA interface defined in <asm/pci.h> instead.
+ */
+#define bus_to_virt    phys_to_virt
+#define virt_to_bus    virt_to_phys
+#define page_to_bus    page_to_phys
+
+# endif /* KERNEL */
+
+/*
+ * Memory fence w/accept.  This should never be used in code that is
+ * not IA-64 specific.
+ */
+#define __ia64_mf_a()  ia64_mfa()
+
+/**
+ * ___ia64_mmiowb - I/O write barrier
+ *
+ * Ensure ordering of I/O space writes.  This will make sure that writes
+ * following the barrier will arrive after all previous writes.  For most
+ * ia64 platforms, this is a simple 'mf.a' instruction.
+ *
+ * See Documentation/DocBook/deviceiobook.tmpl for more information.
+ */
+static inline void ___ia64_mmiowb(void)
+{
+       ia64_mfa();
+}
+
+static inline const unsigned long
+__ia64_get_io_port_base (void)
+{
+       extern unsigned long ia64_iobase;
+
+       return ia64_iobase;
+}
+
+static inline void*
+__ia64_mk_io_addr (unsigned long port)
+{
+       struct io_space *space;
+       unsigned long offset;
+
+       space = &io_space[IO_SPACE_NR(port)];
+       port = IO_SPACE_PORT(port);
+       if (space->sparse)
+               offset = IO_SPACE_SPARSE_ENCODING(port);
+       else
+               offset = port;
+
+       return (void *) (space->mmio_base | offset);
+}
+
+#define __ia64_inb     ___ia64_inb
+#define __ia64_inw     ___ia64_inw
+#define __ia64_inl     ___ia64_inl
+#define __ia64_outb    ___ia64_outb
+#define __ia64_outw    ___ia64_outw
+#define __ia64_outl    ___ia64_outl
+#define __ia64_readb   ___ia64_readb
+#define __ia64_readw   ___ia64_readw
+#define __ia64_readl   ___ia64_readl
+#define __ia64_readq   ___ia64_readq
+#define __ia64_readb_relaxed   ___ia64_readb
+#define __ia64_readw_relaxed   ___ia64_readw
+#define __ia64_readl_relaxed   ___ia64_readl
+#define __ia64_readq_relaxed   ___ia64_readq
+#define __ia64_writeb  ___ia64_writeb
+#define __ia64_writew  ___ia64_writew
+#define __ia64_writel  ___ia64_writel
+#define __ia64_writeq  ___ia64_writeq
+#define __ia64_mmiowb  ___ia64_mmiowb
+
+/*
+ * For the in/out routines, we need to do "mf.a" _after_ doing the I/O access 
to ensure
+ * that the access has completed before executing other I/O accesses.  Since 
we're doing
+ * the accesses through an uncachable (UC) translation, the CPU will execute 
them in
+ * program order.  However, we still need to tell the compiler not to shuffle 
them around
+ * during optimization, which is why we use "volatile" pointers.
+ */
+
+static inline unsigned int
+___ia64_inb (unsigned long port)
+{
+       volatile unsigned char *addr = __ia64_mk_io_addr(port);
+       unsigned char ret;
+
+       ret = *addr;
+       __ia64_mf_a();
+       return ret;
+}
+
+static inline unsigned int
+___ia64_inw (unsigned long port)
+{
+       volatile unsigned short *addr = __ia64_mk_io_addr(port);
+       unsigned short ret;
+
+       ret = *addr;
+       __ia64_mf_a();
+       return ret;
+}
+
+static inline unsigned int
+___ia64_inl (unsigned long port)
+{
+       volatile unsigned int *addr = __ia64_mk_io_addr(port);
+       unsigned int ret;
+
+       ret = *addr;
+       __ia64_mf_a();
+       return ret;
+}
+
+static inline void
+___ia64_outb (unsigned char val, unsigned long port)
+{
+       volatile unsigned char *addr = __ia64_mk_io_addr(port);
+
+       *addr = val;
+       __ia64_mf_a();
+}
+
+static inline void
+___ia64_outw (unsigned short val, unsigned long port)
+{
+       volatile unsigned short *addr = __ia64_mk_io_addr(port);
+
+       *addr = val;
+       __ia64_mf_a();
+}
+
+static inline void
+___ia64_outl (unsigned int val, unsigned long port)
+{
+       volatile unsigned int *addr = __ia64_mk_io_addr(port);
+
+       *addr = val;
+       __ia64_mf_a();
+}
+
+static inline void
+__insb (unsigned long port, void *dst, unsigned long count)
+{
+       unsigned char *dp = dst;
+
+       while (count--)
+               *dp++ = platform_inb(port);
+}
+
+static inline void
+__insw (unsigned long port, void *dst, unsigned long count)
+{
+       unsigned short *dp = dst;
+
+       while (count--)
+               *dp++ = platform_inw(port);
+}
+
+static inline void
+__insl (unsigned long port, void *dst, unsigned long count)
+{
+       unsigned int *dp = dst;
+
+       while (count--)
+               *dp++ = platform_inl(port);
+}
+
+static inline void
+__outsb (unsigned long port, const void *src, unsigned long count)
+{
+       const unsigned char *sp = src;
+
+       while (count--)
+               platform_outb(*sp++, port);
+}
+
+static inline void
+__outsw (unsigned long port, const void *src, unsigned long count)
+{
+       const unsigned short *sp = src;
+
+       while (count--)
+               platform_outw(*sp++, port);
+}
+
+static inline void
+__outsl (unsigned long port, const void *src, unsigned long count)
+{
+       const unsigned int *sp = src;
+
+       while (count--)
+               platform_outl(*sp++, port);
+}
+
+/*
+ * Unfortunately, some platforms are broken and do not follow the IA-64 
architecture
+ * specification regarding legacy I/O support.  Thus, we have to make these 
operations
+ * platform dependent...
+ */
+#define __inb          platform_inb
+#define __inw          platform_inw
+#define __inl          platform_inl
+#define __outb         platform_outb
+#define __outw         platform_outw
+#define __outl         platform_outl
+#define __mmiowb       platform_mmiowb
+
+#define inb(p)         __inb(p)
+#define inw(p)         __inw(p)
+#define inl(p)         __inl(p)
+#define insb(p,d,c)    __insb(p,d,c)
+#define insw(p,d,c)    __insw(p,d,c)
+#define insl(p,d,c)    __insl(p,d,c)
+#define outb(v,p)      __outb(v,p)
+#define outw(v,p)      __outw(v,p)
+#define outl(v,p)      __outl(v,p)
+#define outsb(p,s,c)   __outsb(p,s,c)
+#define outsw(p,s,c)   __outsw(p,s,c)
+#define outsl(p,s,c)   __outsl(p,s,c)
+#define mmiowb()       __mmiowb()
+
+/*
+ * The address passed to these functions are ioremap()ped already.
+ *
+ * We need these to be machine vectors since some platforms don't provide
+ * DMA coherence via PIO reads (PCI drivers and the spec imply that this is
+ * a good idea).  Writes are ok though for all existing ia64 platforms (and
+ * hopefully it'll stay that way).
+ */
+static inline unsigned char
+___ia64_readb (const volatile void __iomem *addr)
+{
+       return *(volatile unsigned char __force *)addr;
+}
+
+static inline unsigned short
+___ia64_readw (const volatile void __iomem *addr)
+{
+       return *(volatile unsigned short __force *)addr;
+}
+
+static inline unsigned int
+___ia64_readl (const volatile void __iomem *addr)
+{
+       return *(volatile unsigned int __force *) addr;
+}
+
+static inline unsigned long
+___ia64_readq (const volatile void __iomem *addr)
+{
+       return *(volatile unsigned long __force *) addr;
+}
+
+static inline void
+__writeb (unsigned char val, volatile void __iomem *addr)
+{
+       *(volatile unsigned char __force *) addr = val;
+}
+
+static inline void
+__writew (unsigned short val, volatile void __iomem *addr)
+{
+       *(volatile unsigned short __force *) addr = val;
+}
+
+static inline void
+__writel (unsigned int val, volatile void __iomem *addr)
+{
+       *(volatile unsigned int __force *) addr = val;
+}
+
+static inline void
+__writeq (unsigned long val, volatile void __iomem *addr)
+{
+       *(volatile unsigned long __force *) addr = val;
+}
+
+#define __readb                platform_readb
+#define __readw                platform_readw
+#define __readl                platform_readl
+#define __readq                platform_readq
+#define __readb_relaxed        platform_readb_relaxed
+#define __readw_relaxed        platform_readw_relaxed
+#define __readl_relaxed        platform_readl_relaxed
+#define __readq_relaxed        platform_readq_relaxed
+
+#define readb(a)       __readb((a))
+#define readw(a)       __readw((a))
+#define readl(a)       __readl((a))
+#define readq(a)       __readq((a))
+#define readb_relaxed(a)       __readb_relaxed((a))
+#define readw_relaxed(a)       __readw_relaxed((a))
+#define readl_relaxed(a)       __readl_relaxed((a))
+#define readq_relaxed(a)       __readq_relaxed((a))
+#define __raw_readb    readb
+#define __raw_readw    readw
+#define __raw_readl    readl
+#define __raw_readq    readq
+#define __raw_readb_relaxed    readb_relaxed
+#define __raw_readw_relaxed    readw_relaxed
+#define __raw_readl_relaxed    readl_relaxed
+#define __raw_readq_relaxed    readq_relaxed
+#define writeb(v,a)    __writeb((v), (a))
+#define writew(v,a)    __writew((v), (a))
+#define writel(v,a)    __writel((v), (a))
+#define writeq(v,a)    __writeq((v), (a))
+#define __raw_writeb   writeb
+#define __raw_writew   writew
+#define __raw_writel   writel
+#define __raw_writeq   writeq
+
+#ifndef inb_p
+# define inb_p         inb
+#endif
+#ifndef inw_p
+# define inw_p         inw
+#endif
+#ifndef inl_p
+# define inl_p         inl
+#endif
+
+#ifndef outb_p
+# define outb_p                outb
+#endif
+#ifndef outw_p
+# define outw_p                outw
+#endif
+#ifndef outl_p
+# define outl_p                outl
+#endif
+
+/*
+ * An "address" in IO memory space is not clearly either an integer or a 
pointer. We will
+ * accept both, thus the casts.
+ *
+ * On ia-64, we access the physical I/O memory space through the uncached 
kernel region.
+ */
+static inline void __iomem *
+ioremap (unsigned long offset, unsigned long size)
+{
+       return (void __iomem *) (__IA64_UNCACHED_OFFSET | (offset));
+}
+
+static inline void
+iounmap (volatile void __iomem *addr)
+{
+}
+
+#define ioremap_nocache(o,s)   ioremap(o,s)
+
+# ifdef __KERNEL__
+
+/*
+ * String version of IO memory access ops:
+ */
+extern void memcpy_fromio(void *dst, const volatile void __iomem *src, long n);
+extern void memcpy_toio(volatile void __iomem *dst, const void *src, long n);
+extern void memset_io(volatile void __iomem *s, int c, long n);
+
+#define dma_cache_inv(_start,_size)             do { } while (0)
+#define dma_cache_wback(_start,_size)           do { } while (0)
+#define dma_cache_wback_inv(_start,_size)       do { } while (0)
+
+# endif /* __KERNEL__ */
+
+/*
+ * Enabling BIO_VMERGE_BOUNDARY forces us to turn off I/O MMU bypassing.  It 
is said that
+ * BIO-level virtual merging can give up to 4% performance boost (not verified 
for ia64).
+ * On the other hand, we know that I/O MMU bypassing gives ~8% performance 
improvement on
+ * SPECweb-like workloads on zx1-based machines.  Thus, for now we favor I/O 
MMU bypassing
+ * over BIO-level virtual merging.
+ */
+extern unsigned long ia64_max_iommu_merge_mask;
+#if 1
+#define BIO_VMERGE_BOUNDARY    0
+#else
+/*
+ * It makes no sense at all to have this BIO_VMERGE_BOUNDARY macro here.  
Should be
+ * replaced by dma_merge_mask() or something of that sort.  Note: the only way
+ * BIO_VMERGE_BOUNDARY is used is to mask off bits.  Effectively, our 
definition gets
+ * expanded into:
+ *
+ *     addr & ((ia64_max_iommu_merge_mask + 1) - 1) == (addr & 
ia64_max_iommu_vmerge_mask)
+ *
+ * which is precisely what we want.
+ */
+#define BIO_VMERGE_BOUNDARY    (ia64_max_iommu_merge_mask + 1)
+#endif
+
+#endif /* _ASM_IA64_IO_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/kregs.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/kregs.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,199 @@
+#ifndef _ASM_IA64_KREGS_H
+#define _ASM_IA64_KREGS_H
+
+/*
+ * Copyright (C) 2001-2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+/*
+ * This file defines the kernel register usage convention used by Linux/ia64.
+ */
+
+/*
+ * Kernel registers:
+ */
+#define IA64_KR_IO_BASE                0       /* ar.k0: legacy I/O base 
address */
+#define IA64_KR_TSSD           1       /* ar.k1: IVE uses this as the TSSD */
+#define IA64_KR_PER_CPU_DATA   3       /* ar.k3: physical per-CPU base */
+#define IA64_KR_CURRENT_STACK  4       /* ar.k4: what's mapped in 
IA64_TR_CURRENT_STACK */
+#define IA64_KR_FPU_OWNER      5       /* ar.k5: fpu-owner (UP only, at the 
moment) */
+#define IA64_KR_CURRENT                6       /* ar.k6: "current" task 
pointer */
+#define IA64_KR_PT_BASE                7       /* ar.k7: page table base 
address (physical) */
+
+#define _IA64_KR_PASTE(x,y)    x##y
+#define _IA64_KR_PREFIX(n)     _IA64_KR_PASTE(ar.k, n)
+#define IA64_KR(n)             _IA64_KR_PREFIX(IA64_KR_##n)
+
+/*
+ * Translation registers:
+ */
+#define IA64_TR_KERNEL         0       /* itr0, dtr0: maps kernel image (code 
& data) */
+#define IA64_TR_PALCODE                1       /* itr1: maps PALcode as 
required by EFI */
+#ifdef CONFIG_VTI
+#define IA64_TR_XEN_IN_DOM     6       /* itr6, dtr6: Double mapping for xen 
image in domain space */
+#endif // CONFIG_VTI
+#define IA64_TR_PERCPU_DATA    1       /* dtr1: percpu data */
+#define IA64_TR_CURRENT_STACK  2       /* dtr2: maps kernel's memory- & 
register-stacks */
+#ifdef XEN
+#define IA64_TR_SHARED_INFO    3       /* dtr3: page shared with domain */
+#define        IA64_TR_VHPT            4       /* dtr4: vhpt */
+#define IA64_TR_ARCH_INFO      5
+#ifdef CONFIG_VTI
+#define IA64_TR_VHPT_IN_DOM    5       /* dtr5: Double mapping for vhpt table 
in domain space */
+#define IA64_TR_RR7_SWITCH_STUB        7       /* dtr7: mapping for rr7 switch 
stub */
+#define IA64_TEMP_PHYSICAL     8       /* itr8, dtr8: temp mapping for guest 
physical memory 256M */
+#endif // CONFIG_VTI
+#endif
+
+/* Processor status register bits: */
+#define IA64_PSR_BE_BIT                1
+#define IA64_PSR_UP_BIT                2
+#define IA64_PSR_AC_BIT                3
+#define IA64_PSR_MFL_BIT       4
+#define IA64_PSR_MFH_BIT       5
+#define IA64_PSR_IC_BIT                13
+#define IA64_PSR_I_BIT         14
+#define IA64_PSR_PK_BIT                15
+#define IA64_PSR_DT_BIT                17
+#define IA64_PSR_DFL_BIT       18
+#define IA64_PSR_DFH_BIT       19
+#define IA64_PSR_SP_BIT                20
+#define IA64_PSR_PP_BIT                21
+#define IA64_PSR_DI_BIT                22
+#define IA64_PSR_SI_BIT                23
+#define IA64_PSR_DB_BIT                24
+#define IA64_PSR_LP_BIT                25
+#define IA64_PSR_TB_BIT                26
+#define IA64_PSR_RT_BIT                27
+/* The following are not affected by save_flags()/restore_flags(): */
+#define IA64_PSR_CPL0_BIT      32
+#define IA64_PSR_CPL1_BIT      33
+#define IA64_PSR_IS_BIT                34
+#define IA64_PSR_MC_BIT                35
+#define IA64_PSR_IT_BIT                36
+#define IA64_PSR_ID_BIT                37
+#define IA64_PSR_DA_BIT                38
+#define IA64_PSR_DD_BIT                39
+#define IA64_PSR_SS_BIT                40
+#define IA64_PSR_RI_BIT                41
+#define IA64_PSR_ED_BIT                43
+#define IA64_PSR_BN_BIT                44
+#define IA64_PSR_IA_BIT                45
+#ifdef CONFIG_VTI
+#define IA64_PSR_VM_BIT                46
+#endif // CONFIG_VTI
+
+/* A mask of PSR bits that we generally don't want to inherit across a 
clone2() or an
+   execve().  Only list flags here that need to be cleared/set for BOTH 
clone2() and
+   execve().  */
+#define IA64_PSR_BITS_TO_CLEAR (IA64_PSR_MFL | IA64_PSR_MFH | IA64_PSR_DB | 
IA64_PSR_LP | \
+                                IA64_PSR_TB  | IA64_PSR_ID  | IA64_PSR_DA | 
IA64_PSR_DD | \
+                                IA64_PSR_SS  | IA64_PSR_ED  | IA64_PSR_IA)
+#define IA64_PSR_BITS_TO_SET   (IA64_PSR_DFH | IA64_PSR_SP)
+
+#define IA64_PSR_BE    (__IA64_UL(1) << IA64_PSR_BE_BIT)
+#define IA64_PSR_UP    (__IA64_UL(1) << IA64_PSR_UP_BIT)
+#define IA64_PSR_AC    (__IA64_UL(1) << IA64_PSR_AC_BIT)
+#define IA64_PSR_MFL   (__IA64_UL(1) << IA64_PSR_MFL_BIT)
+#define IA64_PSR_MFH   (__IA64_UL(1) << IA64_PSR_MFH_BIT)
+#define IA64_PSR_IC    (__IA64_UL(1) << IA64_PSR_IC_BIT)
+#define IA64_PSR_I     (__IA64_UL(1) << IA64_PSR_I_BIT)
+#define IA64_PSR_PK    (__IA64_UL(1) << IA64_PSR_PK_BIT)
+#define IA64_PSR_DT    (__IA64_UL(1) << IA64_PSR_DT_BIT)
+#define IA64_PSR_DFL   (__IA64_UL(1) << IA64_PSR_DFL_BIT)
+#define IA64_PSR_DFH   (__IA64_UL(1) << IA64_PSR_DFH_BIT)
+#define IA64_PSR_SP    (__IA64_UL(1) << IA64_PSR_SP_BIT)
+#define IA64_PSR_PP    (__IA64_UL(1) << IA64_PSR_PP_BIT)
+#define IA64_PSR_DI    (__IA64_UL(1) << IA64_PSR_DI_BIT)
+#define IA64_PSR_SI    (__IA64_UL(1) << IA64_PSR_SI_BIT)
+#define IA64_PSR_DB    (__IA64_UL(1) << IA64_PSR_DB_BIT)
+#define IA64_PSR_LP    (__IA64_UL(1) << IA64_PSR_LP_BIT)
+#define IA64_PSR_TB    (__IA64_UL(1) << IA64_PSR_TB_BIT)
+#define IA64_PSR_RT    (__IA64_UL(1) << IA64_PSR_RT_BIT)
+/* The following are not affected by save_flags()/restore_flags(): */
+#define IA64_PSR_CPL   (__IA64_UL(3) << IA64_PSR_CPL0_BIT)
+#define IA64_PSR_IS    (__IA64_UL(1) << IA64_PSR_IS_BIT)
+#define IA64_PSR_MC    (__IA64_UL(1) << IA64_PSR_MC_BIT)
+#define IA64_PSR_IT    (__IA64_UL(1) << IA64_PSR_IT_BIT)
+#define IA64_PSR_ID    (__IA64_UL(1) << IA64_PSR_ID_BIT)
+#define IA64_PSR_DA    (__IA64_UL(1) << IA64_PSR_DA_BIT)
+#define IA64_PSR_DD    (__IA64_UL(1) << IA64_PSR_DD_BIT)
+#define IA64_PSR_SS    (__IA64_UL(1) << IA64_PSR_SS_BIT)
+#define IA64_PSR_RI    (__IA64_UL(3) << IA64_PSR_RI_BIT)
+#define IA64_PSR_ED    (__IA64_UL(1) << IA64_PSR_ED_BIT)
+#define IA64_PSR_BN    (__IA64_UL(1) << IA64_PSR_BN_BIT)
+#define IA64_PSR_IA    (__IA64_UL(1) << IA64_PSR_IA_BIT)
+#ifdef CONFIG_VTI
+#define IA64_PSR_VM    (__IA64_UL(1) << IA64_PSR_VM_BIT)
+#endif // CONFIG_VTI
+
+/* User mask bits: */
+#define IA64_PSR_UM    (IA64_PSR_BE | IA64_PSR_UP | IA64_PSR_AC | IA64_PSR_MFL 
| IA64_PSR_MFH)
+
+/* Default Control Register */
+#define IA64_DCR_PP_BIT                 0      /* privileged performance 
monitor default */
+#define IA64_DCR_BE_BIT                 1      /* big-endian default */
+#define IA64_DCR_LC_BIT                 2      /* ia32 lock-check enable */
+#define IA64_DCR_DM_BIT                 8      /* defer TLB miss faults */
+#define IA64_DCR_DP_BIT                 9      /* defer page-not-present 
faults */
+#define IA64_DCR_DK_BIT                10      /* defer key miss faults */
+#define IA64_DCR_DX_BIT                11      /* defer key permission faults 
*/
+#define IA64_DCR_DR_BIT                12      /* defer access right faults */
+#define IA64_DCR_DA_BIT                13      /* defer access bit faults */
+#define IA64_DCR_DD_BIT                14      /* defer debug faults */
+
+#define IA64_DCR_PP    (__IA64_UL(1) << IA64_DCR_PP_BIT)
+#define IA64_DCR_BE    (__IA64_UL(1) << IA64_DCR_BE_BIT)
+#define IA64_DCR_LC    (__IA64_UL(1) << IA64_DCR_LC_BIT)
+#define IA64_DCR_DM    (__IA64_UL(1) << IA64_DCR_DM_BIT)
+#define IA64_DCR_DP    (__IA64_UL(1) << IA64_DCR_DP_BIT)
+#define IA64_DCR_DK    (__IA64_UL(1) << IA64_DCR_DK_BIT)
+#define IA64_DCR_DX    (__IA64_UL(1) << IA64_DCR_DX_BIT)
+#define IA64_DCR_DR    (__IA64_UL(1) << IA64_DCR_DR_BIT)
+#define IA64_DCR_DA    (__IA64_UL(1) << IA64_DCR_DA_BIT)
+#define IA64_DCR_DD    (__IA64_UL(1) << IA64_DCR_DD_BIT)
+
+/* Interrupt Status Register */
+#define IA64_ISR_X_BIT         32      /* execute access */
+#define IA64_ISR_W_BIT         33      /* write access */
+#define IA64_ISR_R_BIT         34      /* read access */
+#define IA64_ISR_NA_BIT                35      /* non-access */
+#define IA64_ISR_SP_BIT                36      /* speculative load exception */
+#define IA64_ISR_RS_BIT                37      /* mandatory register-stack 
exception */
+#define IA64_ISR_IR_BIT                38      /* invalid register frame 
exception */
+#define IA64_ISR_CODE_MASK     0xf
+
+#define IA64_ISR_X     (__IA64_UL(1) << IA64_ISR_X_BIT)
+#define IA64_ISR_W     (__IA64_UL(1) << IA64_ISR_W_BIT)
+#define IA64_ISR_R     (__IA64_UL(1) << IA64_ISR_R_BIT)
+#define IA64_ISR_NA    (__IA64_UL(1) << IA64_ISR_NA_BIT)
+#define IA64_ISR_SP    (__IA64_UL(1) << IA64_ISR_SP_BIT)
+#define IA64_ISR_RS    (__IA64_UL(1) << IA64_ISR_RS_BIT)
+#define IA64_ISR_IR    (__IA64_UL(1) << IA64_ISR_IR_BIT)
+
+/* ISR code field for non-access instructions */
+#define IA64_ISR_CODE_TPA      0
+#define IA64_ISR_CODE_FC       1
+#define IA64_ISR_CODE_PROBE    2
+#define IA64_ISR_CODE_TAK      3
+#define IA64_ISR_CODE_LFETCH   4
+#define IA64_ISR_CODE_PROBEF   5
+
+#ifdef XEN
+/* Interruption Function State */
+#define IA64_IFS_V_BIT         63
+#define IA64_IFS_V     (__IA64_UL(1) << IA64_IFS_V_BIT)
+
+/* Page Table Address */
+#define IA64_PTA_VE_BIT 0
+#define IA64_PTA_SIZE_BIT 2
+#define IA64_PTA_VF_BIT 8
+#define IA64_PTA_BASE_BIT 15
+
+#define IA64_PTA_VE     (__IA64_UL(1) << IA64_PTA_VE_BIT)
+#define IA64_PTA_SIZE   (__IA64_UL(0x3f) << IA64_PTA_SIZE_BIT)
+#define IA64_PTA_VF     (__IA64_UL(1) << IA64_PTA_VF_BIT)
+#define IA64_PTA_BASE   (__IA64_UL(0) - ((__IA64_UL(1) << IA64_PTA_BASE_BIT)))
+#endif
+
+#endif /* _ASM_IA64_kREGS_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/mca_asm.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/mca_asm.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,323 @@
+/*
+ * File:       mca_asm.h
+ *
+ * Copyright (C) 1999 Silicon Graphics, Inc.
+ * Copyright (C) Vijay Chander (vijay@xxxxxxxxxxxx)
+ * Copyright (C) Srinivasa Thirumalachar <sprasad@xxxxxxxxxxxx>
+ * Copyright (C) 2000 Hewlett-Packard Co.
+ * Copyright (C) 2000 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 2002 Intel Corp.
+ * Copyright (C) 2002 Jenna Hall <jenna.s.hall@xxxxxxxxx>
+ */
+#ifndef _ASM_IA64_MCA_ASM_H
+#define _ASM_IA64_MCA_ASM_H
+
+#define PSR_IC         13
+#define PSR_I          14
+#define        PSR_DT          17
+#define PSR_RT         27
+#define PSR_MC         35
+#define PSR_IT         36
+#define PSR_BN         44
+
+/*
+ * This macro converts a instruction virtual address to a physical address
+ * Right now for simulation purposes the virtual addresses are
+ * direct mapped to physical addresses.
+ *     1. Lop off bits 61 thru 63 in the virtual address
+ */
+#ifdef XEN
+#define INST_VA_TO_PA(addr)                                                    
\
+       dep     addr    = 0, addr, 60, 4
+#else // XEN
+#define INST_VA_TO_PA(addr)                                                    
\
+       dep     addr    = 0, addr, 61, 3
+#endif // XEN
+/*
+ * This macro converts a data virtual address to a physical address
+ * Right now for simulation purposes the virtual addresses are
+ * direct mapped to physical addresses.
+ *     1. Lop off bits 61 thru 63 in the virtual address
+ */
+#define DATA_VA_TO_PA(addr)                                                    
\
+       tpa     addr    = addr
+/*
+ * This macro converts a data physical address to a virtual address
+ * Right now for simulation purposes the virtual addresses are
+ * direct mapped to physical addresses.
+ *     1. Put 0x7 in bits 61 thru 63.
+ */
+#ifdef XEN
+#define DATA_PA_TO_VA(addr,temp)                                               
        \
+       mov     temp    = 0xf   ;;                                              
        \
+       dep     addr    = temp, addr, 60, 4
+#else // XEN
+#define DATA_PA_TO_VA(addr,temp)                                               
        \
+       mov     temp    = 0x7   ;;                                              
        \
+       dep     addr    = temp, addr, 61, 3
+#endif // XEN
+
+#define GET_THIS_PADDR(reg, var)               \
+       mov     reg = IA64_KR(PER_CPU_DATA);;   \
+        addl   reg = THIS_CPU(var), reg
+
+/*
+ * This macro jumps to the instruction at the given virtual address
+ * and starts execution in physical mode with all the address
+ * translations turned off.
+ *     1.      Save the current psr
+ *     2.      Make sure that all the upper 32 bits are off
+ *
+ *     3.      Clear the interrupt enable and interrupt state collection bits
+ *             in the psr before updating the ipsr and iip.
+ *
+ *     4.      Turn off the instruction, data and rse translation bits of the 
psr
+ *             and store the new value into ipsr
+ *             Also make sure that the interrupts are disabled.
+ *             Ensure that we are in little endian mode.
+ *             [psr.{rt, it, dt, i, be} = 0]
+ *
+ *     5.      Get the physical address corresponding to the virtual address
+ *             of the next instruction bundle and put it in iip.
+ *             (Using magic numbers 24 and 40 in the deposint instruction since
+ *              the IA64_SDK code directly maps to lower 24bits as physical 
address
+ *              from a virtual address).
+ *
+ *     6.      Do an rfi to move the values from ipsr to psr and iip to ip.
+ */
+#define  PHYSICAL_MODE_ENTER(temp1, temp2, start_addr, old_psr)                
                \
+       mov     old_psr = psr;                                                  
        \
+       ;;                                                                      
        \
+       dep     old_psr = 0, old_psr, 32, 32;                                   
        \
+                                                                               
        \
+       mov     ar.rsc = 0 ;                                                    
        \
+       ;;                                                                      
        \
+       srlz.d;                                                                 
        \
+       mov     temp2 = ar.bspstore;                                            
        \
+       ;;                                                                      
        \
+       DATA_VA_TO_PA(temp2);                                                   
        \
+       ;;                                                                      
        \
+       mov     temp1 = ar.rnat;                                                
        \
+       ;;                                                                      
        \
+       mov     ar.bspstore = temp2;                                            
        \
+       ;;                                                                      
        \
+       mov     ar.rnat = temp1;                                                
        \
+       mov     temp1 = psr;                                                    
        \
+       mov     temp2 = psr;                                                    
        \
+       ;;                                                                      
        \
+                                                                               
        \
+       dep     temp2 = 0, temp2, PSR_IC, 2;                                    
        \
+       ;;                                                                      
        \
+       mov     psr.l = temp2;                                                  
        \
+       ;;                                                                      
        \
+       srlz.d;                                                                 
        \
+       dep     temp1 = 0, temp1, 32, 32;                                       
        \
+       ;;                                                                      
        \
+       dep     temp1 = 0, temp1, PSR_IT, 1;                                    
        \
+       ;;                                                                      
        \
+       dep     temp1 = 0, temp1, PSR_DT, 1;                                    
        \
+       ;;                                                                      
        \
+       dep     temp1 = 0, temp1, PSR_RT, 1;                                    
        \
+       ;;                                                                      
        \
+       dep     temp1 = 0, temp1, PSR_I, 1;                                     
        \
+       ;;                                                                      
        \
+       dep     temp1 = 0, temp1, PSR_IC, 1;                                    
        \
+       ;;                                                                      
        \
+       dep     temp1 = -1, temp1, PSR_MC, 1;                                   
        \
+       ;;                                                                      
        \
+       mov     cr.ipsr = temp1;                                                
        \
+       ;;                                                                      
        \
+       LOAD_PHYSICAL(p0, temp2, start_addr);                                   
        \
+       ;;                                                                      
        \
+       mov     cr.iip = temp2;                                                 
        \
+       mov     cr.ifs = r0;                                                    
        \
+       DATA_VA_TO_PA(sp);                                                      
        \
+       DATA_VA_TO_PA(gp);                                                      
        \
+       ;;                                                                      
        \
+       srlz.i;                                                                 
        \
+       ;;                                                                      
        \
+       nop     1;                                                              
        \
+       nop     2;                                                              
        \
+       nop     1;                                                              
        \
+       nop     2;                                                              
        \
+       rfi;                                                                    
        \
+       ;;
+
+/*
+ * This macro jumps to the instruction at the given virtual address
+ * and starts execution in virtual mode with all the address
+ * translations turned on.
+ *     1.      Get the old saved psr
+ *
+ *     2.      Clear the interrupt state collection bit in the current psr.
+ *
+ *     3.      Set the instruction translation bit back in the old psr
+ *             Note we have to do this since we are right now saving only the
+ *             lower 32-bits of old psr.(Also the old psr has the data and
+ *             rse translation bits on)
+ *
+ *     4.      Set ipsr to this old_psr with "it" bit set and "bn" = 1.
+ *
+ *     5.      Reset the current thread pointer (r13).
+ *
+ *     6.      Set iip to the virtual address of the next instruction bundle.
+ *
+ *     7.      Do an rfi to move ipsr to psr and iip to ip.
+ */
+
+#define VIRTUAL_MODE_ENTER(temp1, temp2, start_addr, old_psr)  \
+       mov     temp2 = psr;                                    \
+       ;;                                                      \
+       mov     old_psr = temp2;                                \
+       ;;                                                      \
+       dep     temp2 = 0, temp2, PSR_IC, 2;                    \
+       ;;                                                      \
+       mov     psr.l = temp2;                                  \
+       mov     ar.rsc = 0;                                     \
+       ;;                                                      \
+       srlz.d;                                                 \
+       mov     r13 = ar.k6;                                    \
+       mov     temp2 = ar.bspstore;                            \
+       ;;                                                      \
+       DATA_PA_TO_VA(temp2,temp1);                             \
+       ;;                                                      \
+       mov     temp1 = ar.rnat;                                \
+       ;;                                                      \
+       mov     ar.bspstore = temp2;                            \
+       ;;                                                      \
+       mov     ar.rnat = temp1;                                \
+       ;;                                                      \
+       mov     temp1 = old_psr;                                \
+       ;;                                                      \
+       mov     temp2 = 1;                                      \
+       ;;                                                      \
+       dep     temp1 = temp2, temp1, PSR_IC, 1;                \
+       ;;                                                      \
+       dep     temp1 = temp2, temp1, PSR_IT, 1;                \
+       ;;                                                      \
+       dep     temp1 = temp2, temp1, PSR_DT, 1;                \
+       ;;                                                      \
+       dep     temp1 = temp2, temp1, PSR_RT, 1;                \
+       ;;                                                      \
+       dep     temp1 = temp2, temp1, PSR_BN, 1;                \
+       ;;                                                      \
+                                                               \
+       mov     cr.ipsr = temp1;                                \
+       movl    temp2 = start_addr;                             \
+       ;;                                                      \
+       mov     cr.iip = temp2;                                 \
+       ;;                                                      \
+       DATA_PA_TO_VA(sp, temp1);                               \
+       DATA_PA_TO_VA(gp, temp2);                               \
+       srlz.i;                                                 \
+       ;;                                                      \
+       nop     1;                                              \
+       nop     2;                                              \
+       nop     1;                                              \
+       rfi                                                     \
+       ;;
+
+/*
+ * The following offsets capture the order in which the
+ * RSE related registers from the old context are
+ * saved onto the new stack frame.
+ *
+ *     +-----------------------+
+ *     |NDIRTY [BSP - BSPSTORE]|
+ *     +-----------------------+
+ *     |       RNAT            |
+ *     +-----------------------+
+ *     |       BSPSTORE        |
+ *     +-----------------------+
+ *     |       IFS             |
+ *     +-----------------------+
+ *     |       PFS             |
+ *     +-----------------------+
+ *     |       RSC             |
+ *     +-----------------------+ <-------- Bottom of new stack frame
+ */
+#define  rse_rsc_offset                0
+#define  rse_pfs_offset                (rse_rsc_offset+0x08)
+#define  rse_ifs_offset                (rse_pfs_offset+0x08)
+#define  rse_bspstore_offset   (rse_ifs_offset+0x08)
+#define  rse_rnat_offset       (rse_bspstore_offset+0x08)
+#define  rse_ndirty_offset     (rse_rnat_offset+0x08)
+
+/*
+ * rse_switch_context
+ *
+ *     1. Save old RSC onto the new stack frame
+ *     2. Save PFS onto new stack frame
+ *     3. Cover the old frame and start a new frame.
+ *     4. Save IFS onto new stack frame
+ *     5. Save the old BSPSTORE on the new stack frame
+ *     6. Save the old RNAT on the new stack frame
+ *     7. Write BSPSTORE with the new backing store pointer
+ *     8. Read and save the new BSP to calculate the #dirty registers
+ * NOTE: Look at pages 11-10, 11-11 in PRM Vol 2
+ */
+#define rse_switch_context(temp,p_stackframe,p_bspstore)                       
\
+       ;;                                                                      
\
+       mov     temp=ar.rsc;;                                                   
\
+       st8     [p_stackframe]=temp,8;;                                 \
+       mov     temp=ar.pfs;;                                                   
\
+       st8     [p_stackframe]=temp,8;                                          
\
+       cover ;;                                                                
\
+       mov     temp=cr.ifs;;                                                   
\
+       st8     [p_stackframe]=temp,8;;                                         
\
+       mov     temp=ar.bspstore;;                                              
\
+       st8     [p_stackframe]=temp,8;;                                 \
+       mov     temp=ar.rnat;;                                                  
\
+       st8     [p_stackframe]=temp,8;                                          
\
+       mov     ar.bspstore=p_bspstore;;                                        
\
+       mov     temp=ar.bsp;;                                                   
\
+       sub     temp=temp,p_bspstore;;                                          
\
+       st8     [p_stackframe]=temp,8;;
+
+/*
+ * rse_return_context
+ *     1. Allocate a zero-sized frame
+ *     2. Store the number of dirty registers RSC.loadrs field
+ *     3. Issue a loadrs to insure that any registers from the interrupted
+ *        context which were saved on the new stack frame have been loaded
+ *        back into the stacked registers
+ *     4. Restore BSPSTORE
+ *     5. Restore RNAT
+ *     6. Restore PFS
+ *     7. Restore IFS
+ *     8. Restore RSC
+ *     9. Issue an RFI
+ */
+#define rse_return_context(psr_mask_reg,temp,p_stackframe)                     
\
+       ;;                                                                      
\
+       alloc   temp=ar.pfs,0,0,0,0;                                            
\
+       add     p_stackframe=rse_ndirty_offset,p_stackframe;;                   
\
+       ld8     temp=[p_stackframe];;                                           
\
+       shl     temp=temp,16;;                                                  
\
+       mov     ar.rsc=temp;;                                                   
\
+       loadrs;;                                                                
\
+       add     
p_stackframe=-rse_ndirty_offset+rse_bspstore_offset,p_stackframe;;\
+       ld8     temp=[p_stackframe];;                                           
\
+       mov     ar.bspstore=temp;;                                              
\
+       add     
p_stackframe=-rse_bspstore_offset+rse_rnat_offset,p_stackframe;;\
+       ld8     temp=[p_stackframe];;                                           
\
+       mov     ar.rnat=temp;;                                                  
\
+       add     p_stackframe=-rse_rnat_offset+rse_pfs_offset,p_stackframe;;     
\
+       ld8     temp=[p_stackframe];;                                           
\
+       mov     ar.pfs=temp;;                                                   
\
+       add     p_stackframe=-rse_pfs_offset+rse_ifs_offset,p_stackframe;;      
\
+       ld8     temp=[p_stackframe];;                                           
\
+       mov     cr.ifs=temp;;                                                   
\
+       add     p_stackframe=-rse_ifs_offset+rse_rsc_offset,p_stackframe;;      
\
+       ld8     temp=[p_stackframe];;                                           
\
+       mov     ar.rsc=temp ;                                                   
\
+       mov     temp=psr;;                                                      
\
+       or      temp=temp,psr_mask_reg;;                                        
\
+       mov     cr.ipsr=temp;;                                                  
\
+       mov     temp=ip;;                                                       
\
+       add     temp=0x30,temp;;                                                
\
+       mov     cr.iip=temp;;                                                   
\
+       srlz.i;;                                                                
\
+       rfi;;
+
+#endif /* _ASM_IA64_MCA_ASM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/page.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/page.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,238 @@
+#ifndef _ASM_IA64_PAGE_H
+#define _ASM_IA64_PAGE_H
+/*
+ * Pagetable related stuff.
+ *
+ * Copyright (C) 1998, 1999, 2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <asm/intrinsics.h>
+#include <asm/types.h>
+
+/*
+ * PAGE_SHIFT determines the actual kernel page size.
+ */
+#if defined(CONFIG_IA64_PAGE_SIZE_4KB)
+# define PAGE_SHIFT    12
+#elif defined(CONFIG_IA64_PAGE_SIZE_8KB)
+# define PAGE_SHIFT    13
+#elif defined(CONFIG_IA64_PAGE_SIZE_16KB)
+# define PAGE_SHIFT    14
+#elif defined(CONFIG_IA64_PAGE_SIZE_64KB)
+# define PAGE_SHIFT    16
+#else
+# error Unsupported page size!
+#endif
+
+#define PAGE_SIZE              (__IA64_UL_CONST(1) << PAGE_SHIFT)
+#define PAGE_MASK              (~(PAGE_SIZE - 1))
+#define PAGE_ALIGN(addr)       (((addr) + PAGE_SIZE - 1) & PAGE_MASK)
+
+#define PERCPU_PAGE_SHIFT      16      /* log2() of max. size of per-CPU area 
*/
+
+#define PERCPU_PAGE_SIZE       (__IA64_UL_CONST(1) << PERCPU_PAGE_SHIFT)
+
+#define RGN_MAP_LIMIT  ((1UL << (4*PAGE_SHIFT - 12)) - PAGE_SIZE)      /* per 
region addr limit */
+
+#ifdef CONFIG_HUGETLB_PAGE
+# define REGION_HPAGE          (4UL)   /* note: this is hardcoded in 
reload_context()!*/
+# define REGION_SHIFT          61
+# define HPAGE_REGION_BASE     (REGION_HPAGE << REGION_SHIFT)
+# define HPAGE_SHIFT           hpage_shift
+# define HPAGE_SHIFT_DEFAULT   28      /* check ia64 SDM for architecture 
supported size */
+# define HPAGE_SIZE            (__IA64_UL_CONST(1) << HPAGE_SHIFT)
+# define HPAGE_MASK            (~(HPAGE_SIZE - 1))
+
+# define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
+# define ARCH_HAS_HUGEPAGE_ONLY_RANGE
+#endif /* CONFIG_HUGETLB_PAGE */
+
+#ifdef __ASSEMBLY__
+# define __pa(x)               ((x) - PAGE_OFFSET)
+# define __va(x)               ((x) + PAGE_OFFSET)
+#else /* !__ASSEMBLY */
+# ifdef __KERNEL__
+#  define STRICT_MM_TYPECHECKS
+
+extern void clear_page (void *page);
+extern void copy_page (void *to, void *from);
+
+/*
+ * clear_user_page() and copy_user_page() can't be inline functions because
+ * flush_dcache_page() can't be defined until later...
+ */
+#define clear_user_page(addr, vaddr, page)     \
+do {                                           \
+       clear_page(addr);                       \
+       flush_dcache_page(page);                \
+} while (0)
+
+#define copy_user_page(to, from, vaddr, page)  \
+do {                                           \
+       copy_page((to), (from));                \
+       flush_dcache_page(page);                \
+} while (0)
+
+
+#define alloc_zeroed_user_highpage(vma, vaddr) \
+({                                             \
+       struct page *page = alloc_page_vma(GFP_HIGHUSER | __GFP_ZERO, vma, 
vaddr); \
+       if (page)                               \
+               flush_dcache_page(page);        \
+       page;                                   \
+})
+
+#define __HAVE_ARCH_ALLOC_ZEROED_USER_HIGHPAGE
+
+#define virt_addr_valid(kaddr) pfn_valid(__pa(kaddr) >> PAGE_SHIFT)
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+extern int ia64_pfn_valid (unsigned long pfn);
+#else
+# define ia64_pfn_valid(pfn) 1
+#endif
+
+#ifndef CONFIG_DISCONTIGMEM
+#ifdef XEN
+# define pfn_valid(pfn)                (0)
+# define page_to_pfn(_page)    ((unsigned long)((_page) - frame_table))
+# define pfn_to_page(_pfn)     (frame_table + (_pfn))
+#else
+# define pfn_valid(pfn)                (((pfn) < max_mapnr) && 
ia64_pfn_valid(pfn))
+# define page_to_pfn(page)     ((unsigned long) (page - mem_map))
+# define pfn_to_page(pfn)      (mem_map + (pfn))
+#endif
+#else
+extern struct page *vmem_map;
+extern unsigned long max_low_pfn;
+# define pfn_valid(pfn)                (((pfn) < max_low_pfn) && 
ia64_pfn_valid(pfn))
+# define page_to_pfn(page)     ((unsigned long) (page - vmem_map))
+# define pfn_to_page(pfn)      (vmem_map + (pfn))
+#endif
+
+#define page_to_phys(page)     (page_to_pfn(page) << PAGE_SHIFT)
+#define virt_to_page(kaddr)    pfn_to_page(__pa(kaddr) >> PAGE_SHIFT)
+
+#ifdef XEN
+#define page_to_virt(_page)    phys_to_virt(page_to_phys(_page))
+#define phys_to_page(kaddr)    pfn_to_page(((kaddr) >> PAGE_SHIFT))
+#endif
+
+typedef union ia64_va {
+       struct {
+               unsigned long off : 61;         /* intra-region offset */
+               unsigned long reg :  3;         /* region number */
+       } f;
+       unsigned long l;
+       void *p;
+} ia64_va;
+
+/*
+ * Note: These macros depend on the fact that PAGE_OFFSET has all
+ * region bits set to 1 and all other bits set to zero.  They are
+ * expressed in this way to ensure they result in a single "dep"
+ * instruction.
+ */
+#ifdef XEN
+typedef union xen_va {
+       struct {
+               unsigned long off : 60;
+               unsigned long reg : 4;
+       } f;
+       unsigned long l;
+       void *p;
+} xen_va;
+
+// xen/drivers/console.c uses __va in a declaration (should be fixed!)
+#define __pa(x)                ({xen_va _v; _v.l = (long) (x); _v.f.reg = 0; 
_v.l;})
+#define __va(x)                ({xen_va _v; _v.l = (long) (x); _v.f.reg = -1; 
_v.p;})
+#else
+#define __pa(x)                ({ia64_va _v; _v.l = (long) (x); _v.f.reg = 0; 
_v.l;})
+#define __va(x)                ({ia64_va _v; _v.l = (long) (x); _v.f.reg = -1; 
_v.p;})
+#endif
+
+#define REGION_NUMBER(x)       ({ia64_va _v; _v.l = (long) (x); _v.f.reg;})
+#define REGION_OFFSET(x)       ({ia64_va _v; _v.l = (long) (x); _v.f.off;})
+
+#define REGION_SIZE            REGION_NUMBER(1)
+#define REGION_KERNEL          7
+
+#ifdef CONFIG_HUGETLB_PAGE
+# define htlbpage_to_page(x)   (((unsigned long) REGION_NUMBER(x) << 61)       
                \
+                                | (REGION_OFFSET(x) >> 
(HPAGE_SHIFT-PAGE_SHIFT)))
+# define HUGETLB_PAGE_ORDER    (HPAGE_SHIFT - PAGE_SHIFT)
+# define is_hugepage_only_range(addr, len)             \
+        (REGION_NUMBER(addr) == REGION_HPAGE &&        \
+         REGION_NUMBER((addr)+(len)) == REGION_HPAGE)
+extern unsigned int hpage_shift;
+#endif
+
+static __inline__ int
+get_order (unsigned long size)
+{
+       long double d = size - 1;
+       long order;
+
+       order = ia64_getf_exp(d);
+       order = order - PAGE_SHIFT - 0xffff + 1;
+       if (order < 0)
+               order = 0;
+       return order;
+}
+
+# endif /* __KERNEL__ */
+#endif /* !__ASSEMBLY__ */
+
+#ifdef STRICT_MM_TYPECHECKS
+  /*
+   * These are used to make use of C type-checking..
+   */
+  typedef struct { unsigned long pte; } pte_t;
+  typedef struct { unsigned long pmd; } pmd_t;
+  typedef struct { unsigned long pgd; } pgd_t;
+  typedef struct { unsigned long pgprot; } pgprot_t;
+
+# define pte_val(x)    ((x).pte)
+# define pmd_val(x)    ((x).pmd)
+# define pgd_val(x)    ((x).pgd)
+# define pgprot_val(x) ((x).pgprot)
+
+# define __pte(x)      ((pte_t) { (x) } )
+# define __pgprot(x)   ((pgprot_t) { (x) } )
+
+#else /* !STRICT_MM_TYPECHECKS */
+  /*
+   * .. while these make it easier on the compiler
+   */
+# ifndef __ASSEMBLY__
+    typedef unsigned long pte_t;
+    typedef unsigned long pmd_t;
+    typedef unsigned long pgd_t;
+    typedef unsigned long pgprot_t;
+# endif
+
+# define pte_val(x)    (x)
+# define pmd_val(x)    (x)
+# define pgd_val(x)    (x)
+# define pgprot_val(x) (x)
+
+# define __pte(x)      (x)
+# define __pgd(x)      (x)
+# define __pgprot(x)   (x)
+#endif /* !STRICT_MM_TYPECHECKS */
+
+#ifdef XEN
+#define PAGE_OFFSET                    __IA64_UL_CONST(0xf000000000000000)
+#else
+#define PAGE_OFFSET                    __IA64_UL_CONST(0xe000000000000000)
+#endif
+
+#define VM_DATA_DEFAULT_FLAGS          (VM_READ | VM_WRITE |                   
                \
+                                        VM_MAYREAD | VM_MAYWRITE | VM_MAYEXEC 
|                \
+                                        (((current->personality & 
READ_IMPLIES_EXEC) != 0)     \
+                                         ? VM_EXEC : 0))
+
+#endif /* _ASM_IA64_PAGE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/pal.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/pal.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1567 @@
+#ifndef _ASM_IA64_PAL_H
+#define _ASM_IA64_PAL_H
+
+/*
+ * Processor Abstraction Layer definitions.
+ *
+ * This is based on Intel IA-64 Architecture Software Developer's Manual rev 
1.0
+ * chapter 11 IA-64 Processor Abstraction Layer
+ *
+ * Copyright (C) 1998-2001 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999 Srinivasa Prasad Thirumalachar 
<sprasad@xxxxxxxxxxxxxxxxxxxx>
+ *
+ * 99/10/01    davidm  Make sure we pass zero for reserved parameters.
+ * 00/03/07    davidm  Updated pal_cache_flush() to be in sync with PAL v2.6.
+ * 00/03/23     cfleck  Modified processor min-state save area to match 
updated PAL & SAL info
+ * 00/05/24     eranian Updated to latest PAL spec, fix structures bugs, added
+ * 00/05/25    eranian Support for stack calls, and static physical calls
+ * 00/06/18    eranian Support for stacked physical calls
+ */
+
+/*
+ * Note that some of these calls use a static-register only calling
+ * convention which has nothing to do with the regular calling
+ * convention.
+ */
+#define PAL_CACHE_FLUSH                1       /* flush i/d cache */
+#define PAL_CACHE_INFO         2       /* get detailed i/d cache info */
+#define PAL_CACHE_INIT         3       /* initialize i/d cache */
+#define PAL_CACHE_SUMMARY      4       /* get summary of cache heirarchy */
+#define PAL_MEM_ATTRIB         5       /* list supported memory attributes */
+#define PAL_PTCE_INFO          6       /* purge TLB info */
+#define PAL_VM_INFO            7       /* return supported virtual memory 
features */
+#define PAL_VM_SUMMARY         8       /* return summary on supported vm 
features */
+#define PAL_BUS_GET_FEATURES   9       /* return processor bus interface 
features settings */
+#define PAL_BUS_SET_FEATURES   10      /* set processor bus features */
+#define PAL_DEBUG_INFO         11      /* get number of debug registers */
+#define PAL_FIXED_ADDR         12      /* get fixed component of processors's 
directed address */
+#define PAL_FREQ_BASE          13      /* base frequency of the platform */
+#define PAL_FREQ_RATIOS                14      /* ratio of processor, bus and 
ITC frequency */
+#define PAL_PERF_MON_INFO      15      /* return performance monitor info */
+#define PAL_PLATFORM_ADDR      16      /* set processor interrupt block and IO 
port space addr */
+#define PAL_PROC_GET_FEATURES  17      /* get configurable processor features 
& settings */
+#define PAL_PROC_SET_FEATURES  18      /* enable/disable configurable 
processor features */
+#define PAL_RSE_INFO           19      /* return rse information */
+#define PAL_VERSION            20      /* return version of PAL code */
+#define PAL_MC_CLEAR_LOG       21      /* clear all processor log info */
+#define PAL_MC_DRAIN           22      /* drain operations which could result 
in an MCA */
+#define PAL_MC_EXPECTED                23      /* set/reset expected MCA 
indicator */
+#define PAL_MC_DYNAMIC_STATE   24      /* get processor dynamic state */
+#define PAL_MC_ERROR_INFO      25      /* get processor MCA info and static 
state */
+#define PAL_MC_RESUME          26      /* Return to interrupted process */
+#define PAL_MC_REGISTER_MEM    27      /* Register memory for PAL to use 
during MCAs and inits */
+#define PAL_HALT               28      /* enter the low power HALT state */
+#define PAL_HALT_LIGHT         29      /* enter the low power light halt 
state*/
+#define PAL_COPY_INFO          30      /* returns info needed to relocate PAL 
*/
+#define PAL_CACHE_LINE_INIT    31      /* init tags & data of cache line */
+#define PAL_PMI_ENTRYPOINT     32      /* register PMI memory entry points 
with the processor */
+#define PAL_ENTER_IA_32_ENV    33      /* enter IA-32 system environment */
+#define PAL_VM_PAGE_SIZE       34      /* return vm TC and page walker page 
sizes */
+
+#define PAL_MEM_FOR_TEST       37      /* get amount of memory needed for late 
processor test */
+#define PAL_CACHE_PROT_INFO    38      /* get i/d cache protection info */
+#define PAL_REGISTER_INFO      39      /* return AR and CR register 
information*/
+#define PAL_SHUTDOWN           40      /* enter processor shutdown state */
+#define PAL_PREFETCH_VISIBILITY        41      /* Make Processor Prefetches 
Visible */
+
+#define PAL_COPY_PAL           256     /* relocate PAL procedures and PAL PMI 
*/
+#define PAL_HALT_INFO          257     /* return the low power capabilities of 
processor */
+#define PAL_TEST_PROC          258     /* perform late processor self-test */
+#define PAL_CACHE_READ         259     /* read tag & data of cacheline for 
diagnostic testing */
+#define PAL_CACHE_WRITE                260     /* write tag & data of 
cacheline for diagnostic testing */
+#define PAL_VM_TR_READ         261     /* read contents of translation 
register */
+
+#ifndef __ASSEMBLY__
+
+#include <linux/types.h>
+#include <asm/fpu.h>
+
+/*
+ * Data types needed to pass information into PAL procedures and
+ * interpret information returned by them.
+ */
+
+/* Return status from the PAL procedure */
+typedef s64                            pal_status_t;
+
+#define PAL_STATUS_SUCCESS             0       /* No error */
+#define PAL_STATUS_UNIMPLEMENTED       (-1)    /* Unimplemented procedure */
+#define PAL_STATUS_EINVAL              (-2)    /* Invalid argument */
+#define PAL_STATUS_ERROR               (-3)    /* Error */
+#define PAL_STATUS_CACHE_INIT_FAIL     (-4)    /* Could not initialize the
+                                                * specified level and type of
+                                                * cache without sideeffects
+                                                * and "restrict" was 1
+                                                */
+
+/* Processor cache level in the heirarchy */
+typedef u64                            pal_cache_level_t;
+#define PAL_CACHE_LEVEL_L0             0       /* L0 */
+#define PAL_CACHE_LEVEL_L1             1       /* L1 */
+#define PAL_CACHE_LEVEL_L2             2       /* L2 */
+
+
+/* Processor cache type at a particular level in the heirarchy */
+
+typedef u64                            pal_cache_type_t;
+#define PAL_CACHE_TYPE_INSTRUCTION     1       /* Instruction cache */
+#define PAL_CACHE_TYPE_DATA            2       /* Data or unified cache */
+#define PAL_CACHE_TYPE_INSTRUCTION_DATA        3       /* Both Data & 
Instruction */
+
+
+#define PAL_CACHE_FLUSH_INVALIDATE     1       /* Invalidate clean lines */
+#define PAL_CACHE_FLUSH_CHK_INTRS      2       /* check for interrupts/mc 
while flushing */
+
+/* Processor cache line size in bytes  */
+typedef int                            pal_cache_line_size_t;
+
+/* Processor cache line state */
+typedef u64                            pal_cache_line_state_t;
+#define PAL_CACHE_LINE_STATE_INVALID   0       /* Invalid */
+#define PAL_CACHE_LINE_STATE_SHARED    1       /* Shared */
+#define PAL_CACHE_LINE_STATE_EXCLUSIVE 2       /* Exclusive */
+#define PAL_CACHE_LINE_STATE_MODIFIED  3       /* Modified */
+
+typedef struct pal_freq_ratio {
+       u64 den : 32, num : 32; /* numerator & denominator */
+} itc_ratio, proc_ratio;
+
+typedef        union  pal_cache_config_info_1_s {
+       struct {
+               u64             u               : 1,    /* 0 Unified cache ? */
+                               at              : 2,    /* 2-1 Cache mem attr*/
+                               reserved        : 5,    /* 7-3 Reserved */
+                               associativity   : 8,    /* 16-8 Associativity*/
+                               line_size       : 8,    /* 23-17 Line size */
+                               stride          : 8,    /* 31-24 Stride */
+                               store_latency   : 8,    /*39-32 Store latency*/
+                               load_latency    : 8,    /* 47-40 Load latency*/
+                               store_hints     : 8,    /* 55-48 Store hints*/
+                               load_hints      : 8;    /* 63-56 Load hints */
+       } pcci1_bits;
+       u64                     pcci1_data;
+} pal_cache_config_info_1_t;
+
+typedef        union  pal_cache_config_info_2_s {
+       struct {
+               u64             cache_size      : 32,   /*cache size in bytes*/
+
+
+                               alias_boundary  : 8,    /* 39-32 aliased addr
+                                                        * separation for max
+                                                        * performance.
+                                                        */
+                               tag_ls_bit      : 8,    /* 47-40 LSb of addr*/
+                               tag_ms_bit      : 8,    /* 55-48 MSb of addr*/
+                               reserved        : 8;    /* 63-56 Reserved */
+       } pcci2_bits;
+       u64                     pcci2_data;
+} pal_cache_config_info_2_t;
+
+
+typedef struct pal_cache_config_info_s {
+       pal_status_t                    pcci_status;
+       pal_cache_config_info_1_t       pcci_info_1;
+       pal_cache_config_info_2_t       pcci_info_2;
+       u64                             pcci_reserved;
+} pal_cache_config_info_t;
+
+#define pcci_ld_hints          pcci_info_1.pcci1_bits.load_hints
+#define pcci_st_hints          pcci_info_1.pcci1_bits.store_hints
+#define pcci_ld_latency                pcci_info_1.pcci1_bits.load_latency
+#define pcci_st_latency                pcci_info_1.pcci1_bits.store_latency
+#define pcci_stride            pcci_info_1.pcci1_bits.stride
+#define pcci_line_size         pcci_info_1.pcci1_bits.line_size
+#define pcci_assoc             pcci_info_1.pcci1_bits.associativity
+#define pcci_cache_attr                pcci_info_1.pcci1_bits.at
+#define pcci_unified           pcci_info_1.pcci1_bits.u
+#define pcci_tag_msb           pcci_info_2.pcci2_bits.tag_ms_bit
+#define pcci_tag_lsb           pcci_info_2.pcci2_bits.tag_ls_bit
+#define pcci_alias_boundary    pcci_info_2.pcci2_bits.alias_boundary
+#define pcci_cache_size                pcci_info_2.pcci2_bits.cache_size
+
+
+
+/* Possible values for cache attributes */
+
+#define PAL_CACHE_ATTR_WT              0       /* Write through cache */
+#define PAL_CACHE_ATTR_WB              1       /* Write back cache */
+#define PAL_CACHE_ATTR_WT_OR_WB                2       /* Either write thru or 
write
+                                                * back depending on TLB
+                                                * memory attributes
+                                                */
+
+
+/* Possible values for cache hints */
+
+#define PAL_CACHE_HINT_TEMP_1          0       /* Temporal level 1 */
+#define PAL_CACHE_HINT_NTEMP_1         1       /* Non-temporal level 1 */
+#define PAL_CACHE_HINT_NTEMP_ALL       3       /* Non-temporal all levels */
+
+/* Processor cache protection  information */
+typedef union pal_cache_protection_element_u {
+       u32                     pcpi_data;
+       struct {
+               u32             data_bits       : 8, /* # data bits covered by
+                                                     * each unit of protection
+                                                     */
+
+                               tagprot_lsb     : 6, /* Least -do- */
+                               tagprot_msb     : 6, /* Most Sig. tag address
+                                                     * bit that this
+                                                     * protection covers.
+                                                     */
+                               prot_bits       : 6, /* # of protection bits */
+                               method          : 4, /* Protection method */
+                               t_d             : 2; /* Indicates which part
+                                                     * of the cache this
+                                                     * protection encoding
+                                                     * applies.
+                                                     */
+       } pcp_info;
+} pal_cache_protection_element_t;
+
+#define pcpi_cache_prot_part   pcp_info.t_d
+#define pcpi_prot_method       pcp_info.method
+#define pcpi_prot_bits         pcp_info.prot_bits
+#define pcpi_tagprot_msb       pcp_info.tagprot_msb
+#define pcpi_tagprot_lsb       pcp_info.tagprot_lsb
+#define pcpi_data_bits         pcp_info.data_bits
+
+/* Processor cache part encodings */
+#define PAL_CACHE_PROT_PART_DATA       0       /* Data protection  */
+#define PAL_CACHE_PROT_PART_TAG                1       /* Tag  protection */
+#define PAL_CACHE_PROT_PART_TAG_DATA   2       /* Tag+data protection (tag is
+                                                * more significant )
+                                                */
+#define PAL_CACHE_PROT_PART_DATA_TAG   3       /* Data+tag protection (data is
+                                                * more significant )
+                                                */
+#define PAL_CACHE_PROT_PART_MAX                6
+
+
+typedef struct pal_cache_protection_info_s {
+       pal_status_t                    pcpi_status;
+       pal_cache_protection_element_t  pcp_info[PAL_CACHE_PROT_PART_MAX];
+} pal_cache_protection_info_t;
+
+
+/* Processor cache protection method encodings */
+#define PAL_CACHE_PROT_METHOD_NONE             0       /* No protection */
+#define PAL_CACHE_PROT_METHOD_ODD_PARITY       1       /* Odd parity */
+#define PAL_CACHE_PROT_METHOD_EVEN_PARITY      2       /* Even parity */
+#define PAL_CACHE_PROT_METHOD_ECC              3       /* ECC protection */
+
+
+/* Processor cache line identification in the heirarchy */
+typedef union pal_cache_line_id_u {
+       u64                     pclid_data;
+       struct {
+               u64             cache_type      : 8,    /* 7-0 cache type */
+                               level           : 8,    /* 15-8 level of the
+                                                        * cache in the
+                                                        * heirarchy.
+                                                        */
+                               way             : 8,    /* 23-16 way in the set
+                                                        */
+                               part            : 8,    /* 31-24 part of the
+                                                        * cache
+                                                        */
+                               reserved        : 32;   /* 63-32 is reserved*/
+       } pclid_info_read;
+       struct {
+               u64             cache_type      : 8,    /* 7-0 cache type */
+                               level           : 8,    /* 15-8 level of the
+                                                        * cache in the
+                                                        * heirarchy.
+                                                        */
+                               way             : 8,    /* 23-16 way in the set
+                                                        */
+                               part            : 8,    /* 31-24 part of the
+                                                        * cache
+                                                        */
+                               mesi            : 8,    /* 39-32 cache line
+                                                        * state
+                                                        */
+                               start           : 8,    /* 47-40 lsb of data to
+                                                        * invert
+                                                        */
+                               length          : 8,    /* 55-48 #bits to
+                                                        * invert
+                                                        */
+                               trigger         : 8;    /* 63-56 Trigger error
+                                                        * by doing a load
+                                                        * after the write
+                                                        */
+
+       } pclid_info_write;
+} pal_cache_line_id_u_t;
+
+#define pclid_read_part                pclid_info_read.part
+#define pclid_read_way         pclid_info_read.way
+#define pclid_read_level       pclid_info_read.level
+#define pclid_read_cache_type  pclid_info_read.cache_type
+
+#define pclid_write_trigger    pclid_info_write.trigger
+#define pclid_write_length     pclid_info_write.length
+#define pclid_write_start      pclid_info_write.start
+#define pclid_write_mesi       pclid_info_write.mesi
+#define pclid_write_part       pclid_info_write.part
+#define pclid_write_way                pclid_info_write.way
+#define pclid_write_level      pclid_info_write.level
+#define pclid_write_cache_type pclid_info_write.cache_type
+
+/* Processor cache line part encodings */
+#define PAL_CACHE_LINE_ID_PART_DATA            0       /* Data */
+#define PAL_CACHE_LINE_ID_PART_TAG             1       /* Tag */
+#define PAL_CACHE_LINE_ID_PART_DATA_PROT       2       /* Data protection */
+#define PAL_CACHE_LINE_ID_PART_TAG_PROT                3       /* Tag 
protection */
+#define PAL_CACHE_LINE_ID_PART_DATA_TAG_PROT   4       /* Data+tag
+                                                        * protection
+                                                        */
+typedef struct pal_cache_line_info_s {
+       pal_status_t            pcli_status;            /* Return status of the 
read cache line
+                                                        * info call.
+                                                        */
+       u64                     pcli_data;              /* 64-bit data, tag, 
protection bits .. */
+       u64                     pcli_data_len;          /* data length in bits 
*/
+       pal_cache_line_state_t  pcli_cache_line_state;  /* mesi state */
+
+} pal_cache_line_info_t;
+
+
+/* Machine Check related crap */
+
+/* Pending event status bits  */
+typedef u64                                    pal_mc_pending_events_t;
+
+#define PAL_MC_PENDING_MCA                     (1 << 0)
+#define PAL_MC_PENDING_INIT                    (1 << 1)
+
+/* Error information type */
+typedef u64                                    pal_mc_info_index_t;
+
+#define PAL_MC_INFO_PROCESSOR                  0       /* Processor */
+#define PAL_MC_INFO_CACHE_CHECK                        1       /* Cache check 
*/
+#define PAL_MC_INFO_TLB_CHECK                  2       /* Tlb check */
+#define PAL_MC_INFO_BUS_CHECK                  3       /* Bus check */
+#define PAL_MC_INFO_REQ_ADDR                   4       /* Requestor address */
+#define PAL_MC_INFO_RESP_ADDR                  5       /* Responder address */
+#define PAL_MC_INFO_TARGET_ADDR                        6       /* Target 
address */
+#define PAL_MC_INFO_IMPL_DEP                   7       /* Implementation
+                                                        * dependent
+                                                        */
+
+
+typedef struct pal_process_state_info_s {
+       u64             reserved1       : 2,
+                       rz              : 1,    /* PAL_CHECK processor
+                                                * rendezvous
+                                                * successful.
+                                                */
+
+                       ra              : 1,    /* PAL_CHECK attempted
+                                                * a rendezvous.
+                                                */
+                       me              : 1,    /* Distinct multiple
+                                                * errors occurred
+                                                */
+
+                       mn              : 1,    /* Min. state save
+                                                * area has been
+                                                * registered with PAL
+                                                */
+
+                       sy              : 1,    /* Storage integrity
+                                                * synched
+                                                */
+
+
+                       co              : 1,    /* Continuable */
+                       ci              : 1,    /* MC isolated */
+                       us              : 1,    /* Uncontained storage
+                                                * damage.
+                                                */
+
+
+                       hd              : 1,    /* Non-essential hw
+                                                * lost (no loss of
+                                                * functionality)
+                                                * causing the
+                                                * processor to run in
+                                                * degraded mode.
+                                                */
+
+                       tl              : 1,    /* 1 => MC occurred
+                                                * after an instr was
+                                                * executed but before
+                                                * the trap that
+                                                * resulted from instr
+                                                * execution was
+                                                * generated.
+                                                * (Trap Lost )
+                                                */
+                       mi              : 1,    /* More information available
+                                                * call PAL_MC_ERROR_INFO
+                                                */
+                       pi              : 1,    /* Precise instruction pointer 
*/
+                       pm              : 1,    /* Precise min-state save area 
*/
+
+                       dy              : 1,    /* Processor dynamic
+                                                * state valid
+                                                */
+
+
+                       in              : 1,    /* 0 = MC, 1 = INIT */
+                       rs              : 1,    /* RSE valid */
+                       cm              : 1,    /* MC corrected */
+                       ex              : 1,    /* MC is expected */
+                       cr              : 1,    /* Control regs valid*/
+                       pc              : 1,    /* Perf cntrs valid */
+                       dr              : 1,    /* Debug regs valid */
+                       tr              : 1,    /* Translation regs
+                                                * valid
+                                                */
+                       rr              : 1,    /* Region regs valid */
+                       ar              : 1,    /* App regs valid */
+                       br              : 1,    /* Branch regs valid */
+                       pr              : 1,    /* Predicate registers
+                                                * valid
+                                                */
+
+                       fp              : 1,    /* fp registers valid*/
+                       b1              : 1,    /* Preserved bank one
+                                                * general registers
+                                                * are valid
+                                                */
+                       b0              : 1,    /* Preserved bank zero
+                                                * general registers
+                                                * are valid
+                                                */
+                       gr              : 1,    /* General registers
+                                                * are valid
+                                                * (excl. banked regs)
+                                                */
+                       dsize           : 16,   /* size of dynamic
+                                                * state returned
+                                                * by the processor
+                                                */
+
+                       reserved2       : 11,
+                       cc              : 1,    /* Cache check */
+                       tc              : 1,    /* TLB check */
+                       bc              : 1,    /* Bus check */
+                       rc              : 1,    /* Register file check */
+                       uc              : 1;    /* Uarch check */
+
+} pal_processor_state_info_t;
+
+typedef struct pal_cache_check_info_s {
+       u64             op              : 4,    /* Type of cache
+                                                * operation that
+                                                * caused the machine
+                                                * check.
+                                                */
+                       level           : 2,    /* Cache level */
+                       reserved1       : 2,
+                       dl              : 1,    /* Failure in data part
+                                                * of cache line
+                                                */
+                       tl              : 1,    /* Failure in tag part
+                                                * of cache line
+                                                */
+                       dc              : 1,    /* Failure in dcache */
+                       ic              : 1,    /* Failure in icache */
+                       mesi            : 3,    /* Cache line state */
+                       mv              : 1,    /* mesi valid */
+                       way             : 5,    /* Way in which the
+                                                * error occurred
+                                                */
+                       wiv             : 1,    /* Way field valid */
+                       reserved2       : 10,
+
+                       index           : 20,   /* Cache line index */
+                       reserved3       : 2,
+
+                       is              : 1,    /* instruction set (1 == ia32) 
*/
+                       iv              : 1,    /* instruction set field valid 
*/
+                       pl              : 2,    /* privilege level */
+                       pv              : 1,    /* privilege level field valid 
*/
+                       mcc             : 1,    /* Machine check corrected */
+                       tv              : 1,    /* Target address
+                                                * structure is valid
+                                                */
+                       rq              : 1,    /* Requester identifier
+                                                * structure is valid
+                                                */
+                       rp              : 1,    /* Responder identifier
+                                                * structure is valid
+                                                */
+                       pi              : 1;    /* Precise instruction pointer
+                                                * structure is valid
+                                                */
+} pal_cache_check_info_t;
+
+typedef struct pal_tlb_check_info_s {
+
+       u64             tr_slot         : 8,    /* Slot# of TR where
+                                                * error occurred
+                                                */
+                       trv             : 1,    /* tr_slot field is valid */
+                       reserved1       : 1,
+                       level           : 2,    /* TLB level where failure 
occurred */
+                       reserved2       : 4,
+                       dtr             : 1,    /* Fail in data TR */
+                       itr             : 1,    /* Fail in inst TR */
+                       dtc             : 1,    /* Fail in data TC */
+                       itc             : 1,    /* Fail in inst. TC */
+                       op              : 4,    /* Cache operation */
+                       reserved3       : 30,
+
+                       is              : 1,    /* instruction set (1 == ia32) 
*/
+                       iv              : 1,    /* instruction set field valid 
*/
+                       pl              : 2,    /* privilege level */
+                       pv              : 1,    /* privilege level field valid 
*/
+                       mcc             : 1,    /* Machine check corrected */
+                       tv              : 1,    /* Target address
+                                                * structure is valid
+                                                */
+                       rq              : 1,    /* Requester identifier
+                                                * structure is valid
+                                                */
+                       rp              : 1,    /* Responder identifier
+                                                * structure is valid
+                                                */
+                       pi              : 1;    /* Precise instruction pointer
+                                                * structure is valid
+                                                */
+} pal_tlb_check_info_t;
+
+typedef struct pal_bus_check_info_s {
+       u64             size            : 5,    /* Xaction size */
+                       ib              : 1,    /* Internal bus error */
+                       eb              : 1,    /* External bus error */
+                       cc              : 1,    /* Error occurred
+                                                * during cache-cache
+                                                * transfer.
+                                                */
+                       type            : 8,    /* Bus xaction type*/
+                       sev             : 5,    /* Bus error severity*/
+                       hier            : 2,    /* Bus hierarchy level */
+                       reserved1       : 1,
+                       bsi             : 8,    /* Bus error status
+                                                * info
+                                                */
+                       reserved2       : 22,
+
+                       is              : 1,    /* instruction set (1 == ia32) 
*/
+                       iv              : 1,    /* instruction set field valid 
*/
+                       pl              : 2,    /* privilege level */
+                       pv              : 1,    /* privilege level field valid 
*/
+                       mcc             : 1,    /* Machine check corrected */
+                       tv              : 1,    /* Target address
+                                                * structure is valid
+                                                */
+                       rq              : 1,    /* Requester identifier
+                                                * structure is valid
+                                                */
+                       rp              : 1,    /* Responder identifier
+                                                * structure is valid
+                                                */
+                       pi              : 1;    /* Precise instruction pointer
+                                                * structure is valid
+                                                */
+} pal_bus_check_info_t;
+
+typedef struct pal_reg_file_check_info_s {
+       u64             id              : 4,    /* Register file identifier */
+                       op              : 4,    /* Type of register
+                                                * operation that
+                                                * caused the machine
+                                                * check.
+                                                */
+                       reg_num         : 7,    /* Register number */
+                       rnv             : 1,    /* reg_num valid */
+                       reserved2       : 38,
+
+                       is              : 1,    /* instruction set (1 == ia32) 
*/
+                       iv              : 1,    /* instruction set field valid 
*/
+                       pl              : 2,    /* privilege level */
+                       pv              : 1,    /* privilege level field valid 
*/
+                       mcc             : 1,    /* Machine check corrected */
+                       reserved3       : 3,
+                       pi              : 1;    /* Precise instruction pointer
+                                                * structure is valid
+                                                */
+} pal_reg_file_check_info_t;
+
+typedef struct pal_uarch_check_info_s {
+       u64             sid             : 5,    /* Structure identification */
+                       level           : 3,    /* Level of failure */
+                       array_id        : 4,    /* Array identification */
+                       op              : 4,    /* Type of
+                                                * operation that
+                                                * caused the machine
+                                                * check.
+                                                */
+                       way             : 6,    /* Way of structure */
+                       wv              : 1,    /* way valid */
+                       xv              : 1,    /* index valid */
+                       reserved1       : 8,
+                       index           : 8,    /* Index or set of the uarch
+                                                * structure that failed.
+                                                */
+                       reserved2       : 24,
+
+                       is              : 1,    /* instruction set (1 == ia32) 
*/
+                       iv              : 1,    /* instruction set field valid 
*/
+                       pl              : 2,    /* privilege level */
+                       pv              : 1,    /* privilege level field valid 
*/
+                       mcc             : 1,    /* Machine check corrected */
+                       tv              : 1,    /* Target address
+                                                * structure is valid
+                                                */
+                       rq              : 1,    /* Requester identifier
+                                                * structure is valid
+                                                */
+                       rp              : 1,    /* Responder identifier
+                                                * structure is valid
+                                                */
+                       pi              : 1;    /* Precise instruction pointer
+                                                * structure is valid
+                                                */
+} pal_uarch_check_info_t;
+
+typedef union pal_mc_error_info_u {
+       u64                             pmei_data;
+       pal_processor_state_info_t      pme_processor;
+       pal_cache_check_info_t          pme_cache;
+       pal_tlb_check_info_t            pme_tlb;
+       pal_bus_check_info_t            pme_bus;
+       pal_reg_file_check_info_t       pme_reg_file;
+       pal_uarch_check_info_t          pme_uarch;
+} pal_mc_error_info_t;
+
+#define pmci_proc_unknown_check                        pme_processor.uc
+#define pmci_proc_bus_check                    pme_processor.bc
+#define pmci_proc_tlb_check                    pme_processor.tc
+#define pmci_proc_cache_check                  pme_processor.cc
+#define pmci_proc_dynamic_state_size           pme_processor.dsize
+#define pmci_proc_gpr_valid                    pme_processor.gr
+#define pmci_proc_preserved_bank0_gpr_valid    pme_processor.b0
+#define pmci_proc_preserved_bank1_gpr_valid    pme_processor.b1
+#define pmci_proc_fp_valid                     pme_processor.fp
+#define pmci_proc_predicate_regs_valid         pme_processor.pr
+#define pmci_proc_branch_regs_valid            pme_processor.br
+#define pmci_proc_app_regs_valid               pme_processor.ar
+#define pmci_proc_region_regs_valid            pme_processor.rr
+#define pmci_proc_translation_regs_valid       pme_processor.tr
+#define pmci_proc_debug_regs_valid             pme_processor.dr
+#define pmci_proc_perf_counters_valid          pme_processor.pc
+#define pmci_proc_control_regs_valid           pme_processor.cr
+#define pmci_proc_machine_check_expected       pme_processor.ex
+#define pmci_proc_machine_check_corrected      pme_processor.cm
+#define pmci_proc_rse_valid                    pme_processor.rs
+#define pmci_proc_machine_check_or_init                pme_processor.in
+#define pmci_proc_dynamic_state_valid          pme_processor.dy
+#define pmci_proc_operation                    pme_processor.op
+#define pmci_proc_trap_lost                    pme_processor.tl
+#define pmci_proc_hardware_damage              pme_processor.hd
+#define pmci_proc_uncontained_storage_damage   pme_processor.us
+#define pmci_proc_machine_check_isolated       pme_processor.ci
+#define pmci_proc_continuable                  pme_processor.co
+#define pmci_proc_storage_intergrity_synced    pme_processor.sy
+#define pmci_proc_min_state_save_area_regd     pme_processor.mn
+#define        pmci_proc_distinct_multiple_errors      pme_processor.me
+#define pmci_proc_pal_attempted_rendezvous     pme_processor.ra
+#define pmci_proc_pal_rendezvous_complete      pme_processor.rz
+
+
+#define pmci_cache_level                       pme_cache.level
+#define pmci_cache_line_state                  pme_cache.mesi
+#define pmci_cache_line_state_valid            pme_cache.mv
+#define pmci_cache_line_index                  pme_cache.index
+#define pmci_cache_instr_cache_fail            pme_cache.ic
+#define pmci_cache_data_cache_fail             pme_cache.dc
+#define pmci_cache_line_tag_fail               pme_cache.tl
+#define pmci_cache_line_data_fail              pme_cache.dl
+#define pmci_cache_operation                   pme_cache.op
+#define pmci_cache_way_valid                   pme_cache.wv
+#define pmci_cache_target_address_valid                pme_cache.tv
+#define pmci_cache_way                         pme_cache.way
+#define pmci_cache_mc                          pme_cache.mc
+
+#define pmci_tlb_instr_translation_cache_fail  pme_tlb.itc
+#define pmci_tlb_data_translation_cache_fail   pme_tlb.dtc
+#define pmci_tlb_instr_translation_reg_fail    pme_tlb.itr
+#define pmci_tlb_data_translation_reg_fail     pme_tlb.dtr
+#define pmci_tlb_translation_reg_slot          pme_tlb.tr_slot
+#define pmci_tlb_mc                            pme_tlb.mc
+
+#define pmci_bus_status_info                   pme_bus.bsi
+#define pmci_bus_req_address_valid             pme_bus.rq
+#define pmci_bus_resp_address_valid            pme_bus.rp
+#define pmci_bus_target_address_valid          pme_bus.tv
+#define pmci_bus_error_severity                        pme_bus.sev
+#define pmci_bus_transaction_type              pme_bus.type
+#define pmci_bus_cache_cache_transfer          pme_bus.cc
+#define pmci_bus_transaction_size              pme_bus.size
+#define pmci_bus_internal_error                        pme_bus.ib
+#define pmci_bus_external_error                        pme_bus.eb
+#define pmci_bus_mc                            pme_bus.mc
+
+/*
+ * NOTE: this min_state_save area struct only includes the 1KB
+ * architectural state save area.  The other 3 KB is scratch space
+ * for PAL.
+ */
+
+typedef struct pal_min_state_area_s {
+       u64     pmsa_nat_bits;          /* nat bits for saved GRs  */
+       u64     pmsa_gr[15];            /* GR1  - GR15             */
+       u64     pmsa_bank0_gr[16];      /* GR16 - GR31             */
+       u64     pmsa_bank1_gr[16];      /* GR16 - GR31             */
+       u64     pmsa_pr;                /* predicate registers     */
+       u64     pmsa_br0;               /* branch register 0       */
+       u64     pmsa_rsc;               /* ar.rsc                  */
+       u64     pmsa_iip;               /* cr.iip                  */
+       u64     pmsa_ipsr;              /* cr.ipsr                 */
+       u64     pmsa_ifs;               /* cr.ifs                  */
+       u64     pmsa_xip;               /* previous iip            */
+       u64     pmsa_xpsr;              /* previous psr            */
+       u64     pmsa_xfs;               /* previous ifs            */
+       u64     pmsa_br1;               /* branch register 1       */
+       u64     pmsa_reserved[70];      /* pal_min_state_area should total to 
1KB */
+} pal_min_state_area_t;
+
+
+struct ia64_pal_retval {
+       /*
+        * A zero status value indicates call completed without error.
+        * A negative status value indicates reason of call failure.
+        * A positive status value indicates success but an
+        * informational value should be printed (e.g., "reboot for
+        * change to take effect").
+        */
+       s64 status;
+       u64 v0;
+       u64 v1;
+       u64 v2;
+};
+
+/*
+ * Note: Currently unused PAL arguments are generally labeled
+ * "reserved" so the value specified in the PAL documentation
+ * (generally 0) MUST be passed.  Reserved parameters are not optional
+ * parameters.
+ */
+extern struct ia64_pal_retval ia64_pal_call_static (u64, u64, u64, u64, u64);
+extern struct ia64_pal_retval ia64_pal_call_stacked (u64, u64, u64, u64);
+extern struct ia64_pal_retval ia64_pal_call_phys_static (u64, u64, u64, u64);
+extern struct ia64_pal_retval ia64_pal_call_phys_stacked (u64, u64, u64, u64);
+extern void ia64_save_scratch_fpregs (struct ia64_fpreg *);
+extern void ia64_load_scratch_fpregs (struct ia64_fpreg *);
+
+#define PAL_CALL(iprv,a0,a1,a2,a3) do {                        \
+       struct ia64_fpreg fr[6];                        \
+       ia64_save_scratch_fpregs(fr);                   \
+       iprv = ia64_pal_call_static(a0, a1, a2, a3, 0); \
+       ia64_load_scratch_fpregs(fr);                   \
+} while (0)
+
+#define PAL_CALL_IC_OFF(iprv,a0,a1,a2,a3) do {         \
+       struct ia64_fpreg fr[6];                        \
+       ia64_save_scratch_fpregs(fr);                   \
+       iprv = ia64_pal_call_static(a0, a1, a2, a3, 1); \
+       ia64_load_scratch_fpregs(fr);                   \
+} while (0)
+
+#define PAL_CALL_STK(iprv,a0,a1,a2,a3) do {            \
+       struct ia64_fpreg fr[6];                        \
+       ia64_save_scratch_fpregs(fr);                   \
+       iprv = ia64_pal_call_stacked(a0, a1, a2, a3);   \
+       ia64_load_scratch_fpregs(fr);                   \
+} while (0)
+
+#define PAL_CALL_PHYS(iprv,a0,a1,a2,a3) do {                   \
+       struct ia64_fpreg fr[6];                                \
+       ia64_save_scratch_fpregs(fr);                           \
+       iprv = ia64_pal_call_phys_static(a0, a1, a2, a3);       \
+       ia64_load_scratch_fpregs(fr);                           \
+} while (0)
+
+#define PAL_CALL_PHYS_STK(iprv,a0,a1,a2,a3) do {               \
+       struct ia64_fpreg fr[6];                                \
+       ia64_save_scratch_fpregs(fr);                           \
+       iprv = ia64_pal_call_phys_stacked(a0, a1, a2, a3);      \
+       ia64_load_scratch_fpregs(fr);                           \
+} while (0)
+
+typedef int (*ia64_pal_handler) (u64, ...);
+extern ia64_pal_handler ia64_pal;
+extern void ia64_pal_handler_init (void *);
+
+extern ia64_pal_handler ia64_pal;
+
+extern pal_cache_config_info_t         l0d_cache_config_info;
+extern pal_cache_config_info_t         l0i_cache_config_info;
+extern pal_cache_config_info_t         l1_cache_config_info;
+extern pal_cache_config_info_t         l2_cache_config_info;
+
+extern pal_cache_protection_info_t     l0d_cache_protection_info;
+extern pal_cache_protection_info_t     l0i_cache_protection_info;
+extern pal_cache_protection_info_t     l1_cache_protection_info;
+extern pal_cache_protection_info_t     l2_cache_protection_info;
+
+extern pal_cache_config_info_t         
pal_cache_config_info_get(pal_cache_level_t,
+                                                                 
pal_cache_type_t);
+
+extern pal_cache_protection_info_t     
pal_cache_protection_info_get(pal_cache_level_t,
+                                                                     
pal_cache_type_t);
+
+
+extern void                            pal_error(int);
+
+
+/* Useful wrappers for the current list of pal procedures */
+
+typedef union pal_bus_features_u {
+       u64     pal_bus_features_val;
+       struct {
+               u64     pbf_reserved1                           :       29;
+               u64     pbf_req_bus_parking                     :       1;
+               u64     pbf_bus_lock_mask                       :       1;
+               u64     pbf_enable_half_xfer_rate               :       1;
+               u64     pbf_reserved2                           :       22;
+               u64     pbf_disable_xaction_queueing            :       1;
+               u64     pbf_disable_resp_err_check              :       1;
+               u64     pbf_disable_berr_check                  :       1;
+               u64     pbf_disable_bus_req_internal_err_signal :       1;
+               u64     pbf_disable_bus_req_berr_signal         :       1;
+               u64     pbf_disable_bus_init_event_check        :       1;
+               u64     pbf_disable_bus_init_event_signal       :       1;
+               u64     pbf_disable_bus_addr_err_check          :       1;
+               u64     pbf_disable_bus_addr_err_signal         :       1;
+               u64     pbf_disable_bus_data_err_check          :       1;
+       } pal_bus_features_s;
+} pal_bus_features_u_t;
+
+extern void pal_bus_features_print (u64);
+
+/* Provide information about configurable processor bus features */
+static inline s64
+ia64_pal_bus_get_features (pal_bus_features_u_t *features_avail,
+                          pal_bus_features_u_t *features_status,
+                          pal_bus_features_u_t *features_control)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS(iprv, PAL_BUS_GET_FEATURES, 0, 0, 0);
+       if (features_avail)
+               features_avail->pal_bus_features_val = iprv.v0;
+       if (features_status)
+               features_status->pal_bus_features_val = iprv.v1;
+       if (features_control)
+               features_control->pal_bus_features_val = iprv.v2;
+       return iprv.status;
+}
+
+/* Enables/disables specific processor bus features */
+static inline s64
+ia64_pal_bus_set_features (pal_bus_features_u_t feature_select)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS(iprv, PAL_BUS_SET_FEATURES, 
feature_select.pal_bus_features_val, 0, 0);
+       return iprv.status;
+}
+
+/* Get detailed cache information */
+static inline s64
+ia64_pal_cache_config_info (u64 cache_level, u64 cache_type, 
pal_cache_config_info_t *conf)
+{
+       struct ia64_pal_retval iprv;
+
+       PAL_CALL(iprv, PAL_CACHE_INFO, cache_level, cache_type, 0);
+
+       if (iprv.status == 0) {
+               conf->pcci_status                 = iprv.status;
+               conf->pcci_info_1.pcci1_data      = iprv.v0;
+               conf->pcci_info_2.pcci2_data      = iprv.v1;
+               conf->pcci_reserved               = iprv.v2;
+       }
+       return iprv.status;
+
+}
+
+/* Get detailed cche protection information */
+static inline s64
+ia64_pal_cache_prot_info (u64 cache_level, u64 cache_type, 
pal_cache_protection_info_t *prot)
+{
+       struct ia64_pal_retval iprv;
+
+       PAL_CALL(iprv, PAL_CACHE_PROT_INFO, cache_level, cache_type, 0);
+
+       if (iprv.status == 0) {
+               prot->pcpi_status           = iprv.status;
+               prot->pcp_info[0].pcpi_data = iprv.v0 & 0xffffffff;
+               prot->pcp_info[1].pcpi_data = iprv.v0 >> 32;
+               prot->pcp_info[2].pcpi_data = iprv.v1 & 0xffffffff;
+               prot->pcp_info[3].pcpi_data = iprv.v1 >> 32;
+               prot->pcp_info[4].pcpi_data = iprv.v2 & 0xffffffff;
+               prot->pcp_info[5].pcpi_data = iprv.v2 >> 32;
+       }
+       return iprv.status;
+}
+
+/*
+ * Flush the processor instruction or data caches.  *PROGRESS must be
+ * initialized to zero before calling this for the first time..
+ */
+static inline s64
+ia64_pal_cache_flush (u64 cache_type, u64 invalidate, u64 *progress, u64 
*vector)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_IC_OFF(iprv, PAL_CACHE_FLUSH, cache_type, invalidate, 
*progress);
+       if (vector)
+               *vector = iprv.v0;
+       *progress = iprv.v1;
+       return iprv.status;
+}
+
+
+/* Initialize the processor controlled caches */
+static inline s64
+ia64_pal_cache_init (u64 level, u64 cache_type, u64 rest)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_CACHE_INIT, level, cache_type, rest);
+       return iprv.status;
+}
+
+/* Initialize the tags and data of a data or unified cache line of
+ * processor controlled cache to known values without the availability
+ * of backing memory.
+ */
+static inline s64
+ia64_pal_cache_line_init (u64 physical_addr, u64 data_value)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_CACHE_LINE_INIT, physical_addr, data_value, 0);
+       return iprv.status;
+}
+
+
+/* Read the data and tag of a processor controlled cache line for diags */
+static inline s64
+ia64_pal_cache_read (pal_cache_line_id_u_t line_id, u64 physical_addr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_CACHE_READ, line_id.pclid_data, physical_addr, 0);
+       return iprv.status;
+}
+
+/* Return summary information about the heirarchy of caches controlled by the 
processor */
+static inline s64
+ia64_pal_cache_summary (u64 *cache_levels, u64 *unique_caches)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_CACHE_SUMMARY, 0, 0, 0);
+       if (cache_levels)
+               *cache_levels = iprv.v0;
+       if (unique_caches)
+               *unique_caches = iprv.v1;
+       return iprv.status;
+}
+
+/* Write the data and tag of a processor-controlled cache line for diags */
+static inline s64
+ia64_pal_cache_write (pal_cache_line_id_u_t line_id, u64 physical_addr, u64 
data)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_CACHE_WRITE, line_id.pclid_data, physical_addr, 
data);
+       return iprv.status;
+}
+
+
+/* Return the parameters needed to copy relocatable PAL procedures from ROM to 
memory */
+static inline s64
+ia64_pal_copy_info (u64 copy_type, u64 num_procs, u64 num_iopics,
+                   u64 *buffer_size, u64 *buffer_align)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_COPY_INFO, copy_type, num_procs, num_iopics);
+       if (buffer_size)
+               *buffer_size = iprv.v0;
+       if (buffer_align)
+               *buffer_align = iprv.v1;
+       return iprv.status;
+}
+
+/* Copy relocatable PAL procedures from ROM to memory */
+static inline s64
+ia64_pal_copy_pal (u64 target_addr, u64 alloc_size, u64 processor, u64 
*pal_proc_offset)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_COPY_PAL, target_addr, alloc_size, processor);
+       if (pal_proc_offset)
+               *pal_proc_offset = iprv.v0;
+       return iprv.status;
+}
+
+/* Return the number of instruction and data debug register pairs */
+static inline s64
+ia64_pal_debug_info (u64 *inst_regs,  u64 *data_regs)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_DEBUG_INFO, 0, 0, 0);
+       if (inst_regs)
+               *inst_regs = iprv.v0;
+       if (data_regs)
+               *data_regs = iprv.v1;
+
+       return iprv.status;
+}
+
+#ifdef TBD
+/* Switch from IA64-system environment to IA-32 system environment */
+static inline s64
+ia64_pal_enter_ia32_env (ia32_env1, ia32_env2, ia32_env3)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_ENTER_IA_32_ENV, ia32_env1, ia32_env2, ia32_env3);
+       return iprv.status;
+}
+#endif
+
+/* Get unique geographical address of this processor on its bus */
+static inline s64
+ia64_pal_fixed_addr (u64 *global_unique_addr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_FIXED_ADDR, 0, 0, 0);
+       if (global_unique_addr)
+               *global_unique_addr = iprv.v0;
+       return iprv.status;
+}
+
+/* Get base frequency of the platform if generated by the processor */
+static inline s64
+ia64_pal_freq_base (u64 *platform_base_freq)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_FREQ_BASE, 0, 0, 0);
+       if (platform_base_freq)
+               *platform_base_freq = iprv.v0;
+       return iprv.status;
+}
+
+/*
+ * Get the ratios for processor frequency, bus frequency and interval timer to
+ * to base frequency of the platform
+ */
+static inline s64
+ia64_pal_freq_ratios (struct pal_freq_ratio *proc_ratio, struct pal_freq_ratio 
*bus_ratio,
+                     struct pal_freq_ratio *itc_ratio)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_FREQ_RATIOS, 0, 0, 0);
+       if (proc_ratio)
+               *(u64 *)proc_ratio = iprv.v0;
+       if (bus_ratio)
+               *(u64 *)bus_ratio = iprv.v1;
+       if (itc_ratio)
+               *(u64 *)itc_ratio = iprv.v2;
+       return iprv.status;
+}
+
+/* Make the processor enter HALT or one of the implementation dependent low
+ * power states where prefetching and execution are suspended and cache and
+ * TLB coherency is not maintained.
+ */
+static inline s64
+ia64_pal_halt (u64 halt_state)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_HALT, halt_state, 0, 0);
+       return iprv.status;
+}
+
+typedef union pal_power_mgmt_info_u {
+       u64                     ppmi_data;
+       struct {
+              u64              exit_latency            : 16,
+                               entry_latency           : 16,
+                               power_consumption       : 28,
+                               im                      : 1,
+                               co                      : 1,
+                               reserved                : 2;
+       } pal_power_mgmt_info_s;
+} pal_power_mgmt_info_u_t;
+
+/* Return information about processor's optional power management 
capabilities. */
+static inline s64
+ia64_pal_halt_info (pal_power_mgmt_info_u_t *power_buf)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_STK(iprv, PAL_HALT_INFO, (unsigned long) power_buf, 0, 0);
+       return iprv.status;
+}
+
+/* Cause the processor to enter LIGHT HALT state, where prefetching and 
execution are
+ * suspended, but cache and TLB coherency is maintained.
+ */
+static inline s64
+ia64_pal_halt_light (void)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_HALT_LIGHT, 0, 0, 0);
+       return iprv.status;
+}
+
+/* Clear all the processor error logging   registers and reset the indicator 
that allows
+ * the error logging registers to be written. This procedure also checks the 
pending
+ * machine check bit and pending INIT bit and reports their states.
+ */
+static inline s64
+ia64_pal_mc_clear_log (u64 *pending_vector)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_CLEAR_LOG, 0, 0, 0);
+       if (pending_vector)
+               *pending_vector = iprv.v0;
+       return iprv.status;
+}
+
+/* Ensure that all outstanding transactions in a processor are completed or 
that any
+ * MCA due to thes outstanding transaction is taken.
+ */
+static inline s64
+ia64_pal_mc_drain (void)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_DRAIN, 0, 0, 0);
+       return iprv.status;
+}
+
+/* Return the machine check dynamic processor state */
+static inline s64
+ia64_pal_mc_dynamic_state (u64 offset, u64 *size, u64 *pds)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_DYNAMIC_STATE, offset, 0, 0);
+       if (size)
+               *size = iprv.v0;
+       if (pds)
+               *pds = iprv.v1;
+       return iprv.status;
+}
+
+/* Return processor machine check information */
+static inline s64
+ia64_pal_mc_error_info (u64 info_index, u64 type_index, u64 *size, u64 
*error_info)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_ERROR_INFO, info_index, type_index, 0);
+       if (size)
+               *size = iprv.v0;
+       if (error_info)
+               *error_info = iprv.v1;
+       return iprv.status;
+}
+
+/* Inform PALE_CHECK whether a machine check is expected so that PALE_CHECK 
willnot
+ * attempt to correct any expected machine checks.
+ */
+static inline s64
+ia64_pal_mc_expected (u64 expected, u64 *previous)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_EXPECTED, expected, 0, 0);
+       if (previous)
+               *previous = iprv.v0;
+       return iprv.status;
+}
+
+/* Register a platform dependent location with PAL to which it can save
+ * minimal processor state in the event of a machine check or initialization
+ * event.
+ */
+static inline s64
+ia64_pal_mc_register_mem (u64 physical_addr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_REGISTER_MEM, physical_addr, 0, 0);
+       return iprv.status;
+}
+
+/* Restore minimal architectural processor state, set CMC interrupt if 
necessary
+ * and resume execution
+ */
+static inline s64
+ia64_pal_mc_resume (u64 set_cmci, u64 save_ptr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MC_RESUME, set_cmci, save_ptr, 0);
+       return iprv.status;
+}
+
+/* Return the memory attributes implemented by the processor */
+static inline s64
+ia64_pal_mem_attrib (u64 *mem_attrib)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MEM_ATTRIB, 0, 0, 0);
+       if (mem_attrib)
+               *mem_attrib = iprv.v0 & 0xff;
+       return iprv.status;
+}
+
+/* Return the amount of memory needed for second phase of processor
+ * self-test and the required alignment of memory.
+ */
+static inline s64
+ia64_pal_mem_for_test (u64 *bytes_needed, u64 *alignment)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_MEM_FOR_TEST, 0, 0, 0);
+       if (bytes_needed)
+               *bytes_needed = iprv.v0;
+       if (alignment)
+               *alignment = iprv.v1;
+       return iprv.status;
+}
+
+typedef union pal_perf_mon_info_u {
+       u64                       ppmi_data;
+       struct {
+              u64              generic         : 8,
+                               width           : 8,
+                               cycles          : 8,
+                               retired         : 8,
+                               reserved        : 32;
+       } pal_perf_mon_info_s;
+} pal_perf_mon_info_u_t;
+
+/* Return the performance monitor information about what can be counted
+ * and how to configure the monitors to count the desired events.
+ */
+static inline s64
+ia64_pal_perf_mon_info (u64 *pm_buffer, pal_perf_mon_info_u_t *pm_info)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_PERF_MON_INFO, (unsigned long) pm_buffer, 0, 0);
+       if (pm_info)
+               pm_info->ppmi_data = iprv.v0;
+       return iprv.status;
+}
+
+/* Specifies the physical address of the processor interrupt block
+ * and I/O port space.
+ */
+static inline s64
+ia64_pal_platform_addr (u64 type, u64 physical_addr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_PLATFORM_ADDR, type, physical_addr, 0);
+       return iprv.status;
+}
+
+/* Set the SAL PMI entrypoint in memory */
+static inline s64
+ia64_pal_pmi_entrypoint (u64 sal_pmi_entry_addr)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_PMI_ENTRYPOINT, sal_pmi_entry_addr, 0, 0);
+       return iprv.status;
+}
+
+struct pal_features_s;
+/* Provide information about configurable processor features */
+static inline s64
+ia64_pal_proc_get_features (u64 *features_avail,
+                           u64 *features_status,
+                           u64 *features_control)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS(iprv, PAL_PROC_GET_FEATURES, 0, 0, 0);
+       if (iprv.status == 0) {
+               *features_avail   = iprv.v0;
+               *features_status  = iprv.v1;
+               *features_control = iprv.v2;
+       }
+       return iprv.status;
+}
+
+/* Enable/disable processor dependent features */
+static inline s64
+ia64_pal_proc_set_features (u64 feature_select)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS(iprv, PAL_PROC_SET_FEATURES, feature_select, 0, 0);
+       return iprv.status;
+}
+
+/*
+ * Put everything in a struct so we avoid the global offset table whenever
+ * possible.
+ */
+typedef struct ia64_ptce_info_s {
+       u64             base;
+       u32             count[2];
+       u32             stride[2];
+} ia64_ptce_info_t;
+
+/* Return the information required for the architected loop used to purge
+ * (initialize) the entire TC
+ */
+static inline s64
+ia64_get_ptce (ia64_ptce_info_t *ptce)
+{
+       struct ia64_pal_retval iprv;
+
+       if (!ptce)
+               return -1;
+
+       PAL_CALL(iprv, PAL_PTCE_INFO, 0, 0, 0);
+       if (iprv.status == 0) {
+               ptce->base = iprv.v0;
+               ptce->count[0] = iprv.v1 >> 32;
+               ptce->count[1] = iprv.v1 & 0xffffffff;
+               ptce->stride[0] = iprv.v2 >> 32;
+               ptce->stride[1] = iprv.v2 & 0xffffffff;
+       }
+       return iprv.status;
+}
+
+/* Return info about implemented application and control registers. */
+static inline s64
+ia64_pal_register_info (u64 info_request, u64 *reg_info_1, u64 *reg_info_2)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_REGISTER_INFO, info_request, 0, 0);
+       if (reg_info_1)
+               *reg_info_1 = iprv.v0;
+       if (reg_info_2)
+               *reg_info_2 = iprv.v1;
+       return iprv.status;
+}
+
+typedef union pal_hints_u {
+       u64                     ph_data;
+       struct {
+              u64              si              : 1,
+                               li              : 1,
+                               reserved        : 62;
+       } pal_hints_s;
+} pal_hints_u_t;
+
+/* Return information about the register stack and RSE for this processor
+ * implementation.
+ */
+static inline s64
+ia64_pal_rse_info (u64 *num_phys_stacked, pal_hints_u_t *hints)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_RSE_INFO, 0, 0, 0);
+       if (num_phys_stacked)
+               *num_phys_stacked = iprv.v0;
+       if (hints)
+               hints->ph_data = iprv.v1;
+       return iprv.status;
+}
+
+/* Cause the processor to enter        SHUTDOWN state, where prefetching and 
execution are
+ * suspended, but cause cache and TLB coherency to be maintained.
+ * This is usually called in IA-32 mode.
+ */
+static inline s64
+ia64_pal_shutdown (void)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_SHUTDOWN, 0, 0, 0);
+       return iprv.status;
+}
+
+/* Perform the second phase of processor self-test. */
+static inline s64
+ia64_pal_test_proc (u64 test_addr, u64 test_size, u64 attributes, u64 
*self_test_state)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_TEST_PROC, test_addr, test_size, attributes);
+       if (self_test_state)
+               *self_test_state = iprv.v0;
+       return iprv.status;
+}
+
+typedef union  pal_version_u {
+       u64     pal_version_val;
+       struct {
+               u64     pv_pal_b_rev            :       8;
+               u64     pv_pal_b_model          :       8;
+               u64     pv_reserved1            :       8;
+               u64     pv_pal_vendor           :       8;
+               u64     pv_pal_a_rev            :       8;
+               u64     pv_pal_a_model          :       8;
+               u64     pv_reserved2            :       16;
+       } pal_version_s;
+} pal_version_u_t;
+
+
+/* Return PAL version information */
+static inline s64
+ia64_pal_version (pal_version_u_t *pal_min_version, pal_version_u_t 
*pal_cur_version)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS(iprv, PAL_VERSION, 0, 0, 0);
+       if (pal_min_version)
+               pal_min_version->pal_version_val = iprv.v0;
+
+       if (pal_cur_version)
+               pal_cur_version->pal_version_val = iprv.v1;
+
+       return iprv.status;
+}
+
+typedef union pal_tc_info_u {
+       u64                     pti_val;
+       struct {
+              u64              num_sets        :       8,
+                               associativity   :       8,
+                               num_entries     :       16,
+                               pf              :       1,
+                               unified         :       1,
+                               reduce_tr       :       1,
+                               reserved        :       29;
+       } pal_tc_info_s;
+} pal_tc_info_u_t;
+
+#define tc_reduce_tr           pal_tc_info_s.reduce_tr
+#define tc_unified             pal_tc_info_s.unified
+#define tc_pf                  pal_tc_info_s.pf
+#define tc_num_entries         pal_tc_info_s.num_entries
+#define tc_associativity       pal_tc_info_s.associativity
+#define tc_num_sets            pal_tc_info_s.num_sets
+
+
+/* Return information about the virtual memory characteristics of the processor
+ * implementation.
+ */
+static inline s64
+ia64_pal_vm_info (u64 tc_level, u64 tc_type,  pal_tc_info_u_t *tc_info, u64 
*tc_pages)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_VM_INFO, tc_level, tc_type, 0);
+       if (tc_info)
+               tc_info->pti_val = iprv.v0;
+       if (tc_pages)
+               *tc_pages = iprv.v1;
+       return iprv.status;
+}
+
+/* Get page size information about the virtual memory characteristics of the 
processor
+ * implementation.
+ */
+static inline s64
+ia64_pal_vm_page_size (u64 *tr_pages, u64 *vw_pages)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_VM_PAGE_SIZE, 0, 0, 0);
+       if (tr_pages)
+               *tr_pages = iprv.v0;
+       if (vw_pages)
+               *vw_pages = iprv.v1;
+       return iprv.status;
+}
+
+typedef union pal_vm_info_1_u {
+       u64                     pvi1_val;
+       struct {
+               u64             vw              : 1,
+                               phys_add_size   : 7,
+                               key_size        : 8,
+                               max_pkr         : 8,
+                               hash_tag_id     : 8,
+                               max_dtr_entry   : 8,
+                               max_itr_entry   : 8,
+                               max_unique_tcs  : 8,
+                               num_tc_levels   : 8;
+       } pal_vm_info_1_s;
+} pal_vm_info_1_u_t;
+
+typedef union pal_vm_info_2_u {
+       u64                     pvi2_val;
+       struct {
+               u64             impl_va_msb     : 8,
+                               rid_size        : 8,
+                               reserved        : 48;
+       } pal_vm_info_2_s;
+} pal_vm_info_2_u_t;
+
+/* Get summary information about the virtual memory characteristics of the 
processor
+ * implementation.
+ */
+static inline s64
+ia64_pal_vm_summary (pal_vm_info_1_u_t *vm_info_1, pal_vm_info_2_u_t 
*vm_info_2)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_VM_SUMMARY, 0, 0, 0);
+       if (vm_info_1)
+               vm_info_1->pvi1_val = iprv.v0;
+       if (vm_info_2)
+               vm_info_2->pvi2_val = iprv.v1;
+       return iprv.status;
+}
+
+typedef union pal_itr_valid_u {
+       u64                     piv_val;
+       struct {
+              u64              access_rights_valid     : 1,
+                               priv_level_valid        : 1,
+                               dirty_bit_valid         : 1,
+                               mem_attr_valid          : 1,
+                               reserved                : 60;
+       } pal_tr_valid_s;
+} pal_tr_valid_u_t;
+
+/* Read a translation register */
+static inline s64
+ia64_pal_tr_read (u64 reg_num, u64 tr_type, u64 *tr_buffer, pal_tr_valid_u_t 
*tr_valid)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL_PHYS_STK(iprv, PAL_VM_TR_READ, reg_num, 
tr_type,(u64)ia64_tpa(tr_buffer));
+       if (tr_valid)
+               tr_valid->piv_val = iprv.v0;
+       return iprv.status;
+}
+
+/*
+ * PAL_PREFETCH_VISIBILITY transaction types
+ */
+#define PAL_VISIBILITY_VIRTUAL         0
+#define PAL_VISIBILITY_PHYSICAL                1
+
+/*
+ * PAL_PREFETCH_VISIBILITY return codes
+ */
+#define PAL_VISIBILITY_OK              1
+#define PAL_VISIBILITY_OK_REMOTE_NEEDED        0
+#define PAL_VISIBILITY_INVAL_ARG       -2
+#define PAL_VISIBILITY_ERROR           -3
+
+static inline s64
+ia64_pal_prefetch_visibility (s64 trans_type)
+{
+       struct ia64_pal_retval iprv;
+       PAL_CALL(iprv, PAL_PREFETCH_VISIBILITY, trans_type, 0, 0);
+       return iprv.status;
+}
+
+#ifdef CONFIG_VTI
+#include <asm/vmx_pal.h>
+#endif // CONFIG_VTI
+#endif /* __ASSEMBLY__ */
+
+#endif /* _ASM_IA64_PAL_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/pgalloc.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/pgalloc.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,196 @@
+#ifndef _ASM_IA64_PGALLOC_H
+#define _ASM_IA64_PGALLOC_H
+
+/*
+ * This file contains the functions and defines necessary to allocate
+ * page tables.
+ *
+ * This hopefully works with any (fixed) ia-64 page-size, as defined
+ * in <asm/page.h> (currently 8192).
+ *
+ * Copyright (C) 1998-2001 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 2000, Goutham Rao <goutham.rao@xxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <linux/compiler.h>
+#include <linux/mm.h>
+#include <linux/page-flags.h>
+#include <linux/threads.h>
+
+#include <asm/mmu_context.h>
+#include <asm/processor.h>
+
+/*
+ * Very stupidly, we used to get new pgd's and pmd's, init their contents
+ * to point to the NULL versions of the next level page table, later on
+ * completely re-init them the same way, then free them up.  This wasted
+ * a lot of work and caused unnecessary memory traffic.  How broken...
+ * We fix this by caching them.
+ */
+#define pgd_quicklist          (local_cpu_data->pgd_quick)
+#define pmd_quicklist          (local_cpu_data->pmd_quick)
+#define pgtable_cache_size     (local_cpu_data->pgtable_cache_sz)
+
+static inline pgd_t*
+pgd_alloc_one_fast (struct mm_struct *mm)
+{
+       unsigned long *ret = NULL;
+
+       preempt_disable();
+
+       ret = pgd_quicklist;
+       if (likely(ret != NULL)) {
+               pgd_quicklist = (unsigned long *)(*ret);
+               ret[0] = 0;
+               --pgtable_cache_size;
+       } else
+               ret = NULL;
+
+       preempt_enable();
+
+       return (pgd_t *) ret;
+}
+
+static inline pgd_t*
+pgd_alloc (struct mm_struct *mm)
+{
+       /* the VM system never calls pgd_alloc_one_fast(), so we do it here. */
+       pgd_t *pgd = pgd_alloc_one_fast(mm);
+
+       if (unlikely(pgd == NULL)) {
+#ifdef XEN
+               pgd = (pgd_t *)alloc_xenheap_page();
+               memset(pgd,0,PAGE_SIZE);
+#else
+               pgd = (pgd_t *)__get_free_page(GFP_KERNEL|__GFP_ZERO);
+#endif
+       }
+       return pgd;
+}
+
+static inline void
+pgd_free (pgd_t *pgd)
+{
+       preempt_disable();
+       *(unsigned long *)pgd = (unsigned long) pgd_quicklist;
+       pgd_quicklist = (unsigned long *) pgd;
+       ++pgtable_cache_size;
+       preempt_enable();
+}
+
+static inline void
+pud_populate (struct mm_struct *mm, pud_t *pud_entry, pmd_t *pmd)
+{
+       pud_val(*pud_entry) = __pa(pmd);
+}
+
+static inline pmd_t*
+pmd_alloc_one_fast (struct mm_struct *mm, unsigned long addr)
+{
+       unsigned long *ret = NULL;
+
+       preempt_disable();
+
+       ret = (unsigned long *)pmd_quicklist;
+       if (likely(ret != NULL)) {
+               pmd_quicklist = (unsigned long *)(*ret);
+               ret[0] = 0;
+               --pgtable_cache_size;
+       }
+
+       preempt_enable();
+
+       return (pmd_t *)ret;
+}
+
+static inline pmd_t*
+pmd_alloc_one (struct mm_struct *mm, unsigned long addr)
+{
+#ifdef XEN
+       pmd_t *pmd = (pmd_t *)alloc_xenheap_page();
+       memset(pmd,0,PAGE_SIZE);
+#else
+       pmd_t *pmd = (pmd_t 
*)__get_free_page(GFP_KERNEL|__GFP_REPEAT|__GFP_ZERO);
+#endif
+
+       return pmd;
+}
+
+static inline void
+pmd_free (pmd_t *pmd)
+{
+       preempt_disable();
+       *(unsigned long *)pmd = (unsigned long) pmd_quicklist;
+       pmd_quicklist = (unsigned long *) pmd;
+       ++pgtable_cache_size;
+       preempt_enable();
+}
+
+#define __pmd_free_tlb(tlb, pmd)       pmd_free(pmd)
+
+static inline void
+pmd_populate (struct mm_struct *mm, pmd_t *pmd_entry, struct page *pte)
+{
+       pmd_val(*pmd_entry) = page_to_phys(pte);
+}
+
+static inline void
+pmd_populate_kernel (struct mm_struct *mm, pmd_t *pmd_entry, pte_t *pte)
+{
+       pmd_val(*pmd_entry) = __pa(pte);
+}
+
+static inline struct page *
+pte_alloc_one (struct mm_struct *mm, unsigned long addr)
+{
+#ifdef XEN
+       struct page *pte = alloc_xenheap_page();
+       memset(pte,0,PAGE_SIZE);
+#else
+       struct page *pte = alloc_pages(GFP_KERNEL|__GFP_REPEAT|__GFP_ZERO, 0);
+#endif
+
+       return pte;
+}
+
+static inline pte_t *
+pte_alloc_one_kernel (struct mm_struct *mm, unsigned long addr)
+{
+#ifdef XEN
+       pte_t *pte = (pte_t *)alloc_xenheap_page();
+       memset(pte,0,PAGE_SIZE);
+#else
+       pte_t *pte = (pte_t 
*)__get_free_page(GFP_KERNEL|__GFP_REPEAT|__GFP_ZERO);
+#endif
+
+       return pte;
+}
+
+static inline void
+pte_free (struct page *pte)
+{
+#ifdef XEN
+       free_xenheap_page(pte);
+#else
+       __free_page(pte);
+#endif
+}
+
+static inline void
+pte_free_kernel (pte_t *pte)
+{
+#ifdef XEN
+       free_xenheap_page((unsigned long) pte);
+#else
+       free_page((unsigned long) pte);
+#endif
+}
+
+#define __pte_free_tlb(tlb, pte)       tlb_remove_page((tlb), (pte))
+
+extern void check_pgt_cache (void);
+
+#endif /* _ASM_IA64_PGALLOC_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/processor.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/processor.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,705 @@
+#ifndef _ASM_IA64_PROCESSOR_H
+#define _ASM_IA64_PROCESSOR_H
+
+/*
+ * Copyright (C) 1998-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 1999 Asit Mallick <asit.k.mallick@xxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ *
+ * 11/24/98    S.Eranian       added ia64_set_iva()
+ * 12/03/99    D. Mosberger    implement thread_saved_pc() via kernel unwind 
API
+ * 06/16/00    A. Mallick      added csd/ssd/tssd for ia32 support
+ */
+
+#include <linux/config.h>
+
+#include <asm/intrinsics.h>
+#include <asm/kregs.h>
+#include <asm/ptrace.h>
+#include <asm/ustack.h>
+
+/* Our arch specific arch_init_sched_domain is in arch/ia64/kernel/domain.c */
+#define ARCH_HAS_SCHED_DOMAIN
+
+#define IA64_NUM_DBG_REGS      8
+/*
+ * Limits for PMC and PMD are set to less than maximum architected values
+ * but should be sufficient for a while
+ */
+#define IA64_NUM_PMC_REGS      32
+#define IA64_NUM_PMD_REGS      32
+
+#define DEFAULT_MAP_BASE       __IA64_UL_CONST(0x2000000000000000)
+#define DEFAULT_TASK_SIZE      __IA64_UL_CONST(0xa000000000000000)
+
+/*
+ * TASK_SIZE really is a mis-named.  It really is the maximum user
+ * space address (plus one).  On IA-64, there are five regions of 2TB
+ * each (assuming 8KB page size), for a total of 8TB of user virtual
+ * address space.
+ */
+#define TASK_SIZE              (current->thread.task_size)
+
+/*
+ * MM_VM_SIZE(mm) gives the maximum address (plus 1) which may contain a 
mapping for
+ * address-space MM.  Note that with 32-bit tasks, this is still 
DEFAULT_TASK_SIZE,
+ * because the kernel may have installed helper-mappings above TASK_SIZE.  For 
example,
+ * for x86 emulation, the LDT and GDT are mapped above TASK_SIZE.
+ */
+#define MM_VM_SIZE(mm)         DEFAULT_TASK_SIZE
+
+/*
+ * This decides where the kernel will search for a free chunk of vm
+ * space during mmap's.
+ */
+#define TASK_UNMAPPED_BASE     (current->thread.map_base)
+
+#define IA64_THREAD_FPH_VALID  (__IA64_UL(1) << 0)     /* floating-point high 
state valid? */
+#define IA64_THREAD_DBG_VALID  (__IA64_UL(1) << 1)     /* debug registers 
valid? */
+#define IA64_THREAD_PM_VALID   (__IA64_UL(1) << 2)     /* performance 
registers valid? */
+#define IA64_THREAD_UAC_NOPRINT        (__IA64_UL(1) << 3)     /* don't log 
unaligned accesses */
+#define IA64_THREAD_UAC_SIGBUS (__IA64_UL(1) << 4)     /* generate SIGBUS on 
unaligned acc. */
+                                                       /* bit 5 is currently 
unused */
+#define IA64_THREAD_FPEMU_NOPRINT (__IA64_UL(1) << 6)  /* don't log any fpswa 
faults */
+#define IA64_THREAD_FPEMU_SIGFPE  (__IA64_UL(1) << 7)  /* send a SIGFPE for 
fpswa faults */
+
+#define IA64_THREAD_UAC_SHIFT  3
+#define IA64_THREAD_UAC_MASK   (IA64_THREAD_UAC_NOPRINT | 
IA64_THREAD_UAC_SIGBUS)
+#define IA64_THREAD_FPEMU_SHIFT        6
+#define IA64_THREAD_FPEMU_MASK (IA64_THREAD_FPEMU_NOPRINT | 
IA64_THREAD_FPEMU_SIGFPE)
+
+
+/*
+ * This shift should be large enough to be able to represent 
1000000000/itc_freq with good
+ * accuracy while being small enough to fit 
10*1000000000<<IA64_NSEC_PER_CYC_SHIFT in 64 bits
+ * (this will give enough slack to represent 10 seconds worth of time as a 
scaled number).
+ */
+#define IA64_NSEC_PER_CYC_SHIFT        30
+
+#ifndef __ASSEMBLY__
+
+#include <linux/cache.h>
+#include <linux/compiler.h>
+#include <linux/threads.h>
+#include <linux/types.h>
+
+#include <asm/fpu.h>
+#include <asm/page.h>
+#include <asm/percpu.h>
+#include <asm/rse.h>
+#include <asm/unwind.h>
+#include <asm/atomic.h>
+#ifdef CONFIG_NUMA
+#include <asm/nodedata.h>
+#endif
+#ifdef XEN
+#include <asm/xenprocessor.h>
+#endif
+
+#ifndef XEN
+/* like above but expressed as bitfields for more efficient access: */
+struct ia64_psr {
+       __u64 reserved0 : 1;
+       __u64 be : 1;
+       __u64 up : 1;
+       __u64 ac : 1;
+       __u64 mfl : 1;
+       __u64 mfh : 1;
+       __u64 reserved1 : 7;
+       __u64 ic : 1;
+       __u64 i : 1;
+       __u64 pk : 1;
+       __u64 reserved2 : 1;
+       __u64 dt : 1;
+       __u64 dfl : 1;
+       __u64 dfh : 1;
+       __u64 sp : 1;
+       __u64 pp : 1;
+       __u64 di : 1;
+       __u64 si : 1;
+       __u64 db : 1;
+       __u64 lp : 1;
+       __u64 tb : 1;
+       __u64 rt : 1;
+       __u64 reserved3 : 4;
+       __u64 cpl : 2;
+       __u64 is : 1;
+       __u64 mc : 1;
+       __u64 it : 1;
+       __u64 id : 1;
+       __u64 da : 1;
+       __u64 dd : 1;
+       __u64 ss : 1;
+       __u64 ri : 2;
+       __u64 ed : 1;
+       __u64 bn : 1;
+       __u64 reserved4 : 19;
+};
+#endif
+
+/*
+ * CPU type, hardware bug flags, and per-CPU state.  Frequently used
+ * state comes earlier:
+ */
+struct cpuinfo_ia64 {
+       __u32 softirq_pending;
+       __u64 itm_delta;        /* # of clock cycles between clock ticks */
+       __u64 itm_next;         /* interval timer mask value to use for next 
clock tick */
+       __u64 nsec_per_cyc;     /* 
(1000000000<<IA64_NSEC_PER_CYC_SHIFT)/itc_freq */
+       __u64 unimpl_va_mask;   /* mask of unimplemented virtual address bits 
(from PAL) */
+       __u64 unimpl_pa_mask;   /* mask of unimplemented physical address bits 
(from PAL) */
+       __u64 *pgd_quick;
+       __u64 *pmd_quick;
+       __u64 pgtable_cache_sz;
+       __u64 itc_freq;         /* frequency of ITC counter */
+       __u64 proc_freq;        /* frequency of processor */
+       __u64 cyc_per_usec;     /* itc_freq/1000000 */
+       __u64 ptce_base;
+       __u32 ptce_count[2];
+       __u32 ptce_stride[2];
+       struct task_struct *ksoftirqd;  /* kernel softirq daemon for this CPU */
+
+#ifdef CONFIG_SMP
+       __u64 loops_per_jiffy;
+       int cpu;
+#endif
+
+       /* CPUID-derived information: */
+       __u64 ppn;
+       __u64 features;
+       __u8 number;
+       __u8 revision;
+       __u8 model;
+       __u8 family;
+       __u8 archrev;
+       char vendor[16];
+
+#ifdef CONFIG_NUMA
+       struct ia64_node_data *node_data;
+#endif
+};
+
+DECLARE_PER_CPU(struct cpuinfo_ia64, cpu_info);
+
+/*
+ * The "local" data variable.  It refers to the per-CPU data of the currently 
executing
+ * CPU, much like "current" points to the per-task data of the currently 
executing task.
+ * Do not use the address of local_cpu_data, since it will be different from
+ * cpu_data(smp_processor_id())!
+ */
+#define local_cpu_data         (&__ia64_per_cpu_var(cpu_info))
+#define cpu_data(cpu)          (&per_cpu(cpu_info, cpu))
+
+extern void identify_cpu (struct cpuinfo_ia64 *);
+extern void print_cpu_info (struct cpuinfo_ia64 *);
+
+typedef struct {
+       unsigned long seg;
+} mm_segment_t;
+
+#define SET_UNALIGN_CTL(task,value)                                            
                \
+({                                                                             
                \
+       (task)->thread.flags = (((task)->thread.flags & ~IA64_THREAD_UAC_MASK)  
                \
+                               | (((value) << IA64_THREAD_UAC_SHIFT) & 
IA64_THREAD_UAC_MASK)); \
+       0;                                                                      
                \
+})
+#define GET_UNALIGN_CTL(task,addr)                                             
                \
+({                                                                             
                \
+       put_user(((task)->thread.flags & IA64_THREAD_UAC_MASK) >> 
IA64_THREAD_UAC_SHIFT,        \
+                (int __user *) (addr));                                        
                \
+})
+
+#define SET_FPEMU_CTL(task,value)                                              
                \
+({                                                                             
                \
+       (task)->thread.flags = (((task)->thread.flags & 
~IA64_THREAD_FPEMU_MASK)                \
+                         | (((value) << IA64_THREAD_FPEMU_SHIFT) & 
IA64_THREAD_FPEMU_MASK));   \
+       0;                                                                      
                \
+})
+#define GET_FPEMU_CTL(task,addr)                                               
                \
+({                                                                             
                \
+       put_user(((task)->thread.flags & IA64_THREAD_FPEMU_MASK) >> 
IA64_THREAD_FPEMU_SHIFT,    \
+                (int __user *) (addr));                                        
                \
+})
+
+#ifdef CONFIG_IA32_SUPPORT
+struct desc_struct {
+       unsigned int a, b;
+};
+
+#define desc_empty(desc)               (!((desc)->a + (desc)->b))
+#define desc_equal(desc1, desc2)       (((desc1)->a == (desc2)->a) && 
((desc1)->b == (desc2)->b))
+
+#define GDT_ENTRY_TLS_ENTRIES  3
+#define GDT_ENTRY_TLS_MIN      6
+#define GDT_ENTRY_TLS_MAX      (GDT_ENTRY_TLS_MIN + GDT_ENTRY_TLS_ENTRIES - 1)
+
+#define TLS_SIZE (GDT_ENTRY_TLS_ENTRIES * 8)
+
+struct partial_page_list;
+#endif
+
+struct thread_struct {
+       __u32 flags;                    /* various thread flags (see 
IA64_THREAD_*) */
+       /* writing on_ustack is performance-critical, so it's worth spending 8 
bits on it... */
+       __u8 on_ustack;                 /* executing on user-stacks? */
+       __u8 pad[3];
+       __u64 ksp;                      /* kernel stack pointer */
+       __u64 map_base;                 /* base address for get_unmapped_area() 
*/
+       __u64 task_size;                /* limit for task size */
+       __u64 rbs_bot;                  /* the base address for the RBS */
+       int last_fph_cpu;               /* CPU that may hold the contents of 
f32-f127 */
+
+#ifdef CONFIG_IA32_SUPPORT
+       __u64 eflag;                    /* IA32 EFLAGS reg */
+       __u64 fsr;                      /* IA32 floating pt status reg */
+       __u64 fcr;                      /* IA32 floating pt control reg */
+       __u64 fir;                      /* IA32 fp except. instr. reg */
+       __u64 fdr;                      /* IA32 fp except. data reg */
+       __u64 old_k1;                   /* old value of ar.k1 */
+       __u64 old_iob;                  /* old IOBase value */
+       struct partial_page_list *ppl;  /* partial page list for 4K page size 
issue */
+        /* cached TLS descriptors. */
+       struct desc_struct tls_array[GDT_ENTRY_TLS_ENTRIES];
+
+# define INIT_THREAD_IA32      .eflag =        0,                      \
+                               .fsr =          0,                      \
+                               .fcr =          0x17800000037fULL,      \
+                               .fir =          0,                      \
+                               .fdr =          0,                      \
+                               .old_k1 =       0,                      \
+                               .old_iob =      0,                      \
+                               .ppl =          NULL,
+#else
+# define INIT_THREAD_IA32
+#endif /* CONFIG_IA32_SUPPORT */
+#ifdef CONFIG_PERFMON
+       __u64 pmcs[IA64_NUM_PMC_REGS];
+       __u64 pmds[IA64_NUM_PMD_REGS];
+       void *pfm_context;                   /* pointer to detailed PMU context 
*/
+       unsigned long pfm_needs_checking;    /* when >0, pending perfmon work 
on kernel exit */
+# define INIT_THREAD_PM                .pmcs =                 {0UL, },  \
+                               .pmds =                 {0UL, },  \
+                               .pfm_context =          NULL,     \
+                               .pfm_needs_checking =   0UL,
+#else
+# define INIT_THREAD_PM
+#endif
+       __u64 dbr[IA64_NUM_DBG_REGS];
+       __u64 ibr[IA64_NUM_DBG_REGS];
+       struct ia64_fpreg fph[96];      /* saved/loaded on demand */
+};
+
+#define INIT_THREAD {                                          \
+       .flags =        0,                                      \
+       .on_ustack =    0,                                      \
+       .ksp =          0,                                      \
+       .map_base =     DEFAULT_MAP_BASE,                       \
+       .rbs_bot =      STACK_TOP - DEFAULT_USER_STACK_SIZE,    \
+       .task_size =    DEFAULT_TASK_SIZE,                      \
+       .last_fph_cpu =  -1,                                    \
+       INIT_THREAD_IA32                                        \
+       INIT_THREAD_PM                                          \
+       .dbr =          {0, },                                  \
+       .ibr =          {0, },                                  \
+       .fph =          {{{{0}}}, }                             \
+}
+
+#define start_thread(regs,new_ip,new_sp) do {                                  
                \
+       set_fs(USER_DS);                                                        
                \
+       regs->cr_ipsr = ((regs->cr_ipsr | (IA64_PSR_BITS_TO_SET | 
IA64_PSR_CPL))                \
+                        & ~(IA64_PSR_BITS_TO_CLEAR | IA64_PSR_RI | 
IA64_PSR_IS));              \
+       regs->cr_iip = new_ip;                                                  
                \
+       regs->ar_rsc = 0xf;             /* eager mode, privilege level 3 */     
                \
+       regs->ar_rnat = 0;                                                      
                \
+       regs->ar_bspstore = current->thread.rbs_bot;                            
                \
+       regs->ar_fpsr = FPSR_DEFAULT;                                           
                \
+       regs->loadrs = 0;                                                       
                \
+       regs->r8 = current->mm->dumpable;       /* set "don't zap registers" 
flag */            \
+       regs->r12 = new_sp - 16;        /* allocate 16 byte scratch area */     
                \
+       if (unlikely(!current->mm->dumpable)) {                                 
                \
+               /*                                                              
                \
+                * Zap scratch regs to avoid leaking bits between processes 
with different      \
+                * uid/privileges.                                              
                \
+                */                                                             
                \
+               regs->ar_pfs = 0; regs->b0 = 0; regs->pr = 0;                   
                \
+               regs->r1 = 0; regs->r9  = 0; regs->r11 = 0; regs->r13 = 0; 
regs->r15 = 0;       \
+       }                                                                       
                \
+} while (0)
+
+/* Forward declarations, a strange C thing... */
+struct mm_struct;
+struct task_struct;
+
+/*
+ * Free all resources held by a thread. This is called after the
+ * parent of DEAD_TASK has collected the exit status of the task via
+ * wait().
+ */
+#define release_thread(dead_task)
+
+/* Prepare to copy thread state - unlazy all lazy status */
+#define prepare_to_copy(tsk)   do { } while (0)
+
+/*
+ * This is the mechanism for creating a new kernel thread.
+ *
+ * NOTE 1: Only a kernel-only process (ie the swapper or direct
+ * descendants who haven't done an "execve()") should use this: it
+ * will work within a system call from a "real" process, but the
+ * process memory space will not be free'd until both the parent and
+ * the child have exited.
+ *
+ * NOTE 2: This MUST NOT be an inlined function.  Otherwise, we get
+ * into trouble in init/main.c when the child thread returns to
+ * do_basic_setup() and the timing is such that free_initmem() has
+ * been called already.
+ */
+extern pid_t kernel_thread (int (*fn)(void *), void *arg, unsigned long flags);
+
+/* Get wait channel for task P.  */
+extern unsigned long get_wchan (struct task_struct *p);
+
+/* Return instruction pointer of blocked task TSK.  */
+#define KSTK_EIP(tsk)                                  \
+  ({                                                   \
+       struct pt_regs *_regs = ia64_task_regs(tsk);    \
+       _regs->cr_iip + ia64_psr(_regs)->ri;            \
+  })
+
+/* Return stack pointer of blocked task TSK.  */
+#define KSTK_ESP(tsk)  ((tsk)->thread.ksp)
+
+extern void ia64_getreg_unknown_kr (void);
+extern void ia64_setreg_unknown_kr (void);
+
+#define ia64_get_kr(regnum)                                    \
+({                                                             \
+       unsigned long r = 0;                                    \
+                                                               \
+       switch (regnum) {                                       \
+           case 0: r = ia64_getreg(_IA64_REG_AR_KR0); break;   \
+           case 1: r = ia64_getreg(_IA64_REG_AR_KR1); break;   \
+           case 2: r = ia64_getreg(_IA64_REG_AR_KR2); break;   \
+           case 3: r = ia64_getreg(_IA64_REG_AR_KR3); break;   \
+           case 4: r = ia64_getreg(_IA64_REG_AR_KR4); break;   \
+           case 5: r = ia64_getreg(_IA64_REG_AR_KR5); break;   \
+           case 6: r = ia64_getreg(_IA64_REG_AR_KR6); break;   \
+           case 7: r = ia64_getreg(_IA64_REG_AR_KR7); break;   \
+           default: ia64_getreg_unknown_kr(); break;           \
+       }                                                       \
+       r;                                                      \
+})
+
+#define ia64_set_kr(regnum, r)                                         \
+({                                                             \
+       switch (regnum) {                                       \
+           case 0: ia64_setreg(_IA64_REG_AR_KR0, r); break;    \
+           case 1: ia64_setreg(_IA64_REG_AR_KR1, r); break;    \
+           case 2: ia64_setreg(_IA64_REG_AR_KR2, r); break;    \
+           case 3: ia64_setreg(_IA64_REG_AR_KR3, r); break;    \
+           case 4: ia64_setreg(_IA64_REG_AR_KR4, r); break;    \
+           case 5: ia64_setreg(_IA64_REG_AR_KR5, r); break;    \
+           case 6: ia64_setreg(_IA64_REG_AR_KR6, r); break;    \
+           case 7: ia64_setreg(_IA64_REG_AR_KR7, r); break;    \
+           default: ia64_setreg_unknown_kr(); break;           \
+       }                                                       \
+})
+
+/*
+ * The following three macros can't be inline functions because we don't have 
struct
+ * task_struct at this point.
+ */
+
+/* Return TRUE if task T owns the fph partition of the CPU we're running on. */
+#ifndef XEN
+#define ia64_is_local_fpu_owner(t)                                             
                \
+({                                                                             
                \
+       struct task_struct *__ia64_islfo_task = (t);                            
                \
+       (__ia64_islfo_task->thread.last_fph_cpu == smp_processor_id()           
                \
+        && __ia64_islfo_task == (struct task_struct *) 
ia64_get_kr(IA64_KR_FPU_OWNER));        \
+})
+#endif
+
+/* Mark task T as owning the fph partition of the CPU we're running on. */
+#define ia64_set_local_fpu_owner(t) do {                                       
        \
+       struct task_struct *__ia64_slfo_task = (t);                             
        \
+       __ia64_slfo_task->thread.last_fph_cpu = smp_processor_id();             
        \
+       ia64_set_kr(IA64_KR_FPU_OWNER, (unsigned long) __ia64_slfo_task);       
        \
+} while (0)
+
+/* Mark the fph partition of task T as being invalid on all CPUs.  */
+#define ia64_drop_fpu(t)       ((t)->thread.last_fph_cpu = -1)
+
+extern void __ia64_init_fpu (void);
+extern void __ia64_save_fpu (struct ia64_fpreg *fph);
+extern void __ia64_load_fpu (struct ia64_fpreg *fph);
+extern void ia64_save_debug_regs (unsigned long *save_area);
+extern void ia64_load_debug_regs (unsigned long *save_area);
+
+#ifdef CONFIG_IA32_SUPPORT
+extern void ia32_save_state (struct task_struct *task);
+extern void ia32_load_state (struct task_struct *task);
+#endif
+
+#define ia64_fph_enable()      do { ia64_rsm(IA64_PSR_DFH); ia64_srlz_d(); } 
while (0)
+#define ia64_fph_disable()     do { ia64_ssm(IA64_PSR_DFH); ia64_srlz_d(); } 
while (0)
+
+/* load fp 0.0 into fph */
+static inline void
+ia64_init_fpu (void) {
+       ia64_fph_enable();
+       __ia64_init_fpu();
+       ia64_fph_disable();
+}
+
+/* save f32-f127 at FPH */
+static inline void
+ia64_save_fpu (struct ia64_fpreg *fph) {
+       ia64_fph_enable();
+       __ia64_save_fpu(fph);
+       ia64_fph_disable();
+}
+
+/* load f32-f127 from FPH */
+static inline void
+ia64_load_fpu (struct ia64_fpreg *fph) {
+       ia64_fph_enable();
+       __ia64_load_fpu(fph);
+       ia64_fph_disable();
+}
+
+static inline __u64
+ia64_clear_ic (void)
+{
+       __u64 psr;
+       psr = ia64_getreg(_IA64_REG_PSR);
+       ia64_stop();
+       ia64_rsm(IA64_PSR_I | IA64_PSR_IC);
+       ia64_srlz_i();
+       return psr;
+}
+
+/*
+ * Restore the psr.
+ */
+static inline void
+ia64_set_psr (__u64 psr)
+{
+       ia64_stop();
+       ia64_setreg(_IA64_REG_PSR_L, psr);
+       ia64_srlz_d();
+}
+
+/*
+ * Insert a translation into an instruction and/or data translation
+ * register.
+ */
+static inline void
+ia64_itr (__u64 target_mask, __u64 tr_num,
+         __u64 vmaddr, __u64 pte,
+         __u64 log_page_size)
+{
+       ia64_setreg(_IA64_REG_CR_ITIR, (log_page_size << 2));
+       ia64_setreg(_IA64_REG_CR_IFA, vmaddr);
+       ia64_stop();
+       if (target_mask & 0x1)
+               ia64_itri(tr_num, pte);
+       if (target_mask & 0x2)
+               ia64_itrd(tr_num, pte);
+}
+
+/*
+ * Insert a translation into the instruction and/or data translation
+ * cache.
+ */
+static inline void
+ia64_itc (__u64 target_mask, __u64 vmaddr, __u64 pte,
+         __u64 log_page_size)
+{
+       ia64_setreg(_IA64_REG_CR_ITIR, (log_page_size << 2));
+       ia64_setreg(_IA64_REG_CR_IFA, vmaddr);
+       ia64_stop();
+       /* as per EAS2.6, itc must be the last instruction in an instruction 
group */
+       if (target_mask & 0x1)
+               ia64_itci(pte);
+       if (target_mask & 0x2)
+               ia64_itcd(pte);
+}
+
+/*
+ * Purge a range of addresses from instruction and/or data translation
+ * register(s).
+ */
+static inline void
+ia64_ptr (__u64 target_mask, __u64 vmaddr, __u64 log_size)
+{
+       if (target_mask & 0x1)
+               ia64_ptri(vmaddr, (log_size << 2));
+       if (target_mask & 0x2)
+               ia64_ptrd(vmaddr, (log_size << 2));
+}
+
+/* Set the interrupt vector address.  The address must be suitably aligned 
(32KB).  */
+static inline void
+ia64_set_iva (void *ivt_addr)
+{
+       ia64_setreg(_IA64_REG_CR_IVA, (__u64) ivt_addr);
+       ia64_srlz_i();
+}
+
+/* Set the page table address and control bits.  */
+static inline void
+ia64_set_pta (__u64 pta)
+{
+       /* Note: srlz.i implies srlz.d */
+       ia64_setreg(_IA64_REG_CR_PTA, pta);
+       ia64_srlz_i();
+}
+
+static inline void
+ia64_eoi (void)
+{
+       ia64_setreg(_IA64_REG_CR_EOI, 0);
+       ia64_srlz_d();
+}
+
+#define cpu_relax()    ia64_hint(ia64_hint_pause)
+
+static inline void
+ia64_set_lrr0 (unsigned long val)
+{
+       ia64_setreg(_IA64_REG_CR_LRR0, val);
+       ia64_srlz_d();
+}
+
+static inline void
+ia64_set_lrr1 (unsigned long val)
+{
+       ia64_setreg(_IA64_REG_CR_LRR1, val);
+       ia64_srlz_d();
+}
+
+
+/*
+ * Given the address to which a spill occurred, return the unat bit
+ * number that corresponds to this address.
+ */
+static inline __u64
+ia64_unat_pos (void *spill_addr)
+{
+       return ((__u64) spill_addr >> 3) & 0x3f;
+}
+
+/*
+ * Set the NaT bit of an integer register which was spilled at address
+ * SPILL_ADDR.  UNAT is the mask to be updated.
+ */
+static inline void
+ia64_set_unat (__u64 *unat, void *spill_addr, unsigned long nat)
+{
+       __u64 bit = ia64_unat_pos(spill_addr);
+       __u64 mask = 1UL << bit;
+
+       *unat = (*unat & ~mask) | (nat << bit);
+}
+
+/*
+ * Return saved PC of a blocked thread.
+ * Note that the only way T can block is through a call to schedule() -> 
switch_to().
+ */
+static inline unsigned long
+thread_saved_pc (struct task_struct *t)
+{
+       struct unw_frame_info info;
+       unsigned long ip;
+
+       unw_init_from_blocked_task(&info, t);
+       if (unw_unwind(&info) < 0)
+               return 0;
+       unw_get_ip(&info, &ip);
+       return ip;
+}
+
+/*
+ * Get the current instruction/program counter value.
+ */
+#define current_text_addr() \
+       ({ void *_pc; _pc = (void *)ia64_getreg(_IA64_REG_IP); _pc; })
+
+static inline __u64
+ia64_get_ivr (void)
+{
+       __u64 r;
+       ia64_srlz_d();
+       r = ia64_getreg(_IA64_REG_CR_IVR);
+       ia64_srlz_d();
+       return r;
+}
+
+static inline void
+ia64_set_dbr (__u64 regnum, __u64 value)
+{
+       __ia64_set_dbr(regnum, value);
+#ifdef CONFIG_ITANIUM
+       ia64_srlz_d();
+#endif
+}
+
+static inline __u64
+ia64_get_dbr (__u64 regnum)
+{
+       __u64 retval;
+
+       retval = __ia64_get_dbr(regnum);
+#ifdef CONFIG_ITANIUM
+       ia64_srlz_d();
+#endif
+       return retval;
+}
+
+static inline __u64
+ia64_rotr (__u64 w, __u64 n)
+{
+       return (w >> n) | (w << (64 - n));
+}
+
+#define ia64_rotl(w,n) ia64_rotr((w), (64) - (n))
+
+/*
+ * Take a mapped kernel address and return the equivalent address
+ * in the region 7 identity mapped virtual area.
+ */
+static inline void *
+ia64_imva (void *addr)
+{
+       void *result;
+       result = (void *) ia64_tpa(addr);
+       return __va(result);
+}
+
+#define ARCH_HAS_PREFETCH
+#define ARCH_HAS_PREFETCHW
+#define ARCH_HAS_SPINLOCK_PREFETCH
+#define PREFETCH_STRIDE                        L1_CACHE_BYTES
+
+static inline void
+prefetch (const void *x)
+{
+        ia64_lfetch(ia64_lfhint_none, x);
+}
+
+static inline void
+prefetchw (const void *x)
+{
+       ia64_lfetch_excl(ia64_lfhint_none, x);
+}
+
+#define spin_lock_prefetch(x)  prefetchw(x)
+
+extern unsigned long boot_option_idle_override;
+
+#endif /* !__ASSEMBLY__ */
+
+#endif /* _ASM_IA64_PROCESSOR_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/ptrace.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/ptrace.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,342 @@
+#ifndef _ASM_IA64_PTRACE_H
+#define _ASM_IA64_PTRACE_H
+
+/*
+ * Copyright (C) 1998-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ * Copyright (C) 2003 Intel Co
+ *     Suresh Siddha <suresh.b.siddha@xxxxxxxxx>
+ *     Fenghua Yu <fenghua.yu@xxxxxxxxx>
+ *     Arun Sharma <arun.sharma@xxxxxxxxx>
+ *
+ * 12/07/98    S. Eranian      added pt_regs & switch_stack
+ * 12/21/98    D. Mosberger    updated to match latest code
+ *  6/17/99    D. Mosberger    added second unat member to "struct 
switch_stack"
+ *
+ */
+/*
+ * When a user process is blocked, its state looks as follows:
+ *
+ *            +----------------------+ ------- IA64_STK_OFFSET
+ *                   |                      |   ^
+ *            | struct pt_regs       |  |
+ *           |                      |   |
+ *            +----------------------+  |
+ *           |                      |   |
+ *                   |    memory stack      |   |
+ *           | (growing downwards)  |   |
+ *           //.....................//  |
+ *                                      |
+ *           //.....................//  |
+ *           |                      |   |
+ *            +----------------------+  |
+ *            | struct switch_stack  |  |
+ *           |                      |   |
+ *           +----------------------+   |
+ *           |                      |   |
+ *           //.....................//  |
+ *                                      |
+ *           //.....................//  |
+ *           |                      |   |
+ *           |  register stack      |   |
+ *           | (growing upwards)    |   |
+ *            |                             |   |
+ *           +----------------------+   |  --- IA64_RBS_OFFSET
+ *            |  struct thread_info  |  |  ^
+ *           +----------------------+   |  |
+ *           |                      |   |  |
+ *            |  struct task_struct  |  |  |
+ * current -> |                             |   |  |
+ *           +----------------------+ -------
+ *
+ * Note that ar.ec is not saved explicitly in pt_reg or switch_stack.
+ * This is because ar.ec is saved as part of ar.pfs.
+ */
+
+#include <linux/config.h>
+
+#include <asm/fpu.h>
+#include <asm/offsets.h>
+
+/*
+ * Base-2 logarithm of number of pages to allocate per task structure
+ * (including register backing store and memory stack):
+ */
+#if defined(CONFIG_IA64_PAGE_SIZE_4KB)
+# define KERNEL_STACK_SIZE_ORDER               3
+#elif defined(CONFIG_IA64_PAGE_SIZE_8KB)
+# define KERNEL_STACK_SIZE_ORDER               2
+#elif defined(CONFIG_IA64_PAGE_SIZE_16KB)
+# define KERNEL_STACK_SIZE_ORDER               1
+#else
+# define KERNEL_STACK_SIZE_ORDER               0
+#endif
+
+#define IA64_RBS_OFFSET                        ((IA64_TASK_SIZE + 
IA64_THREAD_INFO_SIZE + 15) & ~15)
+#define IA64_STK_OFFSET                        ((1 << 
KERNEL_STACK_SIZE_ORDER)*PAGE_SIZE)
+
+#define KERNEL_STACK_SIZE              IA64_STK_OFFSET
+
+#ifndef __ASSEMBLY__
+
+#include <asm/current.h>
+#include <asm/page.h>
+
+/*
+ * This struct defines the way the registers are saved on system
+ * calls.
+ *
+ * We don't save all floating point register because the kernel
+ * is compiled to use only a very small subset, so the other are
+ * untouched.
+ *
+ * THIS STRUCTURE MUST BE A MULTIPLE 16-BYTE IN SIZE
+ * (because the memory stack pointer MUST ALWAYS be aligned this way)
+ *
+ */
+#ifdef XEN
+#include <public/arch-ia64.h>
+#define pt_regs cpu_user_regs
+#else
+struct pt_regs {
+       /* The following registers are saved by SAVE_MIN: */
+       unsigned long b6;               /* scratch */
+       unsigned long b7;               /* scratch */
+
+       unsigned long ar_csd;           /* used by cmp8xchg16 (scratch) */
+       unsigned long ar_ssd;           /* reserved for future use (scratch) */
+
+       unsigned long r8;               /* scratch (return value register 0) */
+       unsigned long r9;               /* scratch (return value register 1) */
+       unsigned long r10;              /* scratch (return value register 2) */
+       unsigned long r11;              /* scratch (return value register 3) */
+
+       unsigned long cr_ipsr;          /* interrupted task's psr */
+       unsigned long cr_iip;           /* interrupted task's instruction 
pointer */
+       /*
+        * interrupted task's function state; if bit 63 is cleared, it
+        * contains syscall's ar.pfs.pfm:
+        */
+       unsigned long cr_ifs;
+
+       unsigned long ar_unat;          /* interrupted task's NaT register 
(preserved) */
+       unsigned long ar_pfs;           /* prev function state  */
+       unsigned long ar_rsc;           /* RSE configuration */
+       /* The following two are valid only if cr_ipsr.cpl > 0: */
+       unsigned long ar_rnat;          /* RSE NaT */
+       unsigned long ar_bspstore;      /* RSE bspstore */
+
+       unsigned long pr;               /* 64 predicate registers (1 bit each) 
*/
+       unsigned long b0;               /* return pointer (bp) */
+       unsigned long loadrs;           /* size of dirty partition << 16 */
+
+       unsigned long r1;               /* the gp pointer */
+       unsigned long r12;              /* interrupted task's memory stack 
pointer */
+       unsigned long r13;              /* thread pointer */
+
+       unsigned long ar_fpsr;          /* floating point status (preserved) */
+       unsigned long r15;              /* scratch */
+
+       /* The remaining registers are NOT saved for system calls.  */
+
+       unsigned long r14;              /* scratch */
+       unsigned long r2;               /* scratch */
+       unsigned long r3;               /* scratch */
+
+       /* The following registers are saved by SAVE_REST: */
+       unsigned long r16;              /* scratch */
+       unsigned long r17;              /* scratch */
+       unsigned long r18;              /* scratch */
+       unsigned long r19;              /* scratch */
+       unsigned long r20;              /* scratch */
+       unsigned long r21;              /* scratch */
+       unsigned long r22;              /* scratch */
+       unsigned long r23;              /* scratch */
+       unsigned long r24;              /* scratch */
+       unsigned long r25;              /* scratch */
+       unsigned long r26;              /* scratch */
+       unsigned long r27;              /* scratch */
+       unsigned long r28;              /* scratch */
+       unsigned long r29;              /* scratch */
+       unsigned long r30;              /* scratch */
+       unsigned long r31;              /* scratch */
+
+       unsigned long ar_ccv;           /* compare/exchange value (scratch) */
+
+       /*
+        * Floating point registers that the kernel considers scratch:
+        */
+       struct ia64_fpreg f6;           /* scratch */
+       struct ia64_fpreg f7;           /* scratch */
+       struct ia64_fpreg f8;           /* scratch */
+       struct ia64_fpreg f9;           /* scratch */
+       struct ia64_fpreg f10;          /* scratch */
+       struct ia64_fpreg f11;          /* scratch */
+};
+#endif
+
+/*
+ * This structure contains the addition registers that need to
+ * preserved across a context switch.  This generally consists of
+ * "preserved" registers.
+ */
+struct switch_stack {
+       unsigned long caller_unat;      /* user NaT collection register 
(preserved) */
+       unsigned long ar_fpsr;          /* floating-point status register */
+
+       struct ia64_fpreg f2;           /* preserved */
+       struct ia64_fpreg f3;           /* preserved */
+       struct ia64_fpreg f4;           /* preserved */
+       struct ia64_fpreg f5;           /* preserved */
+
+       struct ia64_fpreg f12;          /* scratch, but untouched by kernel */
+       struct ia64_fpreg f13;          /* scratch, but untouched by kernel */
+       struct ia64_fpreg f14;          /* scratch, but untouched by kernel */
+       struct ia64_fpreg f15;          /* scratch, but untouched by kernel */
+       struct ia64_fpreg f16;          /* preserved */
+       struct ia64_fpreg f17;          /* preserved */
+       struct ia64_fpreg f18;          /* preserved */
+       struct ia64_fpreg f19;          /* preserved */
+       struct ia64_fpreg f20;          /* preserved */
+       struct ia64_fpreg f21;          /* preserved */
+       struct ia64_fpreg f22;          /* preserved */
+       struct ia64_fpreg f23;          /* preserved */
+       struct ia64_fpreg f24;          /* preserved */
+       struct ia64_fpreg f25;          /* preserved */
+       struct ia64_fpreg f26;          /* preserved */
+       struct ia64_fpreg f27;          /* preserved */
+       struct ia64_fpreg f28;          /* preserved */
+       struct ia64_fpreg f29;          /* preserved */
+       struct ia64_fpreg f30;          /* preserved */
+       struct ia64_fpreg f31;          /* preserved */
+
+       unsigned long r4;               /* preserved */
+       unsigned long r5;               /* preserved */
+       unsigned long r6;               /* preserved */
+       unsigned long r7;               /* preserved */
+
+       unsigned long b0;               /* so we can force a direct return in 
copy_thread */
+       unsigned long b1;
+       unsigned long b2;
+       unsigned long b3;
+       unsigned long b4;
+       unsigned long b5;
+
+       unsigned long ar_pfs;           /* previous function state */
+       unsigned long ar_lc;            /* loop counter (preserved) */
+       unsigned long ar_unat;          /* NaT bits for r4-r7 */
+       unsigned long ar_rnat;          /* RSE NaT collection register */
+       unsigned long ar_bspstore;      /* RSE dirty base (preserved) */
+       unsigned long pr;               /* 64 predicate registers (1 bit each) 
*/
+};
+
+#ifdef __KERNEL__
+/*
+ * We use the ia64_psr(regs)->ri to determine which of the three
+ * instructions in bundle (16 bytes) took the sample. Generate
+ * the canonical representation by adding to instruction pointer.
+ */
+# define instruction_pointer(regs) ((regs)->cr_iip + ia64_psr(regs)->ri)
+/* Conserve space in histogram by encoding slot bits in address
+ * bits 2 and 3 rather than bits 0 and 1.
+ */
+#define profile_pc(regs)                                               \
+({                                                                     \
+       unsigned long __ip = instruction_pointer(regs);                 \
+       (__ip & ~3UL) + ((__ip & 3UL) << 2);                            \
+})
+
+  /* given a pointer to a task_struct, return the user's pt_regs */
+# define ia64_task_regs(t)             (((struct pt_regs *) ((char *) (t) + 
IA64_STK_OFFSET)) - 1)
+# define ia64_psr(regs)                        ((struct ia64_psr *) 
&(regs)->cr_ipsr)
+# define user_mode(regs)               (((struct ia64_psr *) 
&(regs)->cr_ipsr)->cpl != 0)
+# define user_stack(task,regs) ((long) regs - (long) task == IA64_STK_OFFSET - 
sizeof(*regs))
+# define fsys_mode(task,regs)                                  \
+  ({                                                           \
+         struct task_struct *_task = (task);                   \
+         struct pt_regs *_regs = (regs);                       \
+         !user_mode(_regs) && user_stack(_task, _regs);        \
+  })
+
+  /*
+   * System call handlers that, upon successful completion, need to return a 
negative value
+   * should call force_successful_syscall_return() right before returning.  On 
architectures
+   * where the syscall convention provides for a separate error flag (e.g., 
alpha, ia64,
+   * ppc{,64}, sparc{,64}, possibly others), this macro can be used to ensure 
that the error
+   * flag will not get set.  On architectures which do not support a separate 
error flag,
+   * the macro is a no-op and the spurious error condition needs to be 
filtered out by some
+   * other means (e.g., in user-level, by passing an extra argument to the 
syscall handler,
+   * or something along those lines).
+   *
+   * On ia64, we can clear the user's pt_regs->r8 to force a successful 
syscall.
+   */
+# define force_successful_syscall_return()     (ia64_task_regs(current)->r8 = 
0)
+
+  struct task_struct;                  /* forward decl */
+  struct unw_frame_info;               /* forward decl */
+
+  extern void show_regs (struct pt_regs *);
+  extern void ia64_do_show_stack (struct unw_frame_info *, void *);
+  extern unsigned long ia64_get_user_rbs_end (struct task_struct *, struct 
pt_regs *,
+                                             unsigned long *);
+  extern long ia64_peek (struct task_struct *, struct switch_stack *, unsigned 
long,
+                        unsigned long, long *);
+  extern long ia64_poke (struct task_struct *, struct switch_stack *, unsigned 
long,
+                        unsigned long, long);
+  extern void ia64_flush_fph (struct task_struct *);
+  extern void ia64_sync_fph (struct task_struct *);
+  extern long ia64_sync_user_rbs (struct task_struct *, struct switch_stack *,
+                                 unsigned long, unsigned long);
+
+  /* get nat bits for scratch registers such that bit N==1 iff scratch 
register rN is a NaT */
+  extern unsigned long ia64_get_scratch_nat_bits (struct pt_regs *pt, unsigned 
long scratch_unat);
+  /* put nat bits for scratch registers such that scratch register rN is a NaT 
iff bit N==1 */
+  extern unsigned long ia64_put_scratch_nat_bits (struct pt_regs *pt, unsigned 
long nat);
+
+  extern void ia64_increment_ip (struct pt_regs *pt);
+  extern void ia64_decrement_ip (struct pt_regs *pt);
+
+#endif /* !__KERNEL__ */
+
+/* pt_all_user_regs is used for PTRACE_GETREGS PTRACE_SETREGS */
+struct pt_all_user_regs {
+       unsigned long nat;
+       unsigned long cr_iip;
+       unsigned long cfm;
+       unsigned long cr_ipsr;
+       unsigned long pr;
+
+       unsigned long gr[32];
+       unsigned long br[8];
+       unsigned long ar[128];
+       struct ia64_fpreg fr[128];
+};
+
+#endif /* !__ASSEMBLY__ */
+
+/* indices to application-registers array in pt_all_user_regs */
+#define PT_AUR_RSC     16
+#define PT_AUR_BSP     17
+#define PT_AUR_BSPSTORE        18
+#define PT_AUR_RNAT    19
+#define PT_AUR_CCV     32
+#define PT_AUR_UNAT    36
+#define PT_AUR_FPSR    40
+#define PT_AUR_PFS     64
+#define PT_AUR_LC      65
+#define PT_AUR_EC      66
+
+/*
+ * The numbers chosen here are somewhat arbitrary but absolutely MUST
+ * not overlap with any of the number assigned in <linux/ptrace.h>.
+ */
+#define PTRACE_SINGLEBLOCK     12      /* resume execution until next branch */
+#define PTRACE_OLD_GETSIGINFO  13      /* (replaced by PTRACE_GETSIGINFO in 
<linux/ptrace.h>)  */
+#define PTRACE_OLD_SETSIGINFO  14      /* (replaced by PTRACE_SETSIGINFO in 
<linux/ptrace.h>)  */
+#define PTRACE_GETREGS         18      /* get all registers (pt_all_user_regs) 
in one shot */
+#define PTRACE_SETREGS         19      /* set all registers (pt_all_user_regs) 
in one shot */
+
+#define PTRACE_OLDSETOPTIONS   21
+
+#endif /* _ASM_IA64_PTRACE_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/sn/sn_sal.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/sn/sn_sal.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,994 @@
+#ifndef _ASM_IA64_SN_SN_SAL_H
+#define _ASM_IA64_SN_SN_SAL_H
+
+/*
+ * System Abstraction Layer definitions for IA64
+ *
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * Copyright (c) 2000-2004 Silicon Graphics, Inc.  All rights reserved.
+ */
+
+
+#include <linux/config.h>
+#include <asm/sal.h>
+#include <asm/sn/sn_cpuid.h>
+#include <asm/sn/arch.h>
+#include <asm/sn/geo.h>
+#include <asm/sn/nodepda.h>
+
+// SGI Specific Calls
+#define  SN_SAL_POD_MODE                           0x02000001
+#define  SN_SAL_SYSTEM_RESET                       0x02000002
+#define  SN_SAL_PROBE                              0x02000003
+#define  SN_SAL_GET_MASTER_NASID                   0x02000004
+#define         SN_SAL_GET_KLCONFIG_ADDR                  0x02000005
+#define  SN_SAL_LOG_CE                            0x02000006
+#define  SN_SAL_REGISTER_CE                       0x02000007
+#define  SN_SAL_GET_PARTITION_ADDR                0x02000009
+#define  SN_SAL_XP_ADDR_REGION                    0x0200000f
+#define  SN_SAL_NO_FAULT_ZONE_VIRTUAL             0x02000010
+#define  SN_SAL_NO_FAULT_ZONE_PHYSICAL            0x02000011
+#define  SN_SAL_PRINT_ERROR                       0x02000012
+#define  SN_SAL_SET_ERROR_HANDLING_FEATURES       0x0200001a   // reentrant
+#define  SN_SAL_GET_FIT_COMPT                     0x0200001b   // reentrant
+#define  SN_SAL_GET_HUB_INFO                       0x0200001c
+#define  SN_SAL_GET_SAPIC_INFO                     0x0200001d
+#define  SN_SAL_CONSOLE_PUTC                       0x02000021
+#define  SN_SAL_CONSOLE_GETC                       0x02000022
+#define  SN_SAL_CONSOLE_PUTS                       0x02000023
+#define  SN_SAL_CONSOLE_GETS                       0x02000024
+#define  SN_SAL_CONSOLE_GETS_TIMEOUT               0x02000025
+#define  SN_SAL_CONSOLE_POLL                       0x02000026
+#define  SN_SAL_CONSOLE_INTR                       0x02000027
+#define  SN_SAL_CONSOLE_PUTB                      0x02000028
+#define  SN_SAL_CONSOLE_XMIT_CHARS                0x0200002a
+#define  SN_SAL_CONSOLE_READC                     0x0200002b
+#define  SN_SAL_SYSCTL_MODID_GET                  0x02000031
+#define  SN_SAL_SYSCTL_GET                         0x02000032
+#define  SN_SAL_SYSCTL_IOBRICK_MODULE_GET          0x02000033
+#define  SN_SAL_SYSCTL_IO_PORTSPEED_GET            0x02000035
+#define  SN_SAL_SYSCTL_SLAB_GET                    0x02000036
+#define  SN_SAL_BUS_CONFIG                        0x02000037
+#define  SN_SAL_SYS_SERIAL_GET                    0x02000038
+#define  SN_SAL_PARTITION_SERIAL_GET              0x02000039
+#define  SN_SAL_SYSCTL_PARTITION_GET              0x0200003a
+#define  SN_SAL_SYSTEM_POWER_DOWN                 0x0200003b
+#define  SN_SAL_GET_MASTER_BASEIO_NASID                   0x0200003c
+#define  SN_SAL_COHERENCE                          0x0200003d
+#define  SN_SAL_MEMPROTECT                         0x0200003e
+#define  SN_SAL_SYSCTL_FRU_CAPTURE                0x0200003f
+
+#define  SN_SAL_SYSCTL_IOBRICK_PCI_OP             0x02000042   // reentrant
+#define         SN_SAL_IROUTER_OP                         0x02000043
+#define  SN_SAL_IOIF_INTERRUPT                    0x0200004a
+#define  SN_SAL_HWPERF_OP                         0x02000050   // lock
+#define  SN_SAL_IOIF_ERROR_INTERRUPT              0x02000051
+
+#define  SN_SAL_IOIF_SLOT_ENABLE                  0x02000053
+#define  SN_SAL_IOIF_SLOT_DISABLE                 0x02000054
+#define  SN_SAL_IOIF_GET_HUBDEV_INFO              0x02000055
+#define  SN_SAL_IOIF_GET_PCIBUS_INFO              0x02000056
+#define  SN_SAL_IOIF_GET_PCIDEV_INFO              0x02000057
+#define  SN_SAL_IOIF_GET_WIDGET_DMAFLUSH_LIST     0x02000058
+
+#define SN_SAL_HUB_ERROR_INTERRUPT                0x02000060
+
+
+/*
+ * Service-specific constants
+ */
+
+/* Console interrupt manipulation */
+       /* action codes */
+#define SAL_CONSOLE_INTR_OFF    0       /* turn the interrupt off */
+#define SAL_CONSOLE_INTR_ON     1       /* turn the interrupt on */
+#define SAL_CONSOLE_INTR_STATUS 2      /* retrieve the interrupt status */
+       /* interrupt specification & status return codes */
+#define SAL_CONSOLE_INTR_XMIT  1       /* output interrupt */
+#define SAL_CONSOLE_INTR_RECV  2       /* input interrupt */
+
+/* interrupt handling */
+#define SAL_INTR_ALLOC         1
+#define SAL_INTR_FREE          2
+
+/*
+ * IRouter (i.e. generalized system controller) operations
+ */
+#define SAL_IROUTER_OPEN       0       /* open a subchannel */
+#define SAL_IROUTER_CLOSE      1       /* close a subchannel */
+#define SAL_IROUTER_SEND       2       /* send part of an IRouter packet */
+#define SAL_IROUTER_RECV       3       /* receive part of an IRouter packet */
+#define SAL_IROUTER_INTR_STATUS        4       /* check the interrupt status 
for
+                                        * an open subchannel
+                                        */
+#define SAL_IROUTER_INTR_ON    5       /* enable an interrupt */
+#define SAL_IROUTER_INTR_OFF   6       /* disable an interrupt */
+#define SAL_IROUTER_INIT       7       /* initialize IRouter driver */
+
+/* IRouter interrupt mask bits */
+#define SAL_IROUTER_INTR_XMIT  SAL_CONSOLE_INTR_XMIT
+#define SAL_IROUTER_INTR_RECV  SAL_CONSOLE_INTR_RECV
+
+
+/*
+ * SAL Error Codes
+ */
+#define SALRET_MORE_PASSES     1
+#define SALRET_OK              0
+#define SALRET_NOT_IMPLEMENTED (-1)
+#define SALRET_INVALID_ARG     (-2)
+#define SALRET_ERROR           (-3)
+
+
+#ifndef XEN
+/**
+ * sn_sal_rev_major - get the major SGI SAL revision number
+ *
+ * The SGI PROM stores its version in sal_[ab]_rev_(major|minor).
+ * This routine simply extracts the major value from the
+ * @ia64_sal_systab structure constructed by ia64_sal_init().
+ */
+static inline int
+sn_sal_rev_major(void)
+{
+       struct ia64_sal_systab *systab = efi.sal_systab;
+
+       return (int)systab->sal_b_rev_major;
+}
+
+/**
+ * sn_sal_rev_minor - get the minor SGI SAL revision number
+ *
+ * The SGI PROM stores its version in sal_[ab]_rev_(major|minor).
+ * This routine simply extracts the minor value from the
+ * @ia64_sal_systab structure constructed by ia64_sal_init().
+ */
+static inline int
+sn_sal_rev_minor(void)
+{
+       struct ia64_sal_systab *systab = efi.sal_systab;
+       
+       return (int)systab->sal_b_rev_minor;
+}
+
+/*
+ * Specify the minimum PROM revsion required for this kernel.
+ * Note that they're stored in hex format...
+ */
+#define SN_SAL_MIN_MAJOR       0x4  /* SN2 kernels need at least PROM 4.0 */
+#define SN_SAL_MIN_MINOR       0x0
+
+/*
+ * Returns the master console nasid, if the call fails, return an illegal
+ * value.
+ */
+static inline u64
+ia64_sn_get_console_nasid(void)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL(ret_stuff, SN_SAL_GET_MASTER_NASID, 0, 0, 0, 0, 0, 0, 0);
+
+       if (ret_stuff.status < 0)
+               return ret_stuff.status;
+
+       /* Master console nasid is in 'v0' */
+       return ret_stuff.v0;
+}
+
+/*
+ * Returns the master baseio nasid, if the call fails, return an illegal
+ * value.
+ */
+static inline u64
+ia64_sn_get_master_baseio_nasid(void)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL(ret_stuff, SN_SAL_GET_MASTER_BASEIO_NASID, 0, 0, 0, 0, 0, 0, 
0);
+
+       if (ret_stuff.status < 0)
+               return ret_stuff.status;
+
+       /* Master baseio nasid is in 'v0' */
+       return ret_stuff.v0;
+}
+
+static inline char *
+ia64_sn_get_klconfig_addr(nasid_t nasid)
+{
+       struct ia64_sal_retval ret_stuff;
+       int cnodeid;
+
+       cnodeid = nasid_to_cnodeid(nasid);
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL(ret_stuff, SN_SAL_GET_KLCONFIG_ADDR, (u64)nasid, 0, 0, 0, 0, 
0, 0);
+
+       /*
+        * We should panic if a valid cnode nasid does not produce
+        * a klconfig address.
+        */
+       if (ret_stuff.status != 0) {
+               panic("ia64_sn_get_klconfig_addr: Returned error %lx\n", 
ret_stuff.status);
+       }
+       return ret_stuff.v0 ? __va(ret_stuff.v0) : NULL;
+}
+#endif /* !XEN */
+
+/*
+ * Returns the next console character.
+ */
+static inline u64
+ia64_sn_console_getc(int *ch)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_GETC, 0, 0, 0, 0, 0, 0, 0);
+
+       /* character is in 'v0' */
+       *ch = (int)ret_stuff.v0;
+
+       return ret_stuff.status;
+}
+
+/*
+ * Read a character from the SAL console device, after a previous interrupt
+ * or poll operation has given us to know that a character is available
+ * to be read.
+ */
+static inline u64
+ia64_sn_console_readc(void)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_READC, 0, 0, 0, 0, 0, 0, 0);
+
+       /* character is in 'v0' */
+       return ret_stuff.v0;
+}
+
+/*
+ * Sends the given character to the console.
+ */
+static inline u64
+ia64_sn_console_putc(char ch)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_PUTC, (uint64_t)ch, 0, 0, 0, 
0, 0, 0);
+
+       return ret_stuff.status;
+}
+
+/*
+ * Sends the given buffer to the console.
+ */
+static inline u64
+ia64_sn_console_putb(const char *buf, int len)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0; 
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_PUTB, (uint64_t)buf, 
(uint64_t)len, 0, 0, 0, 0, 0);
+
+       if ( ret_stuff.status == 0 ) {
+               return ret_stuff.v0;
+       }
+       return (u64)0;
+}
+
+#ifndef XEN
+/*
+ * Print a platform error record
+ */
+static inline u64
+ia64_sn_plat_specific_err_print(int (*hook)(const char*, ...), char *rec)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_REENTRANT(ret_stuff, SN_SAL_PRINT_ERROR, (uint64_t)hook, 
(uint64_t)rec, 0, 0, 0, 0, 0);
+
+       return ret_stuff.status;
+}
+
+/*
+ * Check for Platform errors
+ */
+static inline u64
+ia64_sn_plat_cpei_handler(void)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_LOG_CE, 0, 0, 0, 0, 0, 0, 0);
+
+       return ret_stuff.status;
+}
+
+/*
+ * Checks for console input.
+ */
+static inline u64
+ia64_sn_console_check(int *result)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_POLL, 0, 0, 0, 0, 0, 0, 0);
+
+       /* result is in 'v0' */
+       *result = (int)ret_stuff.v0;
+
+       return ret_stuff.status;
+}
+
+/*
+ * Checks console interrupt status
+ */
+static inline u64
+ia64_sn_console_intr_status(void)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_INTR, 
+                0, SAL_CONSOLE_INTR_STATUS,
+                0, 0, 0, 0, 0);
+
+       if (ret_stuff.status == 0) {
+           return ret_stuff.v0;
+       }
+       
+       return 0;
+}
+
+/*
+ * Enable an interrupt on the SAL console device.
+ */
+static inline void
+ia64_sn_console_intr_enable(uint64_t intr)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_INTR, 
+                intr, SAL_CONSOLE_INTR_ON,
+                0, 0, 0, 0, 0);
+}
+
+/*
+ * Disable an interrupt on the SAL console device.
+ */
+static inline void
+ia64_sn_console_intr_disable(uint64_t intr)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_INTR, 
+                intr, SAL_CONSOLE_INTR_OFF,
+                0, 0, 0, 0, 0);
+}
+
+/*
+ * Sends a character buffer to the console asynchronously.
+ */
+static inline u64
+ia64_sn_console_xmit_chars(char *buf, int len)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_CONSOLE_XMIT_CHARS,
+                (uint64_t)buf, (uint64_t)len,
+                0, 0, 0, 0, 0);
+
+       if (ret_stuff.status == 0) {
+           return ret_stuff.v0;
+       }
+
+       return 0;
+}
+
+/*
+ * Returns the iobrick module Id
+ */
+static inline u64
+ia64_sn_sysctl_iobrick_module_get(nasid_t nasid, int *result)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_SYSCTL_IOBRICK_MODULE_GET, nasid, 0, 
0, 0, 0, 0, 0);
+
+       /* result is in 'v0' */
+       *result = (int)ret_stuff.v0;
+
+       return ret_stuff.status;
+}
+
+/**
+ * ia64_sn_pod_mode - call the SN_SAL_POD_MODE function
+ *
+ * SN_SAL_POD_MODE actually takes an argument, but it's always
+ * 0 when we call it from the kernel, so we don't have to expose
+ * it to the caller.
+ */
+static inline u64
+ia64_sn_pod_mode(void)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SN_SAL_POD_MODE, 0, 0, 0, 0, 0, 0, 0);
+       if (isrv.status)
+               return 0;
+       return isrv.v0;
+}
+
+/**
+ * ia64_sn_probe_mem - read from memory safely
+ * @addr: address to probe
+ * @size: number bytes to read (1,2,4,8)
+ * @data_ptr: address to store value read by probe (-1 returned if probe fails)
+ *
+ * Call into the SAL to do a memory read.  If the read generates a machine
+ * check, this routine will recover gracefully and return -1 to the caller.
+ * @addr is usually a kernel virtual address in uncached space (i.e. the
+ * address starts with 0xc), but if called in physical mode, @addr should
+ * be a physical address.
+ *
+ * Return values:
+ *  0 - probe successful
+ *  1 - probe failed (generated MCA)
+ *  2 - Bad arg
+ * <0 - PAL error
+ */
+static inline u64
+ia64_sn_probe_mem(long addr, long size, void *data_ptr)
+{
+       struct ia64_sal_retval isrv;
+
+       SAL_CALL(isrv, SN_SAL_PROBE, addr, size, 0, 0, 0, 0, 0);
+
+       if (data_ptr) {
+               switch (size) {
+               case 1:
+                       *((u8*)data_ptr) = (u8)isrv.v0;
+                       break;
+               case 2:
+                       *((u16*)data_ptr) = (u16)isrv.v0;
+                       break;
+               case 4:
+                       *((u32*)data_ptr) = (u32)isrv.v0;
+                       break;
+               case 8:
+                       *((u64*)data_ptr) = (u64)isrv.v0;
+                       break;
+               default:
+                       isrv.status = 2;
+               }
+       }
+       return isrv.status;
+}
+
+/*
+ * Retrieve the system serial number as an ASCII string.
+ */
+static inline u64
+ia64_sn_sys_serial_get(char *buf)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_SYS_SERIAL_GET, buf, 0, 0, 0, 0, 0, 
0);
+       return ret_stuff.status;
+}
+
+extern char sn_system_serial_number_string[];
+extern u64 sn_partition_serial_number;
+
+static inline char *
+sn_system_serial_number(void) {
+       if (sn_system_serial_number_string[0]) {
+               return(sn_system_serial_number_string);
+       } else {
+               ia64_sn_sys_serial_get(sn_system_serial_number_string);
+               return(sn_system_serial_number_string);
+       }
+}
+       
+
+/*
+ * Returns a unique id number for this system and partition (suitable for
+ * use with license managers), based in part on the system serial number.
+ */
+static inline u64
+ia64_sn_partition_serial_get(void)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL(ret_stuff, SN_SAL_PARTITION_SERIAL_GET, 0, 0, 0, 0, 0, 0, 0);
+       if (ret_stuff.status != 0)
+           return 0;
+       return ret_stuff.v0;
+}
+
+static inline u64
+sn_partition_serial_number_val(void) {
+       if (sn_partition_serial_number) {
+               return(sn_partition_serial_number);
+       } else {
+               return(sn_partition_serial_number = 
ia64_sn_partition_serial_get());
+       }
+}
+
+/*
+ * Returns the partition id of the nasid passed in as an argument,
+ * or INVALID_PARTID if the partition id cannot be retrieved.
+ */
+static inline partid_t
+ia64_sn_sysctl_partition_get(nasid_t nasid)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL(ret_stuff, SN_SAL_SYSCTL_PARTITION_GET, nasid,
+                0, 0, 0, 0, 0, 0);
+       if (ret_stuff.status != 0)
+           return INVALID_PARTID;
+       return ((partid_t)ret_stuff.v0);
+}
+
+/*
+ * Returns the partition id of the current processor.
+ */
+
+extern partid_t sn_partid;
+
+static inline partid_t
+sn_local_partid(void) {
+       if (sn_partid < 0) {
+               return (sn_partid = 
ia64_sn_sysctl_partition_get(cpuid_to_nasid(smp_processor_id())));
+       } else {
+               return sn_partid;
+       }
+}
+
+/*
+ * Register or unregister a physical address range being referenced across
+ * a partition boundary for which certain SAL errors should be scanned for,
+ * cleaned up and ignored.  This is of value for kernel partitioning code only.
+ * Values for the operation argument:
+ *     1 = register this address range with SAL
+ *     0 = unregister this address range with SAL
+ * 
+ * SAL maintains a reference count on an address range in case it is registered
+ * multiple times.
+ * 
+ * On success, returns the reference count of the address range after the SAL
+ * call has performed the current registration/unregistration.  Returns a
+ * negative value if an error occurred.
+ */
+static inline int
+sn_register_xp_addr_region(u64 paddr, u64 len, int operation)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL(ret_stuff, SN_SAL_XP_ADDR_REGION, paddr, len, (u64)operation,
+                0, 0, 0, 0);
+       return ret_stuff.status;
+}
+
+/*
+ * Register or unregister an instruction range for which SAL errors should
+ * be ignored.  If an error occurs while in the registered range, SAL jumps
+ * to return_addr after ignoring the error.  Values for the operation argument:
+ *     1 = register this instruction range with SAL
+ *     0 = unregister this instruction range with SAL
+ *
+ * Returns 0 on success, or a negative value if an error occurred.
+ */
+static inline int
+sn_register_nofault_code(u64 start_addr, u64 end_addr, u64 return_addr,
+                        int virtual, int operation)
+{
+       struct ia64_sal_retval ret_stuff;
+       u64 call;
+       if (virtual) {
+               call = SN_SAL_NO_FAULT_ZONE_VIRTUAL;
+       } else {
+               call = SN_SAL_NO_FAULT_ZONE_PHYSICAL;
+       }
+       SAL_CALL(ret_stuff, call, start_addr, end_addr, return_addr, (u64)1,
+                0, 0, 0);
+       return ret_stuff.status;
+}
+
+/*
+ * Change or query the coherence domain for this partition. Each cpu-based
+ * nasid is represented by a bit in an array of 64-bit words:
+ *      0 = not in this partition's coherency domain
+ *      1 = in this partition's coherency domain
+ *
+ * It is not possible for the local system's nasids to be removed from
+ * the coherency domain.  Purpose of the domain arguments:
+ *      new_domain = set the coherence domain to the given nasids
+ *      old_domain = return the current coherence domain
+ *
+ * Returns 0 on success, or a negative value if an error occurred.
+ */
+static inline int
+sn_change_coherence(u64 *new_domain, u64 *old_domain)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL(ret_stuff, SN_SAL_COHERENCE, new_domain, old_domain, 0, 0,
+                0, 0, 0);
+       return ret_stuff.status;
+}
+
+/*
+ * Change memory access protections for a physical address range.
+ * nasid_array is not used on Altix, but may be in future architectures.
+ * Available memory protection access classes are defined after the function.
+ */
+static inline int
+sn_change_memprotect(u64 paddr, u64 len, u64 perms, u64 *nasid_array)
+{
+       struct ia64_sal_retval ret_stuff;
+       int cnodeid;
+       unsigned long irq_flags;
+
+       cnodeid = nasid_to_cnodeid(get_node_number(paddr));
+       // spin_lock(&NODEPDA(cnodeid)->bist_lock);
+       local_irq_save(irq_flags);
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_MEMPROTECT, paddr, len, nasid_array,
+                perms, 0, 0, 0);
+       local_irq_restore(irq_flags);
+       // spin_unlock(&NODEPDA(cnodeid)->bist_lock);
+       return ret_stuff.status;
+}
+#define SN_MEMPROT_ACCESS_CLASS_0              0x14a080
+#define SN_MEMPROT_ACCESS_CLASS_1              0x2520c2
+#define SN_MEMPROT_ACCESS_CLASS_2              0x14a1ca
+#define SN_MEMPROT_ACCESS_CLASS_3              0x14a290
+#define SN_MEMPROT_ACCESS_CLASS_6              0x084080
+#define SN_MEMPROT_ACCESS_CLASS_7              0x021080
+
+/*
+ * Turns off system power.
+ */
+static inline void
+ia64_sn_power_down(void)
+{
+       struct ia64_sal_retval ret_stuff;
+       SAL_CALL(ret_stuff, SN_SAL_SYSTEM_POWER_DOWN, 0, 0, 0, 0, 0, 0, 0);
+       while(1);
+       /* never returns */
+}
+
+/**
+ * ia64_sn_fru_capture - tell the system controller to capture hw state
+ *
+ * This routine will call the SAL which will tell the system controller(s)
+ * to capture hw mmr information from each SHub in the system.
+ */
+static inline u64
+ia64_sn_fru_capture(void)
+{
+        struct ia64_sal_retval isrv;
+        SAL_CALL(isrv, SN_SAL_SYSCTL_FRU_CAPTURE, 0, 0, 0, 0, 0, 0, 0);
+        if (isrv.status)
+                return 0;
+        return isrv.v0;
+}
+
+/*
+ * Performs an operation on a PCI bus or slot -- power up, power down
+ * or reset.
+ */
+static inline u64
+ia64_sn_sysctl_iobrick_pci_op(nasid_t n, u64 connection_type, 
+                             u64 bus, char slot, 
+                             u64 action)
+{
+       struct ia64_sal_retval rv = {0, 0, 0, 0};
+
+       SAL_CALL_NOLOCK(rv, SN_SAL_SYSCTL_IOBRICK_PCI_OP, connection_type, n, 
action,
+                bus, (u64) slot, 0, 0);
+       if (rv.status)
+               return rv.v0;
+       return 0;
+}
+
+
+/*
+ * Open a subchannel for sending arbitrary data to the system
+ * controller network via the system controller device associated with
+ * 'nasid'.  Return the subchannel number or a negative error code.
+ */
+static inline int
+ia64_sn_irtr_open(nasid_t nasid)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_OPEN, nasid,
+                          0, 0, 0, 0, 0);
+       return (int) rv.v0;
+}
+
+/*
+ * Close system controller subchannel 'subch' previously opened on 'nasid'.
+ */
+static inline int
+ia64_sn_irtr_close(nasid_t nasid, int subch)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_CLOSE,
+                          (u64) nasid, (u64) subch, 0, 0, 0, 0);
+       return (int) rv.status;
+}
+
+/*
+ * Read data from system controller associated with 'nasid' on
+ * subchannel 'subch'.  The buffer to be filled is pointed to by
+ * 'buf', and its capacity is in the integer pointed to by 'len'.  The
+ * referent of 'len' is set to the number of bytes read by the SAL
+ * call.  The return value is either SALRET_OK (for bytes read) or
+ * SALRET_ERROR (for error or "no data available").
+ */
+static inline int
+ia64_sn_irtr_recv(nasid_t nasid, int subch, char *buf, int *len)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_RECV,
+                          (u64) nasid, (u64) subch, (u64) buf, (u64) len,
+                          0, 0);
+       return (int) rv.status;
+}
+
+/*
+ * Write data to the system controller network via the system
+ * controller associated with 'nasid' on suchannel 'subch'.  The
+ * buffer to be written out is pointed to by 'buf', and 'len' is the
+ * number of bytes to be written.  The return value is either the
+ * number of bytes written (which could be zero) or a negative error
+ * code.
+ */
+static inline int
+ia64_sn_irtr_send(nasid_t nasid, int subch, char *buf, int len)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_SEND,
+                          (u64) nasid, (u64) subch, (u64) buf, (u64) len,
+                          0, 0);
+       return (int) rv.v0;
+}
+
+/*
+ * Check whether any interrupts are pending for the system controller
+ * associated with 'nasid' and its subchannel 'subch'.  The return
+ * value is a mask of pending interrupts (SAL_IROUTER_INTR_XMIT and/or
+ * SAL_IROUTER_INTR_RECV).
+ */
+static inline int
+ia64_sn_irtr_intr(nasid_t nasid, int subch)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_INTR_STATUS,
+                          (u64) nasid, (u64) subch, 0, 0, 0, 0);
+       return (int) rv.v0;
+}
+
+/*
+ * Enable the interrupt indicated by the intr parameter (either
+ * SAL_IROUTER_INTR_XMIT or SAL_IROUTER_INTR_RECV).
+ */
+static inline int
+ia64_sn_irtr_intr_enable(nasid_t nasid, int subch, u64 intr)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_INTR_ON,
+                          (u64) nasid, (u64) subch, intr, 0, 0, 0);
+       return (int) rv.v0;
+}
+
+/*
+ * Disable the interrupt indicated by the intr parameter (either
+ * SAL_IROUTER_INTR_XMIT or SAL_IROUTER_INTR_RECV).
+ */
+static inline int
+ia64_sn_irtr_intr_disable(nasid_t nasid, int subch, u64 intr)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_INTR_OFF,
+                          (u64) nasid, (u64) subch, intr, 0, 0, 0);
+       return (int) rv.v0;
+}
+
+/**
+ * ia64_sn_get_fit_compt - read a FIT entry from the PROM header
+ * @nasid: NASID of node to read
+ * @index: FIT entry index to be retrieved (0..n)
+ * @fitentry: 16 byte buffer where FIT entry will be stored.
+ * @banbuf: optional buffer for retrieving banner
+ * @banlen: length of banner buffer
+ *
+ * Access to the physical PROM chips needs to be serialized since reads and
+ * writes can't occur at the same time, so we need to call into the SAL when
+ * we want to look at the FIT entries on the chips.
+ *
+ * Returns:
+ *     %SALRET_OK if ok
+ *     %SALRET_INVALID_ARG if index too big
+ *     %SALRET_NOT_IMPLEMENTED if running on older PROM
+ *     ??? if nasid invalid OR banner buffer not large enough
+ */
+static inline int
+ia64_sn_get_fit_compt(u64 nasid, u64 index, void *fitentry, void *banbuf,
+                     u64 banlen)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_NOLOCK(rv, SN_SAL_GET_FIT_COMPT, nasid, index, fitentry,
+                       banbuf, banlen, 0, 0);
+       return (int) rv.status;
+}
+
+/*
+ * Initialize the SAL components of the system controller
+ * communication driver; specifically pass in a sizable buffer that
+ * can be used for allocation of subchannel queues as new subchannels
+ * are opened.  "buf" points to the buffer, and "len" specifies its
+ * length.
+ */
+static inline int
+ia64_sn_irtr_init(nasid_t nasid, void *buf, int len)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_REENTRANT(rv, SN_SAL_IROUTER_OP, SAL_IROUTER_INIT,
+                          (u64) nasid, (u64) buf, (u64) len, 0, 0, 0);
+       return (int) rv.status;
+}
+
+/*
+ * Returns the nasid, subnode & slice corresponding to a SAPIC ID
+ *
+ *  In:
+ *     arg0 - SN_SAL_GET_SAPIC_INFO
+ *     arg1 - sapicid (lid >> 16) 
+ *  Out:
+ *     v0 - nasid
+ *     v1 - subnode
+ *     v2 - slice
+ */
+static inline u64
+ia64_sn_get_sapic_info(int sapicid, int *nasid, int *subnode, int *slice)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_GET_SAPIC_INFO, sapicid, 0, 0, 0, 0, 
0, 0);
+
+/***** BEGIN HACK - temp til old proms no longer supported ********/
+       if (ret_stuff.status == SALRET_NOT_IMPLEMENTED) {
+               if (nasid) *nasid = sapicid & 0xfff;
+               if (subnode) *subnode = (sapicid >> 13) & 1;
+               if (slice) *slice = (sapicid >> 12) & 3;
+               return 0;
+       }
+/***** END HACK *******/
+
+       if (ret_stuff.status < 0)
+               return ret_stuff.status;
+
+       if (nasid) *nasid = (int) ret_stuff.v0;
+       if (subnode) *subnode = (int) ret_stuff.v1;
+       if (slice) *slice = (int) ret_stuff.v2;
+       return 0;
+}
+ 
+/*
+ * Returns information about the HUB/SHUB.
+ *  In:
+ *     arg0 - SN_SAL_GET_HUB_INFO
+ *     arg1 - 0 (other values reserved for future use)
+ *  Out:
+ *     v0 - shub type (0=shub1, 1=shub2)
+ *     v1 - masid mask (ex., 0x7ff for 11 bit nasid)
+ *     v2 - bit position of low nasid bit
+ */
+static inline u64
+ia64_sn_get_hub_info(int fc, u64 *arg1, u64 *arg2, u64 *arg3)
+{
+       struct ia64_sal_retval ret_stuff;
+
+       ret_stuff.status = 0;
+       ret_stuff.v0 = 0;
+       ret_stuff.v1 = 0;
+       ret_stuff.v2 = 0;
+       SAL_CALL_NOLOCK(ret_stuff, SN_SAL_GET_HUB_INFO, fc, 0, 0, 0, 0, 0, 0);
+
+/***** BEGIN HACK - temp til old proms no longer supported ********/
+       if (ret_stuff.status == SALRET_NOT_IMPLEMENTED) {
+               if (arg1) *arg1 = 0;
+               if (arg2) *arg2 = 0x7ff;
+               if (arg3) *arg3 = 38;
+               return 0;
+       }
+/***** END HACK *******/
+
+       if (ret_stuff.status < 0)
+               return ret_stuff.status;
+
+       if (arg1) *arg1 = ret_stuff.v0;
+       if (arg2) *arg2 = ret_stuff.v1;
+       if (arg3) *arg3 = ret_stuff.v2;
+       return 0;
+}
+ 
+/*
+ * This is the access point to the Altix PROM hardware performance
+ * and status monitoring interface. For info on using this, see
+ * include/asm-ia64/sn/sn2/sn_hwperf.h
+ */
+static inline int
+ia64_sn_hwperf_op(nasid_t nasid, u64 opcode, u64 a0, u64 a1, u64 a2,
+                  u64 a3, u64 a4, int *v0)
+{
+       struct ia64_sal_retval rv;
+       SAL_CALL_NOLOCK(rv, SN_SAL_HWPERF_OP, (u64)nasid,
+               opcode, a0, a1, a2, a3, a4);
+       if (v0)
+               *v0 = (int) rv.v0;
+       return (int) rv.status;
+}
+#endif /* !XEN */
+#endif /* _ASM_IA64_SN_SN_SAL_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/system.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/system.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,299 @@
+#ifndef _ASM_IA64_SYSTEM_H
+#define _ASM_IA64_SYSTEM_H
+
+/*
+ * System defines. Note that this is included both from .c and .S
+ * files, so it does only defines, not any C code.  This is based
+ * on information published in the Processor Abstraction Layer
+ * and the System Abstraction Layer manual.
+ *
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Asit Mallick <asit.k.mallick@xxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ */
+#include <linux/config.h>
+
+#include <asm/kregs.h>
+#include <asm/page.h>
+#include <asm/pal.h>
+#include <asm/percpu.h>
+#ifdef XEN
+#include <asm/xensystem.h>
+#endif
+
+#define GATE_ADDR              __IA64_UL_CONST(0xa000000000000000)
+/*
+ * 0xa000000000000000+2*PERCPU_PAGE_SIZE
+ * - 0xa000000000000000+3*PERCPU_PAGE_SIZE remain unmapped (guard page)
+ */
+#ifndef XEN
+#define KERNEL_START            __IA64_UL_CONST(0xa000000100000000)
+#define PERCPU_ADDR            (-PERCPU_PAGE_SIZE)
+#endif
+
+#ifndef __ASSEMBLY__
+
+#include <linux/kernel.h>
+#include <linux/types.h>
+
+struct pci_vector_struct {
+       __u16 segment;  /* PCI Segment number */
+       __u16 bus;      /* PCI Bus number */
+       __u32 pci_id;   /* ACPI split 16 bits device, 16 bits function (see 
section 6.1.1) */
+       __u8 pin;       /* PCI PIN (0 = A, 1 = B, 2 = C, 3 = D) */
+       __u32 irq;      /* IRQ assigned */
+};
+
+extern struct ia64_boot_param {
+       __u64 command_line;             /* physical address of command line 
arguments */
+       __u64 efi_systab;               /* physical address of EFI system table 
*/
+       __u64 efi_memmap;               /* physical address of EFI memory map */
+       __u64 efi_memmap_size;          /* size of EFI memory map */
+       __u64 efi_memdesc_size;         /* size of an EFI memory map descriptor 
*/
+       __u32 efi_memdesc_version;      /* memory descriptor version */
+       struct {
+               __u16 num_cols; /* number of columns on console output device */
+               __u16 num_rows; /* number of rows on console output device */
+               __u16 orig_x;   /* cursor's x position */
+               __u16 orig_y;   /* cursor's y position */
+       } console_info;
+       __u64 fpswa;            /* physical address of the fpswa interface */
+       __u64 initrd_start;
+       __u64 initrd_size;
+} *ia64_boot_param;
+
+/*
+ * Macros to force memory ordering.  In these descriptions, "previous"
+ * and "subsequent" refer to program order; "visible" means that all
+ * architecturally visible effects of a memory access have occurred
+ * (at a minimum, this means the memory has been read or written).
+ *
+ *   wmb():    Guarantees that all preceding stores to memory-
+ *             like regions are visible before any subsequent
+ *             stores and that all following stores will be
+ *             visible only after all previous stores.
+ *   rmb():    Like wmb(), but for reads.
+ *   mb():     wmb()/rmb() combo, i.e., all previous memory
+ *             accesses are visible before all subsequent
+ *             accesses and vice versa.  This is also known as
+ *             a "fence."
+ *
+ * Note: "mb()" and its variants cannot be used as a fence to order
+ * accesses to memory mapped I/O registers.  For that, mf.a needs to
+ * be used.  However, we don't want to always use mf.a because (a)
+ * it's (presumably) much slower than mf and (b) mf.a is supported for
+ * sequential memory pages only.
+ */
+#define mb()   ia64_mf()
+#define rmb()  mb()
+#define wmb()  mb()
+#define read_barrier_depends() do { } while(0)
+
+#ifdef CONFIG_SMP
+# define smp_mb()      mb()
+# define smp_rmb()     rmb()
+# define smp_wmb()     wmb()
+# define smp_read_barrier_depends()    read_barrier_depends()
+#else
+# define smp_mb()      barrier()
+# define smp_rmb()     barrier()
+# define smp_wmb()     barrier()
+# define smp_read_barrier_depends()    do { } while(0)
+#endif
+
+/*
+ * XXX check on these---I suspect what Linus really wants here is
+ * acquire vs release semantics but we can't discuss this stuff with
+ * Linus just yet.  Grrr...
+ */
+#define set_mb(var, value)     do { (var) = (value); mb(); } while (0)
+#define set_wmb(var, value)    do { (var) = (value); mb(); } while (0)
+
+#define safe_halt()         ia64_pal_halt_light()    /* PAL_HALT_LIGHT */
+
+/*
+ * The group barrier in front of the rsm & ssm are necessary to ensure
+ * that none of the previous instructions in the same group are
+ * affected by the rsm/ssm.
+ */
+/* For spinlocks etc */
+
+/*
+ * - clearing psr.i is implicitly serialized (visible by next insn)
+ * - setting psr.i requires data serialization
+ * - we need a stop-bit before reading PSR because we sometimes
+ *   write a floating-point register right before reading the PSR
+ *   and that writes to PSR.mfl
+ */
+#define __local_irq_save(x)                    \
+do {                                           \
+       ia64_stop();                            \
+       (x) = ia64_getreg(_IA64_REG_PSR);       \
+       ia64_stop();                            \
+       ia64_rsm(IA64_PSR_I);                   \
+} while (0)
+
+#define __local_irq_disable()                  \
+do {                                           \
+       ia64_stop();                            \
+       ia64_rsm(IA64_PSR_I);                   \
+} while (0)
+
+#define __local_irq_restore(x) ia64_intrin_local_irq_restore((x) & IA64_PSR_I)
+
+#ifdef CONFIG_IA64_DEBUG_IRQ
+
+  extern unsigned long last_cli_ip;
+
+# define __save_ip()           last_cli_ip = ia64_getreg(_IA64_REG_IP)
+
+# define local_irq_save(x)                                     \
+do {                                                           \
+       unsigned long psr;                                      \
+                                                               \
+       __local_irq_save(psr);                                  \
+       if (psr & IA64_PSR_I)                                   \
+               __save_ip();                                    \
+       (x) = psr;                                              \
+} while (0)
+
+# define local_irq_disable()   do { unsigned long x; local_irq_save(x); } 
while (0)
+
+# define local_irq_restore(x)                                  \
+do {                                                           \
+       unsigned long old_psr, psr = (x);                       \
+                                                               \
+       local_save_flags(old_psr);                              \
+       __local_irq_restore(psr);                               \
+       if ((old_psr & IA64_PSR_I) && !(psr & IA64_PSR_I))      \
+               __save_ip();                                    \
+} while (0)
+
+#else /* !CONFIG_IA64_DEBUG_IRQ */
+# define local_irq_save(x)     __local_irq_save(x)
+# define local_irq_disable()   __local_irq_disable()
+# define local_irq_restore(x)  __local_irq_restore(x)
+#endif /* !CONFIG_IA64_DEBUG_IRQ */
+
+#define local_irq_enable()     ({ ia64_stop(); ia64_ssm(IA64_PSR_I); 
ia64_srlz_d(); })
+#define local_save_flags(flags)        ({ ia64_stop(); (flags) = 
ia64_getreg(_IA64_REG_PSR); })
+
+#define irqs_disabled()                                \
+({                                             \
+       unsigned long __ia64_id_flags;          \
+       local_save_flags(__ia64_id_flags);      \
+       (__ia64_id_flags & IA64_PSR_I) == 0;    \
+})
+
+#ifdef __KERNEL__
+
+#define prepare_to_switch()    do { } while(0)
+
+#ifdef CONFIG_IA32_SUPPORT
+# define IS_IA32_PROCESS(regs) (ia64_psr(regs)->is != 0)
+#else
+# define IS_IA32_PROCESS(regs)         0
+struct task_struct;
+static inline void ia32_save_state(struct task_struct *t 
__attribute__((unused))){}
+static inline void ia32_load_state(struct task_struct *t 
__attribute__((unused))){}
+#endif
+
+/*
+ * Context switch from one thread to another.  If the two threads have
+ * different address spaces, schedule() has already taken care of
+ * switching to the new address space by calling switch_mm().
+ *
+ * Disabling access to the fph partition and the debug-register
+ * context switch MUST be done before calling ia64_switch_to() since a
+ * newly created thread returns directly to
+ * ia64_ret_from_syscall_clear_r8.
+ */
+extern struct task_struct *ia64_switch_to (void *next_task);
+
+struct task_struct;
+
+extern void ia64_save_extra (struct task_struct *task);
+extern void ia64_load_extra (struct task_struct *task);
+
+#ifdef CONFIG_PERFMON
+  DECLARE_PER_CPU(unsigned long, pfm_syst_info);
+# define PERFMON_IS_SYSWIDE() (__get_cpu_var(pfm_syst_info) & 0x1)
+#else
+# define PERFMON_IS_SYSWIDE() (0)
+#endif
+
+#ifndef XEN
+#define IA64_HAS_EXTRA_STATE(t)                                                
        \
+       ((t)->thread.flags & (IA64_THREAD_DBG_VALID|IA64_THREAD_PM_VALID)       
\
+        || IS_IA32_PROCESS(ia64_task_regs(t)) || PERFMON_IS_SYSWIDE())
+
+#define __switch_to(prev,next,last) do {                                       
                 \
+       if (IA64_HAS_EXTRA_STATE(prev))                                         
                 \
+               ia64_save_extra(prev);                                          
                 \
+       if (IA64_HAS_EXTRA_STATE(next))                                         
                 \
+               ia64_load_extra(next);                                          
                 \
+       ia64_psr(ia64_task_regs(next))->dfh = !ia64_is_local_fpu_owner(next);   
                 \
+       (last) = ia64_switch_to((next));                                        
                 \
+} while (0)
+#endif 
+
+#ifdef CONFIG_SMP
+/*
+ * In the SMP case, we save the fph state when context-switching away from a 
thread that
+ * modified fph.  This way, when the thread gets scheduled on another CPU, the 
CPU can
+ * pick up the state from task->thread.fph, avoiding the complication of 
having to fetch
+ * the latest fph state from another CPU.  In other words: eager save, lazy 
restore.
+ */
+# define switch_to(prev,next,last) do {                                        
        \
+       if (ia64_psr(ia64_task_regs(prev))->mfh && 
ia64_is_local_fpu_owner(prev)) {                             \
+               ia64_psr(ia64_task_regs(prev))->mfh = 0;                        
\
+               (prev)->thread.flags |= IA64_THREAD_FPH_VALID;                  
\
+               __ia64_save_fpu((prev)->thread.fph);                            
\
+       }                                                                       
\
+       __switch_to(prev, next, last);                                          
\
+} while (0)
+#else
+# define switch_to(prev,next,last)     __switch_to(prev, next, last)
+#endif
+
+/*
+ * On IA-64, we don't want to hold the runqueue's lock during the low-level 
context-switch,
+ * because that could cause a deadlock.  Here is an example by Erich Focht:
+ *
+ * Example:
+ * CPU#0:
+ * schedule()
+ *    -> spin_lock_irq(&rq->lock)
+ *    -> context_switch()
+ *       -> wrap_mmu_context()
+ *          -> read_lock(&tasklist_lock)
+ *
+ * CPU#1:
+ * sys_wait4() or release_task() or forget_original_parent()
+ *    -> write_lock(&tasklist_lock)
+ *    -> do_notify_parent()
+ *       -> wake_up_parent()
+ *          -> try_to_wake_up()
+ *             -> spin_lock_irq(&parent_rq->lock)
+ *
+ * If the parent's rq happens to be on CPU#0, we'll wait for the rq->lock
+ * of that CPU which will not be released, because there we wait for the
+ * tasklist_lock to become available.
+ */
+#define prepare_arch_switch(rq, next)          \
+do {                                           \
+       spin_lock(&(next)->switch_lock);        \
+       spin_unlock(&(rq)->lock);               \
+} while (0)
+#define finish_arch_switch(rq, prev)   spin_unlock_irq(&(prev)->switch_lock)
+#define task_running(rq, p)            ((rq)->curr == (p) || 
spin_is_locked(&(p)->switch_lock))
+
+#define ia64_platform_is(x) (strcmp(x, platform_name) == 0)
+
+void cpu_idle_wait(void);
+#endif /* __KERNEL__ */
+
+#endif /* __ASSEMBLY__ */
+
+#endif /* _ASM_IA64_SYSTEM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux-xen/asm/types.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/types.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,104 @@
+#ifndef _ASM_IA64_TYPES_H
+#define _ASM_IA64_TYPES_H
+#ifdef XEN
+#ifndef __ASSEMBLY__
+typedef unsigned long ssize_t;
+typedef unsigned long size_t;
+typedef long long loff_t;
+#endif
+#endif
+
+/*
+ * This file is never included by application software unless explicitly 
requested (e.g.,
+ * via linux/types.h) in which case the application is Linux specific so 
(user-) name
+ * space pollution is not a major issue.  However, for interoperability, 
libraries still
+ * need to be careful to avoid a name clashes.
+ *
+ * Based on <asm-alpha/types.h>.
+ *
+ * Modified 1998-2000, 2002
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+#ifdef __ASSEMBLY__
+# define __IA64_UL(x)          (x)
+# define __IA64_UL_CONST(x)    x
+
+# ifdef __KERNEL__
+#  define BITS_PER_LONG 64
+# endif
+
+#else
+# define __IA64_UL(x)          ((unsigned long)(x))
+# define __IA64_UL_CONST(x)    x##UL
+
+typedef unsigned int umode_t;
+
+/*
+ * __xx is ok: it doesn't pollute the POSIX namespace. Use these in the
+ * header files exported to user space
+ */
+
+typedef __signed__ char __s8;
+typedef unsigned char __u8;
+
+typedef __signed__ short __s16;
+typedef unsigned short __u16;
+
+typedef __signed__ int __s32;
+typedef unsigned int __u32;
+
+typedef __signed__ long __s64;
+typedef unsigned long __u64;
+
+/*
+ * These aren't exported outside the kernel to avoid name space clashes
+ */
+# ifdef __KERNEL__
+
+typedef __s8 s8;
+typedef __u8 u8;
+
+typedef __s16 s16;
+typedef __u16 u16;
+
+typedef __s32 s32;
+typedef __u32 u32;
+
+typedef __s64 s64;
+typedef __u64 u64;
+
+#ifdef XEN
+/*
+ * Below are truly Linux-specific types that should never collide with
+ * any application/library that wants linux/types.h.
+ */
+
+#ifdef __CHECKER__
+#define __bitwise __attribute__((bitwise))
+#else
+#define __bitwise
+#endif
+
+typedef __u16 __bitwise __le16;
+typedef __u16 __bitwise __be16;
+typedef __u32 __bitwise __le32;
+typedef __u32 __bitwise __be32;
+#if defined(__GNUC__) && !defined(__STRICT_ANSI__)
+typedef __u64 __bitwise __le64;
+typedef __u64 __bitwise __be64;
+#endif
+#endif
+
+#define BITS_PER_LONG 64
+
+/* DMA addresses are 64-bits wide, in general.  */
+
+typedef u64 dma_addr_t;
+
+typedef unsigned short kmem_bufctl_t;
+
+# endif /* __KERNEL__ */
+#endif /* !__ASSEMBLY__ */
+
+#endif /* _ASM_IA64_TYPES_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/asm/uaccess.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/asm/uaccess.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,381 @@
+#ifndef _ASM_IA64_UACCESS_H
+#define _ASM_IA64_UACCESS_H
+
+/*
+ * This file defines various macros to transfer memory areas across
+ * the user/kernel boundary.  This needs to be done carefully because
+ * this code is executed in kernel mode and uses user-specified
+ * addresses.  Thus, we need to be careful not to let the user to
+ * trick us into accessing kernel memory that would normally be
+ * inaccessible.  This code is also fairly performance sensitive,
+ * so we want to spend as little time doing safety checks as
+ * possible.
+ *
+ * To make matters a bit more interesting, these macros sometimes also
+ * called from within the kernel itself, in which case the address
+ * validity check must be skipped.  The get_fs() macro tells us what
+ * to do: if get_fs()==USER_DS, checking is performed, if
+ * get_fs()==KERNEL_DS, checking is bypassed.
+ *
+ * Note that even if the memory area specified by the user is in a
+ * valid address range, it is still possible that we'll get a page
+ * fault while accessing it.  This is handled by filling out an
+ * exception handler fixup entry for each instruction that has the
+ * potential to fault.  When such a fault occurs, the page fault
+ * handler checks to see whether the faulting instruction has a fixup
+ * associated and, if so, sets r8 to -EFAULT and clears r9 to 0 and
+ * then resumes execution at the continuation point.
+ *
+ * Based on <asm-alpha/uaccess.h>.
+ *
+ * Copyright (C) 1998, 1999, 2001-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#ifdef CONFIG_VTI
+#include <asm/vmx_uaccess.h>
+#else // CONFIG_VTI
+
+#include <linux/compiler.h>
+#include <linux/errno.h>
+#include <linux/sched.h>
+
+#include <asm/intrinsics.h>
+#include <asm/pgtable.h>
+
+/*
+ * For historical reasons, the following macros are grossly misnamed:
+ */
+#define KERNEL_DS      ((mm_segment_t) { ~0UL })               /* cf. 
access_ok() */
+#define USER_DS                ((mm_segment_t) { TASK_SIZE-1 })        /* cf. 
access_ok() */
+
+#define VERIFY_READ    0
+#define VERIFY_WRITE   1
+
+#define get_ds()  (KERNEL_DS)
+#define get_fs()  (current_thread_info()->addr_limit)
+#define set_fs(x) (current_thread_info()->addr_limit = (x))
+
+#define segment_eq(a, b)       ((a).seg == (b).seg)
+
+/*
+ * When accessing user memory, we need to make sure the entire area really is 
in
+ * user-level space.  In order to do this efficiently, we make sure that the 
page at
+ * address TASK_SIZE is never valid.  We also need to make sure that the 
address doesn't
+ * point inside the virtually mapped linear page table.
+ */
+#ifdef XEN
+/* VT-i reserves bit 60 for the VMM; guest addresses have bit 60 = bit 59 */
+#define IS_VMM_ADDRESS(addr) ((((addr) >> 60) ^ ((addr) >> 59)) & 1)
+#define __access_ok(addr, size, segment) (!IS_VMM_ADDRESS((unsigned 
long)(addr)))
+#else
+#define __access_ok(addr, size, segment)                                       
        \
+({                                                                             
        \
+       __chk_user_ptr(addr);                                                   
        \
+       (likely((unsigned long) (addr) <= (segment).seg)                        
        \
+        && ((segment).seg == KERNEL_DS.seg                                     
        \
+            || likely(REGION_OFFSET((unsigned long) (addr)) < 
RGN_MAP_LIMIT)));        \
+})
+#endif
+#define access_ok(type, addr, size)    __access_ok((addr), (size), get_fs())
+
+static inline int
+verify_area (int type, const void __user *addr, unsigned long size)
+{
+       return access_ok(type, addr, size) ? 0 : -EFAULT;
+}
+
+/*
+ * These are the main single-value transfer routines.  They automatically
+ * use the right size if we just have the right pointer type.
+ *
+ * Careful to not
+ * (a) re-use the arguments for side effects (sizeof/typeof is ok)
+ * (b) require any knowledge of processes at this stage
+ */
+#define put_user(x, ptr)       __put_user_check((__typeof__(*(ptr))) (x), 
(ptr), sizeof(*(ptr)), get_fs())
+#define get_user(x, ptr)       __get_user_check((x), (ptr), sizeof(*(ptr)), 
get_fs())
+
+/*
+ * The "__xxx" versions do not do address space checking, useful when
+ * doing multiple accesses to the same area (the programmer has to do the
+ * checks by hand with "access_ok()")
+ */
+#define __put_user(x, ptr)     __put_user_nocheck((__typeof__(*(ptr))) (x), 
(ptr), sizeof(*(ptr)))
+#define __get_user(x, ptr)     __get_user_nocheck((x), (ptr), sizeof(*(ptr)))
+
+extern long __put_user_unaligned_unknown (void);
+
+#define __put_user_unaligned(x, ptr)                                           
                \
+({                                                                             
                \
+       long __ret;                                                             
                \
+       switch (sizeof(*(ptr))) {                                               
                \
+               case 1: __ret = __put_user((x), (ptr)); break;                  
                \
+               case 2: __ret = (__put_user((x), (u8 __user *)(ptr)))           
                \
+                       | (__put_user((x) >> 8, ((u8 __user *)(ptr) + 1))); 
break;              \
+               case 4: __ret = (__put_user((x), (u16 __user *)(ptr)))          
                \
+                       | (__put_user((x) >> 16, ((u16 __user *)(ptr) + 1))); 
break;            \
+               case 8: __ret = (__put_user((x), (u32 __user *)(ptr)))          
                \
+                       | (__put_user((x) >> 32, ((u32 __user *)(ptr) + 1))); 
break;            \
+               default: __ret = __put_user_unaligned_unknown();                
                \
+       }                                                                       
                \
+       __ret;                                                                  
                \
+})
+
+extern long __get_user_unaligned_unknown (void);
+
+#define __get_user_unaligned(x, ptr)                                           
                \
+({                                                                             
                \
+       long __ret;                                                             
                \
+       switch (sizeof(*(ptr))) {                                               
                \
+               case 1: __ret = __get_user((x), (ptr)); break;                  
                \
+               case 2: __ret = (__get_user((x), (u8 __user *)(ptr)))           
                \
+                       | (__get_user((x) >> 8, ((u8 __user *)(ptr) + 1))); 
break;              \
+               case 4: __ret = (__get_user((x), (u16 __user *)(ptr)))          
                \
+                       | (__get_user((x) >> 16, ((u16 __user *)(ptr) + 1))); 
break;            \
+               case 8: __ret = (__get_user((x), (u32 __user *)(ptr)))          
                \
+                       | (__get_user((x) >> 32, ((u32 __user *)(ptr) + 1))); 
break;            \
+               default: __ret = __get_user_unaligned_unknown();                
                \
+       }                                                                       
                \
+       __ret;                                                                  
                \
+})
+
+#ifdef ASM_SUPPORTED
+  struct __large_struct { unsigned long buf[100]; };
+# define __m(x) (*(struct __large_struct __user *)(x))
+
+/* We need to declare the __ex_table section before we can use it in .xdata.  
*/
+asm (".section \"__ex_table\", \"a\"\n\t.previous");
+
+# define __get_user_size(val, addr, n, err)                                    
                \
+do {                                                                           
                \
+       register long __gu_r8 asm ("r8") = 0;                                   
                \
+       register long __gu_r9 asm ("r9");                                       
                \
+       asm ("\n[1:]\tld"#n" %0=%2%P2\t// %0 and %1 get overwritten by 
exception handler\n"     \
+            "\t.xdata4 \"__ex_table\", 1b-., 1f-.+4\n"                         
                \
+            "[1:]"                                                             
                \
+            : "=r"(__gu_r9), "=r"(__gu_r8) : "m"(__m(addr)), "1"(__gu_r8));    
                \
+       (err) = __gu_r8;                                                        
                \
+       (val) = __gu_r9;                                                        
                \
+} while (0)
+
+/*
+ * The "__put_user_size()" macro tells gcc it reads from memory instead of 
writing it.  This
+ * is because they do not write to any memory gcc knows about, so there are no 
aliasing
+ * issues.
+ */
+# define __put_user_size(val, addr, n, err)                                    
                \
+do {                                                                           
                \
+       register long __pu_r8 asm ("r8") = 0;                                   
                \
+       asm volatile ("\n[1:]\tst"#n" %1=%r2%P1\t// %0 gets overwritten by 
exception handler\n" \
+                     "\t.xdata4 \"__ex_table\", 1b-., 1f-.\n"                  
                \
+                     "[1:]"                                                    
                \
+                     : "=r"(__pu_r8) : "m"(__m(addr)), "rO"(val), 
"0"(__pu_r8));               \
+       (err) = __pu_r8;                                                        
                \
+} while (0)
+
+#else /* !ASM_SUPPORTED */
+# define RELOC_TYPE    2       /* ip-rel */
+# define __get_user_size(val, addr, n, err)                            \
+do {                                                                   \
+       __ld_user("__ex_table", (unsigned long) addr, n, RELOC_TYPE);   \
+       (err) = ia64_getreg(_IA64_REG_R8);                              \
+       (val) = ia64_getreg(_IA64_REG_R9);                              \
+} while (0)
+# define __put_user_size(val, addr, n, err)                                    
                \
+do {                                                                           
                \
+       __st_user("__ex_table", (unsigned long) addr, n, RELOC_TYPE, (unsigned 
long) (val));    \
+       (err) = ia64_getreg(_IA64_REG_R8);                                      
                \
+} while (0)
+#endif /* !ASM_SUPPORTED */
+
+extern void __get_user_unknown (void);
+
+/*
+ * Evaluating arguments X, PTR, SIZE, and SEGMENT may involve 
subroutine-calls, which
+ * could clobber r8 and r9 (among others).  Thus, be careful not to evaluate 
it while
+ * using r8/r9.
+ */
+#define __do_get_user(check, x, ptr, size, segment)                            
        \
+({                                                                             
        \
+       const __typeof__(*(ptr)) __user *__gu_ptr = (ptr);                      
        \
+       __typeof__ (size) __gu_size = (size);                                   
        \
+       long __gu_err = -EFAULT, __gu_val = 0;                                  
        \
+                                                                               
        \
+       if (!check || __access_ok(__gu_ptr, size, segment))                     
        \
+               switch (__gu_size) {                                            
        \
+                     case 1: __get_user_size(__gu_val, __gu_ptr, 1, __gu_err); 
break;  \
+                     case 2: __get_user_size(__gu_val, __gu_ptr, 2, __gu_err); 
break;  \
+                     case 4: __get_user_size(__gu_val, __gu_ptr, 4, __gu_err); 
break;  \
+                     case 8: __get_user_size(__gu_val, __gu_ptr, 8, __gu_err); 
break;  \
+                     default: __get_user_unknown(); break;                     
        \
+               }                                                               
        \
+       (x) = (__typeof__(*(__gu_ptr))) __gu_val;                               
        \
+       __gu_err;                                                               
        \
+})
+
+#define __get_user_nocheck(x, ptr, size)       __do_get_user(0, x, ptr, size, 
KERNEL_DS)
+#define __get_user_check(x, ptr, size, segment)        __do_get_user(1, x, 
ptr, size, segment)
+
+extern void __put_user_unknown (void);
+
+/*
+ * Evaluating arguments X, PTR, SIZE, and SEGMENT may involve 
subroutine-calls, which
+ * could clobber r8 (among others).  Thus, be careful not to evaluate them 
while using r8.
+ */
+#define __do_put_user(check, x, ptr, size, segment)                            
        \
+({                                                                             
        \
+       __typeof__ (x) __pu_x = (x);                                            
        \
+       __typeof__ (*(ptr)) __user *__pu_ptr = (ptr);                           
        \
+       __typeof__ (size) __pu_size = (size);                                   
        \
+       long __pu_err = -EFAULT;                                                
        \
+                                                                               
        \
+       if (!check || __access_ok(__pu_ptr, __pu_size, segment))                
        \
+               switch (__pu_size) {                                            
        \
+                     case 1: __put_user_size(__pu_x, __pu_ptr, 1, __pu_err); 
break;    \
+                     case 2: __put_user_size(__pu_x, __pu_ptr, 2, __pu_err); 
break;    \
+                     case 4: __put_user_size(__pu_x, __pu_ptr, 4, __pu_err); 
break;    \
+                     case 8: __put_user_size(__pu_x, __pu_ptr, 8, __pu_err); 
break;    \
+                     default: __put_user_unknown(); break;                     
        \
+               }                                                               
        \
+       __pu_err;                                                               
        \
+})
+
+#define __put_user_nocheck(x, ptr, size)       __do_put_user(0, x, ptr, size, 
KERNEL_DS)
+#define __put_user_check(x, ptr, size, segment)        __do_put_user(1, x, 
ptr, size, segment)
+
+/*
+ * Complex access routines
+ */
+extern unsigned long __must_check __copy_user (void __user *to, const void 
__user *from,
+                                              unsigned long count);
+
+static inline unsigned long
+__copy_to_user (void __user *to, const void *from, unsigned long count)
+{
+       return __copy_user(to, (void __user *) from, count);
+}
+
+static inline unsigned long
+__copy_from_user (void *to, const void __user *from, unsigned long count)
+{
+       return __copy_user((void __user *) to, from, count);
+}
+
+#define __copy_to_user_inatomic                __copy_to_user
+#define __copy_from_user_inatomic      __copy_from_user
+#define copy_to_user(to, from, n)                                              
        \
+({                                                                             
        \
+       void __user *__cu_to = (to);                                            
        \
+       const void *__cu_from = (from);                                         
        \
+       long __cu_len = (n);                                                    
        \
+                                                                               
        \
+       if (__access_ok(__cu_to, __cu_len, get_fs()))                           
        \
+               __cu_len = __copy_user(__cu_to, (void __user *) __cu_from, 
__cu_len);   \
+       __cu_len;                                                               
        \
+})
+
+#define copy_from_user(to, from, n)                                            
        \
+({                                                                             
        \
+       void *__cu_to = (to);                                                   
        \
+       const void __user *__cu_from = (from);                                  
        \
+       long __cu_len = (n);                                                    
        \
+                                                                               
        \
+       __chk_user_ptr(__cu_from);                                              
        \
+       if (__access_ok(__cu_from, __cu_len, get_fs()))                         
        \
+               __cu_len = __copy_user((void __user *) __cu_to, __cu_from, 
__cu_len);   \
+       __cu_len;                                                               
        \
+})
+
+#define __copy_in_user(to, from, size) __copy_user((to), (from), (size))
+
+static inline unsigned long
+copy_in_user (void __user *to, const void __user *from, unsigned long n)
+{
+       if (likely(access_ok(VERIFY_READ, from, n) && access_ok(VERIFY_WRITE, 
to, n)))
+               n = __copy_user(to, from, n);
+       return n;
+}
+
+extern unsigned long __do_clear_user (void __user *, unsigned long);
+
+#define __clear_user(to, n)            __do_clear_user(to, n)
+
+#define clear_user(to, n)                                      \
+({                                                             \
+       unsigned long __cu_len = (n);                           \
+       if (__access_ok(to, __cu_len, get_fs()))                \
+               __cu_len = __do_clear_user(to, __cu_len);       \
+       __cu_len;                                               \
+})
+
+
+/*
+ * Returns: -EFAULT if exception before terminator, N if the entire buffer 
filled, else
+ * strlen.
+ */
+extern long __must_check __strncpy_from_user (char *to, const char __user 
*from, long to_len);
+
+#define strncpy_from_user(to, from, n)                                 \
+({                                                                     \
+       const char __user * __sfu_from = (from);                        \
+       long __sfu_ret = -EFAULT;                                       \
+       if (__access_ok(__sfu_from, 0, get_fs()))                       \
+               __sfu_ret = __strncpy_from_user((to), __sfu_from, (n)); \
+       __sfu_ret;                                                      \
+})
+
+/* Returns: 0 if bad, string length+1 (memory size) of string if ok */
+extern unsigned long __strlen_user (const char __user *);
+
+#define strlen_user(str)                               \
+({                                                     \
+       const char __user *__su_str = (str);            \
+       unsigned long __su_ret = 0;                     \
+       if (__access_ok(__su_str, 0, get_fs()))         \
+               __su_ret = __strlen_user(__su_str);     \
+       __su_ret;                                       \
+})
+
+/*
+ * Returns: 0 if exception before NUL or reaching the supplied limit
+ * (N), a value greater than N if the limit would be exceeded, else
+ * strlen.
+ */
+extern unsigned long __strnlen_user (const char __user *, long);
+
+#define strnlen_user(str, len)                                 \
+({                                                             \
+       const char __user *__su_str = (str);                    \
+       unsigned long __su_ret = 0;                             \
+       if (__access_ok(__su_str, 0, get_fs()))                 \
+               __su_ret = __strnlen_user(__su_str, len);       \
+       __su_ret;                                               \
+})
+
+#endif // CONFIG_VTI
+/* Generic code can't deal with the location-relative format that we use for 
compactness.  */
+#define ARCH_HAS_SORT_EXTABLE
+#define ARCH_HAS_SEARCH_EXTABLE
+
+struct exception_table_entry {
+       int addr;       /* location-relative address of insn this fixup is for 
*/
+       int cont;       /* location-relative continuation addr.; if bit 2 is 
set, r9 is set to 0 */
+};
+
+extern void ia64_handle_exception (struct pt_regs *regs, const struct 
exception_table_entry *e);
+extern const struct exception_table_entry *search_exception_tables (unsigned 
long addr);
+
+static inline int
+ia64_done_with_exception (struct pt_regs *regs)
+{
+       const struct exception_table_entry *e;
+       e = search_exception_tables(regs->cr_iip + ia64_psr(regs)->ri);
+       if (e) {
+               ia64_handle_exception(regs, e);
+               return 1;
+       }
+       return 0;
+}
+
+#endif /* _ASM_IA64_UACCESS_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/linux/cpumask.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/linux/cpumask.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,379 @@
+#ifndef __LINUX_CPUMASK_H
+#define __LINUX_CPUMASK_H
+
+/*
+ * Cpumasks provide a bitmap suitable for representing the
+ * set of CPU's in a system, one bit position per CPU number.
+ *
+ * See detailed comments in the file linux/bitmap.h describing the
+ * data type on which these cpumasks are based.
+ *
+ * For details of cpumask_scnprintf() and cpumask_parse(),
+ * see bitmap_scnprintf() and bitmap_parse() in lib/bitmap.c.
+ *
+ * The available cpumask operations are:
+ *
+ * void cpu_set(cpu, mask)             turn on bit 'cpu' in mask
+ * void cpu_clear(cpu, mask)           turn off bit 'cpu' in mask
+ * void cpus_setall(mask)              set all bits
+ * void cpus_clear(mask)               clear all bits
+ * int cpu_isset(cpu, mask)            true iff bit 'cpu' set in mask
+ * int cpu_test_and_set(cpu, mask)     test and set bit 'cpu' in mask
+ *
+ * void cpus_and(dst, src1, src2)      dst = src1 & src2  [intersection]
+ * void cpus_or(dst, src1, src2)       dst = src1 | src2  [union]
+ * void cpus_xor(dst, src1, src2)      dst = src1 ^ src2
+ * void cpus_andnot(dst, src1, src2)   dst = src1 & ~src2
+ * void cpus_complement(dst, src)      dst = ~src
+ *
+ * int cpus_equal(mask1, mask2)                Does mask1 == mask2?
+ * int cpus_intersects(mask1, mask2)   Do mask1 and mask2 intersect?
+ * int cpus_subset(mask1, mask2)       Is mask1 a subset of mask2?
+ * int cpus_empty(mask)                        Is mask empty (no bits sets)?
+ * int cpus_full(mask)                 Is mask full (all bits sets)?
+ * int cpus_weight(mask)               Hamming weigh - number of set bits
+ *
+ * void cpus_shift_right(dst, src, n)  Shift right
+ * void cpus_shift_left(dst, src, n)   Shift left
+ *
+ * int first_cpu(mask)                 Number lowest set bit, or NR_CPUS
+ * int next_cpu(cpu, mask)             Next cpu past 'cpu', or NR_CPUS
+ *
+ * cpumask_t cpumask_of_cpu(cpu)       Return cpumask with bit 'cpu' set
+ * CPU_MASK_ALL                                Initializer - all bits set
+ * CPU_MASK_NONE                       Initializer - no bits set
+ * unsigned long *cpus_addr(mask)      Array of unsigned long's in mask
+ *
+ * int cpumask_scnprintf(buf, len, mask) Format cpumask for printing
+ * int cpumask_parse(ubuf, ulen, mask) Parse ascii string as cpumask
+ *
+ * for_each_cpu_mask(cpu, mask)                for-loop cpu over mask
+ *
+ * int num_online_cpus()               Number of online CPUs
+ * int num_possible_cpus()             Number of all possible CPUs
+ * int num_present_cpus()              Number of present CPUs
+ *
+ * int cpu_online(cpu)                 Is some cpu online?
+ * int cpu_possible(cpu)               Is some cpu possible?
+ * int cpu_present(cpu)                        Is some cpu present (can 
schedule)?
+ *
+ * int any_online_cpu(mask)            First online cpu in mask
+ *
+ * for_each_cpu(cpu)                   for-loop cpu over cpu_possible_map
+ * for_each_online_cpu(cpu)            for-loop cpu over cpu_online_map
+ * for_each_present_cpu(cpu)           for-loop cpu over cpu_present_map
+ *
+ * Subtlety:
+ * 1) The 'type-checked' form of cpu_isset() causes gcc (3.3.2, anyway)
+ *    to generate slightly worse code.  Note for example the additional
+ *    40 lines of assembly code compiling the "for each possible cpu"
+ *    loops buried in the disk_stat_read() macros calls when compiling
+ *    drivers/block/genhd.c (arch i386, CONFIG_SMP=y).  So use a simple
+ *    one-line #define for cpu_isset(), instead of wrapping an inline
+ *    inside a macro, the way we do the other calls.
+ */
+
+#include <linux/kernel.h>
+#include <linux/threads.h>
+#include <linux/bitmap.h>
+#include <asm/bug.h>
+
+typedef struct { DECLARE_BITMAP(bits, NR_CPUS); } cpumask_t;
+extern cpumask_t _unused_cpumask_arg_;
+
+#define cpu_set(cpu, dst) __cpu_set((cpu), &(dst))
+static inline void __cpu_set(int cpu, volatile cpumask_t *dstp)
+{
+       set_bit(cpu, dstp->bits);
+}
+
+#define cpu_clear(cpu, dst) __cpu_clear((cpu), &(dst))
+static inline void __cpu_clear(int cpu, volatile cpumask_t *dstp)
+{
+       clear_bit(cpu, dstp->bits);
+}
+
+#define cpus_setall(dst) __cpus_setall(&(dst), NR_CPUS)
+static inline void __cpus_setall(cpumask_t *dstp, int nbits)
+{
+       bitmap_fill(dstp->bits, nbits);
+}
+
+#define cpus_clear(dst) __cpus_clear(&(dst), NR_CPUS)
+static inline void __cpus_clear(cpumask_t *dstp, int nbits)
+{
+       bitmap_zero(dstp->bits, nbits);
+}
+
+/* No static inline type checking - see Subtlety (1) above. */
+#define cpu_isset(cpu, cpumask) test_bit((cpu), (cpumask).bits)
+
+#define cpu_test_and_set(cpu, cpumask) __cpu_test_and_set((cpu), &(cpumask))
+static inline int __cpu_test_and_set(int cpu, cpumask_t *addr)
+{
+       return test_and_set_bit(cpu, addr->bits);
+}
+
+#define cpus_and(dst, src1, src2) __cpus_and(&(dst), &(src1), &(src2), NR_CPUS)
+static inline void __cpus_and(cpumask_t *dstp, const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       bitmap_and(dstp->bits, src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_or(dst, src1, src2) __cpus_or(&(dst), &(src1), &(src2), NR_CPUS)
+static inline void __cpus_or(cpumask_t *dstp, const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       bitmap_or(dstp->bits, src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_xor(dst, src1, src2) __cpus_xor(&(dst), &(src1), &(src2), NR_CPUS)
+static inline void __cpus_xor(cpumask_t *dstp, const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       bitmap_xor(dstp->bits, src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_andnot(dst, src1, src2) \
+                               __cpus_andnot(&(dst), &(src1), &(src2), NR_CPUS)
+static inline void __cpus_andnot(cpumask_t *dstp, const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       bitmap_andnot(dstp->bits, src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_complement(dst, src) __cpus_complement(&(dst), &(src), NR_CPUS)
+static inline void __cpus_complement(cpumask_t *dstp,
+                                       const cpumask_t *srcp, int nbits)
+{
+       bitmap_complement(dstp->bits, srcp->bits, nbits);
+}
+
+#define cpus_equal(src1, src2) __cpus_equal(&(src1), &(src2), NR_CPUS)
+static inline int __cpus_equal(const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       return bitmap_equal(src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_intersects(src1, src2) __cpus_intersects(&(src1), &(src2), 
NR_CPUS)
+static inline int __cpus_intersects(const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       return bitmap_intersects(src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_subset(src1, src2) __cpus_subset(&(src1), &(src2), NR_CPUS)
+static inline int __cpus_subset(const cpumask_t *src1p,
+                                       const cpumask_t *src2p, int nbits)
+{
+       return bitmap_subset(src1p->bits, src2p->bits, nbits);
+}
+
+#define cpus_empty(src) __cpus_empty(&(src), NR_CPUS)
+static inline int __cpus_empty(const cpumask_t *srcp, int nbits)
+{
+       return bitmap_empty(srcp->bits, nbits);
+}
+
+#define cpus_full(cpumask) __cpus_full(&(cpumask), NR_CPUS)
+static inline int __cpus_full(const cpumask_t *srcp, int nbits)
+{
+       return bitmap_full(srcp->bits, nbits);
+}
+
+#define cpus_weight(cpumask) __cpus_weight(&(cpumask), NR_CPUS)
+static inline int __cpus_weight(const cpumask_t *srcp, int nbits)
+{
+       return bitmap_weight(srcp->bits, nbits);
+}
+
+#define cpus_shift_right(dst, src, n) \
+                       __cpus_shift_right(&(dst), &(src), (n), NR_CPUS)
+static inline void __cpus_shift_right(cpumask_t *dstp,
+                                       const cpumask_t *srcp, int n, int nbits)
+{
+       bitmap_shift_right(dstp->bits, srcp->bits, n, nbits);
+}
+
+#define cpus_shift_left(dst, src, n) \
+                       __cpus_shift_left(&(dst), &(src), (n), NR_CPUS)
+static inline void __cpus_shift_left(cpumask_t *dstp,
+                                       const cpumask_t *srcp, int n, int nbits)
+{
+       bitmap_shift_left(dstp->bits, srcp->bits, n, nbits);
+}
+
+#define first_cpu(src) __first_cpu(&(src), NR_CPUS)
+static inline int __first_cpu(const cpumask_t *srcp, int nbits)
+{
+       return min_t(int, nbits, find_first_bit(srcp->bits, nbits));
+}
+
+#define next_cpu(n, src) __next_cpu((n), &(src), NR_CPUS)
+static inline int __next_cpu(int n, const cpumask_t *srcp, int nbits)
+{
+       return min_t(int, nbits, find_next_bit(srcp->bits, nbits, n+1));
+}
+
+#define cpumask_of_cpu(cpu)                                            \
+({                                                                     \
+       typeof(_unused_cpumask_arg_) m;                                 \
+       if (sizeof(m) == sizeof(unsigned long)) {                       \
+               m.bits[0] = 1UL<<(cpu);                                 \
+       } else {                                                        \
+               cpus_clear(m);                                          \
+               cpu_set((cpu), m);                                      \
+       }                                                               \
+       m;                                                              \
+})
+
+#define CPU_MASK_LAST_WORD BITMAP_LAST_WORD_MASK(NR_CPUS)
+
+#if NR_CPUS <= BITS_PER_LONG
+
+#define CPU_MASK_ALL                                                   \
+(cpumask_t) { {                                                                
\
+       [BITS_TO_LONGS(NR_CPUS)-1] = CPU_MASK_LAST_WORD                 \
+} }
+
+#else
+
+#define CPU_MASK_ALL                                                   \
+(cpumask_t) { {                                                                
\
+       [0 ... BITS_TO_LONGS(NR_CPUS)-2] = ~0UL,                        \
+       [BITS_TO_LONGS(NR_CPUS)-1] = CPU_MASK_LAST_WORD                 \
+} }
+
+#endif
+
+#define CPU_MASK_NONE                                                  \
+(cpumask_t) { {                                                                
\
+       [0 ... BITS_TO_LONGS(NR_CPUS)-1] =  0UL                         \
+} }
+
+#define CPU_MASK_CPU0                                                  \
+(cpumask_t) { {                                                                
\
+       [0] =  1UL                                                      \
+} }
+
+#define cpus_addr(src) ((src).bits)
+
+#define cpumask_scnprintf(buf, len, src) \
+                       __cpumask_scnprintf((buf), (len), &(src), NR_CPUS)
+static inline int __cpumask_scnprintf(char *buf, int len,
+                                       const cpumask_t *srcp, int nbits)
+{
+       return bitmap_scnprintf(buf, len, srcp->bits, nbits);
+}
+
+#define cpumask_parse(ubuf, ulen, src) \
+                       __cpumask_parse((ubuf), (ulen), &(src), NR_CPUS)
+static inline int __cpumask_parse(const char __user *buf, int len,
+                                       cpumask_t *dstp, int nbits)
+{
+       return bitmap_parse(buf, len, dstp->bits, nbits);
+}
+
+#if NR_CPUS > 1
+#define for_each_cpu_mask(cpu, mask)           \
+       for ((cpu) = first_cpu(mask);           \
+               (cpu) < NR_CPUS;                \
+               (cpu) = next_cpu((cpu), (mask)))
+#else /* NR_CPUS == 1 */
+#define for_each_cpu_mask(cpu, mask) for ((cpu) = 0; (cpu) < 1; (cpu)++)
+#endif /* NR_CPUS */
+
+/*
+ * The following particular system cpumasks and operations manage
+ * possible, present and online cpus.  Each of them is a fixed size
+ * bitmap of size NR_CPUS.
+ *
+ *  #ifdef CONFIG_HOTPLUG_CPU
+ *     cpu_possible_map - all NR_CPUS bits set
+ *     cpu_present_map  - has bit 'cpu' set iff cpu is populated
+ *     cpu_online_map   - has bit 'cpu' set iff cpu available to scheduler
+ *  #else
+ *     cpu_possible_map - has bit 'cpu' set iff cpu is populated
+ *     cpu_present_map  - copy of cpu_possible_map
+ *     cpu_online_map   - has bit 'cpu' set iff cpu available to scheduler
+ *  #endif
+ *
+ *  In either case, NR_CPUS is fixed at compile time, as the static
+ *  size of these bitmaps.  The cpu_possible_map is fixed at boot
+ *  time, as the set of CPU id's that it is possible might ever
+ *  be plugged in at anytime during the life of that system boot.
+ *  The cpu_present_map is dynamic(*), representing which CPUs
+ *  are currently plugged in.  And cpu_online_map is the dynamic
+ *  subset of cpu_present_map, indicating those CPUs available
+ *  for scheduling.
+ *
+ *  If HOTPLUG is enabled, then cpu_possible_map is forced to have
+ *  all NR_CPUS bits set, otherwise it is just the set of CPUs that
+ *  ACPI reports present at boot.
+ *
+ *  If HOTPLUG is enabled, then cpu_present_map varies dynamically,
+ *  depending on what ACPI reports as currently plugged in, otherwise
+ *  cpu_present_map is just a copy of cpu_possible_map.
+ *
+ *  (*) Well, cpu_present_map is dynamic in the hotplug case.  If not
+ *      hotplug, it's a copy of cpu_possible_map, hence fixed at boot.
+ *
+ * Subtleties:
+ * 1) UP arch's (NR_CPUS == 1, CONFIG_SMP not defined) hardcode
+ *    assumption that their single CPU is online.  The UP
+ *    cpu_{online,possible,present}_maps are placebos.  Changing them
+ *    will have no useful affect on the following num_*_cpus()
+ *    and cpu_*() macros in the UP case.  This ugliness is a UP
+ *    optimization - don't waste any instructions or memory references
+ *    asking if you're online or how many CPUs there are if there is
+ *    only one CPU.
+ * 2) Most SMP arch's #define some of these maps to be some
+ *    other map specific to that arch.  Therefore, the following
+ *    must be #define macros, not inlines.  To see why, examine
+ *    the assembly code produced by the following.  Note that
+ *    set1() writes phys_x_map, but set2() writes x_map:
+ *        int x_map, phys_x_map;
+ *        #define set1(a) x_map = a
+ *        inline void set2(int a) { x_map = a; }
+ *        #define x_map phys_x_map
+ *        main(){ set1(3); set2(5); }
+ */
+
+extern cpumask_t cpu_possible_map;
+#ifndef XEN
+extern cpumask_t cpu_online_map;
+#endif
+extern cpumask_t cpu_present_map;
+
+#if NR_CPUS > 1
+#define num_online_cpus()      cpus_weight(cpu_online_map)
+#define num_possible_cpus()    cpus_weight(cpu_possible_map)
+#define num_present_cpus()     cpus_weight(cpu_present_map)
+#define cpu_online(cpu)                cpu_isset((cpu), cpu_online_map)
+#define cpu_possible(cpu)      cpu_isset((cpu), cpu_possible_map)
+#define cpu_present(cpu)       cpu_isset((cpu), cpu_present_map)
+#else
+#define num_online_cpus()      1
+#define num_possible_cpus()    1
+#define num_present_cpus()     1
+#define cpu_online(cpu)                ((cpu) == 0)
+#define cpu_possible(cpu)      ((cpu) == 0)
+#define cpu_present(cpu)       ((cpu) == 0)
+#endif
+
+#define any_online_cpu(mask)                   \
+({                                             \
+       int cpu;                                \
+       for_each_cpu_mask(cpu, (mask))          \
+               if (cpu_online(cpu))            \
+                       break;                  \
+       cpu;                                    \
+})
+
+#define for_each_cpu(cpu)        for_each_cpu_mask((cpu), cpu_possible_map)
+#define for_each_online_cpu(cpu)  for_each_cpu_mask((cpu), cpu_online_map)
+#define for_each_present_cpu(cpu) for_each_cpu_mask((cpu), cpu_present_map)
+
+#endif /* __LINUX_CPUMASK_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/linux/hardirq.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/linux/hardirq.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,110 @@
+#ifndef LINUX_HARDIRQ_H
+#define LINUX_HARDIRQ_H
+
+#include <linux/config.h>
+#include <linux/smp_lock.h>
+#include <asm/hardirq.h>
+#include <asm/system.h>
+
+/*
+ * We put the hardirq and softirq counter into the preemption
+ * counter. The bitmask has the following meaning:
+ *
+ * - bits 0-7 are the preemption count (max preemption depth: 256)
+ * - bits 8-15 are the softirq count (max # of softirqs: 256)
+ *
+ * The hardirq count can be overridden per architecture, the default is:
+ *
+ * - bits 16-27 are the hardirq count (max # of hardirqs: 4096)
+ * - ( bit 28 is the PREEMPT_ACTIVE flag. )
+ *
+ * PREEMPT_MASK: 0x000000ff
+ * SOFTIRQ_MASK: 0x0000ff00
+ * HARDIRQ_MASK: 0x0fff0000
+ */
+#define PREEMPT_BITS   8
+#define SOFTIRQ_BITS   8
+
+#ifndef HARDIRQ_BITS
+#define HARDIRQ_BITS   12
+/*
+ * The hardirq mask has to be large enough to have space for potentially
+ * all IRQ sources in the system nesting on a single CPU.
+ */
+#if (1 << HARDIRQ_BITS) < NR_IRQS
+# error HARDIRQ_BITS is too low!
+#endif
+#endif
+
+#define PREEMPT_SHIFT  0
+#define SOFTIRQ_SHIFT  (PREEMPT_SHIFT + PREEMPT_BITS)
+#define HARDIRQ_SHIFT  (SOFTIRQ_SHIFT + SOFTIRQ_BITS)
+
+#define __IRQ_MASK(x)  ((1UL << (x))-1)
+
+#define PREEMPT_MASK   (__IRQ_MASK(PREEMPT_BITS) << PREEMPT_SHIFT)
+#define HARDIRQ_MASK   (__IRQ_MASK(HARDIRQ_BITS) << HARDIRQ_SHIFT)
+#define SOFTIRQ_MASK   (__IRQ_MASK(SOFTIRQ_BITS) << SOFTIRQ_SHIFT)
+
+#define PREEMPT_OFFSET (1UL << PREEMPT_SHIFT)
+#define SOFTIRQ_OFFSET (1UL << SOFTIRQ_SHIFT)
+#define HARDIRQ_OFFSET (1UL << HARDIRQ_SHIFT)
+
+#define hardirq_count()        (preempt_count() & HARDIRQ_MASK)
+#define softirq_count()        (preempt_count() & SOFTIRQ_MASK)
+#define irq_count()    (preempt_count() & (HARDIRQ_MASK | SOFTIRQ_MASK))
+
+/*
+ * Are we doing bottom half or hardware interrupt processing?
+ * Are we in a softirq context? Interrupt context?
+ */
+#define in_irq()               (hardirq_count())
+#define in_softirq()           (softirq_count())
+#ifndef XEN
+#define in_interrupt()         (irq_count())
+#else
+#define in_interrupt()         0               // FIXME LATER
+#endif
+
+#if defined(CONFIG_PREEMPT) && !defined(CONFIG_PREEMPT_BKL)
+# define in_atomic()   ((preempt_count() & ~PREEMPT_ACTIVE) != kernel_locked())
+#else
+# define in_atomic()   ((preempt_count() & ~PREEMPT_ACTIVE) != 0)
+#endif
+
+#ifdef CONFIG_PREEMPT
+# define preemptible() (preempt_count() == 0 && !irqs_disabled())
+# define IRQ_EXIT_OFFSET (HARDIRQ_OFFSET-1)
+#else
+# define preemptible() 0
+# define IRQ_EXIT_OFFSET HARDIRQ_OFFSET
+#endif
+
+#ifdef CONFIG_SMP
+extern void synchronize_irq(unsigned int irq);
+#else
+# define synchronize_irq(irq)  barrier()
+#endif
+
+#define nmi_enter()            irq_enter()
+#define nmi_exit()             sub_preempt_count(HARDIRQ_OFFSET)
+
+#ifndef CONFIG_VIRT_CPU_ACCOUNTING
+static inline void account_user_vtime(struct task_struct *tsk)
+{
+}
+
+static inline void account_system_vtime(struct task_struct *tsk)
+{
+}
+#endif
+
+#define irq_enter()                                    \
+       do {                                            \
+               account_system_vtime(current);          \
+               add_preempt_count(HARDIRQ_OFFSET);      \
+       } while (0)
+
+extern void irq_exit(void);
+
+#endif /* LINUX_HARDIRQ_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux-xen/linux/interrupt.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux-xen/linux/interrupt.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,291 @@
+/* interrupt.h */
+#ifndef _LINUX_INTERRUPT_H
+#define _LINUX_INTERRUPT_H
+
+#include <linux/config.h>
+#include <linux/kernel.h>
+#include <linux/linkage.h>
+#include <linux/bitops.h>
+#include <linux/preempt.h>
+#include <linux/cpumask.h>
+#include <linux/hardirq.h>
+#include <asm/atomic.h>
+#include <asm/ptrace.h>
+#include <asm/system.h>
+
+/*
+ * For 2.4.x compatibility, 2.4.x can use
+ *
+ *     typedef void irqreturn_t;
+ *     #define IRQ_NONE
+ *     #define IRQ_HANDLED
+ *     #define IRQ_RETVAL(x)
+ *
+ * To mix old-style and new-style irq handler returns.
+ *
+ * IRQ_NONE means we didn't handle it.
+ * IRQ_HANDLED means that we did have a valid interrupt and handled it.
+ * IRQ_RETVAL(x) selects on the two depending on x being non-zero (for handled)
+ */
+typedef int irqreturn_t;
+
+#define IRQ_NONE       (0)
+#define IRQ_HANDLED    (1)
+#define IRQ_RETVAL(x)  ((x) != 0)
+
+#ifndef XEN
+struct irqaction {
+       irqreturn_t (*handler)(int, void *, struct pt_regs *);
+       unsigned long flags;
+       cpumask_t mask;
+       const char *name;
+       void *dev_id;
+       struct irqaction *next;
+       int irq;
+       struct proc_dir_entry *dir;
+};
+
+extern irqreturn_t no_action(int cpl, void *dev_id, struct pt_regs *regs);
+extern int request_irq(unsigned int,
+                      irqreturn_t (*handler)(int, void *, struct pt_regs *),
+                      unsigned long, const char *, void *);
+extern void free_irq(unsigned int, void *);
+#endif
+
+
+#ifdef CONFIG_GENERIC_HARDIRQS
+extern void disable_irq_nosync(unsigned int irq);
+extern void disable_irq(unsigned int irq);
+extern void enable_irq(unsigned int irq);
+#endif
+
+/*
+ * Temporary defines for UP kernels, until all code gets fixed.
+ */
+#ifndef CONFIG_SMP
+static inline void __deprecated cli(void)
+{
+       local_irq_disable();
+}
+static inline void __deprecated sti(void)
+{
+       local_irq_enable();
+}
+static inline void __deprecated save_flags(unsigned long *x)
+{
+       local_save_flags(*x);
+}
+#define save_flags(x) save_flags(&x);
+static inline void __deprecated restore_flags(unsigned long x)
+{
+       local_irq_restore(x);
+}
+
+static inline void __deprecated save_and_cli(unsigned long *x)
+{
+       local_irq_save(*x);
+}
+#define save_and_cli(x)        save_and_cli(&x)
+#endif /* CONFIG_SMP */
+
+/* SoftIRQ primitives.  */
+#define local_bh_disable() \
+               do { add_preempt_count(SOFTIRQ_OFFSET); barrier(); } while (0)
+#define __local_bh_enable() \
+               do { barrier(); sub_preempt_count(SOFTIRQ_OFFSET); } while (0)
+
+extern void local_bh_enable(void);
+
+/* PLEASE, avoid to allocate new softirqs, if you need not _really_ high
+   frequency threaded job scheduling. For almost all the purposes
+   tasklets are more than enough. F.e. all serial device BHs et
+   al. should be converted to tasklets, not to softirqs.
+ */
+
+enum
+{
+       HI_SOFTIRQ=0,
+       TIMER_SOFTIRQ,
+       NET_TX_SOFTIRQ,
+       NET_RX_SOFTIRQ,
+       SCSI_SOFTIRQ,
+       TASKLET_SOFTIRQ
+};
+
+/* softirq mask and active fields moved to irq_cpustat_t in
+ * asm/hardirq.h to get better cache usage.  KAO
+ */
+
+struct softirq_action
+{
+       void    (*action)(struct softirq_action *);
+       void    *data;
+};
+
+asmlinkage void do_softirq(void);
+//extern void open_softirq(int nr, void (*action)(struct softirq_action*), 
void *data);
+extern void softirq_init(void);
+#define __raise_softirq_irqoff(nr) do { local_softirq_pending() |= 1UL << 
(nr); } while (0)
+extern void FASTCALL(raise_softirq_irqoff(unsigned int nr));
+extern void FASTCALL(raise_softirq(unsigned int nr));
+
+
+/* Tasklets --- multithreaded analogue of BHs.
+
+   Main feature differing them of generic softirqs: tasklet
+   is running only on one CPU simultaneously.
+
+   Main feature differing them of BHs: different tasklets
+   may be run simultaneously on different CPUs.
+
+   Properties:
+   * If tasklet_schedule() is called, then tasklet is guaranteed
+     to be executed on some cpu at least once after this.
+   * If the tasklet is already scheduled, but its excecution is still not
+     started, it will be executed only once.
+   * If this tasklet is already running on another CPU (or schedule is called
+     from tasklet itself), it is rescheduled for later.
+   * Tasklet is strictly serialized wrt itself, but not
+     wrt another tasklets. If client needs some intertask synchronization,
+     he makes it with spinlocks.
+ */
+
+struct tasklet_struct
+{
+       struct tasklet_struct *next;
+       unsigned long state;
+       atomic_t count;
+       void (*func)(unsigned long);
+       unsigned long data;
+};
+
+#define DECLARE_TASKLET(name, func, data) \
+struct tasklet_struct name = { NULL, 0, ATOMIC_INIT(0), func, data }
+
+#define DECLARE_TASKLET_DISABLED(name, func, data) \
+struct tasklet_struct name = { NULL, 0, ATOMIC_INIT(1), func, data }
+
+
+enum
+{
+       TASKLET_STATE_SCHED,    /* Tasklet is scheduled for execution */
+       TASKLET_STATE_RUN       /* Tasklet is running (SMP only) */
+};
+
+#ifdef CONFIG_SMP
+static inline int tasklet_trylock(struct tasklet_struct *t)
+{
+       return !test_and_set_bit(TASKLET_STATE_RUN, &(t)->state);
+}
+
+static inline void tasklet_unlock(struct tasklet_struct *t)
+{
+       smp_mb__before_clear_bit(); 
+       clear_bit(TASKLET_STATE_RUN, &(t)->state);
+}
+
+static inline void tasklet_unlock_wait(struct tasklet_struct *t)
+{
+       while (test_bit(TASKLET_STATE_RUN, &(t)->state)) { barrier(); }
+}
+#else
+#define tasklet_trylock(t) 1
+#define tasklet_unlock_wait(t) do { } while (0)
+#define tasklet_unlock(t) do { } while (0)
+#endif
+
+extern void FASTCALL(__tasklet_schedule(struct tasklet_struct *t));
+
+static inline void tasklet_schedule(struct tasklet_struct *t)
+{
+       if (!test_and_set_bit(TASKLET_STATE_SCHED, &t->state))
+               __tasklet_schedule(t);
+}
+
+extern void FASTCALL(__tasklet_hi_schedule(struct tasklet_struct *t));
+
+static inline void tasklet_hi_schedule(struct tasklet_struct *t)
+{
+       if (!test_and_set_bit(TASKLET_STATE_SCHED, &t->state))
+               __tasklet_hi_schedule(t);
+}
+
+
+static inline void tasklet_disable_nosync(struct tasklet_struct *t)
+{
+       atomic_inc(&t->count);
+       smp_mb__after_atomic_inc();
+}
+
+static inline void tasklet_disable(struct tasklet_struct *t)
+{
+       tasklet_disable_nosync(t);
+       tasklet_unlock_wait(t);
+       smp_mb();
+}
+
+static inline void tasklet_enable(struct tasklet_struct *t)
+{
+       smp_mb__before_atomic_dec();
+       atomic_dec(&t->count);
+}
+
+static inline void tasklet_hi_enable(struct tasklet_struct *t)
+{
+       smp_mb__before_atomic_dec();
+       atomic_dec(&t->count);
+}
+
+extern void tasklet_kill(struct tasklet_struct *t);
+extern void tasklet_kill_immediate(struct tasklet_struct *t, unsigned int cpu);
+extern void tasklet_init(struct tasklet_struct *t,
+                        void (*func)(unsigned long), unsigned long data);
+
+/*
+ * Autoprobing for irqs:
+ *
+ * probe_irq_on() and probe_irq_off() provide robust primitives
+ * for accurate IRQ probing during kernel initialization.  They are
+ * reasonably simple to use, are not "fooled" by spurious interrupts,
+ * and, unlike other attempts at IRQ probing, they do not get hung on
+ * stuck interrupts (such as unused PS2 mouse interfaces on ASUS boards).
+ *
+ * For reasonably foolproof probing, use them as follows:
+ *
+ * 1. clear and/or mask the device's internal interrupt.
+ * 2. sti();
+ * 3. irqs = probe_irq_on();      // "take over" all unassigned idle IRQs
+ * 4. enable the device and cause it to trigger an interrupt.
+ * 5. wait for the device to interrupt, using non-intrusive polling or a delay.
+ * 6. irq = probe_irq_off(irqs);  // get IRQ number, 0=none, negative=multiple
+ * 7. service the device to clear its pending interrupt.
+ * 8. loop again if paranoia is required.
+ *
+ * probe_irq_on() returns a mask of allocated irq's.
+ *
+ * probe_irq_off() takes the mask as a parameter,
+ * and returns the irq number which occurred,
+ * or zero if none occurred, or a negative irq number
+ * if more than one irq occurred.
+ */
+
+#if defined(CONFIG_GENERIC_HARDIRQS) && !defined(CONFIG_GENERIC_IRQ_PROBE) 
+static inline unsigned long probe_irq_on(void)
+{
+       return 0;
+}
+static inline int probe_irq_off(unsigned long val)
+{
+       return 0;
+}
+static inline unsigned int probe_irq_mask(unsigned long val)
+{
+       return 0;
+}
+#else
+extern unsigned long probe_irq_on(void);       /* returns 0 on failure */
+extern int probe_irq_off(unsigned long);       /* returns 0 or negative on 
failure */
+extern unsigned int probe_irq_mask(unsigned long);     /* returns mask of ISA 
interrupts */
+#endif
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/bug.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/bug.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,34 @@
+#ifndef _ASM_GENERIC_BUG_H
+#define _ASM_GENERIC_BUG_H
+
+#include <linux/compiler.h>
+#include <linux/config.h>
+
+#ifndef HAVE_ARCH_BUG
+#define BUG() do { \
+       printk("kernel BUG at %s:%d!\n", __FILE__, __LINE__); \
+       panic("BUG!"); \
+} while (0)
+#endif
+
+#ifndef HAVE_ARCH_PAGE_BUG
+#define PAGE_BUG(page) do { \
+       printk("page BUG for page at %p\n", page); \
+       BUG(); \
+} while (0)
+#endif
+
+#ifndef HAVE_ARCH_BUG_ON
+#define BUG_ON(condition) do { if (unlikely((condition)!=0)) BUG(); } while(0)
+#endif
+
+#ifndef HAVE_ARCH_WARN_ON
+#define WARN_ON(condition) do { \
+       if (unlikely((condition)!=0)) { \
+               printk("Badness in %s at %s:%d\n", __FUNCTION__, __FILE__, 
__LINE__); \
+               dump_stack(); \
+       } \
+} while (0)
+#endif
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/div64.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/div64.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,58 @@
+#ifndef _ASM_GENERIC_DIV64_H
+#define _ASM_GENERIC_DIV64_H
+/*
+ * Copyright (C) 2003 Bernardo Innocenti <bernie@xxxxxxxxxxx>
+ * Based on former asm-ppc/div64.h and asm-m68knommu/div64.h
+ *
+ * The semantics of do_div() are:
+ *
+ * uint32_t do_div(uint64_t *n, uint32_t base)
+ * {
+ *     uint32_t remainder = *n % base;
+ *     *n = *n / base;
+ *     return remainder;
+ * }
+ *
+ * NOTE: macro parameter n is evaluated multiple times,
+ *       beware of side effects!
+ */
+
+#include <linux/types.h>
+#include <linux/compiler.h>
+
+#if BITS_PER_LONG == 64
+
+# define do_div(n,base) ({                                     \
+       uint32_t __base = (base);                               \
+       uint32_t __rem;                                         \
+       __rem = ((uint64_t)(n)) % __base;                       \
+       (n) = ((uint64_t)(n)) / __base;                         \
+       __rem;                                                  \
+ })
+
+#elif BITS_PER_LONG == 32
+
+extern uint32_t __div64_32(uint64_t *dividend, uint32_t divisor);
+
+/* The unnecessary pointer compare is there
+ * to check for type safety (n must be 64bit)
+ */
+# define do_div(n,base) ({                             \
+       uint32_t __base = (base);                       \
+       uint32_t __rem;                                 \
+       (void)(((typeof((n)) *)0) == ((uint64_t *)0));  \
+       if (likely(((n) >> 32) == 0)) {                 \
+               __rem = (uint32_t)(n) % __base;         \
+               (n) = (uint32_t)(n) / __base;           \
+       } else                                          \
+               __rem = __div64_32(&(n), __base);       \
+       __rem;                                          \
+ })
+
+#else /* BITS_PER_LONG == ?? */
+
+# error do_div() does not yet support the C64
+
+#endif /* BITS_PER_LONG */
+
+#endif /* _ASM_GENERIC_DIV64_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/errno-base.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/errno-base.h       Tue Aug 16 
04:15:23 2005
@@ -0,0 +1,39 @@
+#ifndef _ASM_GENERIC_ERRNO_BASE_H
+#define _ASM_GENERIC_ERRNO_BASE_H
+
+#define        EPERM            1      /* Operation not permitted */
+#define        ENOENT           2      /* No such file or directory */
+#define        ESRCH            3      /* No such process */
+#define        EINTR            4      /* Interrupted system call */
+#define        EIO              5      /* I/O error */
+#define        ENXIO            6      /* No such device or address */
+#define        E2BIG            7      /* Argument list too long */
+#define        ENOEXEC          8      /* Exec format error */
+#define        EBADF            9      /* Bad file number */
+#define        ECHILD          10      /* No child processes */
+#define        EAGAIN          11      /* Try again */
+#define        ENOMEM          12      /* Out of memory */
+#define        EACCES          13      /* Permission denied */
+#define        EFAULT          14      /* Bad address */
+#define        ENOTBLK         15      /* Block device required */
+#define        EBUSY           16      /* Device or resource busy */
+#define        EEXIST          17      /* File exists */
+#define        EXDEV           18      /* Cross-device link */
+#define        ENODEV          19      /* No such device */
+#define        ENOTDIR         20      /* Not a directory */
+#define        EISDIR          21      /* Is a directory */
+#define        EINVAL          22      /* Invalid argument */
+#define        ENFILE          23      /* File table overflow */
+#define        EMFILE          24      /* Too many open files */
+#define        ENOTTY          25      /* Not a typewriter */
+#define        ETXTBSY         26      /* Text file busy */
+#define        EFBIG           27      /* File too large */
+#define        ENOSPC          28      /* No space left on device */
+#define        ESPIPE          29      /* Illegal seek */
+#define        EROFS           30      /* Read-only file system */
+#define        EMLINK          31      /* Too many links */
+#define        EPIPE           32      /* Broken pipe */
+#define        EDOM            33      /* Math argument out of domain of func 
*/
+#define        ERANGE          34      /* Math result not representable */
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/errno.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/errno.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,105 @@
+#ifndef _ASM_GENERIC_ERRNO_H
+#define _ASM_GENERIC_ERRNO_H
+
+#include <asm-generic/errno-base.h>
+
+#define        EDEADLK         35      /* Resource deadlock would occur */
+#define        ENAMETOOLONG    36      /* File name too long */
+#define        ENOLCK          37      /* No record locks available */
+#define        ENOSYS          38      /* Function not implemented */
+#define        ENOTEMPTY       39      /* Directory not empty */
+#define        ELOOP           40      /* Too many symbolic links encountered 
*/
+#define        EWOULDBLOCK     EAGAIN  /* Operation would block */
+#define        ENOMSG          42      /* No message of desired type */
+#define        EIDRM           43      /* Identifier removed */
+#define        ECHRNG          44      /* Channel number out of range */
+#define        EL2NSYNC        45      /* Level 2 not synchronized */
+#define        EL3HLT          46      /* Level 3 halted */
+#define        EL3RST          47      /* Level 3 reset */
+#define        ELNRNG          48      /* Link number out of range */
+#define        EUNATCH         49      /* Protocol driver not attached */
+#define        ENOCSI          50      /* No CSI structure available */
+#define        EL2HLT          51      /* Level 2 halted */
+#define        EBADE           52      /* Invalid exchange */
+#define        EBADR           53      /* Invalid request descriptor */
+#define        EXFULL          54      /* Exchange full */
+#define        ENOANO          55      /* No anode */
+#define        EBADRQC         56      /* Invalid request code */
+#define        EBADSLT         57      /* Invalid slot */
+
+#define        EDEADLOCK       EDEADLK
+
+#define        EBFONT          59      /* Bad font file format */
+#define        ENOSTR          60      /* Device not a stream */
+#define        ENODATA         61      /* No data available */
+#define        ETIME           62      /* Timer expired */
+#define        ENOSR           63      /* Out of streams resources */
+#define        ENONET          64      /* Machine is not on the network */
+#define        ENOPKG          65      /* Package not installed */
+#define        EREMOTE         66      /* Object is remote */
+#define        ENOLINK         67      /* Link has been severed */
+#define        EADV            68      /* Advertise error */
+#define        ESRMNT          69      /* Srmount error */
+#define        ECOMM           70      /* Communication error on send */
+#define        EPROTO          71      /* Protocol error */
+#define        EMULTIHOP       72      /* Multihop attempted */
+#define        EDOTDOT         73      /* RFS specific error */
+#define        EBADMSG         74      /* Not a data message */
+#define        EOVERFLOW       75      /* Value too large for defined data 
type */
+#define        ENOTUNIQ        76      /* Name not unique on network */
+#define        EBADFD          77      /* File descriptor in bad state */
+#define        EREMCHG         78      /* Remote address changed */
+#define        ELIBACC         79      /* Can not access a needed shared 
library */
+#define        ELIBBAD         80      /* Accessing a corrupted shared library 
*/
+#define        ELIBSCN         81      /* .lib section in a.out corrupted */
+#define        ELIBMAX         82      /* Attempting to link in too many 
shared libraries */
+#define        ELIBEXEC        83      /* Cannot exec a shared library 
directly */
+#define        EILSEQ          84      /* Illegal byte sequence */
+#define        ERESTART        85      /* Interrupted system call should be 
restarted */
+#define        ESTRPIPE        86      /* Streams pipe error */
+#define        EUSERS          87      /* Too many users */
+#define        ENOTSOCK        88      /* Socket operation on non-socket */
+#define        EDESTADDRREQ    89      /* Destination address required */
+#define        EMSGSIZE        90      /* Message too long */
+#define        EPROTOTYPE      91      /* Protocol wrong type for socket */
+#define        ENOPROTOOPT     92      /* Protocol not available */
+#define        EPROTONOSUPPORT 93      /* Protocol not supported */
+#define        ESOCKTNOSUPPORT 94      /* Socket type not supported */
+#define        EOPNOTSUPP      95      /* Operation not supported on transport 
endpoint */
+#define        EPFNOSUPPORT    96      /* Protocol family not supported */
+#define        EAFNOSUPPORT    97      /* Address family not supported by 
protocol */
+#define        EADDRINUSE      98      /* Address already in use */
+#define        EADDRNOTAVAIL   99      /* Cannot assign requested address */
+#define        ENETDOWN        100     /* Network is down */
+#define        ENETUNREACH     101     /* Network is unreachable */
+#define        ENETRESET       102     /* Network dropped connection because 
of reset */
+#define        ECONNABORTED    103     /* Software caused connection abort */
+#define        ECONNRESET      104     /* Connection reset by peer */
+#define        ENOBUFS         105     /* No buffer space available */
+#define        EISCONN         106     /* Transport endpoint is already 
connected */
+#define        ENOTCONN        107     /* Transport endpoint is not connected 
*/
+#define        ESHUTDOWN       108     /* Cannot send after transport endpoint 
shutdown */
+#define        ETOOMANYREFS    109     /* Too many references: cannot splice */
+#define        ETIMEDOUT       110     /* Connection timed out */
+#define        ECONNREFUSED    111     /* Connection refused */
+#define        EHOSTDOWN       112     /* Host is down */
+#define        EHOSTUNREACH    113     /* No route to host */
+#define        EALREADY        114     /* Operation already in progress */
+#define        EINPROGRESS     115     /* Operation now in progress */
+#define        ESTALE          116     /* Stale NFS file handle */
+#define        EUCLEAN         117     /* Structure needs cleaning */
+#define        ENOTNAM         118     /* Not a XENIX named type file */
+#define        ENAVAIL         119     /* No XENIX semaphores available */
+#define        EISNAM          120     /* Is a named type file */
+#define        EREMOTEIO       121     /* Remote I/O error */
+#define        EDQUOT          122     /* Quota exceeded */
+
+#define        ENOMEDIUM       123     /* No medium found */
+#define        EMEDIUMTYPE     124     /* Wrong medium type */
+#define        ECANCELED       125     /* Operation Canceled */
+#define        ENOKEY          126     /* Required key not available */
+#define        EKEYEXPIRED     127     /* Key has expired */
+#define        EKEYREVOKED     128     /* Key has been revoked */
+#define        EKEYREJECTED    129     /* Key was rejected by service */
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/ide_iops.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/ide_iops.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,38 @@
+/* Generic I/O and MEMIO string operations.  */
+
+#define __ide_insw     insw
+#define __ide_insl     insl
+#define __ide_outsw    outsw
+#define __ide_outsl    outsl
+
+static __inline__ void __ide_mm_insw(void __iomem *port, void *addr, u32 count)
+{
+       while (count--) {
+               *(u16 *)addr = readw(port);
+               addr += 2;
+       }
+}
+
+static __inline__ void __ide_mm_insl(void __iomem *port, void *addr, u32 count)
+{
+       while (count--) {
+               *(u32 *)addr = readl(port);
+               addr += 4;
+       }
+}
+
+static __inline__ void __ide_mm_outsw(void __iomem *port, void *addr, u32 
count)
+{
+       while (count--) {
+               writew(*(u16 *)addr, port);
+               addr += 2;
+       }
+}
+
+static __inline__ void __ide_mm_outsl(void __iomem * port, void *addr, u32 
count)
+{
+       while (count--) {
+               writel(*(u32 *)addr, port);
+               addr += 4;
+       }
+}
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/iomap.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/iomap.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,63 @@
+#ifndef __GENERIC_IO_H
+#define __GENERIC_IO_H
+
+#include <linux/linkage.h>
+
+/*
+ * These are the "generic" interfaces for doing new-style
+ * memory-mapped or PIO accesses. Architectures may do
+ * their own arch-optimized versions, these just act as
+ * wrappers around the old-style IO register access functions:
+ * read[bwl]/write[bwl]/in[bwl]/out[bwl]
+ *
+ * Don't include this directly, include it from <asm/io.h>.
+ */
+
+/*
+ * Read/write from/to an (offsettable) iomem cookie. It might be a PIO
+ * access or a MMIO access, these functions don't care. The info is
+ * encoded in the hardware mapping set up by the mapping functions
+ * (or the cookie itself, depending on implementation and hw).
+ *
+ * The generic routines just encode the PIO/MMIO as part of the
+ * cookie, and coldly assume that the MMIO IO mappings are not
+ * in the low address range. Architectures for which this is not
+ * true can't use this generic implementation.
+ */
+extern unsigned int fastcall ioread8(void __iomem *);
+extern unsigned int fastcall ioread16(void __iomem *);
+extern unsigned int fastcall ioread32(void __iomem *);
+
+extern void fastcall iowrite8(u8, void __iomem *);
+extern void fastcall iowrite16(u16, void __iomem *);
+extern void fastcall iowrite32(u32, void __iomem *);
+
+/*
+ * "string" versions of the above. Note that they
+ * use native byte ordering for the accesses (on
+ * the assumption that IO and memory agree on a
+ * byte order, and CPU byteorder is irrelevant).
+ *
+ * They do _not_ update the port address. If you
+ * want MMIO that copies stuff laid out in MMIO
+ * memory across multiple ports, use "memcpy_toio()"
+ * and friends.
+ */
+extern void fastcall ioread8_rep(void __iomem *port, void *buf, unsigned long 
count);
+extern void fastcall ioread16_rep(void __iomem *port, void *buf, unsigned long 
count);
+extern void fastcall ioread32_rep(void __iomem *port, void *buf, unsigned long 
count);
+
+extern void fastcall iowrite8_rep(void __iomem *port, const void *buf, 
unsigned long count);
+extern void fastcall iowrite16_rep(void __iomem *port, const void *buf, 
unsigned long count);
+extern void fastcall iowrite32_rep(void __iomem *port, const void *buf, 
unsigned long count);
+
+/* Create a virtual mapping cookie for an IO port range */
+extern void __iomem *ioport_map(unsigned long port, unsigned int nr);
+extern void ioport_unmap(void __iomem *);
+
+/* Create a virtual mapping cookie for a PCI BAR (memory or IO) */
+struct pci_dev;
+extern void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long 
max);
+extern void pci_iounmap(struct pci_dev *dev, void __iomem *);
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/pci-dma-compat.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/pci-dma-compat.h   Tue Aug 16 
04:15:23 2005
@@ -0,0 +1,107 @@
+/* include this file if the platform implements the dma_ DMA Mapping API
+ * and wants to provide the pci_ DMA Mapping API in terms of it */
+
+#ifndef _ASM_GENERIC_PCI_DMA_COMPAT_H
+#define _ASM_GENERIC_PCI_DMA_COMPAT_H
+
+#include <linux/dma-mapping.h>
+
+/* note pci_set_dma_mask isn't here, since it's a public function
+ * exported from drivers/pci, use dma_supported instead */
+
+static inline int
+pci_dma_supported(struct pci_dev *hwdev, u64 mask)
+{
+       return dma_supported(hwdev == NULL ? NULL : &hwdev->dev, mask);
+}
+
+static inline void *
+pci_alloc_consistent(struct pci_dev *hwdev, size_t size,
+                    dma_addr_t *dma_handle)
+{
+       return dma_alloc_coherent(hwdev == NULL ? NULL : &hwdev->dev, size, 
dma_handle, GFP_ATOMIC);
+}
+
+static inline void
+pci_free_consistent(struct pci_dev *hwdev, size_t size,
+                   void *vaddr, dma_addr_t dma_handle)
+{
+       dma_free_coherent(hwdev == NULL ? NULL : &hwdev->dev, size, vaddr, 
dma_handle);
+}
+
+static inline dma_addr_t
+pci_map_single(struct pci_dev *hwdev, void *ptr, size_t size, int direction)
+{
+       return dma_map_single(hwdev == NULL ? NULL : &hwdev->dev, ptr, size, 
(enum dma_data_direction)direction);
+}
+
+static inline void
+pci_unmap_single(struct pci_dev *hwdev, dma_addr_t dma_addr,
+                size_t size, int direction)
+{
+       dma_unmap_single(hwdev == NULL ? NULL : &hwdev->dev, dma_addr, size, 
(enum dma_data_direction)direction);
+}
+
+static inline dma_addr_t
+pci_map_page(struct pci_dev *hwdev, struct page *page,
+            unsigned long offset, size_t size, int direction)
+{
+       return dma_map_page(hwdev == NULL ? NULL : &hwdev->dev, page, offset, 
size, (enum dma_data_direction)direction);
+}
+
+static inline void
+pci_unmap_page(struct pci_dev *hwdev, dma_addr_t dma_address,
+              size_t size, int direction)
+{
+       dma_unmap_page(hwdev == NULL ? NULL : &hwdev->dev, dma_address, size, 
(enum dma_data_direction)direction);
+}
+
+static inline int
+pci_map_sg(struct pci_dev *hwdev, struct scatterlist *sg,
+          int nents, int direction)
+{
+       return dma_map_sg(hwdev == NULL ? NULL : &hwdev->dev, sg, nents, (enum 
dma_data_direction)direction);
+}
+
+static inline void
+pci_unmap_sg(struct pci_dev *hwdev, struct scatterlist *sg,
+            int nents, int direction)
+{
+       dma_unmap_sg(hwdev == NULL ? NULL : &hwdev->dev, sg, nents, (enum 
dma_data_direction)direction);
+}
+
+static inline void
+pci_dma_sync_single_for_cpu(struct pci_dev *hwdev, dma_addr_t dma_handle,
+                   size_t size, int direction)
+{
+       dma_sync_single_for_cpu(hwdev == NULL ? NULL : &hwdev->dev, dma_handle, 
size, (enum dma_data_direction)direction);
+}
+
+static inline void
+pci_dma_sync_single_for_device(struct pci_dev *hwdev, dma_addr_t dma_handle,
+                   size_t size, int direction)
+{
+       dma_sync_single_for_device(hwdev == NULL ? NULL : &hwdev->dev, 
dma_handle, size, (enum dma_data_direction)direction);
+}
+
+static inline void
+pci_dma_sync_sg_for_cpu(struct pci_dev *hwdev, struct scatterlist *sg,
+               int nelems, int direction)
+{
+       dma_sync_sg_for_cpu(hwdev == NULL ? NULL : &hwdev->dev, sg, nelems, 
(enum dma_data_direction)direction);
+}
+
+static inline void
+pci_dma_sync_sg_for_device(struct pci_dev *hwdev, struct scatterlist *sg,
+               int nelems, int direction)
+{
+       dma_sync_sg_for_device(hwdev == NULL ? NULL : &hwdev->dev, sg, nelems, 
(enum dma_data_direction)direction);
+}
+
+static inline int
+pci_dma_mapping_error(dma_addr_t dma_addr)
+{
+       return dma_mapping_error(dma_addr);
+}
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/pci.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/pci.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,34 @@
+/*
+ * linux/include/asm-generic/pci.h
+ *
+ *  Copyright (C) 2003 Russell King
+ */
+#ifndef _ASM_GENERIC_PCI_H
+#define _ASM_GENERIC_PCI_H
+
+/**
+ * pcibios_resource_to_bus - convert resource to PCI bus address
+ * @dev: device which owns this resource
+ * @region: converted bus-centric region (start,end)
+ * @res: resource to convert
+ *
+ * Convert a resource to a PCI device bus address or bus window.
+ */
+static inline void
+pcibios_resource_to_bus(struct pci_dev *dev, struct pci_bus_region *region,
+                        struct resource *res)
+{
+       region->start = res->start;
+       region->end = res->end;
+}
+
+#define pcibios_scan_all_fns(a, b)     0
+
+#ifndef HAVE_ARCH_PCI_GET_LEGACY_IDE_IRQ
+static inline int pci_get_legacy_ide_irq(struct pci_dev *dev, int channel)
+{
+       return channel ? 15 : 14;
+}
+#endif /* HAVE_ARCH_PCI_GET_LEGACY_IDE_IRQ */
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/pgtable-nopud.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/pgtable-nopud.h    Tue Aug 16 
04:15:23 2005
@@ -0,0 +1,56 @@
+#ifndef _PGTABLE_NOPUD_H
+#define _PGTABLE_NOPUD_H
+
+#ifndef __ASSEMBLY__
+
+/*
+ * Having the pud type consist of a pgd gets the size right, and allows
+ * us to conceptually access the pgd entry that this pud is folded into
+ * without casting.
+ */
+typedef struct { pgd_t pgd; } pud_t;
+
+#define PUD_SHIFT      PGDIR_SHIFT
+#define PTRS_PER_PUD   1
+#define PUD_SIZE       (1UL << PUD_SHIFT)
+#define PUD_MASK       (~(PUD_SIZE-1))
+
+/*
+ * The "pgd_xxx()" functions here are trivial for a folded two-level
+ * setup: the pud is never bad, and a pud always exists (as it's folded
+ * into the pgd entry)
+ */
+static inline int pgd_none(pgd_t pgd)          { return 0; }
+static inline int pgd_bad(pgd_t pgd)           { return 0; }
+static inline int pgd_present(pgd_t pgd)       { return 1; }
+static inline void pgd_clear(pgd_t *pgd)       { }
+#define pud_ERROR(pud)                         (pgd_ERROR((pud).pgd))
+
+#define pgd_populate(mm, pgd, pud)             do { } while (0)
+/*
+ * (puds are folded into pgds so this doesn't get actually called,
+ * but the define is needed for a generic inline function.)
+ */
+#define set_pgd(pgdptr, pgdval)                        set_pud((pud_t 
*)(pgdptr), (pud_t) { pgdval })
+
+static inline pud_t * pud_offset(pgd_t * pgd, unsigned long address)
+{
+       return (pud_t *)pgd;
+}
+
+#define pud_val(x)                             (pgd_val((x).pgd))
+#define __pud(x)                               ((pud_t) { __pgd(x) } )
+
+#define pgd_page(pgd)                          (pud_page((pud_t){ pgd }))
+#define pgd_page_kernel(pgd)                   (pud_page_kernel((pud_t){ pgd 
}))
+
+/*
+ * allocating and freeing a pud is trivial: the 1-entry pud is
+ * inside the pgd, so has no extra memory associated with it.
+ */
+#define pud_alloc_one(mm, address)             NULL
+#define pud_free(x)                            do { } while (0)
+#define __pud_free_tlb(tlb, x)                 do { } while (0)
+
+#endif /* __ASSEMBLY__ */
+#endif /* _PGTABLE_NOPUD_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/pgtable.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/pgtable.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,137 @@
+#ifndef _ASM_GENERIC_PGTABLE_H
+#define _ASM_GENERIC_PGTABLE_H
+
+#ifndef __HAVE_ARCH_PTEP_ESTABLISH
+/*
+ * Establish a new mapping:
+ *  - flush the old one
+ *  - update the page tables
+ *  - inform the TLB about the new one
+ *
+ * We hold the mm semaphore for reading and vma->vm_mm->page_table_lock.
+ *
+ * Note: the old pte is known to not be writable, so we don't need to
+ * worry about dirty bits etc getting lost.
+ */
+#ifndef __HAVE_ARCH_SET_PTE_ATOMIC
+#define ptep_establish(__vma, __address, __ptep, __entry)              \
+do {                                                                   \
+       set_pte(__ptep, __entry);                                       \
+       flush_tlb_page(__vma, __address);                               \
+} while (0)
+#else /* __HAVE_ARCH_SET_PTE_ATOMIC */
+#define ptep_establish(__vma, __address, __ptep, __entry)              \
+do {                                                                   \
+       set_pte_atomic(__ptep, __entry);                                \
+       flush_tlb_page(__vma, __address);                               \
+} while (0)
+#endif /* __HAVE_ARCH_SET_PTE_ATOMIC */
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_SET_ACCESS_FLAGS
+/*
+ * Largely same as above, but only sets the access flags (dirty,
+ * accessed, and writable). Furthermore, we know it always gets set
+ * to a "more permissive" setting, which allows most architectures
+ * to optimize this.
+ */
+#define ptep_set_access_flags(__vma, __address, __ptep, __entry, __dirty) \
+do {                                                                     \
+       set_pte(__ptep, __entry);                                         \
+       flush_tlb_page(__vma, __address);                                 \
+} while (0)
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_TEST_AND_CLEAR_YOUNG
+static inline int ptep_test_and_clear_young(pte_t *ptep)
+{
+       pte_t pte = *ptep;
+       if (!pte_young(pte))
+               return 0;
+       set_pte(ptep, pte_mkold(pte));
+       return 1;
+}
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_CLEAR_YOUNG_FLUSH
+#define ptep_clear_flush_young(__vma, __address, __ptep)               \
+({                                                                     \
+       int __young = ptep_test_and_clear_young(__ptep);                \
+       if (__young)                                                    \
+               flush_tlb_page(__vma, __address);                       \
+       __young;                                                        \
+})
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_TEST_AND_CLEAR_DIRTY
+static inline int ptep_test_and_clear_dirty(pte_t *ptep)
+{
+       pte_t pte = *ptep;
+       if (!pte_dirty(pte))
+               return 0;
+       set_pte(ptep, pte_mkclean(pte));
+       return 1;
+}
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_CLEAR_DIRTY_FLUSH
+#define ptep_clear_flush_dirty(__vma, __address, __ptep)               \
+({                                                                     \
+       int __dirty = ptep_test_and_clear_dirty(__ptep);                \
+       if (__dirty)                                                    \
+               flush_tlb_page(__vma, __address);                       \
+       __dirty;                                                        \
+})
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_GET_AND_CLEAR
+static inline pte_t ptep_get_and_clear(pte_t *ptep)
+{
+       pte_t pte = *ptep;
+       pte_clear(ptep);
+       return pte;
+}
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_CLEAR_FLUSH
+#define ptep_clear_flush(__vma, __address, __ptep)                     \
+({                                                                     \
+       pte_t __pte = ptep_get_and_clear(__ptep);                       \
+       flush_tlb_page(__vma, __address);                               \
+       __pte;                                                          \
+})
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_SET_WRPROTECT
+static inline void ptep_set_wrprotect(pte_t *ptep)
+{
+       pte_t old_pte = *ptep;
+       set_pte(ptep, pte_wrprotect(old_pte));
+}
+#endif
+
+#ifndef __HAVE_ARCH_PTEP_MKDIRTY
+static inline void ptep_mkdirty(pte_t *ptep)
+{
+       pte_t old_pte = *ptep;
+       set_pte(ptep, pte_mkdirty(old_pte));
+}
+#endif
+
+#ifndef __HAVE_ARCH_PTE_SAME
+#define pte_same(A,B)  (pte_val(A) == pte_val(B))
+#endif
+
+#ifndef __HAVE_ARCH_PAGE_TEST_AND_CLEAR_DIRTY
+#define page_test_and_clear_dirty(page) (0)
+#endif
+
+#ifndef __HAVE_ARCH_PAGE_TEST_AND_CLEAR_YOUNG
+#define page_test_and_clear_young(page) (0)
+#endif
+
+#ifndef __HAVE_ARCH_PGD_OFFSET_GATE
+#define pgd_offset_gate(mm, addr)      pgd_offset(mm, addr)
+#endif
+
+#endif /* _ASM_GENERIC_PGTABLE_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/sections.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/sections.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,13 @@
+#ifndef _ASM_GENERIC_SECTIONS_H_
+#define _ASM_GENERIC_SECTIONS_H_
+
+/* References to section boundaries */
+
+extern char _text[], _stext[], _etext[];
+extern char _data[], _sdata[], _edata[];
+extern char __bss_start[], __bss_stop[];
+extern char __init_begin[], __init_end[];
+extern char _sinittext[], _einittext[];
+extern char _end[];
+
+#endif /* _ASM_GENERIC_SECTIONS_H_ */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/topology.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/topology.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,48 @@
+/*
+ * linux/include/asm-generic/topology.h
+ *
+ * Written by: Matthew Dobson, IBM Corporation
+ *
+ * Copyright (C) 2002, IBM Corp.
+ *
+ * All rights reserved.          
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or
+ * NON INFRINGEMENT.  See the GNU General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * Send feedback to <colpatch@xxxxxxxxxx>
+ */
+#ifndef _ASM_GENERIC_TOPOLOGY_H
+#define _ASM_GENERIC_TOPOLOGY_H
+
+/* Other architectures wishing to use this simple topology API should fill
+   in the below functions as appropriate in their own <asm/topology.h> file. */
+#ifndef cpu_to_node
+#define cpu_to_node(cpu)       (0)
+#endif
+#ifndef parent_node
+#define parent_node(node)      (0)
+#endif
+#ifndef node_to_cpumask
+#define node_to_cpumask(node)  (cpu_online_map)
+#endif
+#ifndef node_to_first_cpu
+#define node_to_first_cpu(node)        (0)
+#endif
+#ifndef pcibus_to_cpumask
+#define pcibus_to_cpumask(bus) (cpu_online_map)
+#endif
+
+#endif /* _ASM_GENERIC_TOPOLOGY_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm-generic/vmlinux.lds.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm-generic/vmlinux.lds.h      Tue Aug 16 
04:15:23 2005
@@ -0,0 +1,90 @@
+#ifndef LOAD_OFFSET
+#define LOAD_OFFSET 0
+#endif
+
+#ifndef VMLINUX_SYMBOL
+#define VMLINUX_SYMBOL(_sym_) _sym_
+#endif
+
+#define RODATA                                                         \
+       .rodata           : AT(ADDR(.rodata) - LOAD_OFFSET) {           \
+               *(.rodata) *(.rodata.*)                                 \
+               *(__vermagic)           /* Kernel version magic */      \
+       }                                                               \
+                                                                       \
+       .rodata1          : AT(ADDR(.rodata1) - LOAD_OFFSET) {          \
+               *(.rodata1)                                             \
+       }                                                               \
+                                                                       \
+       /* PCI quirks */                                                \
+       .pci_fixup        : AT(ADDR(.pci_fixup) - LOAD_OFFSET) {        \
+               VMLINUX_SYMBOL(__start_pci_fixups_early) = .;           \
+               *(.pci_fixup_early)                                     \
+               VMLINUX_SYMBOL(__end_pci_fixups_early) = .;             \
+               VMLINUX_SYMBOL(__start_pci_fixups_header) = .;          \
+               *(.pci_fixup_header)                                    \
+               VMLINUX_SYMBOL(__end_pci_fixups_header) = .;            \
+               VMLINUX_SYMBOL(__start_pci_fixups_final) = .;           \
+               *(.pci_fixup_final)                                     \
+               VMLINUX_SYMBOL(__end_pci_fixups_final) = .;             \
+               VMLINUX_SYMBOL(__start_pci_fixups_enable) = .;          \
+               *(.pci_fixup_enable)                                    \
+               VMLINUX_SYMBOL(__end_pci_fixups_enable) = .;            \
+       }                                                               \
+                                                                       \
+       /* Kernel symbol table: Normal symbols */                       \
+       __ksymtab         : AT(ADDR(__ksymtab) - LOAD_OFFSET) {         \
+               VMLINUX_SYMBOL(__start___ksymtab) = .;                  \
+               *(__ksymtab)                                            \
+               VMLINUX_SYMBOL(__stop___ksymtab) = .;                   \
+       }                                                               \
+                                                                       \
+       /* Kernel symbol table: GPL-only symbols */                     \
+       __ksymtab_gpl     : AT(ADDR(__ksymtab_gpl) - LOAD_OFFSET) {     \
+               VMLINUX_SYMBOL(__start___ksymtab_gpl) = .;              \
+               *(__ksymtab_gpl)                                        \
+               VMLINUX_SYMBOL(__stop___ksymtab_gpl) = .;               \
+       }                                                               \
+                                                                       \
+       /* Kernel symbol table: Normal symbols */                       \
+       __kcrctab         : AT(ADDR(__kcrctab) - LOAD_OFFSET) {         \
+               VMLINUX_SYMBOL(__start___kcrctab) = .;                  \
+               *(__kcrctab)                                            \
+               VMLINUX_SYMBOL(__stop___kcrctab) = .;                   \
+       }                                                               \
+                                                                       \
+       /* Kernel symbol table: GPL-only symbols */                     \
+       __kcrctab_gpl     : AT(ADDR(__kcrctab_gpl) - LOAD_OFFSET) {     \
+               VMLINUX_SYMBOL(__start___kcrctab_gpl) = .;              \
+               *(__kcrctab_gpl)                                        \
+               VMLINUX_SYMBOL(__stop___kcrctab_gpl) = .;               \
+       }                                                               \
+                                                                       \
+       /* Kernel symbol table: strings */                              \
+        __ksymtab_strings : AT(ADDR(__ksymtab_strings) - LOAD_OFFSET) {        
\
+               *(__ksymtab_strings)                                    \
+       }                                                               \
+                                                                       \
+       /* Built-in module parameters. */                               \
+       __param : AT(ADDR(__param) - LOAD_OFFSET) {                     \
+               VMLINUX_SYMBOL(__start___param) = .;                    \
+               *(__param)                                              \
+               VMLINUX_SYMBOL(__stop___param) = .;                     \
+       }
+
+#define SECURITY_INIT                                                  \
+       .security_initcall.init : {                                     \
+               VMLINUX_SYMBOL(__security_initcall_start) = .;          \
+               *(.security_initcall.init)                              \
+               VMLINUX_SYMBOL(__security_initcall_end) = .;            \
+       }
+
+#define SCHED_TEXT                                                     \
+               VMLINUX_SYMBOL(__sched_text_start) = .;                 \
+               *(.sched.text)                                          \
+               VMLINUX_SYMBOL(__sched_text_end) = .;
+
+#define LOCK_TEXT                                                      \
+               VMLINUX_SYMBOL(__lock_text_start) = .;                  \
+               *(.spinlock.text)                                       \
+               VMLINUX_SYMBOL(__lock_text_end) = .;
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/acpi.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/acpi.h     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,112 @@
+/*
+ *  asm-ia64/acpi.h
+ *
+ *  Copyright (C) 1999 VA Linux Systems
+ *  Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ *  Copyright (C) 2000,2001 J.I. Lee <jung-ik.lee@xxxxxxxxx>
+ *  Copyright (C) 2001,2002 Paul Diefenbaugh <paul.s.diefenbaugh@xxxxxxxxx>
+ *
+ * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ */
+
+#ifndef _ASM_ACPI_H
+#define _ASM_ACPI_H
+
+#ifdef __KERNEL__
+
+#include <linux/init.h>
+#include <linux/numa.h>
+#include <asm/system.h>
+
+#define COMPILER_DEPENDENT_INT64       long
+#define COMPILER_DEPENDENT_UINT64      unsigned long
+
+/*
+ * Calling conventions:
+ *
+ * ACPI_SYSTEM_XFACE        - Interfaces to host OS (handlers, threads)
+ * ACPI_EXTERNAL_XFACE      - External ACPI interfaces
+ * ACPI_INTERNAL_XFACE      - Internal ACPI interfaces
+ * ACPI_INTERNAL_VAR_XFACE  - Internal variable-parameter list interfaces
+ */
+#define ACPI_SYSTEM_XFACE
+#define ACPI_EXTERNAL_XFACE
+#define ACPI_INTERNAL_XFACE
+#define ACPI_INTERNAL_VAR_XFACE
+
+/* Asm macros */
+
+#define ACPI_ASM_MACROS
+#define BREAKPOINT3
+#define ACPI_DISABLE_IRQS() local_irq_disable()
+#define ACPI_ENABLE_IRQS()  local_irq_enable()
+#define ACPI_FLUSH_CPU_CACHE()
+
+static inline int
+ia64_acpi_acquire_global_lock (unsigned int *lock)
+{
+       unsigned int old, new, val;
+       do {
+               old = *lock;
+               new = (((old & ~0x3) + 2) + ((old >> 1) & 0x1));
+               val = ia64_cmpxchg4_acq(lock, new, old);
+       } while (unlikely (val != old));
+       return (new < 3) ? -1 : 0;
+}
+
+static inline int
+ia64_acpi_release_global_lock (unsigned int *lock)
+{
+       unsigned int old, new, val;
+       do {
+               old = *lock;
+               new = old & ~0x3;
+               val = ia64_cmpxchg4_acq(lock, new, old);
+       } while (unlikely (val != old));
+       return old & 0x1;
+}
+
+#define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq)                           \
+       ((Acq) = ia64_acpi_acquire_global_lock((unsigned int *) GLptr))
+
+#define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq)                           \
+       ((Acq) = ia64_acpi_release_global_lock((unsigned int *) GLptr))
+
+#define acpi_disabled 0        /* ACPI always enabled on IA64 */
+#define acpi_noirq 0   /* ACPI always enabled on IA64 */
+#define acpi_pci_disabled 0 /* ACPI PCI always enabled on IA64 */
+#define acpi_strict 1  /* no ACPI spec workarounds on IA64 */
+static inline void disable_acpi(void) { }
+
+const char *acpi_get_sysname (void);
+int acpi_request_vector (u32 int_type);
+int acpi_gsi_to_irq (u32 gsi, unsigned int *irq);
+
+#ifdef CONFIG_ACPI_NUMA
+/* Proximity bitmap length; _PXM is at most 255 (8 bit)*/
+#define MAX_PXM_DOMAINS (256)
+extern int __devinitdata pxm_to_nid_map[MAX_PXM_DOMAINS];
+extern int __initdata nid_to_pxm_map[MAX_NUMNODES];
+#endif
+
+extern u16 ia64_acpiid_to_sapicid[];
+
+#endif /*__KERNEL__*/
+
+#endif /*_ASM_ACPI_H*/
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/asmmacro.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/asmmacro.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,111 @@
+#ifndef _ASM_IA64_ASMMACRO_H
+#define _ASM_IA64_ASMMACRO_H
+
+/*
+ * Copyright (C) 2000-2001, 2003-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#define ENTRY(name)                            \
+       .align 32;                              \
+       .proc name;                             \
+name:
+
+#define ENTRY_MIN_ALIGN(name)                  \
+       .align 16;                              \
+       .proc name;                             \
+name:
+
+#define GLOBAL_ENTRY(name)                     \
+       .global name;                           \
+       ENTRY(name)
+
+#define END(name)                              \
+       .endp name
+
+/*
+ * Helper macros to make unwind directives more readable:
+ */
+
+/* prologue_gr: */
+#define ASM_UNW_PRLG_RP                        0x8
+#define ASM_UNW_PRLG_PFS               0x4
+#define ASM_UNW_PRLG_PSP               0x2
+#define ASM_UNW_PRLG_PR                        0x1
+#define ASM_UNW_PRLG_GRSAVE(ninputs)   (32+(ninputs))
+
+/*
+ * Helper macros for accessing user memory.
+ */
+
+       .section "__ex_table", "a"              // declare section & section 
attributes
+       .previous
+
+# define EX(y,x...)                            \
+       .xdata4 "__ex_table", 99f-., y-.;       \
+  [99:]        x
+# define EXCLR(y,x...)                         \
+       .xdata4 "__ex_table", 99f-., y-.+4;     \
+  [99:]        x
+
+/*
+ * Mark instructions that need a load of a virtual address patched to be
+ * a load of a physical address.  We use this either in critical performance
+ * path (ivt.S - TLB miss processing) or in places where it might not be
+ * safe to use a "tpa" instruction (mca_asm.S - error recovery).
+ */
+       .section ".data.patch.vtop", "a"        // declare section & section 
attributes
+       .previous
+
+#define        LOAD_PHYSICAL(pr, reg, obj)             \
+[1:](pr)movl reg = obj;                                \
+       .xdata4 ".data.patch.vtop", 1b-.
+
+/*
+ * For now, we always put in the McKinley E9 workaround.  On CPUs that don't 
need it,
+ * we'll patch out the work-around bundles with NOPs, so their impact is 
minimal.
+ */
+#define DO_MCKINLEY_E9_WORKAROUND
+
+#ifdef DO_MCKINLEY_E9_WORKAROUND
+       .section ".data.patch.mckinley_e9", "a"
+       .previous
+/* workaround for Itanium 2 Errata 9: */
+# define FSYS_RETURN                                   \
+       .xdata4 ".data.patch.mckinley_e9", 1f-.;        \
+1:{ .mib;                                              \
+       nop.m 0;                                        \
+       mov r16=ar.pfs;                                 \
+       br.call.sptk.many b7=2f;;                       \
+  };                                                   \
+2:{ .mib;                                              \
+       nop.m 0;                                        \
+       mov ar.pfs=r16;                                 \
+       br.ret.sptk.many b6;;                           \
+  }
+#else
+# define FSYS_RETURN   br.ret.sptk.many b6
+#endif
+
+/*
+ * Up until early 2004, use of .align within a function caused bad unwind info.
+ * TEXT_ALIGN(n) expands into ".align n" if a fixed GAS is available or into 
nothing
+ * otherwise.
+ */
+#ifdef HAVE_WORKING_TEXT_ALIGN
+# define TEXT_ALIGN(n) .align n
+#else
+# define TEXT_ALIGN(n)
+#endif
+
+#ifdef HAVE_SERIALIZE_DIRECTIVE
+# define dv_serialize_data             .serialize.data
+# define dv_serialize_instruction      .serialize.instruction
+#else
+# define dv_serialize_data
+# define dv_serialize_instruction
+#endif
+
+#endif /* _ASM_IA64_ASMMACRO_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/atomic.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/atomic.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,183 @@
+#ifndef _ASM_IA64_ATOMIC_H
+#define _ASM_IA64_ATOMIC_H
+
+/*
+ * Atomic operations that C can't guarantee us.  Useful for
+ * resource counting etc..
+ *
+ * NOTE: don't mess with the types below!  The "unsigned long" and
+ * "int" types were carefully placed so as to ensure proper operation
+ * of the macros.
+ *
+ * Copyright (C) 1998, 1999, 2002-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#include <linux/types.h>
+
+#include <asm/intrinsics.h>
+
+/*
+ * On IA-64, counter must always be volatile to ensure that that the
+ * memory accesses are ordered.
+ */
+typedef struct { volatile __s32 counter; } atomic_t;
+typedef struct { volatile __s64 counter; } atomic64_t;
+
+#define ATOMIC_INIT(i)         ((atomic_t) { (i) })
+#define ATOMIC64_INIT(i)       ((atomic64_t) { (i) })
+
+#define atomic_read(v)         ((v)->counter)
+#define atomic64_read(v)       ((v)->counter)
+
+#define atomic_set(v,i)                (((v)->counter) = (i))
+#define atomic64_set(v,i)      (((v)->counter) = (i))
+
+static __inline__ int
+ia64_atomic_add (int i, atomic_t *v)
+{
+       __s32 old, new;
+       CMPXCHG_BUGCHECK_DECL
+
+       do {
+               CMPXCHG_BUGCHECK(v);
+               old = atomic_read(v);
+               new = old + i;
+       } while (ia64_cmpxchg(acq, v, old, new, sizeof(atomic_t)) != old);
+       return new;
+}
+
+static __inline__ int
+ia64_atomic64_add (__s64 i, atomic64_t *v)
+{
+       __s64 old, new;
+       CMPXCHG_BUGCHECK_DECL
+
+       do {
+               CMPXCHG_BUGCHECK(v);
+               old = atomic_read(v);
+               new = old + i;
+       } while (ia64_cmpxchg(acq, v, old, new, sizeof(atomic64_t)) != old);
+       return new;
+}
+
+static __inline__ int
+ia64_atomic_sub (int i, atomic_t *v)
+{
+       __s32 old, new;
+       CMPXCHG_BUGCHECK_DECL
+
+       do {
+               CMPXCHG_BUGCHECK(v);
+               old = atomic_read(v);
+               new = old - i;
+       } while (ia64_cmpxchg(acq, v, old, new, sizeof(atomic_t)) != old);
+       return new;
+}
+
+static __inline__ int
+ia64_atomic64_sub (__s64 i, atomic64_t *v)
+{
+       __s64 old, new;
+       CMPXCHG_BUGCHECK_DECL
+
+       do {
+               CMPXCHG_BUGCHECK(v);
+               old = atomic_read(v);
+               new = old - i;
+       } while (ia64_cmpxchg(acq, v, old, new, sizeof(atomic64_t)) != old);
+       return new;
+}
+
+#define atomic_add_return(i,v)                                         \
+({                                                                     \
+       int __ia64_aar_i = (i);                                         \
+       (__builtin_constant_p(i)                                        \
+        && (   (__ia64_aar_i ==  1) || (__ia64_aar_i ==   4)           \
+            || (__ia64_aar_i ==  8) || (__ia64_aar_i ==  16)           \
+            || (__ia64_aar_i == -1) || (__ia64_aar_i ==  -4)           \
+            || (__ia64_aar_i == -8) || (__ia64_aar_i == -16)))         \
+               ? ia64_fetch_and_add(__ia64_aar_i, &(v)->counter)       \
+               : ia64_atomic_add(__ia64_aar_i, v);                     \
+})
+
+#define atomic64_add_return(i,v)                                       \
+({                                                                     \
+       long __ia64_aar_i = (i);                                        \
+       (__builtin_constant_p(i)                                        \
+        && (   (__ia64_aar_i ==  1) || (__ia64_aar_i ==   4)           \
+            || (__ia64_aar_i ==  8) || (__ia64_aar_i ==  16)           \
+            || (__ia64_aar_i == -1) || (__ia64_aar_i ==  -4)           \
+            || (__ia64_aar_i == -8) || (__ia64_aar_i == -16)))         \
+               ? ia64_fetch_and_add(__ia64_aar_i, &(v)->counter)       \
+               : ia64_atomic64_add(__ia64_aar_i, v);                   \
+})
+
+/*
+ * Atomically add I to V and return TRUE if the resulting value is
+ * negative.
+ */
+static __inline__ int
+atomic_add_negative (int i, atomic_t *v)
+{
+       return atomic_add_return(i, v) < 0;
+}
+
+static __inline__ int
+atomic64_add_negative (__s64 i, atomic64_t *v)
+{
+       return atomic64_add_return(i, v) < 0;
+}
+
+#define atomic_sub_return(i,v)                                         \
+({                                                                     \
+       int __ia64_asr_i = (i);                                         \
+       (__builtin_constant_p(i)                                        \
+        && (   (__ia64_asr_i ==   1) || (__ia64_asr_i ==   4)          \
+            || (__ia64_asr_i ==   8) || (__ia64_asr_i ==  16)          \
+            || (__ia64_asr_i ==  -1) || (__ia64_asr_i ==  -4)          \
+            || (__ia64_asr_i ==  -8) || (__ia64_asr_i == -16)))        \
+               ? ia64_fetch_and_add(-__ia64_asr_i, &(v)->counter)      \
+               : ia64_atomic_sub(__ia64_asr_i, v);                     \
+})
+
+#define atomic64_sub_return(i,v)                                       \
+({                                                                     \
+       long __ia64_asr_i = (i);                                        \
+       (__builtin_constant_p(i)                                        \
+        && (   (__ia64_asr_i ==   1) || (__ia64_asr_i ==   4)          \
+            || (__ia64_asr_i ==   8) || (__ia64_asr_i ==  16)          \
+            || (__ia64_asr_i ==  -1) || (__ia64_asr_i ==  -4)          \
+            || (__ia64_asr_i ==  -8) || (__ia64_asr_i == -16)))        \
+               ? ia64_fetch_and_add(-__ia64_asr_i, &(v)->counter)      \
+               : ia64_atomic64_sub(__ia64_asr_i, v);                   \
+})
+
+#define atomic_dec_return(v)           atomic_sub_return(1, (v))
+#define atomic_inc_return(v)           atomic_add_return(1, (v))
+#define atomic64_dec_return(v)         atomic64_sub_return(1, (v))
+#define atomic64_inc_return(v)         atomic64_add_return(1, (v))
+
+#define atomic_sub_and_test(i,v)       (atomic_sub_return((i), (v)) == 0)
+#define atomic_dec_and_test(v)         (atomic_sub_return(1, (v)) == 0)
+#define atomic_inc_and_test(v)         (atomic_add_return(1, (v)) == 0)
+#define atomic64_sub_and_test(i,v)     (atomic64_sub_return((i), (v)) == 0)
+#define atomic64_dec_and_test(v)       (atomic64_sub_return(1, (v)) == 0)
+#define atomic64_inc_and_test(v)       (atomic64_add_return(1, (v)) == 0)
+
+#define atomic_add(i,v)                        atomic_add_return((i), (v))
+#define atomic_sub(i,v)                        atomic_sub_return((i), (v))
+#define atomic_inc(v)                  atomic_add(1, (v))
+#define atomic_dec(v)                  atomic_sub(1, (v))
+
+#define atomic64_add(i,v)              atomic64_add_return((i), (v))
+#define atomic64_sub(i,v)              atomic64_sub_return((i), (v))
+#define atomic64_inc(v)                        atomic64_add(1, (v))
+#define atomic64_dec(v)                        atomic64_sub(1, (v))
+
+/* Atomic operations are already serializing */
+#define smp_mb__before_atomic_dec()    barrier()
+#define smp_mb__after_atomic_dec()     barrier()
+#define smp_mb__before_atomic_inc()    barrier()
+#define smp_mb__after_atomic_inc()     barrier()
+
+#endif /* _ASM_IA64_ATOMIC_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/bitops.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/bitops.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,410 @@
+#ifndef _ASM_IA64_BITOPS_H
+#define _ASM_IA64_BITOPS_H
+
+/*
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * 02/06/02 find_next_bit() and find_first_bit() added from Erich Focht's ia64 
O(1)
+ *         scheduler patch
+ */
+
+#include <linux/compiler.h>
+#include <linux/types.h>
+#include <asm/bitops.h>
+#include <asm/intrinsics.h>
+
+/**
+ * set_bit - Atomically set a bit in memory
+ * @nr: the bit to set
+ * @addr: the address to start counting from
+ *
+ * This function is atomic and may not be reordered.  See __set_bit()
+ * if you do not require the atomic guarantees.
+ * Note that @nr may be almost arbitrarily large; this function is not
+ * restricted to acting on a single-word quantity.
+ *
+ * The address must be (at least) "long" aligned.
+ * Note that there are driver (e.g., eepro100) which use these operations to 
operate on
+ * hw-defined data-structures, so we can't easily change these operations to 
force a
+ * bigger alignment.
+ *
+ * bit 0 is the LSB of addr; bit 32 is the LSB of (addr+1).
+ */
+static __inline__ void
+set_bit (int nr, volatile void *addr)
+{
+       __u32 bit, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       bit = 1 << (nr & 31);
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old | bit;
+       } while (cmpxchg_acq(m, old, new) != old);
+}
+
+/**
+ * __set_bit - Set a bit in memory
+ * @nr: the bit to set
+ * @addr: the address to start counting from
+ *
+ * Unlike set_bit(), this function is non-atomic and may be reordered.
+ * If it's called on the same region of memory simultaneously, the effect
+ * may be that only one operation succeeds.
+ */
+static __inline__ void
+__set_bit (int nr, volatile void *addr)
+{
+       *((__u32 *) addr + (nr >> 5)) |= (1 << (nr & 31));
+}
+
+/*
+ * clear_bit() has "acquire" semantics.
+ */
+#define smp_mb__before_clear_bit()     smp_mb()
+#define smp_mb__after_clear_bit()      do { /* skip */; } while (0)
+
+/**
+ * clear_bit - Clears a bit in memory
+ * @nr: Bit to clear
+ * @addr: Address to start counting from
+ *
+ * clear_bit() is atomic and may not be reordered.  However, it does
+ * not contain a memory barrier, so if it is used for locking purposes,
+ * you should call smp_mb__before_clear_bit() and/or smp_mb__after_clear_bit()
+ * in order to ensure changes are visible on other processors.
+ */
+static __inline__ void
+clear_bit (int nr, volatile void *addr)
+{
+       __u32 mask, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       mask = ~(1 << (nr & 31));
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old & mask;
+       } while (cmpxchg_acq(m, old, new) != old);
+}
+
+/**
+ * __clear_bit - Clears a bit in memory (non-atomic version)
+ */
+static __inline__ void
+__clear_bit (int nr, volatile void *addr)
+{
+       volatile __u32 *p = (__u32 *) addr + (nr >> 5);
+       __u32 m = 1 << (nr & 31);
+       *p &= ~m;
+}
+
+/**
+ * change_bit - Toggle a bit in memory
+ * @nr: Bit to clear
+ * @addr: Address to start counting from
+ *
+ * change_bit() is atomic and may not be reordered.
+ * Note that @nr may be almost arbitrarily large; this function is not
+ * restricted to acting on a single-word quantity.
+ */
+static __inline__ void
+change_bit (int nr, volatile void *addr)
+{
+       __u32 bit, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       bit = (1 << (nr & 31));
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old ^ bit;
+       } while (cmpxchg_acq(m, old, new) != old);
+}
+
+/**
+ * __change_bit - Toggle a bit in memory
+ * @nr: the bit to set
+ * @addr: the address to start counting from
+ *
+ * Unlike change_bit(), this function is non-atomic and may be reordered.
+ * If it's called on the same region of memory simultaneously, the effect
+ * may be that only one operation succeeds.
+ */
+static __inline__ void
+__change_bit (int nr, volatile void *addr)
+{
+       *((__u32 *) addr + (nr >> 5)) ^= (1 << (nr & 31));
+}
+
+/**
+ * test_and_set_bit - Set a bit and return its old value
+ * @nr: Bit to set
+ * @addr: Address to count from
+ *
+ * This operation is atomic and cannot be reordered.  
+ * It also implies a memory barrier.
+ */
+static __inline__ int
+test_and_set_bit (int nr, volatile void *addr)
+{
+       __u32 bit, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       bit = 1 << (nr & 31);
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old | bit;
+       } while (cmpxchg_acq(m, old, new) != old);
+       return (old & bit) != 0;
+}
+
+/**
+ * __test_and_set_bit - Set a bit and return its old value
+ * @nr: Bit to set
+ * @addr: Address to count from
+ *
+ * This operation is non-atomic and can be reordered.  
+ * If two examples of this operation race, one can appear to succeed
+ * but actually fail.  You must protect multiple accesses with a lock.
+ */
+static __inline__ int
+__test_and_set_bit (int nr, volatile void *addr)
+{
+       __u32 *p = (__u32 *) addr + (nr >> 5);
+       __u32 m = 1 << (nr & 31);
+       int oldbitset = (*p & m) != 0;
+
+       *p |= m;
+       return oldbitset;
+}
+
+/**
+ * test_and_clear_bit - Clear a bit and return its old value
+ * @nr: Bit to set
+ * @addr: Address to count from
+ *
+ * This operation is atomic and cannot be reordered.  
+ * It also implies a memory barrier.
+ */
+static __inline__ int
+test_and_clear_bit (int nr, volatile void *addr)
+{
+       __u32 mask, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       mask = ~(1 << (nr & 31));
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old & mask;
+       } while (cmpxchg_acq(m, old, new) != old);
+       return (old & ~mask) != 0;
+}
+
+/**
+ * __test_and_clear_bit - Clear a bit and return its old value
+ * @nr: Bit to set
+ * @addr: Address to count from
+ *
+ * This operation is non-atomic and can be reordered.  
+ * If two examples of this operation race, one can appear to succeed
+ * but actually fail.  You must protect multiple accesses with a lock.
+ */
+static __inline__ int
+__test_and_clear_bit(int nr, volatile void * addr)
+{
+       __u32 *p = (__u32 *) addr + (nr >> 5);
+       __u32 m = 1 << (nr & 31);
+       int oldbitset = *p & m;
+
+       *p &= ~m;
+       return oldbitset;
+}
+
+/**
+ * test_and_change_bit - Change a bit and return its old value
+ * @nr: Bit to set
+ * @addr: Address to count from
+ *
+ * This operation is atomic and cannot be reordered.  
+ * It also implies a memory barrier.
+ */
+static __inline__ int
+test_and_change_bit (int nr, volatile void *addr)
+{
+       __u32 bit, old, new;
+       volatile __u32 *m;
+       CMPXCHG_BUGCHECK_DECL
+
+       m = (volatile __u32 *) addr + (nr >> 5);
+       bit = (1 << (nr & 31));
+       do {
+               CMPXCHG_BUGCHECK(m);
+               old = *m;
+               new = old ^ bit;
+       } while (cmpxchg_acq(m, old, new) != old);
+       return (old & bit) != 0;
+}
+
+/*
+ * WARNING: non atomic version.
+ */
+static __inline__ int
+__test_and_change_bit (int nr, void *addr)
+{
+       __u32 old, bit = (1 << (nr & 31));
+       __u32 *m = (__u32 *) addr + (nr >> 5);
+
+       old = *m;
+       *m = old ^ bit;
+       return (old & bit) != 0;
+}
+
+static __inline__ int
+test_bit (int nr, const volatile void *addr)
+{
+       return 1 & (((const volatile __u32 *) addr)[nr >> 5] >> (nr & 31));
+}
+
+/**
+ * ffz - find the first zero bit in a long word
+ * @x: The long word to find the bit in
+ *
+ * Returns the bit-number (0..63) of the first (least significant) zero bit.  
Undefined if
+ * no zero exists, so code should check against ~0UL first...
+ */
+static inline unsigned long
+ffz (unsigned long x)
+{
+       unsigned long result;
+
+       result = ia64_popcnt(x & (~x - 1));
+       return result;
+}
+
+/**
+ * __ffs - find first bit in word.
+ * @x: The word to search
+ *
+ * Undefined if no bit exists, so code should check against 0 first.
+ */
+static __inline__ unsigned long
+__ffs (unsigned long x)
+{
+       unsigned long result;
+
+       result = ia64_popcnt((x-1) & ~x);
+       return result;
+}
+
+#ifdef __KERNEL__
+
+/*
+ * find_last_zero_bit - find the last zero bit in a 64 bit quantity
+ * @x: The value to search
+ */
+static inline unsigned long
+ia64_fls (unsigned long x)
+{
+       long double d = x;
+       long exp;
+
+       exp = ia64_getf_exp(d);
+       return exp - 0xffff;
+}
+
+static inline int
+fls (int x)
+{
+       return ia64_fls((unsigned int) x);
+}
+
+/*
+ * ffs: find first bit set. This is defined the same way as the libc and 
compiler builtin
+ * ffs routines, therefore differs in spirit from the above ffz (man ffs): it 
operates on
+ * "int" values only and the result value is the bit number + 1.  ffs(0) is 
defined to
+ * return zero.
+ */
+#define ffs(x) __builtin_ffs(x)
+
+/*
+ * hweightN: returns the hamming weight (i.e. the number
+ * of bits set) of a N-bit word
+ */
+static __inline__ unsigned long
+hweight64 (unsigned long x)
+{
+       unsigned long result;
+       result = ia64_popcnt(x);
+       return result;
+}
+
+#define hweight32(x) hweight64 ((x) & 0xfffffffful)
+#define hweight16(x) hweight64 ((x) & 0xfffful)
+#define hweight8(x)  hweight64 ((x) & 0xfful)
+
+#endif /* __KERNEL__ */
+
+extern int __find_next_zero_bit (const void *addr, unsigned long size,
+                       unsigned long offset);
+extern int __find_next_bit(const void *addr, unsigned long size,
+                       unsigned long offset);
+
+#define find_next_zero_bit(addr, size, offset) \
+                       __find_next_zero_bit((addr), (size), (offset))
+#define find_next_bit(addr, size, offset) \
+                       __find_next_bit((addr), (size), (offset))
+
+/*
+ * The optimizer actually does good code for this case..
+ */
+#define find_first_zero_bit(addr, size) find_next_zero_bit((addr), (size), 0)
+
+#define find_first_bit(addr, size) find_next_bit((addr), (size), 0)
+
+#ifdef __KERNEL__
+
+#define __clear_bit(nr, addr)          clear_bit(nr, addr)
+
+#define ext2_set_bit                   test_and_set_bit
+#define ext2_set_bit_atomic(l,n,a)     test_and_set_bit(n,a)
+#define ext2_clear_bit                 test_and_clear_bit
+#define ext2_clear_bit_atomic(l,n,a)   test_and_clear_bit(n,a)
+#define ext2_test_bit                  test_bit
+#define ext2_find_first_zero_bit       find_first_zero_bit
+#define ext2_find_next_zero_bit                find_next_zero_bit
+
+/* Bitmap functions for the minix filesystem.  */
+#define minix_test_and_set_bit(nr,addr)                
test_and_set_bit(nr,addr)
+#define minix_set_bit(nr,addr)                 set_bit(nr,addr)
+#define minix_test_and_clear_bit(nr,addr)      test_and_clear_bit(nr,addr)
+#define minix_test_bit(nr,addr)                        test_bit(nr,addr)
+#define minix_find_first_zero_bit(addr,size)   find_first_zero_bit(addr,size)
+
+static inline int
+sched_find_first_bit (unsigned long *b)
+{
+       if (unlikely(b[0]))
+               return __ffs(b[0]);
+       if (unlikely(b[1]))
+               return 64 + __ffs(b[1]);
+       return __ffs(b[2]) + 128;
+}
+
+#endif /* __KERNEL__ */
+
+#endif /* _ASM_IA64_BITOPS_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/break.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/break.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,21 @@
+#ifndef _ASM_IA64_BREAK_H
+#define _ASM_IA64_BREAK_H
+
+/*
+ * IA-64 Linux break numbers.
+ *
+ * Copyright (C) 1999 Hewlett-Packard Co
+ * Copyright (C) 1999 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+/*
+ * OS-specific debug break numbers:
+ */
+#define __IA64_BREAK_KDB               0x80100
+
+/*
+ * OS-specific break numbers:
+ */
+#define __IA64_BREAK_SYSCALL           0x100000
+
+#endif /* _ASM_IA64_BREAK_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/bug.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/bug.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,15 @@
+#ifndef _ASM_IA64_BUG_H
+#define _ASM_IA64_BUG_H
+
+#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
+# define ia64_abort()  __builtin_trap()
+#else
+# define ia64_abort()  (*(volatile int *) 0 = 0)
+#endif
+#define BUG() do { printk("kernel BUG at %s:%d!\n", __FILE__, __LINE__); 
ia64_abort(); } while (0)
+
+/* should this BUG should be made generic? */
+#define HAVE_ARCH_BUG
+#include <asm-generic/bug.h>
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/byteorder.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/byteorder.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,42 @@
+#ifndef _ASM_IA64_BYTEORDER_H
+#define _ASM_IA64_BYTEORDER_H
+
+/*
+ * Modified 1998, 1999
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co.
+ */
+
+#include <asm/types.h>
+#include <asm/intrinsics.h>
+#include <linux/compiler.h>
+
+static __inline__ __attribute_const__ __u64
+__ia64_swab64 (__u64 x)
+{
+       __u64 result;
+
+       result = ia64_mux1(x, ia64_mux1_rev);
+       return result;
+}
+
+static __inline__ __attribute_const__ __u32
+__ia64_swab32 (__u32 x)
+{
+       return __ia64_swab64(x) >> 32;
+}
+
+static __inline__ __attribute_const__ __u16
+__ia64_swab16(__u16 x)
+{
+       return __ia64_swab64(x) >> 48;
+}
+
+#define __arch__swab64(x) __ia64_swab64(x)
+#define __arch__swab32(x) __ia64_swab32(x)
+#define __arch__swab16(x) __ia64_swab16(x)
+
+#define __BYTEORDER_HAS_U64__
+
+#include <linux/byteorder/little_endian.h>
+
+#endif /* _ASM_IA64_BYTEORDER_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/cache.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/cache.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,30 @@
+#ifndef _ASM_IA64_CACHE_H
+#define _ASM_IA64_CACHE_H
+
+#include <linux/config.h>
+
+/*
+ * Copyright (C) 1998-2000 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+/* Bytes per L1 (data) cache line.  */
+#define L1_CACHE_SHIFT         CONFIG_IA64_L1_CACHE_SHIFT
+#define L1_CACHE_BYTES         (1 << L1_CACHE_SHIFT)
+
+#define L1_CACHE_SHIFT_MAX 7   /* largest L1 which this arch supports */
+
+#ifdef CONFIG_SMP
+# define SMP_CACHE_SHIFT       L1_CACHE_SHIFT
+# define SMP_CACHE_BYTES       L1_CACHE_BYTES
+#else
+  /*
+   * The "aligned" directive can only _increase_ alignment, so this is
+   * safe and provides an easy way to avoid wasting space on a
+   * uni-processor:
+   */
+# define SMP_CACHE_SHIFT       3
+# define SMP_CACHE_BYTES       (1 << 3)
+#endif
+
+#endif /* _ASM_IA64_CACHE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/cacheflush.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/cacheflush.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,50 @@
+#ifndef _ASM_IA64_CACHEFLUSH_H
+#define _ASM_IA64_CACHEFLUSH_H
+
+/*
+ * Copyright (C) 2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/page-flags.h>
+
+#include <asm/bitops.h>
+#include <asm/page.h>
+
+/*
+ * Cache flushing routines.  This is the kind of stuff that can be very 
expensive, so try
+ * to avoid them whenever possible.
+ */
+
+#define flush_cache_all()                      do { } while (0)
+#define flush_cache_mm(mm)                     do { } while (0)
+#define flush_cache_range(vma, start, end)     do { } while (0)
+#define flush_cache_page(vma, vmaddr)          do { } while (0)
+#define flush_icache_page(vma,page)            do { } while (0)
+#define flush_cache_vmap(start, end)           do { } while (0)
+#define flush_cache_vunmap(start, end)         do { } while (0)
+
+#define flush_dcache_page(page)                        \
+do {                                           \
+       clear_bit(PG_arch_1, &(page)->flags);   \
+} while (0)
+
+#define flush_dcache_mmap_lock(mapping)                do { } while (0)
+#define flush_dcache_mmap_unlock(mapping)      do { } while (0)
+
+extern void flush_icache_range (unsigned long start, unsigned long end);
+
+#define flush_icache_user_range(vma, page, user_addr, len)                     
                \
+do {                                                                           
                \
+       unsigned long _addr = (unsigned long) page_address(page) + ((user_addr) 
& ~PAGE_MASK);  \
+       flush_icache_range(_addr, _addr + (len));                               
                \
+} while (0)
+
+#define copy_to_user_page(vma, page, vaddr, dst, src, len) \
+do { memcpy(dst, src, len); \
+     flush_icache_user_range(vma, page, vaddr, len); \
+} while (0)
+#define copy_from_user_page(vma, page, vaddr, dst, src, len) \
+       memcpy(dst, src, len)
+
+#endif /* _ASM_IA64_CACHEFLUSH_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/checksum.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/checksum.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,76 @@
+#ifndef _ASM_IA64_CHECKSUM_H
+#define _ASM_IA64_CHECKSUM_H
+
+/*
+ * Modified 1998, 1999
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+/*
+ * This is a version of ip_compute_csum() optimized for IP headers,
+ * which always checksum on 4 octet boundaries.
+ */
+extern unsigned short ip_fast_csum (unsigned char * iph, unsigned int ihl);
+
+/*
+ * Computes the checksum of the TCP/UDP pseudo-header returns a 16-bit
+ * checksum, already complemented
+ */
+extern unsigned short int csum_tcpudp_magic (unsigned long saddr,
+                                            unsigned long daddr,
+                                            unsigned short len,
+                                            unsigned short proto,
+                                            unsigned int sum);
+
+extern unsigned int csum_tcpudp_nofold (unsigned long saddr,
+                                       unsigned long daddr,
+                                       unsigned short len,
+                                       unsigned short proto,
+                                       unsigned int sum);
+
+/*
+ * Computes the checksum of a memory block at buff, length len,
+ * and adds in "sum" (32-bit)
+ *
+ * returns a 32-bit number suitable for feeding into itself
+ * or csum_tcpudp_magic
+ *
+ * this function must be called with even lengths, except
+ * for the last fragment, which may be odd
+ *
+ * it's best to have buff aligned on a 32-bit boundary
+ */
+extern unsigned int csum_partial (const unsigned char * buff, int len,
+                                 unsigned int sum);
+
+/*
+ * Same as csum_partial, but copies from src while it checksums.
+ *
+ * Here it is even more important to align src and dst on a 32-bit (or
+ * even better 64-bit) boundary.
+ */
+extern unsigned int csum_partial_copy_from_user (const char *src, char *dst,
+                                                int len, unsigned int sum,
+                                                int *errp);
+
+extern unsigned int csum_partial_copy_nocheck (const char *src, char *dst,
+                                              int len, unsigned int sum);
+
+/*
+ * This routine is used for miscellaneous IP-like checksums, mainly in
+ * icmp.c
+ */
+extern unsigned short ip_compute_csum (unsigned char *buff, int len);
+
+/*
+ * Fold a partial checksum without adding pseudo headers.
+ */
+static inline unsigned short
+csum_fold (unsigned int sum)
+{
+       sum = (sum & 0xffff) + (sum >> 16);
+       sum = (sum & 0xffff) + (sum >> 16);
+       return ~sum;
+}
+
+#endif /* _ASM_IA64_CHECKSUM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/current.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/current.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,17 @@
+#ifndef _ASM_IA64_CURRENT_H
+#define _ASM_IA64_CURRENT_H
+
+/*
+ * Modified 1998-2000
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+#include <asm/intrinsics.h>
+
+/*
+ * In kernel mode, thread pointer (r13) is used to point to the current task
+ * structure.
+ */
+#define current        ((struct task_struct *) ia64_getreg(_IA64_REG_TP))
+
+#endif /* _ASM_IA64_CURRENT_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/delay.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/delay.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,97 @@
+#ifndef _ASM_IA64_DELAY_H
+#define _ASM_IA64_DELAY_H
+
+/*
+ * Delay routines using a pre-computed "cycles/usec" value.
+ *
+ * Copyright (C) 1998, 1999 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999 Asit Mallick <asit.k.mallick@xxxxxxxxx>
+ * Copyright (C) 1999 Don Dugger <don.dugger@xxxxxxxxx>
+ */
+
+#include <linux/config.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/compiler.h>
+
+#include <asm/intrinsics.h>
+#include <asm/processor.h>
+
+static __inline__ void
+ia64_set_itm (unsigned long val)
+{
+       ia64_setreg(_IA64_REG_CR_ITM, val);
+       ia64_srlz_d();
+}
+
+static __inline__ unsigned long
+ia64_get_itm (void)
+{
+       unsigned long result;
+
+       result = ia64_getreg(_IA64_REG_CR_ITM);
+       ia64_srlz_d();
+       return result;
+}
+
+static __inline__ void
+ia64_set_itv (unsigned long val)
+{
+       ia64_setreg(_IA64_REG_CR_ITV, val);
+       ia64_srlz_d();
+}
+
+static __inline__ unsigned long
+ia64_get_itv (void)
+{
+       return ia64_getreg(_IA64_REG_CR_ITV);
+}
+
+static __inline__ void
+ia64_set_itc (unsigned long val)
+{
+       ia64_setreg(_IA64_REG_AR_ITC, val);
+       ia64_srlz_d();
+}
+
+static __inline__ unsigned long
+ia64_get_itc (void)
+{
+       unsigned long result;
+
+       result = ia64_getreg(_IA64_REG_AR_ITC);
+       ia64_barrier();
+#ifdef CONFIG_ITANIUM
+       while (unlikely((__s32) result == -1)) {
+               result = ia64_getreg(_IA64_REG_AR_ITC);
+               ia64_barrier();
+       }
+#endif
+       return result;
+}
+
+extern void ia64_delay_loop (unsigned long loops);
+
+static __inline__ void
+__delay (unsigned long loops)
+{
+       if (unlikely(loops < 1))
+               return;
+
+       ia64_delay_loop (loops - 1);
+}
+
+static __inline__ void
+udelay (unsigned long usecs)
+{
+       unsigned long start = ia64_get_itc();
+       unsigned long cycles = usecs*local_cpu_data->cyc_per_usec;
+
+       while (ia64_get_itc() - start < cycles)
+               cpu_relax();
+}
+
+#endif /* _ASM_IA64_DELAY_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/div64.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/div64.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1 @@
+#include <asm-generic/div64.h>
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm/dma-mapping.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/dma-mapping.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,70 @@
+#ifndef _ASM_IA64_DMA_MAPPING_H
+#define _ASM_IA64_DMA_MAPPING_H
+
+/*
+ * Copyright (C) 2003-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#include <linux/config.h>
+#include <asm/machvec.h>
+
+#define dma_alloc_coherent     platform_dma_alloc_coherent
+#define dma_alloc_noncoherent  platform_dma_alloc_coherent     /* coherent 
mem. is cheap */
+#define dma_free_coherent      platform_dma_free_coherent
+#define dma_free_noncoherent   platform_dma_free_coherent
+#define dma_map_single         platform_dma_map_single
+#define dma_map_sg             platform_dma_map_sg
+#define dma_unmap_single       platform_dma_unmap_single
+#define dma_unmap_sg           platform_dma_unmap_sg
+#define dma_sync_single_for_cpu        platform_dma_sync_single_for_cpu
+#define dma_sync_sg_for_cpu    platform_dma_sync_sg_for_cpu
+#define dma_sync_single_for_device platform_dma_sync_single_for_device
+#define dma_sync_sg_for_device platform_dma_sync_sg_for_device
+#define dma_mapping_error      platform_dma_mapping_error
+
+#define dma_map_page(dev, pg, off, size, dir)                          \
+       dma_map_single(dev, page_address(pg) + (off), (size), (dir))
+#define dma_unmap_page(dev, dma_addr, size, dir)                       \
+       dma_unmap_single(dev, dma_addr, size, dir)
+
+/*
+ * Rest of this file is part of the "Advanced DMA API".  Use at your own risk.
+ * See Documentation/DMA-API.txt for details.
+ */
+
+#define dma_sync_single_range_for_cpu(dev, dma_handle, offset, size, dir)      
\
+       dma_sync_single_for_cpu(dev, dma_handle, size, dir)
+#define dma_sync_single_range_for_device(dev, dma_handle, offset, size, dir)   
\
+       dma_sync_single_for_device(dev, dma_handle, size, dir)
+
+#define dma_supported          platform_dma_supported
+
+static inline int
+dma_set_mask (struct device *dev, u64 mask)
+{
+       if (!dev->dma_mask || !dma_supported(dev, mask))
+               return -EIO;
+       *dev->dma_mask = mask;
+       return 0;
+}
+
+static inline int
+dma_get_cache_alignment (void)
+{
+       extern int ia64_max_cacheline_size;
+       return ia64_max_cacheline_size;
+}
+
+static inline void
+dma_cache_sync (void *vaddr, size_t size, enum dma_data_direction dir)
+{
+       /*
+        * IA-64 is cache-coherent, so this is mostly a no-op.  However, we do 
need to
+        * ensure that dma_cache_sync() enforces order, hence the mb().
+        */
+       mb();
+}
+
+#define dma_is_consistent(dma_handle)  (1)     /* all we do is coherent 
memory... */
+
+#endif /* _ASM_IA64_DMA_MAPPING_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/dma.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/dma.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,23 @@
+#ifndef _ASM_IA64_DMA_H
+#define _ASM_IA64_DMA_H
+
+/*
+ * Copyright (C) 1998-2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <asm/io.h>            /* need byte IO */
+
+extern unsigned long MAX_DMA_ADDRESS;
+
+#ifdef CONFIG_PCI
+  extern int isa_dma_bridge_buggy;
+#else
+# define isa_dma_bridge_buggy  (0)
+#endif
+
+#define free_dma(x)
+
+#endif /* _ASM_IA64_DMA_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/errno.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/errno.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,1 @@
+#include <asm-generic/errno.h>
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/fpu.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/fpu.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,66 @@
+#ifndef _ASM_IA64_FPU_H
+#define _ASM_IA64_FPU_H
+
+/*
+ * Copyright (C) 1998, 1999, 2002, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm/types.h>
+
+/* floating point status register: */
+#define FPSR_TRAP_VD   (1 << 0)        /* invalid op trap disabled */
+#define FPSR_TRAP_DD   (1 << 1)        /* denormal trap disabled */
+#define FPSR_TRAP_ZD   (1 << 2)        /* zero-divide trap disabled */
+#define FPSR_TRAP_OD   (1 << 3)        /* overflow trap disabled */
+#define FPSR_TRAP_UD   (1 << 4)        /* underflow trap disabled */
+#define FPSR_TRAP_ID   (1 << 5)        /* inexact trap disabled */
+#define FPSR_S0(x)     ((x) <<  6)
+#define FPSR_S1(x)     ((x) << 19)
+#define FPSR_S2(x)     (__IA64_UL(x) << 32)
+#define FPSR_S3(x)     (__IA64_UL(x) << 45)
+
+/* floating-point status field controls: */
+#define FPSF_FTZ       (1 << 0)                /* flush-to-zero */
+#define FPSF_WRE       (1 << 1)                /* widest-range exponent */
+#define FPSF_PC(x)     (((x) & 0x3) << 2)      /* precision control */
+#define FPSF_RC(x)     (((x) & 0x3) << 4)      /* rounding control */
+#define FPSF_TD                (1 << 6)                /* trap disabled */
+
+/* floating-point status field flags: */
+#define FPSF_V         (1 <<  7)               /* invalid operation flag */
+#define FPSF_D         (1 <<  8)               /* denormal/unnormal operand 
flag */
+#define FPSF_Z         (1 <<  9)               /* zero divide (IEEE) flag */
+#define FPSF_O         (1 << 10)               /* overflow (IEEE) flag */
+#define FPSF_U         (1 << 11)               /* underflow (IEEE) flag */
+#define FPSF_I         (1 << 12)               /* inexact (IEEE) flag) */
+
+/* floating-point rounding control: */
+#define FPRC_NEAREST   0x0
+#define FPRC_NEGINF    0x1
+#define FPRC_POSINF    0x2
+#define FPRC_TRUNC     0x3
+
+#define FPSF_DEFAULT   (FPSF_PC (0x3) | FPSF_RC (FPRC_NEAREST))
+
+/* This default value is the same as HP-UX uses.  Don't change it
+   without a very good reason.  */
+#define FPSR_DEFAULT   (FPSR_TRAP_VD | FPSR_TRAP_DD | FPSR_TRAP_ZD     \
+                        | FPSR_TRAP_OD | FPSR_TRAP_UD | FPSR_TRAP_ID   \
+                        | FPSR_S0 (FPSF_DEFAULT)                       \
+                        | FPSR_S1 (FPSF_DEFAULT | FPSF_TD | FPSF_WRE)  \
+                        | FPSR_S2 (FPSF_DEFAULT | FPSF_TD)             \
+                        | FPSR_S3 (FPSF_DEFAULT | FPSF_TD))
+
+# ifndef __ASSEMBLY__
+
+struct ia64_fpreg {
+       union {
+               unsigned long bits[2];
+               long double __dummy;    /* force 16-byte alignment */
+       } u;
+};
+
+# endif /* __ASSEMBLY__ */
+
+#endif /* _ASM_IA64_FPU_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/hardirq.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/hardirq.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,38 @@
+#ifndef _ASM_IA64_HARDIRQ_H
+#define _ASM_IA64_HARDIRQ_H
+
+/*
+ * Modified 1998-2002, 2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <linux/threads.h>
+#include <linux/irq.h>
+
+#include <asm/processor.h>
+
+/*
+ * No irq_cpustat_t for IA-64.  The data is held in the per-CPU data structure.
+ */
+
+#define __ARCH_IRQ_STAT        1
+
+#define local_softirq_pending()                
(local_cpu_data->softirq_pending)
+
+#define HARDIRQ_BITS   14
+
+/*
+ * The hardirq mask has to be large enough to have space for potentially all 
IRQ sources
+ * in the system nesting on a single CPU:
+ */
+#if (1 << HARDIRQ_BITS) < NR_IRQS
+# error HARDIRQ_BITS is too low!
+#endif
+
+extern void __iomem *ipi_base_addr;
+
+void ack_bad_irq(unsigned int irq);
+
+#endif /* _ASM_IA64_HARDIRQ_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/hdreg.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/hdreg.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,14 @@
+/*
+ *  linux/include/asm-ia64/hdreg.h
+ *
+ *  Copyright (C) 1994-1996  Linus Torvalds & authors
+ */
+
+#warning this file is obsolete, please do not use it
+
+#ifndef __ASM_IA64_HDREG_H
+#define __ASM_IA64_HDREG_H
+
+typedef unsigned short ide_ioreg_t;
+
+#endif /* __ASM_IA64_HDREG_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/hw_irq.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/hw_irq.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,144 @@
+#ifndef _ASM_IA64_HW_IRQ_H
+#define _ASM_IA64_HW_IRQ_H
+
+/*
+ * Copyright (C) 2001-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/interrupt.h>
+#include <linux/sched.h>
+#include <linux/types.h>
+#include <linux/profile.h>
+
+#include <asm/machvec.h>
+#include <asm/ptrace.h>
+#include <asm/smp.h>
+
+typedef u8 ia64_vector;
+
+/*
+ * 0 special
+ *
+ * 1,3-14 are reserved from firmware
+ *
+ * 16-255 (vectored external interrupts) are available
+ *
+ * 15 spurious interrupt (see IVR)
+ *
+ * 16 lowest priority, 255 highest priority
+ *
+ * 15 classes of 16 interrupts each.
+ */
+#define IA64_MIN_VECTORED_IRQ           16
+#define IA64_MAX_VECTORED_IRQ          255
+#define IA64_NUM_VECTORS               256
+
+#define AUTO_ASSIGN                    -1
+
+#define IA64_SPURIOUS_INT_VECTOR       0x0f
+
+/*
+ * Vectors 0x10-0x1f are used for low priority interrupts, e.g. CMCI.
+ */
+#define IA64_CPEP_VECTOR               0x1c    /* corrected platform error 
polling vector */
+#define IA64_CMCP_VECTOR               0x1d    /* corrected machine-check 
polling vector */
+#define IA64_CPE_VECTOR                        0x1e    /* corrected platform 
error interrupt vector */
+#define IA64_CMC_VECTOR                        0x1f    /* corrected 
machine-check interrupt vector */
+/*
+ * Vectors 0x20-0x2f are reserved for legacy ISA IRQs.
+ */
+#define IA64_FIRST_DEVICE_VECTOR       0x30
+#define IA64_LAST_DEVICE_VECTOR                0xe7
+#define IA64_NUM_DEVICE_VECTORS                (IA64_LAST_DEVICE_VECTOR - 
IA64_FIRST_DEVICE_VECTOR + 1)
+
+#define IA64_MCA_RENDEZ_VECTOR         0xe8    /* MCA rendez interrupt */
+#define IA64_PERFMON_VECTOR            0xee    /* performanc monitor interrupt 
vector */
+#define IA64_TIMER_VECTOR              0xef    /* use highest-prio group 15 
interrupt for timer */
+#define        IA64_MCA_WAKEUP_VECTOR          0xf0    /* MCA wakeup (must be 
>MCA_RENDEZ_VECTOR) */
+#define IA64_IPI_RESCHEDULE            0xfd    /* SMP reschedule */
+#define IA64_IPI_VECTOR                        0xfe    /* inter-processor 
interrupt vector */
+
+/* Used for encoding redirected irqs */
+
+#define IA64_IRQ_REDIRECTED            (1 << 31)
+
+/* IA64 inter-cpu interrupt related definitions */
+
+#define IA64_IPI_DEFAULT_BASE_ADDR     0xfee00000
+
+/* Delivery modes for inter-cpu interrupts */
+enum {
+        IA64_IPI_DM_INT =       0x0,    /* pend an external interrupt */
+        IA64_IPI_DM_PMI =       0x2,    /* pend a PMI */
+        IA64_IPI_DM_NMI =       0x4,    /* pend an NMI (vector 2) */
+        IA64_IPI_DM_INIT =      0x5,    /* pend an INIT interrupt */
+        IA64_IPI_DM_EXTINT =    0x7,    /* pend an 8259-compatible interrupt. 
*/
+};
+
+extern __u8 isa_irq_to_vector_map[16];
+#define isa_irq_to_vector(x)   isa_irq_to_vector_map[(x)]
+
+extern struct hw_interrupt_type irq_type_ia64_lsapic;  /* CPU-internal 
interrupt controller */
+
+extern int assign_irq_vector (int irq);        /* allocate a free vector */
+extern void free_irq_vector (int vector);
+extern void ia64_send_ipi (int cpu, int vector, int delivery_mode, int 
redirect);
+extern void register_percpu_irq (ia64_vector vec, struct irqaction *action);
+
+static inline void
+hw_resend_irq (struct hw_interrupt_type *h, unsigned int vector)
+{
+       platform_send_ipi(smp_processor_id(), vector, IA64_IPI_DM_INT, 0);
+}
+
+/*
+ * Default implementations for the irq-descriptor API:
+ */
+
+extern irq_desc_t irq_desc[NR_IRQS];
+
+#ifndef CONFIG_IA64_GENERIC
+static inline unsigned int
+__ia64_local_vector_to_irq (ia64_vector vec)
+{
+       return (unsigned int) vec;
+}
+#endif
+
+/*
+ * Next follows the irq descriptor interface.  On IA-64, each CPU supports 256 
interrupt
+ * vectors.  On smaller systems, there is a one-to-one correspondence between 
interrupt
+ * vectors and the Linux irq numbers.  However, larger systems may have 
multiple interrupt
+ * domains meaning that the translation from vector number to irq number 
depends on the
+ * interrupt domain that a CPU belongs to.  This API abstracts such 
platform-dependent
+ * differences and provides a uniform means to translate between vector and 
irq numbers
+ * and to obtain the irq descriptor for a given irq number.
+ */
+
+/* Return a pointer to the irq descriptor for IRQ.  */
+static inline irq_desc_t *
+irq_descp (int irq)
+{
+       return irq_desc + irq;
+}
+
+/* Extract the IA-64 vector that corresponds to IRQ.  */
+static inline ia64_vector
+irq_to_vector (int irq)
+{
+       return (ia64_vector) irq;
+}
+
+/*
+ * Convert the local IA-64 vector to the corresponding irq number.  This 
translation is
+ * done in the context of the interrupt domain that the currently executing 
CPU belongs
+ * to.
+ */
+static inline unsigned int
+local_vector_to_irq (ia64_vector vec)
+{
+       return platform_local_vector_to_irq(vec);
+}
+
+#endif /* _ASM_IA64_HW_IRQ_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/intrinsics.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/intrinsics.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,181 @@
+#ifndef _ASM_IA64_INTRINSICS_H
+#define _ASM_IA64_INTRINSICS_H
+
+/*
+ * Compiler-dependent intrinsics.
+ *
+ * Copyright (C) 2002-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#ifndef __ASSEMBLY__
+#include <linux/config.h>
+
+/* include compiler specific intrinsics */
+#include <asm/ia64regs.h>
+#ifdef __INTEL_COMPILER
+# include <asm/intel_intrin.h>
+#else
+# include <asm/gcc_intrin.h>
+#endif
+
+/*
+ * Force an unresolved reference if someone tries to use
+ * ia64_fetch_and_add() with a bad value.
+ */
+extern unsigned long __bad_size_for_ia64_fetch_and_add (void);
+extern unsigned long __bad_increment_for_ia64_fetch_and_add (void);
+
+#define IA64_FETCHADD(tmp,v,n,sz,sem)                                          
\
+({                                                                             
\
+       switch (sz) {                                                           
\
+             case 4:                                                           
\
+               tmp = ia64_fetchadd4_##sem((unsigned int *) v, n);              
\
+               break;                                                          
\
+                                                                               
\
+             case 8:                                                           
\
+               tmp = ia64_fetchadd8_##sem((unsigned long *) v, n);             
\
+               break;                                                          
\
+                                                                               
\
+             default:                                                          
\
+               __bad_size_for_ia64_fetch_and_add();                            
\
+       }                                                                       
\
+})
+
+#define ia64_fetchadd(i,v,sem)                                                 
        \
+({                                                                             
        \
+       __u64 _tmp;                                                             
        \
+       volatile __typeof__(*(v)) *_v = (v);                                    
        \
+       /* Can't use a switch () here: gcc isn't always smart enough for 
that... */     \
+       if ((i) == -16)                                                         
        \
+               IA64_FETCHADD(_tmp, _v, -16, sizeof(*(v)), sem);                
        \
+       else if ((i) == -8)                                                     
        \
+               IA64_FETCHADD(_tmp, _v, -8, sizeof(*(v)), sem);                 
        \
+       else if ((i) == -4)                                                     
        \
+               IA64_FETCHADD(_tmp, _v, -4, sizeof(*(v)), sem);                 
        \
+       else if ((i) == -1)                                                     
        \
+               IA64_FETCHADD(_tmp, _v, -1, sizeof(*(v)), sem);                 
        \
+       else if ((i) == 1)                                                      
        \
+               IA64_FETCHADD(_tmp, _v, 1, sizeof(*(v)), sem);                  
        \
+       else if ((i) == 4)                                                      
        \
+               IA64_FETCHADD(_tmp, _v, 4, sizeof(*(v)), sem);                  
        \
+       else if ((i) == 8)                                                      
        \
+               IA64_FETCHADD(_tmp, _v, 8, sizeof(*(v)), sem);                  
        \
+       else if ((i) == 16)                                                     
        \
+               IA64_FETCHADD(_tmp, _v, 16, sizeof(*(v)), sem);                 
        \
+       else                                                                    
        \
+               _tmp = __bad_increment_for_ia64_fetch_and_add();                
        \
+       (__typeof__(*(v))) (_tmp);      /* return old value */                  
        \
+})
+
+#define ia64_fetch_and_add(i,v)        (ia64_fetchadd(i, v, rel) + (i)) /* 
return new value */
+
+/*
+ * This function doesn't exist, so you'll get a linker error if
+ * something tries to do an invalid xchg().
+ */
+extern void ia64_xchg_called_with_bad_pointer (void);
+
+#define __xchg(x,ptr,size)                                             \
+({                                                                     \
+       unsigned long __xchg_result;                                    \
+                                                                       \
+       switch (size) {                                                 \
+             case 1:                                                   \
+               __xchg_result = ia64_xchg1((__u8 *)ptr, x);             \
+               break;                                                  \
+                                                                       \
+             case 2:                                                   \
+               __xchg_result = ia64_xchg2((__u16 *)ptr, x);            \
+               break;                                                  \
+                                                                       \
+             case 4:                                                   \
+               __xchg_result = ia64_xchg4((__u32 *)ptr, x);            \
+               break;                                                  \
+                                                                       \
+             case 8:                                                   \
+               __xchg_result = ia64_xchg8((__u64 *)ptr, x);            \
+               break;                                                  \
+             default:                                                  \
+               ia64_xchg_called_with_bad_pointer();                    \
+       }                                                               \
+       __xchg_result;                                                  \
+})
+
+#define xchg(ptr,x)                                                         \
+  ((__typeof__(*(ptr))) __xchg ((unsigned long) (x), (ptr), sizeof(*(ptr))))
+
+/*
+ * Atomic compare and exchange.  Compare OLD with MEM, if identical,
+ * store NEW in MEM.  Return the initial value in MEM.  Success is
+ * indicated by comparing RETURN with OLD.
+ */
+
+#define __HAVE_ARCH_CMPXCHG 1
+
+/*
+ * This function doesn't exist, so you'll get a linker error
+ * if something tries to do an invalid cmpxchg().
+ */
+extern long ia64_cmpxchg_called_with_bad_pointer (void);
+
+#define ia64_cmpxchg(sem,ptr,old,new,size)                                     
        \
+({                                                                             
        \
+       __u64 _o_, _r_;                                                         
        \
+                                                                               
        \
+       switch (size) {                                                         
        \
+             case 1: _o_ = (__u8 ) (long) (old); break;                        
        \
+             case 2: _o_ = (__u16) (long) (old); break;                        
        \
+             case 4: _o_ = (__u32) (long) (old); break;                        
        \
+             case 8: _o_ = (__u64) (long) (old); break;                        
        \
+             default: break;                                                   
        \
+       }                                                                       
        \
+       switch (size) {                                                         
        \
+             case 1:                                                           
        \
+               _r_ = ia64_cmpxchg1_##sem((__u8 *) ptr, new, _o_);              
        \
+               break;                                                          
        \
+                                                                               
        \
+             case 2:                                                           
        \
+              _r_ = ia64_cmpxchg2_##sem((__u16 *) ptr, new, _o_);              
        \
+               break;                                                          
        \
+                                                                               
        \
+             case 4:                                                           
        \
+               _r_ = ia64_cmpxchg4_##sem((__u32 *) ptr, new, _o_);             
        \
+               break;                                                          
        \
+                                                                               
        \
+             case 8:                                                           
        \
+               _r_ = ia64_cmpxchg8_##sem((__u64 *) ptr, new, _o_);             
        \
+               break;                                                          
        \
+                                                                               
        \
+             default:                                                          
        \
+               _r_ = ia64_cmpxchg_called_with_bad_pointer();                   
        \
+               break;                                                          
        \
+       }                                                                       
        \
+       (__typeof__(old)) _r_;                                                  
        \
+})
+
+#define cmpxchg_acq(ptr,o,n)   ia64_cmpxchg(acq, (ptr), (o), (n), 
sizeof(*(ptr)))
+#define cmpxchg_rel(ptr,o,n)   ia64_cmpxchg(rel, (ptr), (o), (n), 
sizeof(*(ptr)))
+
+/* for compatibility with other platforms: */
+#define cmpxchg(ptr,o,n)       cmpxchg_acq(ptr,o,n)
+
+#ifdef CONFIG_IA64_DEBUG_CMPXCHG
+# define CMPXCHG_BUGCHECK_DECL int _cmpxchg_bugcheck_count = 128;
+# define CMPXCHG_BUGCHECK(v)                                                   
\
+  do {                                                                         
\
+       if (_cmpxchg_bugcheck_count-- <= 0) {                                   
\
+               void *ip;                                                       
\
+               extern int printk(const char *fmt, ...);                        
\
+               ip = (void *) ia64_getreg(_IA64_REG_IP);                        
\
+               printk("CMPXCHG_BUGCHECK: stuck at %p on word %p\n", ip, (v));  
\
+               break;                                                          
\
+       }                                                                       
\
+  } while (0)
+#else /* !CONFIG_IA64_DEBUG_CMPXCHG */
+# define CMPXCHG_BUGCHECK_DECL
+# define CMPXCHG_BUGCHECK(v)
+#endif /* !CONFIG_IA64_DEBUG_CMPXCHG */
+
+#endif
+#endif /* _ASM_IA64_INTRINSICS_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/ioctl.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/ioctl.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,77 @@
+#ifndef _ASM_IA64_IOCTL_H
+#define _ASM_IA64_IOCTL_H
+
+/*
+ * Based on <asm-i386/ioctl.h>.
+ *
+ * Modified 1998, 1999
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+/* ioctl command encoding: 32 bits total, command in lower 16 bits,
+ * size of the parameter structure in the lower 14 bits of the
+ * upper 16 bits.
+ * Encoding the size of the parameter structure in the ioctl request
+ * is useful for catching programs compiled with old versions
+ * and to avoid overwriting user space outside the user buffer area.
+ * The highest 2 bits are reserved for indicating the ``access mode''.
+ * NOTE: This limits the max parameter size to 16kB -1 !
+ */
+
+/*
+ * The following is for compatibility across the various Linux
+ * platforms.  The ia64 ioctl numbering scheme doesn't really enforce
+ * a type field.  De facto, however, the top 8 bits of the lower 16
+ * bits are indeed used as a type field, so we might just as well make
+ * this explicit here.  Please be sure to use the decoding macros
+ * below from now on.
+ */
+#define _IOC_NRBITS    8
+#define _IOC_TYPEBITS  8
+#define _IOC_SIZEBITS  14
+#define _IOC_DIRBITS   2
+
+#define _IOC_NRMASK    ((1 << _IOC_NRBITS)-1)
+#define _IOC_TYPEMASK  ((1 << _IOC_TYPEBITS)-1)
+#define _IOC_SIZEMASK  ((1 << _IOC_SIZEBITS)-1)
+#define _IOC_DIRMASK   ((1 << _IOC_DIRBITS)-1)
+
+#define _IOC_NRSHIFT   0
+#define _IOC_TYPESHIFT (_IOC_NRSHIFT+_IOC_NRBITS)
+#define _IOC_SIZESHIFT (_IOC_TYPESHIFT+_IOC_TYPEBITS)
+#define _IOC_DIRSHIFT  (_IOC_SIZESHIFT+_IOC_SIZEBITS)
+
+/*
+ * Direction bits.
+ */
+#define _IOC_NONE      0U
+#define _IOC_WRITE     1U
+#define _IOC_READ      2U
+
+#define _IOC(dir,type,nr,size) \
+       (((dir)  << _IOC_DIRSHIFT) | \
+        ((type) << _IOC_TYPESHIFT) | \
+        ((nr)   << _IOC_NRSHIFT) | \
+        ((size) << _IOC_SIZESHIFT))
+
+/* used to create numbers */
+#define _IO(type,nr)           _IOC(_IOC_NONE,(type),(nr),0)
+#define _IOR(type,nr,size)     _IOC(_IOC_READ,(type),(nr),sizeof(size))
+#define _IOW(type,nr,size)     _IOC(_IOC_WRITE,(type),(nr),sizeof(size))
+#define _IOWR(type,nr,size)    
_IOC(_IOC_READ|_IOC_WRITE,(type),(nr),sizeof(size))
+
+/* used to decode ioctl numbers.. */
+#define _IOC_DIR(nr)           (((nr) >> _IOC_DIRSHIFT) & _IOC_DIRMASK)
+#define _IOC_TYPE(nr)          (((nr) >> _IOC_TYPESHIFT) & _IOC_TYPEMASK)
+#define _IOC_NR(nr)            (((nr) >> _IOC_NRSHIFT) & _IOC_NRMASK)
+#define _IOC_SIZE(nr)          (((nr) >> _IOC_SIZESHIFT) & _IOC_SIZEMASK)
+
+/* ...and for the drivers/sound files... */
+
+#define IOC_IN         (_IOC_WRITE << _IOC_DIRSHIFT)
+#define IOC_OUT                (_IOC_READ << _IOC_DIRSHIFT)
+#define IOC_INOUT      ((_IOC_WRITE|_IOC_READ) << _IOC_DIRSHIFT)
+#define IOCSIZE_MASK   (_IOC_SIZEMASK << _IOC_SIZESHIFT)
+#define IOCSIZE_SHIFT  (_IOC_SIZESHIFT)
+
+#endif /* _ASM_IA64_IOCTL_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/irq.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/irq.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,43 @@
+#ifndef _ASM_IA64_IRQ_H
+#define _ASM_IA64_IRQ_H
+
+/*
+ * Copyright (C) 1999-2000, 2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ *
+ * 11/24/98    S.Eranian       updated TIMER_IRQ and irq_canonicalize
+ * 01/20/99    S.Eranian       added keyboard interrupt
+ * 02/29/00     D.Mosberger    moved most things into hw_irq.h
+ */
+
+#define NR_IRQS                256
+#define NR_IRQ_VECTORS NR_IRQS
+
+static __inline__ int
+irq_canonicalize (int irq)
+{
+       /*
+        * We do the legacy thing here of pretending that irqs < 16
+        * are 8259 irqs.  This really shouldn't be necessary at all,
+        * but we keep it here as serial.c still uses it...
+        */
+       return ((irq == 2) ? 9 : irq);
+}
+
+extern void disable_irq (unsigned int);
+extern void disable_irq_nosync (unsigned int);
+extern void enable_irq (unsigned int);
+extern void set_irq_affinity_info (unsigned int irq, int dest, int redir);
+
+#ifdef CONFIG_SMP
+extern void move_irq(int irq);
+#else
+#define move_irq(irq)
+#endif
+
+struct irqaction;
+struct pt_regs;
+int handle_IRQ_event(unsigned int, struct pt_regs *, struct irqaction *);
+
+#endif /* _ASM_IA64_IRQ_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/linkage.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/linkage.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,6 @@
+#ifndef __ASM_LINKAGE_H
+#define __ASM_LINKAGE_H
+
+#define asmlinkage CPP_ASMLINKAGE __attribute__((syscall_linkage))
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/machvec.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/machvec.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,390 @@
+/*
+ * Machine vector for IA-64.
+ *
+ * Copyright (C) 1999 Silicon Graphics, Inc.
+ * Copyright (C) Srinivasa Thirumalachar <sprasad@xxxxxxxxxxxx>
+ * Copyright (C) Vijay Chander <vijay@xxxxxxxxxxxx>
+ * Copyright (C) 1999-2001, 2003-2004 Hewlett-Packard Co.
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#ifndef _ASM_IA64_MACHVEC_H
+#define _ASM_IA64_MACHVEC_H
+
+#include <linux/config.h>
+#include <linux/types.h>
+
+/* forward declarations: */
+struct device;
+struct pt_regs;
+struct scatterlist;
+struct page;
+struct mm_struct;
+struct pci_bus;
+
+typedef void ia64_mv_setup_t (char **);
+typedef void ia64_mv_cpu_init_t (void);
+typedef void ia64_mv_irq_init_t (void);
+typedef void ia64_mv_send_ipi_t (int, int, int, int);
+typedef void ia64_mv_timer_interrupt_t (int, void *, struct pt_regs *);
+typedef void ia64_mv_global_tlb_purge_t (unsigned long, unsigned long, 
unsigned long);
+typedef void ia64_mv_tlb_migrate_finish_t (struct mm_struct *);
+typedef unsigned int ia64_mv_local_vector_to_irq (u8);
+typedef char *ia64_mv_pci_get_legacy_mem_t (struct pci_bus *);
+typedef int ia64_mv_pci_legacy_read_t (struct pci_bus *, u16 port, u32 *val,
+                                      u8 size);
+typedef int ia64_mv_pci_legacy_write_t (struct pci_bus *, u16 port, u32 val,
+                                       u8 size);
+
+/* DMA-mapping interface: */
+typedef void ia64_mv_dma_init (void);
+typedef void *ia64_mv_dma_alloc_coherent (struct device *, size_t, dma_addr_t 
*, int);
+typedef void ia64_mv_dma_free_coherent (struct device *, size_t, void *, 
dma_addr_t);
+typedef dma_addr_t ia64_mv_dma_map_single (struct device *, void *, size_t, 
int);
+typedef void ia64_mv_dma_unmap_single (struct device *, dma_addr_t, size_t, 
int);
+typedef int ia64_mv_dma_map_sg (struct device *, struct scatterlist *, int, 
int);
+typedef void ia64_mv_dma_unmap_sg (struct device *, struct scatterlist *, int, 
int);
+typedef void ia64_mv_dma_sync_single_for_cpu (struct device *, dma_addr_t, 
size_t, int);
+typedef void ia64_mv_dma_sync_sg_for_cpu (struct device *, struct scatterlist 
*, int, int);
+typedef void ia64_mv_dma_sync_single_for_device (struct device *, dma_addr_t, 
size_t, int);
+typedef void ia64_mv_dma_sync_sg_for_device (struct device *, struct 
scatterlist *, int, int);
+typedef int ia64_mv_dma_mapping_error (dma_addr_t dma_addr);
+typedef int ia64_mv_dma_supported (struct device *, u64);
+
+/*
+ * WARNING: The legacy I/O space is _architected_.  Platforms are
+ * expected to follow this architected model (see Section 10.7 in the
+ * IA-64 Architecture Software Developer's Manual).  Unfortunately,
+ * some broken machines do not follow that model, which is why we have
+ * to make the inX/outX operations part of the machine vector.
+ * Platform designers should follow the architected model whenever
+ * possible.
+ */
+typedef unsigned int ia64_mv_inb_t (unsigned long);
+typedef unsigned int ia64_mv_inw_t (unsigned long);
+typedef unsigned int ia64_mv_inl_t (unsigned long);
+typedef void ia64_mv_outb_t (unsigned char, unsigned long);
+typedef void ia64_mv_outw_t (unsigned short, unsigned long);
+typedef void ia64_mv_outl_t (unsigned int, unsigned long);
+typedef void ia64_mv_mmiowb_t (void);
+typedef unsigned char ia64_mv_readb_t (const volatile void __iomem *);
+typedef unsigned short ia64_mv_readw_t (const volatile void __iomem *);
+typedef unsigned int ia64_mv_readl_t (const volatile void __iomem *);
+typedef unsigned long ia64_mv_readq_t (const volatile void __iomem *);
+typedef unsigned char ia64_mv_readb_relaxed_t (const volatile void __iomem *);
+typedef unsigned short ia64_mv_readw_relaxed_t (const volatile void __iomem *);
+typedef unsigned int ia64_mv_readl_relaxed_t (const volatile void __iomem *);
+typedef unsigned long ia64_mv_readq_relaxed_t (const volatile void __iomem *);
+
+static inline void
+machvec_noop (void)
+{
+}
+
+static inline void
+machvec_noop_mm (struct mm_struct *mm)
+{
+}
+
+extern void machvec_setup (char **);
+extern void machvec_timer_interrupt (int, void *, struct pt_regs *);
+extern void machvec_dma_sync_single (struct device *, dma_addr_t, size_t, int);
+extern void machvec_dma_sync_sg (struct device *, struct scatterlist *, int, 
int);
+extern void machvec_tlb_migrate_finish (struct mm_struct *);
+
+# if defined (CONFIG_IA64_HP_SIM)
+#  include <asm/machvec_hpsim.h>
+# elif defined (CONFIG_IA64_DIG)
+#  include <asm/machvec_dig.h>
+# elif defined (CONFIG_IA64_HP_ZX1)
+#  include <asm/machvec_hpzx1.h>
+# elif defined (CONFIG_IA64_HP_ZX1_SWIOTLB)
+#  include <asm/machvec_hpzx1_swiotlb.h>
+# elif defined (CONFIG_IA64_SGI_SN2)
+#  include <asm/machvec_sn2.h>
+# elif defined (CONFIG_IA64_GENERIC)
+
+# ifdef MACHVEC_PLATFORM_HEADER
+#  include MACHVEC_PLATFORM_HEADER
+# else
+#  define platform_name                ia64_mv.name
+#  define platform_setup       ia64_mv.setup
+#  define platform_cpu_init    ia64_mv.cpu_init
+#  define platform_irq_init    ia64_mv.irq_init
+#  define platform_send_ipi    ia64_mv.send_ipi
+#  define platform_timer_interrupt     ia64_mv.timer_interrupt
+#  define platform_global_tlb_purge    ia64_mv.global_tlb_purge
+#  define platform_tlb_migrate_finish  ia64_mv.tlb_migrate_finish
+#  define platform_dma_init            ia64_mv.dma_init
+#  define platform_dma_alloc_coherent  ia64_mv.dma_alloc_coherent
+#  define platform_dma_free_coherent   ia64_mv.dma_free_coherent
+#  define platform_dma_map_single      ia64_mv.dma_map_single
+#  define platform_dma_unmap_single    ia64_mv.dma_unmap_single
+#  define platform_dma_map_sg          ia64_mv.dma_map_sg
+#  define platform_dma_unmap_sg                ia64_mv.dma_unmap_sg
+#  define platform_dma_sync_single_for_cpu ia64_mv.dma_sync_single_for_cpu
+#  define platform_dma_sync_sg_for_cpu ia64_mv.dma_sync_sg_for_cpu
+#  define platform_dma_sync_single_for_device 
ia64_mv.dma_sync_single_for_device
+#  define platform_dma_sync_sg_for_device ia64_mv.dma_sync_sg_for_device
+#  define platform_dma_mapping_error           ia64_mv.dma_mapping_error
+#  define platform_dma_supported       ia64_mv.dma_supported
+#  define platform_local_vector_to_irq ia64_mv.local_vector_to_irq
+#  define platform_pci_get_legacy_mem  ia64_mv.pci_get_legacy_mem
+#  define platform_pci_legacy_read     ia64_mv.pci_legacy_read
+#  define platform_pci_legacy_write    ia64_mv.pci_legacy_write
+#  define platform_inb         ia64_mv.inb
+#  define platform_inw         ia64_mv.inw
+#  define platform_inl         ia64_mv.inl
+#  define platform_outb                ia64_mv.outb
+#  define platform_outw                ia64_mv.outw
+#  define platform_outl                ia64_mv.outl
+#  define platform_mmiowb      ia64_mv.mmiowb
+#  define platform_readb        ia64_mv.readb
+#  define platform_readw        ia64_mv.readw
+#  define platform_readl        ia64_mv.readl
+#  define platform_readq        ia64_mv.readq
+#  define platform_readb_relaxed        ia64_mv.readb_relaxed
+#  define platform_readw_relaxed        ia64_mv.readw_relaxed
+#  define platform_readl_relaxed        ia64_mv.readl_relaxed
+#  define platform_readq_relaxed        ia64_mv.readq_relaxed
+# endif
+
+/* __attribute__((__aligned__(16))) is required to make size of the
+ * structure multiple of 16 bytes.
+ * This will fillup the holes created because of section 3.3.1 in
+ * Software Conventions guide.
+ */
+struct ia64_machine_vector {
+       const char *name;
+       ia64_mv_setup_t *setup;
+       ia64_mv_cpu_init_t *cpu_init;
+       ia64_mv_irq_init_t *irq_init;
+       ia64_mv_send_ipi_t *send_ipi;
+       ia64_mv_timer_interrupt_t *timer_interrupt;
+       ia64_mv_global_tlb_purge_t *global_tlb_purge;
+       ia64_mv_tlb_migrate_finish_t *tlb_migrate_finish;
+       ia64_mv_dma_init *dma_init;
+       ia64_mv_dma_alloc_coherent *dma_alloc_coherent;
+       ia64_mv_dma_free_coherent *dma_free_coherent;
+       ia64_mv_dma_map_single *dma_map_single;
+       ia64_mv_dma_unmap_single *dma_unmap_single;
+       ia64_mv_dma_map_sg *dma_map_sg;
+       ia64_mv_dma_unmap_sg *dma_unmap_sg;
+       ia64_mv_dma_sync_single_for_cpu *dma_sync_single_for_cpu;
+       ia64_mv_dma_sync_sg_for_cpu *dma_sync_sg_for_cpu;
+       ia64_mv_dma_sync_single_for_device *dma_sync_single_for_device;
+       ia64_mv_dma_sync_sg_for_device *dma_sync_sg_for_device;
+       ia64_mv_dma_mapping_error *dma_mapping_error;
+       ia64_mv_dma_supported *dma_supported;
+       ia64_mv_local_vector_to_irq *local_vector_to_irq;
+       ia64_mv_pci_get_legacy_mem_t *pci_get_legacy_mem;
+       ia64_mv_pci_legacy_read_t *pci_legacy_read;
+       ia64_mv_pci_legacy_write_t *pci_legacy_write;
+       ia64_mv_inb_t *inb;
+       ia64_mv_inw_t *inw;
+       ia64_mv_inl_t *inl;
+       ia64_mv_outb_t *outb;
+       ia64_mv_outw_t *outw;
+       ia64_mv_outl_t *outl;
+       ia64_mv_mmiowb_t *mmiowb;
+       ia64_mv_readb_t *readb;
+       ia64_mv_readw_t *readw;
+       ia64_mv_readl_t *readl;
+       ia64_mv_readq_t *readq;
+       ia64_mv_readb_relaxed_t *readb_relaxed;
+       ia64_mv_readw_relaxed_t *readw_relaxed;
+       ia64_mv_readl_relaxed_t *readl_relaxed;
+       ia64_mv_readq_relaxed_t *readq_relaxed;
+} __attribute__((__aligned__(16))); /* align attrib? see above comment */
+
+#define MACHVEC_INIT(name)                     \
+{                                              \
+       #name,                                  \
+       platform_setup,                         \
+       platform_cpu_init,                      \
+       platform_irq_init,                      \
+       platform_send_ipi,                      \
+       platform_timer_interrupt,               \
+       platform_global_tlb_purge,              \
+       platform_tlb_migrate_finish,            \
+       platform_dma_init,                      \
+       platform_dma_alloc_coherent,            \
+       platform_dma_free_coherent,             \
+       platform_dma_map_single,                \
+       platform_dma_unmap_single,              \
+       platform_dma_map_sg,                    \
+       platform_dma_unmap_sg,                  \
+       platform_dma_sync_single_for_cpu,       \
+       platform_dma_sync_sg_for_cpu,           \
+       platform_dma_sync_single_for_device,    \
+       platform_dma_sync_sg_for_device,        \
+       platform_dma_mapping_error,                     \
+       platform_dma_supported,                 \
+       platform_local_vector_to_irq,           \
+       platform_pci_get_legacy_mem,            \
+       platform_pci_legacy_read,               \
+       platform_pci_legacy_write,              \
+       platform_inb,                           \
+       platform_inw,                           \
+       platform_inl,                           \
+       platform_outb,                          \
+       platform_outw,                          \
+       platform_outl,                          \
+       platform_mmiowb,                        \
+       platform_readb,                         \
+       platform_readw,                         \
+       platform_readl,                         \
+       platform_readq,                         \
+       platform_readb_relaxed,                 \
+       platform_readw_relaxed,                 \
+       platform_readl_relaxed,                 \
+       platform_readq_relaxed,                 \
+}
+
+extern struct ia64_machine_vector ia64_mv;
+extern void machvec_init (const char *name);
+
+# else
+#  error Unknown configuration.  Update asm-ia64/machvec.h.
+# endif /* CONFIG_IA64_GENERIC */
+
+/*
+ * Declare default routines which aren't declared anywhere else:
+ */
+extern ia64_mv_dma_init                        swiotlb_init;
+extern ia64_mv_dma_alloc_coherent      swiotlb_alloc_coherent;
+extern ia64_mv_dma_free_coherent       swiotlb_free_coherent;
+extern ia64_mv_dma_map_single          swiotlb_map_single;
+extern ia64_mv_dma_unmap_single                swiotlb_unmap_single;
+extern ia64_mv_dma_map_sg              swiotlb_map_sg;
+extern ia64_mv_dma_unmap_sg            swiotlb_unmap_sg;
+extern ia64_mv_dma_sync_single_for_cpu swiotlb_sync_single_for_cpu;
+extern ia64_mv_dma_sync_sg_for_cpu     swiotlb_sync_sg_for_cpu;
+extern ia64_mv_dma_sync_single_for_device swiotlb_sync_single_for_device;
+extern ia64_mv_dma_sync_sg_for_device  swiotlb_sync_sg_for_device;
+extern ia64_mv_dma_mapping_error       swiotlb_dma_mapping_error;
+extern ia64_mv_dma_supported           swiotlb_dma_supported;
+
+/*
+ * Define default versions so we can extend machvec for new platforms without 
having
+ * to update the machvec files for all existing platforms.
+ */
+#ifndef platform_setup
+# define platform_setup                        machvec_setup
+#endif
+#ifndef platform_cpu_init
+# define platform_cpu_init             machvec_noop
+#endif
+#ifndef platform_irq_init
+# define platform_irq_init             machvec_noop
+#endif
+
+#ifndef platform_send_ipi
+# define platform_send_ipi             ia64_send_ipi   /* default to 
architected version */
+#endif
+#ifndef platform_timer_interrupt
+# define platform_timer_interrupt      machvec_timer_interrupt
+#endif
+#ifndef platform_global_tlb_purge
+# define platform_global_tlb_purge     ia64_global_tlb_purge /* default to 
architected version */
+#endif
+#ifndef platform_tlb_migrate_finish
+# define platform_tlb_migrate_finish   machvec_noop_mm
+#endif
+#ifndef platform_dma_init
+# define platform_dma_init             swiotlb_init
+#endif
+#ifndef platform_dma_alloc_coherent
+# define platform_dma_alloc_coherent   swiotlb_alloc_coherent
+#endif
+#ifndef platform_dma_free_coherent
+# define platform_dma_free_coherent    swiotlb_free_coherent
+#endif
+#ifndef platform_dma_map_single
+# define platform_dma_map_single       swiotlb_map_single
+#endif
+#ifndef platform_dma_unmap_single
+# define platform_dma_unmap_single     swiotlb_unmap_single
+#endif
+#ifndef platform_dma_map_sg
+# define platform_dma_map_sg           swiotlb_map_sg
+#endif
+#ifndef platform_dma_unmap_sg
+# define platform_dma_unmap_sg         swiotlb_unmap_sg
+#endif
+#ifndef platform_dma_sync_single_for_cpu
+# define platform_dma_sync_single_for_cpu      swiotlb_sync_single_for_cpu
+#endif
+#ifndef platform_dma_sync_sg_for_cpu
+# define platform_dma_sync_sg_for_cpu          swiotlb_sync_sg_for_cpu
+#endif
+#ifndef platform_dma_sync_single_for_device
+# define platform_dma_sync_single_for_device   swiotlb_sync_single_for_device
+#endif
+#ifndef platform_dma_sync_sg_for_device
+# define platform_dma_sync_sg_for_device       swiotlb_sync_sg_for_device
+#endif
+#ifndef platform_dma_mapping_error
+# define platform_dma_mapping_error            swiotlb_dma_mapping_error
+#endif
+#ifndef platform_dma_supported
+# define  platform_dma_supported       swiotlb_dma_supported
+#endif
+#ifndef platform_local_vector_to_irq
+# define platform_local_vector_to_irq  __ia64_local_vector_to_irq
+#endif
+#ifndef platform_pci_get_legacy_mem
+# define platform_pci_get_legacy_mem   ia64_pci_get_legacy_mem
+#endif
+#ifndef platform_pci_legacy_read
+# define platform_pci_legacy_read      ia64_pci_legacy_read
+#endif
+#ifndef platform_pci_legacy_write
+# define platform_pci_legacy_write     ia64_pci_legacy_write
+#endif
+#ifndef platform_inb
+# define platform_inb          __ia64_inb
+#endif
+#ifndef platform_inw
+# define platform_inw          __ia64_inw
+#endif
+#ifndef platform_inl
+# define platform_inl          __ia64_inl
+#endif
+#ifndef platform_outb
+# define platform_outb         __ia64_outb
+#endif
+#ifndef platform_outw
+# define platform_outw         __ia64_outw
+#endif
+#ifndef platform_outl
+# define platform_outl         __ia64_outl
+#endif
+#ifndef platform_mmiowb
+# define platform_mmiowb       __ia64_mmiowb
+#endif
+#ifndef platform_readb
+# define platform_readb                __ia64_readb
+#endif
+#ifndef platform_readw
+# define platform_readw                __ia64_readw
+#endif
+#ifndef platform_readl
+# define platform_readl                __ia64_readl
+#endif
+#ifndef platform_readq
+# define platform_readq                __ia64_readq
+#endif
+#ifndef platform_readb_relaxed
+# define platform_readb_relaxed        __ia64_readb_relaxed
+#endif
+#ifndef platform_readw_relaxed
+# define platform_readw_relaxed        __ia64_readw_relaxed
+#endif
+#ifndef platform_readl_relaxed
+# define platform_readl_relaxed        __ia64_readl_relaxed
+#endif
+#ifndef platform_readq_relaxed
+# define platform_readq_relaxed        __ia64_readq_relaxed
+#endif
+
+#endif /* _ASM_IA64_MACHVEC_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm/machvec_hpsim.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/machvec_hpsim.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,18 @@
+#ifndef _ASM_IA64_MACHVEC_HPSIM_h
+#define _ASM_IA64_MACHVEC_HPSIM_h
+
+extern ia64_mv_setup_t hpsim_setup;
+extern ia64_mv_irq_init_t hpsim_irq_init;
+
+/*
+ * This stuff has dual use!
+ *
+ * For a generic kernel, the macros are used to initialize the
+ * platform's machvec structure.  When compiling a non-generic kernel,
+ * the macros are used directly.
+ */
+#define platform_name          "hpsim"
+#define platform_setup         hpsim_setup
+#define platform_irq_init      hpsim_irq_init
+
+#endif /* _ASM_IA64_MACHVEC_HPSIM_h */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/mca.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/mca.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,132 @@
+/*
+ * File:       mca.h
+ * Purpose:    Machine check handling specific defines
+ *
+ * Copyright (C) 1999, 2004 Silicon Graphics, Inc.
+ * Copyright (C) Vijay Chander (vijay@xxxxxxxxxxxx)
+ * Copyright (C) Srinivasa Thirumalachar (sprasad@xxxxxxxxxxxx)
+ * Copyright (C) Russ Anderson (rja@xxxxxxx)
+ */
+
+#ifndef _ASM_IA64_MCA_H
+#define _ASM_IA64_MCA_H
+
+#define IA64_MCA_STACK_SIZE    8192
+
+#if !defined(__ASSEMBLY__)
+
+#include <linux/interrupt.h>
+#include <linux/types.h>
+
+#include <asm/param.h>
+#include <asm/sal.h>
+#include <asm/processor.h>
+#include <asm/mca_asm.h>
+
+#define IA64_MCA_RENDEZ_TIMEOUT                (20 * 1000)     /* value in 
milliseconds - 20 seconds */
+
+typedef struct ia64_fptr {
+       unsigned long fp;
+       unsigned long gp;
+} ia64_fptr_t;
+
+typedef union cmcv_reg_u {
+       u64     cmcv_regval;
+       struct  {
+               u64     cmcr_vector             : 8;
+               u64     cmcr_reserved1          : 4;
+               u64     cmcr_ignored1           : 1;
+               u64     cmcr_reserved2          : 3;
+               u64     cmcr_mask               : 1;
+               u64     cmcr_ignored2           : 47;
+       } cmcv_reg_s;
+
+} cmcv_reg_t;
+
+#define cmcv_mask              cmcv_reg_s.cmcr_mask
+#define cmcv_vector            cmcv_reg_s.cmcr_vector
+
+enum {
+       IA64_MCA_RENDEZ_CHECKIN_NOTDONE =       0x0,
+       IA64_MCA_RENDEZ_CHECKIN_DONE    =       0x1
+};
+
+/* Information maintained by the MC infrastructure */
+typedef struct ia64_mc_info_s {
+       u64             imi_mca_handler;
+       size_t          imi_mca_handler_size;
+       u64             imi_monarch_init_handler;
+       size_t          imi_monarch_init_handler_size;
+       u64             imi_slave_init_handler;
+       size_t          imi_slave_init_handler_size;
+       u8              imi_rendez_checkin[NR_CPUS];
+
+} ia64_mc_info_t;
+
+typedef struct ia64_mca_sal_to_os_state_s {
+       u64             imsto_os_gp;            /* GP of the os registered with 
the SAL */
+       u64             imsto_pal_proc;         /* PAL_PROC entry point - 
physical addr */
+       u64             imsto_sal_proc;         /* SAL_PROC entry point - 
physical addr */
+       u64             imsto_sal_gp;           /* GP of the SAL - physical */
+       u64             imsto_rendez_state;     /* Rendez state information */
+       u64             imsto_sal_check_ra;     /* Return address in SAL_CHECK 
while going
+                                                * back to SAL from OS after 
MCA handling.
+                                                */
+       u64             pal_min_state;          /* from PAL in r17 */
+       u64             proc_state_param;       /* from PAL in r18. See SDV 
2:268 11.3.2.1 */
+} ia64_mca_sal_to_os_state_t;
+
+enum {
+       IA64_MCA_CORRECTED      =       0x0,    /* Error has been corrected by 
OS_MCA */
+       IA64_MCA_WARM_BOOT      =       -1,     /* Warm boot of the system need 
from SAL */
+       IA64_MCA_COLD_BOOT      =       -2,     /* Cold boot of the system need 
from SAL */
+       IA64_MCA_HALT           =       -3      /* System to be halted by SAL */
+};
+
+enum {
+       IA64_MCA_SAME_CONTEXT   =       0x0,    /* SAL to return to same 
context */
+       IA64_MCA_NEW_CONTEXT    =       -1      /* SAL to return to new context 
*/
+};
+
+typedef struct ia64_mca_os_to_sal_state_s {
+       u64             imots_os_status;        /*   OS status to SAL as to 
what happened
+                                                *   with the MCA handling.
+                                                */
+       u64             imots_sal_gp;           /* GP of the SAL - physical */
+       u64             imots_context;          /* 0 if return to same context
+                                                  1 if return to new context */
+       u64             *imots_new_min_state;   /* Pointer to structure 
containing
+                                                * new values of registers in 
the min state
+                                                * save area.
+                                                */
+       u64             imots_sal_check_ra;     /* Return address in SAL_CHECK 
while going
+                                                * back to SAL from OS after 
MCA handling.
+                                                */
+} ia64_mca_os_to_sal_state_t;
+
+/* Per-CPU MCA state that is too big for normal per-CPU variables.  */
+
+struct ia64_mca_cpu {
+       u64 stack[IA64_MCA_STACK_SIZE/8];       /* MCA memory-stack */
+       u64 proc_state_dump[512];
+       u64 stackframe[32];
+       u64 rbstore[IA64_MCA_STACK_SIZE/8];     /* MCA reg.-backing store */
+       u64 init_stack[KERNEL_STACK_SIZE/8];
+} __attribute__ ((aligned(16)));
+
+/* Array of physical addresses of each CPU's MCA area.  */
+extern unsigned long __per_cpu_mca[NR_CPUS];
+
+extern void ia64_mca_init(void);
+extern void ia64_mca_cpu_init(void *);
+extern void ia64_os_mca_dispatch(void);
+extern void ia64_os_mca_dispatch_end(void);
+extern void ia64_mca_ucmc_handler(void);
+extern void ia64_monarch_init_handler(void);
+extern void ia64_slave_init_handler(void);
+extern void ia64_mca_cmc_vector_setup(void);
+extern int  ia64_reg_MCA_extension(void*);
+extern void ia64_unreg_MCA_extension(void);
+
+#endif /* !__ASSEMBLY__ */
+#endif /* _ASM_IA64_MCA_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/meminit.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/meminit.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,60 @@
+#ifndef meminit_h
+#define meminit_h
+
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ */
+
+#include <linux/config.h>
+
+/*
+ * Entries defined so far:
+ *     - boot param structure itself
+ *     - memory map
+ *     - initrd (optional)
+ *     - command line string
+ *     - kernel code & data
+ *
+ * More could be added if necessary
+ */
+#define IA64_MAX_RSVD_REGIONS 5
+
+struct rsvd_region {
+       unsigned long start;    /* virtual address of beginning of element */
+       unsigned long end;      /* virtual address of end of element + 1 */
+};
+
+extern struct rsvd_region rsvd_region[IA64_MAX_RSVD_REGIONS + 1];
+extern int num_rsvd_regions;
+
+extern void find_memory (void);
+extern void reserve_memory (void);
+extern void find_initrd (void);
+extern int filter_rsvd_memory (unsigned long start, unsigned long end, void 
*arg);
+
+/*
+ * For rounding an address to the next IA64_GRANULE_SIZE or order
+ */
+#define GRANULEROUNDDOWN(n)    ((n) & ~(IA64_GRANULE_SIZE-1))
+#define GRANULEROUNDUP(n)      (((n)+IA64_GRANULE_SIZE-1) & 
~(IA64_GRANULE_SIZE-1))
+#define ORDERROUNDDOWN(n)      ((n) & ~((PAGE_SIZE<<MAX_ORDER)-1))
+
+#ifdef CONFIG_DISCONTIGMEM
+  extern void call_pernode_memory (unsigned long start, unsigned long len, 
void *func);
+#else
+# define call_pernode_memory(start, len, func) (*func)(start, len, 0)
+#endif
+
+#define IGNORE_PFN0    1       /* XXX fix me: ignore pfn 0 until TLB miss 
handler is updated... */
+
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+# define LARGE_GAP     0x40000000 /* Use virtual mem map if hole is > than 
this */
+  extern unsigned long vmalloc_end;
+  extern struct page *vmem_map;
+  extern int find_largest_hole (u64 start, u64 end, void *arg);
+  extern int create_mem_map_page_table (u64 start, u64 end, void *arg);
+#endif
+
+#endif /* meminit_h */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/mman.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/mman.h     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,51 @@
+#ifndef _ASM_IA64_MMAN_H
+#define _ASM_IA64_MMAN_H
+
+/*
+ * Based on <asm-i386/mman.h>.
+ *
+ * Modified 1998-2000, 2002
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+#define PROT_READ      0x1             /* page can be read */
+#define PROT_WRITE     0x2             /* page can be written */
+#define PROT_EXEC      0x4             /* page can be executed */
+#define PROT_SEM       0x8             /* page may be used for atomic ops */
+#define PROT_NONE      0x0             /* page can not be accessed */
+#define PROT_GROWSDOWN 0x01000000      /* mprotect flag: extend change to 
start of growsdown vma */
+#define PROT_GROWSUP   0x02000000      /* mprotect flag: extend change to end 
of growsup vma */
+
+#define MAP_SHARED     0x01            /* Share changes */
+#define MAP_PRIVATE    0x02            /* Changes are private */
+#define MAP_TYPE       0x0f            /* Mask for type of mapping */
+#define MAP_FIXED      0x10            /* Interpret addr exactly */
+#define MAP_ANONYMOUS  0x20            /* don't use a file */
+
+#define MAP_GROWSDOWN  0x00100         /* stack-like segment */
+#define MAP_GROWSUP    0x00200         /* register stack-like segment */
+#define MAP_DENYWRITE  0x00800         /* ETXTBSY */
+#define MAP_EXECUTABLE 0x01000         /* mark it as an executable */
+#define MAP_LOCKED     0x02000         /* pages are locked */
+#define MAP_NORESERVE  0x04000         /* don't check for reservations */
+#define MAP_POPULATE   0x08000         /* populate (prefault) pagetables */
+#define MAP_NONBLOCK   0x10000         /* do not block on IO */
+
+#define MS_ASYNC       1               /* sync memory asynchronously */
+#define MS_INVALIDATE  2               /* invalidate the caches */
+#define MS_SYNC                4               /* synchronous memory sync */
+
+#define MCL_CURRENT    1               /* lock all current mappings */
+#define MCL_FUTURE     2               /* lock all future mappings */
+
+#define MADV_NORMAL    0x0             /* default page-in behavior */
+#define MADV_RANDOM    0x1             /* page-in minimum required */
+#define MADV_SEQUENTIAL        0x2             /* read-ahead aggressively */
+#define MADV_WILLNEED  0x3             /* pre-fault pages */
+#define MADV_DONTNEED  0x4             /* discard these pages */
+
+/* compatibility flags */
+#define MAP_ANON       MAP_ANONYMOUS
+#define MAP_FILE       0
+
+#endif /* _ASM_IA64_MMAN_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/numa.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/numa.h     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,74 @@
+/*
+ * This file is subject to the terms and conditions of the GNU General Public
+ * License.  See the file "COPYING" in the main directory of this archive
+ * for more details.
+ *
+ * This file contains NUMA specific prototypes and definitions.
+ *
+ * 2002/08/05 Erich Focht <efocht@xxxxxxxxxx>
+ *
+ */
+#ifndef _ASM_IA64_NUMA_H
+#define _ASM_IA64_NUMA_H
+
+#include <linux/config.h>
+
+#ifdef CONFIG_NUMA
+
+#include <linux/cache.h>
+#include <linux/cpumask.h>
+#include <linux/numa.h>
+#include <linux/smp.h>
+#include <linux/threads.h>
+
+#include <asm/mmzone.h>
+
+extern u8 cpu_to_node_map[NR_CPUS] __cacheline_aligned;
+extern cpumask_t node_to_cpu_mask[MAX_NUMNODES] __cacheline_aligned;
+
+/* Stuff below this line could be architecture independent */
+
+extern int num_node_memblks;           /* total number of memory chunks */
+
+/*
+ * List of node memory chunks. Filled when parsing SRAT table to
+ * obtain information about memory nodes.
+*/
+
+struct node_memblk_s {
+       unsigned long start_paddr;
+       unsigned long size;
+       int nid;                /* which logical node contains this chunk? */
+       int bank;               /* which mem bank on this node */
+};
+
+struct node_cpuid_s {
+       u16     phys_id;        /* id << 8 | eid */
+       int     nid;            /* logical node containing this CPU */
+};
+
+extern struct node_memblk_s node_memblk[NR_NODE_MEMBLKS];
+extern struct node_cpuid_s node_cpuid[NR_CPUS];
+
+/*
+ * ACPI 2.0 SLIT (System Locality Information Table)
+ * http://devresource.hp.com/devresource/Docs/TechPapers/IA64/slit.pdf
+ *
+ * This is a matrix with "distances" between nodes, they should be
+ * proportional to the memory access latency ratios.
+ */
+
+extern u8 numa_slit[MAX_NUMNODES * MAX_NUMNODES];
+#define node_distance(from,to) (numa_slit[(from) * num_online_nodes() + (to)])
+
+extern int paddr_to_nid(unsigned long paddr);
+
+#define local_nodeid (cpu_to_node_map[smp_processor_id()])
+
+#else /* !CONFIG_NUMA */
+
+#define paddr_to_nid(addr)     0
+
+#endif /* CONFIG_NUMA */
+
+#endif /* _ASM_IA64_NUMA_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/param.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/param.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,42 @@
+#ifndef _ASM_IA64_PARAM_H
+#define _ASM_IA64_PARAM_H
+
+/*
+ * Fundamental kernel parameters.
+ *
+ * Based on <asm-i386/param.h>.
+ *
+ * Modified 1998, 1999, 2002-2003
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+#define EXEC_PAGESIZE  65536
+
+#ifndef NOGROUP
+# define NOGROUP       (-1)
+#endif
+
+#define MAXHOSTNAMELEN 64      /* max length of hostname */
+
+#ifdef __KERNEL__
+# include <linux/config.h>     /* mustn't include <linux/config.h> outside of 
#ifdef __KERNEL__ */
+# ifdef CONFIG_IA64_HP_SIM
+  /*
+   * Yeah, simulating stuff is slow, so let us catch some breath between
+   * timer interrupts...
+   */
+#  define HZ     32
+# else
+#  define HZ   1024
+# endif
+# define USER_HZ       HZ
+# define CLOCKS_PER_SEC        HZ      /* frequency at which times() counts */
+#else
+   /*
+    * Technically, this is wrong, but some old apps still refer to it.  The 
proper way to
+    * get the HZ value is via sysconf(_SC_CLK_TCK).
+    */
+# define HZ 1024
+#endif
+
+#endif /* _ASM_IA64_PARAM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/patch.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/patch.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,25 @@
+#ifndef _ASM_IA64_PATCH_H
+#define _ASM_IA64_PATCH_H
+
+/*
+ * Copyright (C) 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * There are a number of reasons for patching instructions.  Rather than 
duplicating code
+ * all over the place, we put the common stuff here.  Reasons for patching: 
in-kernel
+ * module-loader, virtual-to-physical patch-list, McKinley Errata 9 
workaround, and gate
+ * shared library.  Undoubtedly, some of these reasons will disappear and 
others will
+ * be added over time.
+ */
+#include <linux/elf.h>
+#include <linux/types.h>
+
+extern void ia64_patch (u64 insn_addr, u64 mask, u64 val);     /* patch any 
insn slot */
+extern void ia64_patch_imm64 (u64 insn_addr, u64 val);         /* patch "movl" 
w/abs. value*/
+extern void ia64_patch_imm60 (u64 insn_addr, u64 val);         /* patch "brl" 
w/ip-rel value */
+
+extern void ia64_patch_mckinley_e9 (unsigned long start, unsigned long end);
+extern void ia64_patch_vtop (unsigned long start, unsigned long end);
+extern void ia64_patch_gate (void);
+
+#endif /* _ASM_IA64_PATCH_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/pci.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/pci.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,146 @@
+#ifndef _ASM_IA64_PCI_H
+#define _ASM_IA64_PCI_H
+
+#include <linux/mm.h>
+#include <linux/slab.h>
+#include <linux/spinlock.h>
+#include <linux/string.h>
+#include <linux/types.h>
+
+#include <asm/io.h>
+#include <asm/scatterlist.h>
+
+/*
+ * Can be used to override the logic in pci_scan_bus for skipping 
already-configured bus
+ * numbers - to be used for buggy BIOSes or architectures with incomplete PCI 
setup by the
+ * loader.
+ */
+#define pcibios_assign_all_busses()     0
+#define pcibios_scan_all_fns(a, b)     0
+
+#define PCIBIOS_MIN_IO         0x1000
+#define PCIBIOS_MIN_MEM                0x10000000
+
+void pcibios_config_init(void);
+
+struct pci_dev;
+
+/*
+ * PCI_DMA_BUS_IS_PHYS should be set to 1 if there is _necessarily_ a direct 
correspondence
+ * between device bus addresses and CPU physical addresses.  Platforms with a 
hardware I/O
+ * MMU _must_ turn this off to suppress the bounce buffer handling code in the 
block and
+ * network device layers.  Platforms with separate bus address spaces _must_ 
turn this off
+ * and provide a device DMA mapping implementation that takes care of the 
necessary
+ * address translation.
+ *
+ * For now, the ia64 platforms which may have separate/multiple bus address 
spaces all
+ * have I/O MMUs which support the merging of physically discontiguous 
buffers, so we can
+ * use that as the sole factor to determine the setting of PCI_DMA_BUS_IS_PHYS.
+ */
+extern unsigned long ia64_max_iommu_merge_mask;
+#define PCI_DMA_BUS_IS_PHYS    (ia64_max_iommu_merge_mask == ~0UL)
+
+static inline void
+pcibios_set_master (struct pci_dev *dev)
+{
+       /* No special bus mastering setup handling */
+}
+
+static inline void
+pcibios_penalize_isa_irq (int irq)
+{
+       /* We don't do dynamic PCI IRQ allocation */
+}
+
+#define HAVE_ARCH_PCI_MWI 1
+extern int pcibios_prep_mwi (struct pci_dev *);
+
+#include <asm-generic/pci-dma-compat.h>
+
+/* pci_unmap_{single,page} is not a nop, thus... */
+#define DECLARE_PCI_UNMAP_ADDR(ADDR_NAME)      \
+       dma_addr_t ADDR_NAME;
+#define DECLARE_PCI_UNMAP_LEN(LEN_NAME)                \
+       __u32 LEN_NAME;
+#define pci_unmap_addr(PTR, ADDR_NAME)                 \
+       ((PTR)->ADDR_NAME)
+#define pci_unmap_addr_set(PTR, ADDR_NAME, VAL)                \
+       (((PTR)->ADDR_NAME) = (VAL))
+#define pci_unmap_len(PTR, LEN_NAME)                   \
+       ((PTR)->LEN_NAME)
+#define pci_unmap_len_set(PTR, LEN_NAME, VAL)          \
+       (((PTR)->LEN_NAME) = (VAL))
+
+/* The ia64 platform always supports 64-bit addressing. */
+#define pci_dac_dma_supported(pci_dev, mask)           (1)
+#define pci_dac_page_to_dma(dev,pg,off,dir)            ((dma_addr_t) 
page_to_bus(pg) + (off))
+#define pci_dac_dma_to_page(dev,dma_addr)              
(virt_to_page(bus_to_virt(dma_addr)))
+#define pci_dac_dma_to_offset(dev,dma_addr)            offset_in_page(dma_addr)
+#define pci_dac_dma_sync_single_for_cpu(dev,dma_addr,len,dir)  do { } while (0)
+#define pci_dac_dma_sync_single_for_device(dev,dma_addr,len,dir)       do { 
mb(); } while (0)
+
+#define sg_dma_len(sg)         ((sg)->dma_length)
+#define sg_dma_address(sg)     ((sg)->dma_address)
+
+#define HAVE_PCI_MMAP
+extern int pci_mmap_page_range (struct pci_dev *dev, struct vm_area_struct 
*vma,
+                               enum pci_mmap_state mmap_state, int 
write_combine);
+#define HAVE_PCI_LEGACY
+extern int pci_mmap_legacy_page_range(struct pci_bus *bus,
+                                     struct vm_area_struct *vma);
+extern ssize_t pci_read_legacy_io(struct kobject *kobj, char *buf, loff_t off,
+                                 size_t count);
+extern ssize_t pci_write_legacy_io(struct kobject *kobj, char *buf, loff_t off,
+                                  size_t count);
+extern int pci_mmap_legacy_mem(struct kobject *kobj,
+                              struct bin_attribute *attr,
+                              struct vm_area_struct *vma);
+
+#define pci_get_legacy_mem platform_pci_get_legacy_mem
+#define pci_legacy_read platform_pci_legacy_read
+#define pci_legacy_write platform_pci_legacy_write
+
+struct pci_window {
+       struct resource resource;
+       u64 offset;
+};
+
+struct pci_controller {
+       void *acpi_handle;
+       void *iommu;
+       int segment;
+
+       unsigned int windows;
+       struct pci_window *window;
+
+       void *platform_data;
+};
+
+#define PCI_CONTROLLER(busdev) ((struct pci_controller *) busdev->sysdata)
+#define pci_domain_nr(busdev)    (PCI_CONTROLLER(busdev)->segment)
+
+extern struct pci_ops pci_root_ops;
+
+static inline int pci_name_bus(char *name, struct pci_bus *bus)
+{
+       if (pci_domain_nr(bus) == 0) {
+               sprintf(name, "%02x", bus->number);
+       } else {
+               sprintf(name, "%04x:%02x", pci_domain_nr(bus), bus->number);
+       }
+       return 0;
+}
+
+static inline void pcibios_add_platform_entries(struct pci_dev *dev)
+{
+}
+
+extern void pcibios_resource_to_bus(struct pci_dev *dev,
+               struct pci_bus_region *region, struct resource *res);
+
+extern void pcibios_bus_to_resource(struct pci_dev *dev,
+               struct resource *res, struct pci_bus_region *region);
+
+#define pcibios_scan_all_fns(a, b)     0
+
+#endif /* _ASM_IA64_PCI_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/percpu.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/percpu.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,72 @@
+#ifndef _ASM_IA64_PERCPU_H
+#define _ASM_IA64_PERCPU_H
+
+/*
+ * Copyright (C) 2002-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#define PERCPU_ENOUGH_ROOM PERCPU_PAGE_SIZE
+
+#ifdef __ASSEMBLY__
+# define THIS_CPU(var) (per_cpu__##var)  /* use this to mark accesses to 
per-CPU variables... */
+#else /* !__ASSEMBLY__ */
+
+#include <linux/config.h>
+
+#include <linux/threads.h>
+
+#ifdef HAVE_MODEL_SMALL_ATTRIBUTE
+# define __SMALL_ADDR_AREA     __attribute__((__model__ (__small__)))
+#else
+# define __SMALL_ADDR_AREA
+#endif
+
+#define DECLARE_PER_CPU(type, name)                            \
+       extern __SMALL_ADDR_AREA __typeof__(type) per_cpu__##name
+
+/* Separate out the type, so (int[3], foo) works. */
+#define DEFINE_PER_CPU(type, name)                             \
+       __attribute__((__section__(".data.percpu")))            \
+       __SMALL_ADDR_AREA __typeof__(type) per_cpu__##name
+
+/*
+ * Pretty much a literal copy of asm-generic/percpu.h, except that 
percpu_modcopy() is an
+ * external routine, to avoid include-hell.
+ */
+#ifdef CONFIG_SMP
+
+extern unsigned long __per_cpu_offset[NR_CPUS];
+
+/* Equal to __per_cpu_offset[smp_processor_id()], but faster to access: */
+DECLARE_PER_CPU(unsigned long, local_per_cpu_offset);
+
+#define per_cpu(var, cpu)  (*RELOC_HIDE(&per_cpu__##var, 
__per_cpu_offset[cpu]))
+#define __get_cpu_var(var) (*RELOC_HIDE(&per_cpu__##var, 
__ia64_per_cpu_var(local_per_cpu_offset)))
+
+extern void percpu_modcopy(void *pcpudst, const void *src, unsigned long size);
+extern void setup_per_cpu_areas (void);
+extern void *per_cpu_init(void);
+
+#else /* ! SMP */
+
+#define per_cpu(var, cpu)                      (*((void)cpu, &per_cpu__##var))
+#define __get_cpu_var(var)                     per_cpu__##var
+#define per_cpu_init()                         (__phys_per_cpu_start)
+
+#endif /* SMP */
+
+#define EXPORT_PER_CPU_SYMBOL(var)             EXPORT_SYMBOL(per_cpu__##var)
+#define EXPORT_PER_CPU_SYMBOL_GPL(var)         
EXPORT_SYMBOL_GPL(per_cpu__##var)
+
+/*
+ * Be extremely careful when taking the address of this variable!  Due to 
virtual
+ * remapping, it is different from the canonical address returned by 
__get_cpu_var(var)!
+ * On the positive side, using __ia64_per_cpu_var() instead of __get_cpu_var() 
is slightly
+ * more efficient.
+ */
+#define __ia64_per_cpu_var(var)        (per_cpu__##var)
+
+#endif /* !__ASSEMBLY__ */
+
+#endif /* _ASM_IA64_PERCPU_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/pgtable.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/pgtable.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,567 @@
+#ifndef _ASM_IA64_PGTABLE_H
+#define _ASM_IA64_PGTABLE_H
+
+/*
+ * This file contains the functions and defines necessary to modify and use
+ * the IA-64 page table tree.
+ *
+ * This hopefully works with any (fixed) IA-64 page-size, as defined
+ * in <asm/page.h>.
+ *
+ * Copyright (C) 1998-2004 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>
+
+#include <asm/mman.h>
+#include <asm/page.h>
+#include <asm/processor.h>
+#include <asm/system.h>
+#include <asm/types.h>
+
+#define IA64_MAX_PHYS_BITS     50      /* max. number of physical address bits 
(architected) */
+
+/*
+ * First, define the various bits in a PTE.  Note that the PTE format
+ * matches the VHPT short format, the firt doubleword of the VHPD long
+ * format, and the first doubleword of the TLB insertion format.
+ */
+#define _PAGE_P_BIT            0
+#define _PAGE_A_BIT            5
+#define _PAGE_D_BIT            6
+
+#define _PAGE_P                        (1 << _PAGE_P_BIT)      /* page present 
bit */
+#define _PAGE_MA_WB            (0x0 <<  2)     /* write back memory attribute 
*/
+#define _PAGE_MA_UC            (0x4 <<  2)     /* uncacheable memory attribute 
*/
+#define _PAGE_MA_UCE           (0x5 <<  2)     /* UC exported attribute */
+#define _PAGE_MA_WC            (0x6 <<  2)     /* write coalescing memory 
attribute */
+#define _PAGE_MA_NAT           (0x7 <<  2)     /* not-a-thing attribute */
+#define _PAGE_MA_MASK          (0x7 <<  2)
+#define _PAGE_PL_0             (0 <<  7)       /* privilege level 0 (kernel) */
+#define _PAGE_PL_1             (1 <<  7)       /* privilege level 1 (unused) */
+#define _PAGE_PL_2             (2 <<  7)       /* privilege level 2 (unused) */
+#define _PAGE_PL_3             (3 <<  7)       /* privilege level 3 (user) */
+#define _PAGE_PL_MASK          (3 <<  7)
+#define _PAGE_AR_R             (0 <<  9)       /* read only */
+#define _PAGE_AR_RX            (1 <<  9)       /* read & execute */
+#define _PAGE_AR_RW            (2 <<  9)       /* read & write */
+#define _PAGE_AR_RWX           (3 <<  9)       /* read, write & execute */
+#define _PAGE_AR_R_RW          (4 <<  9)       /* read / read & write */
+#define _PAGE_AR_RX_RWX                (5 <<  9)       /* read & exec / read, 
write & exec */
+#define _PAGE_AR_RWX_RW                (6 <<  9)       /* read, write & exec / 
read & write */
+#define _PAGE_AR_X_RX          (7 <<  9)       /* exec & promote / read & exec 
*/
+#define _PAGE_AR_MASK          (7 <<  9)
+#define _PAGE_AR_SHIFT         9
+#define _PAGE_A                        (1 << _PAGE_A_BIT)      /* page 
accessed bit */
+#define _PAGE_D                        (1 << _PAGE_D_BIT)      /* page dirty 
bit */
+#define _PAGE_PPN_MASK         (((__IA64_UL(1) << IA64_MAX_PHYS_BITS) - 1) & 
~0xfffUL)
+#define _PAGE_ED               (__IA64_UL(1) << 52)    /* exception deferral */
+#define _PAGE_PROTNONE         (__IA64_UL(1) << 63)
+
+/* Valid only for a PTE with the present bit cleared: */
+#define _PAGE_FILE             (1 << 1)                /* see swap & file pte 
remarks below */
+
+#define _PFN_MASK              _PAGE_PPN_MASK
+/* Mask of bits which may be changed by pte_modify(); the odd bits are there 
for _PAGE_PROTNONE */
+#define _PAGE_CHG_MASK (_PAGE_P | _PAGE_PROTNONE | _PAGE_PL_MASK | 
_PAGE_AR_MASK | _PAGE_ED)
+
+#define _PAGE_SIZE_4K  12
+#define _PAGE_SIZE_8K  13
+#define _PAGE_SIZE_16K 14
+#define _PAGE_SIZE_64K 16
+#define _PAGE_SIZE_256K        18
+#define _PAGE_SIZE_1M  20
+#define _PAGE_SIZE_4M  22
+#define _PAGE_SIZE_16M 24
+#define _PAGE_SIZE_64M 26
+#define _PAGE_SIZE_256M        28
+#define _PAGE_SIZE_1G  30
+#define _PAGE_SIZE_4G  32
+
+#define __ACCESS_BITS          _PAGE_ED | _PAGE_A | _PAGE_P | _PAGE_MA_WB
+#define __DIRTY_BITS_NO_ED     _PAGE_A | _PAGE_P | _PAGE_D | _PAGE_MA_WB
+#define __DIRTY_BITS           _PAGE_ED | __DIRTY_BITS_NO_ED
+
+/*
+ * Definitions for first level:
+ *
+ * PGDIR_SHIFT determines what a first-level page table entry can map.
+ */
+#define PGDIR_SHIFT            (PAGE_SHIFT + 2*(PAGE_SHIFT-3))
+#define PGDIR_SIZE             (__IA64_UL(1) << PGDIR_SHIFT)
+#define PGDIR_MASK             (~(PGDIR_SIZE-1))
+#define PTRS_PER_PGD           (1UL << (PAGE_SHIFT-3))
+#define USER_PTRS_PER_PGD      (5*PTRS_PER_PGD/8)      /* regions 0-4 are user 
regions */
+#define FIRST_USER_PGD_NR      0
+
+/*
+ * Definitions for second level:
+ *
+ * PMD_SHIFT determines the size of the area a second-level page table
+ * can map.
+ */
+#define PMD_SHIFT      (PAGE_SHIFT + (PAGE_SHIFT-3))
+#define PMD_SIZE       (1UL << PMD_SHIFT)
+#define PMD_MASK       (~(PMD_SIZE-1))
+#define PTRS_PER_PMD   (1UL << (PAGE_SHIFT-3))
+
+/*
+ * Definitions for third level:
+ */
+#define PTRS_PER_PTE   (__IA64_UL(1) << (PAGE_SHIFT-3))
+
+/*
+ * All the normal masks have the "page accessed" bits on, as any time
+ * they are used, the page is accessed. They are cleared only by the
+ * page-out routines.
+ */
+#define PAGE_NONE      __pgprot(_PAGE_PROTNONE | _PAGE_A)
+#define PAGE_SHARED    __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RW)
+#define PAGE_READONLY  __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_R)
+#define PAGE_COPY      __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_R)
+#define PAGE_COPY_EXEC __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RX)
+#define PAGE_GATE      __pgprot(__ACCESS_BITS | _PAGE_PL_0 | _PAGE_AR_X_RX)
+#define PAGE_KERNEL    __pgprot(__DIRTY_BITS  | _PAGE_PL_0 | _PAGE_AR_RWX)
+#define PAGE_KERNELRX  __pgprot(__ACCESS_BITS | _PAGE_PL_0 | _PAGE_AR_RX)
+
+# ifndef __ASSEMBLY__
+
+#include <asm/bitops.h>
+#include <asm/cacheflush.h>
+#include <asm/mmu_context.h>
+#include <asm/processor.h>
+
+/*
+ * Next come the mappings that determine how mmap() protection bits
+ * (PROT_EXEC, PROT_READ, PROT_WRITE, PROT_NONE) get implemented.  The
+ * _P version gets used for a private shared memory segment, the _S
+ * version gets used for a shared memory segment with MAP_SHARED on.
+ * In a private shared memory segment, we do a copy-on-write if a task
+ * attempts to write to the page.
+ */
+       /* xwr */
+#define __P000 PAGE_NONE
+#define __P001 PAGE_READONLY
+#define __P010 PAGE_READONLY   /* write to priv pg -> copy & make writable */
+#define __P011 PAGE_READONLY   /* ditto */
+#define __P100 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_X_RX)
+#define __P101 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RX)
+#define __P110 PAGE_COPY_EXEC
+#define __P111 PAGE_COPY_EXEC
+
+#define __S000 PAGE_NONE
+#define __S001 PAGE_READONLY
+#define __S010 PAGE_SHARED     /* we don't have (and don't need) write-only */
+#define __S011 PAGE_SHARED
+#define __S100 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_X_RX)
+#define __S101 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RX)
+#define __S110 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RWX)
+#define __S111 __pgprot(__ACCESS_BITS | _PAGE_PL_3 | _PAGE_AR_RWX)
+
+#define pgd_ERROR(e)   printk("%s:%d: bad pgd %016lx.\n", __FILE__, __LINE__, 
pgd_val(e))
+#define pmd_ERROR(e)   printk("%s:%d: bad pmd %016lx.\n", __FILE__, __LINE__, 
pmd_val(e))
+#define pte_ERROR(e)   printk("%s:%d: bad pte %016lx.\n", __FILE__, __LINE__, 
pte_val(e))
+
+
+/*
+ * Some definitions to translate between mem_map, PTEs, and page addresses:
+ */
+
+
+/* Quick test to see if ADDR is a (potentially) valid physical address. */
+static inline long
+ia64_phys_addr_valid (unsigned long addr)
+{
+       return (addr & (local_cpu_data->unimpl_pa_mask)) == 0;
+}
+
+/*
+ * kern_addr_valid(ADDR) tests if ADDR is pointing to valid kernel
+ * memory.  For the return value to be meaningful, ADDR must be >=
+ * PAGE_OFFSET.  This operation can be relatively expensive (e.g.,
+ * require a hash-, or multi-level tree-lookup or something of that
+ * sort) but it guarantees to return TRUE only if accessing the page
+ * at that address does not cause an error.  Note that there may be
+ * addresses for which kern_addr_valid() returns FALSE even though an
+ * access would not cause an error (e.g., this is typically true for
+ * memory mapped I/O regions.
+ *
+ * XXX Need to implement this for IA-64.
+ */
+#define kern_addr_valid(addr)  (1)
+
+
+/*
+ * Now come the defines and routines to manage and access the three-level
+ * page table.
+ */
+
+/*
+ * On some architectures, special things need to be done when setting
+ * the PTE in a page table.  Nothing special needs to be on IA-64.
+ */
+#define set_pte(ptep, pteval)  (*(ptep) = (pteval))
+
+#define RGN_SIZE       (1UL << 61)
+#define RGN_KERNEL     7
+
+#define VMALLOC_START          0xa000000200000000UL
+#ifdef CONFIG_VIRTUAL_MEM_MAP
+# define VMALLOC_END_INIT      (0xa000000000000000UL + (1UL << (4*PAGE_SHIFT - 
9)))
+# define VMALLOC_END           vmalloc_end
+  extern unsigned long vmalloc_end;
+#else
+# define VMALLOC_END           (0xa000000000000000UL + (1UL << (4*PAGE_SHIFT - 
9)))
+#endif
+
+/* fs/proc/kcore.c */
+#define        kc_vaddr_to_offset(v) ((v) - 0xa000000000000000UL)
+#define        kc_offset_to_vaddr(o) ((o) + 0xa000000000000000UL)
+
+/*
+ * Conversion functions: convert page frame number (pfn) and a protection 
value to a page
+ * table entry (pte).
+ */
+#define pfn_pte(pfn, pgprot) \
+({ pte_t __pte; pte_val(__pte) = ((pfn) << PAGE_SHIFT) | pgprot_val(pgprot); 
__pte; })
+
+/* Extract pfn from pte.  */
+#define pte_pfn(_pte)          ((pte_val(_pte) & _PFN_MASK) >> PAGE_SHIFT)
+
+#define mk_pte(page, pgprot)   pfn_pte(page_to_pfn(page), (pgprot))
+
+/* This takes a physical page address that is used by the remapping functions 
*/
+#define mk_pte_phys(physpage, pgprot) \
+({ pte_t __pte; pte_val(__pte) = physpage + pgprot_val(pgprot); __pte; })
+
+#define pte_modify(_pte, newprot) \
+       (__pte((pte_val(_pte) & ~_PAGE_CHG_MASK) | (pgprot_val(newprot) & 
_PAGE_CHG_MASK)))
+
+#define page_pte_prot(page,prot)       mk_pte(page, prot)
+#define page_pte(page)                 page_pte_prot(page, __pgprot(0))
+
+#define pte_none(pte)                  (!pte_val(pte))
+#define pte_present(pte)               (pte_val(pte) & (_PAGE_P | 
_PAGE_PROTNONE))
+#define pte_clear(pte)                 (pte_val(*(pte)) = 0UL)
+/* pte_page() returns the "struct page *" corresponding to the PTE: */
+#define pte_page(pte)                  virt_to_page(((pte_val(pte) & 
_PFN_MASK) + PAGE_OFFSET))
+
+#define pmd_none(pmd)                  (!pmd_val(pmd))
+#define pmd_bad(pmd)                   (!ia64_phys_addr_valid(pmd_val(pmd)))
+#define pmd_present(pmd)               (pmd_val(pmd) != 0UL)
+#define pmd_clear(pmdp)                        (pmd_val(*(pmdp)) = 0UL)
+#define pmd_page_kernel(pmd)           ((unsigned long) __va(pmd_val(pmd) & 
_PFN_MASK))
+#define pmd_page(pmd)                  virt_to_page((pmd_val(pmd) + 
PAGE_OFFSET))
+
+#define pud_none(pud)                  (!pud_val(pud))
+#define pud_bad(pud)                   (!ia64_phys_addr_valid(pud_val(pud)))
+#define pud_present(pud)               (pud_val(pud) != 0UL)
+#define pud_clear(pudp)                        (pud_val(*(pudp)) = 0UL)
+
+#define pud_page(pud)                  ((unsigned long) __va(pud_val(pud) & 
_PFN_MASK))
+
+/*
+ * The following have defined behavior only work if pte_present() is true.
+ */
+#define pte_user(pte)          ((pte_val(pte) & _PAGE_PL_MASK) == _PAGE_PL_3)
+#define pte_read(pte)          (((pte_val(pte) & _PAGE_AR_MASK) >> 
_PAGE_AR_SHIFT) < 6)
+#define pte_write(pte) ((unsigned) (((pte_val(pte) & _PAGE_AR_MASK) >> 
_PAGE_AR_SHIFT) - 2) <= 4)
+#define pte_exec(pte)          ((pte_val(pte) & _PAGE_AR_RX) != 0)
+#define pte_dirty(pte)         ((pte_val(pte) & _PAGE_D) != 0)
+#define pte_young(pte)         ((pte_val(pte) & _PAGE_A) != 0)
+#define pte_file(pte)          ((pte_val(pte) & _PAGE_FILE) != 0)
+/*
+ * Note: we convert AR_RWX to AR_RX and AR_RW to AR_R by clearing the 2nd bit 
in the
+ * access rights:
+ */
+#define pte_wrprotect(pte)     (__pte(pte_val(pte) & ~_PAGE_AR_RW))
+#define pte_mkwrite(pte)       (__pte(pte_val(pte) | _PAGE_AR_RW))
+#define pte_mkexec(pte)                (__pte(pte_val(pte) | _PAGE_AR_RX))
+#define pte_mkold(pte)         (__pte(pte_val(pte) & ~_PAGE_A))
+#define pte_mkyoung(pte)       (__pte(pte_val(pte) | _PAGE_A))
+#define pte_mkclean(pte)       (__pte(pte_val(pte) & ~_PAGE_D))
+#define pte_mkdirty(pte)       (__pte(pte_val(pte) | _PAGE_D))
+
+/*
+ * Macro to a page protection value as "uncacheable".  Note that "protection" 
is really a
+ * misnomer here as the protection value contains the memory attribute bits, 
dirty bits,
+ * and various other bits as well.
+ */
+#define pgprot_noncached(prot)         __pgprot((pgprot_val(prot) & 
~_PAGE_MA_MASK) | _PAGE_MA_UC)
+
+/*
+ * Macro to make mark a page protection value as "write-combining".
+ * Note that "protection" is really a misnomer here as the protection
+ * value contains the memory attribute bits, dirty bits, and various
+ * other bits as well.  Accesses through a write-combining translation
+ * works bypasses the caches, but does allow for consecutive writes to
+ * be combined into single (but larger) write transactions.
+ */
+#define pgprot_writecombine(prot)      __pgprot((pgprot_val(prot) & 
~_PAGE_MA_MASK) | _PAGE_MA_WC)
+
+static inline unsigned long
+pgd_index (unsigned long address)
+{
+       unsigned long region = address >> 61;
+       unsigned long l1index = (address >> PGDIR_SHIFT) & ((PTRS_PER_PGD >> 3) 
- 1);
+
+       return (region << (PAGE_SHIFT - 6)) | l1index;
+}
+
+/* The offset in the 1-level directory is given by the 3 region bits
+   (61..63) and the level-1 bits.  */
+static inline pgd_t*
+pgd_offset (struct mm_struct *mm, unsigned long address)
+{
+       return mm->pgd + pgd_index(address);
+}
+
+/* In the kernel's mapped region we completely ignore the region number
+   (since we know it's in region number 5). */
+#define pgd_offset_k(addr) \
+       (init_mm.pgd + (((addr) >> PGDIR_SHIFT) & (PTRS_PER_PGD - 1)))
+
+/* Look up a pgd entry in the gate area.  On IA-64, the gate-area
+   resides in the kernel-mapped segment, hence we use pgd_offset_k()
+   here.  */
+#define pgd_offset_gate(mm, addr)      pgd_offset_k(addr)
+
+/* Find an entry in the second-level page table.. */
+#define pmd_offset(dir,addr) \
+       ((pmd_t *) pud_page(*(dir)) + (((addr) >> PMD_SHIFT) & (PTRS_PER_PMD - 
1)))
+
+/*
+ * Find an entry in the third-level page table.  This looks more complicated 
than it
+ * should be because some platforms place page tables in high memory.
+ */
+#define pte_index(addr)                (((addr) >> PAGE_SHIFT) & (PTRS_PER_PTE 
- 1))
+#define pte_offset_kernel(dir,addr)    ((pte_t *) pmd_page_kernel(*(dir)) + 
pte_index(addr))
+#define pte_offset_map(dir,addr)       pte_offset_kernel(dir, addr)
+#define pte_offset_map_nested(dir,addr)        pte_offset_map(dir, addr)
+#define pte_unmap(pte)                 do { } while (0)
+#define pte_unmap_nested(pte)          do { } while (0)
+
+/* atomic versions of the some PTE manipulations: */
+
+static inline int
+ptep_test_and_clear_young (pte_t *ptep)
+{
+#ifdef CONFIG_SMP
+       if (!pte_young(*ptep))
+               return 0;
+       return test_and_clear_bit(_PAGE_A_BIT, ptep);
+#else
+       pte_t pte = *ptep;
+       if (!pte_young(pte))
+               return 0;
+       set_pte(ptep, pte_mkold(pte));
+       return 1;
+#endif
+}
+
+static inline int
+ptep_test_and_clear_dirty (pte_t *ptep)
+{
+#ifdef CONFIG_SMP
+       if (!pte_dirty(*ptep))
+               return 0;
+       return test_and_clear_bit(_PAGE_D_BIT, ptep);
+#else
+       pte_t pte = *ptep;
+       if (!pte_dirty(pte))
+               return 0;
+       set_pte(ptep, pte_mkclean(pte));
+       return 1;
+#endif
+}
+
+static inline pte_t
+ptep_get_and_clear (pte_t *ptep)
+{
+#ifdef CONFIG_SMP
+       return __pte(xchg((long *) ptep, 0));
+#else
+       pte_t pte = *ptep;
+       pte_clear(ptep);
+       return pte;
+#endif
+}
+
+static inline void
+ptep_set_wrprotect (pte_t *ptep)
+{
+#ifdef CONFIG_SMP
+       unsigned long new, old;
+
+       do {
+               old = pte_val(*ptep);
+               new = pte_val(pte_wrprotect(__pte (old)));
+       } while (cmpxchg((unsigned long *) ptep, old, new) != old);
+#else
+       pte_t old_pte = *ptep;
+       set_pte(ptep, pte_wrprotect(old_pte));
+#endif
+}
+
+static inline void
+ptep_mkdirty (pte_t *ptep)
+{
+#ifdef CONFIG_SMP
+       set_bit(_PAGE_D_BIT, ptep);
+#else
+       pte_t old_pte = *ptep;
+       set_pte(ptep, pte_mkdirty(old_pte));
+#endif
+}
+
+static inline int
+pte_same (pte_t a, pte_t b)
+{
+       return pte_val(a) == pte_val(b);
+}
+
+extern pgd_t swapper_pg_dir[PTRS_PER_PGD];
+extern void paging_init (void);
+
+/*
+ * Note: The macros below rely on the fact that MAX_SWAPFILES_SHIFT <= number 
of
+ *      bits in the swap-type field of the swap pte.  It would be nice to
+ *      enforce that, but we can't easily include <linux/swap.h> here.
+ *      (Of course, better still would be to define MAX_SWAPFILES_SHIFT 
here...).
+ *
+ * Format of swap pte:
+ *     bit   0   : present bit (must be zero)
+ *     bit   1   : _PAGE_FILE (must be zero)
+ *     bits  2- 8: swap-type
+ *     bits  9-62: swap offset
+ *     bit  63   : _PAGE_PROTNONE bit
+ *
+ * Format of file pte:
+ *     bit   0   : present bit (must be zero)
+ *     bit   1   : _PAGE_FILE (must be one)
+ *     bits  2-62: file_offset/PAGE_SIZE
+ *     bit  63   : _PAGE_PROTNONE bit
+ */
+#define __swp_type(entry)              (((entry).val >> 2) & 0x7f)
+#define __swp_offset(entry)            (((entry).val << 1) >> 10)
+#define __swp_entry(type,offset)       ((swp_entry_t) { ((type) << 2) | 
((long) (offset) << 9) })
+#define __pte_to_swp_entry(pte)                ((swp_entry_t) { pte_val(pte) })
+#define __swp_entry_to_pte(x)          ((pte_t) { (x).val })
+
+#define PTE_FILE_MAX_BITS              61
+#define pte_to_pgoff(pte)              ((pte_val(pte) << 1) >> 3)
+#define pgoff_to_pte(off)              ((pte_t) { ((off) << 2) | _PAGE_FILE })
+
+/* XXX is this right? */
+#define io_remap_page_range(vma, vaddr, paddr, size, prot)             \
+               remap_pfn_range(vma, vaddr, (paddr) >> PAGE_SHIFT, size, prot)
+
+/*
+ * ZERO_PAGE is a global shared page that is always zero: used
+ * for zero-mapped memory areas etc..
+ */
+extern unsigned long empty_zero_page[PAGE_SIZE/sizeof(unsigned long)];
+extern struct page *zero_page_memmap_ptr;
+#define ZERO_PAGE(vaddr) (zero_page_memmap_ptr)
+
+/* We provide our own get_unmapped_area to cope with VA holes for userland */
+#define HAVE_ARCH_UNMAPPED_AREA
+
+#ifdef CONFIG_HUGETLB_PAGE
+#define HUGETLB_PGDIR_SHIFT    (HPAGE_SHIFT + 2*(PAGE_SHIFT-3))
+#define HUGETLB_PGDIR_SIZE     (__IA64_UL(1) << HUGETLB_PGDIR_SHIFT)
+#define HUGETLB_PGDIR_MASK     (~(HUGETLB_PGDIR_SIZE-1))
+struct mmu_gather;
+extern void hugetlb_free_pgtables(struct mmu_gather *tlb,
+       struct vm_area_struct * prev, unsigned long start, unsigned long end);
+#endif
+
+/*
+ * IA-64 doesn't have any external MMU info: the page tables contain all the 
necessary
+ * information.  However, we use this routine to take care of any (delayed) 
i-cache
+ * flushing that may be necessary.
+ */
+extern void update_mmu_cache (struct vm_area_struct *vma, unsigned long vaddr, 
pte_t pte);
+
+#define __HAVE_ARCH_PTEP_SET_ACCESS_FLAGS
+/*
+ * Update PTEP with ENTRY, which is guaranteed to be a less
+ * restrictive PTE.  That is, ENTRY may have the ACCESSED, DIRTY, and
+ * WRITABLE bits turned on, when the value at PTEP did not.  The
+ * WRITABLE bit may only be turned if SAFELY_WRITABLE is TRUE.
+ *
+ * SAFELY_WRITABLE is TRUE if we can update the value at PTEP without
+ * having to worry about races.  On SMP machines, there are only two
+ * cases where this is true:
+ *
+ *     (1) *PTEP has the PRESENT bit turned OFF
+ *     (2) ENTRY has the DIRTY bit turned ON
+ *
+ * On ia64, we could implement this routine with a cmpxchg()-loop
+ * which ORs in the _PAGE_A/_PAGE_D bit if they're set in ENTRY.
+ * However, like on x86, we can get a more streamlined version by
+ * observing that it is OK to drop ACCESSED bit updates when
+ * SAFELY_WRITABLE is FALSE.  Besides being rare, all that would do is
+ * result in an extra Access-bit fault, which would then turn on the
+ * ACCESSED bit in the low-level fault handler (iaccess_bit or
+ * daccess_bit in ivt.S).
+ */
+#ifdef CONFIG_SMP
+# define ptep_set_access_flags(__vma, __addr, __ptep, __entry, 
__safely_writable)      \
+do {                                                                           
        \
+       if (__safely_writable) {                                                
        \
+               set_pte(__ptep, __entry);                                       
        \
+               flush_tlb_page(__vma, __addr);                                  
        \
+       }                                                                       
        \
+} while (0)
+#else
+# define ptep_set_access_flags(__vma, __addr, __ptep, __entry, 
__safely_writable)      \
+       ptep_establish(__vma, __addr, __ptep, __entry)
+#endif
+
+#  ifdef CONFIG_VIRTUAL_MEM_MAP
+  /* arch mem_map init routine is needed due to holes in a virtual mem_map */
+#   define __HAVE_ARCH_MEMMAP_INIT
+    extern void memmap_init (unsigned long size, int nid, unsigned long zone,
+                            unsigned long start_pfn);
+#  endif /* CONFIG_VIRTUAL_MEM_MAP */
+# endif /* !__ASSEMBLY__ */
+
+/*
+ * Identity-mapped regions use a large page size.  We'll call such large pages
+ * "granules".  If you can think of a better name that's unambiguous, let me
+ * know...
+ */
+#if defined(CONFIG_IA64_GRANULE_64MB)
+# define IA64_GRANULE_SHIFT    _PAGE_SIZE_64M
+#elif defined(CONFIG_IA64_GRANULE_16MB)
+# define IA64_GRANULE_SHIFT    _PAGE_SIZE_16M
+#endif
+#define IA64_GRANULE_SIZE      (1 << IA64_GRANULE_SHIFT)
+/*
+ * log2() of the page size we use to map the kernel image (IA64_TR_KERNEL):
+ */
+#define KERNEL_TR_PAGE_SHIFT   _PAGE_SIZE_64M
+#define KERNEL_TR_PAGE_SIZE    (1 << KERNEL_TR_PAGE_SHIFT)
+
+/*
+ * No page table caches to initialise
+ */
+#define pgtable_cache_init()   do { } while (0)
+
+/* These tell get_user_pages() that the first gate page is accessible from 
user-level.  */
+#define FIXADDR_USER_START     GATE_ADDR
+#define FIXADDR_USER_END       (GATE_ADDR + 2*PERCPU_PAGE_SIZE)
+
+#define __HAVE_ARCH_PTEP_TEST_AND_CLEAR_YOUNG
+#define __HAVE_ARCH_PTEP_TEST_AND_CLEAR_DIRTY
+#define __HAVE_ARCH_PTEP_GET_AND_CLEAR
+#define __HAVE_ARCH_PTEP_SET_WRPROTECT
+#define __HAVE_ARCH_PTEP_MKDIRTY
+#define __HAVE_ARCH_PTE_SAME
+#define __HAVE_ARCH_PGD_OFFSET_GATE
+#include <asm-generic/pgtable.h>
+#include <asm-generic/pgtable-nopud.h>
+
+#endif /* _ASM_IA64_PGTABLE_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm/ptrace_offsets.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/ptrace_offsets.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,268 @@
+#ifndef _ASM_IA64_PTRACE_OFFSETS_H
+#define _ASM_IA64_PTRACE_OFFSETS_H
+
+/*
+ * Copyright (C) 1999, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+/*
+ * The "uarea" that can be accessed via PEEKUSER and POKEUSER is a
+ * virtual structure that would have the following definition:
+ *
+ *     struct uarea {
+ *             struct ia64_fpreg fph[96];              // f32-f127
+ *             unsigned long nat_bits;
+ *             unsigned long empty1;
+ *             struct ia64_fpreg f2;                   // f2-f5
+ *                     :
+ *             struct ia64_fpreg f5;
+ *             struct ia64_fpreg f10;                  // f10-f31
+ *                     :
+ *             struct ia64_fpreg f31;
+ *             unsigned long r4;                       // r4-r7
+ *                     :
+ *             unsigned long r7;
+ *             unsigned long b1;                       // b1-b5
+ *                     :
+ *             unsigned long b5;
+ *             unsigned long ar_ec;
+ *             unsigned long ar_lc;
+ *             unsigned long empty2[5];
+ *             unsigned long cr_ipsr;
+ *             unsigned long cr_iip;
+ *             unsigned long cfm;
+ *             unsigned long ar_unat;
+ *             unsigned long ar_pfs;
+ *             unsigned long ar_rsc;
+ *             unsigned long ar_rnat;
+ *             unsigned long ar_bspstore;
+ *             unsigned long pr;
+ *             unsigned long b6;
+ *             unsigned long ar_bsp;
+ *             unsigned long r1;
+ *             unsigned long r2;
+ *             unsigned long r3;
+ *             unsigned long r12;
+ *             unsigned long r13;
+ *             unsigned long r14;
+ *             unsigned long r15;
+ *             unsigned long r8;
+ *             unsigned long r9;
+ *             unsigned long r10;
+ *             unsigned long r11;
+ *             unsigned long r16;
+ *                     :
+ *             unsigned long r31;
+ *             unsigned long ar_ccv;
+ *             unsigned long ar_fpsr;
+ *             unsigned long b0;
+ *             unsigned long b7;
+ *             unsigned long f6;
+ *             unsigned long f7;
+ *             unsigned long f8;
+ *             unsigned long f9;
+ *             unsigned long ar_csd;
+ *             unsigned long ar_ssd;
+ *             unsigned long rsvd1[710];
+ *             unsigned long dbr[8];
+ *             unsigned long rsvd2[504];
+ *             unsigned long ibr[8];
+ *             unsigned long rsvd3[504];
+ *             unsigned long pmd[4];
+ *     }
+ */
+
+/* fph: */
+#define PT_F32                 0x0000
+#define PT_F33                 0x0010
+#define PT_F34                 0x0020
+#define PT_F35                 0x0030
+#define PT_F36                 0x0040
+#define PT_F37                 0x0050
+#define PT_F38                 0x0060
+#define PT_F39                 0x0070
+#define PT_F40                 0x0080
+#define PT_F41                 0x0090
+#define PT_F42                 0x00a0
+#define PT_F43                 0x00b0
+#define PT_F44                 0x00c0
+#define PT_F45                 0x00d0
+#define PT_F46                 0x00e0
+#define PT_F47                 0x00f0
+#define PT_F48                 0x0100
+#define PT_F49                 0x0110
+#define PT_F50                 0x0120
+#define PT_F51                 0x0130
+#define PT_F52                 0x0140
+#define PT_F53                 0x0150
+#define PT_F54                 0x0160
+#define PT_F55                 0x0170
+#define PT_F56                 0x0180
+#define PT_F57                 0x0190
+#define PT_F58                 0x01a0
+#define PT_F59                 0x01b0
+#define PT_F60                 0x01c0
+#define PT_F61                 0x01d0
+#define PT_F62                 0x01e0
+#define PT_F63                 0x01f0
+#define PT_F64                 0x0200
+#define PT_F65                 0x0210
+#define PT_F66                 0x0220
+#define PT_F67                 0x0230
+#define PT_F68                 0x0240
+#define PT_F69                 0x0250
+#define PT_F70                 0x0260
+#define PT_F71                 0x0270
+#define PT_F72                 0x0280
+#define PT_F73                 0x0290
+#define PT_F74                 0x02a0
+#define PT_F75                 0x02b0
+#define PT_F76                 0x02c0
+#define PT_F77                 0x02d0
+#define PT_F78                 0x02e0
+#define PT_F79                 0x02f0
+#define PT_F80                 0x0300
+#define PT_F81                 0x0310
+#define PT_F82                 0x0320
+#define PT_F83                 0x0330
+#define PT_F84                 0x0340
+#define PT_F85                 0x0350
+#define PT_F86                 0x0360
+#define PT_F87                 0x0370
+#define PT_F88                 0x0380
+#define PT_F89                 0x0390
+#define PT_F90                 0x03a0
+#define PT_F91                 0x03b0
+#define PT_F92                 0x03c0
+#define PT_F93                 0x03d0
+#define PT_F94                 0x03e0
+#define PT_F95                 0x03f0
+#define PT_F96                 0x0400
+#define PT_F97                 0x0410
+#define PT_F98                 0x0420
+#define PT_F99                 0x0430
+#define PT_F100                        0x0440
+#define PT_F101                        0x0450
+#define PT_F102                        0x0460
+#define PT_F103                        0x0470
+#define PT_F104                        0x0480
+#define PT_F105                        0x0490
+#define PT_F106                        0x04a0
+#define PT_F107                        0x04b0
+#define PT_F108                        0x04c0
+#define PT_F109                        0x04d0
+#define PT_F110                        0x04e0
+#define PT_F111                        0x04f0
+#define PT_F112                        0x0500
+#define PT_F113                        0x0510
+#define PT_F114                        0x0520
+#define PT_F115                        0x0530
+#define PT_F116                        0x0540
+#define PT_F117                        0x0550
+#define PT_F118                        0x0560
+#define PT_F119                        0x0570
+#define PT_F120                        0x0580
+#define PT_F121                        0x0590
+#define PT_F122                        0x05a0
+#define PT_F123                        0x05b0
+#define PT_F124                        0x05c0
+#define PT_F125                        0x05d0
+#define PT_F126                        0x05e0
+#define PT_F127                        0x05f0
+
+#define PT_NAT_BITS            0x0600
+
+#define PT_F2                  0x0610
+#define PT_F3                  0x0620
+#define PT_F4                  0x0630
+#define PT_F5                  0x0640
+#define PT_F10                 0x0650
+#define PT_F11                 0x0660
+#define PT_F12                 0x0670
+#define PT_F13                 0x0680
+#define PT_F14                 0x0690
+#define PT_F15                 0x06a0
+#define PT_F16                 0x06b0
+#define PT_F17                 0x06c0
+#define PT_F18                 0x06d0
+#define PT_F19                 0x06e0
+#define PT_F20                 0x06f0
+#define PT_F21                 0x0700
+#define PT_F22                 0x0710
+#define PT_F23                 0x0720
+#define PT_F24                 0x0730
+#define PT_F25                 0x0740
+#define PT_F26                 0x0750
+#define PT_F27                 0x0760
+#define PT_F28                 0x0770
+#define PT_F29                 0x0780
+#define PT_F30                 0x0790
+#define PT_F31                 0x07a0
+#define PT_R4                  0x07b0
+#define PT_R5                  0x07b8
+#define PT_R6                  0x07c0
+#define PT_R7                  0x07c8
+
+#define PT_B1                  0x07d8
+#define PT_B2                  0x07e0
+#define PT_B3                  0x07e8
+#define PT_B4                  0x07f0
+#define PT_B5                  0x07f8
+
+#define PT_AR_EC               0x0800
+#define PT_AR_LC               0x0808
+
+#define PT_CR_IPSR             0x0830
+#define PT_CR_IIP              0x0838
+#define PT_CFM                 0x0840
+#define PT_AR_UNAT             0x0848
+#define PT_AR_PFS              0x0850
+#define PT_AR_RSC              0x0858
+#define PT_AR_RNAT             0x0860
+#define PT_AR_BSPSTORE         0x0868
+#define PT_PR                  0x0870
+#define PT_B6                  0x0878
+#define PT_AR_BSP              0x0880  /* note: this points to the *end* of 
the backing store! */
+#define PT_R1                  0x0888
+#define PT_R2                  0x0890
+#define PT_R3                  0x0898
+#define PT_R12                 0x08a0
+#define PT_R13                 0x08a8
+#define PT_R14                 0x08b0
+#define PT_R15                 0x08b8
+#define PT_R8                  0x08c0
+#define PT_R9                  0x08c8
+#define PT_R10                 0x08d0
+#define PT_R11                 0x08d8
+#define PT_R16                 0x08e0
+#define PT_R17                 0x08e8
+#define PT_R18                 0x08f0
+#define PT_R19                 0x08f8
+#define PT_R20                 0x0900
+#define PT_R21                 0x0908
+#define PT_R22                 0x0910
+#define PT_R23                 0x0918
+#define PT_R24                 0x0920
+#define PT_R25                 0x0928
+#define PT_R26                 0x0930
+#define PT_R27                 0x0938
+#define PT_R28                 0x0940
+#define PT_R29                 0x0948
+#define PT_R30                 0x0950
+#define PT_R31                 0x0958
+#define PT_AR_CCV              0x0960
+#define PT_AR_FPSR             0x0968
+#define PT_B0                  0x0970
+#define PT_B7                  0x0978
+#define PT_F6                  0x0980
+#define PT_F7                  0x0990
+#define PT_F8                  0x09a0
+#define PT_F9                  0x09b0
+#define PT_AR_CSD              0x09c0
+#define PT_AR_SSD              0x09c8
+
+#define PT_DBR                 0x2000  /* data breakpoint registers */
+#define PT_IBR                 0x3000  /* instruction breakpoint registers */
+#define PT_PMD                 0x4000  /* performance monitoring counters */
+
+#endif /* _ASM_IA64_PTRACE_OFFSETS_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/rse.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/rse.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,66 @@
+#ifndef _ASM_IA64_RSE_H
+#define _ASM_IA64_RSE_H
+
+/*
+ * Copyright (C) 1998, 1999 Hewlett-Packard Co
+ * Copyright (C) 1998, 1999 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * Register stack engine related helper functions.  This file may be
+ * used in applications, so be careful about the name-space and give
+ * some consideration to non-GNU C compilers (though __inline__ is
+ * fine).
+ */
+
+static __inline__ unsigned long
+ia64_rse_slot_num (unsigned long *addr)
+{
+       return (((unsigned long) addr) >> 3) & 0x3f;
+}
+
+/*
+ * Return TRUE if ADDR is the address of an RNAT slot.
+ */
+static __inline__ unsigned long
+ia64_rse_is_rnat_slot (unsigned long *addr)
+{
+       return ia64_rse_slot_num(addr) == 0x3f;
+}
+
+/*
+ * Returns the address of the RNAT slot that covers the slot at
+ * address SLOT_ADDR.
+ */
+static __inline__ unsigned long *
+ia64_rse_rnat_addr (unsigned long *slot_addr)
+{
+       return (unsigned long *) ((unsigned long) slot_addr | (0x3f << 3));
+}
+
+/*
+ * Calculate the number of registers in the dirty partition starting at 
BSPSTORE and
+ * ending at BSP.  This isn't simply (BSP-BSPSTORE)/8 because every 64th slot 
stores
+ * ar.rnat.
+ */
+static __inline__ unsigned long
+ia64_rse_num_regs (unsigned long *bspstore, unsigned long *bsp)
+{
+       unsigned long slots = (bsp - bspstore);
+
+       return slots - (ia64_rse_slot_num(bspstore) + slots)/0x40;
+}
+
+/*
+ * The inverse of the above: given bspstore and the number of
+ * registers, calculate ar.bsp.
+ */
+static __inline__ unsigned long *
+ia64_rse_skip_regs (unsigned long *addr, long num_regs)
+{
+       long delta = ia64_rse_slot_num(addr) + num_regs;
+
+       if (num_regs < 0)
+               delta -= 0x3e;
+       return addr + num_regs + delta/0x3f;
+}
+
+#endif /* _ASM_IA64_RSE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/rwsem.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/rwsem.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,188 @@
+/*
+ * asm-ia64/rwsem.h: R/W semaphores for ia64
+ *
+ * Copyright (C) 2003 Ken Chen <kenneth.w.chen@xxxxxxxxx>
+ * Copyright (C) 2003 Asit Mallick <asit.k.mallick@xxxxxxxxx>
+ *
+ * Based on asm-i386/rwsem.h and other architecture implementation.
+ *
+ * The MSW of the count is the negated number of active writers and
+ * waiting lockers, and the LSW is the total number of active locks.
+ *
+ * The lock count is initialized to 0 (no active and no waiting lockers).
+ *
+ * When a writer subtracts WRITE_BIAS, it'll get 0xffff0001 for the case
+ * of an uncontended lock. Readers increment by 1 and see a positive value
+ * when uncontended, negative if there are writers (and maybe) readers
+ * waiting (in which case it goes to sleep).
+ */
+
+#ifndef _ASM_IA64_RWSEM_H
+#define _ASM_IA64_RWSEM_H
+
+#include <linux/list.h>
+#include <linux/spinlock.h>
+
+#include <asm/intrinsics.h>
+
+/*
+ * the semaphore definition
+ */
+struct rw_semaphore {
+       signed int              count;
+       spinlock_t              wait_lock;
+       struct list_head        wait_list;
+#if RWSEM_DEBUG
+       int                     debug;
+#endif
+};
+
+#define RWSEM_UNLOCKED_VALUE           0x00000000
+#define RWSEM_ACTIVE_BIAS              0x00000001
+#define RWSEM_ACTIVE_MASK              0x0000ffff
+#define RWSEM_WAITING_BIAS             (-0x00010000)
+#define RWSEM_ACTIVE_READ_BIAS         RWSEM_ACTIVE_BIAS
+#define RWSEM_ACTIVE_WRITE_BIAS                (RWSEM_WAITING_BIAS + 
RWSEM_ACTIVE_BIAS)
+
+/*
+ * initialization
+ */
+#if RWSEM_DEBUG
+#define __RWSEM_DEBUG_INIT      , 0
+#else
+#define __RWSEM_DEBUG_INIT     /* */
+#endif
+
+#define __RWSEM_INITIALIZER(name) \
+       { RWSEM_UNLOCKED_VALUE, SPIN_LOCK_UNLOCKED, \
+         LIST_HEAD_INIT((name).wait_list) \
+         __RWSEM_DEBUG_INIT }
+
+#define DECLARE_RWSEM(name) \
+       struct rw_semaphore name = __RWSEM_INITIALIZER(name)
+
+extern struct rw_semaphore *rwsem_down_read_failed(struct rw_semaphore *sem);
+extern struct rw_semaphore *rwsem_down_write_failed(struct rw_semaphore *sem);
+extern struct rw_semaphore *rwsem_wake(struct rw_semaphore *sem);
+extern struct rw_semaphore *rwsem_downgrade_wake(struct rw_semaphore *sem);
+
+static inline void
+init_rwsem (struct rw_semaphore *sem)
+{
+       sem->count = RWSEM_UNLOCKED_VALUE;
+       spin_lock_init(&sem->wait_lock);
+       INIT_LIST_HEAD(&sem->wait_list);
+#if RWSEM_DEBUG
+       sem->debug = 0;
+#endif
+}
+
+/*
+ * lock for reading
+ */
+static inline void
+__down_read (struct rw_semaphore *sem)
+{
+       int result = ia64_fetchadd4_acq((unsigned int *)&sem->count, 1);
+
+       if (result < 0)
+               rwsem_down_read_failed(sem);
+}
+
+/*
+ * lock for writing
+ */
+static inline void
+__down_write (struct rw_semaphore *sem)
+{
+       int old, new;
+
+       do {
+               old = sem->count;
+               new = old + RWSEM_ACTIVE_WRITE_BIAS;
+       } while (cmpxchg_acq(&sem->count, old, new) != old);
+
+       if (old != 0)
+               rwsem_down_write_failed(sem);
+}
+
+/*
+ * unlock after reading
+ */
+static inline void
+__up_read (struct rw_semaphore *sem)
+{
+       int result = ia64_fetchadd4_rel((unsigned int *)&sem->count, -1);
+
+       if (result < 0 && (--result & RWSEM_ACTIVE_MASK) == 0)
+               rwsem_wake(sem);
+}
+
+/*
+ * unlock after writing
+ */
+static inline void
+__up_write (struct rw_semaphore *sem)
+{
+       int old, new;
+
+       do {
+               old = sem->count;
+               new = old - RWSEM_ACTIVE_WRITE_BIAS;
+       } while (cmpxchg_rel(&sem->count, old, new) != old);
+
+       if (new < 0 && (new & RWSEM_ACTIVE_MASK) == 0)
+               rwsem_wake(sem);
+}
+
+/*
+ * trylock for reading -- returns 1 if successful, 0 if contention
+ */
+static inline int
+__down_read_trylock (struct rw_semaphore *sem)
+{
+       int tmp;
+       while ((tmp = sem->count) >= 0) {
+               if (tmp == cmpxchg_acq(&sem->count, tmp, tmp+1)) {
+                       return 1;
+               }
+       }
+       return 0;
+}
+
+/*
+ * trylock for writing -- returns 1 if successful, 0 if contention
+ */
+static inline int
+__down_write_trylock (struct rw_semaphore *sem)
+{
+       int tmp = cmpxchg_acq(&sem->count, RWSEM_UNLOCKED_VALUE,
+                             RWSEM_ACTIVE_WRITE_BIAS);
+       return tmp == RWSEM_UNLOCKED_VALUE;
+}
+
+/*
+ * downgrade write lock to read lock
+ */
+static inline void
+__downgrade_write (struct rw_semaphore *sem)
+{
+       int old, new;
+
+       do {
+               old = sem->count;
+               new = old - RWSEM_WAITING_BIAS;
+       } while (cmpxchg_rel(&sem->count, old, new) != old);
+
+       if (old < 0)
+               rwsem_downgrade_wake(sem);
+}
+
+/*
+ * Implement atomic add functionality.  These used to be "inline" functions, 
but GCC v3.1
+ * doesn't quite optimize this stuff right and ends up with bad calls to 
fetchandadd.
+ */
+#define rwsem_atomic_add(delta, sem)   atomic_add(delta, (atomic_t 
*)(&(sem)->count))
+#define rwsem_atomic_update(delta, sem)        atomic_add_return(delta, 
(atomic_t *)(&(sem)->count))
+
+#endif /* _ASM_IA64_RWSEM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/sal.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/sal.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,840 @@
+#ifndef _ASM_IA64_SAL_H
+#define _ASM_IA64_SAL_H
+
+/*
+ * System Abstraction Layer definitions.
+ *
+ * This is based on version 2.5 of the manual "IA-64 System
+ * Abstraction Layer".
+ *
+ * Copyright (C) 2001 Intel
+ * Copyright (C) 2002 Jenna Hall <jenna.s.hall@xxxxxxxxx>
+ * Copyright (C) 2001 Fred Lewis <frederick.v.lewis@xxxxxxxxx>
+ * Copyright (C) 1998, 1999, 2001, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Srinivasa Prasad Thirumalachar 
<sprasad@xxxxxxxxxxxxxxxxxxxx>
+ *
+ * 02/01/04 J. Hall Updated Error Record Structures to conform to July 2001
+ *                 revision of the SAL spec.
+ * 01/01/03 fvlewis Updated Error Record Structures to conform with Nov. 2000
+ *                  revision of the SAL spec.
+ * 99/09/29 davidm     Updated for SAL 2.6.
+ * 00/03/29 cfleck      Updated SAL Error Logging info for processor (SAL 2.6)
+ *                      (plus examples of platform error info structures from 
smariset @ Intel)
+ */
+
+#define IA64_SAL_PLATFORM_FEATURE_BUS_LOCK_BIT         0
+#define IA64_SAL_PLATFORM_FEATURE_IRQ_REDIR_HINT_BIT   1
+#define IA64_SAL_PLATFORM_FEATURE_IPI_REDIR_HINT_BIT   2
+#define IA64_SAL_PLATFORM_FEATURE_ITC_DRIFT_BIT                3
+
+#define IA64_SAL_PLATFORM_FEATURE_BUS_LOCK       
(1<<IA64_SAL_PLATFORM_FEATURE_BUS_LOCK_BIT)
+#define IA64_SAL_PLATFORM_FEATURE_IRQ_REDIR_HINT 
(1<<IA64_SAL_PLATFORM_FEATURE_IRQ_REDIR_HINT_BIT)
+#define IA64_SAL_PLATFORM_FEATURE_IPI_REDIR_HINT 
(1<<IA64_SAL_PLATFORM_FEATURE_IPI_REDIR_HINT_BIT)
+#define IA64_SAL_PLATFORM_FEATURE_ITC_DRIFT      
(1<<IA64_SAL_PLATFORM_FEATURE_ITC_DRIFT_BIT)
+
+#ifndef __ASSEMBLY__
+
+#include <linux/bcd.h>
+#include <linux/spinlock.h>
+#include <linux/efi.h>
+
+#include <asm/pal.h>
+#include <asm/system.h>
+#include <asm/fpu.h>
+
+extern spinlock_t sal_lock;
+
+/* SAL spec _requires_ eight args for each call. */
+#define __SAL_CALL(result,a0,a1,a2,a3,a4,a5,a6,a7)     \
+       result = (*ia64_sal)(a0,a1,a2,a3,a4,a5,a6,a7)
+
+# define SAL_CALL(result,args...) do {                         \
+       unsigned long __ia64_sc_flags;                          \
+       struct ia64_fpreg __ia64_sc_fr[6];                      \
+       ia64_save_scratch_fpregs(__ia64_sc_fr);                 \
+       spin_lock_irqsave(&sal_lock, __ia64_sc_flags);          \
+       __SAL_CALL(result, args);                               \
+       spin_unlock_irqrestore(&sal_lock, __ia64_sc_flags);     \
+       ia64_load_scratch_fpregs(__ia64_sc_fr);                 \
+} while (0)
+
+# define SAL_CALL_NOLOCK(result,args...) do {          \
+       unsigned long __ia64_scn_flags;                 \
+       struct ia64_fpreg __ia64_scn_fr[6];             \
+       ia64_save_scratch_fpregs(__ia64_scn_fr);        \
+       local_irq_save(__ia64_scn_flags);               \
+       __SAL_CALL(result, args);                       \
+       local_irq_restore(__ia64_scn_flags);            \
+       ia64_load_scratch_fpregs(__ia64_scn_fr);        \
+} while (0)
+
+# define SAL_CALL_REENTRANT(result,args...) do {       \
+       struct ia64_fpreg __ia64_scs_fr[6];             \
+       ia64_save_scratch_fpregs(__ia64_scs_fr);        \
+       preempt_disable();                              \
+       __SAL_CALL(result, args);                       \
+       preempt_enable();                               \
+       ia64_load_scratch_fpregs(__ia64_scs_fr);        \
+} while (0)
+
+#define SAL_SET_VECTORS                        0x01000000
+#define SAL_GET_STATE_INFO             0x01000001
+#define SAL_GET_STATE_INFO_SIZE                0x01000002
+#define SAL_CLEAR_STATE_INFO           0x01000003
+#define SAL_MC_RENDEZ                  0x01000004
+#define SAL_MC_SET_PARAMS              0x01000005
+#define SAL_REGISTER_PHYSICAL_ADDR     0x01000006
+
+#define SAL_CACHE_FLUSH                        0x01000008
+#define SAL_CACHE_INIT                 0x01000009
+#define SAL_PCI_CONFIG_READ            0x01000010
+#define SAL_PCI_CONFIG_WRITE           0x01000011
+#define SAL_FREQ_BASE                  0x01000012
+
+#define SAL_UPDATE_PAL                 0x01000020
+
+struct ia64_sal_retval {
+       /*
+        * A zero status value indicates call completed without error.
+        * A negative status value indicates reason of call failure.
+        * A positive status value indicates success but an
+        * informational value should be printed (e.g., "reboot for
+        * change to take effect").
+        */
+       s64 status;
+       u64 v0;
+       u64 v1;
+       u64 v2;
+};
+
+typedef struct ia64_sal_retval (*ia64_sal_handler) (u64, ...);
+
+enum {
+       SAL_FREQ_BASE_PLATFORM = 0,
+       SAL_FREQ_BASE_INTERVAL_TIMER = 1,
+       SAL_FREQ_BASE_REALTIME_CLOCK = 2
+};
+
+/*
+ * The SAL system table is followed by a variable number of variable
+ * length descriptors.  The structure of these descriptors follows
+ * below.
+ * The defininition follows SAL specs from July 2000
+ */
+struct ia64_sal_systab {
+       u8 signature[4];        /* should be "SST_" */
+       u32 size;               /* size of this table in bytes */
+       u8 sal_rev_minor;
+       u8 sal_rev_major;
+       u16 entry_count;        /* # of entries in variable portion */
+       u8 checksum;
+       u8 reserved1[7];
+       u8 sal_a_rev_minor;
+       u8 sal_a_rev_major;
+       u8 sal_b_rev_minor;
+       u8 sal_b_rev_major;
+       /* oem_id & product_id: terminating NUL is missing if string is exactly 
32 bytes long. */
+       u8 oem_id[32];
+       u8 product_id[32];      /* ASCII product id  */
+       u8 reserved2[8];
+};
+
+enum sal_systab_entry_type {
+       SAL_DESC_ENTRY_POINT = 0,
+       SAL_DESC_MEMORY = 1,
+       SAL_DESC_PLATFORM_FEATURE = 2,
+       SAL_DESC_TR = 3,
+       SAL_DESC_PTC = 4,
+       SAL_DESC_AP_WAKEUP = 5
+};
+
+/*
+ * Entry type: Size:
+ *     0       48
+ *     1       32
+ *     2       16
+ *     3       32
+ *     4       16
+ *     5       16
+ */
+#define SAL_DESC_SIZE(type)    "\060\040\020\040\020\020"[(unsigned) type]
+
+typedef struct ia64_sal_desc_entry_point {
+       u8 type;
+       u8 reserved1[7];
+       u64 pal_proc;
+       u64 sal_proc;
+       u64 gp;
+       u8 reserved2[16];
+}ia64_sal_desc_entry_point_t;
+
+typedef struct ia64_sal_desc_memory {
+       u8 type;
+       u8 used_by_sal; /* needs to be mapped for SAL? */
+       u8 mem_attr;            /* current memory attribute setting */
+       u8 access_rights;       /* access rights set up by SAL */
+       u8 mem_attr_mask;       /* mask of supported memory attributes */
+       u8 reserved1;
+       u8 mem_type;            /* memory type */
+       u8 mem_usage;           /* memory usage */
+       u64 addr;               /* physical address of memory */
+       u32 length;     /* length (multiple of 4KB pages) */
+       u32 reserved2;
+       u8 oem_reserved[8];
+} ia64_sal_desc_memory_t;
+
+typedef struct ia64_sal_desc_platform_feature {
+       u8 type;
+       u8 feature_mask;
+       u8 reserved1[14];
+} ia64_sal_desc_platform_feature_t;
+
+typedef struct ia64_sal_desc_tr {
+       u8 type;
+       u8 tr_type;             /* 0 == instruction, 1 == data */
+       u8 regnum;              /* translation register number */
+       u8 reserved1[5];
+       u64 addr;               /* virtual address of area covered */
+       u64 page_size;          /* encoded page size */
+       u8 reserved2[8];
+} ia64_sal_desc_tr_t;
+
+typedef struct ia64_sal_desc_ptc {
+       u8 type;
+       u8 reserved1[3];
+       u32 num_domains;        /* # of coherence domains */
+       u64 domain_info;        /* physical address of domain info table */
+} ia64_sal_desc_ptc_t;
+
+typedef struct ia64_sal_ptc_domain_info {
+       u64 proc_count;         /* number of processors in domain */
+       u64 proc_list;          /* physical address of LID array */
+} ia64_sal_ptc_domain_info_t;
+
+typedef struct ia64_sal_ptc_domain_proc_entry {
+       u64 id  : 8;            /* id of processor */
+       u64 eid : 8;            /* eid of processor */
+} ia64_sal_ptc_domain_proc_entry_t;
+
+
+#define IA64_SAL_AP_EXTERNAL_INT 0
+
+typedef struct ia64_sal_desc_ap_wakeup {
+       u8 type;
+       u8 mechanism;           /* 0 == external interrupt */
+       u8 reserved1[6];
+       u64 vector;             /* interrupt vector in range 0x10-0xff */
+} ia64_sal_desc_ap_wakeup_t ;
+
+extern ia64_sal_handler ia64_sal;
+extern struct ia64_sal_desc_ptc *ia64_ptc_domain_info;
+
+extern unsigned short sal_revision;    /* supported SAL spec revision */
+extern unsigned short sal_version;     /* SAL version; OEM dependent */
+#define SAL_VERSION_CODE(major, minor) ((BIN2BCD(major) << 8) | BIN2BCD(minor))
+
+extern const char *ia64_sal_strerror (long status);
+extern void ia64_sal_init (struct ia64_sal_systab *sal_systab);
+
+/* SAL information type encodings */
+enum {
+       SAL_INFO_TYPE_MCA  = 0,         /* Machine check abort information */
+        SAL_INFO_TYPE_INIT = 1,                /* Init information */
+        SAL_INFO_TYPE_CMC  = 2,                /* Corrected machine check 
information */
+        SAL_INFO_TYPE_CPE  = 3         /* Corrected platform error information 
*/
+};
+
+/* Encodings for machine check parameter types */
+enum {
+       SAL_MC_PARAM_RENDEZ_INT    = 1, /* Rendezvous interrupt */
+       SAL_MC_PARAM_RENDEZ_WAKEUP = 2, /* Wakeup */
+       SAL_MC_PARAM_CPE_INT       = 3  /* Corrected Platform Error Int */
+};
+
+/* Encodings for rendezvous mechanisms */
+enum {
+       SAL_MC_PARAM_MECHANISM_INT = 1, /* Use interrupt */
+       SAL_MC_PARAM_MECHANISM_MEM = 2  /* Use memory synchronization variable*/
+};
+
+/* Encodings for vectors which can be registered by the OS with SAL */
+enum {
+       SAL_VECTOR_OS_MCA         = 0,
+       SAL_VECTOR_OS_INIT        = 1,
+       SAL_VECTOR_OS_BOOT_RENDEZ = 2
+};
+
+/* Encodings for mca_opt parameter sent to SAL_MC_SET_PARAMS */
+#define        SAL_MC_PARAM_RZ_ALWAYS          0x1
+#define        SAL_MC_PARAM_BINIT_ESCALATE     0x10
+
+/*
+ * Definition of the SAL Error Log from the SAL spec
+ */
+
+/* SAL Error Record Section GUID Definitions */
+#define SAL_PROC_DEV_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf1, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_MEM_DEV_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf2, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_SEL_DEV_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf3, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_PCI_BUS_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf4, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_SMBIOS_DEV_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf5, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_PCI_COMP_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf6, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_SPECIFIC_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf7, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_HOST_CTLR_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf8, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+#define SAL_PLAT_BUS_ERR_SECT_GUID  \
+    EFI_GUID(0xe429faf9, 0x3cb7, 0x11d4, 0xbc, 0xa7, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81)
+
+#define MAX_CACHE_ERRORS       6
+#define MAX_TLB_ERRORS         6
+#define MAX_BUS_ERRORS         1
+
+/* Definition of version  according to SAL spec for logging purposes */
+typedef struct sal_log_revision {
+       u8 minor;               /* BCD (0..99) */
+       u8 major;               /* BCD (0..99) */
+} sal_log_revision_t;
+
+/* Definition of timestamp according to SAL spec for logging purposes */
+typedef struct sal_log_timestamp {
+       u8 slh_second;          /* Second (0..59) */
+       u8 slh_minute;          /* Minute (0..59) */
+       u8 slh_hour;            /* Hour (0..23) */
+       u8 slh_reserved;
+       u8 slh_day;             /* Day (1..31) */
+       u8 slh_month;           /* Month (1..12) */
+       u8 slh_year;            /* Year (00..99) */
+       u8 slh_century;         /* Century (19, 20, 21, ...) */
+} sal_log_timestamp_t;
+
+/* Definition of log record  header structures */
+typedef struct sal_log_record_header {
+       u64 id;                         /* Unique monotonically increasing ID */
+       sal_log_revision_t revision;    /* Major and Minor revision of header */
+       u16 severity;                   /* Error Severity */
+       u32 len;                        /* Length of this error log in bytes */
+       sal_log_timestamp_t timestamp;  /* Timestamp */
+       efi_guid_t platform_guid;       /* Unique OEM Platform ID */
+} sal_log_record_header_t;
+
+#define sal_log_severity_recoverable   0
+#define sal_log_severity_fatal         1
+#define sal_log_severity_corrected     2
+
+/* Definition of log section header structures */
+typedef struct sal_log_sec_header {
+    efi_guid_t guid;                   /* Unique Section ID */
+    sal_log_revision_t revision;       /* Major and Minor revision of Section 
*/
+    u16 reserved;
+    u32 len;                           /* Section length */
+} sal_log_section_hdr_t;
+
+typedef struct sal_log_mod_error_info {
+       struct {
+               u64 check_info              : 1,
+                   requestor_identifier    : 1,
+                   responder_identifier    : 1,
+                   target_identifier       : 1,
+                   precise_ip              : 1,
+                   reserved                : 59;
+       } valid;
+       u64 check_info;
+       u64 requestor_identifier;
+       u64 responder_identifier;
+       u64 target_identifier;
+       u64 precise_ip;
+} sal_log_mod_error_info_t;
+
+typedef struct sal_processor_static_info {
+       struct {
+               u64 minstate        : 1,
+                   br              : 1,
+                   cr              : 1,
+                   ar              : 1,
+                   rr              : 1,
+                   fr              : 1,
+                   reserved        : 58;
+       } valid;
+       pal_min_state_area_t min_state_area;
+       u64 br[8];
+       u64 cr[128];
+       u64 ar[128];
+       u64 rr[8];
+       struct ia64_fpreg __attribute__ ((packed)) fr[128];
+} sal_processor_static_info_t;
+
+struct sal_cpuid_info {
+       u64 regs[5];
+       u64 reserved;
+};
+
+typedef struct sal_log_processor_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 proc_error_map      : 1,
+                   proc_state_param    : 1,
+                   proc_cr_lid         : 1,
+                   psi_static_struct   : 1,
+                   num_cache_check     : 4,
+                   num_tlb_check       : 4,
+                   num_bus_check       : 4,
+                   num_reg_file_check  : 4,
+                   num_ms_check        : 4,
+                   cpuid_info          : 1,
+                   reserved1           : 39;
+       } valid;
+       u64 proc_error_map;
+       u64 proc_state_parameter;
+       u64 proc_cr_lid;
+       /*
+        * The rest of this structure consists of variable-length arrays, which 
can't be
+        * expressed in C.
+        */
+       sal_log_mod_error_info_t info[0];
+       /*
+        * This is what the rest looked like if C supported variable-length 
arrays:
+        *
+        * sal_log_mod_error_info_t cache_check_info[.valid.num_cache_check];
+        * sal_log_mod_error_info_t tlb_check_info[.valid.num_tlb_check];
+        * sal_log_mod_error_info_t bus_check_info[.valid.num_bus_check];
+        * sal_log_mod_error_info_t 
reg_file_check_info[.valid.num_reg_file_check];
+        * sal_log_mod_error_info_t ms_check_info[.valid.num_ms_check];
+        * struct sal_cpuid_info cpuid_info;
+        * sal_processor_static_info_t processor_static_info;
+        */
+} sal_log_processor_info_t;
+
+/* Given a sal_log_processor_info_t pointer, return a pointer to the 
processor_static_info: */
+#define SAL_LPI_PSI_INFO(l)                                                    
                \
+({     sal_log_processor_info_t *_l = (l);                                     
                \
+       ((sal_processor_static_info_t *)                                        
                \
+        ((char *) _l->info + ((_l->valid.num_cache_check + 
_l->valid.num_tlb_check             \
+                               + _l->valid.num_bus_check + 
_l->valid.num_reg_file_check        \
+                               + _l->valid.num_ms_check) * 
sizeof(sal_log_mod_error_info_t)    \
+                              + sizeof(struct sal_cpuid_info))));              
                \
+})
+
+/* platform error log structures */
+
+typedef struct sal_log_mem_dev_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 error_status    : 1,
+                   physical_addr   : 1,
+                   addr_mask       : 1,
+                   node            : 1,
+                   card            : 1,
+                   module          : 1,
+                   bank            : 1,
+                   device          : 1,
+                   row             : 1,
+                   column          : 1,
+                   bit_position    : 1,
+                   requestor_id    : 1,
+                   responder_id    : 1,
+                   target_id       : 1,
+                   bus_spec_data   : 1,
+                   oem_id          : 1,
+                   oem_data        : 1,
+                   reserved        : 47;
+       } valid;
+       u64 error_status;
+       u64 physical_addr;
+       u64 addr_mask;
+       u16 node;
+       u16 card;
+       u16 module;
+       u16 bank;
+       u16 device;
+       u16 row;
+       u16 column;
+       u16 bit_position;
+       u64 requestor_id;
+       u64 responder_id;
+       u64 target_id;
+       u64 bus_spec_data;
+       u8 oem_id[16];
+       u8 oem_data[1];                 /* Variable length data */
+} sal_log_mem_dev_err_info_t;
+
+typedef struct sal_log_sel_dev_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 record_id       : 1,
+                   record_type     : 1,
+                   generator_id    : 1,
+                   evm_rev         : 1,
+                   sensor_type     : 1,
+                   sensor_num      : 1,
+                   event_dir       : 1,
+                   event_data1     : 1,
+                   event_data2     : 1,
+                   event_data3     : 1,
+                   reserved        : 54;
+       } valid;
+       u16 record_id;
+       u8 record_type;
+       u8 timestamp[4];
+       u16 generator_id;
+       u8 evm_rev;
+       u8 sensor_type;
+       u8 sensor_num;
+       u8 event_dir;
+       u8 event_data1;
+       u8 event_data2;
+       u8 event_data3;
+} sal_log_sel_dev_err_info_t;
+
+typedef struct sal_log_pci_bus_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 err_status      : 1,
+                   err_type        : 1,
+                   bus_id          : 1,
+                   bus_address     : 1,
+                   bus_data        : 1,
+                   bus_cmd         : 1,
+                   requestor_id    : 1,
+                   responder_id    : 1,
+                   target_id       : 1,
+                   oem_data        : 1,
+                   reserved        : 54;
+       } valid;
+       u64 err_status;
+       u16 err_type;
+       u16 bus_id;
+       u32 reserved;
+       u64 bus_address;
+       u64 bus_data;
+       u64 bus_cmd;
+       u64 requestor_id;
+       u64 responder_id;
+       u64 target_id;
+       u8 oem_data[1];                 /* Variable length data */
+} sal_log_pci_bus_err_info_t;
+
+typedef struct sal_log_smbios_dev_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 event_type      : 1,
+                   length          : 1,
+                   time_stamp      : 1,
+                   data            : 1,
+                   reserved1       : 60;
+       } valid;
+       u8 event_type;
+       u8 length;
+       u8 time_stamp[6];
+       u8 data[1];                     /* data of variable length, length == 
slsmb_length */
+} sal_log_smbios_dev_err_info_t;
+
+typedef struct sal_log_pci_comp_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 err_status      : 1,
+                   comp_info       : 1,
+                   num_mem_regs    : 1,
+                   num_io_regs     : 1,
+                   reg_data_pairs  : 1,
+                   oem_data        : 1,
+                   reserved        : 58;
+       } valid;
+       u64 err_status;
+       struct {
+               u16 vendor_id;
+               u16 device_id;
+               u8 class_code[3];
+               u8 func_num;
+               u8 dev_num;
+               u8 bus_num;
+               u8 seg_num;
+               u8 reserved[5];
+       } comp_info;
+       u32 num_mem_regs;
+       u32 num_io_regs;
+       u64 reg_data_pairs[1];
+       /*
+        * array of address/data register pairs is num_mem_regs + num_io_regs 
elements
+        * long.  Each array element consists of a u64 address followed by a 
u64 data
+        * value.  The oem_data array immediately follows the reg_data_pairs 
array
+        */
+       u8 oem_data[1];                 /* Variable length data */
+} sal_log_pci_comp_err_info_t;
+
+typedef struct sal_log_plat_specific_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 err_status      : 1,
+                   guid            : 1,
+                   oem_data        : 1,
+                   reserved        : 61;
+       } valid;
+       u64 err_status;
+       efi_guid_t guid;
+       u8 oem_data[1];                 /* platform specific variable length 
data */
+} sal_log_plat_specific_err_info_t;
+
+typedef struct sal_log_host_ctlr_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 err_status      : 1,
+                   requestor_id    : 1,
+                   responder_id    : 1,
+                   target_id       : 1,
+                   bus_spec_data   : 1,
+                   oem_data        : 1,
+                   reserved        : 58;
+       } valid;
+       u64 err_status;
+       u64 requestor_id;
+       u64 responder_id;
+       u64 target_id;
+       u64 bus_spec_data;
+       u8 oem_data[1];                 /* Variable length OEM data */
+} sal_log_host_ctlr_err_info_t;
+
+typedef struct sal_log_plat_bus_err_info {
+       sal_log_section_hdr_t header;
+       struct {
+               u64 err_status      : 1,
+                   requestor_id    : 1,
+                   responder_id    : 1,
+                   target_id       : 1,
+                   bus_spec_data   : 1,
+                   oem_data        : 1,
+                   reserved        : 58;
+       } valid;
+       u64 err_status;
+       u64 requestor_id;
+       u64 responder_id;
+       u64 target_id;
+       u64 bus_spec_data;
+       u8 oem_data[1];                 /* Variable length OEM data */
+} sal_log_plat_bus_err_info_t;
+
+/* Overall platform error section structure */
+typedef union sal_log_platform_err_info {
+       sal_log_mem_dev_err_info_t mem_dev_err;
+       sal_log_sel_dev_err_info_t sel_dev_err;
+       sal_log_pci_bus_err_info_t pci_bus_err;
+       sal_log_smbios_dev_err_info_t smbios_dev_err;
+       sal_log_pci_comp_err_info_t pci_comp_err;
+       sal_log_plat_specific_err_info_t plat_specific_err;
+       sal_log_host_ctlr_err_info_t host_ctlr_err;
+       sal_log_plat_bus_err_info_t plat_bus_err;
+} sal_log_platform_err_info_t;
+
+/* SAL log over-all, multi-section error record structure (processor+platform) 
*/
+typedef struct err_rec {
+       sal_log_record_header_t sal_elog_header;
+       sal_log_processor_info_t proc_err;
+       sal_log_platform_err_info_t plat_err;
+       u8 oem_data_pad[1024];
+} ia64_err_rec_t;
+
+/*
+ * Now define a couple of inline functions for improved type checking
+ * and convenience.
+ */
+static inline long
+ia64_sal_freq_base (unsigned long which, unsigned long *ticks_per_second,
+                   unsigned long *drift_info)
+{
+       struct ia64_sal_retval isrv;
+
+       SAL_CALL(isrv, SAL_FREQ_BASE, which, 0, 0, 0, 0, 0, 0);
+       *ticks_per_second = isrv.v0;
+       *drift_info = isrv.v1;
+       return isrv.status;
+}
+
+/* Flush all the processor and platform level instruction and/or data caches */
+static inline s64
+ia64_sal_cache_flush (u64 cache_type)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_CACHE_FLUSH, cache_type, 0, 0, 0, 0, 0, 0);
+       return isrv.status;
+}
+
+
+/* Initialize all the processor and platform level instruction and data caches 
*/
+static inline s64
+ia64_sal_cache_init (void)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_CACHE_INIT, 0, 0, 0, 0, 0, 0, 0);
+       return isrv.status;
+}
+
+/*
+ * Clear the processor and platform information logged by SAL with respect to 
the machine
+ * state at the time of MCA's, INITs, CMCs, or CPEs.
+ */
+static inline s64
+ia64_sal_clear_state_info (u64 sal_info_type)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL_REENTRANT(isrv, SAL_CLEAR_STATE_INFO, sal_info_type, 0,
+                     0, 0, 0, 0, 0);
+       return isrv.status;
+}
+
+
+/* Get the processor and platform information logged by SAL with respect to 
the machine
+ * state at the time of the MCAs, INITs, CMCs, or CPEs.
+ */
+static inline u64
+ia64_sal_get_state_info (u64 sal_info_type, u64 *sal_info)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL_REENTRANT(isrv, SAL_GET_STATE_INFO, sal_info_type, 0,
+                     sal_info, 0, 0, 0, 0);
+       if (isrv.status)
+               return 0;
+
+       return isrv.v0;
+}
+
+/*
+ * Get the maximum size of the information logged by SAL with respect to the 
machine state
+ * at the time of MCAs, INITs, CMCs, or CPEs.
+ */
+static inline u64
+ia64_sal_get_state_info_size (u64 sal_info_type)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL_REENTRANT(isrv, SAL_GET_STATE_INFO_SIZE, sal_info_type, 0,
+                     0, 0, 0, 0, 0);
+       if (isrv.status)
+               return 0;
+       return isrv.v0;
+}
+
+/*
+ * Causes the processor to go into a spin loop within SAL where SAL awaits a 
wakeup from
+ * the monarch processor.  Must not lock, because it will not return on any 
cpu until the
+ * monarch processor sends a wake up.
+ */
+static inline s64
+ia64_sal_mc_rendez (void)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL_NOLOCK(isrv, SAL_MC_RENDEZ, 0, 0, 0, 0, 0, 0, 0);
+       return isrv.status;
+}
+
+/*
+ * Allow the OS to specify the interrupt number to be used by SAL to interrupt 
OS during
+ * the machine check rendezvous sequence as well as the mechanism to wake up 
the
+ * non-monarch processor at the end of machine check processing.
+ * Returns the complete ia64_sal_retval because some calls return more than 
just a status
+ * value.
+ */
+static inline struct ia64_sal_retval
+ia64_sal_mc_set_params (u64 param_type, u64 i_or_m, u64 i_or_m_val, u64 
timeout, u64 rz_always)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_MC_SET_PARAMS, param_type, i_or_m, i_or_m_val,
+                timeout, rz_always, 0, 0);
+       return isrv;
+}
+
+/* Read from PCI configuration space */
+static inline s64
+ia64_sal_pci_config_read (u64 pci_config_addr, int type, u64 size, u64 *value)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_PCI_CONFIG_READ, pci_config_addr, size, type, 0, 0, 
0, 0);
+       if (value)
+               *value = isrv.v0;
+       return isrv.status;
+}
+
+/* Write to PCI configuration space */
+static inline s64
+ia64_sal_pci_config_write (u64 pci_config_addr, int type, u64 size, u64 value)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_PCI_CONFIG_WRITE, pci_config_addr, size, value,
+                type, 0, 0, 0);
+       return isrv.status;
+}
+
+/*
+ * Register physical addresses of locations needed by SAL when SAL procedures 
are invoked
+ * in virtual mode.
+ */
+static inline s64
+ia64_sal_register_physical_addr (u64 phys_entry, u64 phys_addr)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_REGISTER_PHYSICAL_ADDR, phys_entry, phys_addr,
+                0, 0, 0, 0, 0);
+       return isrv.status;
+}
+
+/*
+ * Register software dependent code locations within SAL. These locations are 
handlers or
+ * entry points where SAL will pass control for the specified event. These 
event handlers
+ * are for the bott rendezvous, MCAs and INIT scenarios.
+ */
+static inline s64
+ia64_sal_set_vectors (u64 vector_type,
+                     u64 handler_addr1, u64 gp1, u64 handler_len1,
+                     u64 handler_addr2, u64 gp2, u64 handler_len2)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_SET_VECTORS, vector_type,
+                       handler_addr1, gp1, handler_len1,
+                       handler_addr2, gp2, handler_len2);
+
+       return isrv.status;
+}
+
+/* Update the contents of PAL block in the non-volatile storage device */
+static inline s64
+ia64_sal_update_pal (u64 param_buf, u64 scratch_buf, u64 scratch_buf_size,
+                    u64 *error_code, u64 *scratch_buf_size_needed)
+{
+       struct ia64_sal_retval isrv;
+       SAL_CALL(isrv, SAL_UPDATE_PAL, param_buf, scratch_buf, scratch_buf_size,
+                0, 0, 0, 0);
+       if (error_code)
+               *error_code = isrv.v0;
+       if (scratch_buf_size_needed)
+               *scratch_buf_size_needed = isrv.v1;
+       return isrv.status;
+}
+
+extern unsigned long sal_platform_features;
+
+extern int (*salinfo_platform_oemdata)(const u8 *, u8 **, u64 *);
+
+struct sal_ret_values {
+       long r8; long r9; long r10; long r11;
+};
+
+#define IA64_SAL_OEMFUNC_MIN           0x02000000
+#define IA64_SAL_OEMFUNC_MAX           0x03ffffff
+
+extern int ia64_sal_oemcall(struct ia64_sal_retval *, u64, u64, u64, u64, u64,
+                           u64, u64, u64);
+extern int ia64_sal_oemcall_nolock(struct ia64_sal_retval *, u64, u64, u64,
+                                  u64, u64, u64, u64, u64);
+extern int ia64_sal_oemcall_reentrant(struct ia64_sal_retval *, u64, u64, u64,
+                                     u64, u64, u64, u64, u64);
+
+extern void ia64_sal_handler_init(void *entry_point, void *gpval);
+
+#endif /* __ASSEMBLY__ */
+
+#endif /* _ASM_IA64_SAL_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm/scatterlist.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/scatterlist.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,28 @@
+#ifndef _ASM_IA64_SCATTERLIST_H
+#define _ASM_IA64_SCATTERLIST_H
+
+/*
+ * Modified 1998-1999, 2001-2002, 2004
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ */
+
+struct scatterlist {
+       struct page *page;
+       unsigned int offset;
+       unsigned int length;    /* buffer length */
+
+       dma_addr_t dma_address;
+       unsigned int dma_length;
+};
+
+/*
+ * It used to be that ISA_DMA_THRESHOLD had something to do with the
+ * DMA-limits of ISA-devices.  Nowadays, its only remaining use (apart
+ * from the aha1542.c driver, which isn't 64-bit clean anyhow) is to
+ * tell the block-layer (via BLK_BOUNCE_ISA) what the max. physical
+ * address of a page is that is allocated with GFP_DMA.  On IA-64,
+ * that's 4GB - 1.
+ */
+#define ISA_DMA_THRESHOLD      0xffffffff
+
+#endif /* _ASM_IA64_SCATTERLIST_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/sections.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/sections.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,22 @@
+#ifndef _ASM_IA64_SECTIONS_H
+#define _ASM_IA64_SECTIONS_H
+
+/*
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm-generic/sections.h>
+
+extern char __per_cpu_start[], __per_cpu_end[], __phys_per_cpu_start[];
+extern char __start___vtop_patchlist[], __end___vtop_patchlist[];
+extern char __start___mckinley_e9_bundles[], __end___mckinley_e9_bundles[];
+extern char __start_gate_section[];
+extern char __start_gate_mckinley_e9_patchlist[], 
__end_gate_mckinley_e9_patchlist[];
+extern char __start_gate_vtop_patchlist[], __end_gate_vtop_patchlist[];
+extern char __start_gate_fsyscall_patchlist[], __end_gate_fsyscall_patchlist[];
+extern char __start_gate_brl_fsys_bubble_down_patchlist[], 
__end_gate_brl_fsys_bubble_down_patchlist[];
+extern char __start_unwind[], __end_unwind[];
+
+#endif /* _ASM_IA64_SECTIONS_H */
+
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/semaphore.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/semaphore.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,102 @@
+#ifndef _ASM_IA64_SEMAPHORE_H
+#define _ASM_IA64_SEMAPHORE_H
+
+/*
+ * Copyright (C) 1998-2000 Hewlett-Packard Co
+ * Copyright (C) 1998-2000 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/wait.h>
+#include <linux/rwsem.h>
+
+#include <asm/atomic.h>
+
+struct semaphore {
+       atomic_t count;
+       int sleepers;
+       wait_queue_head_t wait;
+};
+
+#define __SEMAPHORE_INITIALIZER(name, n)                               \
+{                                                                      \
+       .count          = ATOMIC_INIT(n),                               \
+       .sleepers       = 0,                                            \
+       .wait           = __WAIT_QUEUE_HEAD_INITIALIZER((name).wait)    \
+}
+
+#define __MUTEX_INITIALIZER(name)      __SEMAPHORE_INITIALIZER(name,1)
+
+#define __DECLARE_SEMAPHORE_GENERIC(name,count)                                
        \
+       struct semaphore name = __SEMAPHORE_INITIALIZER(name, count)
+
+#define DECLARE_MUTEX(name)            __DECLARE_SEMAPHORE_GENERIC(name, 1)
+#define DECLARE_MUTEX_LOCKED(name)     __DECLARE_SEMAPHORE_GENERIC(name, 0)
+
+static inline void
+sema_init (struct semaphore *sem, int val)
+{
+       *sem = (struct semaphore) __SEMAPHORE_INITIALIZER(*sem, val);
+}
+
+static inline void
+init_MUTEX (struct semaphore *sem)
+{
+       sema_init(sem, 1);
+}
+
+static inline void
+init_MUTEX_LOCKED (struct semaphore *sem)
+{
+       sema_init(sem, 0);
+}
+
+extern void __down (struct semaphore * sem);
+extern int  __down_interruptible (struct semaphore * sem);
+extern int  __down_trylock (struct semaphore * sem);
+extern void __up (struct semaphore * sem);
+
+/*
+ * Atomically decrement the semaphore's count.  If it goes negative,
+ * block the calling thread in the TASK_UNINTERRUPTIBLE state.
+ */
+static inline void
+down (struct semaphore *sem)
+{
+       might_sleep();
+       if (atomic_dec_return(&sem->count) < 0)
+               __down(sem);
+}
+
+/*
+ * Atomically decrement the semaphore's count.  If it goes negative,
+ * block the calling thread in the TASK_INTERRUPTIBLE state.
+ */
+static inline int
+down_interruptible (struct semaphore * sem)
+{
+       int ret = 0;
+
+       might_sleep();
+       if (atomic_dec_return(&sem->count) < 0)
+               ret = __down_interruptible(sem);
+       return ret;
+}
+
+static inline int
+down_trylock (struct semaphore *sem)
+{
+       int ret = 0;
+
+       if (atomic_dec_return(&sem->count) < 0)
+               ret = __down_trylock(sem);
+       return ret;
+}
+
+static inline void
+up (struct semaphore * sem)
+{
+       if (atomic_inc_return(&sem->count) <= 0)
+               __up(sem);
+}
+
+#endif /* _ASM_IA64_SEMAPHORE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/setup.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/setup.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,6 @@
+#ifndef __IA64_SETUP_H
+#define __IA64_SETUP_H
+
+#define COMMAND_LINE_SIZE      512
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/sigcontext.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/sigcontext.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,70 @@
+#ifndef _ASM_IA64_SIGCONTEXT_H
+#define _ASM_IA64_SIGCONTEXT_H
+
+/*
+ * Copyright (C) 1998, 1999, 2001 Hewlett-Packard Co
+ * Copyright (C) 1998, 1999, 2001 David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm/fpu.h>
+
+#define IA64_SC_FLAG_ONSTACK_BIT               0       /* is handler running 
on signal stack? */
+#define IA64_SC_FLAG_IN_SYSCALL_BIT            1       /* did signal interrupt 
a syscall? */
+#define IA64_SC_FLAG_FPH_VALID_BIT             2       /* is state in 
f[32]-f[127] valid? */
+
+#define IA64_SC_FLAG_ONSTACK           (1 << IA64_SC_FLAG_ONSTACK_BIT)
+#define IA64_SC_FLAG_IN_SYSCALL                (1 << 
IA64_SC_FLAG_IN_SYSCALL_BIT)
+#define IA64_SC_FLAG_FPH_VALID         (1 << IA64_SC_FLAG_FPH_VALID_BIT)
+
+# ifndef __ASSEMBLY__
+
+/*
+ * Note on handling of register backing store: sc_ar_bsp contains the address 
that would
+ * be found in ar.bsp after executing a "cover" instruction the context in 
which the
+ * signal was raised.  If signal delivery required switching to an alternate 
signal stack
+ * (sc_rbs_base is not NULL), the "dirty" partition (as it would exist after 
executing the
+ * imaginary "cover" instruction) is backed by the *alternate* signal stack, 
not the
+ * original one.  In this case, sc_rbs_base contains the base address of the 
new register
+ * backing store.  The number of registers in the dirty partition can be 
calculated as:
+ *
+ *   ndirty = ia64_rse_num_regs(sc_rbs_base, sc_rbs_base + (sc_loadrs >> 16))
+ *
+ */
+
+struct sigcontext {
+       unsigned long           sc_flags;       /* see manifest constants above 
*/
+       unsigned long           sc_nat;         /* bit i == 1 iff scratch reg 
gr[i] is a NaT */
+       stack_t                 sc_stack;       /* previously active stack */
+
+       unsigned long           sc_ip;          /* instruction pointer */
+       unsigned long           sc_cfm;         /* current frame marker */
+       unsigned long           sc_um;          /* user mask bits */
+       unsigned long           sc_ar_rsc;      /* register stack configuration 
register */
+       unsigned long           sc_ar_bsp;      /* backing store pointer */
+       unsigned long           sc_ar_rnat;     /* RSE NaT collection register 
*/
+       unsigned long           sc_ar_ccv;      /* compare and exchange compare 
value register */
+       unsigned long           sc_ar_unat;     /* ar.unat of interrupted 
context */
+       unsigned long           sc_ar_fpsr;     /* floating-point status 
register */
+       unsigned long           sc_ar_pfs;      /* previous function state */
+       unsigned long           sc_ar_lc;       /* loop count register */
+       unsigned long           sc_pr;          /* predicate registers */
+       unsigned long           sc_br[8];       /* branch registers */
+       /* Note: sc_gr[0] is used as the "uc_link" member of ucontext_t */
+       unsigned long           sc_gr[32];      /* general registers (static 
partition) */
+       struct ia64_fpreg       sc_fr[128];     /* floating-point registers */
+
+       unsigned long           sc_rbs_base;    /* NULL or new base of 
sighandler's rbs */
+       unsigned long           sc_loadrs;      /* see description above */
+
+       unsigned long           sc_ar25;        /* cmp8xchg16 uses this */
+       unsigned long           sc_ar26;        /* rsvd for scratch use */
+       unsigned long           sc_rsvd[12];    /* reserved for future use */
+       /*
+        * The mask must come last so we can increase _NSIG_WORDS
+        * without breaking binary compatibility.
+        */
+       sigset_t                sc_mask;        /* signal mask to restore after 
handler returns */
+};
+
+# endif /* __ASSEMBLY__ */
+#endif /* _ASM_IA64_SIGCONTEXT_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/signal.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/signal.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,185 @@
+#ifndef _ASM_IA64_SIGNAL_H
+#define _ASM_IA64_SIGNAL_H
+
+/*
+ * Modified 1998-2001, 2003
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>, Hewlett-Packard Co
+ *
+ * Unfortunately, this file is being included by bits/signal.h in
+ * glibc-2.x.  Hence the #ifdef __KERNEL__ ugliness.
+ */
+
+#define SIGHUP          1
+#define SIGINT          2
+#define SIGQUIT                 3
+#define SIGILL          4
+#define SIGTRAP                 5
+#define SIGABRT                 6
+#define SIGIOT          6
+#define SIGBUS          7
+#define SIGFPE          8
+#define SIGKILL                 9
+#define SIGUSR1                10
+#define SIGSEGV                11
+#define SIGUSR2                12
+#define SIGPIPE                13
+#define SIGALRM                14
+#define SIGTERM                15
+#define SIGSTKFLT      16
+#define SIGCHLD                17
+#define SIGCONT                18
+#define SIGSTOP                19
+#define SIGTSTP                20
+#define SIGTTIN                21
+#define SIGTTOU                22
+#define SIGURG         23
+#define SIGXCPU                24
+#define SIGXFSZ                25
+#define SIGVTALRM      26
+#define SIGPROF                27
+#define SIGWINCH       28
+#define SIGIO          29
+#define SIGPOLL                SIGIO
+/*
+#define SIGLOST                29
+*/
+#define SIGPWR         30
+#define SIGSYS         31
+/* signal 31 is no longer "unused", but the SIGUNUSED macro remains for 
backwards compatibility */
+#define        SIGUNUSED       31
+
+/* These should not be considered constants from userland.  */
+#define SIGRTMIN       32
+#define SIGRTMAX       _NSIG
+
+/*
+ * SA_FLAGS values:
+ *
+ * SA_ONSTACK indicates that a registered stack_t will be used.
+ * SA_INTERRUPT is a no-op, but left due to historical reasons.
+ * SA_RESTART flag to get restarting signals (which were the default long ago)
+ * SA_NOCLDSTOP flag to turn off SIGCHLD when children stop.
+ * SA_RESETHAND clears the handler when the signal is delivered.
+ * SA_NOCLDWAIT flag on SIGCHLD to inhibit zombies.
+ * SA_NODEFER prevents the current signal from being masked in the handler.
+ *
+ * SA_ONESHOT and SA_NOMASK are the historical Linux names for the Single
+ * Unix names RESETHAND and NODEFER respectively.
+ */
+#define SA_NOCLDSTOP   0x00000001
+#define SA_NOCLDWAIT   0x00000002
+#define SA_SIGINFO     0x00000004
+#define SA_ONSTACK     0x08000000
+#define SA_RESTART     0x10000000
+#define SA_NODEFER     0x40000000
+#define SA_RESETHAND   0x80000000
+
+#define SA_NOMASK      SA_NODEFER
+#define SA_ONESHOT     SA_RESETHAND
+#define SA_INTERRUPT   0x20000000 /* dummy -- ignored */
+
+#define SA_RESTORER    0x04000000
+
+/*
+ * sigaltstack controls
+ */
+#define SS_ONSTACK     1
+#define SS_DISABLE     2
+
+/*
+ * The minimum stack size needs to be fairly large because we want to
+ * be sure that an app compiled for today's CPUs will continue to run
+ * on all future CPU models.  The CPU model matters because the signal
+ * frame needs to have space for the complete machine state, including
+ * all physical stacked registers.  The number of physical stacked
+ * registers is CPU model dependent, but given that the width of
+ * ar.rsc.loadrs is 14 bits, we can assume that they'll never take up
+ * more than 16KB of space.
+ */
+#if 1
+  /*
+   * This is a stupid typo: the value was _meant_ to be 131072 (0x20000), but 
I typed it
+   * in wrong. ;-(  To preserve backwards compatibility, we leave the kernel 
at the
+   * incorrect value and fix libc only.
+   */
+# define MINSIGSTKSZ   131027  /* min. stack size for sigaltstack() */
+#else
+# define MINSIGSTKSZ   131072  /* min. stack size for sigaltstack() */
+#endif
+#define SIGSTKSZ       262144  /* default stack size for sigaltstack() */
+
+#ifdef __KERNEL__
+
+#define _NSIG          64
+#define _NSIG_BPW      64
+#define _NSIG_WORDS    (_NSIG / _NSIG_BPW)
+
+/*
+ * These values of sa_flags are used only by the kernel as part of the
+ * irq handling routines.
+ *
+ * SA_INTERRUPT is also used by the irq handling routines.
+ * SA_SHIRQ is for shared interrupt support on PCI and EISA.
+ */
+#define SA_PROBE               SA_ONESHOT
+#define SA_SAMPLE_RANDOM       SA_RESTART
+#define SA_SHIRQ               0x04000000
+#define SA_PERCPU_IRQ          0x02000000
+
+#endif /* __KERNEL__ */
+
+#define SIG_BLOCK          0   /* for blocking signals */
+#define SIG_UNBLOCK        1   /* for unblocking signals */
+#define SIG_SETMASK        2   /* for setting the signal mask */
+
+#define SIG_DFL        ((__sighandler_t)0)     /* default signal handling */
+#define SIG_IGN        ((__sighandler_t)1)     /* ignore signal */
+#define SIG_ERR        ((__sighandler_t)-1)    /* error return from signal */
+
+# ifndef __ASSEMBLY__
+
+#  include <linux/types.h>
+
+/* Avoid too many header ordering problems.  */
+struct siginfo;
+
+/* Type of a signal handler.  */
+typedef void __user (*__sighandler_t)(int);
+
+typedef struct sigaltstack {
+       void __user *ss_sp;
+       int ss_flags;
+       size_t ss_size;
+} stack_t;
+
+#ifdef __KERNEL__
+
+/* Most things should be clean enough to redefine this at will, if care
+   is taken to make libc match.  */
+
+typedef unsigned long old_sigset_t;
+
+typedef struct {
+       unsigned long sig[_NSIG_WORDS];
+} sigset_t;
+
+struct sigaction {
+       __sighandler_t sa_handler;
+       unsigned long sa_flags;
+       sigset_t sa_mask;               /* mask last for extensibility */
+};
+
+struct k_sigaction {
+       struct sigaction sa;
+};
+
+#  include <asm/sigcontext.h>
+
+#define ptrace_signal_deliver(regs, cookie) do { } while (0)
+
+void set_sigdelayed(pid_t pid, int signo, int code, void __user *addr);
+
+#endif /* __KERNEL__ */
+
+# endif /* !__ASSEMBLY__ */
+#endif /* _ASM_IA64_SIGNAL_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/smp.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/smp.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,131 @@
+/*
+ * SMP Support
+ *
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 2001-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#ifndef _ASM_IA64_SMP_H
+#define _ASM_IA64_SMP_H
+
+#include <linux/config.h>
+
+#ifdef CONFIG_SMP
+
+#include <linux/init.h>
+#include <linux/threads.h>
+#include <linux/kernel.h>
+#include <linux/cpumask.h>
+
+#include <asm/bitops.h>
+#include <asm/io.h>
+#include <asm/param.h>
+#include <asm/processor.h>
+#include <asm/ptrace.h>
+
+#define XTP_OFFSET             0x1e0008
+
+#define SMP_IRQ_REDIRECTION    (1 << 0)
+#define SMP_IPI_REDIRECTION    (1 << 1)
+
+#define smp_processor_id()     (current_thread_info()->cpu)
+
+extern struct smp_boot_data {
+       int cpu_count;
+       int cpu_phys_id[NR_CPUS];
+} smp_boot_data __initdata;
+
+extern char no_int_routing __devinitdata;
+
+extern cpumask_t cpu_online_map;
+extern void __iomem *ipi_base_addr;
+extern unsigned char smp_int_redirect;
+
+extern volatile int ia64_cpu_to_sapicid[];
+#define cpu_physical_id(i)     ia64_cpu_to_sapicid[i]
+
+extern unsigned long ap_wakeup_vector;
+
+/*
+ * Function to map hard smp processor id to logical id.  Slow, so don't use 
this in
+ * performance-critical code.
+ */
+static inline int
+cpu_logical_id (int cpuid)
+{
+       int i;
+
+       for (i = 0; i < NR_CPUS; ++i)
+               if (cpu_physical_id(i) == cpuid)
+                       break;
+       return i;
+}
+
+/*
+ * XTP control functions:
+ *     min_xtp   : route all interrupts to this CPU
+ *     normal_xtp: nominal XTP value
+ *     max_xtp   : never deliver interrupts to this CPU.
+ */
+
+static inline void
+min_xtp (void)
+{
+       if (smp_int_redirect & SMP_IRQ_REDIRECTION)
+               writeb(0x00, ipi_base_addr + XTP_OFFSET); /* XTP to min */
+}
+
+static inline void
+normal_xtp (void)
+{
+       if (smp_int_redirect & SMP_IRQ_REDIRECTION)
+               writeb(0x08, ipi_base_addr + XTP_OFFSET); /* XTP normal */
+}
+
+static inline void
+max_xtp (void)
+{
+       if (smp_int_redirect & SMP_IRQ_REDIRECTION)
+               writeb(0x0f, ipi_base_addr + XTP_OFFSET); /* Set XTP to max */
+}
+
+static inline unsigned int
+hard_smp_processor_id (void)
+{
+       union {
+               struct {
+                       unsigned long reserved : 16;
+                       unsigned long eid : 8;
+                       unsigned long id : 8;
+                       unsigned long ignored : 32;
+               } f;
+               unsigned long bits;
+       } lid;
+
+       lid.bits = ia64_getreg(_IA64_REG_CR_LID);
+       return lid.f.id << 8 | lid.f.eid;
+}
+
+/* Upping and downing of CPUs */
+extern int __cpu_disable (void);
+extern void __cpu_die (unsigned int cpu);
+extern void cpu_die (void) __attribute__ ((noreturn));
+extern int __cpu_up (unsigned int cpu);
+extern void __init smp_build_cpu_map(void);
+
+extern void __init init_smp_config (void);
+extern void smp_do_timer (struct pt_regs *regs);
+
+extern int smp_call_function_single (int cpuid, void (*func) (void *info), 
void *info,
+                                    int retry, int wait);
+extern void smp_send_reschedule (int cpu);
+extern void lock_ipi_calllock(void);
+extern void unlock_ipi_calllock(void);
+
+#else
+
+#define cpu_logical_id(cpuid)          0
+
+#endif /* CONFIG_SMP */
+#endif /* _ASM_IA64_SMP_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/spinlock.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/spinlock.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,208 @@
+#ifndef _ASM_IA64_SPINLOCK_H
+#define _ASM_IA64_SPINLOCK_H
+
+/*
+ * Copyright (C) 1998-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ *
+ * This file is used for SMP configurations only.
+ */
+
+#include <linux/compiler.h>
+#include <linux/kernel.h>
+
+#include <asm/atomic.h>
+#include <asm/bitops.h>
+#include <asm/intrinsics.h>
+#include <asm/system.h>
+
+typedef struct {
+       volatile unsigned int lock;
+#ifdef CONFIG_PREEMPT
+       unsigned int break_lock;
+#endif
+} spinlock_t;
+
+#define SPIN_LOCK_UNLOCKED                     (spinlock_t) { 0 }
+#define spin_lock_init(x)                      ((x)->lock = 0)
+
+#ifdef ASM_SUPPORTED
+/*
+ * Try to get the lock.  If we fail to get the lock, make a non-standard call 
to
+ * ia64_spinlock_contention().  We do not use a normal call because that would 
force all
+ * callers of spin_lock() to be non-leaf routines.  Instead, 
ia64_spinlock_contention() is
+ * carefully coded to touch only those registers that spin_lock() marks 
"clobbered".
+ */
+
+#define IA64_SPINLOCK_CLOBBERS "ar.ccv", "ar.pfs", "p14", "p15", "r27", "r28", 
"r29", "r30", "b6", "memory"
+
+static inline void
+_raw_spin_lock_flags (spinlock_t *lock, unsigned long flags)
+{
+       register volatile unsigned int *ptr asm ("r31") = &lock->lock;
+
+#if __GNUC__ < 3 || (__GNUC__ == 3 && __GNUC_MINOR__ < 3)
+# ifdef CONFIG_ITANIUM
+       /* don't use brl on Itanium... */
+       asm volatile ("{\n\t"
+                     "  mov ar.ccv = r0\n\t"
+                     "  mov r28 = ip\n\t"
+                     "  mov r30 = 1;;\n\t"
+                     "}\n\t"
+                     "cmpxchg4.acq r30 = [%1], r30, ar.ccv\n\t"
+                     "movl r29 = ia64_spinlock_contention_pre3_4;;\n\t"
+                     "cmp4.ne p14, p0 = r30, r0\n\t"
+                     "mov b6 = r29;;\n\t"
+                     "mov r27=%2\n\t"
+                     "(p14) br.cond.spnt.many b6"
+                     : "=r"(ptr) : "r"(ptr), "r" (flags) : 
IA64_SPINLOCK_CLOBBERS);
+# else
+       asm volatile ("{\n\t"
+                     "  mov ar.ccv = r0\n\t"
+                     "  mov r28 = ip\n\t"
+                     "  mov r30 = 1;;\n\t"
+                     "}\n\t"
+                     "cmpxchg4.acq r30 = [%1], r30, ar.ccv;;\n\t"
+                     "cmp4.ne p14, p0 = r30, r0\n\t"
+                     "mov r27=%2\n\t"
+                     "(p14) brl.cond.spnt.many 
ia64_spinlock_contention_pre3_4;;"
+                     : "=r"(ptr) : "r"(ptr), "r" (flags) : 
IA64_SPINLOCK_CLOBBERS);
+# endif /* CONFIG_MCKINLEY */
+#else
+# ifdef CONFIG_ITANIUM
+       /* don't use brl on Itanium... */
+       /* mis-declare, so we get the entry-point, not it's function 
descriptor: */
+       asm volatile ("mov r30 = 1\n\t"
+                     "mov r27=%2\n\t"
+                     "mov ar.ccv = r0;;\n\t"
+                     "cmpxchg4.acq r30 = [%0], r30, ar.ccv\n\t"
+                     "movl r29 = ia64_spinlock_contention;;\n\t"
+                     "cmp4.ne p14, p0 = r30, r0\n\t"
+                     "mov b6 = r29;;\n\t"
+                     "(p14) br.call.spnt.many b6 = b6"
+                     : "=r"(ptr) : "r"(ptr), "r" (flags) : 
IA64_SPINLOCK_CLOBBERS);
+# else
+       asm volatile ("mov r30 = 1\n\t"
+                     "mov r27=%2\n\t"
+                     "mov ar.ccv = r0;;\n\t"
+                     "cmpxchg4.acq r30 = [%0], r30, ar.ccv;;\n\t"
+                     "cmp4.ne p14, p0 = r30, r0\n\t"
+                     "(p14) brl.call.spnt.many b6=ia64_spinlock_contention;;"
+                     : "=r"(ptr) : "r"(ptr), "r" (flags) : 
IA64_SPINLOCK_CLOBBERS);
+# endif /* CONFIG_MCKINLEY */
+#endif
+}
+#define _raw_spin_lock(lock) _raw_spin_lock_flags(lock, 0)
+#else /* !ASM_SUPPORTED */
+#define _raw_spin_lock_flags(lock, flags) _raw_spin_lock(lock)
+# define _raw_spin_lock(x)                                                     
        \
+do {                                                                           
        \
+       __u32 *ia64_spinlock_ptr = (__u32 *) (x);                               
        \
+       __u64 ia64_spinlock_val;                                                
        \
+       ia64_spinlock_val = ia64_cmpxchg4_acq(ia64_spinlock_ptr, 1, 0);         
        \
+       if (unlikely(ia64_spinlock_val)) {                                      
        \
+               do {                                                            
        \
+                       while (*ia64_spinlock_ptr)                              
        \
+                               ia64_barrier();                                 
        \
+                       ia64_spinlock_val = 
ia64_cmpxchg4_acq(ia64_spinlock_ptr, 1, 0); \
+               } while (ia64_spinlock_val);                                    
        \
+       }                                                                       
        \
+} while (0)
+#endif /* !ASM_SUPPORTED */
+
+#define spin_is_locked(x)      ((x)->lock != 0)
+#define _raw_spin_unlock(x)    do { barrier(); ((spinlock_t *) x)->lock = 0; } 
while (0)
+#define _raw_spin_trylock(x)   (cmpxchg_acq(&(x)->lock, 0, 1) == 0)
+#define spin_unlock_wait(x)    do { barrier(); } while ((x)->lock)
+
+typedef struct {
+       volatile unsigned int read_counter      : 31;
+       volatile unsigned int write_lock        :  1;
+#ifdef CONFIG_PREEMPT
+       unsigned int break_lock;
+#endif
+} rwlock_t;
+#define RW_LOCK_UNLOCKED (rwlock_t) { 0, 0 }
+
+#define rwlock_init(x)         do { *(x) = RW_LOCK_UNLOCKED; } while(0)
+#define read_can_lock(rw)      (*(volatile int *)(rw) >= 0)
+#define write_can_lock(rw)     (*(volatile int *)(rw) == 0)
+
+#define _raw_read_lock(rw)                                                     
        \
+do {                                                                           
        \
+       rwlock_t *__read_lock_ptr = (rw);                                       
        \
+                                                                               
        \
+       while (unlikely(ia64_fetchadd(1, (int *) __read_lock_ptr, acq) < 0)) {  
        \
+               ia64_fetchadd(-1, (int *) __read_lock_ptr, rel);                
        \
+               while (*(volatile int *)__read_lock_ptr < 0)                    
        \
+                       cpu_relax();                                            
        \
+       }                                                                       
        \
+} while (0)
+
+#define _raw_read_unlock(rw)                                   \
+do {                                                           \
+       rwlock_t *__read_lock_ptr = (rw);                       \
+       ia64_fetchadd(-1, (int *) __read_lock_ptr, rel);        \
+} while (0)
+
+#ifdef ASM_SUPPORTED
+#define _raw_write_lock(rw)                                                    
\
+do {                                                                           
\
+       __asm__ __volatile__ (                                                  
\
+               "mov ar.ccv = r0\n"                                             
\
+               "dep r29 = -1, r0, 31, 1;;\n"                                   
\
+               "1:\n"                                                          
\
+               "ld4 r2 = [%0];;\n"                                             
\
+               "cmp4.eq p0,p7 = r0,r2\n"                                       
\
+               "(p7) br.cond.spnt.few 1b \n"                                   
\
+               "cmpxchg4.acq r2 = [%0], r29, ar.ccv;;\n"                       
\
+               "cmp4.eq p0,p7 = r0, r2\n"                                      
\
+               "(p7) br.cond.spnt.few 1b;;\n"                                  
\
+               :: "r"(rw) : "ar.ccv", "p7", "r2", "r29", "memory");            
\
+} while(0)
+
+#define _raw_write_trylock(rw)                                                 
\
+({                                                                             
\
+       register long result;                                                   
\
+                                                                               
\
+       __asm__ __volatile__ (                                                  
\
+               "mov ar.ccv = r0\n"                                             
\
+               "dep r29 = -1, r0, 31, 1;;\n"                                   
\
+               "cmpxchg4.acq %0 = [%1], r29, ar.ccv\n"                         
\
+               : "=r"(result) : "r"(rw) : "ar.ccv", "r29", "memory");          
\
+       (result == 0);                                                          
\
+})
+
+#else /* !ASM_SUPPORTED */
+
+#define _raw_write_lock(l)                                                     
        \
+({                                                                             
        \
+       __u64 ia64_val, ia64_set_val = ia64_dep_mi(-1, 0, 31, 1);               
        \
+       __u32 *ia64_write_lock_ptr = (__u32 *) (l);                             
        \
+       do {                                                                    
        \
+               while (*ia64_write_lock_ptr)                                    
        \
+                       ia64_barrier();                                         
        \
+               ia64_val = ia64_cmpxchg4_acq(ia64_write_lock_ptr, ia64_set_val, 
0);     \
+       } while (ia64_val);                                                     
        \
+})
+
+#define _raw_write_trylock(rw)                                         \
+({                                                                     \
+       __u64 ia64_val;                                                 \
+       __u64 ia64_set_val = ia64_dep_mi(-1, 0, 31,1);                  \
+       ia64_val = ia64_cmpxchg4_acq((__u32 *)(rw), ia64_set_val, 0);   \
+       (ia64_val == 0);                                                \
+})
+
+#endif /* !ASM_SUPPORTED */
+
+#define _raw_read_trylock(lock) generic_raw_read_trylock(lock)
+
+#define _raw_write_unlock(x)                                                   
        \
+({                                                                             
        \
+       smp_mb__before_clear_bit();     /* need barrier before releasing 
lock... */     \
+       clear_bit(31, (x));                                                     
        \
+})
+
+#endif /*  _ASM_IA64_SPINLOCK_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/string.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/string.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,22 @@
+#ifndef _ASM_IA64_STRING_H
+#define _ASM_IA64_STRING_H
+
+/*
+ * Here is where we want to put optimized versions of the string
+ * routines.
+ *
+ * Copyright (C) 1998-2000, 2002 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <linux/config.h>      /* remove this once we remove the A-step 
workaround... */
+
+#define __HAVE_ARCH_STRLEN     1 /* see arch/ia64/lib/strlen.S */
+#define __HAVE_ARCH_MEMSET     1 /* see arch/ia64/lib/memset.S */
+#define __HAVE_ARCH_MEMCPY     1 /* see arch/ia64/lib/memcpy.S */
+
+extern __kernel_size_t strlen (const char *);
+extern void *memcpy (void *, const void *, __kernel_size_t);
+extern void *memset (void *, int, __kernel_size_t);
+
+#endif /* _ASM_IA64_STRING_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/asm/thread_info.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/thread_info.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2002-2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#ifndef _ASM_IA64_THREAD_INFO_H
+#define _ASM_IA64_THREAD_INFO_H
+
+#include <asm/offsets.h>
+#include <asm/processor.h>
+#include <asm/ptrace.h>
+
+#define PREEMPT_ACTIVE_BIT 30
+#define PREEMPT_ACTIVE (1 << PREEMPT_ACTIVE_BIT)
+
+#ifndef __ASSEMBLY__
+
+/*
+ * On IA-64, we want to keep the task structure and kernel stack together, so 
they can be
+ * mapped by a single TLB entry and so they can be addressed by the "current" 
pointer
+ * without having to do pointer masking.
+ */
+struct thread_info {
+       struct task_struct *task;       /* XXX not really needed, except for 
dup_task_struct() */
+       struct exec_domain *exec_domain;/* execution domain */
+       __u32 flags;                    /* thread_info flags (see TIF_*) */
+       __u32 cpu;                      /* current CPU */
+       mm_segment_t addr_limit;        /* user-level address space limit */
+       __s32 preempt_count;            /* 0=premptable, <0=BUG; will also 
serve as bh-counter */
+       struct restart_block restart_block;
+       struct {
+               int signo;
+               int code;
+               void __user *addr;
+               unsigned long start_time;
+               pid_t pid;
+       } sigdelayed;                   /* Saved information for TIF_SIGDELAYED 
*/
+};
+
+#define THREAD_SIZE                    KERNEL_STACK_SIZE
+
+#define INIT_THREAD_INFO(tsk)                  \
+{                                              \
+       .task           = &tsk,                 \
+       .exec_domain    = &default_exec_domain, \
+       .flags          = 0,                    \
+       .cpu            = 0,                    \
+       .addr_limit     = KERNEL_DS,            \
+       .preempt_count  = 0,                    \
+       .restart_block = {                      \
+               .fn = do_no_restart_syscall,    \
+       },                                      \
+}
+
+/* how to get the thread information struct from C */
+#define current_thread_info()  ((struct thread_info *) ((char *) current + 
IA64_TASK_SIZE))
+#define alloc_thread_info(tsk) ((struct thread_info *) ((char *) (tsk) + 
IA64_TASK_SIZE))
+#define free_thread_info(ti)   /* nothing */
+
+#define __HAVE_ARCH_TASK_STRUCT_ALLOCATOR
+#define alloc_task_struct()    ((task_t *)__get_free_pages(GFP_KERNEL, 
KERNEL_STACK_SIZE_ORDER))
+#define free_task_struct(tsk)  free_pages((unsigned long) (tsk), 
KERNEL_STACK_SIZE_ORDER)
+
+#endif /* !__ASSEMBLY */
+
+/*
+ * thread information flags
+ * - these are process state flags that various assembly files may need to 
access
+ * - pending work-to-be-done flags are in least-significant 16 bits, other 
flags
+ *   in top 16 bits
+ */
+#define TIF_NOTIFY_RESUME      0       /* resumption notification requested */
+#define TIF_SIGPENDING         1       /* signal pending */
+#define TIF_NEED_RESCHED       2       /* rescheduling necessary */
+#define TIF_SYSCALL_TRACE      3       /* syscall trace active */
+#define TIF_SYSCALL_AUDIT      4       /* syscall auditing active */
+#define TIF_SIGDELAYED         5       /* signal delayed from MCA/INIT/NMI/PMI 
context */
+#define TIF_POLLING_NRFLAG     16      /* true if poll_idle() is polling 
TIF_NEED_RESCHED */
+#define TIF_MEMDIE             17
+
+#define _TIF_SYSCALL_TRACE     (1 << TIF_SYSCALL_TRACE)
+#define _TIF_SYSCALL_AUDIT     (1 << TIF_SYSCALL_AUDIT)
+#define _TIF_SYSCALL_TRACEAUDIT        (_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT)
+#define _TIF_NOTIFY_RESUME     (1 << TIF_NOTIFY_RESUME)
+#define _TIF_SIGPENDING                (1 << TIF_SIGPENDING)
+#define _TIF_NEED_RESCHED      (1 << TIF_NEED_RESCHED)
+#define _TIF_SIGDELAYED        (1 << TIF_SIGDELAYED)
+#define _TIF_POLLING_NRFLAG    (1 << TIF_POLLING_NRFLAG)
+
+/* "work to do on user-return" bits */
+#define TIF_ALLWORK_MASK       
(_TIF_NOTIFY_RESUME|_TIF_SIGPENDING|_TIF_NEED_RESCHED|_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT|_TIF_SIGDELAYED)
+/* like TIF_ALLWORK_BITS but sans TIF_SYSCALL_TRACE or TIF_SYSCALL_AUDIT */
+#define TIF_WORK_MASK          
(TIF_ALLWORK_MASK&~(_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT))
+
+#endif /* _ASM_IA64_THREAD_INFO_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/timex.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/timex.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,40 @@
+#ifndef _ASM_IA64_TIMEX_H
+#define _ASM_IA64_TIMEX_H
+
+/*
+ * Copyright (C) 1998-2001, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+/*
+ * 2001/01/18 davidm   Removed CLOCK_TICK_RATE.  It makes no sense on IA-64.
+ *                     Also removed cacheflush_time as it's entirely unused.
+ */
+
+#include <asm/intrinsics.h>
+#include <asm/processor.h>
+
+typedef unsigned long cycles_t;
+
+/*
+ * For performance reasons, we don't want to define CLOCK_TICK_TRATE as
+ * local_cpu_data->itc_rate.  Fortunately, we don't have to, either: according 
to George
+ * Anzinger, 1/CLOCK_TICK_RATE is taken as the resolution of the timer clock.  
The time
+ * calculation assumes that you will use enough of these so that your tick 
size <= 1/HZ.
+ * If the calculation shows that your CLOCK_TICK_RATE can not supply exactly 
1/HZ ticks,
+ * the actual value is calculated and used to update the wall clock each 
jiffie.  Setting
+ * the CLOCK_TICK_RATE to x*HZ insures that the calculation will find no 
errors.  Hence we
+ * pick a multiple of HZ which gives us a (totally virtual) CLOCK_TICK_RATE of 
about
+ * 100MHz.
+ */
+#define CLOCK_TICK_RATE                (HZ * 100000UL)
+
+static inline cycles_t
+get_cycles (void)
+{
+       cycles_t ret;
+
+       ret = ia64_getreg(_IA64_REG_AR_ITC);
+       return ret;
+}
+
+#endif /* _ASM_IA64_TIMEX_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/topology.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/topology.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,90 @@
+/*
+ * linux/include/asm-ia64/topology.h
+ *
+ * Copyright (C) 2002, Erich Focht, NEC
+ *
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+#ifndef _ASM_IA64_TOPOLOGY_H
+#define _ASM_IA64_TOPOLOGY_H
+
+#include <asm/acpi.h>
+#include <asm/numa.h>
+#include <asm/smp.h>
+
+#ifdef CONFIG_NUMA
+/*
+ * Returns the number of the node containing CPU 'cpu'
+ */
+#define cpu_to_node(cpu) (int)(cpu_to_node_map[cpu])
+
+/*
+ * Returns a bitmask of CPUs on Node 'node'.
+ */
+#define node_to_cpumask(node) (node_to_cpu_mask[node])
+
+/*
+ * Returns the number of the node containing Node 'nid'.
+ * Not implemented here. Multi-level hierarchies detected with
+ * the help of node_distance().
+ */
+#define parent_node(nid) (nid)
+
+/*
+ * Returns the number of the first CPU on Node 'node'.
+ */
+#define node_to_first_cpu(node) (__ffs(node_to_cpumask(node)))
+
+void build_cpu_to_node_map(void);
+
+/* sched_domains SD_NODE_INIT for IA64 NUMA machines */
+#define SD_NODE_INIT (struct sched_domain) {           \
+       .span                   = CPU_MASK_NONE,        \
+       .parent                 = NULL,                 \
+       .groups                 = NULL,                 \
+       .min_interval           = 80,                   \
+       .max_interval           = 320,                  \
+       .busy_factor            = 320,                  \
+       .imbalance_pct          = 125,                  \
+       .cache_hot_time         = (10*1000000),         \
+       .cache_nice_tries       = 1,                    \
+       .per_cpu_gain           = 100,                  \
+       .flags                  = SD_LOAD_BALANCE       \
+                               | SD_BALANCE_EXEC       \
+                               | SD_BALANCE_NEWIDLE    \
+                               | SD_WAKE_IDLE          \
+                               | SD_WAKE_BALANCE,      \
+       .last_balance           = jiffies,              \
+       .balance_interval       = 1,                    \
+       .nr_balance_failed      = 0,                    \
+}
+
+/* sched_domains SD_ALLNODES_INIT for IA64 NUMA machines */
+#define SD_ALLNODES_INIT (struct sched_domain) {       \
+       .span                   = CPU_MASK_NONE,        \
+       .parent                 = NULL,                 \
+       .groups                 = NULL,                 \
+       .min_interval           = 80,                   \
+       .max_interval           = 320,                  \
+       .busy_factor            = 320,                  \
+       .imbalance_pct          = 125,                  \
+       .cache_hot_time         = (10*1000000),         \
+       .cache_nice_tries       = 1,                    \
+       .per_cpu_gain           = 100,                  \
+       .flags                  = SD_LOAD_BALANCE       \
+                               | SD_BALANCE_EXEC,      \
+       .last_balance           = jiffies,              \
+       .balance_interval       = 100*(63+num_online_cpus())/64,   \
+       .nr_balance_failed      = 0,                    \
+}
+
+#endif /* CONFIG_NUMA */
+
+#include <asm-generic/topology.h>
+
+#endif /* _ASM_IA64_TOPOLOGY_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/unaligned.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/unaligned.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,121 @@
+#ifndef _ASM_IA64_UNALIGNED_H
+#define _ASM_IA64_UNALIGNED_H
+
+#include <linux/types.h>
+
+/*
+ * The main single-value unaligned transfer routines.
+ *
+ * Based on <asm-alpha/unaligned.h>.
+ *
+ * Copyright (C) 1998, 1999, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+#define get_unaligned(ptr) \
+       ((__typeof__(*(ptr)))ia64_get_unaligned((ptr), sizeof(*(ptr))))
+
+#define put_unaligned(x,ptr) \
+       ia64_put_unaligned((unsigned long)(x), (ptr), sizeof(*(ptr)))
+
+struct __una_u64 { __u64 x __attribute__((packed)); };
+struct __una_u32 { __u32 x __attribute__((packed)); };
+struct __una_u16 { __u16 x __attribute__((packed)); };
+
+static inline unsigned long
+__uld8 (const unsigned long * addr)
+{
+       const struct __una_u64 *ptr = (const struct __una_u64 *) addr;
+       return ptr->x;
+}
+
+static inline unsigned long
+__uld4 (const unsigned int * addr)
+{
+       const struct __una_u32 *ptr = (const struct __una_u32 *) addr;
+       return ptr->x;
+}
+
+static inline unsigned long
+__uld2 (const unsigned short * addr)
+{
+       const struct __una_u16 *ptr = (const struct __una_u16 *) addr;
+       return ptr->x;
+}
+
+static inline void
+__ust8 (unsigned long val, unsigned long * addr)
+{
+       struct __una_u64 *ptr = (struct __una_u64 *) addr;
+       ptr->x = val;
+}
+
+static inline void
+__ust4 (unsigned long val, unsigned int * addr)
+{
+       struct __una_u32 *ptr = (struct __una_u32 *) addr;
+       ptr->x = val;
+}
+
+static inline void
+__ust2 (unsigned long val, unsigned short * addr)
+{
+       struct __una_u16 *ptr = (struct __una_u16 *) addr;
+       ptr->x = val;
+}
+
+
+/*
+ * This function doesn't actually exist.  The idea is that when someone uses 
the macros
+ * below with an unsupported size (datatype), the linker will alert us to the 
problem via
+ * an unresolved reference error.
+ */
+extern unsigned long ia64_bad_unaligned_access_length (void);
+
+#define ia64_get_unaligned(_ptr,size)                                          
\
+({                                                                             
\
+       const void *__ia64_ptr = (_ptr);                                        
\
+       unsigned long __ia64_val;                                               
\
+                                                                               
\
+       switch (size) {                                                         
\
+             case 1:                                                           
\
+               __ia64_val = *(const unsigned char *) __ia64_ptr;               
\
+               break;                                                          
\
+             case 2:                                                           
\
+               __ia64_val = __uld2((const unsigned short *)__ia64_ptr);        
\
+               break;                                                          
\
+             case 4:                                                           
\
+               __ia64_val = __uld4((const unsigned int *)__ia64_ptr);          
\
+               break;                                                          
\
+             case 8:                                                           
\
+               __ia64_val = __uld8((const unsigned long *)__ia64_ptr);         
\
+               break;                                                          
\
+             default:                                                          
\
+               __ia64_val = ia64_bad_unaligned_access_length();                
\
+       }                                                                       
\
+       __ia64_val;                                                             
\
+})
+
+#define ia64_put_unaligned(_val,_ptr,size)                             \
+do {                                                                   \
+       const void *__ia64_ptr = (_ptr);                                \
+       unsigned long __ia64_val = (_val);                              \
+                                                                       \
+       switch (size) {                                                 \
+             case 1:                                                   \
+               *(unsigned char *)__ia64_ptr = (__ia64_val);            \
+               break;                                                  \
+             case 2:                                                   \
+               __ust2(__ia64_val, (unsigned short *)__ia64_ptr);       \
+               break;                                                  \
+             case 4:                                                   \
+               __ust4(__ia64_val, (unsigned int *)__ia64_ptr);         \
+               break;                                                  \
+             case 8:                                                   \
+               __ust8(__ia64_val, (unsigned long *)__ia64_ptr);        \
+               break;                                                  \
+             default:                                                  \
+               ia64_bad_unaligned_access_length();                     \
+       }                                                               \
+} while (0)
+
+#endif /* _ASM_IA64_UNALIGNED_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/unistd.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/unistd.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,399 @@
+#ifndef _ASM_IA64_UNISTD_H
+#define _ASM_IA64_UNISTD_H
+
+/*
+ * IA-64 Linux syscall numbers and inline-functions.
+ *
+ * Copyright (C) 1998-2005 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ */
+
+#include <asm/break.h>
+
+#define __BREAK_SYSCALL                        __IA64_BREAK_SYSCALL
+
+#define __NR_ni_syscall                        1024
+#define __NR_exit                      1025
+#define __NR_read                      1026
+#define __NR_write                     1027
+#define __NR_open                      1028
+#define __NR_close                     1029
+#define __NR_creat                     1030
+#define __NR_link                      1031
+#define __NR_unlink                    1032
+#define __NR_execve                    1033
+#define __NR_chdir                     1034
+#define __NR_fchdir                    1035
+#define __NR_utimes                    1036
+#define __NR_mknod                     1037
+#define __NR_chmod                     1038
+#define __NR_chown                     1039
+#define __NR_lseek                     1040
+#define __NR_getpid                    1041
+#define __NR_getppid                   1042
+#define __NR_mount                     1043
+#define __NR_umount                    1044
+#define __NR_setuid                    1045
+#define __NR_getuid                    1046
+#define __NR_geteuid                   1047
+#define __NR_ptrace                    1048
+#define __NR_access                    1049
+#define __NR_sync                      1050
+#define __NR_fsync                     1051
+#define __NR_fdatasync                 1052
+#define __NR_kill                      1053
+#define __NR_rename                    1054
+#define __NR_mkdir                     1055
+#define __NR_rmdir                     1056
+#define __NR_dup                       1057
+#define __NR_pipe                      1058
+#define __NR_times                     1059
+#define __NR_brk                       1060
+#define __NR_setgid                    1061
+#define __NR_getgid                    1062
+#define __NR_getegid                   1063
+#define __NR_acct                      1064
+#define __NR_ioctl                     1065
+#define __NR_fcntl                     1066
+#define __NR_umask                     1067
+#define __NR_chroot                    1068
+#define __NR_ustat                     1069
+#define __NR_dup2                      1070
+#define __NR_setreuid                  1071
+#define __NR_setregid                  1072
+#define __NR_getresuid                 1073
+#define __NR_setresuid                 1074
+#define __NR_getresgid                 1075
+#define __NR_setresgid                 1076
+#define __NR_getgroups                 1077
+#define __NR_setgroups                 1078
+#define __NR_getpgid                   1079
+#define __NR_setpgid                   1080
+#define __NR_setsid                    1081
+#define __NR_getsid                    1082
+#define __NR_sethostname               1083
+#define __NR_setrlimit                 1084
+#define __NR_getrlimit                 1085
+#define __NR_getrusage                 1086
+#define __NR_gettimeofday              1087
+#define __NR_settimeofday              1088
+#define __NR_select                    1089
+#define __NR_poll                      1090
+#define __NR_symlink                   1091
+#define __NR_readlink                  1092
+#define __NR_uselib                    1093
+#define __NR_swapon                    1094
+#define __NR_swapoff                   1095
+#define __NR_reboot                    1096
+#define __NR_truncate                  1097
+#define __NR_ftruncate                 1098
+#define __NR_fchmod                    1099
+#define __NR_fchown                    1100
+#define __NR_getpriority               1101
+#define __NR_setpriority               1102
+#define __NR_statfs                    1103
+#define __NR_fstatfs                   1104
+#define __NR_gettid                    1105
+#define __NR_semget                    1106
+#define __NR_semop                     1107
+#define __NR_semctl                    1108
+#define __NR_msgget                    1109
+#define __NR_msgsnd                    1110
+#define __NR_msgrcv                    1111
+#define __NR_msgctl                    1112
+#define __NR_shmget                    1113
+#define __NR_shmat                     1114
+#define __NR_shmdt                     1115
+#define __NR_shmctl                    1116
+/* also known as klogctl() in GNU libc: */
+#define __NR_syslog                    1117
+#define __NR_setitimer                 1118
+#define __NR_getitimer                 1119
+/* 1120 was __NR_old_stat */
+/* 1121 was __NR_old_lstat */
+/* 1122 was __NR_old_fstat */
+#define __NR_vhangup                   1123
+#define __NR_lchown                    1124
+#define __NR_remap_file_pages          1125
+#define __NR_wait4                     1126
+#define __NR_sysinfo                   1127
+#define __NR_clone                     1128
+#define __NR_setdomainname             1129
+#define __NR_uname                     1130
+#define __NR_adjtimex                  1131
+/* 1132 was __NR_create_module */
+#define __NR_init_module               1133
+#define __NR_delete_module             1134
+/* 1135 was __NR_get_kernel_syms */
+/* 1136 was __NR_query_module */
+#define __NR_quotactl                  1137
+#define __NR_bdflush                   1138
+#define __NR_sysfs                     1139
+#define __NR_personality               1140
+#define __NR_afs_syscall               1141
+#define __NR_setfsuid                  1142
+#define __NR_setfsgid                  1143
+#define __NR_getdents                  1144
+#define __NR_flock                     1145
+#define __NR_readv                     1146
+#define __NR_writev                    1147
+#define __NR_pread64                   1148
+#define __NR_pwrite64                  1149
+#define __NR__sysctl                   1150
+#define __NR_mmap                      1151
+#define __NR_munmap                    1152
+#define __NR_mlock                     1153
+#define __NR_mlockall                  1154
+#define __NR_mprotect                  1155
+#define __NR_mremap                    1156
+#define __NR_msync                     1157
+#define __NR_munlock                   1158
+#define __NR_munlockall                        1159
+#define __NR_sched_getparam            1160
+#define __NR_sched_setparam            1161
+#define __NR_sched_getscheduler                1162
+#define __NR_sched_setscheduler                1163
+#define __NR_sched_yield               1164
+#define __NR_sched_get_priority_max    1165
+#define __NR_sched_get_priority_min    1166
+#define __NR_sched_rr_get_interval     1167
+#define __NR_nanosleep                 1168
+#define __NR_nfsservctl                        1169
+#define __NR_prctl                     1170
+/* 1171 is reserved for backwards compatibility with old __NR_getpagesize */
+#define __NR_mmap2                     1172
+#define __NR_pciconfig_read            1173
+#define __NR_pciconfig_write           1174
+#define __NR_perfmonctl                        1175
+#define __NR_sigaltstack               1176
+#define __NR_rt_sigaction              1177
+#define __NR_rt_sigpending             1178
+#define __NR_rt_sigprocmask            1179
+#define __NR_rt_sigqueueinfo           1180
+#define __NR_rt_sigreturn              1181
+#define __NR_rt_sigsuspend             1182
+#define __NR_rt_sigtimedwait           1183
+#define __NR_getcwd                    1184
+#define __NR_capget                    1185
+#define __NR_capset                    1186
+#define __NR_sendfile                  1187
+#define __NR_getpmsg                   1188
+#define __NR_putpmsg                   1189
+#define __NR_socket                    1190
+#define __NR_bind                      1191
+#define __NR_connect                   1192
+#define __NR_listen                    1193
+#define __NR_accept                    1194
+#define __NR_getsockname               1195
+#define __NR_getpeername               1196
+#define __NR_socketpair                        1197
+#define __NR_send                      1198
+#define __NR_sendto                    1199
+#define __NR_recv                      1200
+#define __NR_recvfrom                  1201
+#define __NR_shutdown                  1202
+#define __NR_setsockopt                        1203
+#define __NR_getsockopt                        1204
+#define __NR_sendmsg                   1205
+#define __NR_recvmsg                   1206
+#define __NR_pivot_root                        1207
+#define __NR_mincore                   1208
+#define __NR_madvise                   1209
+#define __NR_stat                      1210
+#define __NR_lstat                     1211
+#define __NR_fstat                     1212
+#define __NR_clone2                    1213
+#define __NR_getdents64                        1214
+#define __NR_getunwind                 1215
+#define __NR_readahead                 1216
+#define __NR_setxattr                  1217
+#define __NR_lsetxattr                 1218
+#define __NR_fsetxattr                 1219
+#define __NR_getxattr                  1220
+#define __NR_lgetxattr                 1221
+#define __NR_fgetxattr                 1222
+#define __NR_listxattr                 1223
+#define __NR_llistxattr                        1224
+#define __NR_flistxattr                        1225
+#define __NR_removexattr               1226
+#define __NR_lremovexattr              1227
+#define __NR_fremovexattr              1228
+#define __NR_tkill                     1229
+#define __NR_futex                     1230
+#define __NR_sched_setaffinity         1231
+#define __NR_sched_getaffinity         1232
+#define __NR_set_tid_address           1233
+#define __NR_fadvise64                 1234
+#define __NR_tgkill                    1235
+#define __NR_exit_group                        1236
+#define __NR_lookup_dcookie            1237
+#define __NR_io_setup                  1238
+#define __NR_io_destroy                        1239
+#define __NR_io_getevents              1240
+#define __NR_io_submit                 1241
+#define __NR_io_cancel                 1242
+#define __NR_epoll_create              1243
+#define __NR_epoll_ctl                 1244
+#define __NR_epoll_wait                        1245
+#define __NR_restart_syscall           1246
+#define __NR_semtimedop                        1247
+#define __NR_timer_create              1248
+#define __NR_timer_settime             1249
+#define __NR_timer_gettime             1250
+#define __NR_timer_getoverrun          1251
+#define __NR_timer_delete              1252
+#define __NR_clock_settime             1253
+#define __NR_clock_gettime             1254
+#define __NR_clock_getres              1255
+#define __NR_clock_nanosleep           1256
+#define __NR_fstatfs64                 1257
+#define __NR_statfs64                  1258
+#define __NR_mbind                     1259
+#define __NR_get_mempolicy             1260
+#define __NR_set_mempolicy             1261
+#define __NR_mq_open                   1262
+#define __NR_mq_unlink                 1263
+#define __NR_mq_timedsend              1264
+#define __NR_mq_timedreceive           1265
+#define __NR_mq_notify                 1266
+#define __NR_mq_getsetattr             1267
+#define __NR_kexec_load                        1268
+#define __NR_vserver                   1269
+#define __NR_waitid                    1270
+#define __NR_add_key                   1271
+#define __NR_request_key               1272
+#define __NR_keyctl                    1273
+
+#ifdef __KERNEL__
+
+#include <linux/config.h>
+
+#define NR_syscalls                    256 /* length of syscall table */
+
+#define __ARCH_WANT_SYS_RT_SIGACTION
+
+#ifdef CONFIG_IA32_SUPPORT
+# define __ARCH_WANT_SYS_FADVISE64
+# define __ARCH_WANT_SYS_GETPGRP
+# define __ARCH_WANT_SYS_LLSEEK
+# define __ARCH_WANT_SYS_NICE
+# define __ARCH_WANT_SYS_OLD_GETRLIMIT
+# define __ARCH_WANT_SYS_OLDUMOUNT
+# define __ARCH_WANT_SYS_SIGPENDING
+# define __ARCH_WANT_SYS_SIGPROCMASK
+# define __ARCH_WANT_COMPAT_SYS_TIME
+#endif
+
+#if !defined(__ASSEMBLY__) && !defined(ASSEMBLER)
+
+#include <linux/types.h>
+#include <linux/linkage.h>
+#include <linux/compiler.h>
+
+extern long __ia64_syscall (long a0, long a1, long a2, long a3, long a4, long 
nr);
+
+#ifdef __KERNEL_SYSCALLS__
+
+#include <linux/compiler.h>
+#include <linux/string.h>
+#include <linux/signal.h>
+#include <asm/ptrace.h>
+#include <linux/stringify.h>
+#include <linux/syscalls.h>
+
+static inline long
+open (const char * name, int mode, int flags)
+{
+       return sys_open(name, mode, flags);
+}
+
+static inline long
+dup (int fd)
+{
+       return sys_dup(fd);
+}
+
+static inline long
+close (int fd)
+{
+       return sys_close(fd);
+}
+
+static inline off_t
+lseek (int fd, off_t off, int whence)
+{
+       return sys_lseek(fd, off, whence);
+}
+
+static inline void
+_exit (int value)
+{
+       sys_exit(value);
+}
+
+#define exit(x) _exit(x)
+
+static inline long
+write (int fd, const char * buf, size_t nr)
+{
+       return sys_write(fd, buf, nr);
+}
+
+static inline long
+read (int fd, char * buf, size_t nr)
+{
+       return sys_read(fd, buf, nr);
+}
+
+
+static inline long
+setsid (void)
+{
+       return sys_setsid();
+}
+
+static inline pid_t
+waitpid (int pid, int * wait_stat, int flags)
+{
+       return sys_wait4(pid, wait_stat, flags, NULL);
+}
+
+
+extern int execve (const char *filename, char *const av[], char *const ep[]);
+extern pid_t clone (unsigned long flags, void *sp);
+
+#endif /* __KERNEL_SYSCALLS__ */
+
+asmlinkage unsigned long sys_mmap(
+                               unsigned long addr, unsigned long len,
+                               int prot, int flags,
+                               int fd, long off);
+asmlinkage unsigned long sys_mmap2(
+                               unsigned long addr, unsigned long len,
+                               int prot, int flags,
+                               int fd, long pgoff);
+struct pt_regs;
+struct sigaction;
+long sys_execve(char __user *filename, char __user * __user *argv,
+                          char __user * __user *envp, struct pt_regs *regs);
+asmlinkage long sys_pipe(void);
+asmlinkage long sys_ptrace(long request, pid_t pid,
+                          unsigned long addr, unsigned long data);
+asmlinkage long sys_rt_sigaction(int sig,
+                                const struct sigaction __user *act,
+                                struct sigaction __user *oact,
+                                size_t sigsetsize);
+
+/*
+ * "Conditional" syscalls
+ *
+ * Note, this macro can only be used in the file which defines sys_ni_syscall, 
i.e., in
+ * kernel/sys_ni.c.  This version causes warnings because the declaration 
isn't a
+ * proper prototype, but we can't use __typeof__ either, because not all 
cond_syscall()
+ * declarations have prototypes at the moment.
+ */
+#define cond_syscall(x) asmlinkage long x (void) 
__attribute__((weak,alias("sys_ni_syscall")));
+
+#endif /* !__ASSEMBLY__ */
+#endif /* __KERNEL__ */
+#endif /* _ASM_IA64_UNISTD_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/unwind.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/unwind.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,240 @@
+#ifndef _ASM_IA64_UNWIND_H
+#define _ASM_IA64_UNWIND_H
+
+/*
+ * Copyright (C) 1999-2000, 2003 Hewlett-Packard Co
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *
+ * A simple API for unwinding kernel stacks.  This is used for
+ * debugging and error reporting purposes.  The kernel doesn't need
+ * full-blown stack unwinding with all the bells and whitles, so there
+ * is not much point in implementing the full IA-64 unwind API (though
+ * it would of course be possible to implement the kernel API on top
+ * of it).
+ */
+
+struct task_struct;    /* forward declaration */
+struct switch_stack;   /* forward declaration */
+
+enum unw_application_register {
+       UNW_AR_BSP,
+       UNW_AR_BSPSTORE,
+       UNW_AR_PFS,
+       UNW_AR_RNAT,
+       UNW_AR_UNAT,
+       UNW_AR_LC,
+       UNW_AR_EC,
+       UNW_AR_FPSR,
+       UNW_AR_RSC,
+       UNW_AR_CCV,
+       UNW_AR_CSD,
+       UNW_AR_SSD
+};
+
+/*
+ * The following declarations are private to the unwind
+ * implementation:
+ */
+
+struct unw_stack {
+       unsigned long limit;
+       unsigned long top;
+};
+
+#define UNW_FLAG_INTERRUPT_FRAME       (1UL << 0)
+
+/*
+ * No user of this module should every access this structure directly
+ * as it is subject to change.  It is declared here solely so we can
+ * use automatic variables.
+ */
+struct unw_frame_info {
+       struct unw_stack regstk;
+       struct unw_stack memstk;
+       unsigned int flags;
+       short hint;
+       short prev_script;
+
+       /* current frame info: */
+       unsigned long bsp;              /* backing store pointer value */
+       unsigned long sp;               /* stack pointer value */
+       unsigned long psp;              /* previous sp value */
+       unsigned long ip;               /* instruction pointer value */
+       unsigned long pr;               /* current predicate values */
+       unsigned long *cfm_loc;         /* cfm save location (or NULL) */
+       unsigned long pt;               /* struct pt_regs location */
+
+       struct task_struct *task;
+       struct switch_stack *sw;
+
+       /* preserved state: */
+       unsigned long *bsp_loc;         /* previous bsp save location */
+       unsigned long *bspstore_loc;
+       unsigned long *pfs_loc;
+       unsigned long *rnat_loc;
+       unsigned long *rp_loc;
+       unsigned long *pri_unat_loc;
+       unsigned long *unat_loc;
+       unsigned long *pr_loc;
+       unsigned long *lc_loc;
+       unsigned long *fpsr_loc;
+       struct unw_ireg {
+               unsigned long *loc;
+               struct unw_ireg_nat {
+                       long type : 3;                  /* enum unw_nat_type */
+                       signed long off : 61;           /* NaT word is at 
loc+nat.off */
+               } nat;
+       } r4, r5, r6, r7;
+       unsigned long *b1_loc, *b2_loc, *b3_loc, *b4_loc, *b5_loc;
+       struct ia64_fpreg *f2_loc, *f3_loc, *f4_loc, *f5_loc, *fr_loc[16];
+};
+
+/*
+ * The official API follows below:
+ */
+
+struct unw_table_entry {
+       u64 start_offset;
+       u64 end_offset;
+       u64 info_offset;
+};
+
+/*
+ * Initialize unwind support.
+ */
+extern void unw_init (void);
+
+extern void *unw_add_unwind_table (const char *name, unsigned long 
segment_base, unsigned long gp,
+                                  const void *table_start, const void 
*table_end);
+
+extern void unw_remove_unwind_table (void *handle);
+
+/*
+ * Prepare to unwind blocked task t.
+ */
+extern void unw_init_from_blocked_task (struct unw_frame_info *info, struct 
task_struct *t);
+
+/*
+ * Prepare to unwind from interruption.  The pt-regs and switch-stack 
structures must have
+ * be "adjacent" (no state modifications between pt-regs and switch-stack).
+ */
+extern void unw_init_from_interruption (struct unw_frame_info *info, struct 
task_struct *t,
+                                       struct pt_regs *pt, struct switch_stack 
*sw);
+
+extern void unw_init_frame_info (struct unw_frame_info *info, struct 
task_struct *t,
+                                struct switch_stack *sw);
+
+/*
+ * Prepare to unwind the currently running thread.
+ */
+extern void unw_init_running (void (*callback)(struct unw_frame_info *info, 
void *arg), void *arg);
+
+/*
+ * Unwind to previous to frame.  Returns 0 if successful, negative
+ * number in case of an error.
+ */
+extern int unw_unwind (struct unw_frame_info *info);
+
+/*
+ * Unwind until the return pointer is in user-land (or until an error
+ * occurs).  Returns 0 if successful, negative number in case of
+ * error.
+ */
+extern int unw_unwind_to_user (struct unw_frame_info *info);
+
+#define unw_is_intr_frame(info)        (((info)->flags & 
UNW_FLAG_INTERRUPT_FRAME) != 0)
+
+static inline int
+unw_get_ip (struct unw_frame_info *info, unsigned long *valp)
+{
+       *valp = (info)->ip;
+       return 0;
+}
+
+static inline int
+unw_get_sp (struct unw_frame_info *info, unsigned long *valp)
+{
+       *valp = (info)->sp;
+       return 0;
+}
+
+static inline int
+unw_get_psp (struct unw_frame_info *info, unsigned long *valp)
+{
+       *valp = (info)->psp;
+       return 0;
+}
+
+static inline int
+unw_get_bsp (struct unw_frame_info *info, unsigned long *valp)
+{
+       *valp = (info)->bsp;
+       return 0;
+}
+
+static inline int
+unw_get_cfm (struct unw_frame_info *info, unsigned long *valp)
+{
+       *valp = *(info)->cfm_loc;
+       return 0;
+}
+
+static inline int
+unw_set_cfm (struct unw_frame_info *info, unsigned long val)
+{
+       *(info)->cfm_loc = val;
+       return 0;
+}
+
+static inline int
+unw_get_rp (struct unw_frame_info *info, unsigned long *val)
+{
+       if (!info->rp_loc)
+               return -1;
+       *val = *info->rp_loc;
+       return 0;
+}
+
+extern int unw_access_gr (struct unw_frame_info *, int, unsigned long *, char 
*, int);
+extern int unw_access_br (struct unw_frame_info *, int, unsigned long *, int);
+extern int unw_access_fr (struct unw_frame_info *, int, struct ia64_fpreg *, 
int);
+extern int unw_access_ar (struct unw_frame_info *, int, unsigned long *, int);
+extern int unw_access_pr (struct unw_frame_info *, unsigned long *, int);
+
+static inline int
+unw_set_gr (struct unw_frame_info *i, int n, unsigned long v, char nat)
+{
+       return unw_access_gr(i, n, &v, &nat, 1);
+}
+
+static inline int
+unw_set_br (struct unw_frame_info *i, int n, unsigned long v)
+{
+       return unw_access_br(i, n, &v, 1);
+}
+
+static inline int
+unw_set_fr (struct unw_frame_info *i, int n, struct ia64_fpreg v)
+{
+       return unw_access_fr(i, n, &v, 1);
+}
+
+static inline int
+unw_set_ar (struct unw_frame_info *i, int n, unsigned long v)
+{
+       return unw_access_ar(i, n, &v, 1);
+}
+
+static inline int
+unw_set_pr (struct unw_frame_info *i, unsigned long v)
+{
+       return unw_access_pr(i, &v, 1);
+}
+
+#define unw_get_gr(i,n,v,nat)  unw_access_gr(i,n,v,nat,0)
+#define unw_get_br(i,n,v)      unw_access_br(i,n,v,0)
+#define unw_get_fr(i,n,v)      unw_access_fr(i,n,v,0)
+#define unw_get_ar(i,n,v)      unw_access_ar(i,n,v,0)
+#define unw_get_pr(i,v)                unw_access_pr(i,v,0)
+
+#endif /* _ASM_UNWIND_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/asm/ustack.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/asm/ustack.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,16 @@
+#ifndef _ASM_IA64_USTACK_H
+#define _ASM_IA64_USTACK_H
+
+/*
+ * Constants for the user stack size
+ */
+
+#include <asm/page.h>
+
+/* The absolute hard limit for stack size is 1/2 of the mappable space in the 
region */
+#define MAX_USER_STACK_SIZE    (RGN_MAP_LIMIT/2)
+/* Make a default stack size of 2GB */
+#define DEFAULT_USER_STACK_SIZE        (1UL << 31)
+#define STACK_TOP              (0x6000000000000000UL + RGN_MAP_LIMIT)
+
+#endif /* _ASM_IA64_USTACK_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/bcd.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/bcd.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,20 @@
+/* Permission is hereby granted to copy, modify and redistribute this code
+ * in terms of the GNU Library General Public License, Version 2 or later,
+ * at your option.
+ */
+
+/* macros to translate to/from binary and binary-coded decimal (frequently
+ * found in RTC chips).
+ */
+
+#ifndef _BCD_H
+#define _BCD_H
+
+#define BCD2BIN(val)   (((val) & 0x0f) + ((val)>>4)*10)
+#define BIN2BCD(val)   ((((val)/10)<<4) + (val)%10)
+
+/* backwards compat */
+#define BCD_TO_BIN(val) ((val)=BCD2BIN(val))
+#define BIN_TO_BCD(val) ((val)=BIN2BCD(val))
+
+#endif /* _BCD_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/bitmap.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/bitmap.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,255 @@
+#ifndef __LINUX_BITMAP_H
+#define __LINUX_BITMAP_H
+
+#ifndef __ASSEMBLY__
+
+#include <linux/types.h>
+#include <linux/bitops.h>
+#include <linux/string.h>
+
+/*
+ * bitmaps provide bit arrays that consume one or more unsigned
+ * longs.  The bitmap interface and available operations are listed
+ * here, in bitmap.h
+ *
+ * Function implementations generic to all architectures are in
+ * lib/bitmap.c.  Functions implementations that are architecture
+ * specific are in various include/asm-<arch>/bitops.h headers
+ * and other arch/<arch> specific files.
+ *
+ * See lib/bitmap.c for more details.
+ */
+
+/*
+ * The available bitmap operations and their rough meaning in the
+ * case that the bitmap is a single unsigned long are thus:
+ *
+ * bitmap_zero(dst, nbits)                     *dst = 0UL
+ * bitmap_fill(dst, nbits)                     *dst = ~0UL
+ * bitmap_copy(dst, src, nbits)                        *dst = *src
+ * bitmap_and(dst, src1, src2, nbits)          *dst = *src1 & *src2
+ * bitmap_or(dst, src1, src2, nbits)           *dst = *src1 | *src2
+ * bitmap_xor(dst, src1, src2, nbits)          *dst = *src1 ^ *src2
+ * bitmap_andnot(dst, src1, src2, nbits)       *dst = *src1 & ~(*src2)
+ * bitmap_complement(dst, src, nbits)          *dst = ~(*src)
+ * bitmap_equal(src1, src2, nbits)             Are *src1 and *src2 equal?
+ * bitmap_intersects(src1, src2, nbits)        Do *src1 and *src2 overlap?
+ * bitmap_subset(src1, src2, nbits)            Is *src1 a subset of *src2?
+ * bitmap_empty(src, nbits)                    Are all bits zero in *src?
+ * bitmap_full(src, nbits)                     Are all bits set in *src?
+ * bitmap_weight(src, nbits)                   Hamming Weight: number set bits
+ * bitmap_shift_right(dst, src, n, nbits)      *dst = *src >> n
+ * bitmap_shift_left(dst, src, n, nbits)       *dst = *src << n
+ * bitmap_scnprintf(buf, len, src, nbits)      Print bitmap src to buf
+ * bitmap_parse(ubuf, ulen, dst, nbits)                Parse bitmap dst from 
buf
+ */
+
+/*
+ * Also the following operations in asm/bitops.h apply to bitmaps.
+ *
+ * set_bit(bit, addr)                  *addr |= bit
+ * clear_bit(bit, addr)                        *addr &= ~bit
+ * change_bit(bit, addr)               *addr ^= bit
+ * test_bit(bit, addr)                 Is bit set in *addr?
+ * test_and_set_bit(bit, addr)         Set bit and return old value
+ * test_and_clear_bit(bit, addr)       Clear bit and return old value
+ * test_and_change_bit(bit, addr)      Change bit and return old value
+ * find_first_zero_bit(addr, nbits)    Position first zero bit in *addr
+ * find_first_bit(addr, nbits)         Position first set bit in *addr
+ * find_next_zero_bit(addr, nbits, bit)        Position next zero bit in *addr 
>= bit
+ * find_next_bit(addr, nbits, bit)     Position next set bit in *addr >= bit
+ */
+
+/*
+ * The DECLARE_BITMAP(name,bits) macro, in linux/types.h, can be used
+ * to declare an array named 'name' of just enough unsigned longs to
+ * contain all bit positions from 0 to 'bits' - 1.
+ */
+
+/*
+ * lib/bitmap.c provides these functions:
+ */
+
+extern int __bitmap_empty(const unsigned long *bitmap, int bits);
+extern int __bitmap_full(const unsigned long *bitmap, int bits);
+extern int __bitmap_equal(const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern void __bitmap_complement(unsigned long *dst, const unsigned long *src,
+                       int bits);
+extern void __bitmap_shift_right(unsigned long *dst,
+                        const unsigned long *src, int shift, int bits);
+extern void __bitmap_shift_left(unsigned long *dst,
+                        const unsigned long *src, int shift, int bits);
+extern void __bitmap_and(unsigned long *dst, const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern void __bitmap_or(unsigned long *dst, const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern void __bitmap_xor(unsigned long *dst, const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern void __bitmap_andnot(unsigned long *dst, const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern int __bitmap_intersects(const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern int __bitmap_subset(const unsigned long *bitmap1,
+                       const unsigned long *bitmap2, int bits);
+extern int __bitmap_weight(const unsigned long *bitmap, int bits);
+
+extern int bitmap_scnprintf(char *buf, unsigned int len,
+                       const unsigned long *src, int nbits);
+extern int bitmap_parse(const char __user *ubuf, unsigned int ulen,
+                       unsigned long *dst, int nbits);
+extern int bitmap_find_free_region(unsigned long *bitmap, int bits, int order);
+extern void bitmap_release_region(unsigned long *bitmap, int pos, int order);
+extern int bitmap_allocate_region(unsigned long *bitmap, int pos, int order);
+
+#define BITMAP_LAST_WORD_MASK(nbits)                                   \
+(                                                                      \
+       ((nbits) % BITS_PER_LONG) ?                                     \
+               (1UL<<((nbits) % BITS_PER_LONG))-1 : ~0UL               \
+)
+
+static inline void bitmap_zero(unsigned long *dst, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = 0UL;
+       else {
+               int len = BITS_TO_LONGS(nbits) * sizeof(unsigned long);
+               memset(dst, 0, len);
+       }
+}
+
+static inline void bitmap_fill(unsigned long *dst, int nbits)
+{
+       size_t nlongs = BITS_TO_LONGS(nbits);
+       if (nlongs > 1) {
+               int len = (nlongs - 1) * sizeof(unsigned long);
+               memset(dst, 0xff,  len);
+       }
+       dst[nlongs - 1] = BITMAP_LAST_WORD_MASK(nbits);
+}
+
+static inline void bitmap_copy(unsigned long *dst, const unsigned long *src,
+                       int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src;
+       else {
+               int len = BITS_TO_LONGS(nbits) * sizeof(unsigned long);
+               memcpy(dst, src, len);
+       }
+}
+
+static inline void bitmap_and(unsigned long *dst, const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src1 & *src2;
+       else
+               __bitmap_and(dst, src1, src2, nbits);
+}
+
+static inline void bitmap_or(unsigned long *dst, const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src1 | *src2;
+       else
+               __bitmap_or(dst, src1, src2, nbits);
+}
+
+static inline void bitmap_xor(unsigned long *dst, const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src1 ^ *src2;
+       else
+               __bitmap_xor(dst, src1, src2, nbits);
+}
+
+static inline void bitmap_andnot(unsigned long *dst, const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src1 & ~(*src2);
+       else
+               __bitmap_andnot(dst, src1, src2, nbits);
+}
+
+static inline void bitmap_complement(unsigned long *dst, const unsigned long 
*src,
+                       int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = ~(*src) & BITMAP_LAST_WORD_MASK(nbits);
+       else
+               __bitmap_complement(dst, src, nbits);
+}
+
+static inline int bitmap_equal(const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               return ! ((*src1 ^ *src2) & BITMAP_LAST_WORD_MASK(nbits));
+       else
+               return __bitmap_equal(src1, src2, nbits);
+}
+
+static inline int bitmap_intersects(const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               return ((*src1 & *src2) & BITMAP_LAST_WORD_MASK(nbits)) != 0;
+       else
+               return __bitmap_intersects(src1, src2, nbits);
+}
+
+static inline int bitmap_subset(const unsigned long *src1,
+                       const unsigned long *src2, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               return ! ((*src1 & ~(*src2)) & BITMAP_LAST_WORD_MASK(nbits));
+       else
+               return __bitmap_subset(src1, src2, nbits);
+}
+
+static inline int bitmap_empty(const unsigned long *src, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               return ! (*src & BITMAP_LAST_WORD_MASK(nbits));
+       else
+               return __bitmap_empty(src, nbits);
+}
+
+static inline int bitmap_full(const unsigned long *src, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               return ! (~(*src) & BITMAP_LAST_WORD_MASK(nbits));
+       else
+               return __bitmap_full(src, nbits);
+}
+
+static inline int bitmap_weight(const unsigned long *src, int nbits)
+{
+       return __bitmap_weight(src, nbits);
+}
+
+static inline void bitmap_shift_right(unsigned long *dst,
+                       const unsigned long *src, int n, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = *src >> n;
+       else
+               __bitmap_shift_right(dst, src, n, nbits);
+}
+
+static inline void bitmap_shift_left(unsigned long *dst,
+                       const unsigned long *src, int n, int nbits)
+{
+       if (nbits <= BITS_PER_LONG)
+               *dst = (*src << n) & BITMAP_LAST_WORD_MASK(nbits);
+       else
+               __bitmap_shift_left(dst, src, n, nbits);
+}
+
+#endif /* __ASSEMBLY__ */
+
+#endif /* __LINUX_BITMAP_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/bitops.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/bitops.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,137 @@
+#ifndef _LINUX_BITOPS_H
+#define _LINUX_BITOPS_H
+#include <asm/types.h>
+
+/*
+ * ffs: find first bit set. This is defined the same way as
+ * the libc and compiler builtin ffs routines, therefore
+ * differs in spirit from the above ffz (man ffs).
+ */
+
+static inline int generic_ffs(int x)
+{
+       int r = 1;
+
+       if (!x)
+               return 0;
+       if (!(x & 0xffff)) {
+               x >>= 16;
+               r += 16;
+       }
+       if (!(x & 0xff)) {
+               x >>= 8;
+               r += 8;
+       }
+       if (!(x & 0xf)) {
+               x >>= 4;
+               r += 4;
+       }
+       if (!(x & 3)) {
+               x >>= 2;
+               r += 2;
+       }
+       if (!(x & 1)) {
+               x >>= 1;
+               r += 1;
+       }
+       return r;
+}
+
+/*
+ * fls: find last bit set.
+ */
+
+static __inline__ int generic_fls(int x)
+{
+       int r = 32;
+
+       if (!x)
+               return 0;
+       if (!(x & 0xffff0000u)) {
+               x <<= 16;
+               r -= 16;
+       }
+       if (!(x & 0xff000000u)) {
+               x <<= 8;
+               r -= 8;
+       }
+       if (!(x & 0xf0000000u)) {
+               x <<= 4;
+               r -= 4;
+       }
+       if (!(x & 0xc0000000u)) {
+               x <<= 2;
+               r -= 2;
+       }
+       if (!(x & 0x80000000u)) {
+               x <<= 1;
+               r -= 1;
+       }
+       return r;
+}
+
+/*
+ * Include this here because some architectures need generic_ffs/fls in
+ * scope
+ */
+#include <asm/bitops.h>
+
+static __inline__ int get_bitmask_order(unsigned int count)
+{
+       int order;
+       
+       order = fls(count);
+       return order;   /* We could be slightly more clever with -1 here... */
+}
+
+/*
+ * hweightN: returns the hamming weight (i.e. the number
+ * of bits set) of a N-bit word
+ */
+
+static inline unsigned int generic_hweight32(unsigned int w)
+{
+        unsigned int res = (w & 0x55555555) + ((w >> 1) & 0x55555555);
+        res = (res & 0x33333333) + ((res >> 2) & 0x33333333);
+        res = (res & 0x0F0F0F0F) + ((res >> 4) & 0x0F0F0F0F);
+        res = (res & 0x00FF00FF) + ((res >> 8) & 0x00FF00FF);
+        return (res & 0x0000FFFF) + ((res >> 16) & 0x0000FFFF);
+}
+
+static inline unsigned int generic_hweight16(unsigned int w)
+{
+        unsigned int res = (w & 0x5555) + ((w >> 1) & 0x5555);
+        res = (res & 0x3333) + ((res >> 2) & 0x3333);
+        res = (res & 0x0F0F) + ((res >> 4) & 0x0F0F);
+        return (res & 0x00FF) + ((res >> 8) & 0x00FF);
+}
+
+static inline unsigned int generic_hweight8(unsigned int w)
+{
+        unsigned int res = (w & 0x55) + ((w >> 1) & 0x55);
+        res = (res & 0x33) + ((res >> 2) & 0x33);
+        return (res & 0x0F) + ((res >> 4) & 0x0F);
+}
+
+static inline unsigned long generic_hweight64(__u64 w)
+{
+#if BITS_PER_LONG < 64
+       return generic_hweight32((unsigned int)(w >> 32)) +
+                               generic_hweight32((unsigned int)w);
+#else
+       u64 res;
+       res = (w & 0x5555555555555555ul) + ((w >> 1) & 0x5555555555555555ul);
+       res = (res & 0x3333333333333333ul) + ((res >> 2) & 
0x3333333333333333ul);
+       res = (res & 0x0F0F0F0F0F0F0F0Ful) + ((res >> 4) & 
0x0F0F0F0F0F0F0F0Ful);
+       res = (res & 0x00FF00FF00FF00FFul) + ((res >> 8) & 
0x00FF00FF00FF00FFul);
+       res = (res & 0x0000FFFF0000FFFFul) + ((res >> 16) & 
0x0000FFFF0000FFFFul);
+       return (res & 0x00000000FFFFFFFFul) + ((res >> 32) & 
0x00000000FFFFFFFFul);
+#endif
+}
+
+static inline unsigned long hweight_long(unsigned long w)
+{
+       return sizeof(w) == 4 ? generic_hweight32(w) : generic_hweight64(w);
+}
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/byteorder/generic.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/byteorder/generic.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,172 @@
+#ifndef _LINUX_BYTEORDER_GENERIC_H
+#define _LINUX_BYTEORDER_GENERIC_H
+
+/*
+ * linux/byteorder_generic.h
+ * Generic Byte-reordering support
+ *
+ * Francois-Rene Rideau <fare@xxxxxxxxx> 19970707
+ *    gathered all the good ideas from all asm-foo/byteorder.h into one file,
+ *    cleaned them up.
+ *    I hope it is compliant with non-GCC compilers.
+ *    I decided to put __BYTEORDER_HAS_U64__ in byteorder.h,
+ *    because I wasn't sure it would be ok to put it in types.h
+ *    Upgraded it to 2.1.43
+ * Francois-Rene Rideau <fare@xxxxxxxxx> 19971012
+ *    Upgraded it to 2.1.57
+ *    to please Linus T., replaced huge #ifdef's between little/big endian
+ *    by nestedly #include'd files.
+ * Francois-Rene Rideau <fare@xxxxxxxxx> 19971205
+ *    Made it to 2.1.71; now a facelift:
+ *    Put files under include/linux/byteorder/
+ *    Split swab from generic support.
+ *
+ * TODO:
+ *   = Regular kernel maintainers could also replace all these manual
+ *    byteswap macros that remain, disseminated among drivers,
+ *    after some grep or the sources...
+ *   = Linus might want to rename all these macros and files to fit his taste,
+ *    to fit his personal naming scheme.
+ *   = it seems that a few drivers would also appreciate
+ *    nybble swapping support...
+ *   = every architecture could add their byteswap macro in asm/byteorder.h
+ *    see how some architectures already do (i386, alpha, ppc, etc)
+ *   = cpu_to_beXX and beXX_to_cpu might some day need to be well
+ *    distinguished throughout the kernel. This is not the case currently,
+ *    since little endian, big endian, and pdp endian machines needn't it.
+ *    But this might be the case for, say, a port of Linux to 20/21 bit
+ *    architectures (and F21 Linux addict around?).
+ */
+
+/*
+ * The following macros are to be defined by <asm/byteorder.h>:
+ *
+ * Conversion of long and short int between network and host format
+ *     ntohl(__u32 x)
+ *     ntohs(__u16 x)
+ *     htonl(__u32 x)
+ *     htons(__u16 x)
+ * It seems that some programs (which? where? or perhaps a standard? POSIX?)
+ * might like the above to be functions, not macros (why?).
+ * if that's true, then detect them, and take measures.
+ * Anyway, the measure is: define only ___ntohl as a macro instead,
+ * and in a separate file, have
+ * unsigned long inline ntohl(x){return ___ntohl(x);}
+ *
+ * The same for constant arguments
+ *     __constant_ntohl(__u32 x)
+ *     __constant_ntohs(__u16 x)
+ *     __constant_htonl(__u32 x)
+ *     __constant_htons(__u16 x)
+ *
+ * Conversion of XX-bit integers (16- 32- or 64-)
+ * between native CPU format and little/big endian format
+ * 64-bit stuff only defined for proper architectures
+ *     cpu_to_[bl]eXX(__uXX x)
+ *     [bl]eXX_to_cpu(__uXX x)
+ *
+ * The same, but takes a pointer to the value to convert
+ *     cpu_to_[bl]eXXp(__uXX x)
+ *     [bl]eXX_to_cpup(__uXX x)
+ *
+ * The same, but change in situ
+ *     cpu_to_[bl]eXXs(__uXX x)
+ *     [bl]eXX_to_cpus(__uXX x)
+ *
+ * See asm-foo/byteorder.h for examples of how to provide
+ * architecture-optimized versions
+ *
+ */
+
+
+#if defined(__KERNEL__)
+/*
+ * inside the kernel, we can use nicknames;
+ * outside of it, we must avoid POSIX namespace pollution...
+ */
+#define cpu_to_le64 __cpu_to_le64
+#define le64_to_cpu __le64_to_cpu
+#define cpu_to_le32 __cpu_to_le32
+#define le32_to_cpu __le32_to_cpu
+#define cpu_to_le16 __cpu_to_le16
+#define le16_to_cpu __le16_to_cpu
+#define cpu_to_be64 __cpu_to_be64
+#define be64_to_cpu __be64_to_cpu
+#define cpu_to_be32 __cpu_to_be32
+#define be32_to_cpu __be32_to_cpu
+#define cpu_to_be16 __cpu_to_be16
+#define be16_to_cpu __be16_to_cpu
+#define cpu_to_le64p __cpu_to_le64p
+#define le64_to_cpup __le64_to_cpup
+#define cpu_to_le32p __cpu_to_le32p
+#define le32_to_cpup __le32_to_cpup
+#define cpu_to_le16p __cpu_to_le16p
+#define le16_to_cpup __le16_to_cpup
+#define cpu_to_be64p __cpu_to_be64p
+#define be64_to_cpup __be64_to_cpup
+#define cpu_to_be32p __cpu_to_be32p
+#define be32_to_cpup __be32_to_cpup
+#define cpu_to_be16p __cpu_to_be16p
+#define be16_to_cpup __be16_to_cpup
+#define cpu_to_le64s __cpu_to_le64s
+#define le64_to_cpus __le64_to_cpus
+#define cpu_to_le32s __cpu_to_le32s
+#define le32_to_cpus __le32_to_cpus
+#define cpu_to_le16s __cpu_to_le16s
+#define le16_to_cpus __le16_to_cpus
+#define cpu_to_be64s __cpu_to_be64s
+#define be64_to_cpus __be64_to_cpus
+#define cpu_to_be32s __cpu_to_be32s
+#define be32_to_cpus __be32_to_cpus
+#define cpu_to_be16s __cpu_to_be16s
+#define be16_to_cpus __be16_to_cpus
+#endif
+
+
+#if defined(__KERNEL__)
+/*
+ * Handle ntohl and suches. These have various compatibility
+ * issues - like we want to give the prototype even though we
+ * also have a macro for them in case some strange program
+ * wants to take the address of the thing or something..
+ *
+ * Note that these used to return a "long" in libc5, even though
+ * long is often 64-bit these days.. Thus the casts.
+ *
+ * They have to be macros in order to do the constant folding
+ * correctly - if the argument passed into a inline function
+ * it is no longer constant according to gcc..
+ */
+
+#undef ntohl
+#undef ntohs
+#undef htonl
+#undef htons
+
+/*
+ * Do the prototypes. Somebody might want to take the
+ * address or some such sick thing..
+ */
+extern __u32                   ntohl(__be32);
+extern __be32                  htonl(__u32);
+extern __u16                   ntohs(__be16);
+extern __be16                  htons(__u16);
+
+#if defined(__GNUC__) && (__GNUC__ >= 2) && defined(__OPTIMIZE__)
+
+#define ___htonl(x) __cpu_to_be32(x)
+#define ___htons(x) __cpu_to_be16(x)
+#define ___ntohl(x) __be32_to_cpu(x)
+#define ___ntohs(x) __be16_to_cpu(x)
+
+#define htonl(x) ___htonl(x)
+#define ntohl(x) ___ntohl(x)
+#define htons(x) ___htons(x)
+#define ntohs(x) ___ntohs(x)
+
+#endif /* OPTIMIZE */
+
+#endif /* KERNEL */
+
+
+#endif /* _LINUX_BYTEORDER_GENERIC_H */
diff -r b5196e075602 -r e3d811cca4e1 
xen/include/asm-ia64/linux/byteorder/little_endian.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/byteorder/little_endian.h      Tue Aug 16 
04:15:23 2005
@@ -0,0 +1,106 @@
+#ifndef _LINUX_BYTEORDER_LITTLE_ENDIAN_H
+#define _LINUX_BYTEORDER_LITTLE_ENDIAN_H
+
+#ifndef __LITTLE_ENDIAN
+#define __LITTLE_ENDIAN 1234
+#endif
+#ifndef __LITTLE_ENDIAN_BITFIELD
+#define __LITTLE_ENDIAN_BITFIELD
+#endif
+
+#include <linux/types.h>
+#include <linux/byteorder/swab.h>
+
+#define __constant_htonl(x) ((__force __be32)___constant_swab32((x)))
+#define __constant_ntohl(x) ___constant_swab32((__force __be32)(x))
+#define __constant_htons(x) ((__force __be16)___constant_swab16((x)))
+#define __constant_ntohs(x) ___constant_swab16((__force __be16)(x))
+#define __constant_cpu_to_le64(x) ((__force __le64)(__u64)(x))
+#define __constant_le64_to_cpu(x) ((__force __u64)(__le64)(x))
+#define __constant_cpu_to_le32(x) ((__force __le32)(__u32)(x))
+#define __constant_le32_to_cpu(x) ((__force __u32)(__le32)(x))
+#define __constant_cpu_to_le16(x) ((__force __le16)(__u16)(x))
+#define __constant_le16_to_cpu(x) ((__force __u16)(__le16)(x))
+#define __constant_cpu_to_be64(x) ((__force __be64)___constant_swab64((x)))
+#define __constant_be64_to_cpu(x) ___constant_swab64((__force 
__u64)(__be64)(x))
+#define __constant_cpu_to_be32(x) ((__force __be32)___constant_swab32((x)))
+#define __constant_be32_to_cpu(x) ___constant_swab32((__force 
__u32)(__be32)(x))
+#define __constant_cpu_to_be16(x) ((__force __be16)___constant_swab16((x)))
+#define __constant_be16_to_cpu(x) ___constant_swab16((__force 
__u16)(__be16)(x))
+#define __cpu_to_le64(x) ((__force __le64)(__u64)(x))
+#define __le64_to_cpu(x) ((__force __u64)(__le64)(x))
+#define __cpu_to_le32(x) ((__force __le32)(__u32)(x))
+#define __le32_to_cpu(x) ((__force __u32)(__le32)(x))
+#define __cpu_to_le16(x) ((__force __le16)(__u16)(x))
+#define __le16_to_cpu(x) ((__force __u16)(__le16)(x))
+#define __cpu_to_be64(x) ((__force __be64)__swab64((x)))
+#define __be64_to_cpu(x) __swab64((__force __u64)(__be64)(x))
+#define __cpu_to_be32(x) ((__force __be32)__swab32((x)))
+#define __be32_to_cpu(x) __swab32((__force __u32)(__be32)(x))
+#define __cpu_to_be16(x) ((__force __be16)__swab16((x)))
+#define __be16_to_cpu(x) __swab16((__force __u16)(__be16)(x))
+
+static inline __le64 __cpu_to_le64p(const __u64 *p)
+{
+       return (__force __le64)*p;
+}
+static inline __u64 __le64_to_cpup(const __le64 *p)
+{
+       return (__force __u64)*p;
+}
+static inline __le32 __cpu_to_le32p(const __u32 *p)
+{
+       return (__force __le32)*p;
+}
+static inline __u32 __le32_to_cpup(const __le32 *p)
+{
+       return (__force __u32)*p;
+}
+static inline __le16 __cpu_to_le16p(const __u16 *p)
+{
+       return (__force __le16)*p;
+}
+static inline __u16 __le16_to_cpup(const __le16 *p)
+{
+       return (__force __u16)*p;
+}
+static inline __be64 __cpu_to_be64p(const __u64 *p)
+{
+       return (__force __be64)__swab64p(p);
+}
+static inline __u64 __be64_to_cpup(const __be64 *p)
+{
+       return __swab64p((__u64 *)p);
+}
+static inline __be32 __cpu_to_be32p(const __u32 *p)
+{
+       return (__force __be32)__swab32p(p);
+}
+static inline __u32 __be32_to_cpup(const __be32 *p)
+{
+       return __swab32p((__u32 *)p);
+}
+static inline __be16 __cpu_to_be16p(const __u16 *p)
+{
+       return (__force __be16)__swab16p(p);
+}
+static inline __u16 __be16_to_cpup(const __be16 *p)
+{
+       return __swab16p((__u16 *)p);
+}
+#define __cpu_to_le64s(x) do {} while (0)
+#define __le64_to_cpus(x) do {} while (0)
+#define __cpu_to_le32s(x) do {} while (0)
+#define __le32_to_cpus(x) do {} while (0)
+#define __cpu_to_le16s(x) do {} while (0)
+#define __le16_to_cpus(x) do {} while (0)
+#define __cpu_to_be64s(x) __swab64s((x))
+#define __be64_to_cpus(x) __swab64s((x))
+#define __cpu_to_be32s(x) __swab32s((x))
+#define __be32_to_cpus(x) __swab32s((x))
+#define __cpu_to_be16s(x) __swab16s((x))
+#define __be16_to_cpus(x) __swab16s((x))
+
+#include <linux/byteorder/generic.h>
+
+#endif /* _LINUX_BYTEORDER_LITTLE_ENDIAN_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/byteorder/swab.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/byteorder/swab.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,192 @@
+#ifndef _LINUX_BYTEORDER_SWAB_H
+#define _LINUX_BYTEORDER_SWAB_H
+
+/*
+ * linux/byteorder/swab.h
+ * Byte-swapping, independently from CPU endianness
+ *     swabXX[ps]?(foo)
+ *
+ * Francois-Rene Rideau <fare@xxxxxxxxx> 19971205
+ *    separated swab functions from cpu_to_XX,
+ *    to clean up support for bizarre-endian architectures.
+ *
+ * See asm-i386/byteorder.h and suches for examples of how to provide
+ * architecture-dependent optimized versions
+ *
+ */
+
+#include <linux/compiler.h>
+
+/* casts are necessary for constants, because we never know how for sure
+ * how U/UL/ULL map to __u16, __u32, __u64. At least not in a portable way.
+ */
+#define ___swab16(x) \
+({ \
+       __u16 __x = (x); \
+       ((__u16)( \
+               (((__u16)(__x) & (__u16)0x00ffU) << 8) | \
+               (((__u16)(__x) & (__u16)0xff00U) >> 8) )); \
+})
+
+#define ___swab32(x) \
+({ \
+       __u32 __x = (x); \
+       ((__u32)( \
+               (((__u32)(__x) & (__u32)0x000000ffUL) << 24) | \
+               (((__u32)(__x) & (__u32)0x0000ff00UL) <<  8) | \
+               (((__u32)(__x) & (__u32)0x00ff0000UL) >>  8) | \
+               (((__u32)(__x) & (__u32)0xff000000UL) >> 24) )); \
+})
+
+#define ___swab64(x) \
+({ \
+       __u64 __x = (x); \
+       ((__u64)( \
+               (__u64)(((__u64)(__x) & (__u64)0x00000000000000ffULL) << 56) | \
+               (__u64)(((__u64)(__x) & (__u64)0x000000000000ff00ULL) << 40) | \
+               (__u64)(((__u64)(__x) & (__u64)0x0000000000ff0000ULL) << 24) | \
+               (__u64)(((__u64)(__x) & (__u64)0x00000000ff000000ULL) <<  8) | \
+               (__u64)(((__u64)(__x) & (__u64)0x000000ff00000000ULL) >>  8) | \
+               (__u64)(((__u64)(__x) & (__u64)0x0000ff0000000000ULL) >> 24) | \
+               (__u64)(((__u64)(__x) & (__u64)0x00ff000000000000ULL) >> 40) | \
+               (__u64)(((__u64)(__x) & (__u64)0xff00000000000000ULL) >> 56) 
)); \
+})
+
+#define ___constant_swab16(x) \
+       ((__u16)( \
+               (((__u16)(x) & (__u16)0x00ffU) << 8) | \
+               (((__u16)(x) & (__u16)0xff00U) >> 8) ))
+#define ___constant_swab32(x) \
+       ((__u32)( \
+               (((__u32)(x) & (__u32)0x000000ffUL) << 24) | \
+               (((__u32)(x) & (__u32)0x0000ff00UL) <<  8) | \
+               (((__u32)(x) & (__u32)0x00ff0000UL) >>  8) | \
+               (((__u32)(x) & (__u32)0xff000000UL) >> 24) ))
+#define ___constant_swab64(x) \
+       ((__u64)( \
+               (__u64)(((__u64)(x) & (__u64)0x00000000000000ffULL) << 56) | \
+               (__u64)(((__u64)(x) & (__u64)0x000000000000ff00ULL) << 40) | \
+               (__u64)(((__u64)(x) & (__u64)0x0000000000ff0000ULL) << 24) | \
+               (__u64)(((__u64)(x) & (__u64)0x00000000ff000000ULL) <<  8) | \
+               (__u64)(((__u64)(x) & (__u64)0x000000ff00000000ULL) >>  8) | \
+               (__u64)(((__u64)(x) & (__u64)0x0000ff0000000000ULL) >> 24) | \
+               (__u64)(((__u64)(x) & (__u64)0x00ff000000000000ULL) >> 40) | \
+               (__u64)(((__u64)(x) & (__u64)0xff00000000000000ULL) >> 56) ))
+
+/*
+ * provide defaults when no architecture-specific optimization is detected
+ */
+#ifndef __arch__swab16
+#  define __arch__swab16(x) ({ __u16 __tmp = (x) ; ___swab16(__tmp); })
+#endif
+#ifndef __arch__swab32
+#  define __arch__swab32(x) ({ __u32 __tmp = (x) ; ___swab32(__tmp); })
+#endif
+#ifndef __arch__swab64
+#  define __arch__swab64(x) ({ __u64 __tmp = (x) ; ___swab64(__tmp); })
+#endif
+
+#ifndef __arch__swab16p
+#  define __arch__swab16p(x) __arch__swab16(*(x))
+#endif
+#ifndef __arch__swab32p
+#  define __arch__swab32p(x) __arch__swab32(*(x))
+#endif
+#ifndef __arch__swab64p
+#  define __arch__swab64p(x) __arch__swab64(*(x))
+#endif
+
+#ifndef __arch__swab16s
+#  define __arch__swab16s(x) do { *(x) = __arch__swab16p((x)); } while (0)
+#endif
+#ifndef __arch__swab32s
+#  define __arch__swab32s(x) do { *(x) = __arch__swab32p((x)); } while (0)
+#endif
+#ifndef __arch__swab64s
+#  define __arch__swab64s(x) do { *(x) = __arch__swab64p((x)); } while (0)
+#endif
+
+
+/*
+ * Allow constant folding
+ */
+#if defined(__GNUC__) && (__GNUC__ >= 2) && defined(__OPTIMIZE__)
+#  define __swab16(x) \
+(__builtin_constant_p((__u16)(x)) ? \
+ ___swab16((x)) : \
+ __fswab16((x)))
+#  define __swab32(x) \
+(__builtin_constant_p((__u32)(x)) ? \
+ ___swab32((x)) : \
+ __fswab32((x)))
+#  define __swab64(x) \
+(__builtin_constant_p((__u64)(x)) ? \
+ ___swab64((x)) : \
+ __fswab64((x)))
+#else
+#  define __swab16(x) __fswab16(x)
+#  define __swab32(x) __fswab32(x)
+#  define __swab64(x) __fswab64(x)
+#endif /* OPTIMIZE */
+
+
+static __inline__ __attribute_const__ __u16 __fswab16(__u16 x)
+{
+       return __arch__swab16(x);
+}
+static __inline__ __u16 __swab16p(const __u16 *x)
+{
+       return __arch__swab16p(x);
+}
+static __inline__ void __swab16s(__u16 *addr)
+{
+       __arch__swab16s(addr);
+}
+
+static __inline__ __attribute_const__ __u32 __fswab32(__u32 x)
+{
+       return __arch__swab32(x);
+}
+static __inline__ __u32 __swab32p(const __u32 *x)
+{
+       return __arch__swab32p(x);
+}
+static __inline__ void __swab32s(__u32 *addr)
+{
+       __arch__swab32s(addr);
+}
+
+#ifdef __BYTEORDER_HAS_U64__
+static __inline__ __attribute_const__ __u64 __fswab64(__u64 x)
+{
+#  ifdef __SWAB_64_THRU_32__
+       __u32 h = x >> 32;
+        __u32 l = x & ((1ULL<<32)-1);
+        return (((__u64)__swab32(l)) << 32) | ((__u64)(__swab32(h)));
+#  else
+       return __arch__swab64(x);
+#  endif
+}
+static __inline__ __u64 __swab64p(const __u64 *x)
+{
+       return __arch__swab64p(x);
+}
+static __inline__ void __swab64s(__u64 *addr)
+{
+       __arch__swab64s(addr);
+}
+#endif /* __BYTEORDER_HAS_U64__ */
+
+#if defined(__KERNEL__)
+#define swab16 __swab16
+#define swab32 __swab32
+#define swab64 __swab64
+#define swab16p __swab16p
+#define swab32p __swab32p
+#define swab64p __swab64p
+#define swab16s __swab16s
+#define swab32s __swab32s
+#define swab64s __swab64s
+#endif
+
+#endif /* _LINUX_BYTEORDER_SWAB_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/dma-mapping.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/dma-mapping.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,56 @@
+#ifndef _ASM_LINUX_DMA_MAPPING_H
+#define _ASM_LINUX_DMA_MAPPING_H
+
+#include <linux/device.h>
+#include <linux/err.h>
+
+/* These definitions mirror those in pci.h, so they can be used
+ * interchangeably with their PCI_ counterparts */
+enum dma_data_direction {
+       DMA_BIDIRECTIONAL = 0,
+       DMA_TO_DEVICE = 1,
+       DMA_FROM_DEVICE = 2,
+       DMA_NONE = 3,
+};
+
+#define DMA_64BIT_MASK 0xffffffffffffffffULL
+#define DMA_32BIT_MASK 0x00000000ffffffffULL
+
+#include <asm/dma-mapping.h>
+
+/* Backwards compat, remove in 2.7.x */
+#define dma_sync_single                dma_sync_single_for_cpu
+#define dma_sync_sg            dma_sync_sg_for_cpu
+
+extern u64 dma_get_required_mask(struct device *dev);
+
+/* flags for the coherent memory api */
+#define        DMA_MEMORY_MAP                  0x01
+#define DMA_MEMORY_IO                  0x02
+#define DMA_MEMORY_INCLUDES_CHILDREN   0x04
+#define DMA_MEMORY_EXCLUSIVE           0x08
+
+#ifndef ARCH_HAS_DMA_DECLARE_COHERENT_MEMORY
+static inline int
+dma_declare_coherent_memory(struct device *dev, dma_addr_t bus_addr,
+                           dma_addr_t device_addr, size_t size, int flags)
+{
+       return 0;
+}
+
+static inline void
+dma_release_declared_memory(struct device *dev)
+{
+}
+
+static inline void *
+dma_mark_declared_memory_occupied(struct device *dev,
+                                 dma_addr_t device_addr, size_t size)
+{
+       return ERR_PTR(-EBUSY);
+}
+#endif
+
+#endif
+
+
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/efi.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/efi.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,399 @@
+#ifndef _LINUX_EFI_H
+#define _LINUX_EFI_H
+
+/*
+ * Extensible Firmware Interface
+ * Based on 'Extensible Firmware Interface Specification' version 0.9, April 
30, 1999
+ *
+ * Copyright (C) 1999 VA Linux Systems
+ * Copyright (C) 1999 Walt Drummond <drummond@xxxxxxxxxxx>
+ * Copyright (C) 1999, 2002-2003 Hewlett-Packard Co.
+ *     David Mosberger-Tang <davidm@xxxxxxxxxx>
+ *     Stephane Eranian <eranian@xxxxxxxxxx>
+ */
+#include <linux/init.h>
+#include <linux/string.h>
+#include <linux/time.h>
+#include <linux/types.h>
+#include <linux/proc_fs.h>
+#include <linux/rtc.h>
+#include <linux/ioport.h>
+
+#include <asm/page.h>
+#include <asm/system.h>
+
+#define EFI_SUCCESS            0
+#define EFI_LOAD_ERROR          ( 1 | (1UL << (BITS_PER_LONG-1)))
+#define EFI_INVALID_PARAMETER  ( 2 | (1UL << (BITS_PER_LONG-1)))
+#define EFI_UNSUPPORTED                ( 3 | (1UL << (BITS_PER_LONG-1)))
+#define EFI_BAD_BUFFER_SIZE     ( 4 | (1UL << (BITS_PER_LONG-1)))
+#define EFI_BUFFER_TOO_SMALL   ( 5 | (1UL << (BITS_PER_LONG-1)))
+#define EFI_NOT_FOUND          (14 | (1UL << (BITS_PER_LONG-1)))
+
+typedef unsigned long efi_status_t;
+typedef u8 efi_bool_t;
+typedef u16 efi_char16_t;              /* UNICODE character */
+
+
+typedef struct {
+       u8 b[16];
+} efi_guid_t;
+
+#define EFI_GUID(a,b,c,d0,d1,d2,d3,d4,d5,d6,d7) \
+((efi_guid_t) \
+{{ (a) & 0xff, ((a) >> 8) & 0xff, ((a) >> 16) & 0xff, ((a) >> 24) & 0xff, \
+  (b) & 0xff, ((b) >> 8) & 0xff, \
+  (c) & 0xff, ((c) >> 8) & 0xff, \
+  (d0), (d1), (d2), (d3), (d4), (d5), (d6), (d7) }})
+
+/*
+ * Generic EFI table header
+ */
+typedef        struct {
+       u64 signature;
+       u32 revision;
+       u32 headersize;
+       u32 crc32;
+       u32 reserved;
+} efi_table_hdr_t;
+
+/*
+ * Memory map descriptor:
+ */
+
+/* Memory types: */
+#define EFI_RESERVED_TYPE               0
+#define EFI_LOADER_CODE                         1
+#define EFI_LOADER_DATA                         2
+#define EFI_BOOT_SERVICES_CODE          3
+#define EFI_BOOT_SERVICES_DATA          4
+#define EFI_RUNTIME_SERVICES_CODE       5
+#define EFI_RUNTIME_SERVICES_DATA       6
+#define EFI_CONVENTIONAL_MEMORY                 7
+#define EFI_UNUSABLE_MEMORY             8
+#define EFI_ACPI_RECLAIM_MEMORY                 9
+#define EFI_ACPI_MEMORY_NVS            10
+#define EFI_MEMORY_MAPPED_IO           11
+#define EFI_MEMORY_MAPPED_IO_PORT_SPACE        12
+#define EFI_PAL_CODE                   13
+#define EFI_MAX_MEMORY_TYPE            14
+
+/* Attribute values: */
+#define EFI_MEMORY_UC          ((u64)0x0000000000000001ULL)    /* uncached */
+#define EFI_MEMORY_WC          ((u64)0x0000000000000002ULL)    /* 
write-coalescing */
+#define EFI_MEMORY_WT          ((u64)0x0000000000000004ULL)    /* 
write-through */
+#define EFI_MEMORY_WB          ((u64)0x0000000000000008ULL)    /* write-back */
+#define EFI_MEMORY_WP          ((u64)0x0000000000001000ULL)    /* 
write-protect */
+#define EFI_MEMORY_RP          ((u64)0x0000000000002000ULL)    /* read-protect 
*/
+#define EFI_MEMORY_XP          ((u64)0x0000000000004000ULL)    /* 
execute-protect */
+#define EFI_MEMORY_RUNTIME     ((u64)0x8000000000000000ULL)    /* range 
requires runtime mapping */
+#define EFI_MEMORY_DESCRIPTOR_VERSION  1
+
+#define EFI_PAGE_SHIFT         12
+
+/*
+ * For current x86 implementations of EFI, there is
+ * additional padding in the mem descriptors.  This is not
+ * the case in ia64.  Need to have this fixed in the f/w.
+ */
+typedef struct {
+       u32 type;
+       u32 pad;
+       u64 phys_addr;
+       u64 virt_addr;
+       u64 num_pages;
+       u64 attribute;
+#if defined (__i386__)
+       u64 pad1;
+#endif
+} efi_memory_desc_t;
+
+typedef int (*efi_freemem_callback_t) (unsigned long start, unsigned long end, 
void *arg);
+
+/*
+ * Types and defines for Time Services
+ */
+#define EFI_TIME_ADJUST_DAYLIGHT 0x1
+#define EFI_TIME_IN_DAYLIGHT     0x2
+#define EFI_UNSPECIFIED_TIMEZONE 0x07ff
+
+typedef struct {
+       u16 year;
+       u8 month;
+       u8 day;
+       u8 hour;
+       u8 minute;
+       u8 second;
+       u8 pad1;
+       u32 nanosecond;
+       s16 timezone;
+       u8 daylight;
+       u8 pad2;
+} efi_time_t;
+
+typedef struct {
+       u32 resolution;
+       u32 accuracy;
+       u8 sets_to_zero;
+} efi_time_cap_t;
+
+/*
+ * Types and defines for EFI ResetSystem
+ */
+#define EFI_RESET_COLD 0
+#define EFI_RESET_WARM 1
+#define EFI_RESET_SHUTDOWN 2
+
+/*
+ * EFI Runtime Services table
+ */
+#define EFI_RUNTIME_SERVICES_SIGNATURE ((u64)0x5652453544e5552ULL)
+#define EFI_RUNTIME_SERVICES_REVISION  0x00010000
+
+typedef struct {
+       efi_table_hdr_t hdr;
+       unsigned long get_time;
+       unsigned long set_time;
+       unsigned long get_wakeup_time;
+       unsigned long set_wakeup_time;
+       unsigned long set_virtual_address_map;
+       unsigned long convert_pointer;
+       unsigned long get_variable;
+       unsigned long get_next_variable;
+       unsigned long set_variable;
+       unsigned long get_next_high_mono_count;
+       unsigned long reset_system;
+} efi_runtime_services_t;
+
+typedef efi_status_t efi_get_time_t (efi_time_t *tm, efi_time_cap_t *tc);
+typedef efi_status_t efi_set_time_t (efi_time_t *tm);
+typedef efi_status_t efi_get_wakeup_time_t (efi_bool_t *enabled, efi_bool_t 
*pending,
+                                           efi_time_t *tm);
+typedef efi_status_t efi_set_wakeup_time_t (efi_bool_t enabled, efi_time_t 
*tm);
+typedef efi_status_t efi_get_variable_t (efi_char16_t *name, efi_guid_t 
*vendor, u32 *attr,
+                                        unsigned long *data_size, void *data);
+typedef efi_status_t efi_get_next_variable_t (unsigned long *name_size, 
efi_char16_t *name,
+                                             efi_guid_t *vendor);
+typedef efi_status_t efi_set_variable_t (efi_char16_t *name, efi_guid_t 
*vendor, 
+                                        unsigned long attr, unsigned long 
data_size, 
+                                        void *data);
+typedef efi_status_t efi_get_next_high_mono_count_t (u32 *count);
+typedef void efi_reset_system_t (int reset_type, efi_status_t status,
+                                unsigned long data_size, efi_char16_t *data);
+typedef efi_status_t efi_set_virtual_address_map_t (unsigned long 
memory_map_size,
+                                               unsigned long descriptor_size,
+                                               u32 descriptor_version,
+                                               efi_memory_desc_t *virtual_map);
+
+/*
+ *  EFI Configuration Table and GUID definitions
+ */
+#define NULL_GUID \
+    EFI_GUID(  0x00000000, 0x0000, 0x0000, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 
0x00, 0x00 )
+
+#define MPS_TABLE_GUID    \
+    EFI_GUID(  0xeb9d2d2f, 0x2d88, 0x11d3, 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 
0xc1, 0x4d )
+
+#define ACPI_TABLE_GUID    \
+    EFI_GUID(  0xeb9d2d30, 0x2d88, 0x11d3, 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 
0xc1, 0x4d )
+
+#define ACPI_20_TABLE_GUID    \
+    EFI_GUID(  0x8868e871, 0xe4f1, 0x11d3, 0xbc, 0x22, 0x0, 0x80, 0xc7, 0x3c, 
0x88, 0x81 )
+
+#define SMBIOS_TABLE_GUID    \
+    EFI_GUID(  0xeb9d2d31, 0x2d88, 0x11d3, 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 
0xc1, 0x4d )
+
+#define SAL_SYSTEM_TABLE_GUID    \
+    EFI_GUID(  0xeb9d2d32, 0x2d88, 0x11d3, 0x9a, 0x16, 0x0, 0x90, 0x27, 0x3f, 
0xc1, 0x4d )
+
+#define HCDP_TABLE_GUID        \
+    EFI_GUID(  0xf951938d, 0x620b, 0x42ef, 0x82, 0x79, 0xa8, 0x4b, 0x79, 0x61, 
0x78, 0x98 )
+
+#define UGA_IO_PROTOCOL_GUID \
+    EFI_GUID(  0x61a4d49e, 0x6f68, 0x4f1b, 0xb9, 0x22, 0xa8, 0x6e, 0xed, 0xb, 
0x7, 0xa2 )
+
+#define EFI_GLOBAL_VARIABLE_GUID \
+    EFI_GUID(  0x8be4df61, 0x93ca, 0x11d2, 0xaa, 0x0d, 0x00, 0xe0, 0x98, 0x03, 
0x2b, 0x8c )
+
+typedef struct {
+       efi_guid_t guid;
+       unsigned long table;
+} efi_config_table_t;
+
+#define EFI_SYSTEM_TABLE_SIGNATURE ((u64)0x5453595320494249ULL)
+#define EFI_SYSTEM_TABLE_REVISION  ((1 << 16) | 00)
+
+typedef struct {
+       efi_table_hdr_t hdr;
+       unsigned long fw_vendor;        /* physical addr of CHAR16 vendor 
string */
+       u32 fw_revision;
+       unsigned long con_in_handle;
+       unsigned long con_in;
+       unsigned long con_out_handle;
+       unsigned long con_out;
+       unsigned long stderr_handle;
+       unsigned long stderr;
+       efi_runtime_services_t *runtime;
+       unsigned long boottime;
+       unsigned long nr_tables;
+       unsigned long tables;
+} efi_system_table_t;
+
+struct efi_memory_map {
+       efi_memory_desc_t *phys_map;
+       efi_memory_desc_t *map;
+       int nr_map;
+       unsigned long desc_version;
+};
+
+/*
+ * All runtime access to EFI goes through this structure:
+ */
+extern struct efi {
+       efi_system_table_t *systab;     /* EFI system table */
+       void *mps;                      /* MPS table */
+       void *acpi;                     /* ACPI table  (IA64 ext 0.71) */
+       void *acpi20;                   /* ACPI table  (ACPI 2.0) */
+       void *smbios;                   /* SM BIOS table */
+       void *sal_systab;               /* SAL system table */
+       void *boot_info;                /* boot info table */
+       void *hcdp;                     /* HCDP table */
+       void *uga;                      /* UGA table */
+       efi_get_time_t *get_time;
+       efi_set_time_t *set_time;
+       efi_get_wakeup_time_t *get_wakeup_time;
+       efi_set_wakeup_time_t *set_wakeup_time;
+       efi_get_variable_t *get_variable;
+       efi_get_next_variable_t *get_next_variable;
+       efi_set_variable_t *set_variable;
+       efi_get_next_high_mono_count_t *get_next_high_mono_count;
+       efi_reset_system_t *reset_system;
+       efi_set_virtual_address_map_t *set_virtual_address_map;
+} efi;
+
+static inline int
+efi_guidcmp (efi_guid_t left, efi_guid_t right)
+{
+       return memcmp(&left, &right, sizeof (efi_guid_t));
+}
+
+static inline char *
+efi_guid_unparse(efi_guid_t *guid, char *out)
+{
+       sprintf(out, 
"%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x",
+               guid->b[3], guid->b[2], guid->b[1], guid->b[0],
+               guid->b[5], guid->b[4], guid->b[7], guid->b[6],
+               guid->b[8], guid->b[9], guid->b[10], guid->b[11],
+               guid->b[12], guid->b[13], guid->b[14], guid->b[15]);
+        return out;
+}
+
+extern void efi_init (void);
+extern void *efi_get_pal_addr (void);
+extern void efi_map_pal_code (void);
+extern void efi_map_memmap(void);
+extern void efi_memmap_walk (efi_freemem_callback_t callback, void *arg);
+extern void efi_gettimeofday (struct timespec *ts);
+extern void efi_enter_virtual_mode (void);     /* switch EFI to virtual mode, 
if possible */
+extern u64 efi_get_iobase (void);
+extern u32 efi_mem_type (unsigned long phys_addr);
+extern u64 efi_mem_attributes (unsigned long phys_addr);
+extern int __init efi_uart_console_only (void);
+extern void efi_initialize_iomem_resources(struct resource *code_resource,
+                                       struct resource *data_resource);
+extern efi_status_t phys_efi_get_time(efi_time_t *tm, efi_time_cap_t *tc);
+extern unsigned long __init efi_get_time(void);
+extern int __init efi_set_rtc_mmss(unsigned long nowtime);
+extern struct efi_memory_map memmap;
+
+/**
+ * efi_range_is_wc - check the WC bit on an address range
+ * @start: starting kvirt address
+ * @len: length of range
+ *
+ * Consult the EFI memory map and make sure it's ok to set this range WC.
+ * Returns true or false.
+ */
+static inline int efi_range_is_wc(unsigned long start, unsigned long len)
+{
+       int i;
+
+       for (i = 0; i < len; i += (1UL << EFI_PAGE_SHIFT)) {
+               unsigned long paddr = __pa(start + i);
+               if (!(efi_mem_attributes(paddr) & EFI_MEMORY_WC))
+                       return 0;
+       }
+       /* The range checked out */
+       return 1;
+}
+
+#ifdef CONFIG_EFI_PCDP
+extern int __init efi_setup_pcdp_console(char *);
+#endif
+
+/*
+ * We play games with efi_enabled so that the compiler will, if possible, 
remove
+ * EFI-related code altogether.
+ */
+#ifdef CONFIG_EFI
+# ifdef CONFIG_X86
+   extern int efi_enabled;
+# else
+#  define efi_enabled 1
+# endif
+#else
+# define efi_enabled 0
+#endif
+
+/*
+ * Variable Attributes
+ */
+#define EFI_VARIABLE_NON_VOLATILE       0x0000000000000001
+#define EFI_VARIABLE_BOOTSERVICE_ACCESS 0x0000000000000002
+#define EFI_VARIABLE_RUNTIME_ACCESS     0x0000000000000004
+
+/*
+ * EFI Device Path information
+ */
+#define EFI_DEV_HW                     0x01
+#define  EFI_DEV_PCI                            1
+#define  EFI_DEV_PCCARD                                 2
+#define  EFI_DEV_MEM_MAPPED                     3
+#define  EFI_DEV_VENDOR                                 4
+#define  EFI_DEV_CONTROLLER                     5
+#define EFI_DEV_ACPI                   0x02
+#define   EFI_DEV_BASIC_ACPI                    1
+#define   EFI_DEV_EXPANDED_ACPI                         2
+#define EFI_DEV_MSG                    0x03
+#define   EFI_DEV_MSG_ATAPI                     1
+#define   EFI_DEV_MSG_SCSI                      2
+#define   EFI_DEV_MSG_FC                        3
+#define   EFI_DEV_MSG_1394                      4
+#define   EFI_DEV_MSG_USB                       5
+#define   EFI_DEV_MSG_USB_CLASS                        15
+#define   EFI_DEV_MSG_I20                       6
+#define   EFI_DEV_MSG_MAC                      11
+#define   EFI_DEV_MSG_IPV4                     12
+#define   EFI_DEV_MSG_IPV6                     13
+#define   EFI_DEV_MSG_INFINIBAND                9
+#define   EFI_DEV_MSG_UART                     14
+#define   EFI_DEV_MSG_VENDOR                   10
+#define EFI_DEV_MEDIA                  0x04
+#define   EFI_DEV_MEDIA_HARD_DRIVE              1
+#define   EFI_DEV_MEDIA_CDROM                   2
+#define   EFI_DEV_MEDIA_VENDOR                  3
+#define   EFI_DEV_MEDIA_FILE                    4
+#define   EFI_DEV_MEDIA_PROTOCOL                5
+#define EFI_DEV_BIOS_BOOT              0x05
+#define EFI_DEV_END_PATH               0x7F
+#define EFI_DEV_END_PATH2              0xFF
+#define   EFI_DEV_END_INSTANCE                 0x01
+#define   EFI_DEV_END_ENTIRE                   0xFF
+
+struct efi_generic_dev_path {
+       u8 type;
+       u8 sub_type;
+       u16 length;
+} __attribute ((packed));
+
+#endif /* _LINUX_EFI_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/err.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/err.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,31 @@
+#ifndef _LINUX_ERR_H
+#define _LINUX_ERR_H
+
+#include <linux/compiler.h>
+
+#include <asm/errno.h>
+
+/*
+ * Kernel pointers have redundant information, so we can use a
+ * scheme where we can return either an error code or a dentry
+ * pointer with the same return value.
+ *
+ * This should be a per-architecture thing, to allow different
+ * error and pointer decisions.
+ */
+static inline void *ERR_PTR(long error)
+{
+       return (void *) error;
+}
+
+static inline long PTR_ERR(const void *ptr)
+{
+       return (long) ptr;
+}
+
+static inline long IS_ERR(const void *ptr)
+{
+       return unlikely((unsigned long)ptr > (unsigned long)-1000L);
+}
+
+#endif /* _LINUX_ERR_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/gfp.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/gfp.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,134 @@
+#ifndef __LINUX_GFP_H
+#define __LINUX_GFP_H
+
+#include <linux/mmzone.h>
+#include <linux/stddef.h>
+#include <linux/linkage.h>
+#include <linux/config.h>
+
+struct vm_area_struct;
+
+/*
+ * GFP bitmasks..
+ */
+/* Zone modifiers in GFP_ZONEMASK (see linux/mmzone.h - low two bits) */
+#define __GFP_DMA      0x01
+#define __GFP_HIGHMEM  0x02
+
+/*
+ * Action modifiers - doesn't change the zoning
+ *
+ * __GFP_REPEAT: Try hard to allocate the memory, but the allocation attempt
+ * _might_ fail.  This depends upon the particular VM implementation.
+ *
+ * __GFP_NOFAIL: The VM implementation _must_ retry infinitely: the caller
+ * cannot handle allocation failures.
+ *
+ * __GFP_NORETRY: The VM implementation must not retry indefinitely.
+ */
+#define __GFP_WAIT     0x10    /* Can wait and reschedule? */
+#define __GFP_HIGH     0x20    /* Should access emergency pools? */
+#define __GFP_IO       0x40    /* Can start physical IO? */
+#define __GFP_FS       0x80    /* Can call down to low-level FS? */
+#define __GFP_COLD     0x100   /* Cache-cold page required */
+#define __GFP_NOWARN   0x200   /* Suppress page allocation failure warning */
+#define __GFP_REPEAT   0x400   /* Retry the allocation.  Might fail */
+#define __GFP_NOFAIL   0x800   /* Retry for ever.  Cannot fail */
+#define __GFP_NORETRY  0x1000  /* Do not retry.  Might fail */
+#define __GFP_NO_GROW  0x2000  /* Slab internal usage */
+#define __GFP_COMP     0x4000  /* Add compound page metadata */
+#define __GFP_ZERO     0x8000  /* Return zeroed page on success */
+
+#define __GFP_BITS_SHIFT 16    /* Room for 16 __GFP_FOO bits */
+#define __GFP_BITS_MASK ((1 << __GFP_BITS_SHIFT) - 1)
+
+/* if you forget to add the bitmask here kernel will crash, period */
+#define GFP_LEVEL_MASK (__GFP_WAIT|__GFP_HIGH|__GFP_IO|__GFP_FS| \
+                       __GFP_COLD|__GFP_NOWARN|__GFP_REPEAT| \
+                       __GFP_NOFAIL|__GFP_NORETRY|__GFP_NO_GROW|__GFP_COMP)
+
+#define GFP_ATOMIC     (__GFP_HIGH)
+#define GFP_NOIO       (__GFP_WAIT)
+#define GFP_NOFS       (__GFP_WAIT | __GFP_IO)
+#define GFP_KERNEL     (__GFP_WAIT | __GFP_IO | __GFP_FS)
+#define GFP_USER       (__GFP_WAIT | __GFP_IO | __GFP_FS)
+#define GFP_HIGHUSER   (__GFP_WAIT | __GFP_IO | __GFP_FS | __GFP_HIGHMEM)
+
+/* Flag - indicates that the buffer will be suitable for DMA.  Ignored on some
+   platforms, used as appropriate on others */
+
+#define GFP_DMA                __GFP_DMA
+
+
+/*
+ * There is only one page-allocator function, and two main namespaces to
+ * it. The alloc_page*() variants return 'struct page *' and as such
+ * can allocate highmem pages, the *get*page*() variants return
+ * virtual kernel addresses to the allocated page(s).
+ */
+
+/*
+ * We get the zone list from the current node and the gfp_mask.
+ * This zone list contains a maximum of MAXNODES*MAX_NR_ZONES zones.
+ *
+ * For the normal case of non-DISCONTIGMEM systems the NODE_DATA() gets
+ * optimized to &contig_page_data at compile-time.
+ */
+
+#ifndef HAVE_ARCH_FREE_PAGE
+static inline void arch_free_page(struct page *page, int order) { }
+#endif
+
+extern struct page *
+FASTCALL(__alloc_pages(unsigned int, unsigned int, struct zonelist *));
+
+static inline struct page *alloc_pages_node(int nid, unsigned int gfp_mask,
+                                               unsigned int order)
+{
+       if (unlikely(order >= MAX_ORDER))
+               return NULL;
+
+       return __alloc_pages(gfp_mask, order,
+               NODE_DATA(nid)->node_zonelists + (gfp_mask & GFP_ZONEMASK));
+}
+
+#ifdef CONFIG_NUMA
+extern struct page *alloc_pages_current(unsigned gfp_mask, unsigned order);
+
+static inline struct page *
+alloc_pages(unsigned int gfp_mask, unsigned int order)
+{
+       if (unlikely(order >= MAX_ORDER))
+               return NULL;
+
+       return alloc_pages_current(gfp_mask, order);
+}
+extern struct page *alloc_page_vma(unsigned gfp_mask,
+                       struct vm_area_struct *vma, unsigned long addr);
+#else
+#define alloc_pages(gfp_mask, order) \
+               alloc_pages_node(numa_node_id(), gfp_mask, order)
+#define alloc_page_vma(gfp_mask, vma, addr) alloc_pages(gfp_mask, 0)
+#endif
+#define alloc_page(gfp_mask) alloc_pages(gfp_mask, 0)
+
+extern unsigned long FASTCALL(__get_free_pages(unsigned int gfp_mask, unsigned 
int order));
+extern unsigned long FASTCALL(get_zeroed_page(unsigned int gfp_mask));
+
+#define __get_free_page(gfp_mask) \
+               __get_free_pages((gfp_mask),0)
+
+#define __get_dma_pages(gfp_mask, order) \
+               __get_free_pages((gfp_mask) | GFP_DMA,(order))
+
+extern void FASTCALL(__free_pages(struct page *page, unsigned int order));
+extern void FASTCALL(free_pages(unsigned long addr, unsigned int order));
+extern void FASTCALL(free_hot_page(struct page *page));
+extern void FASTCALL(free_cold_page(struct page *page));
+
+#define __free_page(page) __free_pages((page), 0)
+#define free_page(addr) free_pages((addr),0)
+
+void page_alloc_init(void);
+
+#endif /* __LINUX_GFP_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/initrd.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/initrd.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,20 @@
+
+#define INITRD_MINOR 250 /* shouldn't collide with /dev/ram* too soon ... */
+
+/* 1 = load ramdisk, 0 = don't load */
+extern int rd_doload;
+
+/* 1 = prompt for ramdisk, 0 = don't prompt */
+extern int rd_prompt;
+
+/* starting block # of image */
+extern int rd_image_start;
+
+/* 1 if it is not an error if initrd_start < memory_start */
+extern int initrd_below_start_ok;
+
+/* free_initrd_mem always gets called with the next two as arguments.. */
+extern unsigned long initrd_start, initrd_end;
+extern void free_initrd_mem(unsigned long, unsigned long);
+
+extern unsigned int real_root_dev;
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/jiffies.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/jiffies.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,450 @@
+#ifndef _LINUX_JIFFIES_H
+#define _LINUX_JIFFIES_H
+
+#include <linux/kernel.h>
+#include <linux/types.h>
+#include <linux/time.h>
+#include <linux/timex.h>
+#include <asm/param.h>                 /* for HZ */
+#include <asm/div64.h>
+
+#ifndef div_long_long_rem
+#define div_long_long_rem(dividend,divisor,remainder) \
+({                                                     \
+       u64 result = dividend;                          \
+       *remainder = do_div(result,divisor);            \
+       result;                                         \
+})
+#endif
+
+/*
+ * The following defines establish the engineering parameters of the PLL
+ * model. The HZ variable establishes the timer interrupt frequency, 100 Hz
+ * for the SunOS kernel, 256 Hz for the Ultrix kernel and 1024 Hz for the
+ * OSF/1 kernel. The SHIFT_HZ define expresses the same value as the
+ * nearest power of two in order to avoid hardware multiply operations.
+ */
+#if HZ >= 12 && HZ < 24
+# define SHIFT_HZ      4
+#elif HZ >= 24 && HZ < 48
+# define SHIFT_HZ      5
+#elif HZ >= 48 && HZ < 96
+# define SHIFT_HZ      6
+#elif HZ >= 96 && HZ < 192
+# define SHIFT_HZ      7
+#elif HZ >= 192 && HZ < 384
+# define SHIFT_HZ      8
+#elif HZ >= 384 && HZ < 768
+# define SHIFT_HZ      9
+#elif HZ >= 768 && HZ < 1536
+# define SHIFT_HZ      10
+#else
+# error You lose.
+#endif
+
+/* LATCH is used in the interval timer and ftape setup. */
+#define LATCH  ((CLOCK_TICK_RATE + HZ/2) / HZ) /* For divider */
+
+/* Suppose we want to devide two numbers NOM and DEN: NOM/DEN, the we can
+ * improve accuracy by shifting LSH bits, hence calculating:
+ *     (NOM << LSH) / DEN
+ * This however means trouble for large NOM, because (NOM << LSH) may no
+ * longer fit in 32 bits. The following way of calculating this gives us
+ * some slack, under the following conditions:
+ *   - (NOM / DEN) fits in (32 - LSH) bits.
+ *   - (NOM % DEN) fits in (32 - LSH) bits.
+ */
+#define SH_DIV(NOM,DEN,LSH) (   ((NOM / DEN) << LSH)                    \
+                             + (((NOM % DEN) << LSH) + DEN / 2) / DEN)
+
+/* HZ is the requested value. ACTHZ is actual HZ ("<< 8" is for accuracy) */
+#define ACTHZ (SH_DIV (CLOCK_TICK_RATE, LATCH, 8))
+
+/* TICK_NSEC is the time between ticks in nsec assuming real ACTHZ */
+#define TICK_NSEC (SH_DIV (1000000UL * 1000, ACTHZ, 8))
+
+/* TICK_USEC is the time between ticks in usec assuming fake USER_HZ */
+#define TICK_USEC ((1000000UL + USER_HZ/2) / USER_HZ)
+
+/* TICK_USEC_TO_NSEC is the time between ticks in nsec assuming real ACTHZ and 
*/
+/* a value TUSEC for TICK_USEC (can be set bij adjtimex)               */
+#define TICK_USEC_TO_NSEC(TUSEC) (SH_DIV (TUSEC * USER_HZ * 1000, ACTHZ, 8))
+
+/* some arch's have a small-data section that can be accessed register-relative
+ * but that can only take up to, say, 4-byte variables. jiffies being part of
+ * an 8-byte variable may not be correctly accessed unless we force the issue
+ */
+#define __jiffy_data  __attribute__((section(".data")))
+
+/*
+ * The 64-bit value is not volatile - you MUST NOT read it
+ * without sampling the sequence number in xtime_lock.
+ * get_jiffies_64() will do this for you as appropriate.
+ */
+extern u64 __jiffy_data jiffies_64;
+extern unsigned long volatile __jiffy_data jiffies;
+
+#if (BITS_PER_LONG < 64)
+u64 get_jiffies_64(void);
+#else
+static inline u64 get_jiffies_64(void)
+{
+       return (u64)jiffies;
+}
+#endif
+
+/*
+ *     These inlines deal with timer wrapping correctly. You are 
+ *     strongly encouraged to use them
+ *     1. Because people otherwise forget
+ *     2. Because if the timer wrap changes in future you won't have to
+ *        alter your driver code.
+ *
+ * time_after(a,b) returns true if the time a is after time b.
+ *
+ * Do this with "<0" and ">=0" to only test the sign of the result. A
+ * good compiler would generate better code (and a really good compiler
+ * wouldn't care). Gcc is currently neither.
+ */
+#define time_after(a,b)                \
+       (typecheck(unsigned long, a) && \
+        typecheck(unsigned long, b) && \
+        ((long)(b) - (long)(a) < 0))
+#define time_before(a,b)       time_after(b,a)
+
+#define time_after_eq(a,b)     \
+       (typecheck(unsigned long, a) && \
+        typecheck(unsigned long, b) && \
+        ((long)(a) - (long)(b) >= 0))
+#define time_before_eq(a,b)    time_after_eq(b,a)
+
+/*
+ * Have the 32 bit jiffies value wrap 5 minutes after boot
+ * so jiffies wrap bugs show up earlier.
+ */
+#define INITIAL_JIFFIES ((unsigned long)(unsigned int) (-300*HZ))
+
+/*
+ * Change timeval to jiffies, trying to avoid the
+ * most obvious overflows..
+ *
+ * And some not so obvious.
+ *
+ * Note that we don't want to return MAX_LONG, because
+ * for various timeout reasons we often end up having
+ * to wait "jiffies+1" in order to guarantee that we wait
+ * at _least_ "jiffies" - so "jiffies+1" had better still
+ * be positive.
+ */
+#define MAX_JIFFY_OFFSET ((~0UL >> 1)-1)
+
+/*
+ * We want to do realistic conversions of time so we need to use the same
+ * values the update wall clock code uses as the jiffies size.  This value
+ * is: TICK_NSEC (which is defined in timex.h).  This
+ * is a constant and is in nanoseconds.  We will used scaled math
+ * with a set of scales defined here as SEC_JIFFIE_SC,  USEC_JIFFIE_SC and
+ * NSEC_JIFFIE_SC.  Note that these defines contain nothing but
+ * constants and so are computed at compile time.  SHIFT_HZ (computed in
+ * timex.h) adjusts the scaling for different HZ values.
+
+ * Scaled math???  What is that?
+ *
+ * Scaled math is a way to do integer math on values that would,
+ * otherwise, either overflow, underflow, or cause undesired div
+ * instructions to appear in the execution path.  In short, we "scale"
+ * up the operands so they take more bits (more precision, less
+ * underflow), do the desired operation and then "scale" the result back
+ * by the same amount.  If we do the scaling by shifting we avoid the
+ * costly mpy and the dastardly div instructions.
+
+ * Suppose, for example, we want to convert from seconds to jiffies
+ * where jiffies is defined in nanoseconds as NSEC_PER_JIFFIE.  The
+ * simple math is: jiff = (sec * NSEC_PER_SEC) / NSEC_PER_JIFFIE; We
+ * observe that (NSEC_PER_SEC / NSEC_PER_JIFFIE) is a constant which we
+ * might calculate at compile time, however, the result will only have
+ * about 3-4 bits of precision (less for smaller values of HZ).
+ *
+ * So, we scale as follows:
+ * jiff = (sec) * (NSEC_PER_SEC / NSEC_PER_JIFFIE);
+ * jiff = ((sec) * ((NSEC_PER_SEC * SCALE)/ NSEC_PER_JIFFIE)) / SCALE;
+ * Then we make SCALE a power of two so:
+ * jiff = ((sec) * ((NSEC_PER_SEC << SCALE)/ NSEC_PER_JIFFIE)) >> SCALE;
+ * Now we define:
+ * #define SEC_CONV = ((NSEC_PER_SEC << SCALE)/ NSEC_PER_JIFFIE))
+ * jiff = (sec * SEC_CONV) >> SCALE;
+ *
+ * Often the math we use will expand beyond 32-bits so we tell C how to
+ * do this and pass the 64-bit result of the mpy through the ">> SCALE"
+ * which should take the result back to 32-bits.  We want this expansion
+ * to capture as much precision as possible.  At the same time we don't
+ * want to overflow so we pick the SCALE to avoid this.  In this file,
+ * that means using a different scale for each range of HZ values (as
+ * defined in timex.h).
+ *
+ * For those who want to know, gcc will give a 64-bit result from a "*"
+ * operator if the result is a long long AND at least one of the
+ * operands is cast to long long (usually just prior to the "*" so as
+ * not to confuse it into thinking it really has a 64-bit operand,
+ * which, buy the way, it can do, but it take more code and at least 2
+ * mpys).
+
+ * We also need to be aware that one second in nanoseconds is only a
+ * couple of bits away from overflowing a 32-bit word, so we MUST use
+ * 64-bits to get the full range time in nanoseconds.
+
+ */
+
+/*
+ * Here are the scales we will use.  One for seconds, nanoseconds and
+ * microseconds.
+ *
+ * Within the limits of cpp we do a rough cut at the SEC_JIFFIE_SC and
+ * check if the sign bit is set.  If not, we bump the shift count by 1.
+ * (Gets an extra bit of precision where we can use it.)
+ * We know it is set for HZ = 1024 and HZ = 100 not for 1000.
+ * Haven't tested others.
+
+ * Limits of cpp (for #if expressions) only long (no long long), but
+ * then we only need the most signicant bit.
+ */
+
+#define SEC_JIFFIE_SC (31 - SHIFT_HZ)
+#if !((((NSEC_PER_SEC << 2) / TICK_NSEC) << (SEC_JIFFIE_SC - 2)) & 0x80000000)
+#undef SEC_JIFFIE_SC
+#define SEC_JIFFIE_SC (32 - SHIFT_HZ)
+#endif
+#define NSEC_JIFFIE_SC (SEC_JIFFIE_SC + 29)
+#define USEC_JIFFIE_SC (SEC_JIFFIE_SC + 19)
+#define SEC_CONVERSION ((unsigned long)((((u64)NSEC_PER_SEC << SEC_JIFFIE_SC) 
+\
+                                TICK_NSEC -1) / (u64)TICK_NSEC))
+
+#define NSEC_CONVERSION ((unsigned long)((((u64)1 << NSEC_JIFFIE_SC) +\
+                                        TICK_NSEC -1) / (u64)TICK_NSEC))
+#define USEC_CONVERSION  \
+                    ((unsigned long)((((u64)NSEC_PER_USEC << USEC_JIFFIE_SC) +\
+                                        TICK_NSEC -1) / (u64)TICK_NSEC))
+/*
+ * USEC_ROUND is used in the timeval to jiffie conversion.  See there
+ * for more details.  It is the scaled resolution rounding value.  Note
+ * that it is a 64-bit value.  Since, when it is applied, we are already
+ * in jiffies (albit scaled), it is nothing but the bits we will shift
+ * off.
+ */
+#define USEC_ROUND (u64)(((u64)1 << USEC_JIFFIE_SC) - 1)
+/*
+ * The maximum jiffie value is (MAX_INT >> 1).  Here we translate that
+ * into seconds.  The 64-bit case will overflow if we are not careful,
+ * so use the messy SH_DIV macro to do it.  Still all constants.
+ */
+#if BITS_PER_LONG < 64
+# define MAX_SEC_IN_JIFFIES \
+       (long)((u64)((u64)MAX_JIFFY_OFFSET * TICK_NSEC) / NSEC_PER_SEC)
+#else  /* take care of overflow on 64 bits machines */
+# define MAX_SEC_IN_JIFFIES \
+       (SH_DIV((MAX_JIFFY_OFFSET >> SEC_JIFFIE_SC) * TICK_NSEC, NSEC_PER_SEC, 
1) - 1)
+
+#endif
+
+/*
+ * Convert jiffies to milliseconds and back.
+ *
+ * Avoid unnecessary multiplications/divisions in the
+ * two most common HZ cases:
+ */
+static inline unsigned int jiffies_to_msecs(const unsigned long j)
+{
+#if HZ <= 1000 && !(1000 % HZ)
+       return (1000 / HZ) * j;
+#elif HZ > 1000 && !(HZ % 1000)
+       return (j + (HZ / 1000) - 1)/(HZ / 1000);
+#else
+       return (j * 1000) / HZ;
+#endif
+}
+
+static inline unsigned int jiffies_to_usecs(const unsigned long j)
+{
+#if HZ <= 1000000 && !(1000000 % HZ)
+       return (1000000 / HZ) * j;
+#elif HZ > 1000000 && !(HZ % 1000000)
+       return (j + (HZ / 1000000) - 1)/(HZ / 1000000);
+#else
+       return (j * 1000000) / HZ;
+#endif
+}
+
+static inline unsigned long msecs_to_jiffies(const unsigned int m)
+{
+       if (m > jiffies_to_msecs(MAX_JIFFY_OFFSET))
+               return MAX_JIFFY_OFFSET;
+#if HZ <= 1000 && !(1000 % HZ)
+       return (m + (1000 / HZ) - 1) / (1000 / HZ);
+#elif HZ > 1000 && !(HZ % 1000)
+       return m * (HZ / 1000);
+#else
+       return (m * HZ + 999) / 1000;
+#endif
+}
+
+static inline unsigned long usecs_to_jiffies(const unsigned int u)
+{
+       if (u > jiffies_to_usecs(MAX_JIFFY_OFFSET))
+               return MAX_JIFFY_OFFSET;
+#if HZ <= 1000000 && !(1000000 % HZ)
+       return (u + (1000000 / HZ) - 1) / (1000000 / HZ);
+#elif HZ > 1000000 && !(HZ % 1000000)
+       return u * (HZ / 1000000);
+#else
+       return (u * HZ + 999999) / 1000000;
+#endif
+}
+
+/*
+ * The TICK_NSEC - 1 rounds up the value to the next resolution.  Note
+ * that a remainder subtract here would not do the right thing as the
+ * resolution values don't fall on second boundries.  I.e. the line:
+ * nsec -= nsec % TICK_NSEC; is NOT a correct resolution rounding.
+ *
+ * Rather, we just shift the bits off the right.
+ *
+ * The >> (NSEC_JIFFIE_SC - SEC_JIFFIE_SC) converts the scaled nsec
+ * value to a scaled second value.
+ */
+static __inline__ unsigned long
+timespec_to_jiffies(const struct timespec *value)
+{
+       unsigned long sec = value->tv_sec;
+       long nsec = value->tv_nsec + TICK_NSEC - 1;
+
+       if (sec >= MAX_SEC_IN_JIFFIES){
+               sec = MAX_SEC_IN_JIFFIES;
+               nsec = 0;
+       }
+       return (((u64)sec * SEC_CONVERSION) +
+               (((u64)nsec * NSEC_CONVERSION) >>
+                (NSEC_JIFFIE_SC - SEC_JIFFIE_SC))) >> SEC_JIFFIE_SC;
+
+}
+
+static __inline__ void
+jiffies_to_timespec(const unsigned long jiffies, struct timespec *value)
+{
+       /*
+        * Convert jiffies to nanoseconds and separate with
+        * one divide.
+        */
+       u64 nsec = (u64)jiffies * TICK_NSEC;
+       value->tv_sec = div_long_long_rem(nsec, NSEC_PER_SEC, &value->tv_nsec);
+}
+
+/* Same for "timeval"
+ *
+ * Well, almost.  The problem here is that the real system resolution is
+ * in nanoseconds and the value being converted is in micro seconds.
+ * Also for some machines (those that use HZ = 1024, in-particular),
+ * there is a LARGE error in the tick size in microseconds.
+
+ * The solution we use is to do the rounding AFTER we convert the
+ * microsecond part.  Thus the USEC_ROUND, the bits to be shifted off.
+ * Instruction wise, this should cost only an additional add with carry
+ * instruction above the way it was done above.
+ */
+static __inline__ unsigned long
+timeval_to_jiffies(const struct timeval *value)
+{
+       unsigned long sec = value->tv_sec;
+       long usec = value->tv_usec;
+
+       if (sec >= MAX_SEC_IN_JIFFIES){
+               sec = MAX_SEC_IN_JIFFIES;
+               usec = 0;
+       }
+       return (((u64)sec * SEC_CONVERSION) +
+               (((u64)usec * USEC_CONVERSION + USEC_ROUND) >>
+                (USEC_JIFFIE_SC - SEC_JIFFIE_SC))) >> SEC_JIFFIE_SC;
+}
+
+static __inline__ void
+jiffies_to_timeval(const unsigned long jiffies, struct timeval *value)
+{
+       /*
+        * Convert jiffies to nanoseconds and separate with
+        * one divide.
+        */
+       u64 nsec = (u64)jiffies * TICK_NSEC;
+       value->tv_sec = div_long_long_rem(nsec, NSEC_PER_SEC, &value->tv_usec);
+       value->tv_usec /= NSEC_PER_USEC;
+}
+
+/*
+ * Convert jiffies/jiffies_64 to clock_t and back.
+ */
+static inline clock_t jiffies_to_clock_t(long x)
+{
+#if (TICK_NSEC % (NSEC_PER_SEC / USER_HZ)) == 0
+       return x / (HZ / USER_HZ);
+#else
+       u64 tmp = (u64)x * TICK_NSEC;
+       do_div(tmp, (NSEC_PER_SEC / USER_HZ));
+       return (long)tmp;
+#endif
+}
+
+static inline unsigned long clock_t_to_jiffies(unsigned long x)
+{
+#if (HZ % USER_HZ)==0
+       if (x >= ~0UL / (HZ / USER_HZ))
+               return ~0UL;
+       return x * (HZ / USER_HZ);
+#else
+       u64 jif;
+
+       /* Don't worry about loss of precision here .. */
+       if (x >= ~0UL / HZ * USER_HZ)
+               return ~0UL;
+
+       /* .. but do try to contain it here */
+       jif = x * (u64) HZ;
+       do_div(jif, USER_HZ);
+       return jif;
+#endif
+}
+
+static inline u64 jiffies_64_to_clock_t(u64 x)
+{
+#if (TICK_NSEC % (NSEC_PER_SEC / USER_HZ)) == 0
+       do_div(x, HZ / USER_HZ);
+#else
+       /*
+        * There are better ways that don't overflow early,
+        * but even this doesn't overflow in hundreds of years
+        * in 64 bits, so..
+        */
+       x *= TICK_NSEC;
+       do_div(x, (NSEC_PER_SEC / USER_HZ));
+#endif
+       return x;
+}
+
+static inline u64 nsec_to_clock_t(u64 x)
+{
+#if (NSEC_PER_SEC % USER_HZ) == 0
+       do_div(x, (NSEC_PER_SEC / USER_HZ));
+#elif (USER_HZ % 512) == 0
+       x *= USER_HZ/512;
+       do_div(x, (NSEC_PER_SEC / 512));
+#else
+       /*
+         * max relative error 5.7e-8 (1.8s per year) for USER_HZ <= 1024,
+         * overflow after 64.99 years.
+         * exact for HZ=60, 72, 90, 120, 144, 180, 300, 600, 900, ...
+         */
+       x *= 9;
+       do_div(x, (unsigned long)((9ull * NSEC_PER_SEC + (USER_HZ/2))
+                                 / USER_HZ));
+#endif
+       return x;
+}
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/kmalloc_sizes.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/kmalloc_sizes.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,33 @@
+#if (PAGE_SIZE == 4096)
+       CACHE(32)
+#endif
+       CACHE(64)
+#if L1_CACHE_BYTES < 64
+       CACHE(96)
+#endif
+       CACHE(128)
+#if L1_CACHE_BYTES < 128
+       CACHE(192)
+#endif
+       CACHE(256)
+       CACHE(512)
+       CACHE(1024)
+       CACHE(2048)
+       CACHE(4096)
+       CACHE(8192)
+       CACHE(16384)
+       CACHE(32768)
+       CACHE(65536)
+       CACHE(131072)
+#ifndef CONFIG_MMU
+       CACHE(262144)
+       CACHE(524288)
+       CACHE(1048576)
+#ifdef CONFIG_LARGE_ALLOCS
+       CACHE(2097152)
+       CACHE(4194304)
+       CACHE(8388608)
+       CACHE(16777216)
+       CACHE(33554432)
+#endif /* CONFIG_LARGE_ALLOCS */
+#endif /* CONFIG_MMU */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/linkage.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/linkage.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,47 @@
+#ifndef _LINUX_LINKAGE_H
+#define _LINUX_LINKAGE_H
+
+#include <linux/config.h>
+#include <asm/linkage.h>
+
+#ifdef __cplusplus
+#define CPP_ASMLINKAGE extern "C"
+#else
+#define CPP_ASMLINKAGE
+#endif
+
+#ifndef asmlinkage
+#define asmlinkage CPP_ASMLINKAGE
+#endif
+
+#ifndef prevent_tail_call
+# define prevent_tail_call(ret) do { } while (0)
+#endif
+
+#ifndef __ALIGN
+#define __ALIGN                .align 4,0x90
+#define __ALIGN_STR    ".align 4,0x90"
+#endif
+
+#ifdef __ASSEMBLY__
+
+#define ALIGN __ALIGN
+#define ALIGN_STR __ALIGN_STR
+
+#define ENTRY(name) \
+  .globl name; \
+  ALIGN; \
+  name:
+
+#endif
+
+#define NORET_TYPE    /**/
+#define ATTRIB_NORET  __attribute__((noreturn))
+#define NORET_AND     noreturn,
+
+#ifndef FASTCALL
+#define FASTCALL(x)    x
+#define fastcall
+#endif
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/linuxtime.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/linuxtime.h    Tue Aug 16 04:15:23 2005
@@ -0,0 +1,181 @@
+#ifndef _LINUX_TIME_H
+#define _LINUX_TIME_H
+
+#include <linux/types.h>
+
+#ifdef __KERNEL__
+#include <linux/seqlock.h>
+#endif
+
+#ifndef _STRUCT_TIMESPEC
+#define _STRUCT_TIMESPEC
+struct timespec {
+       time_t  tv_sec;         /* seconds */
+       long    tv_nsec;        /* nanoseconds */
+};
+#endif /* _STRUCT_TIMESPEC */
+
+struct timeval {
+       time_t          tv_sec;         /* seconds */
+       suseconds_t     tv_usec;        /* microseconds */
+};
+
+struct timezone {
+       int     tz_minuteswest; /* minutes west of Greenwich */
+       int     tz_dsttime;     /* type of dst correction */
+};
+
+#ifdef __KERNEL__
+
+/* Parameters used to convert the timespec values */
+#ifndef USEC_PER_SEC
+#define USEC_PER_SEC (1000000L)
+#endif
+
+#ifndef NSEC_PER_SEC
+#define NSEC_PER_SEC (1000000000L)
+#endif
+
+#ifndef NSEC_PER_USEC
+#define NSEC_PER_USEC (1000L)
+#endif
+
+static __inline__ int timespec_equal(struct timespec *a, struct timespec *b) 
+{ 
+       return (a->tv_sec == b->tv_sec) && (a->tv_nsec == b->tv_nsec);
+} 
+
+/* Converts Gregorian date to seconds since 1970-01-01 00:00:00.
+ * Assumes input in normal date format, i.e. 1980-12-31 23:59:59
+ * => year=1980, mon=12, day=31, hour=23, min=59, sec=59.
+ *
+ * [For the Julian calendar (which was used in Russia before 1917,
+ * Britain & colonies before 1752, anywhere else before 1582,
+ * and is still in use by some communities) leave out the
+ * -year/100+year/400 terms, and add 10.]
+ *
+ * This algorithm was first published by Gauss (I think).
+ *
+ * WARNING: this function will overflow on 2106-02-07 06:28:16 on
+ * machines were long is 32-bit! (However, as time_t is signed, we
+ * will already get problems at other places on 2038-01-19 03:14:08)
+ */
+static inline unsigned long
+mktime (unsigned int year, unsigned int mon,
+       unsigned int day, unsigned int hour,
+       unsigned int min, unsigned int sec)
+{
+       if (0 >= (int) (mon -= 2)) {    /* 1..12 -> 11,12,1..10 */
+               mon += 12;              /* Puts Feb last since it has leap day 
*/
+               year -= 1;
+       }
+
+       return (((
+               (unsigned long) (year/4 - year/100 + year/400 + 367*mon/12 + 
day) +
+                       year*365 - 719499
+           )*24 + hour /* now have hours */
+         )*60 + min /* now have minutes */
+       )*60 + sec; /* finally seconds */
+}
+
+extern struct timespec xtime;
+extern struct timespec wall_to_monotonic;
+extern seqlock_t xtime_lock;
+
+static inline unsigned long get_seconds(void)
+{ 
+       return xtime.tv_sec;
+}
+
+struct timespec current_kernel_time(void);
+
+#define CURRENT_TIME (current_kernel_time())
+#define CURRENT_TIME_SEC ((struct timespec) { xtime.tv_sec, 0 })
+
+extern void do_gettimeofday(struct timeval *tv);
+extern int do_settimeofday(struct timespec *tv);
+extern int do_sys_settimeofday(struct timespec *tv, struct timezone *tz);
+extern void clock_was_set(void); // call when ever the clock is set
+extern int do_posix_clock_monotonic_gettime(struct timespec *tp);
+extern long do_nanosleep(struct timespec *t);
+extern long do_utimes(char __user * filename, struct timeval * times);
+struct itimerval;
+extern int do_setitimer(int which, struct itimerval *value, struct itimerval 
*ovalue);
+extern int do_getitimer(int which, struct itimerval *value);
+extern void getnstimeofday (struct timespec *tv);
+
+extern struct timespec timespec_trunc(struct timespec t, unsigned gran);
+
+static inline void
+set_normalized_timespec (struct timespec *ts, time_t sec, long nsec)
+{
+       while (nsec > NSEC_PER_SEC) {
+               nsec -= NSEC_PER_SEC;
+               ++sec;
+       }
+       while (nsec < 0) {
+               nsec += NSEC_PER_SEC;
+               --sec;
+       }
+       ts->tv_sec = sec;
+       ts->tv_nsec = nsec;
+}
+
+#endif /* __KERNEL__ */
+
+#define NFDBITS                        __NFDBITS
+
+#define FD_SETSIZE             __FD_SETSIZE
+#define FD_SET(fd,fdsetp)      __FD_SET(fd,fdsetp)
+#define FD_CLR(fd,fdsetp)      __FD_CLR(fd,fdsetp)
+#define FD_ISSET(fd,fdsetp)    __FD_ISSET(fd,fdsetp)
+#define FD_ZERO(fdsetp)                __FD_ZERO(fdsetp)
+
+/*
+ * Names of the interval timers, and structure
+ * defining a timer setting.
+ */
+#define        ITIMER_REAL     0
+#define        ITIMER_VIRTUAL  1
+#define        ITIMER_PROF     2
+
+struct  itimerspec {
+        struct  timespec it_interval;    /* timer period */
+        struct  timespec it_value;       /* timer expiration */
+};
+
+struct itimerval {
+       struct  timeval it_interval;    /* timer interval */
+       struct  timeval it_value;       /* current value */
+};
+
+
+/*
+ * The IDs of the various system clocks (for POSIX.1b interval timers).
+ */
+#define CLOCK_REALTIME           0
+#define CLOCK_MONOTONIC          1
+#define CLOCK_PROCESS_CPUTIME_ID 2
+#define CLOCK_THREAD_CPUTIME_ID         3
+#define CLOCK_REALTIME_HR       4
+#define CLOCK_MONOTONIC_HR       5
+
+/*
+ * The IDs of various hardware clocks
+ */
+
+
+#define CLOCK_SGI_CYCLE 10
+#define MAX_CLOCKS 16
+#define CLOCKS_MASK  (CLOCK_REALTIME | CLOCK_MONOTONIC | \
+                     CLOCK_REALTIME_HR | CLOCK_MONOTONIC_HR)
+#define CLOCKS_MONO (CLOCK_MONOTONIC & CLOCK_MONOTONIC_HR)
+
+/*
+ * The various flags for setting POSIX.1b interval timers.
+ */
+
+#define TIMER_ABSTIME 0x01
+
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/mmzone.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/mmzone.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,415 @@
+#ifndef _LINUX_MMZONE_H
+#define _LINUX_MMZONE_H
+
+#ifdef __KERNEL__
+#ifndef __ASSEMBLY__
+
+#include <linux/config.h>
+#include <linux/spinlock.h>
+#include <linux/list.h>
+#include <linux/wait.h>
+#include <linux/cache.h>
+#include <linux/threads.h>
+#include <linux/numa.h>
+#include <asm/atomic.h>
+
+/* Free memory management - zoned buddy allocator.  */
+#ifndef CONFIG_FORCE_MAX_ZONEORDER
+#define MAX_ORDER 11
+#else
+#define MAX_ORDER CONFIG_FORCE_MAX_ZONEORDER
+#endif
+
+struct free_area {
+       struct list_head        free_list;
+       unsigned long           nr_free;
+};
+
+struct pglist_data;
+
+/*
+ * zone->lock and zone->lru_lock are two of the hottest locks in the kernel.
+ * So add a wild amount of padding here to ensure that they fall into separate
+ * cachelines.  There are very few zone structures in the machine, so space
+ * consumption is not a concern here.
+ */
+#if defined(CONFIG_SMP)
+struct zone_padding {
+       char x[0];
+} ____cacheline_maxaligned_in_smp;
+#define ZONE_PADDING(name)     struct zone_padding name;
+#else
+#define ZONE_PADDING(name)
+#endif
+
+struct per_cpu_pages {
+       int count;              /* number of pages in the list */
+       int low;                /* low watermark, refill needed */
+       int high;               /* high watermark, emptying needed */
+       int batch;              /* chunk size for buddy add/remove */
+       struct list_head list;  /* the list of pages */
+};
+
+struct per_cpu_pageset {
+       struct per_cpu_pages pcp[2];    /* 0: hot.  1: cold */
+#ifdef CONFIG_NUMA
+       unsigned long numa_hit;         /* allocated in intended node */
+       unsigned long numa_miss;        /* allocated in non intended node */
+       unsigned long numa_foreign;     /* was intended here, hit elsewhere */
+       unsigned long interleave_hit;   /* interleaver prefered this zone */
+       unsigned long local_node;       /* allocation from local node */
+       unsigned long other_node;       /* allocation from other node */
+#endif
+} ____cacheline_aligned_in_smp;
+
+#define ZONE_DMA               0
+#define ZONE_NORMAL            1
+#define ZONE_HIGHMEM           2
+
+#define MAX_NR_ZONES           3       /* Sync this with ZONES_SHIFT */
+#define ZONES_SHIFT            2       /* ceil(log2(MAX_NR_ZONES)) */
+
+
+/*
+ * When a memory allocation must conform to specific limitations (such
+ * as being suitable for DMA) the caller will pass in hints to the
+ * allocator in the gfp_mask, in the zone modifier bits.  These bits
+ * are used to select a priority ordered list of memory zones which
+ * match the requested limits.  GFP_ZONEMASK defines which bits within
+ * the gfp_mask should be considered as zone modifiers.  Each valid
+ * combination of the zone modifier bits has a corresponding list
+ * of zones (in node_zonelists).  Thus for two zone modifiers there
+ * will be a maximum of 4 (2 ** 2) zonelists, for 3 modifiers there will
+ * be 8 (2 ** 3) zonelists.  GFP_ZONETYPES defines the number of possible
+ * combinations of zone modifiers in "zone modifier space".
+ */
+#define GFP_ZONEMASK   0x03
+/*
+ * As an optimisation any zone modifier bits which are only valid when
+ * no other zone modifier bits are set (loners) should be placed in
+ * the highest order bits of this field.  This allows us to reduce the
+ * extent of the zonelists thus saving space.  For example in the case
+ * of three zone modifier bits, we could require up to eight zonelists.
+ * If the left most zone modifier is a "loner" then the highest valid
+ * zonelist would be four allowing us to allocate only five zonelists.
+ * Use the first form when the left most bit is not a "loner", otherwise
+ * use the second.
+ */
+/* #define GFP_ZONETYPES       (GFP_ZONEMASK + 1) */           /* Non-loner */
+#define GFP_ZONETYPES  ((GFP_ZONEMASK + 1) / 2 + 1)            /* Loner */
+
+/*
+ * On machines where it is needed (eg PCs) we divide physical memory
+ * into multiple physical zones. On a PC we have 3 zones:
+ *
+ * ZONE_DMA      < 16 MB       ISA DMA capable memory
+ * ZONE_NORMAL 16-896 MB       direct mapped by the kernel
+ * ZONE_HIGHMEM         > 896 MB       only page cache and user processes
+ */
+
+struct zone {
+       /* Fields commonly accessed by the page allocator */
+       unsigned long           free_pages;
+       unsigned long           pages_min, pages_low, pages_high;
+       /*
+        * We don't know if the memory that we're going to allocate will be 
freeable
+        * or/and it will be released eventually, so to avoid totally wasting 
several
+        * GB of ram we must reserve some of the lower zone memory (otherwise 
we risk
+        * to run OOM on the lower zones despite there's tons of freeable ram
+        * on the higher zones). This array is recalculated at runtime if the
+        * sysctl_lowmem_reserve_ratio sysctl changes.
+        */
+       unsigned long           lowmem_reserve[MAX_NR_ZONES];
+
+       struct per_cpu_pageset  pageset[NR_CPUS];
+
+       /*
+        * free areas of different sizes
+        */
+       spinlock_t              lock;
+       struct free_area        free_area[MAX_ORDER];
+
+
+       ZONE_PADDING(_pad1_)
+
+       /* Fields commonly accessed by the page reclaim scanner */
+       spinlock_t              lru_lock;       
+       struct list_head        active_list;
+       struct list_head        inactive_list;
+       unsigned long           nr_scan_active;
+       unsigned long           nr_scan_inactive;
+       unsigned long           nr_active;
+       unsigned long           nr_inactive;
+       unsigned long           pages_scanned;     /* since last reclaim */
+       int                     all_unreclaimable; /* All pages pinned */
+
+       /*
+        * prev_priority holds the scanning priority for this zone.  It is
+        * defined as the scanning priority at which we achieved our reclaim
+        * target at the previous try_to_free_pages() or balance_pgdat()
+        * invokation.
+        *
+        * We use prev_priority as a measure of how much stress page reclaim is
+        * under - it drives the swappiness decision: whether to unmap mapped
+        * pages.
+        *
+        * temp_priority is used to remember the scanning priority at which
+        * this zone was successfully refilled to free_pages == pages_high.
+        *
+        * Access to both these fields is quite racy even on uniprocessor.  But
+        * it is expected to average out OK.
+        */
+       int temp_priority;
+       int prev_priority;
+
+
+       ZONE_PADDING(_pad2_)
+       /* Rarely used or read-mostly fields */
+
+       /*
+        * wait_table           -- the array holding the hash table
+        * wait_table_size      -- the size of the hash table array
+        * wait_table_bits      -- wait_table_size == (1 << wait_table_bits)
+        *
+        * The purpose of all these is to keep track of the people
+        * waiting for a page to become available and make them
+        * runnable again when possible. The trouble is that this
+        * consumes a lot of space, especially when so few things
+        * wait on pages at a given time. So instead of using
+        * per-page waitqueues, we use a waitqueue hash table.
+        *
+        * The bucket discipline is to sleep on the same queue when
+        * colliding and wake all in that wait queue when removing.
+        * When something wakes, it must check to be sure its page is
+        * truly available, a la thundering herd. The cost of a
+        * collision is great, but given the expected load of the
+        * table, they should be so rare as to be outweighed by the
+        * benefits from the saved space.
+        *
+        * __wait_on_page_locked() and unlock_page() in mm/filemap.c, are the
+        * primary users of these fields, and in mm/page_alloc.c
+        * free_area_init_core() performs the initialization of them.
+        */
+       wait_queue_head_t       * wait_table;
+       unsigned long           wait_table_size;
+       unsigned long           wait_table_bits;
+
+       /*
+        * Discontig memory support fields.
+        */
+       struct pglist_data      *zone_pgdat;
+       struct page             *zone_mem_map;
+       /* zone_start_pfn == zone_start_paddr >> PAGE_SHIFT */
+       unsigned long           zone_start_pfn;
+
+       unsigned long           spanned_pages;  /* total size, including holes 
*/
+       unsigned long           present_pages;  /* amount of memory (excluding 
holes) */
+
+       /*
+        * rarely used fields:
+        */
+       char                    *name;
+} ____cacheline_maxaligned_in_smp;
+
+
+/*
+ * The "priority" of VM scanning is how much of the queues we will scan in one
+ * go. A value of 12 for DEF_PRIORITY implies that we will scan 1/4096th of the
+ * queues ("queue_length >> 12") during an aging round.
+ */
+#define DEF_PRIORITY 12
+
+/*
+ * One allocation request operates on a zonelist. A zonelist
+ * is a list of zones, the first one is the 'goal' of the
+ * allocation, the other zones are fallback zones, in decreasing
+ * priority.
+ *
+ * Right now a zonelist takes up less than a cacheline. We never
+ * modify it apart from boot-up, and only a few indices are used,
+ * so despite the zonelist table being relatively big, the cache
+ * footprint of this construct is very small.
+ */
+struct zonelist {
+       struct zone *zones[MAX_NUMNODES * MAX_NR_ZONES + 1]; // NULL delimited
+};
+
+
+/*
+ * The pg_data_t structure is used in machines with CONFIG_DISCONTIGMEM
+ * (mostly NUMA machines?) to denote a higher-level memory zone than the
+ * zone denotes.
+ *
+ * On NUMA machines, each NUMA node would have a pg_data_t to describe
+ * it's memory layout.
+ *
+ * Memory statistics and page replacement data structures are maintained on a
+ * per-zone basis.
+ */
+struct bootmem_data;
+typedef struct pglist_data {
+       struct zone node_zones[MAX_NR_ZONES];
+       struct zonelist node_zonelists[GFP_ZONETYPES];
+       int nr_zones;
+       struct page *node_mem_map;
+       struct bootmem_data *bdata;
+       unsigned long node_start_pfn;
+       unsigned long node_present_pages; /* total number of physical pages */
+       unsigned long node_spanned_pages; /* total size of physical page
+                                            range, including holes */
+       int node_id;
+       struct pglist_data *pgdat_next;
+       wait_queue_head_t kswapd_wait;
+       struct task_struct *kswapd;
+       int kswapd_max_order;
+} pg_data_t;
+
+#define node_present_pages(nid)        (NODE_DATA(nid)->node_present_pages)
+#define node_spanned_pages(nid)        (NODE_DATA(nid)->node_spanned_pages)
+
+extern struct pglist_data *pgdat_list;
+
+void __get_zone_counts(unsigned long *active, unsigned long *inactive,
+                       unsigned long *free, struct pglist_data *pgdat);
+void get_zone_counts(unsigned long *active, unsigned long *inactive,
+                       unsigned long *free);
+void build_all_zonelists(void);
+void wakeup_kswapd(struct zone *zone, int order);
+int zone_watermark_ok(struct zone *z, int order, unsigned long mark,
+               int alloc_type, int can_try_harder, int gfp_high);
+
+/*
+ * zone_idx() returns 0 for the ZONE_DMA zone, 1 for the ZONE_NORMAL zone, etc.
+ */
+#define zone_idx(zone)         ((zone) - (zone)->zone_pgdat->node_zones)
+
+/**
+ * for_each_pgdat - helper macro to iterate over all nodes
+ * @pgdat - pointer to a pg_data_t variable
+ *
+ * Meant to help with common loops of the form
+ * pgdat = pgdat_list;
+ * while(pgdat) {
+ *     ...
+ *     pgdat = pgdat->pgdat_next;
+ * }
+ */
+#define for_each_pgdat(pgdat) \
+       for (pgdat = pgdat_list; pgdat; pgdat = pgdat->pgdat_next)
+
+/*
+ * next_zone - helper magic for for_each_zone()
+ * Thanks to William Lee Irwin III for this piece of ingenuity.
+ */
+static inline struct zone *next_zone(struct zone *zone)
+{
+       pg_data_t *pgdat = zone->zone_pgdat;
+
+       if (zone < pgdat->node_zones + MAX_NR_ZONES - 1)
+               zone++;
+       else if (pgdat->pgdat_next) {
+               pgdat = pgdat->pgdat_next;
+               zone = pgdat->node_zones;
+       } else
+               zone = NULL;
+
+       return zone;
+}
+
+/**
+ * for_each_zone - helper macro to iterate over all memory zones
+ * @zone - pointer to struct zone variable
+ *
+ * The user only needs to declare the zone variable, for_each_zone
+ * fills it in. This basically means for_each_zone() is an
+ * easier to read version of this piece of code:
+ *
+ * for (pgdat = pgdat_list; pgdat; pgdat = pgdat->node_next)
+ *     for (i = 0; i < MAX_NR_ZONES; ++i) {
+ *             struct zone * z = pgdat->node_zones + i;
+ *             ...
+ *     }
+ * }
+ */
+#define for_each_zone(zone) \
+       for (zone = pgdat_list->node_zones; zone; zone = next_zone(zone))
+
+static inline int is_highmem_idx(int idx)
+{
+       return (idx == ZONE_HIGHMEM);
+}
+
+static inline int is_normal_idx(int idx)
+{
+       return (idx == ZONE_NORMAL);
+}
+/**
+ * is_highmem - helper function to quickly check if a struct zone is a 
+ *              highmem zone or not.  This is an attempt to keep references
+ *              to ZONE_{DMA/NORMAL/HIGHMEM/etc} in general code to a minimum.
+ * @zone - pointer to struct zone variable
+ */
+static inline int is_highmem(struct zone *zone)
+{
+       return zone == zone->zone_pgdat->node_zones + ZONE_HIGHMEM;
+}
+
+static inline int is_normal(struct zone *zone)
+{
+       return zone == zone->zone_pgdat->node_zones + ZONE_NORMAL;
+}
+
+/* These two functions are used to setup the per zone pages min values */
+struct ctl_table;
+struct file;
+int min_free_kbytes_sysctl_handler(struct ctl_table *, int, struct file *, 
+                                       void __user *, size_t *, loff_t *);
+extern int sysctl_lowmem_reserve_ratio[MAX_NR_ZONES-1];
+int lowmem_reserve_ratio_sysctl_handler(struct ctl_table *, int, struct file *,
+                                       void __user *, size_t *, loff_t *);
+
+#include <linux/topology.h>
+/* Returns the number of the current Node. */
+#define numa_node_id()         (cpu_to_node(_smp_processor_id()))
+
+#ifndef CONFIG_DISCONTIGMEM
+
+extern struct pglist_data contig_page_data;
+#define NODE_DATA(nid)         (&contig_page_data)
+#define NODE_MEM_MAP(nid)      mem_map
+#define MAX_NODES_SHIFT                1
+#define pfn_to_nid(pfn)                (0)
+
+#else /* CONFIG_DISCONTIGMEM */
+
+#include <asm/mmzone.h>
+
+#if BITS_PER_LONG == 32 || defined(ARCH_HAS_ATOMIC_UNSIGNED)
+/*
+ * with 32 bit page->flags field, we reserve 8 bits for node/zone info.
+ * there are 3 zones (2 bits) and this leaves 8-2=6 bits for nodes.
+ */
+#define MAX_NODES_SHIFT                6
+#elif BITS_PER_LONG == 64
+/*
+ * with 64 bit flags field, there's plenty of room.
+ */
+#define MAX_NODES_SHIFT                10
+#endif
+
+#endif /* !CONFIG_DISCONTIGMEM */
+
+#if NODES_SHIFT > MAX_NODES_SHIFT
+#error NODES_SHIFT > MAX_NODES_SHIFT
+#endif
+
+/* There are currently 3 zones: DMA, Normal & Highmem, thus we need 2 bits */
+#define MAX_ZONES_SHIFT                2
+
+#if ZONES_SHIFT > MAX_ZONES_SHIFT
+#error ZONES_SHIFT > MAX_ZONES_SHIFT
+#endif
+
+#endif /* !__ASSEMBLY__ */
+#endif /* __KERNEL__ */
+#endif /* _LINUX_MMZONE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/numa.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/numa.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,16 @@
+#ifndef _LINUX_NUMA_H
+#define _LINUX_NUMA_H
+
+#include <linux/config.h>
+
+#ifdef CONFIG_DISCONTIGMEM
+#include <asm/numnodes.h>
+#endif
+
+#ifndef NODES_SHIFT
+#define NODES_SHIFT     0
+#endif
+
+#define MAX_NUMNODES    (1 << NODES_SHIFT)
+
+#endif /* _LINUX_NUMA_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/page-flags.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/page-flags.h   Tue Aug 16 04:15:23 2005
@@ -0,0 +1,321 @@
+/*
+ * Macros for manipulating and testing page->flags
+ */
+
+#ifndef PAGE_FLAGS_H
+#define PAGE_FLAGS_H
+
+#include <linux/percpu.h>
+#include <linux/cache.h>
+#include <asm/pgtable.h>
+
+/*
+ * Various page->flags bits:
+ *
+ * PG_reserved is set for special pages, which can never be swapped out. Some
+ * of them might not even exist (eg empty_bad_page)...
+ *
+ * The PG_private bitflag is set if page->private contains a valid value.
+ *
+ * During disk I/O, PG_locked is used. This bit is set before I/O and
+ * reset when I/O completes. page_waitqueue(page) is a wait queue of all tasks
+ * waiting for the I/O on this page to complete.
+ *
+ * PG_uptodate tells whether the page's contents is valid.  When a read
+ * completes, the page becomes uptodate, unless a disk I/O error happened.
+ *
+ * For choosing which pages to swap out, inode pages carry a PG_referenced bit,
+ * which is set any time the system accesses that page through the (mapping,
+ * index) hash table.  This referenced bit, together with the referenced bit
+ * in the page tables, is used to manipulate page->age and move the page across
+ * the active, inactive_dirty and inactive_clean lists.
+ *
+ * Note that the referenced bit, the page->lru list_head and the active,
+ * inactive_dirty and inactive_clean lists are protected by the
+ * zone->lru_lock, and *NOT* by the usual PG_locked bit!
+ *
+ * PG_error is set to indicate that an I/O error occurred on this page.
+ *
+ * PG_arch_1 is an architecture specific page state bit.  The generic code
+ * guarantees that this bit is cleared for a page when it first is entered into
+ * the page cache.
+ *
+ * PG_highmem pages are not permanently mapped into the kernel virtual address
+ * space, they need to be kmapped separately for doing IO on the pages.  The
+ * struct page (these bits with information) are always mapped into kernel
+ * address space...
+ */
+
+/*
+ * Don't use the *_dontuse flags.  Use the macros.  Otherwise you'll break
+ * locked- and dirty-page accounting.  The top eight bits of page->flags are
+ * used for page->zone, so putting flag bits there doesn't work.
+ */
+#define PG_locked               0      /* Page is locked. Don't touch. */
+#define PG_error                1
+#define PG_referenced           2
+#define PG_uptodate             3
+
+#define PG_dirty                4
+#define PG_lru                  5
+#define PG_active               6
+#define PG_slab                         7      /* slab debug (Suparna wants 
this) */
+
+#define PG_highmem              8
+#define PG_checked              9      /* kill me in 2.5.<early>. */
+#define PG_arch_1              10
+#define PG_reserved            11
+
+#define PG_private             12      /* Has something at ->private */
+#define PG_writeback           13      /* Page is under writeback */
+#define PG_nosave              14      /* Used for system suspend/resume */
+#define PG_compound            15      /* Part of a compound page */
+
+#define PG_swapcache           16      /* Swap page: swp_entry_t in private */
+#define PG_mappedtodisk                17      /* Has blocks allocated on-disk 
*/
+#define PG_reclaim             18      /* To be reclaimed asap */
+#define PG_nosave_free         19      /* Free, should not be written */
+
+
+/*
+ * Global page accounting.  One instance per CPU.  Only unsigned longs are
+ * allowed.
+ */
+struct page_state {
+       unsigned long nr_dirty;         /* Dirty writeable pages */
+       unsigned long nr_writeback;     /* Pages under writeback */
+       unsigned long nr_unstable;      /* NFS unstable pages */
+       unsigned long nr_page_table_pages;/* Pages used for pagetables */
+       unsigned long nr_mapped;        /* mapped into pagetables */
+       unsigned long nr_slab;          /* In slab */
+#define GET_PAGE_STATE_LAST nr_slab
+
+       /*
+        * The below are zeroed by get_page_state().  Use get_full_page_state()
+        * to add up all these.
+        */
+       unsigned long pgpgin;           /* Disk reads */
+       unsigned long pgpgout;          /* Disk writes */
+       unsigned long pswpin;           /* swap reads */
+       unsigned long pswpout;          /* swap writes */
+       unsigned long pgalloc_high;     /* page allocations */
+
+       unsigned long pgalloc_normal;
+       unsigned long pgalloc_dma;
+       unsigned long pgfree;           /* page freeings */
+       unsigned long pgactivate;       /* pages moved inactive->active */
+       unsigned long pgdeactivate;     /* pages moved active->inactive */
+
+       unsigned long pgfault;          /* faults (major+minor) */
+       unsigned long pgmajfault;       /* faults (major only) */
+       unsigned long pgrefill_high;    /* inspected in refill_inactive_zone */
+       unsigned long pgrefill_normal;
+       unsigned long pgrefill_dma;
+
+       unsigned long pgsteal_high;     /* total highmem pages reclaimed */
+       unsigned long pgsteal_normal;
+       unsigned long pgsteal_dma;
+       unsigned long pgscan_kswapd_high;/* total highmem pages scanned */
+       unsigned long pgscan_kswapd_normal;
+
+       unsigned long pgscan_kswapd_dma;
+       unsigned long pgscan_direct_high;/* total highmem pages scanned */
+       unsigned long pgscan_direct_normal;
+       unsigned long pgscan_direct_dma;
+       unsigned long pginodesteal;     /* pages reclaimed via inode freeing */
+
+       unsigned long slabs_scanned;    /* slab objects scanned */
+       unsigned long kswapd_steal;     /* pages reclaimed by kswapd */
+       unsigned long kswapd_inodesteal;/* reclaimed via kswapd inode freeing */
+       unsigned long pageoutrun;       /* kswapd's calls to page reclaim */
+       unsigned long allocstall;       /* direct reclaim calls */
+
+       unsigned long pgrotated;        /* pages rotated to tail of the LRU */
+};
+
+extern void get_page_state(struct page_state *ret);
+extern void get_full_page_state(struct page_state *ret);
+extern unsigned long __read_page_state(unsigned offset);
+extern void __mod_page_state(unsigned offset, unsigned long delta);
+
+#define read_page_state(member) \
+       __read_page_state(offsetof(struct page_state, member))
+
+#define mod_page_state(member, delta)  \
+       __mod_page_state(offsetof(struct page_state, member), (delta))
+
+#define inc_page_state(member) mod_page_state(member, 1UL)
+#define dec_page_state(member) mod_page_state(member, 0UL - 1)
+#define add_page_state(member,delta) mod_page_state(member, (delta))
+#define sub_page_state(member,delta) mod_page_state(member, 0UL - (delta))
+
+#define mod_page_state_zone(zone, member, delta)                               
\
+       do {                                                                    
\
+               unsigned offset;                                                
\
+               if (is_highmem(zone))                                           
\
+                       offset = offsetof(struct page_state, member##_high);    
\
+               else if (is_normal(zone))                                       
\
+                       offset = offsetof(struct page_state, member##_normal);  
\
+               else                                                            
\
+                       offset = offsetof(struct page_state, member##_dma);     
\
+               __mod_page_state(offset, (delta));                              
\
+       } while (0)
+
+/*
+ * Manipulation of page state flags
+ */
+#define PageLocked(page)               \
+               test_bit(PG_locked, &(page)->flags)
+#define SetPageLocked(page)            \
+               set_bit(PG_locked, &(page)->flags)
+#define TestSetPageLocked(page)                \
+               test_and_set_bit(PG_locked, &(page)->flags)
+#define ClearPageLocked(page)          \
+               clear_bit(PG_locked, &(page)->flags)
+#define TestClearPageLocked(page)      \
+               test_and_clear_bit(PG_locked, &(page)->flags)
+
+#define PageError(page)                test_bit(PG_error, &(page)->flags)
+#define SetPageError(page)     set_bit(PG_error, &(page)->flags)
+#define ClearPageError(page)   clear_bit(PG_error, &(page)->flags)
+
+#define PageReferenced(page)   test_bit(PG_referenced, &(page)->flags)
+#define SetPageReferenced(page)        set_bit(PG_referenced, &(page)->flags)
+#define ClearPageReferenced(page)      clear_bit(PG_referenced, &(page)->flags)
+#define TestClearPageReferenced(page) test_and_clear_bit(PG_referenced, 
&(page)->flags)
+
+#define PageUptodate(page)     test_bit(PG_uptodate, &(page)->flags)
+#ifndef SetPageUptodate
+#define SetPageUptodate(page)  set_bit(PG_uptodate, &(page)->flags)
+#endif
+#define ClearPageUptodate(page)        clear_bit(PG_uptodate, &(page)->flags)
+
+#define PageDirty(page)                test_bit(PG_dirty, &(page)->flags)
+#define SetPageDirty(page)     set_bit(PG_dirty, &(page)->flags)
+#define TestSetPageDirty(page) test_and_set_bit(PG_dirty, &(page)->flags)
+#define ClearPageDirty(page)   clear_bit(PG_dirty, &(page)->flags)
+#define TestClearPageDirty(page) test_and_clear_bit(PG_dirty, &(page)->flags)
+
+#define SetPageLRU(page)       set_bit(PG_lru, &(page)->flags)
+#define PageLRU(page)          test_bit(PG_lru, &(page)->flags)
+#define TestSetPageLRU(page)   test_and_set_bit(PG_lru, &(page)->flags)
+#define TestClearPageLRU(page) test_and_clear_bit(PG_lru, &(page)->flags)
+
+#define PageActive(page)       test_bit(PG_active, &(page)->flags)
+#define SetPageActive(page)    set_bit(PG_active, &(page)->flags)
+#define ClearPageActive(page)  clear_bit(PG_active, &(page)->flags)
+#define TestClearPageActive(page) test_and_clear_bit(PG_active, &(page)->flags)
+#define TestSetPageActive(page) test_and_set_bit(PG_active, &(page)->flags)
+
+#define PageSlab(page)         test_bit(PG_slab, &(page)->flags)
+#define SetPageSlab(page)      set_bit(PG_slab, &(page)->flags)
+#define ClearPageSlab(page)    clear_bit(PG_slab, &(page)->flags)
+#define TestClearPageSlab(page)        test_and_clear_bit(PG_slab, 
&(page)->flags)
+#define TestSetPageSlab(page)  test_and_set_bit(PG_slab, &(page)->flags)
+
+#ifdef CONFIG_HIGHMEM
+#define PageHighMem(page)      test_bit(PG_highmem, &(page)->flags)
+#else
+#define PageHighMem(page)      0 /* needed to optimize away at compile time */
+#endif
+
+#define PageChecked(page)      test_bit(PG_checked, &(page)->flags)
+#define SetPageChecked(page)   set_bit(PG_checked, &(page)->flags)
+#define ClearPageChecked(page) clear_bit(PG_checked, &(page)->flags)
+
+#define PageReserved(page)     test_bit(PG_reserved, &(page)->flags)
+#define SetPageReserved(page)  set_bit(PG_reserved, &(page)->flags)
+#define ClearPageReserved(page)        clear_bit(PG_reserved, &(page)->flags)
+#define __ClearPageReserved(page)      __clear_bit(PG_reserved, &(page)->flags)
+
+#define SetPagePrivate(page)   set_bit(PG_private, &(page)->flags)
+#define ClearPagePrivate(page) clear_bit(PG_private, &(page)->flags)
+#define PagePrivate(page)      test_bit(PG_private, &(page)->flags)
+#define __SetPagePrivate(page)  __set_bit(PG_private, &(page)->flags)
+#define __ClearPagePrivate(page) __clear_bit(PG_private, &(page)->flags)
+
+#define PageWriteback(page)    test_bit(PG_writeback, &(page)->flags)
+#define SetPageWriteback(page)                                         \
+       do {                                                            \
+               if (!test_and_set_bit(PG_writeback,                     \
+                               &(page)->flags))                        \
+                       inc_page_state(nr_writeback);                   \
+       } while (0)
+#define TestSetPageWriteback(page)                                     \
+       ({                                                              \
+               int ret;                                                \
+               ret = test_and_set_bit(PG_writeback,                    \
+                                       &(page)->flags);                \
+               if (!ret)                                               \
+                       inc_page_state(nr_writeback);                   \
+               ret;                                                    \
+       })
+#define ClearPageWriteback(page)                                       \
+       do {                                                            \
+               if (test_and_clear_bit(PG_writeback,                    \
+                               &(page)->flags))                        \
+                       dec_page_state(nr_writeback);                   \
+       } while (0)
+#define TestClearPageWriteback(page)                                   \
+       ({                                                              \
+               int ret;                                                \
+               ret = test_and_clear_bit(PG_writeback,                  \
+                               &(page)->flags);                        \
+               if (ret)                                                \
+                       dec_page_state(nr_writeback);                   \
+               ret;                                                    \
+       })
+
+#define PageNosave(page)       test_bit(PG_nosave, &(page)->flags)
+#define SetPageNosave(page)    set_bit(PG_nosave, &(page)->flags)
+#define TestSetPageNosave(page)        test_and_set_bit(PG_nosave, 
&(page)->flags)
+#define ClearPageNosave(page)          clear_bit(PG_nosave, &(page)->flags)
+#define TestClearPageNosave(page)      test_and_clear_bit(PG_nosave, 
&(page)->flags)
+
+#define PageNosaveFree(page)   test_bit(PG_nosave_free, &(page)->flags)
+#define SetPageNosaveFree(page)        set_bit(PG_nosave_free, &(page)->flags)
+#define ClearPageNosaveFree(page)              clear_bit(PG_nosave_free, 
&(page)->flags)
+
+#define PageMappedToDisk(page) test_bit(PG_mappedtodisk, &(page)->flags)
+#define SetPageMappedToDisk(page) set_bit(PG_mappedtodisk, &(page)->flags)
+#define ClearPageMappedToDisk(page) clear_bit(PG_mappedtodisk, &(page)->flags)
+
+#define PageReclaim(page)      test_bit(PG_reclaim, &(page)->flags)
+#define SetPageReclaim(page)   set_bit(PG_reclaim, &(page)->flags)
+#define ClearPageReclaim(page) clear_bit(PG_reclaim, &(page)->flags)
+#define TestClearPageReclaim(page) test_and_clear_bit(PG_reclaim, 
&(page)->flags)
+
+#ifdef CONFIG_HUGETLB_PAGE
+#define PageCompound(page)     test_bit(PG_compound, &(page)->flags)
+#else
+#define PageCompound(page)     0
+#endif
+#define SetPageCompound(page)  set_bit(PG_compound, &(page)->flags)
+#define ClearPageCompound(page)        clear_bit(PG_compound, &(page)->flags)
+
+#ifdef CONFIG_SWAP
+#define PageSwapCache(page)    test_bit(PG_swapcache, &(page)->flags)
+#define SetPageSwapCache(page) set_bit(PG_swapcache, &(page)->flags)
+#define ClearPageSwapCache(page) clear_bit(PG_swapcache, &(page)->flags)
+#else
+#define PageSwapCache(page)    0
+#endif
+
+struct page;   /* forward declaration */
+
+int test_clear_page_dirty(struct page *page);
+int __clear_page_dirty(struct page *page);
+int test_clear_page_writeback(struct page *page);
+int test_set_page_writeback(struct page *page);
+
+static inline void clear_page_dirty(struct page *page)
+{
+       test_clear_page_dirty(page);
+}
+
+static inline void set_page_writeback(struct page *page)
+{
+       test_set_page_writeback(page);
+}
+
+#endif /* PAGE_FLAGS_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/percpu.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/percpu.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,61 @@
+#ifndef __LINUX_PERCPU_H
+#define __LINUX_PERCPU_H
+#include <linux/spinlock.h> /* For preempt_disable() */
+#include <linux/slab.h> /* For kmalloc() */
+#include <linux/smp.h>
+#include <linux/string.h> /* For memset() */
+#include <asm/percpu.h>
+
+/* Enough to cover all DEFINE_PER_CPUs in kernel, including modules. */
+#ifndef PERCPU_ENOUGH_ROOM
+#define PERCPU_ENOUGH_ROOM 32768
+#endif
+
+/* Must be an lvalue. */
+#define get_cpu_var(var) (*({ preempt_disable(); &__get_cpu_var(var); }))
+#define put_cpu_var(var) preempt_enable()
+
+#ifdef CONFIG_SMP
+
+struct percpu_data {
+       void *ptrs[NR_CPUS];
+       void *blkp;
+};
+
+/* 
+ * Use this to get to a cpu's version of the per-cpu object allocated using
+ * alloc_percpu.  Non-atomic access to the current CPU's version should
+ * probably be combined with get_cpu()/put_cpu().
+ */ 
+#define per_cpu_ptr(ptr, cpu)                   \
+({                                              \
+        struct percpu_data *__p = (struct percpu_data *)~(unsigned long)(ptr); 
\
+        (__typeof__(ptr))__p->ptrs[(cpu)];     \
+})
+
+extern void *__alloc_percpu(size_t size, size_t align);
+extern void free_percpu(const void *);
+
+#else /* CONFIG_SMP */
+
+#define per_cpu_ptr(ptr, cpu) (ptr)
+
+static inline void *__alloc_percpu(size_t size, size_t align)
+{
+       void *ret = kmalloc(size, GFP_KERNEL);
+       if (ret)
+               memset(ret, 0, size);
+       return ret;
+}
+static inline void free_percpu(const void *ptr)
+{      
+       kfree(ptr);
+}
+
+#endif /* CONFIG_SMP */
+
+/* Simple wrapper for the common case: zeros memory. */
+#define alloc_percpu(type) \
+       ((type *)(__alloc_percpu(sizeof(type), __alignof__(type))))
+
+#endif /* __LINUX_PERCPU_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/preempt.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/preempt.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,62 @@
+#ifndef __LINUX_PREEMPT_H
+#define __LINUX_PREEMPT_H
+
+/*
+ * include/linux/preempt.h - macros for accessing and manipulating
+ * preempt_count (used for kernel preemption, interrupt count, etc.)
+ */
+
+#include <linux/config.h>
+#include <linux/linkage.h>
+
+#ifdef CONFIG_DEBUG_PREEMPT
+  extern void fastcall add_preempt_count(int val);
+  extern void fastcall sub_preempt_count(int val);
+#else
+# define add_preempt_count(val)        do { preempt_count() += (val); } while 
(0)
+# define sub_preempt_count(val)        do { preempt_count() -= (val); } while 
(0)
+#endif
+
+#define inc_preempt_count() add_preempt_count(1)
+#define dec_preempt_count() sub_preempt_count(1)
+
+#define preempt_count()        (current_thread_info()->preempt_count)
+
+#ifdef CONFIG_PREEMPT
+
+asmlinkage void preempt_schedule(void);
+
+#define preempt_disable() \
+do { \
+       inc_preempt_count(); \
+       barrier(); \
+} while (0)
+
+#define preempt_enable_no_resched() \
+do { \
+       barrier(); \
+       dec_preempt_count(); \
+} while (0)
+
+#define preempt_check_resched() \
+do { \
+       if (unlikely(test_thread_flag(TIF_NEED_RESCHED))) \
+               preempt_schedule(); \
+} while (0)
+
+#define preempt_enable() \
+do { \
+       preempt_enable_no_resched(); \
+       preempt_check_resched(); \
+} while (0)
+
+#else
+
+#define preempt_disable()              do { } while (0)
+#define preempt_enable_no_resched()    do { } while (0)
+#define preempt_enable()               do { } while (0)
+#define preempt_check_resched()                do { } while (0)
+
+#endif
+
+#endif /* __LINUX_PREEMPT_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/rbtree.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/rbtree.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,141 @@
+/*
+  Red Black Trees
+  (C) 1999  Andrea Arcangeli <andrea@xxxxxxx>
+  
+  This program is free software; you can redistribute it and/or modify
+  it under the terms of the GNU General Public License as published by
+  the Free Software Foundation; either version 2 of the License, or
+  (at your option) any later version.
+
+  This program is distributed in the hope that it will be useful,
+  but WITHOUT ANY WARRANTY; without even the implied warranty of
+  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+  GNU General Public License for more details.
+
+  You should have received a copy of the GNU General Public License
+  along with this program; if not, write to the Free Software
+  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+  linux/include/linux/rbtree.h
+
+  To use rbtrees you'll have to implement your own insert and search cores.
+  This will avoid us to use callbacks and to drop drammatically performances.
+  I know it's not the cleaner way,  but in C (not in C++) to get
+  performances and genericity...
+
+  Some example of insert and search follows here. The search is a plain
+  normal search over an ordered tree. The insert instead must be implemented
+  int two steps: as first thing the code must insert the element in
+  order as a red leaf in the tree, then the support library function
+  rb_insert_color() must be called. Such function will do the
+  not trivial work to rebalance the rbtree if necessary.
+
+-----------------------------------------------------------------------
+static inline struct page * rb_search_page_cache(struct inode * inode,
+                                                unsigned long offset)
+{
+       struct rb_node * n = inode->i_rb_page_cache.rb_node;
+       struct page * page;
+
+       while (n)
+       {
+               page = rb_entry(n, struct page, rb_page_cache);
+
+               if (offset < page->offset)
+                       n = n->rb_left;
+               else if (offset > page->offset)
+                       n = n->rb_right;
+               else
+                       return page;
+       }
+       return NULL;
+}
+
+static inline struct page * __rb_insert_page_cache(struct inode * inode,
+                                                  unsigned long offset,
+                                                  struct rb_node * node)
+{
+       struct rb_node ** p = &inode->i_rb_page_cache.rb_node;
+       struct rb_node * parent = NULL;
+       struct page * page;
+
+       while (*p)
+       {
+               parent = *p;
+               page = rb_entry(parent, struct page, rb_page_cache);
+
+               if (offset < page->offset)
+                       p = &(*p)->rb_left;
+               else if (offset > page->offset)
+                       p = &(*p)->rb_right;
+               else
+                       return page;
+       }
+
+       rb_link_node(node, parent, p);
+
+       return NULL;
+}
+
+static inline struct page * rb_insert_page_cache(struct inode * inode,
+                                                unsigned long offset,
+                                                struct rb_node * node)
+{
+       struct page * ret;
+       if ((ret = __rb_insert_page_cache(inode, offset, node)))
+               goto out;
+       rb_insert_color(node, &inode->i_rb_page_cache);
+ out:
+       return ret;
+}
+-----------------------------------------------------------------------
+*/
+
+#ifndef        _LINUX_RBTREE_H
+#define        _LINUX_RBTREE_H
+
+#include <linux/kernel.h>
+#include <linux/stddef.h>
+
+struct rb_node
+{
+       struct rb_node *rb_parent;
+       int rb_color;
+#define        RB_RED          0
+#define        RB_BLACK        1
+       struct rb_node *rb_right;
+       struct rb_node *rb_left;
+};
+
+struct rb_root
+{
+       struct rb_node *rb_node;
+};
+
+#define RB_ROOT        (struct rb_root) { NULL, }
+#define        rb_entry(ptr, type, member) container_of(ptr, type, member)
+
+extern void rb_insert_color(struct rb_node *, struct rb_root *);
+extern void rb_erase(struct rb_node *, struct rb_root *);
+
+/* Find logical next and previous nodes in a tree */
+extern struct rb_node *rb_next(struct rb_node *);
+extern struct rb_node *rb_prev(struct rb_node *);
+extern struct rb_node *rb_first(struct rb_root *);
+extern struct rb_node *rb_last(struct rb_root *);
+
+/* Fast replacement of a single node without remove/rebalance/add/rebalance */
+extern void rb_replace_node(struct rb_node *victim, struct rb_node *new, 
+                           struct rb_root *root);
+
+static inline void rb_link_node(struct rb_node * node, struct rb_node * parent,
+                               struct rb_node ** rb_link)
+{
+       node->rb_parent = parent;
+       node->rb_color = RB_RED;
+       node->rb_left = node->rb_right = NULL;
+
+       *rb_link = node;
+}
+
+#endif /* _LINUX_RBTREE_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/rwsem.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/rwsem.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,115 @@
+/* rwsem.h: R/W semaphores, public interface
+ *
+ * Written by David Howells (dhowells@xxxxxxxxxx).
+ * Derived from asm-i386/semaphore.h
+ */
+
+#ifndef _LINUX_RWSEM_H
+#define _LINUX_RWSEM_H
+
+#include <linux/linkage.h>
+
+#define RWSEM_DEBUG 0
+
+#ifdef __KERNEL__
+
+#include <linux/config.h>
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <asm/system.h>
+#include <asm/atomic.h>
+
+struct rw_semaphore;
+
+#ifdef CONFIG_RWSEM_GENERIC_SPINLOCK
+#include <linux/rwsem-spinlock.h> /* use a generic implementation */
+#else
+#include <asm/rwsem.h> /* use an arch-specific implementation */
+#endif
+
+#ifndef rwsemtrace
+#if RWSEM_DEBUG
+extern void FASTCALL(rwsemtrace(struct rw_semaphore *sem, const char *str));
+#else
+#define rwsemtrace(SEM,FMT)
+#endif
+#endif
+
+/*
+ * lock for reading
+ */
+static inline void down_read(struct rw_semaphore *sem)
+{
+       might_sleep();
+       rwsemtrace(sem,"Entering down_read");
+       __down_read(sem);
+       rwsemtrace(sem,"Leaving down_read");
+}
+
+/*
+ * trylock for reading -- returns 1 if successful, 0 if contention
+ */
+static inline int down_read_trylock(struct rw_semaphore *sem)
+{
+       int ret;
+       rwsemtrace(sem,"Entering down_read_trylock");
+       ret = __down_read_trylock(sem);
+       rwsemtrace(sem,"Leaving down_read_trylock");
+       return ret;
+}
+
+/*
+ * lock for writing
+ */
+static inline void down_write(struct rw_semaphore *sem)
+{
+       might_sleep();
+       rwsemtrace(sem,"Entering down_write");
+       __down_write(sem);
+       rwsemtrace(sem,"Leaving down_write");
+}
+
+/*
+ * trylock for writing -- returns 1 if successful, 0 if contention
+ */
+static inline int down_write_trylock(struct rw_semaphore *sem)
+{
+       int ret;
+       rwsemtrace(sem,"Entering down_write_trylock");
+       ret = __down_write_trylock(sem);
+       rwsemtrace(sem,"Leaving down_write_trylock");
+       return ret;
+}
+
+/*
+ * release a read lock
+ */
+static inline void up_read(struct rw_semaphore *sem)
+{
+       rwsemtrace(sem,"Entering up_read");
+       __up_read(sem);
+       rwsemtrace(sem,"Leaving up_read");
+}
+
+/*
+ * release a write lock
+ */
+static inline void up_write(struct rw_semaphore *sem)
+{
+       rwsemtrace(sem,"Entering up_write");
+       __up_write(sem);
+       rwsemtrace(sem,"Leaving up_write");
+}
+
+/*
+ * downgrade write lock to read lock
+ */
+static inline void downgrade_write(struct rw_semaphore *sem)
+{
+       rwsemtrace(sem,"Entering downgrade_write");
+       __downgrade_write(sem);
+       rwsemtrace(sem,"Leaving downgrade_write");
+}
+
+#endif /* __KERNEL__ */
+#endif /* _LINUX_RWSEM_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/seqlock.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/seqlock.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,175 @@
+#ifndef __LINUX_SEQLOCK_H
+#define __LINUX_SEQLOCK_H
+/*
+ * Reader/writer consistent mechanism without starving writers. This type of
+ * lock for data where the reader wants a consitent set of information
+ * and is willing to retry if the information changes.  Readers never
+ * block but they may have to retry if a writer is in
+ * progress. Writers do not wait for readers. 
+ *
+ * This is not as cache friendly as brlock. Also, this will not work
+ * for data that contains pointers, because any writer could
+ * invalidate a pointer that a reader was following.
+ *
+ * Expected reader usage:
+ *     do {
+ *         seq = read_seqbegin(&foo);
+ *     ...
+ *      } while (read_seqretry(&foo, seq));
+ *
+ *
+ * On non-SMP the spin locks disappear but the writer still needs
+ * to increment the sequence variables because an interrupt routine could
+ * change the state of the data.
+ *
+ * Based on x86_64 vsyscall gettimeofday 
+ * by Keith Owens and Andrea Arcangeli
+ */
+
+#include <linux/config.h>
+#include <linux/spinlock.h>
+#include <linux/preempt.h>
+
+typedef struct {
+       unsigned sequence;
+       spinlock_t lock;
+} seqlock_t;
+
+/*
+ * These macros triggered gcc-3.x compile-time problems.  We think these are
+ * OK now.  Be cautious.
+ */
+#define SEQLOCK_UNLOCKED { 0, SPIN_LOCK_UNLOCKED }
+#define seqlock_init(x)        do { *(x) = (seqlock_t) SEQLOCK_UNLOCKED; } 
while (0)
+
+
+/* Lock out other writers and update the count.
+ * Acts like a normal spin_lock/unlock.
+ * Don't need preempt_disable() because that is in the spin_lock already.
+ */
+static inline void write_seqlock(seqlock_t *sl)
+{
+       spin_lock(&sl->lock);
+       ++sl->sequence;
+       smp_wmb();                      
+}      
+
+static inline void write_sequnlock(seqlock_t *sl) 
+{
+       smp_wmb();
+       sl->sequence++;
+       spin_unlock(&sl->lock);
+}
+
+static inline int write_tryseqlock(seqlock_t *sl)
+{
+       int ret = spin_trylock(&sl->lock);
+
+       if (ret) {
+               ++sl->sequence;
+               smp_wmb();                      
+       }
+       return ret;
+}
+
+/* Start of read calculation -- fetch last complete writer token */
+static inline unsigned read_seqbegin(const seqlock_t *sl)
+{
+       unsigned ret = sl->sequence;
+       smp_rmb();
+       return ret;
+}
+
+/* Test if reader processed invalid data.
+ * If initial values is odd, 
+ *     then writer had already started when section was entered
+ * If sequence value changed
+ *     then writer changed data while in section
+ *    
+ * Using xor saves one conditional branch.
+ */
+static inline int read_seqretry(const seqlock_t *sl, unsigned iv)
+{
+       smp_rmb();
+       return (iv & 1) | (sl->sequence ^ iv);
+}
+
+
+/*
+ * Version using sequence counter only.
+ * This can be used when code has its own mutex protecting the
+ * updating starting before the write_seqcountbeqin() and ending
+ * after the write_seqcount_end().
+ */
+
+typedef struct seqcount {
+       unsigned sequence;
+} seqcount_t;
+
+#define SEQCNT_ZERO { 0 }
+#define seqcount_init(x)       do { *(x) = (seqcount_t) SEQCNT_ZERO; } while 
(0)
+
+/* Start of read using pointer to a sequence counter only.  */
+static inline unsigned read_seqcount_begin(const seqcount_t *s)
+{
+       unsigned ret = s->sequence;
+       smp_rmb();
+       return ret;
+}
+
+/* Test if reader processed invalid data.
+ * Equivalent to: iv is odd or sequence number has changed.
+ *                (iv & 1) || (*s != iv)
+ * Using xor saves one conditional branch.
+ */
+static inline int read_seqcount_retry(const seqcount_t *s, unsigned iv)
+{
+       smp_rmb();
+       return (iv & 1) | (s->sequence ^ iv);
+}
+
+
+/*
+ * Sequence counter only version assumes that callers are using their
+ * own mutexing.
+ */
+static inline void write_seqcount_begin(seqcount_t *s)
+{
+       s->sequence++;
+       smp_wmb();
+}
+
+static inline void write_seqcount_end(seqcount_t *s)
+{
+       smp_wmb();
+       s->sequence++;
+}
+
+/*
+ * Possible sw/hw IRQ protected versions of the interfaces.
+ */
+#define write_seqlock_irqsave(lock, flags)                             \
+       do { local_irq_save(flags); write_seqlock(lock); } while (0)
+#define write_seqlock_irq(lock)                                                
\
+       do { local_irq_disable();   write_seqlock(lock); } while (0)
+#define write_seqlock_bh(lock)                                         \
+        do { local_bh_disable();    write_seqlock(lock); } while (0)
+
+#define write_sequnlock_irqrestore(lock, flags)                                
\
+       do { write_sequnlock(lock); local_irq_restore(flags); } while(0)
+#define write_sequnlock_irq(lock)                                      \
+       do { write_sequnlock(lock); local_irq_enable(); } while(0)
+#define write_sequnlock_bh(lock)                                       \
+       do { write_sequnlock(lock); local_bh_enable(); } while(0)
+
+#define read_seqbegin_irqsave(lock, flags)                             \
+       ({ local_irq_save(flags);   read_seqbegin(lock); })
+
+#define read_seqretry_irqrestore(lock, iv, flags)                      \
+       ({                                                              \
+               int ret = read_seqretry(lock, iv);                      \
+               local_irq_restore(flags);                               \
+               ret;                                                    \
+       })
+
+#endif /* __LINUX_SEQLOCK_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/slab.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/slab.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,3 @@
+#include <xen/xmalloc.h>
+#include <linux/gfp.h>
+#include <asm/delay.h>
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/stddef.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/stddef.h       Tue Aug 16 04:15:23 2005
@@ -0,0 +1,20 @@
+#ifndef _LINUX_STDDEF_H
+#define _LINUX_STDDEF_H
+
+#include <linux/compiler.h>
+
+#undef NULL
+#if defined(__cplusplus)
+#define NULL 0
+#else
+#define NULL ((void *)0)
+#endif
+
+#undef offsetof
+#ifdef __compiler_offsetof
+#define offsetof(TYPE,MEMBER) __compiler_offsetof(TYPE,MEMBER)
+#else
+#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
+#endif
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/thread_info.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/thread_info.h  Tue Aug 16 04:15:23 2005
@@ -0,0 +1,92 @@
+/* thread_info.h: common low-level thread information accessors
+ *
+ * Copyright (C) 2002  David Howells (dhowells@xxxxxxxxxx)
+ * - Incorporating suggestions made by Linus Torvalds
+ */
+
+#ifndef _LINUX_THREAD_INFO_H
+#define _LINUX_THREAD_INFO_H
+
+/*
+ * System call restart block. 
+ */
+struct restart_block {
+       long (*fn)(struct restart_block *);
+       unsigned long arg0, arg1, arg2, arg3;
+};
+
+extern long do_no_restart_syscall(struct restart_block *parm);
+
+#include <linux/bitops.h>
+#include <asm/thread_info.h>
+
+#ifdef __KERNEL__
+
+/*
+ * flag set/clear/test wrappers
+ * - pass TIF_xxxx constants to these functions
+ */
+
+static inline void set_thread_flag(int flag)
+{
+       set_bit(flag,&current_thread_info()->flags);
+}
+
+static inline void clear_thread_flag(int flag)
+{
+       clear_bit(flag,&current_thread_info()->flags);
+}
+
+static inline int test_and_set_thread_flag(int flag)
+{
+       return test_and_set_bit(flag,&current_thread_info()->flags);
+}
+
+static inline int test_and_clear_thread_flag(int flag)
+{
+       return test_and_clear_bit(flag,&current_thread_info()->flags);
+}
+
+static inline int test_thread_flag(int flag)
+{
+       return test_bit(flag,&current_thread_info()->flags);
+}
+
+static inline void set_ti_thread_flag(struct thread_info *ti, int flag)
+{
+       set_bit(flag,&ti->flags);
+}
+
+static inline void clear_ti_thread_flag(struct thread_info *ti, int flag)
+{
+       clear_bit(flag,&ti->flags);
+}
+
+static inline int test_and_set_ti_thread_flag(struct thread_info *ti, int flag)
+{
+       return test_and_set_bit(flag,&ti->flags);
+}
+
+static inline int test_and_clear_ti_thread_flag(struct thread_info *ti, int 
flag)
+{
+       return test_and_clear_bit(flag,&ti->flags);
+}
+
+static inline int test_ti_thread_flag(struct thread_info *ti, int flag)
+{
+       return test_bit(flag,&ti->flags);
+}
+
+static inline void set_need_resched(void)
+{
+       set_thread_flag(TIF_NEED_RESCHED);
+}
+
+static inline void clear_need_resched(void)
+{
+       clear_thread_flag(TIF_NEED_RESCHED);
+}
+
+#endif
+
+#endif /* _LINUX_THREAD_INFO_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/threads.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/threads.h      Tue Aug 16 04:15:23 2005
@@ -0,0 +1,35 @@
+#ifndef _LINUX_THREADS_H
+#define _LINUX_THREADS_H
+
+#include <linux/config.h>
+
+/*
+ * The default limit for the nr of threads is now in
+ * /proc/sys/kernel/threads-max.
+ */
+ 
+/*
+ * Maximum supported processors that can run under SMP.  This value is
+ * set via configure setting.  The maximum is equal to the size of the
+ * bitmasks used on that platform, i.e. 32 or 64.  Setting this smaller
+ * saves quite a bit of memory.
+ */
+#ifdef CONFIG_SMP
+#define NR_CPUS                CONFIG_NR_CPUS
+#else
+#define NR_CPUS                1
+#endif
+
+#define MIN_THREADS_LEFT_FOR_ROOT 4
+
+/*
+ * This controls the default maximum pid allocated to a process
+ */
+#define PID_MAX_DEFAULT 0x8000
+
+/*
+ * A maximum of 4 million PIDs should be enough for a while:
+ */
+#define PID_MAX_LIMIT (sizeof(long) > 4 ? 4*1024*1024 : PID_MAX_DEFAULT)
+
+#endif
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/timex.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/timex.h        Tue Aug 16 04:15:23 2005
@@ -0,0 +1,322 @@
+/*****************************************************************************
+ *                                                                           *
+ * Copyright (c) David L. Mills 1993                                         *
+ *                                                                           *
+ * Permission to use, copy, modify, and distribute this software and its     *
+ * documentation for any purpose and without fee is hereby granted, provided *
+ * that the above copyright notice appears in all copies and that both the   *
+ * copyright notice and this permission notice appear in supporting          *
+ * documentation, and that the name University of Delaware not be used in    *
+ * advertising or publicity pertaining to distribution of the software       *
+ * without specific, written prior permission.  The University of Delaware   *
+ * makes no representations about the suitability this software for any      *
+ * purpose.  It is provided "as is" without express or implied warranty.     *
+ *                                                                           *
+ *****************************************************************************/
+
+/*
+ * Modification history timex.h
+ *
+ * 29 Dec 97   Russell King
+ *     Moved CLOCK_TICK_RATE, CLOCK_TICK_FACTOR and FINETUNE to asm/timex.h
+ *     for ARM machines
+ *
+ *  9 Jan 97    Adrian Sun
+ *      Shifted LATCH define to allow access to alpha machines.
+ *
+ * 26 Sep 94   David L. Mills
+ *     Added defines for hybrid phase/frequency-lock loop.
+ *
+ * 19 Mar 94   David L. Mills
+ *     Moved defines from kernel routines to header file and added new
+ *     defines for PPS phase-lock loop.
+ *
+ * 20 Feb 94   David L. Mills
+ *     Revised status codes and structures for external clock and PPS
+ *     signal discipline.
+ *
+ * 28 Nov 93   David L. Mills
+ *     Adjusted parameters to improve stability and increase poll
+ *     interval.
+ *
+ * 17 Sep 93    David L. Mills
+ *      Created file $NTP/include/sys/timex.h
+ * 07 Oct 93    Torsten Duwe
+ *      Derived linux/timex.h
+ * 1995-08-13    Torsten Duwe
+ *      kernel PLL updated to 1994-12-13 specs (rfc-1589)
+ * 1997-08-30    Ulrich Windl
+ *      Added new constant NTP_PHASE_LIMIT
+ * 2004-08-12    Christoph Lameter
+ *      Reworked time interpolation logic
+ */
+#ifndef _LINUX_TIMEX_H
+#define _LINUX_TIMEX_H
+
+#include <linux/config.h>
+#include <linux/compiler.h>
+#include <linux/time.h>
+
+#include <asm/param.h>
+#include <asm/timex.h>
+
+/*
+ * SHIFT_KG and SHIFT_KF establish the damping of the PLL and are chosen
+ * for a slightly underdamped convergence characteristic. SHIFT_KH
+ * establishes the damping of the FLL and is chosen by wisdom and black
+ * art.
+ *
+ * MAXTC establishes the maximum time constant of the PLL. With the
+ * SHIFT_KG and SHIFT_KF values given and a time constant range from
+ * zero to MAXTC, the PLL will converge in 15 minutes to 16 hours,
+ * respectively.
+ */
+#define SHIFT_KG 6             /* phase factor (shift) */
+#define SHIFT_KF 16            /* PLL frequency factor (shift) */
+#define SHIFT_KH 2             /* FLL frequency factor (shift) */
+#define MAXTC 6                        /* maximum time constant (shift) */
+
+/*
+ * The SHIFT_SCALE define establishes the decimal point of the time_phase
+ * variable which serves as an extension to the low-order bits of the
+ * system clock variable. The SHIFT_UPDATE define establishes the decimal
+ * point of the time_offset variable which represents the current offset
+ * with respect to standard time. The FINENSEC define represents 1 nsec in
+ * scaled units.
+ *
+ * SHIFT_USEC defines the scaling (shift) of the time_freq and
+ * time_tolerance variables, which represent the current frequency
+ * offset and maximum frequency tolerance.
+ *
+ * FINENSEC is 1 ns in SHIFT_UPDATE units of the time_phase variable.
+ */
+#define SHIFT_SCALE 22         /* phase scale (shift) */
+#define SHIFT_UPDATE (SHIFT_KG + MAXTC) /* time offset scale (shift) */
+#define SHIFT_USEC 16          /* frequency offset scale (shift) */
+#define FINENSEC (1L << (SHIFT_SCALE - 10)) /* ~1 ns in phase units */
+
+#define MAXPHASE 512000L        /* max phase error (us) */
+#define MAXFREQ (512L << SHIFT_USEC)  /* max frequency error (ppm) */
+#define MAXTIME (200L << PPS_AVG) /* max PPS error (jitter) (200 us) */
+#define MINSEC 16L              /* min interval between updates (s) */
+#define MAXSEC 1200L            /* max interval between updates (s) */
+#define        NTP_PHASE_LIMIT (MAXPHASE << 5) /* beyond max. dispersion */
+
+/*
+ * The following defines are used only if a pulse-per-second (PPS)
+ * signal is available and connected via a modem control lead, such as
+ * produced by the optional ppsclock feature incorporated in the Sun
+ * asynch driver. They establish the design parameters of the frequency-
+ * lock loop used to discipline the CPU clock oscillator to the PPS
+ * signal.
+ *
+ * PPS_AVG is the averaging factor for the frequency loop, as well as
+ * the time and frequency dispersion.
+ *
+ * PPS_SHIFT and PPS_SHIFTMAX specify the minimum and maximum
+ * calibration intervals, respectively, in seconds as a power of two.
+ *
+ * PPS_VALID is the maximum interval before the PPS signal is considered
+ * invalid and protocol updates used directly instead.
+ *
+ * MAXGLITCH is the maximum interval before a time offset of more than
+ * MAXTIME is believed.
+ */
+#define PPS_AVG 2              /* pps averaging constant (shift) */
+#define PPS_SHIFT 2            /* min interval duration (s) (shift) */
+#define PPS_SHIFTMAX 8         /* max interval duration (s) (shift) */
+#define PPS_VALID 120          /* pps signal watchdog max (s) */
+#define MAXGLITCH 30           /* pps signal glitch max (s) */
+
+/*
+ * syscall interface - used (mainly by NTP daemon)
+ * to discipline kernel clock oscillator
+ */
+struct timex {
+       unsigned int modes;     /* mode selector */
+       long offset;            /* time offset (usec) */
+       long freq;              /* frequency offset (scaled ppm) */
+       long maxerror;          /* maximum error (usec) */
+       long esterror;          /* estimated error (usec) */
+       int status;             /* clock command/status */
+       long constant;          /* pll time constant */
+       long precision;         /* clock precision (usec) (read only) */
+       long tolerance;         /* clock frequency tolerance (ppm)
+                                * (read only)
+                                */
+       struct timeval time;    /* (read only) */
+       long tick;              /* (modified) usecs between clock ticks */
+
+       long ppsfreq;           /* pps frequency (scaled ppm) (ro) */
+       long jitter;            /* pps jitter (us) (ro) */
+       int shift;              /* interval duration (s) (shift) (ro) */
+       long stabil;            /* pps stability (scaled ppm) (ro) */
+       long jitcnt;            /* jitter limit exceeded (ro) */
+       long calcnt;            /* calibration intervals (ro) */
+       long errcnt;            /* calibration errors (ro) */
+       long stbcnt;            /* stability limit exceeded (ro) */
+
+       int  :32; int  :32; int  :32; int  :32;
+       int  :32; int  :32; int  :32; int  :32;
+       int  :32; int  :32; int  :32; int  :32;
+};
+
+/*
+ * Mode codes (timex.mode)
+ */
+#define ADJ_OFFSET             0x0001  /* time offset */
+#define ADJ_FREQUENCY          0x0002  /* frequency offset */
+#define ADJ_MAXERROR           0x0004  /* maximum time error */
+#define ADJ_ESTERROR           0x0008  /* estimated time error */
+#define ADJ_STATUS             0x0010  /* clock status */
+#define ADJ_TIMECONST          0x0020  /* pll time constant */
+#define ADJ_TICK               0x4000  /* tick value */
+#define ADJ_OFFSET_SINGLESHOT  0x8001  /* old-fashioned adjtime */
+
+/* xntp 3.4 compatibility names */
+#define MOD_OFFSET     ADJ_OFFSET
+#define MOD_FREQUENCY  ADJ_FREQUENCY
+#define MOD_MAXERROR   ADJ_MAXERROR
+#define MOD_ESTERROR   ADJ_ESTERROR
+#define MOD_STATUS     ADJ_STATUS
+#define MOD_TIMECONST  ADJ_TIMECONST
+#define MOD_CLKB       ADJ_TICK
+#define MOD_CLKA       ADJ_OFFSET_SINGLESHOT /* 0x8000 in original */
+
+
+/*
+ * Status codes (timex.status)
+ */
+#define STA_PLL                0x0001  /* enable PLL updates (rw) */
+#define STA_PPSFREQ    0x0002  /* enable PPS freq discipline (rw) */
+#define STA_PPSTIME    0x0004  /* enable PPS time discipline (rw) */
+#define STA_FLL                0x0008  /* select frequency-lock mode (rw) */
+
+#define STA_INS                0x0010  /* insert leap (rw) */
+#define STA_DEL                0x0020  /* delete leap (rw) */
+#define STA_UNSYNC     0x0040  /* clock unsynchronized (rw) */
+#define STA_FREQHOLD   0x0080  /* hold frequency (rw) */
+
+#define STA_PPSSIGNAL  0x0100  /* PPS signal present (ro) */
+#define STA_PPSJITTER  0x0200  /* PPS signal jitter exceeded (ro) */
+#define STA_PPSWANDER  0x0400  /* PPS signal wander exceeded (ro) */
+#define STA_PPSERROR   0x0800  /* PPS signal calibration error (ro) */
+
+#define STA_CLOCKERR   0x1000  /* clock hardware fault (ro) */
+
+#define STA_RONLY (STA_PPSSIGNAL | STA_PPSJITTER | STA_PPSWANDER | \
+    STA_PPSERROR | STA_CLOCKERR) /* read-only bits */
+
+/*
+ * Clock states (time_state)
+ */
+#define TIME_OK                0       /* clock synchronized, no leap second */
+#define TIME_INS       1       /* insert leap second */
+#define TIME_DEL       2       /* delete leap second */
+#define TIME_OOP       3       /* leap second in progress */
+#define TIME_WAIT      4       /* leap second has occurred */
+#define TIME_ERROR     5       /* clock not synchronized */
+#define TIME_BAD       TIME_ERROR /* bw compat */
+
+#ifdef __KERNEL__
+/*
+ * kernel variables
+ * Note: maximum error = NTP synch distance = dispersion + delay / 2;
+ * estimated error = NTP dispersion.
+ */
+extern unsigned long tick_usec;                /* USER_HZ period (usec) */
+extern unsigned long tick_nsec;                /* ACTHZ          period (nsec) 
*/
+extern int tickadj;                    /* amount of adjustment per tick */
+
+/*
+ * phase-lock loop variables
+ */
+extern int time_state;         /* clock status */
+extern int time_status;                /* clock synchronization status bits */
+extern long time_offset;       /* time adjustment (us) */
+extern long time_constant;     /* pll time constant */
+extern long time_tolerance;    /* frequency tolerance (ppm) */
+extern long time_precision;    /* clock precision (us) */
+extern long time_maxerror;     /* maximum error */
+extern long time_esterror;     /* estimated error */
+
+extern long time_phase;                /* phase offset (scaled us) */
+extern long time_freq;         /* frequency offset (scaled ppm) */
+extern long time_adj;          /* tick adjust (scaled 1 / HZ) */
+extern long time_reftime;      /* time at last adjustment (s) */
+
+extern long time_adjust;       /* The amount of adjtime left */
+extern long time_next_adjust;  /* Value for time_adjust at next tick */
+
+/* interface variables pps->timer interrupt */
+extern long pps_offset;                /* pps time offset (us) */
+extern long pps_jitter;                /* time dispersion (jitter) (us) */
+extern long pps_freq;          /* frequency offset (scaled ppm) */
+extern long pps_stabil;                /* frequency dispersion (scaled ppm) */
+extern long pps_valid;         /* pps signal watchdog counter */
+
+/* interface variables pps->adjtimex */
+extern int pps_shift;          /* interval duration (s) (shift) */
+extern long pps_jitcnt;                /* jitter limit exceeded */
+extern long pps_calcnt;                /* calibration intervals */
+extern long pps_errcnt;                /* calibration errors */
+extern long pps_stbcnt;                /* stability limit exceeded */
+
+#ifdef CONFIG_TIME_INTERPOLATION
+
+#define TIME_SOURCE_CPU 0
+#define TIME_SOURCE_MMIO64 1
+#define TIME_SOURCE_MMIO32 2
+#define TIME_SOURCE_FUNCTION 3
+
+/* For proper operations time_interpolator clocks must run slightly slower
+ * than the standard clock since the interpolator may only correct by having
+ * time jump forward during a tick. A slower clock is usually a side effect
+ * of the integer divide of the nanoseconds in a second by the frequency.
+ * The accuracy of the division can be increased by specifying a shift.
+ * However, this may cause the clock not to be slow enough.
+ * The interpolator will self-tune the clock by slowing down if no
+ * resets occur or speeding up if the time jumps per analysis cycle
+ * become too high.
+ *
+ * Setting jitter compensates for a fluctuating timesource by comparing
+ * to the last value read from the timesource to insure that an earlier value
+ * is not returned by a later call. The price to pay
+ * for the compensation is that the timer routines are not as scalable anymore.
+ */
+
+struct time_interpolator {
+       u16 source;                     /* time source flags */
+       u8 shift;                       /* increases accuracy of multiply by 
shifting. */
+                               /* Note that bits may be lost if shift is set 
too high */
+       u8 jitter;                      /* if set compensate for fluctuations */
+       u32 nsec_per_cyc;               /* set by register_time_interpolator() 
*/
+       void *addr;                     /* address of counter or function */
+       u64 mask;                       /* mask the valid bits of the counter */
+       unsigned long offset;           /* nsec offset at last update of 
interpolator */
+       u64 last_counter;               /* counter value in units of the 
counter at last update */
+       u64 last_cycle;                 /* Last timer value if 
TIME_SOURCE_JITTER is set */
+       u64 frequency;                  /* frequency in counts/second */
+       long drift;                     /* drift in parts-per-million (or -1) */
+       unsigned long skips;            /* skips forward */
+       unsigned long ns_skipped;       /* nanoseconds skipped */
+       struct time_interpolator *next;
+};
+
+extern void register_time_interpolator(struct time_interpolator *);
+extern void unregister_time_interpolator(struct time_interpolator *);
+extern void time_interpolator_reset(void);
+extern unsigned long time_interpolator_get_offset(void);
+
+#else /* !CONFIG_TIME_INTERPOLATION */
+
+static inline void
+time_interpolator_reset(void)
+{
+}
+
+#endif /* !CONFIG_TIME_INTERPOLATION */
+
+#endif /* KERNEL */
+
+#endif /* LINUX_TIMEX_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/topology.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/topology.h     Tue Aug 16 04:15:23 2005
@@ -0,0 +1,133 @@
+/*
+ * include/linux/topology.h
+ *
+ * Written by: Matthew Dobson, IBM Corporation
+ *
+ * Copyright (C) 2002, IBM Corp.
+ *
+ * All rights reserved.          
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or
+ * NON INFRINGEMENT.  See the GNU General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * Send feedback to <colpatch@xxxxxxxxxx>
+ */
+#ifndef _LINUX_TOPOLOGY_H
+#define _LINUX_TOPOLOGY_H
+
+#include <linux/cpumask.h>
+#include <linux/bitops.h>
+#include <linux/mmzone.h>
+#include <linux/smp.h>
+
+#include <asm/topology.h>
+
+#ifndef nr_cpus_node
+#define nr_cpus_node(node)                                                     
\
+       ({                                                                      
\
+               cpumask_t __tmp__;                                              
\
+               __tmp__ = node_to_cpumask(node);                                
\
+               cpus_weight(__tmp__);                                           
\
+       })
+#endif
+
+#define for_each_node_with_cpus(node)                                          
\
+       for_each_online_node(node)                                              
\
+               if (nr_cpus_node(node))
+
+#ifndef node_distance
+/* Conform to ACPI 2.0 SLIT distance definitions */
+#define LOCAL_DISTANCE         10
+#define REMOTE_DISTANCE                20
+#define node_distance(from,to) ((from) == (to) ? LOCAL_DISTANCE : 
REMOTE_DISTANCE)
+#endif
+#ifndef PENALTY_FOR_NODE_WITH_CPUS
+#define PENALTY_FOR_NODE_WITH_CPUS     (1)
+#endif
+
+/*
+ * Below are the 3 major initializers used in building sched_domains:
+ * SD_SIBLING_INIT, for SMT domains
+ * SD_CPU_INIT, for SMP domains
+ * SD_NODE_INIT, for NUMA domains
+ *
+ * Any architecture that cares to do any tuning to these values should do so
+ * by defining their own arch-specific initializer in include/asm/topology.h.
+ * A definition there will automagically override these default initializers
+ * and allow arch-specific performance tuning of sched_domains.
+ */
+#ifdef CONFIG_SCHED_SMT
+/* MCD - Do we really need this?  It is always on if CONFIG_SCHED_SMT is,
+ * so can't we drop this in favor of CONFIG_SCHED_SMT?
+ */
+#define ARCH_HAS_SCHED_WAKE_IDLE
+/* Common values for SMT siblings */
+#ifndef SD_SIBLING_INIT
+#define SD_SIBLING_INIT (struct sched_domain) {                \
+       .span                   = CPU_MASK_NONE,        \
+       .parent                 = NULL,                 \
+       .groups                 = NULL,                 \
+       .min_interval           = 1,                    \
+       .max_interval           = 2,                    \
+       .busy_factor            = 8,                    \
+       .imbalance_pct          = 110,                  \
+       .cache_hot_time         = 0,                    \
+       .cache_nice_tries       = 0,                    \
+       .per_cpu_gain           = 25,                   \
+       .flags                  = SD_LOAD_BALANCE       \
+                               | SD_BALANCE_NEWIDLE    \
+                               | SD_BALANCE_EXEC       \
+                               | SD_WAKE_AFFINE        \
+                               | SD_WAKE_IDLE          \
+                               | SD_SHARE_CPUPOWER,    \
+       .last_balance           = jiffies,              \
+       .balance_interval       = 1,                    \
+       .nr_balance_failed      = 0,                    \
+}
+#endif
+#endif /* CONFIG_SCHED_SMT */
+
+/* Common values for CPUs */
+#ifndef SD_CPU_INIT
+#define SD_CPU_INIT (struct sched_domain) {            \
+       .span                   = CPU_MASK_NONE,        \
+       .parent                 = NULL,                 \
+       .groups                 = NULL,                 \
+       .min_interval           = 1,                    \
+       .max_interval           = 4,                    \
+       .busy_factor            = 64,                   \
+       .imbalance_pct          = 125,                  \
+       .cache_hot_time         = (5*1000000/2),        \
+       .cache_nice_tries       = 1,                    \
+       .per_cpu_gain           = 100,                  \
+       .flags                  = SD_LOAD_BALANCE       \
+                               | SD_BALANCE_NEWIDLE    \
+                               | SD_BALANCE_EXEC       \
+                               | SD_WAKE_AFFINE        \
+                               | SD_WAKE_IDLE          \
+                               | SD_WAKE_BALANCE,      \
+       .last_balance           = jiffies,              \
+       .balance_interval       = 1,                    \
+       .nr_balance_failed      = 0,                    \
+}
+#endif
+
+#ifdef CONFIG_NUMA
+#ifndef SD_NODE_INIT
+#error Please define an appropriate SD_NODE_INIT in include/asm/topology.h!!!
+#endif
+#endif /* CONFIG_NUMA */
+
+#endif /* _LINUX_TOPOLOGY_H */
diff -r b5196e075602 -r e3d811cca4e1 xen/include/asm-ia64/linux/wait.h
--- /dev/null   Mon Aug 15 20:28:07 2005
+++ b/xen/include/asm-ia64/linux/wait.h Tue Aug 16 04:15:23 2005
@@ -0,0 +1,400 @@
+#ifndef _LINUX_WAIT_H
+#define _LINUX_WAIT_H
+
+#define WNOHANG                0x00000001
+#define WUNTRACED      0x00000002
+#define WSTOPPED       WUNTRACED
+#define WEXITED                0x00000004
+#define WCONTINUED     0x00000008
+#define WNOWAIT                0x01000000      /* Don't reap, just poll 
status.  */
+
+#define __WNOTHREAD    0x20000000      /* Don't wait on children of other 
threads in this group */
+#define __WALL         0x40000000      /* Wait on all children, regardless of 
type */
+#define __WCLONE       0x80000000      /* Wait only on non-SIGCHLD children */
+
+/* First argument to waitid: */
+#define P_ALL          0
+#define P_PID          1
+#define P_PGID         2
+
+#ifdef __KERNEL__
+
+#include <linux/config.h>
+#include <linux/list.h>
+#include <linux/stddef.h>
+#include <linux/spinlock.h>
+#include <asm/system.h>
+#include <asm/current.h>
+
+typedef struct __wait_queue wait_queue_t;
+typedef int (*wait_queue_func_t)(wait_queue_t *wait, unsigned mode, int sync, 
void *key);
+int default_wake_function(wait_queue_t *wait, unsigned mode, int sync, void 
*key);
+
+struct __wait_queue {
+       unsigned int flags;
+#define WQ_FLAG_EXCLUSIVE      0x01
+       struct task_struct * task;
+       wait_queue_func_t func;
+       struct list_head task_list;
+};
+
+struct wait_bit_key {
+       void *flags;
+       int bit_nr;
+};
+
+struct wait_bit_queue {
+       struct wait_bit_key key;
+       wait_queue_t wait;
+};
+
+struct __wait_queue_head {
+       spinlock_t lock;
+       struct list_head task_list;
+};
+typedef struct __wait_queue_head wait_queue_head_t;
+
+
+/*
+ * Macros for declaration and initialisaton of the datatypes
+ */
+
+#define __WAITQUEUE_INITIALIZER(name, tsk) {                           \
+       .task           = tsk,                                          \
+       .func           = default_wake_function,                        \
+       .task_list      = { NULL, NULL } }
+
+#define DECLARE_WAITQUEUE(name, tsk)                                   \
+       wait_queue_t name = __WAITQUEUE_INITIALIZER(name, tsk)
+
+#define __WAIT_QUEUE_HEAD_INITIALIZER(name) {                          \
+       .lock           = SPIN_LOCK_UNLOCKED,                           \
+       .task_list      = { &(name).task_list, &(name).task_list } }
+
+#define DECLARE_WAIT_QUEUE_HEAD(name) \
+       wait_queue_head_t name = __WAIT_QUEUE_HEAD_INITIALIZER(name)
+
+#define __WAIT_BIT_KEY_INITIALIZER(word, bit)                          \
+       { .flags = word, .bit_nr = bit, }
+
+static inline void init_waitqueue_head(wait_queue_head_t *q)
+{
+       q->lock = SPIN_LOCK_UNLOCKED;
+       INIT_LIST_HEAD(&q->task_list);
+}
+
+static inline void init_waitqueue_entry(wait_queue_t *q, struct task_struct *p)
+{
+       q->flags = 0;
+       q->task = p;
+       q->func = default_wake_function;
+}
+
+static inline void init_waitqueue_func_entry(wait_queue_t *q,
+                                       wait_queue_func_t func)
+{
+       q->flags = 0;
+       q->task = NULL;
+       q->func = func;
+}
+
+static inline int waitqueue_active(wait_queue_head_t *q)
+{
+       return !list_empty(&q->task_list);
+}
+
+/*
+ * Used to distinguish between sync and async io wait context:
+ * sync i/o typically specifies a NULL wait queue entry or a wait
+ * queue entry bound to a task (current task) to wake up.
+ * aio specifies a wait queue entry with an async notification
+ * callback routine, not associated with any task.
+ */
+#define is_sync_wait(wait)     (!(wait) || ((wait)->task))
+
+extern void FASTCALL(add_wait_queue(wait_queue_head_t *q, wait_queue_t * 
wait));
+extern void FASTCALL(add_wait_queue_exclusive(wait_queue_head_t *q, 
wait_queue_t * wait));
+extern void FASTCALL(remove_wait_queue(wait_queue_head_t *q, wait_queue_t * 
wait));
+
+static inline void __add_wait_queue(wait_queue_head_t *head, wait_queue_t *new)
+{
+       list_add(&new->task_list, &head->task_list);
+}
+
+/*
+ * Used for wake-one threads:
+ */
+static inline void __add_wait_queue_tail(wait_queue_head_t *head,
+                                               wait_queue_t *new)
+{
+       list_add_tail(&new->task_list, &head->task_list);
+}
+
+static inline void __remove_wait_queue(wait_queue_head_t *head,
+                                                       wait_queue_t *old)
+{
+       list_del(&old->task_list);
+}
+
+void FASTCALL(__wake_up(wait_queue_head_t *q, unsigned int mode, int nr, void 
*key));
+extern void FASTCALL(__wake_up_locked(wait_queue_head_t *q, unsigned int 
mode));
+extern void FASTCALL(__wake_up_sync(wait_queue_head_t *q, unsigned int mode, 
int nr));
+void FASTCALL(__wake_up_bit(wait_queue_head_t *, void *, int));
+int FASTCALL(__wait_on_bit(wait_queue_head_t *, struct wait_bit_queue *, int 
(*)(void *), unsigned));
+int FASTCALL(__wait_on_bit_lock(wait_queue_head_t *, struct wait_bit_queue *, 
int (*)(void *), unsigned));
+void FASTCALL(wake_up_bit(void *, int));
+int FASTCALL(out_of_line_wait_on_bit(void *, int, int (*)(void *), unsigned));
+int FASTCALL(out_of_line_wait_on_bit_lock(void *, int, int (*)(void *), 
unsigned));
+wait_queue_head_t *FASTCALL(bit_waitqueue(void *, int));
+
+#define wake_up(x)                     __wake_up(x, TASK_UNINTERRUPTIBLE | 
TASK_INTERRUPTIBLE, 1, NULL)
+#define wake_up_nr(x, nr)              __wake_up(x, TASK_UNINTERRUPTIBLE | 
TASK_INTERRUPTIBLE, nr, NULL)
+#define wake_up_all(x)                 __wake_up(x, TASK_UNINTERRUPTIBLE | 
TASK_INTERRUPTIBLE, 0, NULL)
+#define wake_up_interruptible(x)       __wake_up(x, TASK_INTERRUPTIBLE, 1, 
NULL)
+#define wake_up_interruptible_nr(x, nr)        __wake_up(x, 
TASK_INTERRUPTIBLE, nr, NULL)
+#define wake_up_interruptible_all(x)   __wake_up(x, TASK_INTERRUPTIBLE, 0, 
NULL)
+#define        wake_up_locked(x)               __wake_up_locked((x), 
TASK_UNINTERRUPTIBLE | TASK_INTERRUPTIBLE)
+#define wake_up_interruptible_sync(x)   __wake_up_sync((x),TASK_INTERRUPTIBLE, 
1)
+
+#define __wait_event(wq, condition)                                    \
+do {                                                                   \
+       DEFINE_WAIT(__wait);                                            \
+                                                                       \
+       for (;;) {                                                      \
+               prepare_to_wait(&wq, &__wait, TASK_UNINTERRUPTIBLE);    \
+               if (condition)                                          \
+                       break;                                          \
+               schedule();                                             \
+       }                                                               \
+       finish_wait(&wq, &__wait);                                      \
+} while (0)
+
+#define wait_event(wq, condition)                                      \
+do {                                                                   \
+       if (condition)                                                  \
+               break;                                                  \
+       __wait_event(wq, condition);                                    \
+} while (0)
+
+#define __wait_event_timeout(wq, condition, ret)                       \
+do {                                                                   \
+       DEFINE_WAIT(__wait);                                            \
+                                                                       \
+       for (;;) {                                                      \
+               prepare_to_wait(&wq, &__wait, TASK_UNINTERRUPTIBLE);    \
+               if (condition)                                          \
+                       break;                                          \
+               ret = schedule_timeout(ret);                            \
+               if (!ret)                                               \
+                       break;                                          \
+       }                                                               \
+       finish_wait(&wq, &__wait);                                      \
+} while (0)
+
+#define wait_event_timeout(wq, condition, timeout)                     \
+({                                                                     \
+       long __ret = timeout;                                           \
+       if (!(condition))                                               \
+               __wait_event_timeout(wq, condition, __ret);             \
+       __ret;                                                          \
+})
+
+#define __wait_event_interruptible(wq, condition, ret)                 \
+do {                                                                   \
+       DEFINE_WAIT(__wait);                                            \
+                                                                       \
+       for (;;) {                                                      \
+               prepare_to_wait(&wq, &__wait, TASK_INTERRUPTIBLE);      \
+               if (condition)                                          \
+                       break;                                          \
+               if (!signal_pending(current)) {                         \
+                       schedule();                                     \
+                       continue;                                       \
+               }                                                       \
+               ret = -ERESTARTSYS;                                     \
+               break;                                                  \
+       }                                                               \
+       finish_wait(&wq, &__wait);                                      \
+} while (0)
+
+#define wait_event_interruptible(wq, condition)                                
\
+({                                                                     \
+       int __ret = 0;                                                  \
+       if (!(condition))                                               \
+               __wait_event_interruptible(wq, condition, __ret);       \
+       __ret;                                                          \
+})
+
+#define __wait_event_interruptible_timeout(wq, condition, ret)         \
+do {                                                                   \
+       DEFINE_WAIT(__wait);                                            \
+                                                                       \
+       for (;;) {                                                      \
+               prepare_to_wait(&wq, &__wait, TASK_INTERRUPTIBLE);      \
+               if (condition)                                          \
+                       break;                                          \
+               if (!signal_pending(current)) {                         \
+                       ret = schedule_timeout(ret);                    \
+                       if (!ret)                                       \
+                               break;                                  \
+                       continue;                                       \
+               }                                                       \
+               ret = -ERESTARTSYS;                                     \
+               break;                                                  \
+       }                                                               \
+       finish_wait(&wq, &__wait);                                      \
+} while (0)
+
+#define wait_event_interruptible_timeout(wq, condition, timeout)       \
+({                                                                     \
+       long __ret = timeout;                                           \
+       if (!(condition))                                               \
+               __wait_event_interruptible_timeout(wq, condition, __ret); \
+       __ret;                                                          \
+})
+
+#define __wait_event_interruptible_exclusive(wq, condition, ret)       \
+do {                                                                   \
+       DEFINE_WAIT(__wait);                                            \
+                                                                       \
+       for (;;) {                                                      \
+               prepare_to_wait_exclusive(&wq, &__wait,                 \
+                                       TASK_INTERRUPTIBLE);            \
+               if (condition)                                          \
+                       break;                                          \
+               if (!signal_pending(current)) {                         \
+                       schedule();                                     \
+                       continue;                                       \
+               }                                                       \
+               ret = -ERESTARTSYS;                                     \
+               break;                                                  \
+       }                                                               \
+       finish_wait(&wq, &__wait);                                      \
+} while (0)
+
+#define wait_event_interruptible_exclusive(wq, condition)              \
+({                                                                     \
+       int __ret = 0;                                                  \
+       if (!(condition))                                               \
+               __wait_event_interruptible_exclusive(wq, condition, __ret);\
+       __ret;                                                          \
+})
+
+/*
+ * Must be called with the spinlock in the wait_queue_head_t held.
+ */
+static inline void add_wait_queue_exclusive_locked(wait_queue_head_t *q,
+                                                  wait_queue_t * wait)
+{
+       wait->flags |= WQ_FLAG_EXCLUSIVE;
+       __add_wait_queue_tail(q,  wait);
+}
+
+/*
+ * Must be called with the spinlock in the wait_queue_head_t held.
+ */
+static inline void remove_wait_queue_locked(wait_queue_head_t *q,
+                                           wait_queue_t * wait)
+{
+       __remove_wait_queue(q,  wait);
+}
+
+/*
+ * These are the old interfaces to sleep waiting for an event.
+ * They are racy.  DO NOT use them, use the wait_event* interfaces above.  
+ * We plan to remove these interfaces during 2.7.
+ */
+extern void FASTCALL(sleep_on(wait_queue_head_t *q));
+extern long FASTCALL(sleep_on_timeout(wait_queue_head_t *q,
+                                     signed long timeout));
+extern void FASTCALL(interruptible_sleep_on(wait_queue_head_t *q));
+extern long FASTCALL(interruptible_sleep_on_timeout(wait_queue_head_t *q,
+                                                   signed long timeout));
+
+/*
+ * Waitqueues which are removed from the waitqueue_head at wakeup time
+ */
+void FASTCALL(prepare_to_wait(wait_queue_head_t *q,
+                               wait_queue_t *wait, int state));
+void FASTCALL(prepare_to_wait_exclusive(wait_queue_head_t *q,
+                               wait_queue_t *wait, int state));
+void FASTCALL(finish_wait(wait_queue_head_t *q, wait_queue_t *wait));
+int autoremove_wake_function(wait_queue_t *wait, unsigned mode, int sync, void 
*key);
+int wake_bit_function(wait_queue_t *wait, unsigned mode, int sync, void *key);
+
+#define DEFINE_WAIT(name)                                              \
+       wait_queue_t name = {                                           \
+               .task           = current,                              \
+               .func           = autoremove_wake_function,             \
+               .task_list      = {     .next = &(name).task_list,      \
+                                       .prev = &(name).task_list,      \
+                               },                                      \
+       }
+
+#define DEFINE_WAIT_BIT(name, word, bit)                               \
+       struct wait_bit_queue name = {                                  \
+               .key = __WAIT_BIT_KEY_INITIALIZER(word, bit),           \
+               .wait   = {                                             \
+                       .task           = current,                      \
+                       .func           = wake_bit_function,            \
+                       .task_list      =                               \
+                               LIST_HEAD_INIT((name).wait.task_list),  \
+               },                                                      \
+       }
+
+#define init_wait(wait)                                                        
\
+       do {                                                            \
+               (wait)->task = current;                                 \
+               (wait)->func = autoremove_wake_function;                \
+               INIT_LIST_HEAD(&(wait)->task_list);                     \
+       } while (0)
+
+/**
+ * wait_on_bit - wait for a bit to be cleared
+ * @word: the word being waited on, a kernel virtual address
+ * @bit: the bit of the word being waited on
+ * @action: the function used to sleep, which may take special actions
+ * @mode: the task state to sleep in
+ *
+ * There is a standard hashed waitqueue table for generic use. This
+ * is the part of the hashtable's accessor API that waits on a bit.
+ * For instance, if one were to have waiters on a bitflag, one would
+ * call wait_on_bit() in threads waiting for the bit to clear.
+ * One uses wait_on_bit() where one is waiting for the bit to clear,
+ * but has no intention of setting it.
+ */
+static inline int wait_on_bit(void *word, int bit,
+                               int (*action)(void *), unsigned mode)
+{
+       if (!test_bit(bit, word))
+               return 0;
+       return out_of_line_wait_on_bit(word, bit, action, mode);
+}
+
+/**
+ * wait_on_bit_lock - wait for a bit to be cleared, when wanting to set it
+ * @word: the word being waited on, a kernel virtual address
+ * @bit: the bit of the word being waited on
+ * @action: the function used to sleep, which may take special actions
+ * @mode: the task state to sleep in
+ *
+ * There is a standard hashed waitqueue table for generic use. This
+ * is the part of the hashtable's accessor API that waits on a bit
+ * when one intends to set it, for instance, trying to lock bitflags.
+ * For instance, if one were to have waiters trying to set bitflag
+ * and waiting for it to clear before setting it, one would call
+ * wait_on_bit() in threads waiting to be able to set the bit.
+ * One uses wait_on_bit_lock() where one is waiting for the bit to
+ * clear with the intention of setting it, and when done, clearing it.
+ */
+static inline int wait_on_bit_lock(void *word, int bit,
+                               int (*action)(void *), unsigned mode)
+{
+       if (!test_and_set_bit(bit, word))
+               return 0;
+       return out_of_line_wait_on_bit_lock(word, bit, action, mode);
+}
+       
+#endif /* __KERNEL__ */
+
+#endif

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

<Prev in Thread] Current Thread [Next in Thread>