PATCH: 64bit file handling

Marcus Meissner marcus at jet.franken.de
Fri May 11 05:04:38 CDT 2001


Hi,

This patch implements 64bit filehandling. In case 64bit file functions
are not there, they are implement as forwarders to 32bit functions in 
library/port.c.

I was unable to test the forwarders (except that they compile I think),
since you can't avoid linking against the real functions with glibc.

This patch will cause warnings (and probably errors) if not compiled on
gcc, due to missing long long.

Tested on:
	* glibc 2.2.1, linux 2.4.2	(compiles and works)
	* glibc 2.1.3, linux 2.2.14	(compiles and works, but 
					 64 bit files cannot be created)

I have included a small test program, which tests the included functions.

Please report any failures.

Ciao, Marcus

Changelog:
	Implemented 64bit filesize handling.
	Removed several unneeded sys/stat.h includes.

Index: configure.in
===================================================================
RCS file: /home/wine/wine/configure.in,v
retrieving revision 1.199
diff -u -r1.199 configure.in
--- configure.in	2001/05/07 18:21:11	1.199
+++ configure.in	2001/05/11 10:10:11
@@ -757,6 +772,8 @@
 	ecvt \
 	finite \
 	fpclass \
+	fstat64 \
+	ftruncate64 \
 	getnetbyaddr \
 	getnetbyname \
 	getpagesize \
@@ -766,7 +783,9 @@
 	getservbyport \
 	getsockopt \
 	inet_network \
+	lseek64 \
 	lstat \
+	lstat64 \
 	memmove \
 	mmap \
 	rfork \
@@ -774,6 +793,7 @@
 	sendmsg \
 	settimeofday \
 	sigaltstack \
+	stat64 \
 	statfs \
 	strcasecmp \
 	strerror \
@@ -850,6 +870,43 @@
 AC_TYPE_SIZE_T()
 AC_CHECK_SIZEOF(long long,0)
 
+AC_CACHE_CHECK("for off64_t",
+	wine_cv_off64_t,
+	AC_TRY_COMPILE([
+		#define _LARGEFILE64_SOURCE
+		#include <sys/types.h>
+	],[
+		off64_t testoffset;
+	],
+	wine_cv_off64_t="yes",
+	wine_cv_off64_t="no",
+	wine_cv_off64_t="yes"
+	)
+    )
+    if test "$wine_cv_off64_t" = "yes"
+    then
+        AC_DEFINE(HAVE_OFF64_T)
+    fi
+
+AC_CACHE_CHECK("for struct stat64",
+	wine_cv_struct_stat64,
+	AC_TRY_COMPILE([
+		#define _LARGEFILE64_SOURCE
+		#include <sys/types.h>
+		#include <sys/stat.h>
+	],[
+		struct stat64 tst64;
+	],
+	wine_cv_struct_stat64="yes",
+	wine_cv_struct_stat64="no",
+	wine_cv_struct_stat64="yes"
+	)
+    )
+    if test "$wine_cv_struct_stat64" = "yes"
+    then
+        AC_DEFINE(HAVE_STRUCT_STAT64)
+    fi
+
 AC_CACHE_CHECK("whether linux/input.h is for real",
 	wine_cv_linux_input_h,
 	AC_TRY_COMPILE([
Index: dlls/shell32/shelllink.c
===================================================================
RCS file: /home/wine/wine/dlls/shell32/shelllink.c,v
retrieving revision 1.33
diff -u -r1.33 shelllink.c
--- dlls/shell32/shelllink.c	2001/02/12 01:17:39	1.33
+++ dlls/shell32/shelllink.c	2001/05/11 10:10:42
@@ -8,7 +8,6 @@
 #include "config.h"
 
 #include <string.h>
-#include <sys/stat.h>
 #include <stdio.h>
 #include <unistd.h>
 #include <errno.h>
Index: dlls/winaspi/aspi.c
===================================================================
RCS file: /home/wine/wine/dlls/winaspi/aspi.c,v
retrieving revision 1.12
diff -u -r1.12 aspi.c
--- dlls/winaspi/aspi.c	2001/05/09 17:31:34	1.12
+++ dlls/winaspi/aspi.c	2001/05/11 10:10:53
@@ -25,7 +25,6 @@
 */
 #include <stdio.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <sys/ioctl.h>
 #include <fcntl.h>
 #include <dirent.h>
Index: dlls/winaspi/winaspi16.c
===================================================================
RCS file: /home/wine/wine/dlls/winaspi/winaspi16.c,v
retrieving revision 1.25
diff -u -r1.25 winaspi16.c
--- dlls/winaspi/winaspi16.c	2000/12/13 20:20:14	1.25
+++ dlls/winaspi/winaspi16.c	2001/05/11 10:10:53
@@ -2,7 +2,6 @@
 
 #include <stdlib.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <memory.h>
Index: dlls/winaspi/winaspi32.c
===================================================================
RCS file: /home/wine/wine/dlls/winaspi/winaspi32.c,v
retrieving revision 1.14
diff -u -r1.14 winaspi32.c
--- dlls/winaspi/winaspi32.c	2001/01/17 22:03:19	1.14
+++ dlls/winaspi/winaspi32.c	2001/05/11 10:10:53
@@ -4,7 +4,6 @@
 #include <stdlib.h>
 #include <stdio.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <memory.h>
Index: dlls/winedos/dosvm.c
===================================================================
RCS file: /home/wine/wine/dlls/winedos/dosvm.c,v
retrieving revision 1.5
diff -u -r1.5 dosvm.c
--- dlls/winedos/dosvm.c	2001/04/27 18:03:09	1.5
+++ dlls/winedos/dosvm.c	2001/05/11 10:10:54
@@ -17,7 +17,6 @@
 #include <unistd.h>
 #include <sys/time.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 
 #include "wine/winbase16.h"
 #include "wine/exception.h"
Index: dlls/wineps/afm.c
===================================================================
RCS file: /home/wine/wine/dlls/wineps/afm.c,v
retrieving revision 1.13
diff -u -r1.13 afm.c
--- dlls/wineps/afm.c	2001/05/09 17:11:59	1.13
+++ dlls/wineps/afm.c	2001/05/11 10:10:58
@@ -9,7 +9,6 @@
 #include <string.h>
 #include <stdlib.h> 	/* qsort() & bsearch() */
 #include <stdio.h>
-#include <sys/stat.h>
 #include <dirent.h>
 #include <limits.h> 	/* INT_MIN */
 #include <float.h>  	/* FLT_MAX */
Index: dlls/wininet/ftp.c
===================================================================
RCS file: /home/wine/wine/dlls/wininet/ftp.c,v
retrieving revision 1.14
diff -u -r1.14 ftp.c
--- dlls/wininet/ftp.c	2001/02/15 21:24:07	1.14
+++ dlls/wininet/ftp.c	2001/05/11 10:11:03
@@ -22,7 +22,6 @@
 #ifdef HAVE_SYS_SOCKET_H
 # include <sys/socket.h>
 #endif
-#include <sys/stat.h>
 #include <unistd.h>
 #include <time.h>
 #ifdef HAVE_NETINET_IN_SYSTM_H
Index: files/file.c
===================================================================
RCS file: /home/wine/wine/files/file.c,v
retrieving revision 1.95
diff -u -r1.95 file.c
--- files/file.c	2001/03/22 20:09:34	1.95
+++ files/file.c	2001/05/11 10:11:26
@@ -10,6 +10,7 @@
  */
 
 #include "config.h"
+#include "wine/port.h"
 
 #include <assert.h>
 #include <ctype.h>
@@ -36,7 +37,6 @@
 #include "windef.h"
 #include "winbase.h"
 #include "wine/winbase16.h"
-#include "wine/port.h"
 #include "drive.h"
 #include "file.h"
 #include "heap.h"
@@ -491,7 +491,7 @@
  *
  * Fill a file information from a struct stat.
  */
-static void FILE_FillInfo( struct stat *st, BY_HANDLE_FILE_INFORMATION *info )
+static void FILE_FillInfo( struct stat64 *st, BY_HANDLE_FILE_INFORMATION *info )
 {
     if (S_ISDIR(st->st_mode))
         info->dwFileAttributes = FILE_ATTRIBUTE_DIRECTORY;
@@ -506,7 +506,11 @@
 
     info->dwVolumeSerialNumber = 0;  /* FIXME */
     info->nFileSizeHigh = 0;
-    info->nFileSizeLow  = S_ISDIR(st->st_mode) ? 0 : st->st_size;
+    info->nFileSizeLow  = 0;
+    if (!S_ISDIR(st->st_mode)) {
+	info->nFileSizeHigh = st->st_size >> 32;
+	info->nFileSizeLow  = st->st_size & 0xffffffff;
+    }
     info->nNumberOfLinks = st->st_nlink;
     info->nFileIndexHigh = 0;
     info->nFileIndexLow  = st->st_ino;
@@ -520,9 +524,9 @@
  */
 BOOL FILE_Stat( LPCSTR unixName, BY_HANDLE_FILE_INFORMATION *info )
 {
-    struct stat st;
+    struct stat64 st;
 
-    if (lstat( unixName, &st ) == -1)
+    if (lstat64( unixName, &st ) == -1)
     {
         FILE_SetDosError();
         return FALSE;
@@ -532,7 +536,7 @@
     {
         /* do a "real" stat to find out
 	   about the type of the symlink destination */
-        if (stat( unixName, &st ) == -1)
+        if (stat64( unixName, &st ) == -1)
         {
             FILE_SetDosError();
             return FALSE;
@@ -1644,17 +1652,8 @@
 {
     DWORD ret = 0xffffffff;
 
-    if (highword &&
-        ((distance >= 0 && *highword != 0) || (distance < 0 && *highword != -1)))
-    {
-        FIXME("64-bit offsets not supported yet\n"
-              "SetFilePointer(%08x,%08lx,%08lx,%08lx)\n",
-              hFile,distance,*highword,method);
-        SetLastError( ERROR_INVALID_PARAMETER );
-        return ret;
-    }
-    TRACE("handle %d offset %ld origin %ld\n",
-          hFile, distance, method );
+    TRACE("handle %d offset %ld high %ld origin %ld\n",
+          hFile, distance, highword?*highword:0, method );
 
     SERVER_START_REQ( set_file_pointer )
     {
@@ -2015,7 +2015,10 @@
 BOOL WINAPI MoveFileA( LPCSTR fn1, LPCSTR fn2 )
 {
     DOS_FULL_NAME full_name1, full_name2;
-    struct stat fstat;
+    /* Even though we do not need the size, stat will fail for large files, 
+     * so we need to use stat64 here. */
+    struct stat64 fstat;
+
 
     TRACE("(%s,%s)\n", fn1, fn2 );
 
@@ -2035,7 +2038,7 @@
     }
       else return TRUE;
     else /*copy */ {
-      if (stat(  full_name1.long_name, &fstat ))
+      if (stat64(  full_name1.long_name, &fstat ))
 	{
 	  WARN("Invalid source file %s\n",
 			full_name1.long_name);
Index: graphics/x11drv/xfont.c
===================================================================
RCS file: /home/wine/wine/graphics/x11drv/xfont.c,v
retrieving revision 1.72
diff -u -r1.72 xfont.c
--- graphics/x11drv/xfont.c	2001/05/11 00:17:47	1.72
+++ graphics/x11drv/xfont.c	2001/05/11 10:11:42
@@ -19,10 +19,8 @@
 #include <string.h>
 #include <unistd.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <fcntl.h>
 #include <math.h>
-#include <assert.h>
 
 #include "windef.h"
 #include "wingdi.h"
Index: include/acconfig.h
===================================================================
RCS file: /home/wine/wine/include/acconfig.h,v
retrieving revision 1.37
diff -u -r1.37 acconfig.h
--- include/acconfig.h	2001/04/27 18:02:47	1.37
+++ include/acconfig.h	2001/05/11 10:11:43
@@ -122,3 +125,9 @@
 
 /* Define if we have CUPS */
 #undef HAVE_CUPS
+
+/* Define if we have 64 bit file offsets */
+#undef HAVE_OFF64_T
+
+/* Define if we have struct stat64 */
+#undef HAVE_STRUCT_STAT64
Index: include/wine/port.h
===================================================================
RCS file: /home/wine/wine/include/wine/port.h,v
retrieving revision 1.10
diff -u -r1.10 port.h
--- include/wine/port.h	2001/01/11 00:54:22	1.10
+++ include/wine/port.h	2001/05/11 10:11:56
@@ -6,9 +6,10 @@
 #ifndef __WINE_WINE_PORT_H
 #define __WINE_WINE_PORT_H
 
+#define _LARGEFILE64_SOURCE	/* for glibc 64 bit file functions */
+
 #include "config.h"
 #include "winnt.h"
-
 #include <sys/types.h>
 #include <sys/time.h>
 #include <sys/stat.h>
@@ -130,6 +131,54 @@
 #ifndef S_ISLNK
 #define S_ISLNK(mod) (0)
 #endif /* S_ISLNK */
+
+#ifndef HAVE_OFF64_T
+# if SIZEOF_LONG_LONG > 0 
+typedef long long off64_t;
+# else
+typedef long off64_t;
+# endif
+#endif
+
+#ifndef HAVE_STRUCT_STAT64
+/* This does not convert all struct members to 64bit, only size. */
+struct stat64 {
+    dev_t         st_dev;      /* device */
+    ino_t         st_ino;      /* inode */
+    mode_t        st_mode;     /* protection */
+    nlink_t       st_nlink;    /* number of hard links */
+    uid_t         st_uid;      /* user ID of owner */
+    gid_t         st_gid;      /* group ID of owner */
+    dev_t         st_rdev;     /* device type (if inode device) */
+    off64_t       st_size;     /* total size, in bytes */
+    unsigned long st_blksize;  /* blocksize for filesystem I/O */
+    unsigned long st_blocks;   /* number of blocks allocated */
+    time_t        st_atime;    /* time of last access */
+    time_t        st_mtime;    /* time of last modification */
+    time_t        st_ctime;    /* time of last change */
+};
+#endif
+
+#ifndef HAVE_LSEEK64
+extern off64_t lseek64(int fildes, off64_t offset, int whence);
+#endif
+
+#ifndef HAVE_STAT64
+extern int stat64(const char *file_name, struct stat64 *buf);
+#endif
+
+#ifndef HAVE_LSTAT64
+extern int lstat64(const char *file_name, struct stat64 *buf);
+#endif
+
+#ifndef HAVE_FSTAT64
+extern int fstat64(int fd, struct stat64 *buf);
+#endif
+
+#ifndef HAVE_FTRUNCATE64
+extern int ftruncate64(int fd, off64_t offset);
+#endif
+
 
 extern void *wine_dlopen( const char *filename, int flag, char *error, int errorsize );
 extern void *wine_dlsym( void *handle, const char *symbol, char *error, int errorsize );
Index: library/loader.c
===================================================================
RCS file: /home/wine/wine/library/loader.c,v
retrieving revision 1.8
diff -u -r1.8 loader.c
--- library/loader.c	2001/02/13 20:23:45	1.8
+++ library/loader.c	2001/05/11 10:11:57
@@ -5,6 +5,7 @@
  */
 
 #include "config.h"
+#include "wine/port.h"
 
 #include <assert.h>
 #include <ctype.h>
@@ -18,7 +19,6 @@
 
 #include "winnt.h"
 #include "wine/library.h"
-#include "wine/port.h"
 
 #define MAX_DLLS 100
 
Index: library/port.c
===================================================================
RCS file: /home/wine/wine/library/port.c,v
retrieving revision 1.10
diff -u -r1.10 port.c
--- library/port.c	2001/02/20 01:59:27	1.10
+++ library/port.c	2001/05/11 10:11:58
@@ -5,6 +5,7 @@
  */
 
 #include "config.h"
+#include "wine/port.h"
 
 #ifdef __BEOS__
 #include <be/kernel/fs_info.h>
@@ -43,7 +44,6 @@
 # include <dlfcn.h>
 #endif
 
-#include "wine/port.h"
 
 /***********************************************************************
  *		usleep
@@ -389,7 +389,84 @@
 }
 #endif /* HAVE_LSTAT */
 
+static void
+_convert_stat_stat64(struct stat64 *stto,struct stat *stfrom) {
+#define X(x) stto->st_##x = stfrom->st_##x;
+    X(dev);X(ino);X(mode);X(nlink);X(uid);X(gid);X(rdev);X(blksize);
+    X(blocks);X(atime);X(mtime);X(ctime);
+#undef X
+    stto->st_size = (off64_t)stfrom->st_size;
+}
+
+/***********************************************************************
+ *		stat64
+ */
+#ifndef HAVE_STAT64
+int stat64(const char *file_name, struct stat64 *buf)
+{
+    struct stat stbuf;
+    int res = stat(file_name,&stbuf);
+    _convert_stat_stat64(buf,&stbuf);
+    return res;
+}
+#endif /* HAVE_STAT64 */
+
+/***********************************************************************
+ *		lstat64
+ */
+#ifndef HAVE_LSTAT64
+int lstat64(const char *file_name, struct stat64 *buf)
+{
+    struct stat stbuf;
+    int res = lstat(file_name,&stbuf);
+    _convert_stat_stat64(buf,&stbuf);
+    return res;
+}
+#endif /* HAVE_LSTAT64 */
+
+/***********************************************************************
+ *		fstat64
+ */
+#ifndef HAVE_FSTAT64
+int fstat64(int fd, struct stat64 *buf)
+{
+    struct stat stbuf;
+    int res = fstat(fd,&stbuf);
+    _convert_stat_stat64(buf,&stbuf);
+    return res;
+}
+#endif /* HAVE_FSTAT */
+
+/***********************************************************************
+ *		lseek64
+ */
+#ifndef HAVE_LSEEK64
+off64_t lseek64(int fd, off64_t where, int whence)
+{
+    off_t res;
+    if ((where >= 0x8000000LL)  || ( where <= -0x7fffffffLL)) {
+	errno = EFBIG; /* FIXME: hack */
+	return -1;
+    }
 
+    res = lseek(fd,(off_t)where,whence);
+    return (off64_t)res;
+}
+#endif /* HAVE_LSEEK64 */
+
+/***********************************************************************
+ *		ftruncate64
+ */
+#ifndef HAVE_FTRUNCATE64
+int ftruncate64(int fd, off64_t where)
+{
+    if ((where >= 0x8000000LL)  || ( where <= -0x7fffffffLL)) {
+	errno = EFBIG; /* FIXME: hack */
+	return -1;
+    }
+    return ftruncate(fd,(off_t)where);
+}
+#endif /* HAVE_LSEEK64 */
 /***********************************************************************
  *		getrlimit
  */
Index: libtest/Makefile.in
===================================================================
RCS file: /home/wine/wine/libtest/Makefile.in,v
retrieving revision 1.22
diff -u -r1.22 Makefile.in
--- libtest/Makefile.in	2000/12/06 00:05:15	1.22
+++ libtest/Makefile.in	2001/05/11 10:11:58
@@ -5,7 +5,7 @@
 SRCDIR     = @srcdir@
 VPATH      = @srcdir@
 MODULE     = none
-PROGRAMS   = expand hello hello2 hello3 hello4 hello5 new rolex vartest volinfo
+PROGRAMS   = expand hello hello2 hello3 hello4 hello5 new rolex vartest volinfo lfs
 ALL_LIBS   = $(LIBWINE) $(LIBS)
 
 C_SRCS = \
@@ -15,6 +15,7 @@
 	hello3.c \
 	hello4.c \
 	hello5.c \
+	lfs.c \
 	new.c \
 	rolex.c \
 	vartest.c \
@@ -27,6 +28,7 @@
 	hello3.spec \
 	hello4.spec \
 	hello5.spec \
+	lfs.spec \
 	new.spec \
 	rolex.spec \
 	vartest.spec \
@@ -43,6 +45,11 @@
 	$(LDPATH) $(WINEBUILD) @DLLFLAGS@ -L $(DLLDIR) -sym expand.o -o expand.spec.c -spec expand.spec
 expand.so: expand.o expand.spec.o
 	$(LDSHARED) $(LDDLLFLAGS) -o expand.so $+ $(ALL_LIBS)
+
+lfs.spec.c: lfs.spec lfs.o $(WINEBUILD)
+	$(LDPATH) $(WINEBUILD) @DLLFLAGS@ -L $(DLLDIR) -sym lfs.o -o lfs.spec.c -spec lfs.spec
+lfs.so: lfs.o lfs.spec.o
+	$(LDSHARED) $(LDDLLFLAGS) -o lfs.so $+ $(ALL_LIBS)
 
 hello.spec.c: hello.spec hello.o $(WINEBUILD)
 	$(LDPATH) $(WINEBUILD) @DLLFLAGS@ -L $(DLLDIR) -sym hello.o -o hello.spec.c -spec hello.spec
Index: loader/dos/dosmod.c
===================================================================
RCS file: /home/wine/wine/loader/dos/dosmod.c,v
retrieving revision 1.10
diff -u -r1.10 dosmod.c
--- loader/dos/dosmod.c	2000/12/01 23:53:47	1.10
+++ loader/dos/dosmod.c	2001/05/11 10:12:01
@@ -21,7 +21,6 @@
 #include <unistd.h>
 #include <fcntl.h>
 #include <signal.h>
-#include <sys/stat.h>
 #ifdef HAVE_SYS_MMAN_H
 # include <sys/mman.h>
 #endif
Index: loader/ne/resource.c
===================================================================
RCS file: /home/wine/wine/loader/ne/resource.c,v
retrieving revision 1.25
diff -u -r1.25 resource.c
--- loader/ne/resource.c	2001/01/15 20:13:44	1.25
+++ loader/ne/resource.c	2001/05/11 10:12:02
@@ -10,7 +10,6 @@
 #include <stdlib.h>
 #include <string.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <fcntl.h>
 #include <unistd.h>
 #include "windef.h"
Index: loader/ne/segment.c
===================================================================
RCS file: /home/wine/wine/loader/ne/segment.c,v
retrieving revision 1.39
diff -u -r1.39 segment.c
--- loader/ne/segment.c	2001/01/15 22:20:50	1.39
+++ loader/ne/segment.c	2001/05/11 10:12:04
@@ -9,7 +9,6 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <fcntl.h>
 #include <unistd.h>
 #include <ctype.h>
Index: msdos/int13.c
===================================================================
RCS file: /home/wine/wine/msdos/int13.c,v
retrieving revision 1.8
diff -u -r1.8 int13.c
--- msdos/int13.c	2000/12/12 00:44:43	1.8
+++ msdos/int13.c	2001/05/11 10:12:10
@@ -5,11 +5,10 @@
 #include <stdlib.h>
 #include <unistd.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <sys/ioctl.h>
 #include <fcntl.h>
 #ifdef linux
-#include <linux/fd.h>
+# include <linux/fd.h>
 #endif
 #include "miscemu.h"
 /* #define DEBUG_INT */
Index: msdos/int21.c
===================================================================
RCS file: /home/wine/wine/msdos/int21.c,v
retrieving revision 1.61
diff -u -r1.61 int21.c
--- msdos/int21.c	2001/05/09 17:31:35	1.61
+++ msdos/int21.c	2001/05/11 10:12:16
@@ -12,7 +12,6 @@
 # include <sys/file.h>
 #endif
 #include <string.h>
-#include <sys/stat.h>
 #include <sys/time.h>
 #include <sys/types.h>
 #include <unistd.h>
Index: server/console.c
===================================================================
RCS file: /home/wine/wine/server/console.c,v
retrieving revision 1.26
diff -u -r1.26 console.c
--- server/console.c	2001/03/22 19:35:27	1.26
+++ server/console.c	2001/05/11 10:12:31
@@ -15,10 +15,6 @@
 #include <string.h>
 #include <stdio.h>
 #include <stdlib.h>
-#ifdef HAVE_SYS_ERRNO_H
-#include <sys/errno.h>
-#endif
-#include <sys/stat.h>
 #include <sys/time.h>
 #include <sys/types.h>
 #include <time.h>
Index: server/file.c
===================================================================
RCS file: /home/wine/wine/server/file.c,v
retrieving revision 1.39
diff -u -r1.39 file.c
--- server/file.c	2001/04/13 22:38:39	1.39
+++ server/file.c	2001/05/11 10:12:32
@@ -5,6 +5,7 @@
  */
 
 #include "config.h"
+#include "wine/port.h"
 
 #include <assert.h>
 #include <fcntl.h>
@@ -150,9 +151,12 @@
     case GENERIC_WRITE: flags |= O_WRONLY; break;
     case GENERIC_READ|GENERIC_WRITE: flags |= O_RDWR; break;
     }
+#ifndef O_LARGEFILE
+# define O_LARGEFILE 0
+#endif
 
     /* FIXME: should set error to STATUS_OBJECT_NAME_COLLISION if file existed before */
-    if ((fd = open( name, flags | O_NONBLOCK,
+    if ((fd = open( name, flags | O_NONBLOCK | O_LARGEFILE,
                     (attrs & FILE_ATTRIBUTE_READONLY) ? 0444 : 0666 )) == -1)
         goto file_error;
     /* refuse to open a directory */
@@ -193,9 +197,8 @@
     char *name;
     int fd;
 
-    do
-    {
-        if (!(name = tmpnam(NULL)))
+    do {
+	if (!(name = tmpnam(NULL)))
         {
             set_error( STATUS_TOO_MANY_OPENED_FILES );
             return -1;
@@ -258,11 +261,11 @@
 
 static int file_get_info( struct object *obj, struct get_file_info_request *req )
 {
-    struct stat st;
+    struct stat64 st;
     struct file *file = (struct file *)obj;
     assert( obj->ops == &file_ops );
 
-    if (fstat( file->obj.fd, &st ) == -1)
+    if (fstat64( file->obj.fd, &st ) == -1)
     {
         file_set_error();
         return 0;
@@ -275,8 +278,13 @@
     if (!(st.st_mode & S_IWUSR)) req->attr |= FILE_ATTRIBUTE_READONLY;
     req->access_time = st.st_atime;
     req->write_time  = st.st_mtime;
-    req->size_high   = 0;
-    req->size_low    = S_ISDIR(st.st_mode) ? 0 : st.st_size;
+    if (S_ISDIR(st.st_mode)) {
+	req->size_high = 0;
+	req->size_low  = 0;
+    } else {
+	req->size_high   = st.st_size >> 32;
+	req->size_low    = st.st_size & 0xffffffff;
+    }
     req->links       = st.st_nlink;
     req->index_high  = st.st_dev;
     req->index_low   = st.st_ino;
@@ -331,21 +339,15 @@
     return (struct file *)get_handle_obj( process, handle, access, &file_ops );
 }
 
-static int set_file_pointer( handle_t handle, int *low, int *high, int whence )
+static int set_file_pointer( handle_t handle, unsigned int *low, int *high, int whence )
 {
     struct file *file;
-    int result;
-
-    if ((*low >= 0 && *high != 0) || (*low < 0 && *high != -1))
-    {
-        fprintf( stderr, "set_file_pointer: offset > 2Gb not supported yet\n" );
-        set_error( STATUS_INVALID_PARAMETER );
-        return 0;
-    }
+    off64_t result,xto;
 
+    xto = *low+((off64_t)*high<<32);
     if (!(file = get_file_obj( current->process, handle, 0 )))
         return 0;
-    if ((result = lseek( file->obj.fd, *low, whence )) == -1)
+    if ((result = lseek64(file->obj.fd,xto,whence))==-1)
     {
         /* Check for seek before start of file */
 
@@ -358,7 +360,8 @@
         release_object( file );
         return 0;
     }
-    *low = result;
+    *low  = result & 0xffffffff;
+    *high = result >> 32;
     release_object( file );
     return 1;
 }
@@ -366,12 +369,12 @@
 static int truncate_file( handle_t handle )
 {
     struct file *file;
-    int result;
+    off64_t result;
 
     if (!(file = get_file_obj( current->process, handle, GENERIC_WRITE )))
         return 0;
-    if (((result = lseek( file->obj.fd, 0, SEEK_CUR )) == -1) ||
-        (ftruncate( file->obj.fd, result ) == -1))
+    if (((result = lseek64( file->obj.fd, 0, SEEK_CUR )) == -1) ||
+        (ftruncate64( file->obj.fd, result ) == -1))
     {
         file_set_error();
         release_object( file );
@@ -384,20 +387,16 @@
 /* try to grow the file to the specified size */
 int grow_file( struct file *file, int size_high, int size_low )
 {
-    struct stat st;
+    struct stat64 st;
+    off64_t	size = size_low + (((off64_t)size_high)<<32);
 
-    if (size_high)
-    {
-        set_error( STATUS_INVALID_PARAMETER );
-        return 0;
-    }
-    if (fstat( file->obj.fd, &st ) == -1)
+    if (fstat64( file->obj.fd, &st ) == -1)
     {
         file_set_error();
         return 0;
     }
-    if (st.st_size >= size_low) return 1;  /* already large enough */
-    if (ftruncate( file->obj.fd, size_low ) != -1) return 1;
+    if (st.st_size >= size) return 1;  /* already large enough */
+    if (ftruncate64( file->obj.fd, size ) != -1) return 1;
     file_set_error();
     return 0;
 }
Index: server/pipe.c
===================================================================
RCS file: /home/wine/wine/server/pipe.c,v
retrieving revision 1.17
diff -u -r1.17 pipe.c
--- server/pipe.c	2001/01/05 04:08:08	1.17
+++ server/pipe.c	2001/05/11 10:12:33
@@ -14,7 +14,6 @@
 #ifdef HAVE_SYS_ERRNO_H
 #include <sys/errno.h>
 #endif
-#include <sys/stat.h>
 #include <sys/time.h>
 #include <sys/types.h>
 #include <time.h>
Index: server/serial.c
===================================================================
RCS file: /home/wine/wine/server/serial.c,v
retrieving revision 1.9
diff -u -r1.9 serial.c
--- server/serial.c	2001/03/22 20:09:34	1.9
+++ server/serial.c	2001/05/11 10:12:33
@@ -20,7 +20,6 @@
 #ifdef HAVE_SYS_ERRNO_H
 #include <sys/errno.h>
 #endif
-#include <sys/stat.h>
 #include <sys/time.h>
 #include <sys/types.h>
 #include <time.h>
Index: server/sock.c
===================================================================
RCS file: /home/wine/wine/server/sock.c,v
retrieving revision 1.17
diff -u -r1.17 sock.c
--- server/sock.c	2001/01/05 04:08:08	1.17
+++ server/sock.c	2001/05/11 10:12:34
@@ -18,7 +18,6 @@
 #ifdef HAVE_SYS_ERRNO_H
 # include <sys/errno.h>
 #endif
-#include <sys/stat.h>
 #include <sys/time.h>
 #include <sys/types.h>
 #ifdef HAVE_SYS_SOCKET_H
Index: win32/device.c
===================================================================
RCS file: /home/wine/wine/win32/device.c,v
retrieving revision 1.48
diff -u -r1.48 device.c
--- win32/device.c	2001/02/28 05:31:04	1.48
+++ win32/device.c	2001/05/11 10:12:41
@@ -9,16 +9,9 @@
 
 #include "config.h"
 
-#include <errno.h>
-#include <assert.h>
 #include <stdlib.h>
 #include <unistd.h>
 #include <sys/types.h>
-#include <sys/stat.h>
-#ifdef HAVE_SYS_MMAN_H
-#include <sys/mman.h>
-#endif
-#include <fcntl.h>
 #include <string.h>
 #include <stdarg.h>
 #include <time.h>
Index: win32/file.c
===================================================================
RCS file: /home/wine/wine/win32/file.c,v
retrieving revision 1.25
diff -u -r1.25 file.c
--- win32/file.c	2001/04/27 18:03:51	1.25
+++ win32/file.c	2001/05/11 10:12:43
@@ -5,6 +5,7 @@
  */
 
 #include "config.h"
+#include "wine/port.h"
 
 #include <errno.h>
 #ifdef HAVE_SYS_ERRNO_H
@@ -56,7 +57,7 @@
  */
 BOOL WINAPI SetFileAttributesA(LPCSTR lpFileName, DWORD attributes)
 {
-    struct stat buf;
+    struct stat64 buf;
     DOS_FULL_NAME full_name;
 
     if (!DOSFS_GetFullName( lpFileName, TRUE, &full_name ))
@@ -69,7 +70,7 @@
         FIXME("(%s):%lx illegal combination with FILE_ATTRIBUTE_NORMAL.\n",
 	      lpFileName,attributes);
     }
-    if(stat(full_name.long_name,&buf)==-1)
+    if(stat64(full_name.long_name,&buf)==-1)
     {
         FILE_SetDosError();
         return FALSE;
Index: windows/clipboard.c
===================================================================
RCS file: /home/wine/wine/windows/clipboard.c,v
retrieving revision 1.37
diff -u -r1.37 clipboard.c
--- windows/clipboard.c	2001/05/09 17:31:36	1.37
+++ windows/clipboard.c	2001/05/11 10:12:46
@@ -19,7 +19,6 @@
 
 #include <stdlib.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <fcntl.h>
 #include <unistd.h>
 #include <string.h>
--- libtest/lfs.spec Apr 12 20:40:09 2001
+++ libtest/lfs.spec	Tue May  8 22:40:26 2001
@@ -0,0 +1,6 @@
+name	lfs
+mode	guiexe
+type	win32
+init	WinMain
+import	kernel32.dll
+import	ntdll.dll
--- libtest/lfs.c Apr 12 20:40:09 2001
+++ libtest/lfs.c	Fri May 11 11:09:10 2001
@@ -0,0 +1,48 @@
+/*
+ * This example demonstrates 64 bit file handling.
+ */
+#include <stdio.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <sys/time.h>
+#include "winbase.h"
+
+int PASCAL WinMain (HINSTANCE inst, HINSTANCE prev, LPSTR cmdline, int show)
+{
+	HANDLE			hf;
+	DWORD			ret, highoff, written;
+
+	hf = CreateFile("hallo.test",GENERIC_READ|GENERIC_WRITE,0,NULL,CREATE_NEW,0,0);
+	if (hf == INVALID_HANDLE_VALUE) {
+	    fprintf(stderr,"CF failed with %ld\n",GetLastError());
+	    return 0;
+	}
+
+	highoff=1;
+	if (-1==SetFilePointer(hf,0,&highoff,SEEK_SET)) {
+	    fprintf(stderr,"SFP failed with %ld\n",GetLastError());
+	    unlink("hallo.test");
+	    return 0;
+	}
+	written=0;
+	if (!WriteFile(hf,".",1,&written,NULL)) {
+	    fprintf(stderr,"WF failed with %ld\n",GetLastError());
+	    unlink("hallo.test");
+	    return 0;
+	}
+	fprintf(stderr,"It should now show a 4 GB file here:\n");
+	system("ls -l hallo.test");
+
+	highoff = 0;
+	SetLastError(0);
+	ret = GetFileSize(hf,&highoff);
+	if ((ret == -1)&&GetLastError()) {
+	    fprintf(stderr,"GFS failed with %ld\n",GetLastError());
+	    unlink("hallo.test");
+	    return 0;
+	}
+	CloseHandle(hf);
+	fprintf(stderr,"file size is %ld.%ld (%Ld)\n",highoff,ret,(((long long)highoff)<<32)+ret);
+	DeleteFile("hallo.test");
+	return 0;
+}




More information about the wine-patches mailing list