1# Macros to detect C compiler features 2# config/c-compiler.m4 3 4 5# PGAC_C_SIGNED 6# ------------- 7# Check if the C compiler understands signed types. 8AC_DEFUN([PGAC_C_SIGNED], 9[AC_CACHE_CHECK(for signed types, pgac_cv_c_signed, 10[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], 11[signed char c; signed short s; signed int i;])], 12[pgac_cv_c_signed=yes], 13[pgac_cv_c_signed=no])]) 14if test x"$pgac_cv_c_signed" = xno ; then 15 AC_DEFINE(signed,, [Define to empty if the C compiler does not understand signed types.]) 16fi])# PGAC_C_SIGNED 17 18 19 20# PGAC_C_PRINTF_ARCHETYPE 21# ----------------------- 22# Select the format archetype to be used by gcc to check printf-type functions. 23# We prefer "gnu_printf", as that most closely matches the features supported 24# by src/port/snprintf.c (particularly the %m conversion spec). However, 25# on some NetBSD versions, that doesn't work while "__syslog__" does. 26# If all else fails, use "printf". 27AC_DEFUN([PGAC_PRINTF_ARCHETYPE], 28[AC_CACHE_CHECK([for printf format archetype], pgac_cv_printf_archetype, 29[pgac_cv_printf_archetype=gnu_printf 30PGAC_TEST_PRINTF_ARCHETYPE 31if [[ "$ac_archetype_ok" = no ]]; then 32 pgac_cv_printf_archetype=__syslog__ 33 PGAC_TEST_PRINTF_ARCHETYPE 34 if [[ "$ac_archetype_ok" = no ]]; then 35 pgac_cv_printf_archetype=printf 36 fi 37fi]) 38AC_DEFINE_UNQUOTED([PG_PRINTF_ATTRIBUTE], [$pgac_cv_printf_archetype], 39[Define to best printf format archetype, usually gnu_printf if available.]) 40])# PGAC_PRINTF_ARCHETYPE 41 42# Subroutine: test $pgac_cv_printf_archetype, set $ac_archetype_ok to yes or no 43AC_DEFUN([PGAC_TEST_PRINTF_ARCHETYPE], 44[ac_save_c_werror_flag=$ac_c_werror_flag 45ac_c_werror_flag=yes 46AC_COMPILE_IFELSE([AC_LANG_PROGRAM( 47[extern void pgac_write(int ignore, const char *fmt,...) 48__attribute__((format($pgac_cv_printf_archetype, 2, 3)));], 49[pgac_write(0, "error %s: %m", "foo");])], 50 [ac_archetype_ok=yes], 51 [ac_archetype_ok=no]) 52ac_c_werror_flag=$ac_save_c_werror_flag 53])# PGAC_TEST_PRINTF_ARCHETYPE 54 55 56# PGAC_TYPE_64BIT_INT(TYPE) 57# ------------------------- 58# Check if TYPE is a working 64 bit integer type. Set HAVE_TYPE_64 to 59# yes or no respectively, and define HAVE_TYPE_64 if yes. 60AC_DEFUN([PGAC_TYPE_64BIT_INT], 61[define([Ac_define], [translit([have_$1_64], [a-z *], [A-Z_P])])dnl 62define([Ac_cachevar], [translit([pgac_cv_type_$1_64], [ *], [_p])])dnl 63AC_CACHE_CHECK([whether $1 is 64 bits], [Ac_cachevar], 64[AC_RUN_IFELSE([AC_LANG_SOURCE( 65[typedef $1 ac_int64; 66 67/* 68 * These are globals to discourage the compiler from folding all the 69 * arithmetic tests down to compile-time constants. 70 */ 71ac_int64 a = 20000001; 72ac_int64 b = 40000005; 73 74int does_int64_work() 75{ 76 ac_int64 c,d; 77 78 if (sizeof(ac_int64) != 8) 79 return 0; /* definitely not the right size */ 80 81 /* Do perfunctory checks to see if 64-bit arithmetic seems to work */ 82 c = a * b; 83 d = (c + b) / b; 84 if (d != a+1) 85 return 0; 86 return 1; 87} 88 89int 90main() { 91 return (! does_int64_work()); 92}])], 93[Ac_cachevar=yes], 94[Ac_cachevar=no], 95[# If cross-compiling, check the size reported by the compiler and 96# trust that the arithmetic works. 97AC_COMPILE_IFELSE([AC_LANG_BOOL_COMPILE_TRY([], [sizeof($1) == 8])], 98 Ac_cachevar=yes, 99 Ac_cachevar=no)])]) 100 101Ac_define=$Ac_cachevar 102if test x"$Ac_cachevar" = xyes ; then 103 AC_DEFINE(Ac_define, 1, [Define to 1 if `]$1[' works and is 64 bits.]) 104fi 105undefine([Ac_define])dnl 106undefine([Ac_cachevar])dnl 107])# PGAC_TYPE_64BIT_INT 108 109 110# PGAC_TYPE_128BIT_INT 111# --------------------- 112# Check if __int128 is a working 128 bit integer type, and if so 113# define PG_INT128_TYPE to that typename, and define ALIGNOF_PG_INT128_TYPE 114# as its alignment requirement. 115# 116# This currently only detects a GCC/clang extension, but support for other 117# environments may be added in the future. 118# 119# For the moment we only test for support for 128bit math; support for 120# 128bit literals and snprintf is not required. 121AC_DEFUN([PGAC_TYPE_128BIT_INT], 122[AC_CACHE_CHECK([for __int128], [pgac_cv__128bit_int], 123[AC_LINK_IFELSE([AC_LANG_PROGRAM([ 124/* 125 * We don't actually run this test, just link it to verify that any support 126 * functions needed for __int128 are present. 127 * 128 * These are globals to discourage the compiler from folding all the 129 * arithmetic tests down to compile-time constants. We do not have 130 * convenient support for 128bit literals at this point... 131 */ 132__int128 a = 48828125; 133__int128 b = 97656250; 134],[ 135__int128 c,d; 136a = (a << 12) + 1; /* 200000000001 */ 137b = (b << 12) + 5; /* 400000000005 */ 138/* try the most relevant arithmetic ops */ 139c = a * b; 140d = (c + b) / b; 141/* must use the results, else compiler may optimize arithmetic away */ 142if (d != a+1) 143 return 1; 144])], 145[pgac_cv__128bit_int=yes], 146[pgac_cv__128bit_int=no])]) 147if test x"$pgac_cv__128bit_int" = xyes ; then 148 # Use of non-default alignment with __int128 tickles bugs in some compilers. 149 # If not cross-compiling, we can test for bugs and disable use of __int128 150 # with buggy compilers. If cross-compiling, hope for the best. 151 # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83925 152 AC_CACHE_CHECK([for __int128 alignment bug], [pgac_cv__128bit_int_bug], 153 [AC_RUN_IFELSE([AC_LANG_PROGRAM([ 154/* This must match the corresponding code in c.h: */ 155#if defined(__GNUC__) || defined(__SUNPRO_C) || defined(__IBMC__) 156#define pg_attribute_aligned(a) __attribute__((aligned(a))) 157#endif 158typedef __int128 int128a 159#if defined(pg_attribute_aligned) 160pg_attribute_aligned(8) 161#endif 162; 163int128a holder; 164void pass_by_val(void *buffer, int128a par) { holder = par; } 165],[ 166long int i64 = 97656225L << 12; 167int128a q; 168pass_by_val(main, (int128a) i64); 169q = (int128a) i64; 170if (q != holder) 171 return 1; 172])], 173 [pgac_cv__128bit_int_bug=ok], 174 [pgac_cv__128bit_int_bug=broken], 175 [pgac_cv__128bit_int_bug="assuming ok"])]) 176 if test x"$pgac_cv__128bit_int_bug" != xbroken ; then 177 AC_DEFINE(PG_INT128_TYPE, __int128, [Define to the name of a signed 128-bit integer type.]) 178 AC_CHECK_ALIGNOF(PG_INT128_TYPE) 179 fi 180fi])# PGAC_TYPE_128BIT_INT 181 182 183# PGAC_C_FUNCNAME_SUPPORT 184# ----------------------- 185# Check if the C compiler understands __func__ (C99) or __FUNCTION__ (gcc). 186# Define HAVE_FUNCNAME__FUNC or HAVE_FUNCNAME__FUNCTION accordingly. 187AC_DEFUN([PGAC_C_FUNCNAME_SUPPORT], 188[AC_CACHE_CHECK(for __func__, pgac_cv_funcname_func_support, 189[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include <stdio.h>], 190[printf("%s\n", __func__);])], 191[pgac_cv_funcname_func_support=yes], 192[pgac_cv_funcname_func_support=no])]) 193if test x"$pgac_cv_funcname_func_support" = xyes ; then 194AC_DEFINE(HAVE_FUNCNAME__FUNC, 1, 195 [Define to 1 if your compiler understands __func__.]) 196else 197AC_CACHE_CHECK(for __FUNCTION__, pgac_cv_funcname_function_support, 198[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([#include <stdio.h>], 199[printf("%s\n", __FUNCTION__);])], 200[pgac_cv_funcname_function_support=yes], 201[pgac_cv_funcname_function_support=no])]) 202if test x"$pgac_cv_funcname_function_support" = xyes ; then 203AC_DEFINE(HAVE_FUNCNAME__FUNCTION, 1, 204 [Define to 1 if your compiler understands __FUNCTION__.]) 205fi 206fi])# PGAC_C_FUNCNAME_SUPPORT 207 208 209 210# PGAC_C_STATIC_ASSERT 211# -------------------- 212# Check if the C compiler understands _Static_assert(), 213# and define HAVE__STATIC_ASSERT if so. 214# 215# We actually check the syntax ({ _Static_assert(...) }), because we need 216# gcc-style compound expressions to be able to wrap the thing into macros. 217AC_DEFUN([PGAC_C_STATIC_ASSERT], 218[AC_CACHE_CHECK(for _Static_assert, pgac_cv__static_assert, 219[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 220[({ _Static_assert(1, "foo"); })])], 221[pgac_cv__static_assert=yes], 222[pgac_cv__static_assert=no])]) 223if test x"$pgac_cv__static_assert" = xyes ; then 224AC_DEFINE(HAVE__STATIC_ASSERT, 1, 225 [Define to 1 if your compiler understands _Static_assert.]) 226fi])# PGAC_C_STATIC_ASSERT 227 228 229 230# PGAC_C_TYPEOF 231# ------------- 232# Check if the C compiler understands typeof or a variant. Define 233# HAVE_TYPEOF if so, and define 'typeof' to the actual key word. 234# 235AC_DEFUN([PGAC_C_TYPEOF], 236[AC_CACHE_CHECK(for typeof, pgac_cv_c_typeof, 237[pgac_cv_c_typeof=no 238for pgac_kw in typeof __typeof__ decltype; do 239 AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], 240[int x = 0; 241$pgac_kw(x) y; 242y = x; 243return y;])], 244[pgac_cv_c_typeof=$pgac_kw]) 245 test "$pgac_cv_c_typeof" != no && break 246done]) 247if test "$pgac_cv_c_typeof" != no; then 248 AC_DEFINE(HAVE_TYPEOF, 1, 249 [Define to 1 if your compiler understands `typeof' or something similar.]) 250 if test "$pgac_cv_c_typeof" != typeof; then 251 AC_DEFINE_UNQUOTED(typeof, $pgac_cv_c_typeof, [Define to how the compiler spells `typeof'.]) 252 fi 253fi])# PGAC_C_TYPEOF 254 255 256 257# PGAC_C_TYPES_COMPATIBLE 258# ----------------------- 259# Check if the C compiler understands __builtin_types_compatible_p, 260# and define HAVE__BUILTIN_TYPES_COMPATIBLE_P if so. 261# 262# We check usage with __typeof__, though it's unlikely any compiler would 263# have the former and not the latter. 264AC_DEFUN([PGAC_C_TYPES_COMPATIBLE], 265[AC_CACHE_CHECK(for __builtin_types_compatible_p, pgac_cv__types_compatible, 266[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], 267[[ int x; static int y[__builtin_types_compatible_p(__typeof__(x), int)]; ]])], 268[pgac_cv__types_compatible=yes], 269[pgac_cv__types_compatible=no])]) 270if test x"$pgac_cv__types_compatible" = xyes ; then 271AC_DEFINE(HAVE__BUILTIN_TYPES_COMPATIBLE_P, 1, 272 [Define to 1 if your compiler understands __builtin_types_compatible_p.]) 273fi])# PGAC_C_TYPES_COMPATIBLE 274 275 276# PGAC_C_BUILTIN_CONSTANT_P 277# ------------------------- 278# Check if the C compiler understands __builtin_constant_p(), 279# and define HAVE__BUILTIN_CONSTANT_P if so. 280# We need __builtin_constant_p("string literal") to be true, but some older 281# compilers don't think that, so test for that case explicitly. 282AC_DEFUN([PGAC_C_BUILTIN_CONSTANT_P], 283[AC_CACHE_CHECK(for __builtin_constant_p, pgac_cv__builtin_constant_p, 284[AC_COMPILE_IFELSE([AC_LANG_SOURCE( 285[[static int x; 286 static int y[__builtin_constant_p(x) ? x : 1]; 287 static int z[__builtin_constant_p("string literal") ? 1 : x]; 288]] 289)], 290[pgac_cv__builtin_constant_p=yes], 291[pgac_cv__builtin_constant_p=no])]) 292if test x"$pgac_cv__builtin_constant_p" = xyes ; then 293AC_DEFINE(HAVE__BUILTIN_CONSTANT_P, 1, 294 [Define to 1 if your compiler understands __builtin_constant_p.]) 295fi])# PGAC_C_BUILTIN_CONSTANT_P 296 297 298 299# PGAC_C_BUILTIN_OP_OVERFLOW 300# ------------------------- 301# Check if the C compiler understands __builtin_$op_overflow(), 302# and define HAVE__BUILTIN_OP_OVERFLOW if so. 303# 304# Check for the most complicated case, 64 bit multiplication, as a 305# proxy for all of the operations. To detect the case where the compiler 306# knows the function but library support is missing, we must link not just 307# compile, and store the results in global variables so the compiler doesn't 308# optimize away the call. 309AC_DEFUN([PGAC_C_BUILTIN_OP_OVERFLOW], 310[AC_CACHE_CHECK(for __builtin_mul_overflow, pgac_cv__builtin_op_overflow, 311[AC_LINK_IFELSE([AC_LANG_PROGRAM([ 312PG_INT64_TYPE a = 1; 313PG_INT64_TYPE b = 1; 314PG_INT64_TYPE result; 315int oflo; 316], 317[oflo = __builtin_mul_overflow(a, b, &result);])], 318[pgac_cv__builtin_op_overflow=yes], 319[pgac_cv__builtin_op_overflow=no])]) 320if test x"$pgac_cv__builtin_op_overflow" = xyes ; then 321AC_DEFINE(HAVE__BUILTIN_OP_OVERFLOW, 1, 322 [Define to 1 if your compiler understands __builtin_$op_overflow.]) 323fi])# PGAC_C_BUILTIN_OP_OVERFLOW 324 325 326 327# PGAC_C_BUILTIN_UNREACHABLE 328# -------------------------- 329# Check if the C compiler understands __builtin_unreachable(), 330# and define HAVE__BUILTIN_UNREACHABLE if so. 331# 332# NB: Don't get the idea of putting a for(;;); or such before the 333# __builtin_unreachable() call. Some compilers would remove it before linking 334# and only a warning instead of an error would be produced. 335AC_DEFUN([PGAC_C_BUILTIN_UNREACHABLE], 336[AC_CACHE_CHECK(for __builtin_unreachable, pgac_cv__builtin_unreachable, 337[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 338[__builtin_unreachable();])], 339[pgac_cv__builtin_unreachable=yes], 340[pgac_cv__builtin_unreachable=no])]) 341if test x"$pgac_cv__builtin_unreachable" = xyes ; then 342AC_DEFINE(HAVE__BUILTIN_UNREACHABLE, 1, 343 [Define to 1 if your compiler understands __builtin_unreachable.]) 344fi])# PGAC_C_BUILTIN_UNREACHABLE 345 346 347 348# PGAC_C_COMPUTED_GOTO 349# ----------------------- 350# Check if the C compiler knows computed gotos (gcc extension, also 351# available in at least clang). If so, define HAVE_COMPUTED_GOTO. 352# 353# Checking whether computed gotos are supported syntax-wise ought to 354# be enough, as the syntax is otherwise illegal. 355AC_DEFUN([PGAC_C_COMPUTED_GOTO], 356[AC_CACHE_CHECK(for computed goto support, pgac_cv_computed_goto, 357[AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], 358[[void *labeladdrs[] = {&&my_label}; 359 goto *labeladdrs[0]; 360 my_label: 361 return 1; 362]])], 363[pgac_cv_computed_goto=yes], 364[pgac_cv_computed_goto=no])]) 365if test x"$pgac_cv_computed_goto" = xyes ; then 366AC_DEFINE(HAVE_COMPUTED_GOTO, 1, 367 [Define to 1 if your compiler handles computed gotos.]) 368fi])# PGAC_C_COMPUTED_GOTO 369 370 371 372# PGAC_CHECK_BUILTIN_FUNC 373# ----------------------- 374# This is similar to AC_CHECK_FUNCS(), except that it will work for compiler 375# builtin functions, as that usually fails to. 376# The first argument is the function name, eg [__builtin_clzl], and the 377# second is its argument list, eg [unsigned long x]. The current coding 378# works only for a single argument named x; we might generalize that later. 379# It's assumed that the function's result type is coercible to int. 380# On success, we define "HAVEfuncname" (there's usually more than enough 381# underscores already, so we don't add another one). 382AC_DEFUN([PGAC_CHECK_BUILTIN_FUNC], 383[AC_CACHE_CHECK(for $1, pgac_cv$1, 384[AC_LINK_IFELSE([AC_LANG_PROGRAM([ 385int 386call$1($2) 387{ 388 return $1(x); 389}], [])], 390[pgac_cv$1=yes], 391[pgac_cv$1=no])]) 392if test x"${pgac_cv$1}" = xyes ; then 393AC_DEFINE_UNQUOTED(AS_TR_CPP([HAVE$1]), 1, 394 [Define to 1 if your compiler understands $1.]) 395fi])# PGAC_CHECK_BUILTIN_FUNC 396 397 398 399# PGAC_PROG_VARCC_VARFLAGS_OPT 400# ----------------------- 401# Given a compiler, variable name and a string, check if the compiler 402# supports the string as a command-line option. If it does, add the 403# string to the given variable. 404AC_DEFUN([PGAC_PROG_VARCC_VARFLAGS_OPT], 405[define([Ac_cachevar], [AS_TR_SH([pgac_cv_prog_$1_cflags_$3])])dnl 406AC_CACHE_CHECK([whether ${$1} supports $3, for $2], [Ac_cachevar], 407[pgac_save_CFLAGS=$CFLAGS 408pgac_save_CC=$CC 409CC=${$1} 410CFLAGS="${$2} $3" 411ac_save_c_werror_flag=$ac_c_werror_flag 412ac_c_werror_flag=yes 413_AC_COMPILE_IFELSE([AC_LANG_PROGRAM()], 414 [Ac_cachevar=yes], 415 [Ac_cachevar=no]) 416ac_c_werror_flag=$ac_save_c_werror_flag 417CFLAGS="$pgac_save_CFLAGS" 418CC="$pgac_save_CC"]) 419if test x"$Ac_cachevar" = x"yes"; then 420 $2="${$2} $3" 421fi 422undefine([Ac_cachevar])dnl 423])# PGAC_PROG_VARCC_VARFLAGS_OPT 424 425 426 427# PGAC_PROG_CC_CFLAGS_OPT 428# ----------------------- 429# Given a string, check if the compiler supports the string as a 430# command-line option. If it does, add the string to CFLAGS. 431AC_DEFUN([PGAC_PROG_CC_CFLAGS_OPT], [ 432PGAC_PROG_VARCC_VARFLAGS_OPT(CC, CFLAGS, $1) 433])# PGAC_PROG_CC_CFLAGS_OPT 434 435 436 437# PGAC_PROG_CC_VAR_OPT 438# ----------------------- 439# Given a variable name and a string, check if the compiler supports 440# the string as a command-line option. If it does, add the string to 441# the given variable. 442AC_DEFUN([PGAC_PROG_CC_VAR_OPT], 443[PGAC_PROG_VARCC_VARFLAGS_OPT(CC, $1, $2) 444])# PGAC_PROG_CC_VAR_OPT 445 446 447 448# PGAC_PROG_VARCXX_VARFLAGS_OPT 449# ----------------------- 450# Given a compiler, variable name and a string, check if the compiler 451# supports the string as a command-line option. If it does, add the 452# string to the given variable. 453AC_DEFUN([PGAC_PROG_VARCXX_VARFLAGS_OPT], 454[define([Ac_cachevar], [AS_TR_SH([pgac_cv_prog_$1_cxxflags_$3])])dnl 455AC_CACHE_CHECK([whether ${$1} supports $3, for $2], [Ac_cachevar], 456[pgac_save_CXXFLAGS=$CXXFLAGS 457pgac_save_CXX=$CXX 458CXX=${$1} 459CXXFLAGS="${$2} $3" 460ac_save_cxx_werror_flag=$ac_cxx_werror_flag 461ac_cxx_werror_flag=yes 462AC_LANG_PUSH(C++) 463_AC_COMPILE_IFELSE([AC_LANG_PROGRAM()], 464 [Ac_cachevar=yes], 465 [Ac_cachevar=no]) 466AC_LANG_POP([]) 467ac_cxx_werror_flag=$ac_save_cxx_werror_flag 468CXXFLAGS="$pgac_save_CXXFLAGS" 469CXX="$pgac_save_CXX"]) 470if test x"$Ac_cachevar" = x"yes"; then 471 $2="${$2} $3" 472fi 473undefine([Ac_cachevar])dnl 474])# PGAC_PROG_VARCXX_VARFLAGS_OPT 475 476 477 478# PGAC_PROG_CXX_CFLAGS_OPT 479# ----------------------- 480# Given a string, check if the compiler supports the string as a 481# command-line option. If it does, add the string to CXXFLAGS. 482AC_DEFUN([PGAC_PROG_CXX_CFLAGS_OPT], 483[PGAC_PROG_VARCXX_VARFLAGS_OPT(CXX, CXXFLAGS, $1) 484])# PGAC_PROG_CXX_VAR_OPT 485 486 487 488# PGAC_PROG_CC_LDFLAGS_OPT 489# ------------------------ 490# Given a string, check if the compiler supports the string as a 491# command-line option. If it does, add the string to LDFLAGS. 492# For reasons you'd really rather not know about, this checks whether 493# you can link to a particular function, not just whether you can link. 494# In fact, we must actually check that the resulting program runs :-( 495AC_DEFUN([PGAC_PROG_CC_LDFLAGS_OPT], 496[define([Ac_cachevar], [AS_TR_SH([pgac_cv_prog_cc_ldflags_$1])])dnl 497AC_CACHE_CHECK([whether $CC supports $1], [Ac_cachevar], 498[pgac_save_LDFLAGS=$LDFLAGS 499LDFLAGS="$pgac_save_LDFLAGS $1" 500AC_RUN_IFELSE([AC_LANG_PROGRAM([extern void $2 (); void (*fptr) () = $2;],[])], 501 [Ac_cachevar=yes], 502 [Ac_cachevar=no], 503 [Ac_cachevar="assuming no"]) 504LDFLAGS="$pgac_save_LDFLAGS"]) 505if test x"$Ac_cachevar" = x"yes"; then 506 LDFLAGS="$LDFLAGS $1" 507fi 508undefine([Ac_cachevar])dnl 509])# PGAC_PROG_CC_LDFLAGS_OPT 510 511# PGAC_HAVE_GCC__SYNC_CHAR_TAS 512# ------------------------- 513# Check if the C compiler understands __sync_lock_test_and_set(char), 514# and define HAVE_GCC__SYNC_CHAR_TAS 515# 516# NB: There are platforms where test_and_set is available but compare_and_swap 517# is not, so test this separately. 518# NB: Some platforms only do 32bit tas, others only do 8bit tas. Test both. 519AC_DEFUN([PGAC_HAVE_GCC__SYNC_CHAR_TAS], 520[AC_CACHE_CHECK(for builtin __sync char locking functions, pgac_cv_gcc_sync_char_tas, 521[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 522 [char lock = 0; 523 __sync_lock_test_and_set(&lock, 1); 524 __sync_lock_release(&lock);])], 525 [pgac_cv_gcc_sync_char_tas="yes"], 526 [pgac_cv_gcc_sync_char_tas="no"])]) 527if test x"$pgac_cv_gcc_sync_char_tas" = x"yes"; then 528 AC_DEFINE(HAVE_GCC__SYNC_CHAR_TAS, 1, [Define to 1 if you have __sync_lock_test_and_set(char *) and friends.]) 529fi])# PGAC_HAVE_GCC__SYNC_CHAR_TAS 530 531# PGAC_HAVE_GCC__SYNC_INT32_TAS 532# ------------------------- 533# Check if the C compiler understands __sync_lock_test_and_set(), 534# and define HAVE_GCC__SYNC_INT32_TAS 535AC_DEFUN([PGAC_HAVE_GCC__SYNC_INT32_TAS], 536[AC_CACHE_CHECK(for builtin __sync int32 locking functions, pgac_cv_gcc_sync_int32_tas, 537[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 538 [int lock = 0; 539 __sync_lock_test_and_set(&lock, 1); 540 __sync_lock_release(&lock);])], 541 [pgac_cv_gcc_sync_int32_tas="yes"], 542 [pgac_cv_gcc_sync_int32_tas="no"])]) 543if test x"$pgac_cv_gcc_sync_int32_tas" = x"yes"; then 544 AC_DEFINE(HAVE_GCC__SYNC_INT32_TAS, 1, [Define to 1 if you have __sync_lock_test_and_set(int *) and friends.]) 545fi])# PGAC_HAVE_GCC__SYNC_INT32_TAS 546 547# PGAC_HAVE_GCC__SYNC_INT32_CAS 548# ------------------------- 549# Check if the C compiler understands __sync_compare_and_swap() for 32bit 550# types, and define HAVE_GCC__SYNC_INT32_CAS if so. 551AC_DEFUN([PGAC_HAVE_GCC__SYNC_INT32_CAS], 552[AC_CACHE_CHECK(for builtin __sync int32 atomic operations, pgac_cv_gcc_sync_int32_cas, 553[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 554 [int val = 0; 555 __sync_val_compare_and_swap(&val, 0, 37);])], 556 [pgac_cv_gcc_sync_int32_cas="yes"], 557 [pgac_cv_gcc_sync_int32_cas="no"])]) 558if test x"$pgac_cv_gcc_sync_int32_cas" = x"yes"; then 559 AC_DEFINE(HAVE_GCC__SYNC_INT32_CAS, 1, [Define to 1 if you have __sync_val_compare_and_swap(int *, int, int).]) 560fi])# PGAC_HAVE_GCC__SYNC_INT32_CAS 561 562# PGAC_HAVE_GCC__SYNC_INT64_CAS 563# ------------------------- 564# Check if the C compiler understands __sync_compare_and_swap() for 64bit 565# types, and define HAVE_GCC__SYNC_INT64_CAS if so. 566AC_DEFUN([PGAC_HAVE_GCC__SYNC_INT64_CAS], 567[AC_CACHE_CHECK(for builtin __sync int64 atomic operations, pgac_cv_gcc_sync_int64_cas, 568[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 569 [PG_INT64_TYPE lock = 0; 570 __sync_val_compare_and_swap(&lock, 0, (PG_INT64_TYPE) 37);])], 571 [pgac_cv_gcc_sync_int64_cas="yes"], 572 [pgac_cv_gcc_sync_int64_cas="no"])]) 573if test x"$pgac_cv_gcc_sync_int64_cas" = x"yes"; then 574 AC_DEFINE(HAVE_GCC__SYNC_INT64_CAS, 1, [Define to 1 if you have __sync_val_compare_and_swap(int64 *, int64, int64).]) 575fi])# PGAC_HAVE_GCC__SYNC_INT64_CAS 576 577# PGAC_HAVE_GCC__ATOMIC_INT32_CAS 578# ------------------------- 579# Check if the C compiler understands __atomic_compare_exchange_n() for 32bit 580# types, and define HAVE_GCC__ATOMIC_INT32_CAS if so. 581AC_DEFUN([PGAC_HAVE_GCC__ATOMIC_INT32_CAS], 582[AC_CACHE_CHECK(for builtin __atomic int32 atomic operations, pgac_cv_gcc_atomic_int32_cas, 583[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 584 [int val = 0; 585 int expect = 0; 586 __atomic_compare_exchange_n(&val, &expect, 37, 0, __ATOMIC_SEQ_CST, __ATOMIC_RELAXED);])], 587 [pgac_cv_gcc_atomic_int32_cas="yes"], 588 [pgac_cv_gcc_atomic_int32_cas="no"])]) 589if test x"$pgac_cv_gcc_atomic_int32_cas" = x"yes"; then 590 AC_DEFINE(HAVE_GCC__ATOMIC_INT32_CAS, 1, [Define to 1 if you have __atomic_compare_exchange_n(int *, int *, int).]) 591fi])# PGAC_HAVE_GCC__ATOMIC_INT32_CAS 592 593# PGAC_HAVE_GCC__ATOMIC_INT64_CAS 594# ------------------------- 595# Check if the C compiler understands __atomic_compare_exchange_n() for 64bit 596# types, and define HAVE_GCC__ATOMIC_INT64_CAS if so. 597AC_DEFUN([PGAC_HAVE_GCC__ATOMIC_INT64_CAS], 598[AC_CACHE_CHECK(for builtin __atomic int64 atomic operations, pgac_cv_gcc_atomic_int64_cas, 599[AC_LINK_IFELSE([AC_LANG_PROGRAM([], 600 [PG_INT64_TYPE val = 0; 601 PG_INT64_TYPE expect = 0; 602 __atomic_compare_exchange_n(&val, &expect, 37, 0, __ATOMIC_SEQ_CST, __ATOMIC_RELAXED);])], 603 [pgac_cv_gcc_atomic_int64_cas="yes"], 604 [pgac_cv_gcc_atomic_int64_cas="no"])]) 605if test x"$pgac_cv_gcc_atomic_int64_cas" = x"yes"; then 606 AC_DEFINE(HAVE_GCC__ATOMIC_INT64_CAS, 1, [Define to 1 if you have __atomic_compare_exchange_n(int64 *, int64 *, int64).]) 607fi])# PGAC_HAVE_GCC__ATOMIC_INT64_CAS 608 609# PGAC_SSE42_CRC32_INTRINSICS 610# ----------------------- 611# Check if the compiler supports the x86 CRC instructions added in SSE 4.2, 612# using the _mm_crc32_u8 and _mm_crc32_u32 intrinsic functions. (We don't 613# test the 8-byte variant, _mm_crc32_u64, but it is assumed to be present if 614# the other ones are, on x86-64 platforms) 615# 616# An optional compiler flag can be passed as argument (e.g. -msse4.2). If the 617# intrinsics are supported, sets pgac_sse42_crc32_intrinsics, and CFLAGS_SSE42. 618AC_DEFUN([PGAC_SSE42_CRC32_INTRINSICS], 619[define([Ac_cachevar], [AS_TR_SH([pgac_cv_sse42_crc32_intrinsics_$1])])dnl 620AC_CACHE_CHECK([for _mm_crc32_u8 and _mm_crc32_u32 with CFLAGS=$1], [Ac_cachevar], 621[pgac_save_CFLAGS=$CFLAGS 622CFLAGS="$pgac_save_CFLAGS $1" 623AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <nmmintrin.h>], 624 [unsigned int crc = 0; 625 crc = _mm_crc32_u8(crc, 0); 626 crc = _mm_crc32_u32(crc, 0); 627 /* return computed value, to prevent the above being optimized away */ 628 return crc == 0;])], 629 [Ac_cachevar=yes], 630 [Ac_cachevar=no]) 631CFLAGS="$pgac_save_CFLAGS"]) 632if test x"$Ac_cachevar" = x"yes"; then 633 CFLAGS_SSE42="$1" 634 pgac_sse42_crc32_intrinsics=yes 635fi 636undefine([Ac_cachevar])dnl 637])# PGAC_SSE42_CRC32_INTRINSICS 638 639 640# PGAC_ARMV8_CRC32C_INTRINSICS 641# ----------------------- 642# Check if the compiler supports the CRC32C instructions using the __crc32cb, 643# __crc32ch, __crc32cw, and __crc32cd intrinsic functions. These instructions 644# were first introduced in ARMv8 in the optional CRC Extension, and became 645# mandatory in ARMv8.1. 646# 647# An optional compiler flag can be passed as argument (e.g. 648# -march=armv8-a+crc). If the intrinsics are supported, sets 649# pgac_armv8_crc32c_intrinsics, and CFLAGS_ARMV8_CRC32C. 650AC_DEFUN([PGAC_ARMV8_CRC32C_INTRINSICS], 651[define([Ac_cachevar], [AS_TR_SH([pgac_cv_armv8_crc32c_intrinsics_$1])])dnl 652AC_CACHE_CHECK([for __crc32cb, __crc32ch, __crc32cw, and __crc32cd with CFLAGS=$1], [Ac_cachevar], 653[pgac_save_CFLAGS=$CFLAGS 654CFLAGS="$pgac_save_CFLAGS $1" 655AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <arm_acle.h>], 656 [unsigned int crc = 0; 657 crc = __crc32cb(crc, 0); 658 crc = __crc32ch(crc, 0); 659 crc = __crc32cw(crc, 0); 660 crc = __crc32cd(crc, 0); 661 /* return computed value, to prevent the above being optimized away */ 662 return crc == 0;])], 663 [Ac_cachevar=yes], 664 [Ac_cachevar=no]) 665CFLAGS="$pgac_save_CFLAGS"]) 666if test x"$Ac_cachevar" = x"yes"; then 667 CFLAGS_ARMV8_CRC32C="$1" 668 pgac_armv8_crc32c_intrinsics=yes 669fi 670undefine([Ac_cachevar])dnl 671])# PGAC_ARMV8_CRC32C_INTRINSICS 672