diff --git a/newlib/ChangeLog b/newlib/ChangeLog index 68c910d1b..9d297d033 100644 --- a/newlib/ChangeLog +++ b/newlib/ChangeLog @@ -1,3 +1,53 @@ +2002-07-17 Jeff Johnston + + * configure.host(stdio64_dir): New setting that is used to + enable building of new stdio64 directory. + * libc/Makefile.am[HAVE_STDIO64_DIR]: Add support for + large files. + (stmp-stdio64,stdio64.texi): New targets to optionally add in + stdio64 info to info files. + * libc/Makefile.in: Regenerated. + * libc/configure: Ditto. + * libc/configure.in: Add configuration variables that are set + when stdio64 is selected as subdir in configure.host. + * libc/libc.texinfo: Add optional menu item for Stdio64, based + on whether STDIO64 flag is set or not. + * libc/sys.tex: Add optional stdio64 syscalls based on whether + STDIO64 flag is set or not. + * libc/include/reent.h[__LARGE64_FILES]: Add new stdio64 + _r sycall routines. + * libc/include/stdio.h[__LARGE64_FILES]: Add new stdio64 prototypes. + (FILE): Typedef'd to __FILE instead of struct __sFILE directly. + (__SL64): New file flag indicating file is opened via fopen64. + * libc/include/sys/_types.h(_off64_t): Added. + * libc/include/sys/config.h: For x86-linux, define __LARGE64_FILES. + * libc/include/sys/reent.h(struct __sFILE64): New file structure + for 64-bit offset large file support. + (__FILE): New intermediate type either set to struct __sFILE64 or + struct __sFILE, depending on whether __LARGE64_FILES is set or not. + * libc/reent/Makefile.am[HAVE_STDIO64_DIR]: Add new files. + * libc/reent/Makefile.in: Regenerated. + * libc/reent/fstat64r.c: New file. + * libc/reent/lseek64r.c: Ditto. + * libc/reent/open64r.c: Ditto. + * libc/reent/reent.tex: Optionally add stdio64 reentrant syscalls + based on whether STDIO64 flag is set. + * libc/stdio/stdio.tex: Add blank line. + * libc/stdio64/Makefile.am: New file. + * libc/stdio64/Makefile.in: Ditto. + * libc/stdio64/fgetpos64.c: Ditto. + * libc/stdio64/fopen64.: Ditto. + * libc/stdio64/freopen64.c: Ditto. + * libc/stdio64/fseeko64.c: Ditto. + * libc/stdio64/fsetpos64.c: Ditto. + * libc/stdio64/ftello64.c: Ditto. + * libc/stdio64/local64.h: Ditto. + * libc/stdio64/stdio64.c: Ditto. + * libc/stdio64/stdio64.tex: Ditto. + * libc/stdio64/tmpfile64.c: Ditto. + * libc/sys/linux/io64.c: Add weak aliases for lseek64, fstat64, and + open64. + 2002-07-16 Jeff Johnston * libc/Makefile.am (stmp-extra): New target to set makeinfo flag diff --git a/newlib/configure.host b/newlib/configure.host index c5e3e2465..4cb7bbab7 100644 --- a/newlib/configure.host +++ b/newlib/configure.host @@ -30,6 +30,7 @@ # have_sys_mach_dir Is there a machine subdirectory in sys subdirectory # posix_dir "posix" to build libc/posix, "" otherwise # signal_dir "signal" to build libc/signal, "" otherwise +# stdio64_dir "stdio64" to build libc/stdio64, "" otherwise # syscall_dir "syscalls" to build libc/syscalls, "" otherwise # unix_dir "unix" to build libc/unix, "" otherwise # use_libtool flag: use libtool to build newlib? @@ -44,6 +45,7 @@ machine_dir= sys_dir= posix_dir= signal_dir=signal +stdio64_dir= syscall_dir= unix_dir= mach_add_setjmp= @@ -238,6 +240,7 @@ case "${host}" in i[3456]86-pc-linux-*) use_libtool=yes have_sys_mach_dir=yes + stdio64_dir=stdio64 oext=lo aext=la ;; *) ;; #shared library not supported for ${host} diff --git a/newlib/libc/Makefile.am b/newlib/libc/Makefile.am index 7e8bdba1d..3f631e94c 100644 --- a/newlib/libc/Makefile.am +++ b/newlib/libc/Makefile.am @@ -18,9 +18,13 @@ if HAVE_UNIX_DIR UNIX_SUBDIR = unix endif +if HAVE_STDIO64_DIR +STDIO64_SUBDIR = stdio64 +endif + # The order of SUBDIRS is important for the integrated documentation. # Do not change the order without considering the doc impact. -SUBDIRS = argz stdlib ctype search stdio string $(SIGNAL_SUBDIR) time locale sys reent \ +SUBDIRS = argz stdlib ctype search stdio $(STDIO64_SUBDIR) string $(SIGNAL_SUBDIR) time locale sys reent \ $(extra_dir) errno misc machine $(UNIX_SUBDIR) $(POSIX_SUBDIR) $(SYSCALLS_SUBDIR) . noinst_DATA = $(CRT0) @@ -33,6 +37,7 @@ SUBLIBS = \ ctype/libctype.$(aext) \ search/libsearch.$(aext) \ stdio/libstdio.$(aext) \ + $(LIBC_STDIO64_LIB) \ string/libstring.$(aext) \ $(LIBC_SIGNAL_LIB) \ time/libtime.$(aext) \ @@ -54,6 +59,7 @@ SUBLIBS = \ ctype/lib.$(aext) \ search/lib.$(aext) \ stdio/lib.$(aext) \ + $(LIBC_STDIO64_LIB) \ string/lib.$(aext) \ $(LIBC_SIGNAL_LIB) \ time/lib.$(aext) \ @@ -106,6 +112,7 @@ SUBDEFS = \ stdlib/stmp-def \ ctype/stmp-def \ stdio/stmp-def \ + $(LIBC_STDIO64_DEF) \ string/stmp-def \ $(LIBC_SIGNAL_DEF) \ time/stmp-def \ @@ -114,7 +121,7 @@ SUBDEFS = \ $(LIBC_EXTRA_DEF) \ misc/stmp-def -libc.info: sigset.texi extra.texi targetdep.tex $(SUBDEFS) +libc.info: sigset.texi extra.texi stdio64.texi targetdep.tex $(SUBDEFS) stmp-sigset: config.status if test -n "$(LIBC_SIGNAL_LIB)"; then \ @@ -138,6 +145,17 @@ stmp-extra: config.status extra.texi: stmp-extra ; @true +stmp-stdio64: config.status + if test -n "$(LIBC_STDIO64_LIB)"; then \ + echo "@set STDIO64" >tmp.texi; \ + else \ + echo "@clear STDIO64" >tmp.texi; \ + fi + $(SHELL) $(newlib_basedir)/../move-if-change tmp.texi stdio64.texi + touch $@ + +stdio64.texi: stmp-stdio64 ; @true + stmp-targetdep: force rm -f tmp.texi targetdoc=`pwd`/tmp.texi; \ @@ -158,7 +176,8 @@ $(SUBDEFS): stmp-targetdep ; @true force: CLEANFILES = $(CRT0) \ - sigset.texi stmp-sigset tmp.texi targetdep.tex stmp-targetdep + sigset.texi stmp-sigset extra.texi stmp-extra \ + stdio64.texi stmp-stdio64 tmp.texi targetdep.tex stmp-targetdep ACLOCAL_AMFLAGS = -I .. CONFIG_STATUS_DEPENDENCIES = $(newlib_basedir)/configure.host diff --git a/newlib/libc/Makefile.in b/newlib/libc/Makefile.in index 4b2095aca..d10beafa8 100644 --- a/newlib/libc/Makefile.in +++ b/newlib/libc/Makefile.in @@ -81,6 +81,8 @@ LIBC_MACHINE_LIB = @LIBC_MACHINE_LIB@ LIBC_POSIX_LIB = @LIBC_POSIX_LIB@ LIBC_SIGNAL_DEF = @LIBC_SIGNAL_DEF@ LIBC_SIGNAL_LIB = @LIBC_SIGNAL_LIB@ +LIBC_STDIO64_DEF = @LIBC_STDIO64_DEF@ +LIBC_STDIO64_LIB = @LIBC_STDIO64_LIB@ LIBC_SYSCALL_LIB = @LIBC_SYSCALL_LIB@ LIBC_SYS_LIB = @LIBC_SYS_LIB@ LIBC_UNIX_LIB = @LIBC_UNIX_LIB@ @@ -113,9 +115,11 @@ AUTOMAKE_OPTIONS = cygnus @HAVE_UNIX_DIR_TRUE@UNIX_SUBDIR = @HAVE_UNIX_DIR_TRUE@unix +@HAVE_STDIO64_DIR_TRUE@STDIO64_SUBDIR = @HAVE_STDIO64_DIR_TRUE@stdio64 + # The order of SUBDIRS is important for the integrated documentation. # Do not change the order without considering the doc impact. -SUBDIRS = argz stdlib ctype search stdio string $(SIGNAL_SUBDIR) time locale sys reent \ +SUBDIRS = argz stdlib ctype search stdio $(STDIO64_SUBDIR) string $(SIGNAL_SUBDIR) time locale sys reent \ $(extra_dir) errno misc machine $(UNIX_SUBDIR) $(POSIX_SUBDIR) $(SYSCALLS_SUBDIR) . @@ -128,6 +132,7 @@ noinst_DATA = $(CRT0) @USE_LIBTOOL_TRUE@ ctype/libctype.$(aext) \ @USE_LIBTOOL_TRUE@ search/libsearch.$(aext) \ @USE_LIBTOOL_TRUE@ stdio/libstdio.$(aext) \ +@USE_LIBTOOL_TRUE@ $(LIBC_STDIO64_LIB) \ @USE_LIBTOOL_TRUE@ string/libstring.$(aext) \ @USE_LIBTOOL_TRUE@ $(LIBC_SIGNAL_LIB) \ @USE_LIBTOOL_TRUE@ time/libtime.$(aext) \ @@ -147,6 +152,7 @@ noinst_DATA = $(CRT0) @USE_LIBTOOL_FALSE@ ctype/lib.$(aext) \ @USE_LIBTOOL_FALSE@ search/lib.$(aext) \ @USE_LIBTOOL_FALSE@ stdio/lib.$(aext) \ +@USE_LIBTOOL_FALSE@ $(LIBC_STDIO64_LIB) \ @USE_LIBTOOL_FALSE@ string/lib.$(aext) \ @USE_LIBTOOL_FALSE@ $(LIBC_SIGNAL_LIB) \ @USE_LIBTOOL_FALSE@ time/lib.$(aext) \ @@ -177,6 +183,7 @@ SUBDEFS = \ stdlib/stmp-def \ ctype/stmp-def \ stdio/stmp-def \ + $(LIBC_STDIO64_DEF) \ string/stmp-def \ $(LIBC_SIGNAL_DEF) \ time/stmp-def \ @@ -187,7 +194,8 @@ SUBDEFS = \ CLEANFILES = $(CRT0) \ - sigset.texi stmp-sigset tmp.texi targetdep.tex stmp-targetdep + sigset.texi stmp-sigset extra.texi stmp-extra \ + stdio64.texi stmp-stdio64 tmp.texi targetdep.tex stmp-targetdep ACLOCAL_AMFLAGS = -I .. @@ -232,8 +240,9 @@ DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST) TAR = gtar GZIP_ENV = --best -DIST_SUBDIRS = argz stdlib ctype search stdio string signal time locale \ -sys reent @extra_dir@ errno misc machine unix posix syscalls . +DIST_SUBDIRS = argz stdlib ctype search stdio stdio64 string signal \ +time locale sys reent @extra_dir@ errno misc machine unix posix \ +syscalls . SOURCES = libc.a.c $(libc_la_SOURCES) OBJECTS = libc.a.$(OBJEXT) $(libc_la_OBJECTS) @@ -693,7 +702,7 @@ crt0.o: sys/crt0.o sys/crt0.o: ; @true -libc.info: sigset.texi extra.texi targetdep.tex $(SUBDEFS) +libc.info: sigset.texi extra.texi stdio64.texi targetdep.tex $(SUBDEFS) stmp-sigset: config.status if test -n "$(LIBC_SIGNAL_LIB)"; then \ @@ -717,6 +726,17 @@ stmp-extra: config.status extra.texi: stmp-extra ; @true +stmp-stdio64: config.status + if test -n "$(LIBC_STDIO64_LIB)"; then \ + echo "@set STDIO64" >tmp.texi; \ + else \ + echo "@clear STDIO64" >tmp.texi; \ + fi + $(SHELL) $(newlib_basedir)/../move-if-change tmp.texi stdio64.texi + touch $@ + +stdio64.texi: stmp-stdio64 ; @true + stmp-targetdep: force rm -f tmp.texi targetdoc=`pwd`/tmp.texi; \ diff --git a/newlib/libc/configure b/newlib/libc/configure index b068fd2ea..6800203b3 100755 --- a/newlib/libc/configure +++ b/newlib/libc/configure @@ -2961,6 +2961,28 @@ else HAVE_SIGNAL_DIR_FALSE= fi +LIBC_STDIO64_LIB= +LIBC_STDIO64_DEF= +if test -n "${stdio64_dir}"; then + if test "${use_libtool}" = "yes"; then + LIBC_STDIO64_LIB=${stdio64_dir}/lib${stdio64_dir}.${aext} + else + LIBC_STDIO64_LIB=${stdio64_dir}/lib.${aext} + fi + LIBC_STDIO64_DEF=${stdio64_dir}/stmp-def +fi + + + + +if test x${stdio64_dir} != x; then + HAVE_STDIO64_DIR_TRUE= + HAVE_STDIO64_DIR_FALSE='#' +else + HAVE_STDIO64_DIR_TRUE='#' + HAVE_STDIO64_DIR_FALSE= +fi + LIBC_SYSCALL_LIB= if test -n "${syscall_dir}"; then if test "${use_libtool}" = "yes"; then @@ -3143,7 +3165,7 @@ done ac_given_srcdir=$srcdir ac_given_INSTALL="$INSTALL" -trap 'rm -fr `echo "Makefile argz/Makefile ctype/Makefile errno/Makefile locale/Makefile misc/Makefile reent/Makefile search/Makefile stdio/Makefile stdlib/Makefile string/Makefile time/Makefile posix/Makefile signal/Makefile syscalls/Makefile unix/Makefile" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 +trap 'rm -fr `echo "Makefile argz/Makefile ctype/Makefile errno/Makefile locale/Makefile misc/Makefile reent/Makefile search/Makefile stdio/Makefile stdio64/Makefile stdlib/Makefile string/Makefile time/Makefile posix/Makefile signal/Makefile syscalls/Makefile unix/Makefile" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 EOF cat >> $CONFIG_STATUS <> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then diff --git a/newlib/libc/configure.in b/newlib/libc/configure.in index 0e61b0902..6a5eeed5e 100644 --- a/newlib/libc/configure.in +++ b/newlib/libc/configure.in @@ -55,6 +55,20 @@ AC_SUBST(LIBC_SIGNAL_LIB) AC_SUBST(LIBC_SIGNAL_DEF) AM_CONDITIONAL(HAVE_SIGNAL_DIR, test x${signal_dir} != x) +LIBC_STDIO64_LIB= +LIBC_STDIO64_DEF= +if test -n "${stdio64_dir}"; then + if test "${use_libtool}" = "yes"; then + LIBC_STDIO64_LIB=${stdio64_dir}/lib${stdio64_dir}.${aext} + else + LIBC_STDIO64_LIB=${stdio64_dir}/lib.${aext} + fi + LIBC_STDIO64_DEF=${stdio64_dir}/stmp-def +fi +AC_SUBST(LIBC_STDIO64_LIB) +AC_SUBST(LIBC_STDIO64_DEF) +AM_CONDITIONAL(HAVE_STDIO64_DIR, test x${stdio64_dir} != x) + LIBC_SYSCALL_LIB= if test -n "${syscall_dir}"; then if test "${use_libtool}" = "yes"; then @@ -110,4 +124,4 @@ fi AC_SUBST(LIBC_MACHINE_LIB) AC_SUBST(machine_dir) -AC_OUTPUT(Makefile argz/Makefile ctype/Makefile errno/Makefile locale/Makefile misc/Makefile reent/Makefile search/Makefile stdio/Makefile stdlib/Makefile string/Makefile time/Makefile posix/Makefile signal/Makefile syscalls/Makefile unix/Makefile) +AC_OUTPUT(Makefile argz/Makefile ctype/Makefile errno/Makefile locale/Makefile misc/Makefile reent/Makefile search/Makefile stdio/Makefile stdio64/Makefile stdlib/Makefile string/Makefile time/Makefile posix/Makefile signal/Makefile syscalls/Makefile unix/Makefile) diff --git a/newlib/libc/include/reent.h b/newlib/libc/include/reent.h index 56fae91a4..b54e4cbb8 100644 --- a/newlib/libc/include/reent.h +++ b/newlib/libc/include/reent.h @@ -81,6 +81,14 @@ extern _ssize_t _write_r _PARAMS ((struct _reent *, int, const void *, size_t)); /* This one is not guaranteed to be available on all targets. */ extern int _gettimeofday_r _PARAMS ((struct _reent *, struct timeval *tp, struct timezone *tzp)); +#ifdef __LARGE64_FILES +struct stat64; + +extern _off64_t _lseek64_r _PARAMS ((struct _reent *, int, _off64_t, int)); +extern int _fstat64_r _PARAMS ((struct _reent *, int, struct stat64 *)); +extern int _open64_r _PARAMS ((struct _reent *, const char *, int, int)); +#endif + #ifdef __cplusplus } #endif diff --git a/newlib/libc/include/stdio.h b/newlib/libc/include/stdio.h index 1cc83ab01..9e93ed5bc 100644 --- a/newlib/libc/include/stdio.h +++ b/newlib/libc/include/stdio.h @@ -37,7 +37,7 @@ #include /* - * defines __sFILE, _fpos_t. + * defines __FILE, _fpos_t. * They must be defined there because struct _reent needs them (and we don't * want reent.h to include this file. */ @@ -48,7 +48,11 @@ _BEGIN_STD_C typedef _fpos_t fpos_t; -typedef struct __sFILE FILE; +typedef __FILE FILE; + +#ifdef __LARGE64_FILES +typedef _fpos64_t fpos64_t; +#endif #include @@ -68,8 +72,9 @@ typedef struct __sFILE FILE; #define __SOFF 0x1000 /* set iff _offset is in fact correct */ #define __SMOD 0x2000 /* true => fgetline modified _p text */ #if defined(__CYGWIN__) || defined(__CYGWIN__) -#define __SCLE 0x4000 /* convert line endings CR/LF <-> NL */ +# define __SCLE 0x4000 /* convert line endings CR/LF <-> NL */ #endif +#define __SL64 0x8000 /* is 64-bit offset large file */ /* * The following three definitions are for ANSI C, which took them @@ -279,6 +284,22 @@ int _EXFUN(_vsscanf_r, (struct _reent *, const char *, const char *, __VALIST)); ssize_t _EXFUN(__getdelim, (char **, size_t *, int, FILE *)); ssize_t _EXFUN(__getline, (char **, size_t *, FILE *)); +#ifdef __LARGE64_FILES +FILE * _EXFUN(fopen64, (const char *, const char *)); +_off64_t _EXFUN(ftello64, (FILE *)); +_off64_t _EXFUN(fseeko64, (FILE *, _off64_t, int)); +int _EXFUN(fgetpos64, (FILE *, _fpos64_t *)); +int _EXFUN(fsetpos64, (FILE *, const _fpos64_t *)); +FILE * _EXFUN(tmpfile64, (void)); + +FILE * _EXFUN(_fopen64_r, (struct _reent *,const char *, const char *)); +_off64_t _EXFUN(_ftello64_r, (struct _reent *, FILE *)); +_off64_t _EXFUN(_fseeko64_r, (struct _reent *, FILE *, _off64_t, int)); +int _EXFUN(_fgetpos64_r, (struct _reent *, FILE *, _fpos64_t *)); +int _EXFUN(_fsetpos64_r, (struct _reent *, FILE *, const _fpos64_t *)); +FILE * _EXFUN(_tmpfile64_r, (struct _reent *)); +#endif /* __LARGE64_FILES */ + /* * Routines internal to the implementation. */ diff --git a/newlib/libc/include/sys/_types.h b/newlib/libc/include/sys/_types.h index a2f6e3929..a487676bc 100644 --- a/newlib/libc/include/sys/_types.h +++ b/newlib/libc/include/sys/_types.h @@ -10,6 +10,7 @@ #define _SYS__TYPES_H typedef long _off_t; +__extension__ typedef long long _off64_t; #if defined(__INT_MAX__) && __INT_MAX__ == 2147483647 typedef int _ssize_t; diff --git a/newlib/libc/include/sys/config.h b/newlib/libc/include/sys/config.h index e12e800f5..e49238d3a 100644 --- a/newlib/libc/include/sys/config.h +++ b/newlib/libc/include/sys/config.h @@ -48,6 +48,7 @@ #define HAVE_GETDATE #define _HAVE_SYSTYPES #define _READ_WRITE_RETURN_TYPE _ssize_t +#define __LARGE64_FILES 1 #endif #endif diff --git a/newlib/libc/include/sys/reent.h b/newlib/libc/include/sys/reent.h index f75684cdf..4b570cee7 100644 --- a/newlib/libc/include/sys/reent.h +++ b/newlib/libc/include/sys/reent.h @@ -23,8 +23,11 @@ typedef unsigned __Long __ULong; #endif #endif -#ifndef __Long +#if !defined( __Long) #include +#endif + +#ifndef __Long #define __Long __int32_t typedef __uint32_t __ULong; #endif @@ -34,13 +37,6 @@ typedef __uint32_t __ULong; * by having nearly everything possible allocated at first use. */ -struct _glue -{ - struct _glue *_next; - int _niobs; - struct __sFILE *_iobs; -}; - struct _Bigint { struct _Bigint *_next; @@ -88,7 +84,7 @@ struct _atexit { /* * Stdio buffers. * - * This and __sFILE are defined here because we need them for struct _reent, + * This and __FILE are defined here because we need them for struct _reent, * but we don't want stdio.h included when stdlib.h is. */ @@ -105,6 +101,10 @@ struct __sbuf { typedef long _fpos_t; /* XXX must match off_t in */ /* (and must be `long' for now) */ +#ifdef __LARGE64_FILES +typedef _off64_t _fpos64_t; +#endif + /* * Stdio state variables. * @@ -196,6 +196,57 @@ struct __sFILE { #endif }; +#ifdef __LARGE64_FILES +struct __sFILE64 { + unsigned char *_p; /* current position in (some) buffer */ + int _r; /* read space left for getc() */ + int _w; /* write space left for putc() */ + short _flags; /* flags, below; this FILE is free if 0 */ + short _file; /* fileno, if Unix descriptor, else -1 */ + struct __sbuf _bf; /* the buffer (at least 1 byte, if !NULL) */ + int _lbfsize; /* 0 or -_bf._size, for inline putc */ + + struct _reent *_data; + + /* operations */ + _PTR _cookie; /* cookie passed to io functions */ + + _READ_WRITE_RETURN_TYPE _EXFUN((*_read),(_PTR _cookie, char *_buf, int _n)); + _READ_WRITE_RETURN_TYPE _EXFUN((*_write),(_PTR _cookie, const char *_buf, + int _n)); + _fpos_t _EXFUN((*_seek),(_PTR _cookie, _fpos_t _offset, int _whence)); + int _EXFUN((*_close),(_PTR _cookie)); + + /* separate buffer for long sequences of ungetc() */ + struct __sbuf _ub; /* ungetc buffer */ + unsigned char *_up; /* saved _p when _p is doing ungetc data */ + int _ur; /* saved _r when _r is counting ungetc data */ + + /* tricks to meet minimum requirements even when malloc() fails */ + unsigned char _ubuf[3]; /* guarantee an ungetc() buffer */ + unsigned char _nbuf[1]; /* guarantee a getc() buffer */ + + /* separate buffer for fgetline() when line crosses buffer boundary */ + struct __sbuf _lb; /* buffer for fgetline() */ + + /* Unix stdio files get aligned to block boundaries on fseek() */ + int _blksize; /* stat.st_blksize (may be != _bf._size) */ + int _flags2; /* for future use */ + _off64_t _offset; /* current lseek offset */ + _fpos64_t _EXFUN((*_seek64),(_PTR _cookie, _fpos64_t _offset, int _whence)); +}; +typedef struct __sFILE64 __FILE; +#else +typedef struct __sFILE __FILE; +#endif /* __LARGE64_FILES */ + +struct _glue +{ + struct _glue *_next; + int _niobs; + __FILE *_iobs; +}; + /* * rand48 family support * @@ -271,7 +322,7 @@ struct _reent /* FILE is a big struct and may change over time. To try to achieve binary compatibility with future versions, put stdin,stdout,stderr here. These are pointers into member __sf defined below. */ - struct __sFILE *_stdin, *_stdout, *_stderr; /* XXX */ + __FILE *_stdin, *_stdout, *_stderr; /* XXX */ int _errno; /* local copy of errno */ @@ -305,22 +356,22 @@ struct _reent struct _atexit _atexit; struct _glue __sglue; /* root of glue chain */ - struct __sFILE *__sf; /* file descriptors */ + __FILE *__sf; /* file descriptors */ struct __sFILE_fake __sf_fake; /* fake initial stdin/out/err */ struct _misc_reent *_misc; /* strtok, multibyte states */ char *_signal_buf; /* strsignal */ }; #define _REENT_INIT(var) \ - { (struct __sFILE *)&var.__sf_fake, (struct __sFILE *)&var.__sf_fake, \ - (struct __sFILE *)&var.__sf_fake, 0, 0, _NULL, 0, 0, \ + { (__FILE *)&var.__sf_fake, (__FILE *)&var.__sf_fake, \ + (__FILE *)&var.__sf_fake, 0, 0, _NULL, 0, 0, \ "C", _NULL, _NULL, 0, 0, _NULL, _NULL, _NULL, _NULL, _NULL, \ { 0, _NULL, _NULL, 0 }, { _NULL, 0, _NULL }, _NULL, 0, _NULL, _NULL } #define _REENT_INIT_PTR(var) \ - { var->_stdin = (struct __sFILE *)&var->__sf_fake; \ - var->_stdout = (struct __sFILE *)&var->__sf_fake; \ - var->_stderr = (struct __sFILE *)&var->__sf_fake; \ + { var->_stdin = (__FILE *)&var->__sf_fake; \ + var->_stdout = (__FILE *)&var->__sf_fake; \ + var->_stderr = (__FILE *)&var->__sf_fake; \ var->_errno = 0; \ var->_inc = 0; \ var->_emergency = _NULL; \ @@ -453,7 +504,7 @@ struct _reent /* FILE is a big struct and may change over time. To try to achieve binary compatibility with future versions, put stdin,stdout,stderr here. These are pointers into member __sf defined below. */ - struct __sFILE *_stdin, *_stdout, *_stderr; + __FILE *_stdin, *_stdout, *_stderr; int _inc; /* used by tmpnam */ char _emergency[_REENT_EMERGENCY_SIZE]; @@ -511,11 +562,11 @@ struct _reent /* signal info */ void (**(_sig_func))(int); - /* These are here last so that __sFILE can grow without changing the offsets + /* These are here last so that __FILE can grow without changing the offsets of the above members (on the off chance that future binary compatibility would be broken otherwise). */ - struct _glue __sglue; /* root of glue chain */ - struct __sFILE __sf[3]; /* first three file descriptors */ + struct _glue __sglue; /* root of glue chain */ + __FILE __sf[3]; /* first three file descriptors */ }; #define _REENT_INIT(var) \ diff --git a/newlib/libc/libc.texinfo b/newlib/libc/libc.texinfo index 250fd9ca2..ef4410195 100644 --- a/newlib/libc/libc.texinfo +++ b/newlib/libc/libc.texinfo @@ -152,11 +152,17 @@ into another language, under the above conditions for modified versions. @c switch to set SIGNALS on or off, according to whether config picks up @c signal subdirectory: @include sigset.texi +@include extra.texi +@include stdio64.texi @menu * Stdlib:: * Ctype:: * Stdio:: +@ifset STDIO64 +* Stdio64:: +@end ifset + * Strings:: @ifset SIGNALS * Signals:: diff --git a/newlib/libc/reent/Makefile.am b/newlib/libc/reent/Makefile.am index 0333eff03..0504158d4 100644 --- a/newlib/libc/reent/Makefile.am +++ b/newlib/libc/reent/Makefile.am @@ -4,6 +4,18 @@ AUTOMAKE_OPTIONS = cygnus INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) +if HAVE_STDIO64_DIR +STDIO64_OBJECTS = \ + fstat64r.$(oext) \ + lseek64r.$(oext) \ + open64r.$(oext) + +STDIO64_DEFS = \ + fstat64r.def \ + lseek64r.def \ + open64r.def +endif + LIB_SOURCES = \ closer.c \ reent.c \ @@ -28,10 +40,14 @@ libreent_la_LDFLAGS = -Xcompiler -nostdlib if USE_LIBTOOL noinst_LTLIBRARIES = libreent.la libreent_la_SOURCES = $(LIB_SOURCES) +libreent_la_LIBADD = $(STDIO64_OBJECTS) +libreent_la_DEPENDENCIES = $(STDIO64_OBJECTS) noinst_DATA = objectlist.awk.in else noinst_LIBRARIES = lib.a lib_a_SOURCES = $(LIB_SOURCES) +lib_a_LIBADD = $(STDIO64_OBJECTS) +lib_a_DEPENDENCIES = $(STDIO64_OBJECTS) noinst_DATA = endif # USE_LIBTOOL @@ -51,6 +67,7 @@ CHEWOUT_FILES = \ statr.def \ timer.def \ unlinkr.def \ + $(STDIO64_DEFS) \ writer.def SUFFIXES = .def .h diff --git a/newlib/libc/reent/Makefile.in b/newlib/libc/reent/Makefile.in index dd08deca6..91d0bce7a 100644 --- a/newlib/libc/reent/Makefile.in +++ b/newlib/libc/reent/Makefile.in @@ -82,6 +82,8 @@ LIBC_MACHINE_LIB = @LIBC_MACHINE_LIB@ LIBC_POSIX_LIB = @LIBC_POSIX_LIB@ LIBC_SIGNAL_DEF = @LIBC_SIGNAL_DEF@ LIBC_SIGNAL_LIB = @LIBC_SIGNAL_LIB@ +LIBC_STDIO64_DEF = @LIBC_STDIO64_DEF@ +LIBC_STDIO64_LIB = @LIBC_STDIO64_LIB@ LIBC_SYSCALL_LIB = @LIBC_SYSCALL_LIB@ LIBC_SYS_LIB = @LIBC_SYS_LIB@ LIBC_UNIX_LIB = @LIBC_UNIX_LIB@ @@ -108,6 +110,16 @@ AUTOMAKE_OPTIONS = cygnus INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) +@HAVE_STDIO64_DIR_TRUE@STDIO64_OBJECTS = @HAVE_STDIO64_DIR_TRUE@\ +@HAVE_STDIO64_DIR_TRUE@ fstat64r.$(oext) \ +@HAVE_STDIO64_DIR_TRUE@ lseek64r.$(oext) \ +@HAVE_STDIO64_DIR_TRUE@ open64r.$(oext) + +@HAVE_STDIO64_DIR_TRUE@STDIO64_DEFS = @HAVE_STDIO64_DIR_TRUE@\ +@HAVE_STDIO64_DIR_TRUE@ fstat64r.def \ +@HAVE_STDIO64_DIR_TRUE@ lseek64r.def \ +@HAVE_STDIO64_DIR_TRUE@ open64r.def + LIB_SOURCES = \ closer.c \ reent.c \ @@ -132,10 +144,14 @@ libreent_la_LDFLAGS = -Xcompiler -nostdlib @USE_LIBTOOL_TRUE@noinst_LTLIBRARIES = @USE_LIBTOOL_TRUE@libreent.la @USE_LIBTOOL_TRUE@libreent_la_SOURCES = @USE_LIBTOOL_TRUE@$(LIB_SOURCES) +@USE_LIBTOOL_TRUE@libreent_la_LIBADD = @USE_LIBTOOL_TRUE@$(STDIO64_OBJECTS) +@USE_LIBTOOL_TRUE@libreent_la_DEPENDENCIES = @USE_LIBTOOL_TRUE@$(STDIO64_OBJECTS) @USE_LIBTOOL_TRUE@noinst_DATA = @USE_LIBTOOL_TRUE@objectlist.awk.in @USE_LIBTOOL_FALSE@noinst_DATA = @USE_LIBTOOL_FALSE@noinst_LIBRARIES = @USE_LIBTOOL_FALSE@lib.a @USE_LIBTOOL_FALSE@lib_a_SOURCES = @USE_LIBTOOL_FALSE@$(LIB_SOURCES) +@USE_LIBTOOL_FALSE@lib_a_LIBADD = @USE_LIBTOOL_FALSE@$(STDIO64_OBJECTS) +@USE_LIBTOOL_FALSE@lib_a_DEPENDENCIES = @USE_LIBTOOL_FALSE@$(STDIO64_OBJECTS) CHEWOUT_FILES = \ closer.def \ @@ -151,6 +167,7 @@ CHEWOUT_FILES = \ statr.def \ timer.def \ unlinkr.def \ + $(STDIO64_DEFS) \ writer.def @@ -169,7 +186,6 @@ LIBRARIES = $(noinst_LIBRARIES) DEFS = @DEFS@ -I. -I$(srcdir) CPPFLAGS = @CPPFLAGS@ LIBS = @LIBS@ -lib_a_LIBADD = @USE_LIBTOOL_FALSE@lib_a_OBJECTS = closer.$(OBJEXT) reent.$(OBJEXT) \ @USE_LIBTOOL_FALSE@impure.$(OBJEXT) execr.$(OBJEXT) fstatr.$(OBJEXT) \ @USE_LIBTOOL_FALSE@getreent.$(OBJEXT) linkr.$(OBJEXT) lseekr.$(OBJEXT) \ @@ -178,7 +194,6 @@ lib_a_LIBADD = @USE_LIBTOOL_FALSE@timer.$(OBJEXT) unlinkr.$(OBJEXT) writer.$(OBJEXT) LTLIBRARIES = $(noinst_LTLIBRARIES) -libreent_la_LIBADD = @USE_LIBTOOL_TRUE@libreent_la_OBJECTS = closer.lo reent.lo impure.lo \ @USE_LIBTOOL_TRUE@execr.lo fstatr.lo getreent.lo linkr.lo lseekr.lo \ @USE_LIBTOOL_TRUE@openr.lo readr.lo signalr.lo signgam.lo sbrkr.lo \ diff --git a/newlib/libc/reent/fstat64r.c b/newlib/libc/reent/fstat64r.c new file mode 100644 index 000000000..c74cf58d4 --- /dev/null +++ b/newlib/libc/reent/fstat64r.c @@ -0,0 +1,72 @@ +#ifdef __LARGE64_FILES + +/* Reentrant versions of fstat system call. This implementation just + calls the fstat system call. */ + +#include +#include +#include +#include <_syslist.h> + +/* Some targets provides their own versions of these functions. Those + targets should define REENTRANT_SYSCALLS_PROVIDED in TARGET_CFLAGS. */ + +#ifdef _REENT_ONLY +#ifndef REENTRANT_SYSCALLS_PROVIDED +#define REENTRANT_SYSCALLS_PROVIDED +#endif +#endif + +#ifdef REENTRANT_SYSCALLS_PROVIDED + +int _dummy_fstat_syscalls = 1; + +#else + +/* We use the errno variable used by the system dependent layer. */ +#undef errno +extern int errno; + +/* +FUNCTION + <<_fstat64_r>>---Reentrant version of fstat64 + +INDEX + _fstat64_r + +ANSI_SYNOPSIS + #include + int _fstat64_r(struct _reent *<[ptr]>, + int <[fd]>, struct stat64 *<[pstat]>); + +TRAD_SYNOPSIS + #include + int _fstat64_r(<[ptr]>, <[fd]>, <[pstat]>) + struct _reent *<[ptr]>; + int <[fd]>; + struct stat *<[pstat]>; + +DESCRIPTION + This is a reentrant version of <>. It + takes a pointer to the global data block, which holds + <>. This function is only enabled on systems + that define __LARGE64_FILES. +*/ + +int +_fstat64_r (ptr, fd, pstat) + struct _reent *ptr; + int fd; + struct stat64 *pstat; +{ + int ret; + + errno = 0; + if ((ret = _fstat64 (fd, pstat)) == -1 && errno != 0) + ptr->_errno = errno; + return ret; +} + +#endif /* ! defined (REENTRANT_SYSCALLS_PROVIDED) */ + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/reent/lseek64r.c b/newlib/libc/reent/lseek64r.c new file mode 100644 index 000000000..c760a5b5d --- /dev/null +++ b/newlib/libc/reent/lseek64r.c @@ -0,0 +1,68 @@ +#ifdef __LARGE64_FILES + +/* Reentrant versions of lseek system call. */ + +#include +#include +#include <_syslist.h> + +/* Some targets provides their own versions of this functions. Those + targets should define REENTRANT_SYSCALLS_PROVIDED in TARGET_CFLAGS. */ + +#ifdef _REENT_ONLY +#ifndef REENTRANT_SYSCALLS_PROVIDED +#define REENTRANT_SYSCALLS_PROVIDED +#endif +#endif + +#ifndef REENTRANT_SYSCALLS_PROVIDED + +/* We use the errno variable used by the system dependent layer. */ +#undef errno +extern int errno; + +/* +FUNCTION + <<_lseek64_r>>---Reentrant version of lseek + +INDEX + _lseek64_r + +ANSI_SYNOPSIS + #include + off64_t _lseek64_r(struct _reent *<[ptr]>, + int <[fd]>, off64_t <[pos]>, int <[whence]>); + +TRAD_SYNOPSIS + #include + off64_t _lseek64_r(<[ptr]>, <[fd]>, <[pos]>, <[whence]>) + struct _reent *<[ptr]>; + int <[fd]>; + off64_t <[pos]>; + int <[whence]>; + +DESCRIPTION + This is a reentrant version of <>. It + takes a pointer to the global data block, which holds + <>. This function only exists on a system + with large file support. +*/ + +off64_t +_lseek64_r (ptr, fd, pos, whence) + struct _reent *ptr; + int fd; + off64_t pos; + int whence; +{ + off64_t ret; + + errno = 0; + if ((ret = _lseek64 (fd, pos, whence)) == (off64_t) -1 && errno != 0) + ptr->_errno = errno; + return ret; +} + +#endif /* ! defined (REENTRANT_SYSCALLS_PROVIDED) */ + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/reent/open64r.c b/newlib/libc/reent/open64r.c new file mode 100644 index 000000000..d5ec7bcc5 --- /dev/null +++ b/newlib/libc/reent/open64r.c @@ -0,0 +1,69 @@ +#ifdef __LARGE64_FILES + +/* Reentrant versions of open system call. */ + +#include +#include +#include +#include <_syslist.h> + +/* Some targets provides their own versions of this functions. Those + targets should define REENTRANT_SYSCALLS_PROVIDED in TARGET_CFLAGS. */ + +#ifdef _REENT_ONLY +#ifndef REENTRANT_SYSCALLS_PROVIDED +#define REENTRANT_SYSCALLS_PROVIDED +#endif +#endif + +#ifndef REENTRANT_SYSCALLS_PROVIDED + +/* We use the errno variable used by the system dependent layer. */ +#undef errno +extern int errno; + +/* +FUNCTION + <<_open64_r>>---Reentrant version of open64 + +INDEX + _open64_r + +ANSI_SYNOPSIS + #include + int _open64_r(struct _reent *<[ptr]>, + const char *<[file]>, int <[flags]>, int <[mode]>); + +TRAD_SYNOPSIS + #include + int _open64_r(<[ptr]>, <[file]>, <[flags]>, <[mode]>) + struct _reent *<[ptr]>; + char *<[file]>; + int <[flags]>; + int <[mode]>; + +DESCRIPTION + This is a reentrant version of <>. It + takes a pointer to the global data block, which holds + <>. This function only exists on systems with + large file support. +*/ + +int +_open64_r (ptr, file, flags, mode) + struct _reent *ptr; + _CONST char *file; + int flags; + int mode; +{ + int ret; + + errno = 0; + if ((ret = _open64 (file, flags, mode)) == -1 && errno != 0) + ptr->_errno = errno; + return ret; +} + +#endif /* ! defined (REENTRANT_SYSCALLS_PROVIDED) */ + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/reent/reent.tex b/newlib/libc/reent/reent.tex index 545624ca9..e76330b32 100644 --- a/newlib/libc/reent/reent.tex +++ b/newlib/libc/reent/reent.tex @@ -107,6 +107,11 @@ _fstat_r _sbrk_r _gettimeofday_r _stat_r _getpid_r _times_r +@ifset STDIO64 +@exdent @emph{Additional 64-bit I/O System functions:} +_fstat64_r _lseek64_r _open64_r +@end ifset + @exdent @emph{Time function:} _asctime_r @end example diff --git a/newlib/libc/stdio/stdio.tex b/newlib/libc/stdio/stdio.tex index 725b2f35b..217aed1ef 100644 --- a/newlib/libc/stdio/stdio.tex +++ b/newlib/libc/stdio/stdio.tex @@ -189,3 +189,4 @@ structure. @page @include stdio/vfprintf.def + diff --git a/newlib/libc/stdio64/Makefile.am b/newlib/libc/stdio64/Makefile.am new file mode 100644 index 000000000..eca225ac8 --- /dev/null +++ b/newlib/libc/stdio64/Makefile.am @@ -0,0 +1,64 @@ +## Process this file with automake to generate Makefile.in + +AUTOMAKE_OPTIONS = cygnus + +INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) + +LIB_SOURCES = \ + fgetpos64.c \ + fopen64.c \ + freopen64.c \ + fseeko64.c \ + fsetpos64.c \ + fstat64r.c \ + ftello64.c \ + lseek64r.c \ + open64r.c \ + stdio64.c \ + tmpfile64.c + +libstdio64_la_LDFLAGS = -Xcompiler -nostdlib + +if USE_LIBTOOL +noinst_LTLIBRARIES = libstdio64.la +libstdio64_la_SOURCES = $(LIB_SOURCES) +LIB_COMPILE = $(LTCOMPILE) +noinst_DATA = objectlist.awk.in +else +noinst_LIBRARIES = lib.a +lib_a_SOURCES = $(LIB_SOURCES) +LIB_COMPILE = $(COMPILE) +noinst_DATA = +endif # USE_LIBTOOL + +include $(srcdir)/../../Makefile.shared + +AM_CFLAGS = -I $(srcdir)/../stdio + +CHEWOUT_FILES = \ + fgetpos64.def \ + fopen64.def \ + freopen64.def \ + fseeko64.def \ + fsetpos64.def \ + fstat64r.def \ + ftello64.def \ + lseek64r.def \ + open64r.def \ + tmpfile64.def + +SUFFIXES = .def + +CHEW = ../../doc/makedoc -f $(srcdir)/../../doc/doc.str + +.c.def: + $(CHEW) < $< > $*.def 2> $*.ref + touch stmp-def + +TARGETDOC = ../tmp.texi + +doc: $(CHEWOUT_FILES) + cat $(srcdir)/stdio64.tex >> $(TARGETDOC) + +CLEANFILES = $(CHEWOUT_FILES) *.ref + diff --git a/newlib/libc/stdio64/Makefile.in b/newlib/libc/stdio64/Makefile.in new file mode 100644 index 000000000..7d57f4d0d --- /dev/null +++ b/newlib/libc/stdio64/Makefile.in @@ -0,0 +1,412 @@ +# Makefile.in generated automatically by automake 1.4 from Makefile.am + +# Copyright (C) 1994, 1995-8, 1999 Free Software Foundation, Inc. +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + + + +SHELL = @SHELL@ + +srcdir = @srcdir@ +top_srcdir = @top_srcdir@ +VPATH = @srcdir@ +prefix = @prefix@ +exec_prefix = @exec_prefix@ + +bindir = @bindir@ +sbindir = @sbindir@ +libexecdir = @libexecdir@ +datadir = @datadir@ +sysconfdir = @sysconfdir@ +sharedstatedir = @sharedstatedir@ +localstatedir = @localstatedir@ +libdir = @libdir@ +infodir = @infodir@ +mandir = @mandir@ +includedir = @includedir@ +oldincludedir = /usr/include + +DESTDIR = + +pkgdatadir = $(datadir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ + +top_builddir = .. + +ACLOCAL = @ACLOCAL@ +AUTOCONF = @AUTOCONF@ +AUTOMAKE = @AUTOMAKE@ +AUTOHEADER = @AUTOHEADER@ + +INSTALL = @INSTALL@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ $(AM_INSTALL_PROGRAM_FLAGS) +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +transform = @program_transform_name@ + +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_alias = @build_alias@ +build_triplet = @build@ +host_alias = @host_alias@ +host_triplet = @host@ +target_alias = @target_alias@ +target_triplet = @target@ +AR = @AR@ +AS = @AS@ +CC = @CC@ +CPP = @CPP@ +CRT0 = @CRT0@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +DLLTOOL = @DLLTOOL@ +EXEEXT = @EXEEXT@ +GCJ = @GCJ@ +GCJFLAGS = @GCJFLAGS@ +LDFLAGS = @LDFLAGS@ +LIBC_EXTRA_DEF = @LIBC_EXTRA_DEF@ +LIBC_EXTRA_LIB = @LIBC_EXTRA_LIB@ +LIBC_MACHINE_LIB = @LIBC_MACHINE_LIB@ +LIBC_POSIX_LIB = @LIBC_POSIX_LIB@ +LIBC_SIGNAL_DEF = @LIBC_SIGNAL_DEF@ +LIBC_SIGNAL_LIB = @LIBC_SIGNAL_LIB@ +LIBC_SYSCALL_LIB = @LIBC_SYSCALL_LIB@ +LIBC_SYS_LIB = @LIBC_SYS_LIB@ +LIBC_UNIX_LIB = @LIBC_UNIX_LIB@ +LIBTOOL = @LIBTOOL@ +LN_S = @LN_S@ +MAINT = @MAINT@ +MAKEINFO = @MAKEINFO@ +NEWLIB_CFLAGS = @NEWLIB_CFLAGS@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +PACKAGE = @PACKAGE@ +RANLIB = @RANLIB@ +STRIP = @STRIP@ +VERSION = @VERSION@ +aext = @aext@ +extra_dir = @extra_dir@ +libm_machine_dir = @libm_machine_dir@ +machine_dir = @machine_dir@ +newlib_basedir = @newlib_basedir@ +oext = @oext@ +sys_dir = @sys_dir@ + +AUTOMAKE_OPTIONS = cygnus + +INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) + +LIB_SOURCES = \ + fgetpos64.c \ + fopen64.c \ + freopen64.c \ + fseeko64.c \ + fsetpos64.c \ + ftello64.c \ + stdio64.c \ + tmpfile64.c + + +libstdio64_la_LDFLAGS = -Xcompiler -nostdlib + +@USE_LIBTOOL_TRUE@noinst_LTLIBRARIES = @USE_LIBTOOL_TRUE@libstdio64.la +@USE_LIBTOOL_TRUE@libstdio64_la_SOURCES = @USE_LIBTOOL_TRUE@$(LIB_SOURCES) +@USE_LIBTOOL_TRUE@LIB_COMPILE = @USE_LIBTOOL_TRUE@$(LTCOMPILE) +@USE_LIBTOOL_FALSE@LIB_COMPILE = @USE_LIBTOOL_FALSE@$(COMPILE) +@USE_LIBTOOL_TRUE@noinst_DATA = @USE_LIBTOOL_TRUE@objectlist.awk.in +@USE_LIBTOOL_FALSE@noinst_DATA = +@USE_LIBTOOL_FALSE@noinst_LIBRARIES = @USE_LIBTOOL_FALSE@lib.a +@USE_LIBTOOL_FALSE@lib_a_SOURCES = @USE_LIBTOOL_FALSE@$(LIB_SOURCES) + +AM_CFLAGS = -I $(srcdir)/../stdio + +CHEWOUT_FILES = \ + fgetpos64.def \ + fopen64.def \ + freopen64.def \ + fseeko64.def \ + fsetpos64.def \ + ftello64.def \ + tmpfile64.def + + +SUFFIXES = .def + +CHEW = ../../doc/makedoc -f $(srcdir)/../../doc/doc.str + +TARGETDOC = ../tmp.texi + +CLEANFILES = $(CHEWOUT_FILES) *.ref +mkinstalldirs = $(SHELL) $(top_srcdir)/../../mkinstalldirs +CONFIG_CLEAN_FILES = +LIBRARIES = $(noinst_LIBRARIES) + + +DEFS = @DEFS@ -I. -I$(srcdir) +CPPFLAGS = @CPPFLAGS@ +LIBS = @LIBS@ +lib_a_LIBADD = +@USE_LIBTOOL_FALSE@lib_a_OBJECTS = fgetpos64.$(OBJEXT) \ +@USE_LIBTOOL_FALSE@fopen64.$(OBJEXT) freopen64.$(OBJEXT) \ +@USE_LIBTOOL_FALSE@fseeko64.$(OBJEXT) fsetpos64.$(OBJEXT) \ +@USE_LIBTOOL_FALSE@ftello64.$(OBJEXT) stdio64.$(OBJEXT) \ +@USE_LIBTOOL_FALSE@tmpfile64.$(OBJEXT) +LTLIBRARIES = $(noinst_LTLIBRARIES) + +libstdio64_la_LIBADD = +@USE_LIBTOOL_TRUE@libstdio64_la_OBJECTS = fgetpos64.lo fopen64.lo \ +@USE_LIBTOOL_TRUE@freopen64.lo fseeko64.lo fsetpos64.lo ftello64.lo \ +@USE_LIBTOOL_TRUE@stdio64.lo tmpfile64.lo +CFLAGS = @CFLAGS@ +COMPILE = $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) --mode=compile $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +CCLD = $(CC) +LINK = $(LIBTOOL) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ +DATA = $(noinst_DATA) + +DIST_COMMON = Makefile.am Makefile.in + + +DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST) + +TAR = gtar +GZIP_ENV = --best +SOURCES = $(lib_a_SOURCES) $(libstdio64_la_SOURCES) +OBJECTS = $(lib_a_OBJECTS) $(libstdio64_la_OBJECTS) + +all: all-redirect +.SUFFIXES: +.SUFFIXES: .S .c .def .lo .o .obj .s +$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ Makefile.am $(top_srcdir)/configure.in $(ACLOCAL_M4) $(srcdir)/../../Makefile.shared + cd $(top_srcdir) && $(AUTOMAKE) --cygnus stdio64/Makefile + +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + cd $(top_builddir) \ + && CONFIG_FILES=$(subdir)/$@ CONFIG_HEADERS= $(SHELL) ./config.status + + +mostlyclean-noinstLIBRARIES: + +clean-noinstLIBRARIES: + -test -z "$(noinst_LIBRARIES)" || rm -f $(noinst_LIBRARIES) + +distclean-noinstLIBRARIES: + +maintainer-clean-noinstLIBRARIES: + +.c.o: + $(COMPILE) -c $< + +# FIXME: We should only use cygpath when building on Windows, +# and only if it is available. +.c.obj: + $(COMPILE) -c `cygpath -w $<` + +.s.o: + $(COMPILE) -c $< + +.S.o: + $(COMPILE) -c $< + +mostlyclean-compile: + -rm -f *.o core *.core + -rm -f *.$(OBJEXT) + +clean-compile: + +distclean-compile: + -rm -f *.tab.c + +maintainer-clean-compile: + +.c.lo: + $(LIBTOOL) --mode=compile $(COMPILE) -c $< + +.s.lo: + $(LIBTOOL) --mode=compile $(COMPILE) -c $< + +.S.lo: + $(LIBTOOL) --mode=compile $(COMPILE) -c $< + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs + +distclean-libtool: + +maintainer-clean-libtool: + +lib.a: $(lib_a_OBJECTS) $(lib_a_DEPENDENCIES) + -rm -f lib.a + $(AR) cru lib.a $(lib_a_OBJECTS) $(lib_a_LIBADD) + $(RANLIB) lib.a + +mostlyclean-noinstLTLIBRARIES: + +clean-noinstLTLIBRARIES: + -test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES) + +distclean-noinstLTLIBRARIES: + +maintainer-clean-noinstLTLIBRARIES: + +libstdio64.la: $(libstdio64_la_OBJECTS) $(libstdio64_la_DEPENDENCIES) + $(LINK) $(libstdio64_la_LDFLAGS) $(libstdio64_la_OBJECTS) $(libstdio64_la_LIBADD) $(LIBS) + +tags: TAGS + +ID: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + here=`pwd` && cd $(srcdir) \ + && mkid -f$$here/ID $$unique $(LISP) + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) $(LISP) + tags=; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + test -z "$(ETAGS_ARGS)$$unique$(LISP)$$tags" \ + || (cd $(srcdir) && etags $(ETAGS_ARGS) $$tags $$unique $(LISP) -o $$here/TAGS) + +mostlyclean-tags: + +clean-tags: + +distclean-tags: + -rm -f TAGS ID + +maintainer-clean-tags: + +distdir = $(top_builddir)/$(PACKAGE)-$(VERSION)/$(subdir) + +subdir = stdio64 + +distdir: $(DISTFILES) + @for file in $(DISTFILES); do \ + if test -f $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + cp -pr $$d/$$file $(distdir)/$$file; \ + else \ + test -f $(distdir)/$$file \ + || ln $$d/$$file $(distdir)/$$file 2> /dev/null \ + || cp -p $$d/$$file $(distdir)/$$file || :; \ + fi; \ + done +info-am: +info: info-am +dvi-am: +dvi: dvi-am +check-am: +check: check-am +installcheck-am: +installcheck: installcheck-am +install-info-am: +install-info: install-info-am +install-exec-am: +install-exec: install-exec-am + +install-data-am: +install-data: install-data-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am +install: install-am +uninstall-am: +uninstall: uninstall-am +all-am: Makefile $(LIBRARIES) $(LTLIBRARIES) $(DATA) +all-redirect: all-am +install-strip: + $(MAKE) $(AM_MAKEFLAGS) AM_INSTALL_PROGRAM_FLAGS=-s install +installdirs: + + +mostlyclean-generic: + +clean-generic: + -test -z "$(CLEANFILES)" || rm -f $(CLEANFILES) + +distclean-generic: + -rm -f Makefile $(CONFIG_CLEAN_FILES) + -rm -f config.cache config.log stamp-h stamp-h[0-9]* + +maintainer-clean-generic: +mostlyclean-am: mostlyclean-noinstLIBRARIES mostlyclean-compile \ + mostlyclean-libtool mostlyclean-noinstLTLIBRARIES \ + mostlyclean-tags mostlyclean-generic + +mostlyclean: mostlyclean-am + +clean-am: clean-noinstLIBRARIES clean-compile clean-libtool \ + clean-noinstLTLIBRARIES clean-tags clean-generic \ + mostlyclean-am + +clean: clean-am + +distclean-am: distclean-noinstLIBRARIES distclean-compile \ + distclean-libtool distclean-noinstLTLIBRARIES \ + distclean-tags distclean-generic clean-am + -rm -f libtool + +distclean: distclean-am + +maintainer-clean-am: maintainer-clean-noinstLIBRARIES \ + maintainer-clean-compile maintainer-clean-libtool \ + maintainer-clean-noinstLTLIBRARIES \ + maintainer-clean-tags maintainer-clean-generic \ + distclean-am + @echo "This command is intended for maintainers to use;" + @echo "it deletes files that may require special tools to rebuild." + +maintainer-clean: maintainer-clean-am + +.PHONY: mostlyclean-noinstLIBRARIES distclean-noinstLIBRARIES \ +clean-noinstLIBRARIES maintainer-clean-noinstLIBRARIES \ +mostlyclean-compile distclean-compile clean-compile \ +maintainer-clean-compile mostlyclean-libtool distclean-libtool \ +clean-libtool maintainer-clean-libtool mostlyclean-noinstLTLIBRARIES \ +distclean-noinstLTLIBRARIES clean-noinstLTLIBRARIES \ +maintainer-clean-noinstLTLIBRARIES tags mostlyclean-tags distclean-tags \ +clean-tags maintainer-clean-tags distdir info-am info dvi-am dvi check \ +check-am installcheck-am installcheck install-info-am install-info \ +install-exec-am install-exec install-data-am install-data install-am \ +install uninstall-am uninstall all-redirect all-am all installdirs \ +mostlyclean-generic distclean-generic clean-generic \ +maintainer-clean-generic clean mostlyclean distclean maintainer-clean + + +objectlist.awk.in: $(noinst_LTLIBRARIES) + -rm -f objectlist.awk.in + for i in `ls *.lo` ; \ + do \ + echo $$i `pwd`/$$i >> objectlist.awk.in ; \ + done + +.c.def: + $(CHEW) < $< > $*.def 2> $*.ref + touch stmp-def + +doc: $(CHEWOUT_FILES) + cat $(srcdir)/stdio64.tex >> $(TARGETDOC) + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/newlib/libc/stdio64/fgetpos64.c b/newlib/libc/stdio64/fgetpos64.c new file mode 100644 index 000000000..055d53655 --- /dev/null +++ b/newlib/libc/stdio64/fgetpos64.c @@ -0,0 +1,66 @@ +#ifdef __LARGE64_FILES + +/* +FUNCTION +<>---record position in a large stream or file + +INDEX + fgetpos64 + +ANSI_SYNOPSIS + #include + int fgetpos64(FILE *<[fp]>, _fpos64_t *<[pos]>); + +TRAD_SYNOPSIS + #include + int fgetpos64(<[fp]>, <[pos]>) + FILE *<[fp]>; + _fpos64_t *<[pos]>; + +DESCRIPTION +Objects of type <> can have a ``position'' that records how much +of the file your program has already read. Many of the <> functions +depend on this position, and many change it as a side effect. + +You can use <> to report on the current position for a file +identified by <[fp]> that was opened by <>; <> will write +a value representing that position at <<*<[pos]>>>. Later, you can +use this value with <> to return the file to this +position. + +In the current implementation, <> simply uses a character +count to represent the file position; this is the same number that +would be returned by <>. + +RETURNS +<> returns <<0>> when successful. If <> fails, the +result is <<1>>. Failure occurs on streams that do not support +positioning or streams not opened via <>; the global <> +indicates these conditions with the value <>. + +PORTABILITY +<> is a glibc extension. + +No supporting OS subroutines are required. +*/ + +#include + +int +_DEFUN (fgetpos64, (fp, pos), + FILE * fp _AND + _fpos64_t * pos) +{ + _flockfile(fp); + *pos = (_fpos64_t)ftello64 (fp); + + if (*pos != -1) + { + _funlockfile(fp); + return 0; + } + _funlockfile(fp); + return 1; +} + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/fopen64.c b/newlib/libc/stdio64/fopen64.c new file mode 100644 index 000000000..58ea1459c --- /dev/null +++ b/newlib/libc/stdio64/fopen64.c @@ -0,0 +1,131 @@ +#ifdef __LARGE64_FILES + +/* + * Copyright (c) 1990 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that the above copyright notice and this paragraph are + * duplicated in all such forms and that any documentation, + * advertising materials, and other materials related to such + * distribution and use acknowledge that the software was developed + * by the University of California, Berkeley. The name of the + * University may not be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +/* +FUNCTION +<>---open a large file + +INDEX + fopen64 +INDEX + _fopen64_r + +ANSI_SYNOPSIS + #include + FILE *fopen64(const char *<[file]>, const char *<[mode]>); + FILE *_fopen64_r(void *<[reent]>, + const char *<[file]>, const char *<[mode]>); + +TRAD_SYNOPSIS + #include + FILE *fopen64(<[file]>, <[mode]>) + char *<[file]>; + char *<[mode]>; + + FILE *_fopen64_r(<[reent]>, <[file]>, <[mode]>) + char *<[reent]>; + char *<[file]>; + char *<[mode]>; + +DESCRIPTION +<> is identical to <> except it opens a large file that +is potentially >2GB in size. See <> for further details. + +RETURNS +<> return a file pointer which you can use for other file +operations, unless the file you requested could not be opened; in that +situation, the result is <>. If the reason for failure was an +invalid string at <[mode]>, <> is set to <>. + +PORTABILITY +<> is a glibc extension. + +Supporting OS subroutines required: <>, <>, <>, +<>, <>, <>, <>, <>. +*/ + +/* Copied from fopen.c */ + +#if defined(LIBC_SCCS) && !defined(lint) +static char sccsid[] = "%W% (Berkeley) %G%"; +#endif /* LIBC_SCCS and not lint */ + +#include +#include +#include "local64.h" +#ifdef __CYGWIN__ +#include +#endif + +FILE * +_DEFUN (_fopen64_r, (ptr, file, mode), + struct _reent *ptr _AND + _CONST char *file _AND + _CONST char *mode) +{ + register FILE *fp; + register int f; + int flags, oflags; + + if ((flags = __sflags (ptr, mode, &oflags)) == 0) + return NULL; + if ((fp = __sfp (ptr)) == NULL) + return NULL; + + if ((f = _open64_r (fp->_data, file, oflags, 0666)) < 0) + { + fp->_flags = 0; /* release */ + return NULL; + } + + fp->_file = f; + fp->_flags = flags; + fp->_cookie = (_PTR) fp; + fp->_read = __sread; + fp->_write = __swrite64; + fp->_seek = __sseek; + fp->_seek64 = __sseek64; + fp->_close = __sclose; + + if (fp->_flags & __SAPP) + fseeko64 (fp, 0, SEEK_END); + +#ifdef __SCLE + if (__stextmode (fp->_file)) + fp->_flags |= __SCLE; +#endif + + fp->_flags |= __SL64; + + return fp; +} + +#ifndef _REENT_ONLY + +FILE * +_DEFUN (fopen64, (file, mode), + _CONST char *file _AND + _CONST char *mode) +{ + return _fopen64_r (_REENT, file, mode); +} + +#endif + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/freopen64.c b/newlib/libc/stdio64/freopen64.c new file mode 100644 index 000000000..53b8e3ee8 --- /dev/null +++ b/newlib/libc/stdio64/freopen64.c @@ -0,0 +1,169 @@ +#ifdef __LARGE64_FILES + +/* + * Copyright (c) 1990 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that the above copyright notice and this paragraph are + * duplicated in all such forms and that any documentation, + * advertising materials, and other materials related to such + * distribution and use acknowledge that the software was developed + * by the University of California, Berkeley. The name of the + * University may not be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +/* +FUNCTION +<>---open a large file using an existing file descriptor + +INDEX + freopen64 + +ANSI_SYNOPSIS + #include + FILE *freopen64(const char *<[file]>, const char *<[mode]>, + FILE *<[fp]>); + +TRAD_SYNOPSIS + #include + FILE *freopen64(<[file]>, <[mode]>, <[fp]>) + char *<[file]>; + char *<[mode]>; + FILE *<[fp]>; + +DESCRIPTION +Use this variant of <> if you wish to specify a particular file +descriptor <[fp]> (notably <>, <>, or <>) for +the file. + +If <[fp]> was associated with another file or stream, <> +closes that other file or stream (but ignores any errors while closing +it). + +<[file]> and <[mode]> are used just as in <>. + +RETURNS +If successful, the result is the same as the argument <[fp]>. If the +file cannot be opened as specified, the result is <>. + +PORTABILITY +<> is a glibc extension. + +Supporting OS subroutines required: <>, <>, <>, +<>, <>, <>, <>, <>. +*/ + +#include +#include +#include +#include +#include "local64.h" + +/* + * Re-direct an existing, open (probably) file to some other file. + */ + +FILE * +_DEFUN (freopen64, (file, mode, fp), + _CONST char *file _AND + _CONST char *mode _AND + register FILE *fp) +{ + register int f; + int flags, oflags, e; + struct _reent *ptr; + + _flockfile(fp); + + CHECK_INIT (fp); + ptr = fp->_data; + + if ((flags = __sflags (ptr, mode, &oflags)) == 0) + { + (void) fclose (fp); + _funlockfile(fp); + return NULL; + } + + /* + * Remember whether the stream was open to begin with, and + * which file descriptor (if any) was associated with it. + * If it was attached to a descriptor, defer closing it, + * so that, e.g., freopen("/dev/stdin", "r", stdin) works. + * This is unnecessary if it was not a Unix file. + */ + + if (fp->_flags == 0) + fp->_flags = __SEOF; /* hold on to it */ + else + { + if (fp->_flags & __SWR) + (void) fflush (fp); + /* if close is NULL, closing is a no-op, hence pointless */ + if (fp->_close != NULL) + (void) (*fp->_close) (fp->_cookie); + } + + /* + * Now get a new descriptor to refer to the new file. + */ + + f = _open64_r (ptr, (char *) file, oflags, 0666); + e = ptr->_errno; + + /* + * Finish closing fp. Even if the open succeeded above, + * we cannot keep fp->_base: it may be the wrong size. + * This loses the effect of any setbuffer calls, + * but stdio has always done this before. + */ + + if (fp->_flags & __SMBF) + _free_r (ptr, (char *) fp->_bf._base); + fp->_w = 0; + fp->_r = 0; + fp->_p = NULL; + fp->_bf._base = NULL; + fp->_bf._size = 0; + fp->_lbfsize = 0; + if (HASUB (fp)) + FREEUB (fp); + fp->_ub._size = 0; + if (HASLB (fp)) + FREELB (fp); + fp->_lb._size = 0; + + if (f < 0) + { /* did not get it after all */ + fp->_flags = 0; /* set it free */ + ptr->_errno = e; /* restore in case _close clobbered */ + _funlockfile(fp); + return NULL; + } + + fp->_flags = flags; + fp->_file = f; + fp->_cookie = (_PTR) fp; + fp->_read = __sread; + fp->_write = __swrite64; + fp->_seek = __sseek; + fp->_seek64 = __sseek64; + fp->_close = __sclose; + +#ifdef __SCLE + if (__stextmode(fp->_file)) + fp->_flags |= __SCLE; +#endif + + fp->flags |= __SL64; + + _funlockfile(fp); + return fp; +} + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/fseeko64.c b/newlib/libc/stdio64/fseeko64.c new file mode 100644 index 000000000..2c312cfbe --- /dev/null +++ b/newlib/libc/stdio64/fseeko64.c @@ -0,0 +1,330 @@ +#ifdef __LARGE64_FILES + +/* + * Copyright (c) 1990 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that the above copyright notice and this paragraph are + * duplicated in all such forms and that any documentation, + * advertising materials, and other materials related to such + * distribution and use acknowledge that the software was developed + * by the University of California, Berkeley. The name of the + * University may not be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +/* +FUNCTION +<>---set file position for large file + +INDEX + fseeko64 + +ANSI_SYNOPSIS + #include + int fseeko64(FILE *<[fp]>, _off64_t <[offset]>, int <[whence]>) + +TRAD_SYNOPSIS + #include + + int fseeko64(<[fp]>, <[offset]>, <[whence]>) + FILE *<[fp]>; + _off64_t <[offset]>; + int <[whence]>; + +DESCRIPTION +Objects of type <> can have a ``position'' that records how much +of the file your program has already read. Many of the <> functions +depend on this position, and many change it as a side effect. + +You can use <> to set the position for the file identified by +<[fp]> that was opened via <>. The value of <[offset]> determines +the new position, in one of three ways selected by the value of <[whence]> +(defined as macros in `<>'): + +<>---<[offset]> is the absolute file position (an offset +from the beginning of the file) desired. <[offset]> must be positive. + +<>---<[offset]> is relative to the current file position. +<[offset]> can meaningfully be either positive or negative. + +<>---<[offset]> is relative to the current end of file. +<[offset]> can meaningfully be either positive (to increase the size +of the file) or negative. + +See <> to determine the current file position. + +RETURNS +<> returns <<0>> when successful. On failure, the +result is <>. The reason for failure is indicated in <>: +either <> (the stream identified by <[fp]> doesn't support +repositioning or wasn't opened via <>) or <> +(invalid file position). + +PORTABILITY +<> is a glibc extension. + +Supporting OS subroutines required: <>, <>, <>, +<>, <>, <>, <>. +*/ + +#include +#include +#include +#include +#include +#include +#include "local64.h" + +#define POS_ERR (-(_fpos64_t)1) + +/* + * Seek the given file to the given offset. + * `Whence' must be one of the three SEEK_* macros. + */ + +int +fseeko64 (fp, offset, whence) + register FILE *fp; + _off64_t offset; + int whence; +{ + struct _reent *ptr; + _fpos64_t _EXFUN ((*seekfn), (void *, _fpos64_t, int)); + _fpos64_t target, curoff; + size_t n; + struct stat st; + int havepos; + + _flockfile(fp); + + /* Make sure stdio is set up. */ + + CHECK_INIT (fp); + ptr = fp->_data; + + /* If we've been doing some writing, and we're in append mode + then we don't really know where the filepos is. */ + + if (fp->_flags & __SAPP && fp->_flags & __SWR) + { + /* So flush the buffer and seek to the end. */ + fflush (fp); + } + + /* Have to be able to seek. */ + + if ((seekfn = fp->_seek64) == NULL || !(fp->_flags & __SL64)) + { + ptr->_errno = ESPIPE; /* ??? */ + _funlockfile(fp); + return EOF; + } + + /* + * Change any SEEK_CUR to SEEK_SET, and check `whence' argument. + * After this, whence is either SEEK_SET or SEEK_END. + */ + + switch (whence) + { + case SEEK_CUR: + /* + * In order to seek relative to the current stream offset, + * we have to first find the current stream offset a la + * ftell (see ftell for details). + */ + fflush(fp); /* may adjust seek offset on append stream */ + if (fp->_flags & __SOFF) + curoff = fp->_offset; + else + { + curoff = (*seekfn) (fp->_cookie, (_fpos64_t) 0, SEEK_CUR); + if (curoff == -1L) + { + _funlockfile(fp); + return EOF; + } + } + if (fp->_flags & __SRD) + { + curoff -= fp->_r; + if (HASUB (fp)) + curoff -= fp->_ur; + } + else if (fp->_flags & __SWR && fp->_p != NULL) + curoff += fp->_p - fp->_bf._base; + + offset += curoff; + whence = SEEK_SET; + havepos = 1; + break; + + case SEEK_SET: + case SEEK_END: + havepos = 0; + break; + + default: + ptr->_errno = EINVAL; + _funlockfile(fp); + return (EOF); + } + + /* + * Can only optimise if: + * reading (and not reading-and-writing); + * not unbuffered; and + * this is a `regular' Unix file (and hence seekfn==__sseek). + * We must check __NBF first, because it is possible to have __NBF + * and __SOPT both set. + */ + + if (fp->_bf._base == NULL) + __smakebuf (fp); + if (fp->_flags & (__SWR | __SRW | __SNBF | __SNPT)) + goto dumb; + if ((fp->_flags & __SOPT) == 0) + { + if (seekfn != __sseek64 + || fp->_file < 0 + || _fstat64_r (ptr, fp->_file, &st) + || (st.st_mode & S_IFMT) != S_IFREG) + { + fp->_flags |= __SNPT; + goto dumb; + } +#ifdef HAVE_BLKSIZE + fp->_blksize = st.st_blksize; +#else + fp->_blksize = 1024; +#endif + fp->_flags |= __SOPT; + } + + /* + * We are reading; we can try to optimise. + * Figure out where we are going and where we are now. + */ + + if (whence == SEEK_SET) + target = offset; + else + { + if (_fstat64_r (ptr, fp->_file, &st)) + goto dumb; + target = st.st_size + offset; + } + + if (!havepos) + { + if (fp->_flags & __SOFF) + curoff = fp->_offset; + else + { + curoff = (*seekfn) (fp->_cookie, (_fpos64_t)0, SEEK_CUR); + if (curoff == POS_ERR) + goto dumb; + } + curoff -= fp->_r; + if (HASUB (fp)) + curoff -= fp->_ur; + } + + /* + * Compute the number of bytes in the input buffer (pretending + * that any ungetc() input has been discarded). Adjust current + * offset backwards by this count so that it represents the + * file offset for the first byte in the current input buffer. + */ + + if (HASUB (fp)) + { + curoff += fp->_r; /* kill off ungetc */ + n = fp->_up - fp->_bf._base; + curoff -= n; + n += fp->_ur; + } + else + { + n = fp->_p - fp->_bf._base; + curoff -= n; + n += fp->_r; + } + + /* + * If the target offset is within the current buffer, + * simply adjust the pointers, clear EOF, undo ungetc(), + * and return. (If the buffer was modified, we have to + * skip this; see fgetline.c.) + */ + + if ((fp->_flags & __SMOD) == 0 && + target >= curoff && target < curoff + n) + { + register int o = target - curoff; + + fp->_p = fp->_bf._base + o; + fp->_r = n - o; + if (HASUB (fp)) + FREEUB (fp); + fp->_flags &= ~__SEOF; + _funlockfile(fp); + return 0; + } + + /* + * The place we want to get to is not within the current buffer, + * but we can still be kind to the kernel copyout mechanism. + * By aligning the file offset to a block boundary, we can let + * the kernel use the VM hardware to map pages instead of + * copying bytes laboriously. Using a block boundary also + * ensures that we only read one block, rather than two. + */ + + curoff = target & ~((_fpos64_t)(fp->_blksize - 1)); + if ((*seekfn) (fp->_cookie, curoff, SEEK_SET) == POS_ERR) + goto dumb; + fp->_r = 0; + fp->_p = fp->_bf._base; + if (HASUB (fp)) + FREEUB (fp); + fp->_flags &= ~__SEOF; + n = target - curoff; + if (n) + { + if (__srefill (fp) || fp->_r < n) + goto dumb; + fp->_p += n; + fp->_r -= n; + } + _funlockfile(fp); + return 0; + + /* + * We get here if we cannot optimise the seek ... just + * do it. Allow the seek function to change fp->_bf._base. + */ + +dumb: + if (fflush (fp) || (*seekfn) (fp->_cookie, offset, whence) == POS_ERR) + { + _funlockfile(fp); + return EOF; + } + /* success: clear EOF indicator and discard ungetc() data */ + if (HASUB (fp)) + FREEUB (fp); + fp->_p = fp->_bf._base; + fp->_r = 0; + /* fp->_w = 0; *//* unnecessary (I think...) */ + fp->_flags &= ~__SEOF; + _funlockfile(fp); + return 0; +} + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/fsetpos64.c b/newlib/libc/stdio64/fsetpos64.c new file mode 100644 index 000000000..0cc552d47 --- /dev/null +++ b/newlib/libc/stdio64/fsetpos64.c @@ -0,0 +1,57 @@ +#ifdef __LARGE64_FILES + +/* +FUNCTION +<>---restore position of a large stream or file + +INDEX + fsetpos64 + +ANSI_SYNOPSIS + #include + int fsetpos64(FILE *<[fp]>, const _fpos64_t *<[pos]>); + +TRAD_SYNOPSIS + #include + int fsetpos64(<[fp]>, <[pos]>) + FILE *<[fp]>; + _fpos64_t *<[pos]>; + +DESCRIPTION +Objects of type <> can have a ``position'' that records how much +of the file your program has already read. Many of the <> functions +depend on this position, and many change it as a side effect. + +You can use <> to return the large file identified by <[fp]> to a +previous position <<*<[pos]>>> (after first recording it with <>). + +See <> for a similar facility. + +RETURNS +<> returns <<0>> when successful. If <> fails, the +result is <<1>>. The reason for failure is indicated in <>: +either <> (the stream identified by <[fp]> doesn't support +64-bit repositioning) or <> (invalid file position). + +PORTABILITY +<> is a glibc extension. + +Supporting OS subroutines required: <>, <>, <>, +<>, <>, <>, <>. +*/ + +#include + +int +_DEFUN (fsetpos64, (iop, pos), + FILE * iop _AND + _CONST _fpos64_t * pos) +{ + int x = fseeko64 (iop, (_off64_t)(*pos), SEEK_SET); + + if (x != 0) + return 1; + return 0; +} + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/ftello64.c b/newlib/libc/stdio64/ftello64.c new file mode 100644 index 000000000..c6b888cf4 --- /dev/null +++ b/newlib/libc/stdio64/ftello64.c @@ -0,0 +1,138 @@ +#ifdef __LARGE64_FILES + +/* + * Copyright (c) 1990 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that the above copyright notice and this paragraph are + * duplicated in all such forms and that any documentation, + * advertising materials, and other materials related to such + * distribution and use acknowledge that the software was developed + * by the University of California, Berkeley. The name of the + * University may not be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +/* +FUNCTION +<>---return position in a stream or file + +INDEX + ftello64 + +ANSI_SYNOPSIS + #include + _off64_t ftello64(FILE *<[fp]>); + +TRAD_SYNOPSIS + #include + _off64_t ftello64(<[fp]>) + FILE *<[fp]>; + +DESCRIPTION +Objects of type <> can have a ``position'' that records how much +of the file your program has already read. Many of the <> functions +depend on this position, and many change it as a side effect. + +The result of <> is the current position for a large file +identified by <[fp]>. If you record this result, you can later +use it with <> to return the file to this +position. The difference between <> and <> is that +<> returns <> and <> is designed to work +for large files (>2GB) and returns <<_off64_t>>. + +In the current implementation, <> simply uses a character +count to represent the file position; this is the same number that +would be recorded by <>. + +The function exists only if the __LARGE64_FILES flag is defined. +An error occurs if the <[fp]> was not opened via <>. + +RETURNS +<> returns the file position, if possible. If it cannot do +this, it returns <<-1>>. Failure occurs on streams that do not support +positioning or not opened via <>; the global <> indicates +this condition with the value <>. + +PORTABILITY +<> is a glibc extension. + +No supporting OS subroutines are required. +*/ + +#if defined(LIBC_SCCS) && !defined(lint) +static char sccsid[] = "%W% (Berkeley) %G%"; +#endif /* LIBC_SCCS and not lint */ + +/* + * ftello64: return current offset. + */ + +#include +#include + +#include "local64.h" + +_off64_t +_DEFUN (ftello64, (fp), + register FILE * fp) +{ + _fpos64_t pos; + + _flockfile(fp); + + /* Ensure stdio is set up. */ + + CHECK_INIT (fp); + + if (fp->_seek64 == NULL) + { + fp->_data->_errno = ESPIPE; + _funlockfile(fp); + return -1L; + } + + /* Find offset of underlying I/O object, then + adjust for buffered bytes. */ + fflush(fp); /* may adjust seek offset on append stream */ + if (fp->_flags & __SOFF) + pos = fp->_offset; + else + { + pos = (*fp->_seek64) (fp->_cookie, (_fpos64_t) 0, SEEK_CUR); + if (pos == -1L) + { + _funlockfile(fp); + return pos; + } + } + if (fp->_flags & __SRD) + { + /* + * Reading. Any unread characters (including + * those from ungetc) cause the position to be + * smaller than that in the underlying object. + */ + pos -= fp->_r; + if (HASUB (fp)) + pos -= fp->_ur; + } + else if (fp->_flags & __SWR && fp->_p != NULL) + { + /* + * Writing. Any buffered characters cause the + * position to be greater than that in the + * underlying object. + */ + pos += fp->_p - fp->_bf._base; + } + + _funlockfile(fp); + return pos; +} + +#endif /* __LARGE64_FILES */ diff --git a/newlib/libc/stdio64/local64.h b/newlib/libc/stdio64/local64.h new file mode 100644 index 000000000..b1ed1dcbb --- /dev/null +++ b/newlib/libc/stdio64/local64.h @@ -0,0 +1,13 @@ +/* + * Information local to this implementation of stdio64, + * in particular, macros and private variables. + */ + +#include "local.h" + +#ifdef __LARGE64_FILES +extern fpos64_t _EXFUN(__sseek64,(void *, fpos64_t, int)); +extern fpos64_t _EXFUN(__sseek64_error,(void *, fpos64_t, int)); +extern _READ_WRITE_RETURN_TYPE _EXFUN(__swrite64,(void *, char const *, int)); +#endif + diff --git a/newlib/libc/stdio64/stdio64.c b/newlib/libc/stdio64/stdio64.c new file mode 100644 index 000000000..7b9e16480 --- /dev/null +++ b/newlib/libc/stdio64/stdio64.c @@ -0,0 +1,79 @@ +/* No user fns here. Pesch 15apr92. */ + +/* + * Copyright (c) 1990 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that the above copyright notice and this paragraph are + * duplicated in all such forms and that any documentation, + * advertising materials, and other materials related to such + * distribution and use acknowledge that the software was developed + * by the University of California, Berkeley. The name of the + * University may not be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +#include +#include +#include +#include +#include +#include "local.h" + +#ifdef __LARGE64_FILES +_fpos64_t +__sseek64 (cookie, offset, whence) + _PTR cookie; + _fpos64_t offset; + int whence; +{ + register FILE *fp = (FILE *) cookie; + register _off64_t ret; + + ret = _lseek64_r (fp->_data, fp->_file, (_off64_t) offset, whence); + if (ret == (_fpos64_t)-1L) + fp->_flags &= ~__SOFF; + else + { + fp->_flags |= __SOFF; + fp->_offset = ret; + } + return ret; +} + +_READ_WRITE_RETURN_TYPE +__swrite64 (cookie, buf, n) + _PTR cookie; + char _CONST *buf; + int n; +{ + register FILE *fp = (FILE *) cookie; + int w; +#ifdef __SCLE + int oldmode=0; +#endif + + if (fp->_flags & __SAPP) + (void) _lseek64_r (fp->_data, fp->_file, (_off64_t)0, SEEK_END); + fp->_flags &= ~__SOFF; /* in case O_APPEND mode is set */ + +#ifdef __SCLE + if (fp->_flags & __SCLE) + oldmode = setmode(fp->_file, O_BINARY); +#endif + + w = _write_r (fp->_data, fp->_file, buf, n); + +#ifdef __SCLE + if (oldmode) + setmode(fp->_file, oldmode); +#endif + + return w; +} +#endif /* __LARGE64_FILES */ + diff --git a/newlib/libc/stdio64/stdio64.tex b/newlib/libc/stdio64/stdio64.tex new file mode 100644 index 000000000..55818c354 --- /dev/null +++ b/newlib/libc/stdio64/stdio64.tex @@ -0,0 +1,42 @@ +@node Stdio64 +@chapter Large File Input and Output (@file{stdio.h}) + +This chapter comprises additional functions to manage large files which +are potentially larger than 2GB. + +The underlying facilities for input and output depend on the host +system, but these functions provide a uniform interface. + +The corresponding declarations are in @file{stdio.h}. + +@menu +* fopen64:: Open a large file +* freopen64:: Open a large file using an existing file descriptor +* fsetpos64:: Restore position of a large stream or file +* fgetpos64:: Get position of a large stream or file +* ftello64:: Return position in a large stream or file +* fseeko64:: Set large file position +* tmpfile64:: Create a temporary large file +@end menu + +@page +@include stdio64/fopen64.def + +@page +@include stdio64/freopen64.def + +@page +@include stdio64/ftello64.def + +@page +@include stdio64/fseeko64.def + +@page +@include stdio64/fgetpos64.def + +@page +@include stdio64/fsetpos64.def + +@page +@include stdio64/tmpfile64.def + diff --git a/newlib/libc/stdio64/tmpfile64.c b/newlib/libc/stdio64/tmpfile64.c new file mode 100644 index 000000000..c26a6204b --- /dev/null +++ b/newlib/libc/stdio64/tmpfile64.c @@ -0,0 +1,84 @@ +#ifdef __LARGE64_FILES + +/* +FUNCTION +<>---create a large temporary file + +INDEX + tmpfile64 +INDEX + _tmpfile64_r + +ANSI_SYNOPSIS + #include + FILE *tmpfile64(void); + + FILE *_tmpfile64_r(void *<[reent]>); + +TRAD_SYNOPSIS + #include + FILE *tmpfile64(); + + FILE *_tmpfile64_r(<[reent]>) + char *<[reent]>; + +DESCRIPTION +Create a large temporary file (a file which will be deleted automatically), +using a name generated by <>. The temporary file is opened with +the mode <<"wb+">>, permitting you to read and write anywhere in it +as a binary file (without any data transformations the host system may +perform for text files). The file may be larger than 2GB. + +The alternate function <<_tmpfile64_r>> is a reentrant version. The +argument <[reent]> is a pointer to a reentrancy structure. + +Both <> and <<_tmpfile64_r>> are only defined if __LARGE64_FILES +is defined. + +RETURNS +<> normally returns a pointer to the temporary file. If no +temporary file could be created, the result is NULL, and <> +records the reason for failure. + +PORTABILITY +<> is a glibc extension. + +Supporting OS subroutines required: <>, <>, <>, +<>, <>, <>, <>, <>, <>. + +<> also requires the global pointer <>. +*/ + +#include +#include + +FILE * +_DEFUN (_tmpfile64_r, (ptr), + struct _reent *ptr) +{ + FILE *fp; + int e; + char *f; + char buf[L_tmpnam]; + + if ((f = _tmpnam_r (ptr, buf)) == NULL) + return NULL; + fp = fopen64 (f, "wb+"); + e = ptr->_errno; + _CAST_VOID remove (f); + ptr->_errno = e; + return fp; +} + +#ifndef _REENT_ONLY + +FILE * +_DEFUN_VOID (tmpfile64) +{ + return _tmpfile64_r (_REENT); +} + +#endif + +#endif /* __LARGE64_FILES */ + diff --git a/newlib/libc/sys.tex b/newlib/libc/sys.tex index 3182b71c5..362732ace 100644 --- a/newlib/libc/sys.tex +++ b/newlib/libc/sys.tex @@ -180,7 +180,14 @@ int lseek(int file, int ptr, int dir)@{ @} @end example -@c FIXME! Why no stub for open? +@item open +Open a file. Minimal implementation: + +@example +int open(const char *name, int flags, int mode)@{ + return -1; +@} +@end example @item read Read from a file. Minimal implementation: @@ -341,6 +348,17 @@ int _open_r(void *@var{reent}, const char *@var{file}, int @var{flags}, int @var{mode}); @end example +@ifset STDIO64 +@item _open64_r +A reentrant version of @code{open64}. It takes a pointer +to the global data block, which holds @code{errno}. + +@example +int _open64_r(void *@var{reent}, + const char *@var{file}, int @var{flags}, int @var{mode}); +@end example +@end ifset + @item _close_r A reentrant version of @code{close}. It takes a pointer to the global data block, which holds @code{errno}. @@ -358,6 +376,17 @@ off_t _lseek_r(void *@var{reent}, int @var{fd}, off_t @var{pos}, int @var{whence}); @end example +@ifset STDIO64 +@item _lseek64_r +A reentrant version of @code{lseek64}. It takes a pointer to the global +data block, which holds @code{errno}. + +@example +off_t _lseek64_r(void *@var{reent}, + int @var{fd}, off_t @var{pos}, int @var{whence}); +@end example +@end ifset + @item _read_r A reentrant version of @code{read}. It takes a pointer to the global data block, which holds @code{errno}. @@ -410,6 +439,17 @@ int _fstat_r(void *@var{reent}, int @var{fd}, struct stat *@var{pstat}); @end example +@ifset STDIO64 +@item _fstat64_r +A reentrant version of @code{fstat64}. It takes a pointer to the global +data block, which holds @code{errno}. + +@example +int _fstat64_r(void *@var{reent}, + int @var{fd}, struct stat *@var{pstat}); +@end example +@end ifset + @item _link_r A reentrant version of @code{link}. It takes a pointer to the global data block, which holds @code{errno}. diff --git a/newlib/libc/sys/linux/io64.c b/newlib/libc/sys/linux/io64.c index f54c40597..90e48888e 100644 --- a/newlib/libc/sys/linux/io64.c +++ b/newlib/libc/sys/linux/io64.c @@ -27,6 +27,7 @@ loff_t __libc_lseek64(int fd, loff_t offset, int whence) return pos; } weak_alias(__libc_lseek64,lseek64); +weak_alias(__libc_lseek64,_lseek64); int __libc_open64(const char *path, int oflag, ...) { @@ -41,6 +42,8 @@ int __libc_open64(const char *path, int oflag, ...) return __libc_open(path, oflag | O_LARGEFILE, mode); } weak_alias(__libc_open64,open64); +weak_alias(__libc_open64,_open64); weak_alias(__libc_open64,__open64); +weak_alias(__libc_fstat64,_fstat64);