1# Copyright (C) 2002-2004, 2006-2018 Free Software Foundation, Inc. 2# This file is free software; the Free Software Foundation 3# gives unlimited permission to copy and/or distribute it, 4# with or without modifications, as long as this notice is preserved. 5 6# Test whether the *printf family of functions supports infinite and NaN 7# 'double' arguments and negative zero arguments in the %f, %e, %g 8# directives. (ISO C99, POSIX:2001) 9# Result is gl_cv_func_printf_infinite. 10 11printf_infinite_double_test = ''' 12#include <stdio.h> 13#include <string.h> 14static int 15strisnan (const char *string, size_t start_index, size_t end_index) 16{ 17 if (start_index < end_index) 18 { 19 if (string[start_index] == '-') 20 start_index++; 21 if (start_index + 3 <= end_index 22 && memcmp (string + start_index, "nan", 3) == 0) 23 { 24 start_index += 3; 25 if (start_index == end_index 26 || (string[start_index] == '(' && string[end_index - 1] == ')')) 27 return 1; 28 } 29 } 30 return 0; 31} 32static int 33have_minus_zero () 34{ 35 static double plus_zero = 0.0; 36 double minus_zero = - plus_zero; 37 return memcmp (&plus_zero, &minus_zero, sizeof (double)) != 0; 38} 39static char buf[10000]; 40static double zero = 0.0; 41int main () 42{ 43 int result = 0; 44 if (sprintf (buf, "%f", 1.0 / zero) < 0 45 || (strcmp (buf, "inf") != 0 && strcmp (buf, "infinity") != 0)) 46 result |= 1; 47 if (sprintf (buf, "%f", -1.0 / zero) < 0 48 || (strcmp (buf, "-inf") != 0 && strcmp (buf, "-infinity") != 0)) 49 result |= 1; 50 if (sprintf (buf, "%f", zero / zero) < 0 51 || !strisnan (buf, 0, strlen (buf))) 52 result |= 2; 53 if (sprintf (buf, "%e", 1.0 / zero) < 0 54 || (strcmp (buf, "inf") != 0 && strcmp (buf, "infinity") != 0)) 55 result |= 4; 56 if (sprintf (buf, "%e", -1.0 / zero) < 0 57 || (strcmp (buf, "-inf") != 0 && strcmp (buf, "-infinity") != 0)) 58 result |= 4; 59 if (sprintf (buf, "%e", zero / zero) < 0 60 || !strisnan (buf, 0, strlen (buf))) 61 result |= 8; 62 if (sprintf (buf, "%g", 1.0 / zero) < 0 63 || (strcmp (buf, "inf") != 0 && strcmp (buf, "infinity") != 0)) 64 result |= 16; 65 if (sprintf (buf, "%g", -1.0 / zero) < 0 66 || (strcmp (buf, "-inf") != 0 && strcmp (buf, "-infinity") != 0)) 67 result |= 16; 68 if (sprintf (buf, "%g", zero / zero) < 0 69 || !strisnan (buf, 0, strlen (buf))) 70 result |= 32; 71 /* This test fails on HP-UX 10.20. */ 72 if (have_minus_zero ()) 73 if (sprintf (buf, "%g", - zero) < 0 74 || strcmp (buf, "-0") != 0) 75 result |= 64; 76 return result; 77} 78''' 79 80if not meson.is_cross_build() or meson.has_exe_wrapper() 81 run_result = cc.run(printf_infinite_double_test, 82 name : 'printf supports infinite \'double\' arguments') 83 gl_cv_func_printf_infinite = run_result.compiled() and run_result.returncode() == 0 84else 85 if host_system in ['linux', 'android'] 86 gl_cv_func_printf_infinite = true 87 elif (host_system.startswith ('freebsd1') or 88 host_system.startswith ('freebsd2') or 89 host_system.startswith ('freebsd3') or 90 host_system.startswith ('freebsd4') or 91 host_system.startswith ('freebsd5')) 92 gl_cv_func_printf_infinite = false 93 elif (host_system.startswith ('freebsd') or 94 host_system.startswith ('kfreebsd')) 95 gl_cv_func_printf_infinite = true 96 elif (host_system.startswith ('darwin1') or 97 host_system.startswith ('darwin2') or 98 host_system.startswith ('darwin3') or 99 host_system.startswith ('darwin4') or 100 host_system.startswith ('darwin5')) 101 gl_cv_func_printf_infinite = false 102 elif host_system.startswith ('darwin') 103 gl_cv_func_printf_infinite = true 104 elif (host_system.startswith ('hpux7') or 105 host_system.startswith ('hpux8') or 106 host_system.startswith ('hpux9') or 107 host_system.startswith ('hpux10')) 108 gl_cv_func_printf_infinite = false 109 elif host_system.startswith ('hpux') 110 gl_cv_func_printf_infinite = true 111 elif (host_system.startswith ('netbsd1') or 112 host_system.startswith ('netbsd2') or 113 host_system.startswith ('netbsdelf1') or 114 host_system.startswith ('netbsdelf2') or 115 host_system.startswith ('netbsdaout1') or 116 host_system.startswith ('netbsdaout2') or 117 host_system.startswith ('netbsdcoff1') or 118 host_system.startswith ('netbsdcoff2')) 119 gl_cv_func_printf_infinite = false 120 elif host_system.startswith ('netbsd') 121 gl_cv_func_printf_infinite = true 122 elif host_system.startswith ('beos') 123 gl_cv_func_printf_infinite = true 124 elif host_system.startswith ('windows') 125 # Guess yes on MSVC, no on mingw. 126 if cc.get_id() == 'msvc' or cc.get_id() == 'clang-cl' 127 gl_cv_func_printf_infinite = true 128 else 129 gl_cv_func_printf_infinite = false 130 endif 131 else 132 # If we don't know, assume the worst. 133 gl_cv_func_printf_infinite = false 134 endif 135endif 136