In summary, this patch:

1) Correctly returns the "old" value.
2) Uses builtin function instead of inline asm.
Nice catch.  Patch is ok. Could you please also prepare patch for
crt's intrinsic-implementation files?

As before, plus:

3) Fixes both winnt.h and the crt intrinsic files.
4) Uses intrin-mac.h to avoid duplicating code.

dw
Index: mingw-w64-crt/intrincs/ilockand.c
===================================================================
--- mingw-w64-crt/intrincs/ilockand.c   (revision 5872)
+++ mingw-w64-crt/intrincs/ilockand.c   (working copy)
@@ -1,12 +1,7 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
-__LONG32 _InterlockedAnd(__LONG32 volatile *Destination, __LONG32 Value)
-{
-  __asm__ __volatile__("lock ; andl %0,%1"
-    : :"r"(Value),"m"(*Destination)
-    : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedAnd, __LONG32, &)
 
 __LONG32 InterlockedAnd(__LONG32 volatile *, __LONG32) 
__attribute__((alias("_InterlockedAnd")));
 
Index: mingw-w64-crt/intrincs/ilockand64.c
===================================================================
--- mingw-w64-crt/intrincs/ilockand64.c (revision 5872)
+++ mingw-w64-crt/intrincs/ilockand64.c (working copy)
@@ -1,12 +1,8 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
 #ifdef _WIN64
-__int64 _InterlockedAnd64(__int64 volatile *Destination, __int64 Value)
-{
-  __asm__ __volatile__("lock ; andq %0,%1"
-    : : "r"(Value),"m"(*Destination) : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedAnd64, __int64, &)
 #else
 __int64 __stdcall InterlockedCompareExchange64(__int64 volatile *Destination,
   __int64 Exchange, __int64 Comperand);
Index: mingw-w64-crt/intrincs/ilockor.c
===================================================================
--- mingw-w64-crt/intrincs/ilockor.c    (revision 5872)
+++ mingw-w64-crt/intrincs/ilockor.c    (working copy)
@@ -1,11 +1,7 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
-__LONG32 _InterlockedOr(__LONG32 volatile *Destination, __LONG32 Value)
-{
-  __asm__ __volatile__("lock ; orl %0,%1"
-    : : "r"(Value),"m"(*Destination) : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedOr, __LONG32, |)
 
 __LONG32 InterlockedOr(__LONG32 volatile *, __LONG32) 
__attribute__((alias("_InterlockedOr")));
 
Index: mingw-w64-crt/intrincs/ilockor64.c
===================================================================
--- mingw-w64-crt/intrincs/ilockor64.c  (revision 5872)
+++ mingw-w64-crt/intrincs/ilockor64.c  (working copy)
@@ -1,12 +1,8 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
 #ifdef _WIN64
-__int64 _InterlockedOr64(__int64 volatile *Destination, __int64 Value)
-{
-  __asm__ __volatile__("lock ; orq %0,%1"
-    : : "r"(Value),"m"(*Destination) : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedOr64, __int64, |)
 #else
 __int64 __stdcall InterlockedCompareExchange64(__int64 volatile *Destination,
   __int64 Exchange, __int64 Comperand);
Index: mingw-w64-crt/intrincs/ilockxor.c
===================================================================
--- mingw-w64-crt/intrincs/ilockxor.c   (revision 5872)
+++ mingw-w64-crt/intrincs/ilockxor.c   (working copy)
@@ -1,11 +1,7 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
-__LONG32 _InterlockedXor(__LONG32 volatile *Destination, __LONG32 Value)
-{
-  __asm__ __volatile__("lock ; xorl %0,%1"
-    : : "r"(Value),"m"(*Destination) : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedXor, __LONG32, ^)
 
 __LONG32 InterlockedXor(__LONG32 volatile *, __LONG32) 
__attribute__((alias("_InterlockedXor")));
 
Index: mingw-w64-crt/intrincs/ilockxor64.c
===================================================================
--- mingw-w64-crt/intrincs/ilockxor64.c (revision 5872)
+++ mingw-w64-crt/intrincs/ilockxor64.c (working copy)
@@ -1,12 +1,8 @@
 #include <intrin.h>
+#include <psdk_inc/intrin-mac.h>
 
 #ifdef _WIN64
-__int64 _InterlockedXor64(__int64 volatile *Destination, __int64 Value)
-{
-  __asm__ __volatile__("lock ; xorq %0,%1"
-    : : "r"(Value),"m"(*Destination) : "memory");
-  return *Destination;
-}
+__buildlogicali(_InterlockedXor64, __int64, ^)
 #else
 __int64 __stdcall InterlockedCompareExchange64(__int64 volatile *Destination,
   __int64 Exchange, __int64 Comperand);
Index: mingw-w64-headers/include/psdk_inc/intrin-mac.h
===================================================================
--- mingw-w64-headers/include/psdk_inc/intrin-mac.h     (revision 5872)
+++ mingw-w64-headers/include/psdk_inc/intrin-mac.h     (working copy)
@@ -18,4 +18,14 @@
       : "memory"); \
 }
 
+// This macro is used by InterlockedAnd, InterlockedOr, InterlockedXor, 
InterlockedAnd64, InterlockedOr64, InterlockedXor64
+#define __buildlogicali(x, y, o) y x(volatile y *Destination, y Value) \
+{ \
+   y lPrev; \
+   do { \
+      lPrev = *Destination; \
+   } while (__sync_val_compare_and_swap(Destination, lPrev, lPrev o Value) != 
lPrev); \
+   return lPrev; \
+}
+
 #endif /* _INTRIN-MAC_ */
Index: mingw-w64-headers/include/winnt.h
===================================================================
--- mingw-w64-headers/include/winnt.h   (revision 5872)
+++ mingw-w64-headers/include/winnt.h   (working copy)
@@ -1417,37 +1417,14 @@
        : "memory");
       return prev;
     }
-    __CRT_INLINE LONG InterlockedAnd(LONG volatile *Destination,LONG Value) {
-      __asm__ __volatile__("lock ; andl %0,%1"
-       : :"r"(Value),"m"(*Destination)
-       : "memory");
-      return *Destination;
-    }
-    __CRT_INLINE LONG InterlockedOr(LONG volatile *Destination,LONG Value) {
-      __asm__ __volatile__("lock ; orl %0,%1"
-       : : "r"(Value),"m"(*Destination) : "memory");
-      return *Destination;
-    }
-    __CRT_INLINE LONG InterlockedXor(LONG volatile *Destination,LONG Value) {
-      __asm__ __volatile__("lock ; xorl %0,%1"
-       : : "r"(Value),"m"(*Destination) : "memory");
-      return *Destination;
-    }
-    __CRT_INLINE LONG64 InterlockedAnd64(LONG64 volatile *Destination,LONG64 
Value) {
-      __asm__ __volatile__("lock ; andq %0,%1"
-       : : "r"(Value),"m"(*Destination) : "memory");
-      return *Destination;
-    }
-    __CRT_INLINE LONG64 InterlockedOr64(LONG64 volatile *Destination,LONG64 
Value) {
-      __asm__ __volatile__("lock ; orq %0,%1"
-       : : "r"(Value),"m"(*Destination) : "memory");
-      return *Destination;
-    }
-    __CRT_INLINE LONG64 InterlockedXor64(LONG64 volatile *Destination,LONG64 
Value) {
-      __asm__ __volatile__("lock ; xorq %0,%1"
-       : : "r"(Value),"m"(*Destination) : "memory");
-      return *Destination;
-    }
+
+__CRT_INLINE __buildlogicali(InterlockedAnd, LONG, &)
+__CRT_INLINE __buildlogicali(InterlockedOr, LONG, |)
+__CRT_INLINE __buildlogicali(InterlockedXor, LONG, ^)
+
+__CRT_INLINE __buildlogicali(InterlockedAnd64, LONG64, &)
+__CRT_INLINE __buildlogicali(InterlockedOr64, LONG64, |)
+__CRT_INLINE __buildlogicali(InterlockedXor64, LONG64, ^)
 #endif /* !__CRT__NO_INLINE */
 
     LONG InterlockedExchangeAdd(LONG volatile *Addend,LONG Value);
------------------------------------------------------------------------------
Try New Relic Now & We'll Send You this Cool Shirt
New Relic is the only SaaS-based application performance monitoring service 
that delivers powerful full stack analytics. Optimize and monitor your
browser, app, & servers with just a few lines of code. Try New Relic
and get this awesome Nerd Life shirt! http://p.sf.net/sfu/newrelic_d2d_may
_______________________________________________
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public

Reply via email to