OLD | NEW |
(Empty) | |
| 1 # memmem.m4 serial 24 |
| 2 dnl Copyright (C) 2002-2004, 2007-2012 Free Software Foundation, Inc. |
| 3 dnl This file is free software; the Free Software Foundation |
| 4 dnl gives unlimited permission to copy and/or distribute it, |
| 5 dnl with or without modifications, as long as this notice is preserved. |
| 6 |
| 7 dnl Check that memmem is present and functional. |
| 8 AC_DEFUN([gl_FUNC_MEMMEM_SIMPLE], |
| 9 [ |
| 10 dnl Persuade glibc <string.h> to declare memmem(). |
| 11 AC_REQUIRE([AC_USE_SYSTEM_EXTENSIONS]) |
| 12 |
| 13 AC_REQUIRE([gl_HEADER_STRING_H_DEFAULTS]) |
| 14 AC_CHECK_FUNCS([memmem]) |
| 15 if test $ac_cv_func_memmem = yes; then |
| 16 HAVE_MEMMEM=1 |
| 17 else |
| 18 HAVE_MEMMEM=0 |
| 19 fi |
| 20 AC_CHECK_DECLS_ONCE([memmem]) |
| 21 if test $ac_cv_have_decl_memmem = no; then |
| 22 HAVE_DECL_MEMMEM=0 |
| 23 else |
| 24 dnl Detect http://sourceware.org/bugzilla/show_bug.cgi?id=12092. |
| 25 dnl Also check that we handle empty needles correctly. |
| 26 AC_CACHE_CHECK([whether memmem works], |
| 27 [gl_cv_func_memmem_works_always], |
| 28 [AC_RUN_IFELSE([AC_LANG_PROGRAM([[ |
| 29 #include <string.h> /* for memmem */ |
| 30 #define P "_EF_BF_BD" |
| 31 #define HAYSTACK "F_BD_CE_BD" P P P P "_C3_88_20" P P P "_C3_A7_20" P |
| 32 #define NEEDLE P P P P P |
| 33 ]], [[ |
| 34 int result = 0; |
| 35 if (memmem (HAYSTACK, strlen (HAYSTACK), NEEDLE, strlen (NEEDLE))) |
| 36 result |= 1; |
| 37 /* Check for empty needle behavior. */ |
| 38 { |
| 39 const char *haystack = "AAA"; |
| 40 if (memmem (haystack, 3, NULL, 0) != haystack) |
| 41 result |= 2; |
| 42 } |
| 43 return result; |
| 44 ]])], |
| 45 [gl_cv_func_memmem_works_always=yes], |
| 46 [gl_cv_func_memmem_works_always=no], |
| 47 [dnl glibc 2.9..2.12 and cygwin 1.7.7 have issue #12092 above. |
| 48 dnl Also empty needles work on glibc >= 2.1 and cygwin >= 1.7.0. |
| 49 dnl uClibc is not affected, since it uses different source code. |
| 50 dnl Assume that it works on all other platforms (even if not linear). |
| 51 AC_EGREP_CPP([Lucky user], |
| 52 [ |
| 53 #ifdef __GNU_LIBRARY__ |
| 54 #include <features.h> |
| 55 #if ((__GLIBC__ == 2 && ((__GLIBC_MINOR > 0 && __GLIBC_MINOR__ < 9) \ |
| 56 || __GLIBC_MINOR__ > 12)) \ |
| 57 || (__GLIBC__ > 2)) \ |
| 58 || defined __UCLIBC__ |
| 59 Lucky user |
| 60 #endif |
| 61 #elif defined __CYGWIN__ |
| 62 #include <cygwin/version.h> |
| 63 #if CYGWIN_VERSION_DLL_COMBINED > CYGWIN_VERSION_DLL_MAKE_COMBINED (1007, 7) |
| 64 Lucky user |
| 65 #endif |
| 66 #else |
| 67 Lucky user |
| 68 #endif |
| 69 ], |
| 70 [gl_cv_func_memmem_works_always="guessing yes"], |
| 71 [gl_cv_func_memmem_works_always="guessing no"]) |
| 72 ]) |
| 73 ]) |
| 74 case "$gl_cv_func_memmem_works_always" in |
| 75 *yes) ;; |
| 76 *) |
| 77 REPLACE_MEMMEM=1 |
| 78 ;; |
| 79 esac |
| 80 fi |
| 81 gl_PREREQ_MEMMEM |
| 82 ]) # gl_FUNC_MEMMEM_SIMPLE |
| 83 |
| 84 dnl Additionally, check that memmem has linear performance characteristics |
| 85 AC_DEFUN([gl_FUNC_MEMMEM], |
| 86 [ |
| 87 AC_REQUIRE([gl_FUNC_MEMMEM_SIMPLE]) |
| 88 if test $HAVE_DECL_MEMMEM = 1 && test $REPLACE_MEMMEM = 0; then |
| 89 AC_CACHE_CHECK([whether memmem works in linear time], |
| 90 [gl_cv_func_memmem_works_fast], |
| 91 [AC_RUN_IFELSE([AC_LANG_PROGRAM([[ |
| 92 #include <signal.h> /* for signal */ |
| 93 #include <string.h> /* for memmem */ |
| 94 #include <stdlib.h> /* for malloc */ |
| 95 #include <unistd.h> /* for alarm */ |
| 96 static void quit (int sig) { exit (sig + 128); } |
| 97 ]], [[ |
| 98 int result = 0; |
| 99 size_t m = 1000000; |
| 100 char *haystack = (char *) malloc (2 * m + 1); |
| 101 char *needle = (char *) malloc (m + 1); |
| 102 /* Failure to compile this test due to missing alarm is okay, |
| 103 since all such platforms (mingw) also lack memmem. */ |
| 104 signal (SIGALRM, quit); |
| 105 alarm (5); |
| 106 /* Check for quadratic performance. */ |
| 107 if (haystack && needle) |
| 108 { |
| 109 memset (haystack, 'A', 2 * m); |
| 110 haystack[2 * m] = 'B'; |
| 111 memset (needle, 'A', m); |
| 112 needle[m] = 'B'; |
| 113 if (!memmem (haystack, 2 * m + 1, needle, m + 1)) |
| 114 result |= 1; |
| 115 } |
| 116 return result; |
| 117 ]])], |
| 118 [gl_cv_func_memmem_works_fast=yes], [gl_cv_func_memmem_works_fast=no], |
| 119 [dnl Only glibc >= 2.9 and cygwin > 1.7.0 are known to have a |
| 120 dnl memmem that works in linear time. |
| 121 AC_EGREP_CPP([Lucky user], |
| 122 [ |
| 123 #include <features.h> |
| 124 #ifdef __GNU_LIBRARY__ |
| 125 #if ((__GLIBC__ == 2 && __GLIBC_MINOR__ >= 9) || (__GLIBC__ > 2)) \ |
| 126 && !defined __UCLIBC__ |
| 127 Lucky user |
| 128 #endif |
| 129 #endif |
| 130 #ifdef __CYGWIN__ |
| 131 #include <cygwin/version.h> |
| 132 #if CYGWIN_VERSION_DLL_COMBINED > CYGWIN_VERSION_DLL_MAKE_COMBINED (1007, 0) |
| 133 Lucky user |
| 134 #endif |
| 135 #endif |
| 136 ], |
| 137 [gl_cv_func_memmem_works_fast="guessing yes"], |
| 138 [gl_cv_func_memmem_works_fast="guessing no"]) |
| 139 ]) |
| 140 ]) |
| 141 case "$gl_cv_func_memmem_works_fast" in |
| 142 *yes) ;; |
| 143 *) |
| 144 REPLACE_MEMMEM=1 |
| 145 ;; |
| 146 esac |
| 147 fi |
| 148 ]) # gl_FUNC_MEMMEM |
| 149 |
| 150 # Prerequisites of lib/memmem.c. |
| 151 AC_DEFUN([gl_PREREQ_MEMMEM], [:]) |
OLD | NEW |