[RFD] Trying to move Cygwin over to 64 bit file access

J. Johnston jjohnstn@redhat.com
Wed Jun 12 17:01:00 GMT 2002

Corinna Vinschen wrote:
> On Tue, Jun 11, 2002 at 03:56:44PM -0400, J. Johnston wrote:
> > Actually, this should be relatively straightforward.  What you need to
> > do is to extend the current __sFILE structure and create a new __sFILE64.
> > You still need the old __sFILE struct.  The new structure adds a 64-bit
> > offset field to the end and changes the prototype of the _seek function pointer.
> > You also need to add a new flag to stdio.h (0x8000 is still available) which means "this
> Yeah, that sounds good to me.
> > is a 64-bit offset file".  The flag gets set on by fopen64 which returns a
> > struct __sFILE64 pointer.  You can set fopen -> fopen64 and FILE to be struct __sFILE64
> > by default so it is all hidden for new code.
> This is done by some Makefile magic in Cygwin then.  We already use
> this technique to give new applications access to POSIX regex funcs
> while old apps still use the original V8 regex implementation.
> > For the REENT struct you can just always let the default std streams default as 32-bit
> > files.  If there is any reason to check, you can always look at the difference
> > between the original stdin, stdout, and stderr pointers which will tell you which
> > type of FILE was used at compilation time.
> Would it hurt to redefine REENT using __sFILE64?  All these are pointers
> so the REENT struct wouldn't grow.  It's just the evaluation of 32/64
> bit needed additionally.

The problem you might run into is if the user has allocated their own reentrancy structure
with an old header file.  In the findfp.c code, we set the _iobs pointer to &__sf[0].
You can see how this won't work if we treat them as __sFILE64.  So, you must account for
both scenarios where the _iobs field is accessed.

> Style question:
> What about the newlib functions?  Just to pick an example, is it ok to
> define e.g. _lseek_r in libc/reent/lseekr.c as
>   #ifdef __CYGWIN__
>   typedef __off64_t __loff_t
>   #define LSEEK lseek64
>   #else
>   typedef off_t __loff_t
>   #define LSEEK _lseek
>   #endif
>   __loff_t
>   _lseek_r (ptr, fd, pos, whence)
>      struct _reent *ptr;
>      int fd;
>      __loff_t pos;
>      int whence;
>   {
>     __loff_t ret;
>     errno = 0;
>     if ((ret = LSEEK (fd, pos, whence)) == (off_t) -1 && errno != 0)
>       ptr->_errno = errno;
>     return ret;
>   }
> or would you prefer a different way to do stuff like that?

I would prefer:
 1. you don't use __CYGWIN__ as the flag to check since other platforms may need/want this
 2. you are consistent with the naming scheme (_lseek64 vs lseek64)

In the case above, the cast should be (__loff_t)-1 but I am sure you would have spotted
that if it wasn't just an example.

It would also be nice if you could update the reent docs to mention that for platforms that
support 64-bit platforms they should set flag-x and supply OS calls: a, b, c...

-- Jeff J.

More information about the Newlib mailing list