1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168
|
# ftello.m4
# serial 17
dnl Copyright (C) 2007-2025 Free Software Foundation, Inc.
dnl This file is free software; the Free Software Foundation
dnl gives unlimited permission to copy and/or distribute it,
dnl with or without modifications, as long as this notice is preserved.
dnl This file is offered as-is, without any warranty.
AC_DEFUN([gl_FUNC_FTELLO],
[
AC_REQUIRE([gl_STDIO_H_DEFAULTS])
AC_REQUIRE([AC_PROG_CC])
AC_REQUIRE([gl_STDIN_LARGE_OFFSET])
AC_REQUIRE([gl_SYS_TYPES_H])
dnl Persuade glibc <stdio.h> to declare ftello().
AC_REQUIRE([AC_USE_SYSTEM_EXTENSIONS])
AC_CHECK_DECLS_ONCE([ftello])
if test $ac_cv_have_decl_ftello = no; then
HAVE_DECL_FTELLO=0
fi
AC_CACHE_CHECK([for ftello], [gl_cv_func_ftello],
[
AC_LINK_IFELSE(
[AC_LANG_PROGRAM(
[[#include <stdio.h>]],
[[ftello (stdin);]])],
[gl_cv_func_ftello=yes],
[gl_cv_func_ftello=no])
])
if test $gl_cv_func_ftello = no; then
HAVE_FTELLO=0
else
if test $WINDOWS_64_BIT_OFF_T = 1; then
REPLACE_FTELLO=1
fi
if test $gl_cv_var_stdin_large_offset = no; then
REPLACE_FTELLO=1
fi
AC_REQUIRE([AC_CANONICAL_HOST])
if test $REPLACE_FTELLO = 0; then
dnl On native Windows, in some circumstances, ftell(), ftello(),
dnl fgetpos(), lseek(), _lseeki64() all succeed on devices of type
dnl FILE_TYPE_PIPE. However, to match POSIX behaviour, we want
dnl ftell(), ftello(), fgetpos(), lseek() to fail when the argument fd
dnl designates a pipe. See also
dnl https://github.com/python/cpython/issues/78961#issuecomment-1093800325
case "$host_os" in
mingw* | windows*) REPLACE_FTELLO=1 ;;
esac
fi
if test $REPLACE_FTELLO = 0; then
dnl Detect bug on Solaris.
dnl ftell and ftello produce incorrect results after putc that followed a
dnl getc call that reached EOF on Solaris. This is because the _IOREAD
dnl flag does not get cleared in this case, even though _IOWRT gets set,
dnl and ftell and ftello look whether the _IOREAD flag is set.
AC_CACHE_CHECK([whether ftello works],
[gl_cv_func_ftello_works],
[
dnl Initial guess, used when cross-compiling or when /dev/tty cannot
dnl be opened.
changequote(,)dnl
case "$host_os" in
# Guess no on Solaris.
solaris*) gl_cv_func_ftello_works="guessing no" ;;
# Guess yes on native Windows.
mingw* | windows*) gl_cv_func_ftello_works="guessing yes" ;;
# Guess yes otherwise.
*) gl_cv_func_ftello_works="guessing yes" ;;
esac
changequote([,])dnl
AC_RUN_IFELSE(
[AC_LANG_SOURCE([[
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define TESTFILE "conftest.tmp"
int
main (void)
{
FILE *fp;
/* Create a file with some contents. */
fp = fopen (TESTFILE, "w");
if (fp == NULL)
return 70;
if (fwrite ("foogarsh", 1, 8, fp) < 8)
{ fclose (fp); return 71; }
if (fclose (fp))
return 72;
/* The file's contents is now "foogarsh". */
/* Try writing after reading to EOF. */
fp = fopen (TESTFILE, "r+");
if (fp == NULL)
return 73;
if (fseek (fp, -1, SEEK_END))
{ fclose (fp); return 74; }
if (!(getc (fp) == 'h'))
{ fclose (fp); return 1; }
if (!(getc (fp) == EOF))
{ fclose (fp); return 2; }
if (!(ftell (fp) == 8))
{ fclose (fp); return 3; }
if (!(ftell (fp) == 8))
{ fclose (fp); return 4; }
if (!(putc ('!', fp) == '!'))
{ fclose (fp); return 5; }
if (!(ftell (fp) == 9))
{ fclose (fp); return 6; }
if (!(fclose (fp) == 0))
return 7;
fp = fopen (TESTFILE, "r");
if (fp == NULL)
return 75;
{
char buf[10];
if (!(fread (buf, 1, 10, fp) == 9))
{ fclose (fp); return 10; }
if (!(memcmp (buf, "foogarsh!", 9) == 0))
{ fclose (fp); return 11; }
}
if (!(fclose (fp) == 0))
return 12;
/* The file's contents is now "foogarsh!". */
return 0;
}]])],
[gl_cv_func_ftello_works=yes],
[gl_cv_func_ftello_works=no], [:])
])
case "$gl_cv_func_ftello_works" in
*yes) ;;
*)
REPLACE_FTELLO=1
AC_DEFINE([FTELLO_BROKEN_AFTER_SWITCHING_FROM_READ_TO_WRITE], [1],
[Define to 1 if the system's ftello function has the Solaris bug.])
;;
esac
fi
if test $REPLACE_FTELLO = 0; then
dnl Detect bug on macOS >= 10.15.
gl_FUNC_UNGETC_WORKS
if test $gl_ftello_broken_after_ungetc = yes; then
REPLACE_FTELLO=1
AC_DEFINE([FTELLO_BROKEN_AFTER_UNGETC], [1],
[Define to 1 if the system's ftello function has the macOS bug.])
fi
fi
fi
])
# Prerequisites of lib/ftello.c.
AC_DEFUN([gl_PREREQ_FTELLO],
[
if test $gl_cv_func_ftello != no; then
AC_DEFINE([HAVE_FTELLO], [1],
[Define to 1 if the system has the ftello function.])
fi
dnl Native Windows has the function _ftelli64. mingw hides it, but mingw64
dnl makes it usable again.
AC_CHECK_FUNCS([_ftelli64])
])
|