Commit e055a3ee authored by Alexandre Julliard's avatar Alexandre Julliard

configure: Require 64-bit compare-and-swap support from gcc.

parent 7e7e81f0
......@@ -17415,6 +17415,67 @@ $as_echo "$ac_cv_c_logicalop_noisy" >&6; }
test "$ac_cv_c_logicalop_noisy" = yes || EXTRACFLAGS="$EXTRACFLAGS -Wlogical-op"
fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for flags needed for 64-bit compare-and-swap support" >&5
$as_echo_n "checking for flags needed for 64-bit compare-and-swap support... " >&6; }
if ${wine_cv_64bit_compare_swap+:} false; then :
$as_echo_n "(cached) " >&6
else
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#error no
#endif
int
main ()
{
;
return 0;
}
_ACEOF
if ac_fn_c_try_compile "$LINENO"; then :
wine_cv_64bit_compare_swap="none needed"
else
case $host_cpu in
*i[3456]86*) wine_cv_64bit_compare_swap="-march=i586" ;;
*arm*) wine_cv_64bit_compare_swap="-march=armv7-a" ;;
*) wine_cv_64bit_compare_swap="unknown" ;;
esac
if test "x$wine_cv_64bit_compare_swap" != unknown
then
CFLAGS="$CFLAGS $wine_cv_64bit_compare_swap"
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#error no
#endif
int
main ()
{
;
return 0;
}
_ACEOF
if ac_fn_c_try_compile "$LINENO"; then :
else
wine_cv_64bit_compare_swap="unknown"
fi
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
CFLAGS=$saved_CFLAGS
fi
fi
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $wine_cv_64bit_compare_swap" >&5
$as_echo "$wine_cv_64bit_compare_swap" >&6; }
case "$wine_cv_64bit_compare_swap" in
unknown) as_fn_error $? "gcc doesn't support 64-bit compare-and-swap on this platform" "$LINENO" 5 ;;
"none needed") ;;
*) EXTRACFLAGS="$EXTRACFLAGS $wine_cv_64bit_compare_swap" ;;
esac
for ac_flag in $CFLAGS; do
case $ac_flag in
-g) { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the compiler supports -gdwarf-2" >&5
......
......@@ -2054,6 +2054,32 @@ char*f(const char *h,char n) {return strchr(h,n);}]])],[ac_cv_c_logicalop_noisy=
CFLAGS=$saved_string_h_CFLAGS
test "$ac_cv_c_logicalop_noisy" = yes || EXTRACFLAGS="$EXTRACFLAGS -Wlogical-op"])
dnl Check for 64-bit compare-and-swap
AC_CACHE_CHECK([for flags needed for 64-bit compare-and-swap support], wine_cv_64bit_compare_swap,
[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#error no
#endif]])],
[wine_cv_64bit_compare_swap="none needed"],
[case $host_cpu in
*i[[3456]]86*) wine_cv_64bit_compare_swap="-march=i586" ;;
*arm*) wine_cv_64bit_compare_swap="-march=armv7-a" ;;
*) wine_cv_64bit_compare_swap="unknown" ;;
esac
if test "x$wine_cv_64bit_compare_swap" != unknown
then
dnl try with the new flags
CFLAGS="$CFLAGS $wine_cv_64bit_compare_swap"
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#error no
#endif]])],,[wine_cv_64bit_compare_swap="unknown"])
CFLAGS=$saved_CFLAGS
fi])])
case "$wine_cv_64bit_compare_swap" in
unknown) AC_MSG_ERROR([gcc doesn't support 64-bit compare-and-swap on this platform]) ;;
"none needed") ;;
*) EXTRACFLAGS="$EXTRACFLAGS $wine_cv_64bit_compare_swap" ;;
esac
dnl Default to dwarf-2 debug info
for ac_flag in $CFLAGS; do
case $ac_flag in
......
......@@ -377,33 +377,10 @@ LONGLONG WINAPI RtlExtendedMagicDivide(
/*************************************************************************
* RtlInterlockedCompareExchange64 (NTDLL.@)
*/
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
LONGLONG WINAPI RtlInterlockedCompareExchange64( LONGLONG *dest, LONGLONG xchg, LONGLONG compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
#else
__ASM_STDCALL_FUNC(RtlInterlockedCompareExchange64, 20,
"push %ebx\n\t"
__ASM_CFI(".cfi_adjust_cfa_offset 4\n\t")
__ASM_CFI(".cfi_rel_offset %ebx,0\n\t")
"push %esi\n\t"
__ASM_CFI(".cfi_adjust_cfa_offset 4\n\t")
__ASM_CFI(".cfi_rel_offset %esi,0\n\t")
"movl 12(%esp),%esi\n\t"
"movl 16(%esp),%ebx\n\t"
"movl 20(%esp),%ecx\n\t"
"movl 24(%esp),%eax\n\t"
"movl 28(%esp),%edx\n\t"
"lock; cmpxchg8b (%esi)\n\t"
"pop %esi\n\t"
__ASM_CFI(".cfi_same_value %esi\n\t")
__ASM_CFI(".cfi_adjust_cfa_offset -4\n\t")
"pop %ebx\n\t"
__ASM_CFI(".cfi_same_value %ebx\n\t")
__ASM_CFI(".cfi_adjust_cfa_offset -4\n\t")
"ret $20")
#endif
#endif /* _WIN64 */
......
......@@ -121,10 +121,6 @@ static inline TEB64 *NtCurrentTeb64(void) { return (TEB64 *)NtCurrentTeb()->GdiB
NTSTATUS WINAPI RtlHashUnicodeString(PCUNICODE_STRING,BOOLEAN,ULONG,ULONG*);
#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#define InterlockedCompareExchange64(dest,xchg,cmp) RtlInterlockedCompareExchange64(dest,xchg,cmp)
#endif
/* convert from straight ASCII to Unicode without depending on the current codepage */
static inline void ascii_to_unicode( WCHAR *dst, const char *src, size_t len )
{
......
......@@ -26,10 +26,6 @@
#include "unixlib.h"
#include "wine/list.h"
#ifndef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
#define InterlockedCompareExchange64(dest,xchg,cmp) RtlInterlockedCompareExchange64(dest,xchg,cmp)
#endif
#ifdef __i386__
static const enum cpu_type client_cpu = CPU_x86;
#elif defined(__x86_64__)
......
......@@ -2995,14 +2995,17 @@ static FORCEINLINE void *WINAPI InterlockedExchangePointer( void *volatile *dest
static FORCEINLINE LONG WINAPI InterlockedCompareExchange( LONG volatile *dest, LONG xchg, LONG compare )
{
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4
return __sync_val_compare_and_swap( dest, compare, xchg );
#else
LONG ret;
__asm__ __volatile__( "lock; cmpxchgl %2,(%1)"
: "=a" (ret) : "r" (dest), "r" (xchg), "0" (compare) : "memory" );
return ret;
#endif
}
static FORCEINLINE PVOID WINAPI InterlockedCompareExchangePointer( PVOID volatile *dest, PVOID xchg, PVOID compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
static FORCEINLINE LONGLONG WINAPI InterlockedCompareExchange64( LONGLONG volatile *dest, LONGLONG xchg, LONGLONG compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
static FORCEINLINE LONG WINAPI InterlockedExchange( LONG volatile *dest, LONG val )
......@@ -3019,44 +3022,17 @@ static FORCEINLINE LONG WINAPI InterlockedExchange( LONG volatile *dest, LONG va
static FORCEINLINE LONG WINAPI InterlockedExchangeAdd( LONG volatile *dest, LONG incr )
{
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4
return __sync_fetch_and_add( dest, incr );
#else
LONG ret;
__asm__ __volatile__( "lock; xaddl %0,(%1)"
: "=r" (ret) : "r" (dest), "0" (incr) : "memory" );
return ret;
#endif
}
static FORCEINLINE LONG WINAPI InterlockedIncrement( LONG volatile *dest )
{
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4
return __sync_add_and_fetch( dest, 1 );
#else
return InterlockedExchangeAdd( dest, 1 ) + 1;
#endif
}
static FORCEINLINE LONG WINAPI InterlockedDecrement( LONG volatile *dest )
{
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4
return __sync_add_and_fetch( dest, -1 );
#else
return InterlockedExchangeAdd( dest, -1 ) - 1;
#endif
}
#ifdef _WIN64
static FORCEINLINE PVOID WINAPI InterlockedCompareExchangePointer( PVOID volatile *dest, PVOID xchg, PVOID compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
static FORCEINLINE LONGLONG WINAPI InterlockedCompareExchange64( LONGLONG volatile *dest, LONGLONG xchg, LONGLONG compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
static FORCEINLINE PVOID WINAPI InterlockedExchangePointer( PVOID volatile *dest, PVOID val )
......@@ -3064,35 +3040,14 @@ static FORCEINLINE PVOID WINAPI InterlockedExchangePointer( PVOID volatile *dest
PVOID ret;
#ifdef __x86_64__
__asm__ __volatile__( "lock; xchgq %0,(%1)" : "=r" (ret) :"r" (dest), "0" (val) : "memory" );
#elif defined(__i386__)
__asm__ __volatile__( "lock; xchgl %0,(%1)" : "=r" (ret) :"r" (dest), "0" (val) : "memory" );
#else
do ret = *dest; while (!__sync_bool_compare_and_swap( dest, ret, val ));
#endif
return ret;
}
#else
static FORCEINLINE PVOID WINAPI InterlockedCompareExchangePointer( PVOID volatile *dest, PVOID xchg, PVOID compare )
{
return (PVOID)InterlockedCompareExchange( (LONG volatile*)dest, (LONG)xchg, (LONG)compare );
}
static FORCEINLINE PVOID WINAPI InterlockedExchangePointer( PVOID volatile *dest, PVOID val )
{
return (PVOID)InterlockedExchange( (LONG volatile*)dest, (LONG)val );
}
#ifdef __GCC_HAVE_SYNC_COMPARE_AND_SWAP_8
static FORCEINLINE LONGLONG WINAPI InterlockedCompareExchange64( LONGLONG volatile *dest, LONGLONG xchg, LONGLONG compare )
{
return __sync_val_compare_and_swap( dest, compare, xchg );
}
#else
WINBASEAPI LONGLONG WINAPI InterlockedCompareExchange64(LONGLONG volatile*,LONGLONG,LONGLONG);
#endif
#endif
#endif /* __GNUC__ */
#ifdef __WINESRC__
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment