PATCH: more ppc

Marcus Meissner meissner at suse.de
Mon Aug 5 02:47:32 CDT 2002


Hi,

This merges parts of old ppc stuff and newer things from me.

... still missing GET_IP(), signal_ppc.c ... 

Ciao, Marcus

License: LGPL
Changelog:
	Josh DuBois
	Marcus Meissner <meissner at suse.de>
	PowerPC locked exchange functions merged from old ppc patch.
	NtCurrentTeb handling for PowerPC (using gpr 13)

Index: include/winnt.h
===================================================================
RCS file: /home/wine/wine/include/winnt.h,v
retrieving revision 1.115
diff -u -r1.115 winnt.h
--- include/winnt.h	22 Jul 2002 20:51:02 -0000	1.115
+++ include/winnt.h	5 Aug 2002 07:42:12 -0000
@@ -2314,6 +2314,14 @@
   __asm mov teb, eax;
   return teb;
 }
+#elif defined(__powerpc__)
+extern inline struct _TEB * WINAPI NtCurrentTeb(void);
+extern inline struct _TEB * WINAPI NtCurrentTeb(void)
+{
+    struct _TEB *teb;
+    __asm__("\tmr %0, 13" : "=r" (teb));
+    return teb;
+}
 #else
 extern struct _TEB * WINAPI NtCurrentTeb(void);
 #endif
Index: library/port.c
===================================================================
RCS file: /home/wine/wine/library/port.c,v
retrieving revision 1.33
diff -u -r1.33 port.c
--- library/port.c	31 Jul 2002 23:20:47 -0000	1.33
+++ library/port.c	5 Aug 2002 07:42:13 -0000
@@ -696,6 +696,94 @@
                   "lock; xaddl %eax,(%edx)\n\t"
                   "ret");
 
+#elif defined(__powerpc__)
+void* interlocked_cmpxchg_ptr( void **dest, void* xchg, void* compare)
+{
+    long ret;
+    long scratch;
+    __asm__ __volatile__(
+    "sync; "
+    "0:    lwarx %0,0,%2 ;"
+    "      xor. %1,%4,%0;"
+    "      bne 1f;"
+    "      stwcx. %3,0,%2;"
+    "      bne- 0b;"
+    "1:    "
+    "sync; "
+    : "=&r"(ret), "=&r"(scratch)
+    : "r"(dest), "r"(xchg), "r"(compare)
+    : "cr0", "memory");
+    return (void*)ret;
+}
+
+long interlocked_cmpxchg( long *dest, long xchg, long compare)
+{
+    long ret;
+    long scratch;
+    __asm__ __volatile__(
+    "sync; "
+    "0:    lwarx %0,0,%2 ;"
+    "      xor. %1,%4,%0;"
+    "      bne 1f;"
+    "      stwcx. %3,0,%2;"
+    "      bne- 0b;"
+    "1:    "
+    "sync; "
+    : "=&r"(ret), "=&r"(scratch)
+    : "r"(dest), "r"(xchg), "r"(compare)
+    : "cr0", "memory");
+    return ret;
+}
+
+long interlocked_xchg_add( long *dest, long incr )
+{
+    void *ret __attribute__ ((aligned (4))) = &ret;
+    long inc = incr;
+    long zero = 0;
+    __asm__ __volatile__(
+	"sync; "
+	"0:    lwarx %0, %3, %1;"
+	"      add %0, %2, %0;"
+	"      stwcx. %0, %3, %1;"
+	"      bne- 0b;"
+	"sync; "
+	: "=&r"(ret)
+	: "r"(dest), "r"(inc), "r"(zero)
+	: "cr0", "memory"
+    );
+    return (long)ret;
+}
+
+long interlocked_xchg( long* dest, long val )
+{
+    void *ret __attribute__ ((aligned (4))) = &ret;
+    __asm__ __volatile__(
+    "sync; "
+    "0:    lwarx %0,0,%1 ;"
+    "      stwcx. %2,0,%1;"
+    "      bne- 0b;"
+    "sync; "
+    : "=&r"(ret)
+    : "r"(dest), "r"(val)
+    : "cr0", "memory");
+    return (long)ret;
+}
+
+void* interlocked_xchg_ptr( void** dest, void* val )
+{
+    void *ret __attribute__ ((aligned (4))) = &ret;
+    __asm__ __volatile__(
+    "sync; "
+    "0:    lwarx %0,0,%1 ;"
+    "      stwcx. %2,0,%1;"
+    "      bne- 0b;"
+    "sync; "
+    : "=&r"(ret)
+    : "r"(dest), "r"(val)
+    : "cr0", "memory");
+    return (void*)ret;
+}
+
 #elif defined(__sparc__) && defined(__sun__)
 
 /*
@@ -757,7 +845,6 @@
     _lwp_mutex_unlock( &interlocked_mutex );
     return retv;
 }
-
 #else
 # error You must implement the interlocked* functions for your CPU
 #endif
Index: scheduler/sysdeps.c
===================================================================
RCS file: /home/wine/wine/scheduler/sysdeps.c,v
retrieving revision 1.45
diff -u -r1.45 sysdeps.c
--- scheduler/sysdeps.c	17 May 2002 03:31:09 -0000	1.45
+++ scheduler/sysdeps.c	5 Aug 2002 07:42:13 -0000
@@ -85,6 +85,9 @@
 #if defined(__i386__)
     /* On the i386, the current thread is in the %fs register */
     wine_set_fs( teb->teb_sel );
+#elif defined(__powerpc__)
+    /* On PowerPC, the current TEB is in the gpr13 register */
+    __asm__ __volatile__("mr 13, %0" : : "r" (teb));
 #elif defined(HAVE__LWP_CREATE)
     /* On non-i386 Solaris, we use the LWP private pointer */
     _lwp_setprivate( teb );
@@ -249,13 +252,13 @@
   __asm int 3;
 }
 #endif /* defined(__GNUC__) || defined(_MSC_VER) */
-#else /* defined(__i386__) */
+#else /* !defined(__i386__) */
 void SYSDEPS_CallOnStack( void (*func)(LPVOID), LPVOID arg )
 {
     func( arg );
     while(1); /* avoid warning */
 }
-#endif /* defined(__i386__) */
+#endif /* !defined(__i386__) */
 
 
 /***********************************************************************
@@ -335,6 +338,8 @@
     extern void *_lwp_getprivate(void);
     return (struct _TEB *)_lwp_getprivate();
 }
+#elif defined(__powerpc__)
+__ASM_GLOBAL_FUNC( NtCurrentTeb, "\n\tmr 3,13\n\tblr" );
 #else
 # error NtCurrentTeb not defined for this architecture
 #endif  /* __i386__ */



More information about the wine-patches mailing list