[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [xen-unstable] IA64-specific code for new Qemu
# HG changeset patch # User chris@xxxxxxxxxxxxxxxxxxxxxxxx # Node ID 42aa63188a88d8c384a74e42163963bb84f974af # Parent 7654157278f1403614c047247751418fd25846c5 IA64-specific code for new Qemu Due to some ia64 patches aren't checked into xen-unstable.hg. I reversed related logic. Signed-off-by: Zhang xiantao <xiantao.zhang@xxxxxxxxx> Signed-off-by: Christian Limpach <Christian.Limpach@xxxxxxxxxxxxx> --- tools/ioemu/cpu-all.h | 25 ++++++++ tools/ioemu/exec-all.h | 22 +++++-- tools/ioemu/hw/iommu.c | 4 + tools/ioemu/patches/domain-timeoffset | 10 +-- tools/ioemu/patches/ioemu-ia64 | 93 ++++++++++++++++++++++++++++++++ tools/ioemu/patches/series | 1 tools/ioemu/patches/vnc-fixes | 6 +- tools/ioemu/patches/vnc-start-vncviewer | 8 +- tools/ioemu/target-i386-dm/cpu.h | 4 + tools/ioemu/target-i386-dm/exec-dm.c | 20 ++++++ tools/ioemu/vl.c | 29 +++++++++ 11 files changed, 204 insertions(+), 18 deletions(-) diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/cpu-all.h --- a/tools/ioemu/cpu-all.h Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/cpu-all.h Wed Jul 26 13:41:10 2006 +0100 @@ -835,6 +835,31 @@ static __inline__ void atomic_clear_bit( :"=m" (*(volatile long *)addr) :"dIr" (nr)); } +#elif defined(__ia64__) +#include "ia64_intrinsic.h" +#define atomic_set_bit(nr, addr) ({ \ + typeof(*addr) bit, old, new; \ + volatile typeof(*addr) *m; \ + \ + m = (volatile typeof(*addr)*)(addr + nr / (8*sizeof(*addr))); \ + bit = 1 << (nr % (8*sizeof(*addr))); \ + do { \ + old = *m; \ + new = old | bit; \ + } while (cmpxchg_acq(m, old, new) != old); \ +}) + +#define atomic_clear_bit(nr, addr) ({ \ + typeof(*addr) bit, old, new; \ + volatile typeof(*addr) *m; \ + \ + m = (volatile typeof(*addr)*)(addr + nr / (8*sizeof(*addr))); \ + bit = ~(1 << (nr % (8*sizeof(*addr)))); \ + do { \ + old = *m; \ + new = old & bit; \ + } while (cmpxchg_acq(m, old, new) != old); \ +}) #endif /* memory API */ diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/exec-all.h --- a/tools/ioemu/exec-all.h Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/exec-all.h Wed Jul 26 13:41:10 2006 +0100 @@ -391,6 +391,15 @@ static inline int testandset (int *p) } #endif +#ifdef __ia64__ +#include "ia64_intrinsic.h" +static inline int testandset (int *p) +{ + uint32_t o = 0, n = 1; + return (int)cmpxchg_acq(p, o, n); +} +#endif + #ifdef __s390__ static inline int testandset (int *p) { @@ -462,12 +471,13 @@ static inline int testandset (int *p) } #endif -#ifdef __ia64 -#include <ia64intrin.h> - -static inline int testandset (int *p) -{ - return __sync_lock_test_and_set (p, 1); +#ifdef __ia64__ +#include "ia64_intrinsic.h" + +static inline int testandset (int *p) +{ + uint32_t o = 0, n = 1; + return (int)cmpxchg_acq(p, o, n); } #endif diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/hw/iommu.c --- a/tools/ioemu/hw/iommu.c Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/hw/iommu.c Wed Jul 26 13:41:10 2006 +0100 @@ -82,7 +82,11 @@ do { printf("IOMMU: " fmt , ##args); } w #define IOPTE_VALID 0x00000002 /* IOPTE is valid */ #define IOPTE_WAZ 0x00000001 /* Write as zeros */ +#if defined(__i386__) || defined(__x86_64__) #define PAGE_SHIFT 12 +#elif defined(__ia64__) +#define PAGE_SHIFT 14 +#endif #define PAGE_SIZE (1 << PAGE_SHIFT) #define PAGE_MASK (PAGE_SIZE - 1) diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/patches/domain-timeoffset --- a/tools/ioemu/patches/domain-timeoffset Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/patches/domain-timeoffset Wed Jul 26 13:41:10 2006 +0100 @@ -1,7 +1,7 @@ Index: ioemu/hw/mc146818rtc.c Index: ioemu/hw/mc146818rtc.c =================================================================== ---- ioemu.orig/hw/mc146818rtc.c 2006-07-26 13:18:13.783025944 +0100 -+++ ioemu/hw/mc146818rtc.c 2006-07-26 13:20:34.934314196 +0100 +--- ioemu.orig/hw/mc146818rtc.c 2006-07-26 13:39:11.256088974 +0100 ++++ ioemu/hw/mc146818rtc.c 2006-07-26 13:39:18.026364657 +0100 @@ -178,10 +178,27 @@ } } @@ -46,8 +46,8 @@ Index: ioemu/hw/mc146818rtc.c static void rtc_copy_date(RTCState *s) Index: ioemu/hw/pc.c =================================================================== ---- ioemu.orig/hw/pc.c 2006-07-26 13:20:34.463363339 +0100 -+++ ioemu/hw/pc.c 2006-07-26 13:20:34.935314092 +0100 +--- ioemu.orig/hw/pc.c 2006-07-26 13:39:17.773391722 +0100 ++++ ioemu/hw/pc.c 2006-07-26 13:39:18.027364550 +0100 @@ -151,7 +151,7 @@ } @@ -117,8 +117,8 @@ Index: ioemu/hw/pc.c QEMUMachine pc_machine = { Index: ioemu/vl.c =================================================================== ---- ioemu.orig/vl.c 2006-07-26 13:20:34.812326925 +0100 -+++ ioemu/vl.c 2006-07-26 13:20:34.937313883 +0100 +--- ioemu.orig/vl.c 2006-07-26 13:39:17.903377815 +0100 ++++ ioemu/vl.c 2006-07-26 13:39:18.029364336 +0100 @@ -164,6 +164,8 @@ int xc_handle; @@ -162,7 +162,7 @@ Index: ioemu/vl.c } } } -@@ -5963,7 +5971,8 @@ +@@ -5992,7 +6000,8 @@ machine->init(ram_size, vga_ram_size, boot_device, ds, fd_filename, snapshot, @@ -174,8 +174,8 @@ Index: ioemu/vl.c qemu_mod_timer(gui_timer, qemu_get_clock(rt_clock)); Index: ioemu/vl.h =================================================================== ---- ioemu.orig/vl.h 2006-07-26 13:20:34.467362921 +0100 -+++ ioemu/vl.h 2006-07-26 13:20:34.938313779 +0100 +--- ioemu.orig/vl.h 2006-07-26 13:39:17.778391187 +0100 ++++ ioemu/vl.h 2006-07-26 13:39:18.030364229 +0100 @@ -556,7 +556,7 @@ int boot_device, DisplayState *ds, const char **fd_filename, int snapshot, diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/patches/series --- a/tools/ioemu/patches/series Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/patches/series Wed Jul 26 13:41:10 2006 +0100 @@ -10,6 +10,7 @@ xen-domain-name xen-domain-name xen-domid xen-mm +ioemu-ia64 qemu-smp qemu-no-apic qemu-nobios diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/patches/vnc-fixes --- a/tools/ioemu/patches/vnc-fixes Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/patches/vnc-fixes Wed Jul 26 13:41:10 2006 +0100 @@ -1,8 +1,8 @@ Index: ioemu/vl.c Index: ioemu/vl.c =================================================================== ---- ioemu.orig/vl.c 2006-07-14 15:56:03.043099185 +0100 -+++ ioemu/vl.c 2006-07-14 15:56:03.123090082 +0100 -@@ -5974,8 +5974,10 @@ +--- ioemu.orig/vl.c 2006-07-26 13:39:18.439320475 +0100 ++++ ioemu/vl.c 2006-07-26 13:39:18.499314057 +0100 +@@ -6003,8 +6003,10 @@ kernel_filename, kernel_cmdline, initrd_filename, timeoffset); @@ -17,8 +17,8 @@ Index: ioemu/vl.c if (use_gdbstub) { Index: ioemu/vnc.c =================================================================== ---- ioemu.orig/vnc.c 2006-07-14 15:56:03.040099527 +0100 -+++ ioemu/vnc.c 2006-07-14 15:56:03.124089968 +0100 +--- ioemu.orig/vnc.c 2006-07-26 13:39:18.437320689 +0100 ++++ ioemu/vnc.c 2006-07-26 13:39:18.500313950 +0100 @@ -3,6 +3,7 @@ * * Copyright (C) 2006 Anthony Liguori <anthony@xxxxxxxxxxxxx> diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/patches/vnc-start-vncviewer --- a/tools/ioemu/patches/vnc-start-vncviewer Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/patches/vnc-start-vncviewer Wed Jul 26 13:41:10 2006 +0100 @@ -1,7 +1,7 @@ Index: ioemu/vnc.c Index: ioemu/vnc.c =================================================================== ---- ioemu.orig/vnc.c 2006-07-14 18:29:36.810169908 +0100 -+++ ioemu/vnc.c 2006-07-14 18:30:17.437628819 +0100 +--- ioemu.orig/vnc.c 2006-07-26 13:39:18.500313950 +0100 ++++ ioemu/vnc.c 2006-07-26 13:39:18.648298117 +0100 @@ -999,3 +999,25 @@ vnc_dpy_resize(vs->ds, 640, 400); @@ -30,8 +30,8 @@ Index: ioemu/vnc.c +} Index: ioemu/vl.c =================================================================== ---- ioemu.orig/vl.c 2006-07-14 18:29:36.809170020 +0100 -+++ ioemu/vl.c 2006-07-14 18:30:17.435629043 +0100 +--- ioemu.orig/vl.c 2006-07-26 13:39:18.499314057 +0100 ++++ ioemu/vl.c 2006-07-26 13:39:18.650297903 +0100 @@ -121,6 +121,7 @@ int bios_size; static DisplayState display_state; @@ -82,7 +82,7 @@ Index: ioemu/vl.c case QEMU_OPTION_domainname: strncat(domain_name, optarg, sizeof(domain_name) - 20); break; -@@ -5881,6 +5889,8 @@ +@@ -5910,6 +5918,8 @@ dumb_display_init(ds); } else if (vnc_display != -1) { vnc_display_init(ds, vnc_display); @@ -93,8 +93,8 @@ Index: ioemu/vl.c sdl_display_init(ds, full_screen); Index: ioemu/vl.h =================================================================== ---- ioemu.orig/vl.h 2006-07-14 18:29:36.810169908 +0100 -+++ ioemu/vl.h 2006-07-14 18:30:17.436628931 +0100 +--- ioemu.orig/vl.h 2006-07-26 13:39:18.030364229 +0100 ++++ ioemu/vl.h 2006-07-26 13:39:18.651297796 +0100 @@ -732,6 +732,7 @@ /* vnc.c */ diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/target-i386-dm/cpu.h --- a/tools/ioemu/target-i386-dm/cpu.h Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/target-i386-dm/cpu.h Wed Jul 26 13:41:10 2006 +0100 @@ -80,7 +80,11 @@ int cpu_x86_inl(CPUX86State *env, int ad /* helper2.c */ int main_loop(void); +#if defined(__i386__) || defined(__x86_64__) #define TARGET_PAGE_BITS 12 +#elif defined(__ia64__) +#define TARGET_PAGE_BITS 14 +#endif #include "cpu-all.h" #endif /* CPU_I386_H */ diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/target-i386-dm/exec-dm.c --- a/tools/ioemu/target-i386-dm/exec-dm.c Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/target-i386-dm/exec-dm.c Wed Jul 26 13:41:10 2006 +0100 @@ -339,6 +339,23 @@ CPUReadMemoryFunc **cpu_get_io_memory_re { return io_mem_read[io_index >> IO_MEM_SHIFT]; } + +#ifdef __ia64__ +/* IA64 has seperate I/D cache, with coherence maintained by DMA controller. + * So to emulate right behavior that guest OS is assumed, we need to flush + * I/D cache here. + */ +static void sync_icache(unsigned long address, int len) +{ + int l; + + for(l = 0; l < (len + 32); l += 32) + __ia64_fc(address + l); + + ia64_sync_i(); + ia64_srlz_i(); +} +#endif /* physical memory access (slow version, mainly for debug) */ #if defined(CONFIG_USER_ONLY) @@ -455,6 +472,9 @@ void cpu_physical_memory_rw(target_phys_ ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) + (addr & ~TARGET_PAGE_MASK); memcpy(buf, ptr, l); +#ifdef __ia64__ + sync_icache((unsigned long)ptr, l); +#endif } } len -= l; diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/vl.c --- a/tools/ioemu/vl.c Wed Jul 26 13:36:13 2006 +0100 +++ b/tools/ioemu/vl.c Wed Jul 26 13:41:10 2006 +0100 @@ -5754,6 +5754,7 @@ int main(int argc, char **argv) exit(-1); } +#if defined(__i386__) || defined(__x86_64__) if (xc_get_pfn_list(xc_handle, domid, page_array, nr_pages) != nr_pages) { fprintf(logfile, "xc_get_pfn_list returned error %d\n", errno); exit(-1); @@ -5774,6 +5775,34 @@ int main(int argc, char **argv) fprintf(logfile, "shared page at pfn:%lx, mfn: %"PRIx64"\n", nr_pages - 1, (uint64_t)(page_array[nr_pages - 1])); +#elif defined(__ia64__) + if (xc_ia64_get_pfn_list(xc_handle, domid, + page_array, 0, nr_pages) != nr_pages) { + fprintf(logfile, "xc_ia64_get_pfn_list returned error %d\n", errno); + exit(-1); + } + + phys_ram_base = xc_map_foreign_batch(xc_handle, domid, + PROT_READ|PROT_WRITE, + page_array, nr_pages); + if (phys_ram_base == 0) { + fprintf(logfile, "xc_map_foreign_batch returned error %d\n", errno); + exit(-1); + } + + if (xc_ia64_get_pfn_list(xc_handle, domid, page_array, + nr_pages + (GFW_SIZE >> PAGE_SHIFT), 1)!= 1){ + fprintf(logfile, "xc_ia64_get_pfn_list returned error %d\n", errno); + exit(-1); + } + + shared_page = xc_map_foreign_range(xc_handle, domid, PAGE_SIZE, + PROT_READ|PROT_WRITE, + page_array[0]); + + fprintf(logfile, "shared page at pfn:%lx, mfn: %l016x\n", + IO_PAGE_START >> PAGE_SHIFT, page_array[0]); +#endif #else /* !CONFIG_DM */ #ifdef CONFIG_SOFTMMU diff -r 7654157278f1 -r 42aa63188a88 tools/ioemu/patches/ioemu-ia64 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tools/ioemu/patches/ioemu-ia64 Wed Jul 26 13:41:10 2006 +0100 @@ -0,0 +1,471 @@ +Index: ioemu/hw/iommu.c +=================================================================== +--- ioemu.orig/hw/iommu.c 2006-07-14 13:43:45.000000000 +0100 ++++ ioemu/hw/iommu.c 2006-07-26 13:34:50.039997837 +0100 +@@ -82,7 +82,11 @@ + #define IOPTE_VALID 0x00000002 /* IOPTE is valid */ + #define IOPTE_WAZ 0x00000001 /* Write as zeros */ + ++#if defined(__i386__) || defined(__x86_64__) + #define PAGE_SHIFT 12 ++#elif defined(__ia64__) ++#define PAGE_SHIFT 14 ++#endif + #define PAGE_SIZE (1 << PAGE_SHIFT) + #define PAGE_MASK (PAGE_SIZE - 1) + +Index: ioemu/cpu-all.h +=================================================================== +--- ioemu.orig/cpu-all.h 2006-07-26 13:33:45.946834283 +0100 ++++ ioemu/cpu-all.h 2006-07-26 13:34:50.038997944 +0100 +@@ -835,6 +835,31 @@ + :"=m" (*(volatile long *)addr) + :"dIr" (nr)); + } ++#elif defined(__ia64__) ++#include "ia64_intrinsic.h" ++#define atomic_set_bit(nr, addr) ({ \ ++ typeof(*addr) bit, old, new; \ ++ volatile typeof(*addr) *m; \ ++ \ ++ m = (volatile typeof(*addr)*)(addr + nr / (8*sizeof(*addr))); \ ++ bit = 1 << (nr % (8*sizeof(*addr))); \ ++ do { \ ++ old = *m; \ ++ new = old | bit; \ ++ } while (cmpxchg_acq(m, old, new) != old); \ ++}) ++ ++#define atomic_clear_bit(nr, addr) ({ \ ++ typeof(*addr) bit, old, new; \ ++ volatile typeof(*addr) *m; \ ++ \ ++ m = (volatile typeof(*addr)*)(addr + nr / (8*sizeof(*addr))); \ ++ bit = ~(1 << (nr % (8*sizeof(*addr)))); \ ++ do { \ ++ old = *m; \ ++ new = old & bit; \ ++ } while (cmpxchg_acq(m, old, new) != old); \ ++}) + #endif + + /* memory API */ +Index: ioemu/vl.c +=================================================================== +--- ioemu.orig/vl.c 2006-07-26 13:33:45.996828953 +0100 ++++ ioemu/vl.c 2006-07-26 13:34:50.044997304 +0100 +@@ -5577,6 +5577,7 @@ + exit(-1); + } + ++#if defined(__i386__) || defined(__x86_64__) + if (xc_get_pfn_list(xc_handle, domid, page_array, nr_pages) != nr_pages) { + fprintf(logfile, "xc_get_pfn_list returned error %d\n", errno); + exit(-1); +@@ -5597,6 +5598,34 @@ + fprintf(logfile, "shared page at pfn:%lx, mfn: %"PRIx64"\n", nr_pages - 1, + (uint64_t)(page_array[nr_pages - 1])); + ++#elif defined(__ia64__) ++ if (xc_ia64_get_pfn_list(xc_handle, domid, ++ page_array, 0, nr_pages) != nr_pages) { ++ fprintf(logfile, "xc_ia64_get_pfn_list returned error %d\n", errno); ++ exit(-1); ++ } ++ ++ phys_ram_base = xc_map_foreign_batch(xc_handle, domid, ++ PROT_READ|PROT_WRITE, ++ page_array, nr_pages); ++ if (phys_ram_base == 0) { ++ fprintf(logfile, "xc_map_foreign_batch returned error %d\n", errno); ++ exit(-1); ++ } ++ ++ if (xc_ia64_get_pfn_list(xc_handle, domid, page_array, ++ nr_pages + (GFW_SIZE >> PAGE_SHIFT), 1)!= 1){ ++ fprintf(logfile, "xc_ia64_get_pfn_list returned error %d\n", errno); ++ exit(-1); ++ } ++ ++ shared_page = xc_map_foreign_range(xc_handle, domid, PAGE_SIZE, ++ PROT_READ|PROT_WRITE, ++ page_array[0]); ++ ++ fprintf(logfile, "shared page at pfn:%lx, mfn: %l016x\n", ++ IO_PAGE_START >> PAGE_SHIFT, page_array[0]); ++#endif + #else /* !CONFIG_DM */ + + #ifdef CONFIG_SOFTMMU +Index: ioemu/target-i386-dm/exec-dm.c +=================================================================== +--- ioemu.orig/target-i386-dm/exec-dm.c 2006-07-26 13:33:45.882841107 +0100 ++++ ioemu/target-i386-dm/exec-dm.c 2006-07-26 13:34:50.040997731 +0100 +@@ -340,6 +340,23 @@ + return io_mem_read[io_index >> IO_MEM_SHIFT]; + } + ++#ifdef __ia64__ ++/* IA64 has seperate I/D cache, with coherence maintained by DMA controller. ++ * So to emulate right behavior that guest OS is assumed, we need to flush ++ * I/D cache here. ++ */ ++static void sync_icache(unsigned long address, int len) ++{ ++ int l; ++ ++ for(l = 0; l < (len + 32); l += 32) ++ __ia64_fc(address + l); ++ ++ ia64_sync_i(); ++ ia64_srlz_i(); ++} ++#endif ++ + /* physical memory access (slow version, mainly for debug) */ + #if defined(CONFIG_USER_ONLY) + void cpu_physical_memory_rw(target_phys_addr_t addr, uint8_t *buf, +@@ -455,6 +472,9 @@ + ptr = phys_ram_base + (pd & TARGET_PAGE_MASK) + + (addr & ~TARGET_PAGE_MASK); + memcpy(buf, ptr, l); ++#ifdef __ia64__ ++ sync_icache((unsigned long)ptr, l); ++#endif + } + } + len -= l; +Index: ioemu/exec-all.h +=================================================================== +--- ioemu.orig/exec-all.h 2006-07-26 13:33:45.861843346 +0100 ++++ ioemu/exec-all.h 2006-07-26 13:38:30.096491388 +0100 +@@ -391,6 +391,15 @@ + } + #endif + ++#ifdef __ia64__ ++#include "ia64_intrinsic.h" ++static inline int testandset (int *p) ++{ ++ uint32_t o = 0, n = 1; ++ return (int)cmpxchg_acq(p, o, n); ++} ++#endif ++ + #ifdef __s390__ + static inline int testandset (int *p) + { +@@ -462,12 +471,13 @@ + } + #endif + +-#ifdef __ia64 +-#include <ia64intrin.h> ++#ifdef __ia64__ ++#include "ia64_intrinsic.h" + + static inline int testandset (int *p) + { +- return __sync_lock_test_and_set (p, 1); ++ uint32_t o = 0, n = 1; ++ return (int)cmpxchg_acq(p, o, n); + } + #endif + +Index: ioemu/target-i386-dm/cpu.h +=================================================================== +--- ioemu.orig/target-i386-dm/cpu.h 2006-07-26 13:33:45.882841107 +0100 ++++ ioemu/target-i386-dm/cpu.h 2006-07-26 13:34:50.040997731 +0100 +@@ -80,7 +80,11 @@ + /* helper2.c */ + int main_loop(void); + ++#if defined(__i386__) || defined(__x86_64__) + #define TARGET_PAGE_BITS 12 ++#elif defined(__ia64__) ++#define TARGET_PAGE_BITS 14 ++#endif + #include "cpu-all.h" + + #endif /* CPU_I386_H */ +Index: ioemu/ia64_intrinsic.h +=================================================================== +--- /dev/null 1970-01-01 00:00:00.000000000 +0000 ++++ ioemu/ia64_intrinsic.h 2006-07-26 13:34:50.038997944 +0100 +@@ -0,0 +1,276 @@ ++#ifndef IA64_INTRINSIC_H ++#define IA64_INTRINSIC_H ++ ++/* ++ * Compiler-dependent Intrinsics ++ * ++ * Copyright (C) 2002,2003 Jun Nakajima <jun.nakajima@xxxxxxxxx> ++ * Copyright (C) 2002,2003 Suresh Siddha <suresh.b.siddha@xxxxxxxxx> ++ * ++ */ ++extern long ia64_cmpxchg_called_with_bad_pointer (void); ++extern void ia64_bad_param_for_getreg (void); ++#define ia64_cmpxchg(sem,ptr,o,n,s) ({ \ ++ uint64_t _o, _r; \ ++ switch(s) { \ ++ case 1: _o = (uint8_t)(long)(o); break; \ ++ case 2: _o = (uint16_t)(long)(o); break; \ ++ case 4: _o = (uint32_t)(long)(o); break; \ ++ case 8: _o = (uint64_t)(long)(o); break; \ ++ default: break; \ ++ } \ ++ switch(s) { \ ++ case 1: \ ++ _r = ia64_cmpxchg1_##sem((uint8_t*)ptr,n,_o); break; \ ++ case 2: \ ++ _r = ia64_cmpxchg2_##sem((uint16_t*)ptr,n,_o); break; \ ++ case 4: \ ++ _r = ia64_cmpxchg4_##sem((uint32_t*)ptr,n,_o); break; \ ++ case 8: \ ++ _r = ia64_cmpxchg8_##sem((uint64_t*)ptr,n,_o); break; \ ++ default: \ ++ _r = ia64_cmpxchg_called_with_bad_pointer(); break; \ ++ } \ ++ (__typeof__(o)) _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)) ++ ++/* ++ * 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 ++ ++/* 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 ++ ++#ifdef __INTEL_COMPILER ++void __fc(uint64_t *addr); ++void __synci(void); ++void __isrlz(void); ++void __dsrlz(void); ++uint64_t __getReg(const int whichReg); ++uint64_t _InterlockedCompareExchange8_rel(volatile uint8_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange8_acq(volatile uint8_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange16_rel(volatile uint16_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange16_acq(volatile uint16_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange_rel(volatile uint32_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange_acq(volatile uint32_t *dest, uint64_t xchg, uint64_t comp); ++uint64_t _InterlockedCompareExchange64_rel(volatile uint64_t *dest, uint64_t xchg, uint64_t comp); ++u64_t _InterlockedCompareExchange64_acq(volatile uint64_t *dest, uint64_t xchg, uint64_t comp); ++ ++#define ia64_cmpxchg1_rel _InterlockedCompareExchange8_rel ++#define ia64_cmpxchg1_acq _InterlockedCompareExchange8_acq ++#define ia64_cmpxchg2_rel _InterlockedCompareExchange16_rel ++#define ia64_cmpxchg2_acq _InterlockedCompareExchange16_acq ++#define ia64_cmpxchg4_rel _InterlockedCompareExchange_rel ++#define ia64_cmpxchg4_acq _InterlockedCompareExchange_acq ++#define ia64_cmpxchg8_rel _InterlockedCompareExchange64_rel ++#define ia64_cmpxchg8_acq _InterlockedCompareExchange64_acq ++ ++#define ia64_srlz_d __dsrlz ++#define ia64_srlz_i __isrlz ++#define __ia64_fc __fc ++#define ia64_sync_i __synci ++#define __ia64_getreg __getReg ++#else /* __INTEL_COMPILER */ ++#define ia64_cmpxchg1_acq(ptr, new, old) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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) \ ++({ \ ++ uint64_t 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_srlz_i() asm volatile (";; srlz.i ;;" ::: "memory") ++#define ia64_srlz_d() asm volatile (";; srlz.d" ::: "memory"); ++#define __ia64_fc(addr) asm volatile ("fc %0" :: "r"(addr) : "memory") ++#define ia64_sync_i() asm volatile (";; sync.i" ::: "memory") ++ ++register unsigned long ia64_r13 asm ("r13") __attribute_used__; ++#define __ia64_getreg(regnum) \ ++({ \ ++ uint64_t 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; \ ++}) ++ ++#endif /* __INTEL_COMPILER */ ++#endif /* IA64_INTRINSIC_H */ _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |