Actual POSIX calls to replace ANSI stdio routines.

This commit is contained in:
Ryan C. Gordon 2002-06-02 03:48:56 +00:00
parent b1b5975001
commit 22412b925b
1 changed files with 53 additions and 39 deletions

View File

@ -33,15 +33,15 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <ctype.h>
#include <unistd.h> #include <unistd.h>
#include <ctype.h>
#include <sys/types.h> #include <sys/types.h>
#include <pwd.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/param.h> #include <pwd.h>
#include <dirent.h> #include <dirent.h>
#include <time.h>
#include <errno.h> #include <errno.h>
#include <fcntl.h>
#include <assert.h>
#define __PHYSICSFS_INTERNAL__ #define __PHYSICSFS_INTERNAL__
#include "physfs_internal.h" #include "physfs_internal.h"
@ -351,72 +351,86 @@ int __PHYSFS_platformMkDir(const char *path)
} /* __PHYSFS_platformMkDir */ } /* __PHYSFS_platformMkDir */
static void *doOpen(const char *filename, const char *mode) static void *doOpen(const char *filename, int mode)
{ {
FILE *retval; int fd;
int *retval;
errno = 0; errno = 0;
retval = fopen(filename, mode); fd = open(filename, mode, S_IRUSR | S_IWUSR);
if (retval == NULL) if (fd < 0)
__PHYSFS_setError(strerror(errno)); __PHYSFS_setError(strerror(errno));
retval = (int *) malloc(sizeof (int));
if (retval == NULL)
{
close(fd);
BAIL_MACRO(ERR_OUT_OF_MEMORY, NULL);
} /* if */
*retval = fd;
return((void *) retval); return((void *) retval);
} /* doOpen */ } /* doOpen */
void *__PHYSFS_platformOpenRead(const char *filename) void *__PHYSFS_platformOpenRead(const char *filename)
{ {
return(doOpen(filename, "rb")); return(doOpen(filename, O_RDONLY));
} /* __PHYSFS_platformOpenRead */ } /* __PHYSFS_platformOpenRead */
void *__PHYSFS_platformOpenWrite(const char *filename) void *__PHYSFS_platformOpenWrite(const char *filename)
{ {
return(doOpen(filename, "wb")); return(doOpen(filename, O_WRONLY | O_CREAT | O_TRUNC));
} /* __PHYSFS_platformOpenWrite */ } /* __PHYSFS_platformOpenWrite */
void *__PHYSFS_platformOpenAppend(const char *filename) void *__PHYSFS_platformOpenAppend(const char *filename)
{ {
return(doOpen(filename, "ab")); return(doOpen(filename, O_WRONLY | O_CREAT | O_APPEND));
} /* __PHYSFS_platformOpenAppend */ } /* __PHYSFS_platformOpenAppend */
PHYSFS_sint64 __PHYSFS_platformRead(void *opaque, void *buffer, PHYSFS_sint64 __PHYSFS_platformRead(void *opaque, void *buffer,
PHYSFS_uint32 size, PHYSFS_uint32 count) PHYSFS_uint32 size, PHYSFS_uint32 count)
{ {
FILE *io = (FILE *) opaque; int fd = *((int *) opaque);
int rc = fread(buffer, size, count, io); int max = size * count;
if (rc < count) int rc = read(fd, buffer, max);
{
int err = errno;
BAIL_IF_MACRO(ferror(io), strerror(err), rc);
BAIL_MACRO(ERR_PAST_EOF, rc);
} /* if */
return(rc); BAIL_IF_MACRO(rc == -1, strerror(errno), rc);
assert(rc <= max);
if ((rc < max) && (size > 1))
lseek(fd, -(rc % size), SEEK_CUR); /* rollback to object boundary. */
return(rc / size);
} /* __PHYSFS_platformRead */ } /* __PHYSFS_platformRead */
PHYSFS_sint64 __PHYSFS_platformWrite(void *opaque, const void *buffer, PHYSFS_sint64 __PHYSFS_platformWrite(void *opaque, const void *buffer,
PHYSFS_uint32 size, PHYSFS_uint32 count) PHYSFS_uint32 size, PHYSFS_uint32 count)
{ {
FILE *io = (FILE *) opaque; int fd = *((int *) opaque);
int rc = fwrite((void *) buffer, size, count, io); int max = size * count;
if (rc < count) int rc = write(fd, (void *) buffer, max);
__PHYSFS_setError(strerror(errno));
return(rc); BAIL_IF_MACRO(rc == -1, strerror(errno), rc);
assert(rc <= max);
if ((rc < max) && (size > 1))
lseek(fd, -(rc % size), SEEK_CUR); /* rollback to object boundary. */
return(rc / size);
} /* __PHYSFS_platformWrite */ } /* __PHYSFS_platformWrite */
int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos) int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos)
{ {
FILE *io = (FILE *) opaque; int fd = *((int *) opaque);
/* !!! FIXME: Use llseek where available. */ /* !!! FIXME: Use llseek where available. */
errno = 0; BAIL_IF_MACRO(lseek(fd, (int) pos, SEEK_SET) != 0, strerror(errno), 0);
BAIL_IF_MACRO(fseek(io, pos, SEEK_SET) != 0, strerror(errno), 0);
return(1); return(1);
} /* __PHYSFS_platformSeek */ } /* __PHYSFS_platformSeek */
@ -424,8 +438,8 @@ int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos)
PHYSFS_sint64 __PHYSFS_platformTell(void *opaque) PHYSFS_sint64 __PHYSFS_platformTell(void *opaque)
{ {
FILE *io = (FILE *) opaque; int fd = *((int *) opaque);
PHYSFS_sint64 retval = ftell(io); PHYSFS_sint64 retval = lseek(fd, 0, SEEK_CUR);
BAIL_IF_MACRO(retval == -1, strerror(errno), -1); BAIL_IF_MACRO(retval == -1, strerror(errno), -1);
return(retval); return(retval);
} /* __PHYSFS_platformTell */ } /* __PHYSFS_platformTell */
@ -433,39 +447,39 @@ PHYSFS_sint64 __PHYSFS_platformTell(void *opaque)
PHYSFS_sint64 __PHYSFS_platformFileLength(void *opaque) PHYSFS_sint64 __PHYSFS_platformFileLength(void *opaque)
{ {
FILE *io = (FILE *) opaque; int fd = *((int *) opaque);
struct stat statbuf; struct stat statbuf;
errno = 0; BAIL_IF_MACRO(fstat(fd, &statbuf) == -1, strerror(errno), -1);
BAIL_IF_MACRO(fstat(fileno(io), &statbuf) == -1, strerror(errno), -1);
return((PHYSFS_sint64) statbuf.st_size); return((PHYSFS_sint64) statbuf.st_size);
} /* __PHYSFS_platformFileLength */ } /* __PHYSFS_platformFileLength */
int __PHYSFS_platformEOF(void *opaque) int __PHYSFS_platformEOF(void *opaque)
{ {
return(feof((FILE *) opaque)); PHYSFS_sint64 pos = __PHYSFS_platformTell(opaque);
PHYSFS_sint64 len = __PHYSFS_platformFileLength(opaque);
return(pos >= len);
} /* __PHYSFS_platformEOF */ } /* __PHYSFS_platformEOF */
int __PHYSFS_platformFlush(void *opaque) int __PHYSFS_platformFlush(void *opaque)
{ {
errno = 0; int fd = *((int *) opaque);
BAIL_IF_MACRO(fflush((FILE *) opaque) == EOF, strerror(errno), 0); BAIL_IF_MACRO(fsync(fd) == -1, strerror(errno), 0);
return(1); return(1);
} /* __PHYSFS_platformFlush */ } /* __PHYSFS_platformFlush */
int __PHYSFS_platformClose(void *opaque) int __PHYSFS_platformClose(void *opaque)
{ {
errno = 0; int fd = *((int *) opaque);
BAIL_IF_MACRO(fclose((FILE *) opaque) == EOF, strerror(errno), 0); BAIL_IF_MACRO(close(fd) == -1, strerror(errno), 0);
return(1); return(1);
} /* __PHYSFS_platformClose */ } /* __PHYSFS_platformClose */
int __PHYSFS_platformDelete(const char *path) int __PHYSFS_platformDelete(const char *path)
{ {
errno = 0;
BAIL_IF_MACRO(remove(path) == -1, strerror(errno), 0); BAIL_IF_MACRO(remove(path) == -1, strerror(errno), 0);
return(1); return(1);
} /* __PHYSFS_platformDelete */ } /* __PHYSFS_platformDelete */