fix file position/size procs to use 64-bit APIs

svn: r7313
This commit is contained in:
Matthew Flatt 2007-09-11 14:30:09 +00:00
parent e4164955da
commit 35c63173d0
4 changed files with 70 additions and 58 deletions

View File

@ -110,6 +110,8 @@
# define USE_ON_EXIT_FOR_ATEXIT
# endif
#define USE_TRANSITIONAL_64_FILE_OPS
# ifndef i386
# define FLUSH_SPARC_REGISTER_WINDOWS
# endif
@ -203,6 +205,10 @@
# define MZ_TCP_LISTEN_IPV6_ONLY_SOCKOPT
#if !defined(__x86_64__)
# define USE_TRANSITIONAL_64_FILE_OPS
#endif
# define FLAGS_ALREADY_SET
#if defined(i386)
@ -1023,6 +1029,10 @@
/* NEED_RESET_STDOUT_BLOCKING enures that file descriptors 1 and 2
are reset to blocking mode before exiting. */
/* USE_TRANSITIONAL_64_FILE_OPS uses fseeko64, lseek64, stat64,
etc. for file operations involving sizes (that can requires
64-bit arithmetic). Use this when off_t is only 32 bits wide. */
/* USE_ULIMIT uses ulimit instead of getdtablesize (Unix). */
/* USE_DYNAMIC_FDSET_SIZE allocates fd_set records based on the

View File

@ -5366,7 +5366,7 @@ static Scheme_Object *file_or_dir_permissions(int argc, Scheme_Object *argv[])
static Scheme_Object *file_size(int argc, Scheme_Object *argv[])
{
char *filename;
unsigned long len = 0;
mzlonglong len = 0;
if (!SCHEME_PATH_STRINGP(argv[0]))
scheme_wrong_type("file-size", SCHEME_PATH_STRING_STR, 0, argc, argv);
@ -5378,17 +5378,16 @@ static Scheme_Object *file_size(int argc, Scheme_Object *argv[])
#ifdef DOS_FILE_SYSTEM
{
mzlonglong filesize;
if (UNC_stat(filename, strlen(filename), NULL, NULL, NULL, &filesize)) {
return scheme_make_integer_value_from_long_long(filesize);
if (UNC_stat(filename, strlen(filename), NULL, NULL, NULL, &len)) {
return scheme_make_integer_value_from_long_long(len);
}
}
#else
{
struct MSC_IZE(stat) buf;
struct MSC_IZE(BIG_OFF_T_IZE(stat)) buf;
while (1) {
if (!MSC_W_IZE(stat)(MSC_WIDE_PATH(filename), &buf))
if (!MSC_W_IZE(BIG_OFF_T_IZE(stat))(MSC_WIDE_PATH(filename), &buf))
break;
else if (errno != EINTR)
goto failed;
@ -5400,7 +5399,7 @@ static Scheme_Object *file_size(int argc, Scheme_Object *argv[])
len = buf.st_size;
}
return scheme_make_integer_value_from_unsigned(len);
return scheme_make_integer_value_from_long_long(len);
failed:
#endif

View File

@ -87,7 +87,6 @@ extern int osk_not_console; /* set by cmd-line flag */
#define mzAssert(x) /* if (!(x)) abort() */
/******************** Generic FILEs ********************/
typedef struct {
@ -4128,26 +4127,25 @@ scheme_file_position(int argc, Scheme_Object *argv[])
scheme_make_provided_string(argv[0], 2, NULL),
scheme_make_provided_string(argv[1], 2, NULL));
if ((argc > 1) && SCHEME_BIGNUMP(argv[1]))
scheme_raise_exn(MZEXN_FAIL_CONTRACT,
"file-position: new position is too large: %s for port: %s",
scheme_make_provided_string(argv[1], 2, NULL),
scheme_make_provided_string(argv[0], 2, NULL));
if (argc > 1) {
long n;
mzlonglong nll;
int whence;
if (SCHEME_INTP(argv[1])) {
n = SCHEME_INT_VAL(argv[1]);
if (SCHEME_EOFP(argv[1])) {
nll = 0;
whence = SEEK_END;
} else if (scheme_get_long_long_val(argv[1], &nll)) {
whence = SEEK_SET;
} else {
n = 0;
whence = SEEK_END;
scheme_raise_exn(MZEXN_FAIL_CONTRACT,
"file-position: new position is too large: %s for port: %s",
scheme_make_provided_string(argv[1], 2, NULL),
scheme_make_provided_string(argv[0], 2, NULL));
return NULL;
}
if (f) {
if (fseek(f, n, whence)) {
if (BIG_OFF_T_IZE(fseeko)(f, nll, whence)) {
scheme_raise_exn(MZEXN_FAIL_FILESYSTEM,
"file-position: position change failed on file (%e)",
errno);
@ -4161,20 +4159,14 @@ scheme_file_position(int argc, Scheme_Object *argv[])
}
# ifdef WINDOWS_FILE_HANDLES
lv = SetFilePointer((HANDLE)fd, n, NULL,
((whence == SEEK_SET) ? FILE_BEGIN : FILE_END));
# else
# ifdef MAC_FILE_HANDLES
{
errno = SetFPos(fd, ((whence == SEEK_SET) ? fsFromStart : fsFromLEOF), n);
if (errno == noErr)
lv = 0;
else
lv = -1;
{
if (!SetFilePointerEx((HANDLE)fd, nll, NULL,
((whence == SEEK_SET) ? FILE_BEGIN : FILE_END)))
lv = -1;
}
# else
lv = lseek(fd, n, whence);
# endif
# else
lv = BIG_OFF_T_IZE(lseek)(fd, nll, whence);
# endif
if (lv < 0) {
@ -4201,6 +4193,16 @@ scheme_file_position(int argc, Scheme_Object *argv[])
}
#endif
} else {
long n;
if (whence == SEEK_SET) {
if (!scheme_get_int_val(argv[1], &n)) {
scheme_raise_out_of_memory(NULL, NULL);
}
} else {
n = 0;
}
if (whence == SEEK_END) {
if (wis)
n = is->u.hot;
@ -4251,64 +4253,59 @@ scheme_file_position(int argc, Scheme_Object *argv[])
return scheme_void;
} else {
long p;
mzlonglong pll;
if (f) {
p = ftell(f);
pll = BIG_OFF_T_IZE(ftello)(f);
#ifdef MZ_FDS
} else if (had_fd) {
# ifdef WINDOWS_FILE_HANDLES
p = SetFilePointer((HANDLE)fd, 0, NULL, FILE_CURRENT);
# else
# ifdef MAC_FILE_HANDLES
{
SInt32 pos;
errno = GetFPos(fd, &pos);
if (errno == noErr)
p = pos;
else
p = -1;
LARGE_INTEGER li;
if (!SetFilePointerEx((HANDLE)fd, 0, &li, FILE_CURRENT))
pll = -1;
else
pll = li;
}
# else
p = lseek(fd, 0, 1);
# endif
# else
pll = BIG_OFF_T_IZE(lseek)(fd, 0, 1);
# endif
if (p < 0) {
if (pll < 0) {
if (SCHEME_INPUT_PORTP(argv[0])) {
p = scheme_tell(argv[0]);
pll = scheme_tell(argv[0]);
} else {
p = scheme_output_tell(argv[0]);
pll = scheme_output_tell(argv[0]);
}
} else {
if (SCHEME_INPUT_PORTP(argv[0])) {
Scheme_Input_Port *ip;
ip = scheme_input_port_record(argv[0]);
p -= ((Scheme_FD *)ip->port_data)->bufcount;
pll -= ((Scheme_FD *)ip->port_data)->bufcount;
} else {
Scheme_Output_Port *op;
op = scheme_output_port_record(argv[0]);
p += ((Scheme_FD *)op->port_data)->bufcount;
pll += ((Scheme_FD *)op->port_data)->bufcount;
}
}
#endif
} else if (wis)
p = is->index;
pll = is->index;
else {
/* u.pos > index implies we previously moved past the end with file-position */
if (is->u.pos > is->index)
p = is->u.pos;
pll = is->u.pos;
else
p = is->index;
pll = is->index;
}
/* Back up for un-gotten & peeked chars: */
if (SCHEME_INPUT_PORTP(argv[0])) {
Scheme_Input_Port *ip;
ip = scheme_input_port_record(argv[0]);
p -= ip->ungotten_count;
p -= pipe_char_count(ip->peeked_read);
pll -= ip->ungotten_count;
pll -= pipe_char_count(ip->peeked_read);
}
return scheme_make_integer(p);
return scheme_make_integer_value_from_long_long(pll);
}
}

View File

@ -2565,6 +2565,12 @@ Scheme_Object *scheme_get_native_arity(Scheme_Object *closure);
/* filesystem utilities */
/*========================================================================*/
#ifdef USE_TRANSITIONAL_64_FILE_OPS
# define BIG_OFF_T_IZE(n) n ## 64
#else
# define BIG_OFF_T_IZE(n) n
#endif
int scheme_is_relative_path(const char *s, long len, int kind);
int scheme_is_complete_path(const char *s, long len, int kind);