Added typedefs and platform-specific i/o.
This commit is contained in:
parent
3b798738f6
commit
f2887cf047
|
@ -70,7 +70,11 @@
|
||||||
"write" functions to get data from a "const" buffer. Added an
|
"write" functions to get data from a "const" buffer. Added an
|
||||||
"extras" dir, which currently contains PhysFS->SDL_RWops glue code.
|
"extras" dir, which currently contains PhysFS->SDL_RWops glue code.
|
||||||
03202002 - Patched platform/win32.c to compile.
|
03202002 - Patched platform/win32.c to compile.
|
||||||
03242002 - Added __PHYSFS_platformInit() and __PHYSFS_platformDeinit().
|
03242002 - Added __PHYSFS_platformInit() and __PHYSFS_platformDeinit(). Win32
|
||||||
|
improvements by Gregory S. Read. Added PHYSFS_[us]int(8|16|32)
|
||||||
|
types...this breaks binary compatibility with previous PhysicsFS
|
||||||
|
releases! Added platform specific i/o functions, so we don't have
|
||||||
|
to rely on stdio anymore.
|
||||||
|
|
||||||
--ryan. (icculus@clutteredmind.org)
|
--ryan. (icculus@clutteredmind.org)
|
||||||
|
|
||||||
|
|
3
Makefile
3
Makefile
|
@ -136,7 +136,8 @@ BINDIR := bin
|
||||||
SRCDIR := .
|
SRCDIR := .
|
||||||
|
|
||||||
CFLAGS += $(use_asm) -I$(SRCDIR) -I/usr/include/readline -D_REENTRANT -fsigned-char -DPLATFORM_UNIX
|
CFLAGS += $(use_asm) -I$(SRCDIR) -I/usr/include/readline -D_REENTRANT -fsigned-char -DPLATFORM_UNIX
|
||||||
CFLAGS += -Wall -Werror -fno-exceptions -fno-rtti -ansi -pedantic
|
CFLAGS += -Wall -Werror -fno-exceptions -fno-rtti -ansi
|
||||||
|
#-pedantic
|
||||||
|
|
||||||
LDFLAGS += -lm
|
LDFLAGS += -lm
|
||||||
|
|
||||||
|
|
|
@ -16,14 +16,14 @@
|
||||||
#define __PHYSICSFS_INTERNAL__
|
#define __PHYSICSFS_INTERNAL__
|
||||||
#include "physfs_internal.h"
|
#include "physfs_internal.h"
|
||||||
|
|
||||||
static int DIR_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 DIR_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
static int DIR_write(FileHandle *handle, const void *buffer,
|
static PHYSFS_sint64 DIR_write(FileHandle *handle, const void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
static int DIR_eof(FileHandle *handle);
|
static int DIR_eof(FileHandle *handle);
|
||||||
static int DIR_tell(FileHandle *handle);
|
static PHYSFS_sint64 DIR_tell(FileHandle *handle);
|
||||||
static int DIR_seek(FileHandle *handle, int offset);
|
static int DIR_seek(FileHandle *handle, PHYSFS_uint64 offset);
|
||||||
static int DIR_fileLength(FileHandle *handle);
|
static PHYSFS_sint64 DIR_fileLength(FileHandle *handle);
|
||||||
static int DIR_fileClose(FileHandle *handle);
|
static int DIR_fileClose(FileHandle *handle);
|
||||||
static int DIR_isArchive(const char *filename, int forWriting);
|
static int DIR_isArchive(const char *filename, int forWriting);
|
||||||
static DirHandle *DIR_openArchive(const char *name, int forWriting);
|
static DirHandle *DIR_openArchive(const char *name, int forWriting);
|
||||||
|
@ -94,8 +94,8 @@ const PHYSFS_ArchiveInfo __PHYSFS_ArchiveInfo_DIR =
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
static int DIR_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 DIR_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
FILE *h = (FILE *) (handle->opaque);
|
FILE *h = (FILE *) (handle->opaque);
|
||||||
size_t retval;
|
size_t retval;
|
||||||
|
@ -109,8 +109,8 @@ static int DIR_read(FileHandle *handle, void *buffer,
|
||||||
} /* DIR_read */
|
} /* DIR_read */
|
||||||
|
|
||||||
|
|
||||||
static int DIR_write(FileHandle *handle, const void *buffer,
|
static PHYSFS_sint64 DIR_write(FileHandle *handle, const void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
FILE *h = (FILE *) (handle->opaque);
|
FILE *h = (FILE *) (handle->opaque);
|
||||||
size_t retval;
|
size_t retval;
|
||||||
|
@ -130,19 +130,19 @@ static int DIR_eof(FileHandle *handle)
|
||||||
} /* DIR_eof */
|
} /* DIR_eof */
|
||||||
|
|
||||||
|
|
||||||
static int DIR_tell(FileHandle *handle)
|
static PHYSFS_sint64 DIR_tell(FileHandle *handle)
|
||||||
{
|
{
|
||||||
return(ftell((FILE *) (handle->opaque)));
|
return(ftell((FILE *) (handle->opaque)));
|
||||||
} /* DIR_tell */
|
} /* DIR_tell */
|
||||||
|
|
||||||
|
|
||||||
static int DIR_seek(FileHandle *handle, int offset)
|
static int DIR_seek(FileHandle *handle, PHYSFS_uint64 offset)
|
||||||
{
|
{
|
||||||
return(fseek((FILE *) (handle->opaque), offset, SEEK_SET) == 0);
|
return(fseek((FILE *) (handle->opaque), offset, SEEK_SET) == 0);
|
||||||
} /* DIR_seek */
|
} /* DIR_seek */
|
||||||
|
|
||||||
|
|
||||||
static int DIR_fileLength(FileHandle *handle)
|
static PHYSFS_sint64 DIR_fileLength(FileHandle *handle)
|
||||||
{
|
{
|
||||||
return(__PHYSFS_platformFileLength((FILE *) (handle->opaque)));
|
return(__PHYSFS_platformFileLength((FILE *) (handle->opaque)));
|
||||||
} /* DIR_fileLength */
|
} /* DIR_fileLength */
|
||||||
|
|
|
@ -39,35 +39,33 @@
|
||||||
#define __PHYSICSFS_INTERNAL__
|
#define __PHYSICSFS_INTERNAL__
|
||||||
#include "physfs_internal.h"
|
#include "physfs_internal.h"
|
||||||
|
|
||||||
#if 0
|
|
||||||
#if (!defined PHYSFS_SUPPORTS_GRP)
|
#if (!defined PHYSFS_SUPPORTS_GRP)
|
||||||
#error PHYSFS_SUPPORTS_GRP must be defined.
|
#error PHYSFS_SUPPORTS_GRP must be defined.
|
||||||
#endif
|
#endif
|
||||||
#endif
|
|
||||||
|
|
||||||
/* !!! FIXME: Using the same file handle for all reads is a RACE CONDITION! */
|
/* !!! FIXME: Using the same file handle for all reads is a RACE CONDITION! */
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
FILE *handle;
|
FILE *handle;
|
||||||
int totalEntries;
|
PHYSFS_uint32 totalEntries;
|
||||||
} GRPinfo;
|
} GRPinfo;
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
int startPos;
|
PHYSFS_uint32 startPos;
|
||||||
int curPos;
|
PHYSFS_uint32 curPos;
|
||||||
int size;
|
PHYSFS_uint32 size;
|
||||||
} GRPfileinfo;
|
} GRPfileinfo;
|
||||||
|
|
||||||
|
|
||||||
static void GRP_dirClose(DirHandle *h);
|
static void GRP_dirClose(DirHandle *h);
|
||||||
static int GRP_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 GRP_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
static int GRP_eof(FileHandle *handle);
|
static int GRP_eof(FileHandle *handle);
|
||||||
static int GRP_tell(FileHandle *handle);
|
static PHYSFS_sint64 GRP_tell(FileHandle *handle);
|
||||||
static int GRP_seek(FileHandle *handle, int offset);
|
static int GRP_seek(FileHandle *handle, PHYSFS_uint64 offset);
|
||||||
static int GRP_fileLength(FileHandle *handle);
|
static PHYSFS_sint64 GRP_fileLength(FileHandle *handle);
|
||||||
static int GRP_fileClose(FileHandle *handle);
|
static int GRP_fileClose(FileHandle *handle);
|
||||||
static int GRP_isArchive(const char *filename, int forWriting);
|
static int GRP_isArchive(const char *filename, int forWriting);
|
||||||
static DirHandle *GRP_openArchive(const char *name, int forWriting);
|
static DirHandle *GRP_openArchive(const char *name, int forWriting);
|
||||||
|
@ -125,13 +123,13 @@ static void GRP_dirClose(DirHandle *h)
|
||||||
} /* GRP_dirClose */
|
} /* GRP_dirClose */
|
||||||
|
|
||||||
|
|
||||||
static int GRP_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 GRP_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
||||||
FILE *fh = (FILE *) (((GRPinfo *) (handle->dirHandle->opaque))->handle);
|
FILE *fh = (FILE *) (((GRPinfo *) (handle->dirHandle->opaque))->handle);
|
||||||
int bytesLeft = (finfo->startPos + finfo->size) - finfo->curPos;
|
PHYSFS_uint32 bytesLeft = (finfo->startPos + finfo->size) - finfo->curPos;
|
||||||
unsigned int objsLeft = bytesLeft / objSize;
|
PHYSFS_uint32 objsLeft = bytesLeft / objSize;
|
||||||
size_t retval = 0;
|
size_t retval = 0;
|
||||||
|
|
||||||
if (objsLeft < objCount)
|
if (objsLeft < objCount)
|
||||||
|
@ -144,9 +142,9 @@ static int GRP_read(FileHandle *handle, void *buffer,
|
||||||
retval = fread(buffer, objSize, objCount, fh);
|
retval = fread(buffer, objSize, objCount, fh);
|
||||||
finfo->curPos += (retval * objSize);
|
finfo->curPos += (retval * objSize);
|
||||||
BAIL_IF_MACRO((retval < (size_t) objCount) && (ferror(fh)),
|
BAIL_IF_MACRO((retval < (size_t) objCount) && (ferror(fh)),
|
||||||
strerror(errno), (int) retval);
|
strerror(errno), (PHYSFS_sint64) retval);
|
||||||
|
|
||||||
return((int) retval);
|
return((PHYSFS_sint64) retval);
|
||||||
} /* GRP_read */
|
} /* GRP_read */
|
||||||
|
|
||||||
|
|
||||||
|
@ -157,14 +155,14 @@ static int GRP_eof(FileHandle *handle)
|
||||||
} /* GRP_eof */
|
} /* GRP_eof */
|
||||||
|
|
||||||
|
|
||||||
static int GRP_tell(FileHandle *handle)
|
static PHYSFS_sint64 GRP_tell(FileHandle *handle)
|
||||||
{
|
{
|
||||||
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
||||||
return(finfo->curPos - finfo->startPos);
|
return(finfo->curPos - finfo->startPos);
|
||||||
} /* GRP_tell */
|
} /* GRP_tell */
|
||||||
|
|
||||||
|
|
||||||
static int GRP_seek(FileHandle *handle, int offset)
|
static int GRP_seek(FileHandle *handle, PHYSFS_uint64 offset)
|
||||||
{
|
{
|
||||||
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
||||||
int newPos = finfo->startPos + offset;
|
int newPos = finfo->startPos + offset;
|
||||||
|
@ -176,7 +174,7 @@ static int GRP_seek(FileHandle *handle, int offset)
|
||||||
} /* GRP_seek */
|
} /* GRP_seek */
|
||||||
|
|
||||||
|
|
||||||
static int GRP_fileLength(FileHandle *handle)
|
static PHYSFS_sint64 GRP_fileLength(FileHandle *handle)
|
||||||
{
|
{
|
||||||
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
GRPfileinfo *finfo = (GRPfileinfo *) (handle->opaque);
|
||||||
return(finfo->size);
|
return(finfo->size);
|
||||||
|
@ -191,14 +189,10 @@ static int GRP_fileClose(FileHandle *handle)
|
||||||
} /* GRP_fileClose */
|
} /* GRP_fileClose */
|
||||||
|
|
||||||
|
|
||||||
static int openGrp(const char *filename, int forWriting, FILE **fh, int *count)
|
static int openGrp(const char *filename, int forWriting, FILE **fh, PHYSFS_sint32 *count)
|
||||||
{
|
{
|
||||||
char buf[12];
|
char buf[12];
|
||||||
|
|
||||||
/* !!! FIXME: Get me platform-independent typedefs! */
|
|
||||||
if (sizeof (int) != 4)
|
|
||||||
assert(0);
|
|
||||||
|
|
||||||
*fh = NULL;
|
*fh = NULL;
|
||||||
BAIL_IF_MACRO(forWriting, ERR_ARC_IS_READ_ONLY, 0);
|
BAIL_IF_MACRO(forWriting, ERR_ARC_IS_READ_ONLY, 0);
|
||||||
|
|
||||||
|
@ -208,10 +202,10 @@ static int openGrp(const char *filename, int forWriting, FILE **fh, int *count)
|
||||||
|
|
||||||
errno = 0;
|
errno = 0;
|
||||||
BAIL_IF_MACRO(fread(buf, 12, 1, *fh) != 1, strerror(errno), 0);
|
BAIL_IF_MACRO(fread(buf, 12, 1, *fh) != 1, strerror(errno), 0);
|
||||||
BAIL_IF_MACRO(strncmp(buf, "KenSilverman", 12) != 0,
|
BAIL_IF_MACRO(memcmp(buf, "KenSilverman", 12) != 0,
|
||||||
ERR_UNSUPPORTED_ARCHIVE, 0);
|
ERR_UNSUPPORTED_ARCHIVE, 0);
|
||||||
|
|
||||||
if (fread(count, 4, 1, *fh) != 1)
|
if (fread(count, sizeof (PHYSFS_sint32), 1, *fh) != 1)
|
||||||
*count = 0;
|
*count = 0;
|
||||||
|
|
||||||
return(1);
|
return(1);
|
||||||
|
@ -312,7 +306,8 @@ static LinkedStringList *GRP_enumerateFiles(DirHandle *h,
|
||||||
} /* GRP_enumerateFiles */
|
} /* GRP_enumerateFiles */
|
||||||
|
|
||||||
|
|
||||||
static int getFileEntry(DirHandle *h, const char *name, int *size)
|
static PHYSFS_sint32 getFileEntry(DirHandle *h, const char *name,
|
||||||
|
PHYSFS_sint32 *size)
|
||||||
{
|
{
|
||||||
char buf[16];
|
char buf[16];
|
||||||
GRPinfo *g = (GRPinfo *) (h->opaque);
|
GRPinfo *g = (GRPinfo *) (h->opaque);
|
||||||
|
@ -338,23 +333,24 @@ static int getFileEntry(DirHandle *h, const char *name, int *size)
|
||||||
|
|
||||||
for (i = 0; i < g->totalEntries; i++)
|
for (i = 0; i < g->totalEntries; i++)
|
||||||
{
|
{
|
||||||
int fsize;
|
PHYSFS_sint32 l = 0;
|
||||||
|
|
||||||
errno = 0;
|
errno = 0;
|
||||||
BAIL_IF_MACRO(fread(buf, 16, 1, fh) != 1, strerror(errno), -1);
|
BAIL_IF_MACRO(fread(buf, 12, 1, fh) != 1, strerror(errno), -1);
|
||||||
|
|
||||||
fsize = *((int *) (buf + 12));
|
errno = 0;
|
||||||
|
BAIL_IF_MACRO(fread(&l, sizeof (l), 1, fh) != 1, strerror(errno), -1);
|
||||||
|
|
||||||
buf[12] = '\0'; /* FILENAME.EXT is all you get. */
|
buf[12] = '\0'; /* FILENAME.EXT is all you get. */
|
||||||
|
|
||||||
if (__PHYSFS_platformStricmp(buf, name) == 0)
|
if (__PHYSFS_platformStricmp(buf, name) == 0)
|
||||||
{
|
{
|
||||||
if (size != NULL)
|
if (size != NULL)
|
||||||
*size = fsize;
|
*size = l;
|
||||||
return(retval);
|
return(retval);
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
retval += fsize;
|
retval += l;
|
||||||
} /* for */
|
} /* for */
|
||||||
|
|
||||||
return(-1); /* not found. */
|
return(-1); /* not found. */
|
||||||
|
@ -383,7 +379,8 @@ static FileHandle *GRP_openRead(DirHandle *h, const char *name)
|
||||||
{
|
{
|
||||||
FileHandle *retval;
|
FileHandle *retval;
|
||||||
GRPfileinfo *finfo;
|
GRPfileinfo *finfo;
|
||||||
int size, offset;
|
PHYSFS_sint32 size;
|
||||||
|
PHYSFS_sint32 offset;
|
||||||
|
|
||||||
offset = getFileEntry(h, name, &size);
|
offset = getFileEntry(h, name, &size);
|
||||||
BAIL_IF_MACRO(offset == -1, ERR_NO_SUCH_FILE, NULL);
|
BAIL_IF_MACRO(offset == -1, ERR_NO_SUCH_FILE, NULL);
|
||||||
|
|
|
@ -58,12 +58,12 @@ typedef struct
|
||||||
#define SYMLINK_RECURSE_COUNT 20
|
#define SYMLINK_RECURSE_COUNT 20
|
||||||
|
|
||||||
|
|
||||||
static int ZIP_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 ZIP_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
static int ZIP_eof(FileHandle *handle);
|
static int ZIP_eof(FileHandle *handle);
|
||||||
static int ZIP_tell(FileHandle *handle);
|
static PHYSFS_sint64 ZIP_tell(FileHandle *handle);
|
||||||
static int ZIP_seek(FileHandle *handle, int offset);
|
static int ZIP_seek(FileHandle *handle, PHYSFS_uint64 offset);
|
||||||
static int ZIP_fileLength(FileHandle *handle);
|
static PHYSFS_sint64 ZIP_fileLength(FileHandle *handle);
|
||||||
static int ZIP_fileClose(FileHandle *handle);
|
static int ZIP_fileClose(FileHandle *handle);
|
||||||
static int ZIP_isArchive(const char *filename, int forWriting);
|
static int ZIP_isArchive(const char *filename, int forWriting);
|
||||||
static char *ZIP_realpath(unzFile fh, unz_file_info *info);
|
static char *ZIP_realpath(unzFile fh, unz_file_info *info);
|
||||||
|
@ -116,12 +116,12 @@ const PHYSFS_ArchiveInfo __PHYSFS_ArchiveInfo_ZIP =
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static int ZIP_read(FileHandle *handle, void *buffer,
|
static PHYSFS_sint64 ZIP_read(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
unzFile fh = ((ZIPfileinfo *) (handle->opaque))->handle;
|
unzFile fh = ((ZIPfileinfo *) (handle->opaque))->handle;
|
||||||
int bytes = objSize * objCount;
|
int bytes = (int) (objSize * objCount); /* !!! FIXME: overflow? */
|
||||||
int rc = unzReadCurrentFile(fh, buffer, bytes);
|
PHYSFS_sint32 rc = unzReadCurrentFile(fh, buffer, bytes);
|
||||||
|
|
||||||
if (rc < bytes)
|
if (rc < bytes)
|
||||||
__PHYSFS_setError(ERR_PAST_EOF);
|
__PHYSFS_setError(ERR_PAST_EOF);
|
||||||
|
@ -140,18 +140,18 @@ static int ZIP_eof(FileHandle *handle)
|
||||||
} /* ZIP_eof */
|
} /* ZIP_eof */
|
||||||
|
|
||||||
|
|
||||||
static int ZIP_tell(FileHandle *handle)
|
static PHYSFS_sint64 ZIP_tell(FileHandle *handle)
|
||||||
{
|
{
|
||||||
return(unztell(((ZIPfileinfo *) (handle->opaque))->handle));
|
return(unztell(((ZIPfileinfo *) (handle->opaque))->handle));
|
||||||
} /* ZIP_tell */
|
} /* ZIP_tell */
|
||||||
|
|
||||||
|
|
||||||
static int ZIP_seek(FileHandle *handle, int offset)
|
static int ZIP_seek(FileHandle *handle, PHYSFS_uint64 offset)
|
||||||
{
|
{
|
||||||
/* this blows. */
|
/* !!! FIXME : this blows. */
|
||||||
unzFile fh = ((ZIPfileinfo *) (handle->opaque))->handle;
|
unzFile fh = ((ZIPfileinfo *) (handle->opaque))->handle;
|
||||||
char *buf = NULL;
|
char *buf = NULL;
|
||||||
int bufsize = 4096 * 2;
|
PHYSFS_uint32 bufsize = 4096 * 2;
|
||||||
|
|
||||||
BAIL_IF_MACRO(unztell(fh) == offset, NULL, 1);
|
BAIL_IF_MACRO(unztell(fh) == offset, NULL, 1);
|
||||||
BAIL_IF_MACRO(ZIP_fileLength(handle) <= offset, ERR_PAST_EOF, 0);
|
BAIL_IF_MACRO(ZIP_fileLength(handle) <= offset, ERR_PAST_EOF, 0);
|
||||||
|
@ -169,8 +169,8 @@ static int ZIP_seek(FileHandle *handle, int offset)
|
||||||
|
|
||||||
while (offset > 0)
|
while (offset > 0)
|
||||||
{
|
{
|
||||||
int chunk = (offset > bufsize) ? bufsize : offset;
|
PHYSFS_uint32 chunk = (offset > bufsize) ? bufsize : offset;
|
||||||
int rc = unzReadCurrentFile(fh, buf, chunk);
|
PHYSFS_sint32 rc = unzReadCurrentFile(fh, buf, chunk);
|
||||||
BAIL_IF_MACRO(rc == 0, ERR_IO_ERROR, 0); /* shouldn't happen. */
|
BAIL_IF_MACRO(rc == 0, ERR_IO_ERROR, 0); /* shouldn't happen. */
|
||||||
BAIL_IF_MACRO(rc == UNZ_ERRNO, ERR_IO_ERROR, 0);
|
BAIL_IF_MACRO(rc == UNZ_ERRNO, ERR_IO_ERROR, 0);
|
||||||
BAIL_IF_MACRO(rc < 0, ERR_COMPRESSION, 0);
|
BAIL_IF_MACRO(rc < 0, ERR_COMPRESSION, 0);
|
||||||
|
@ -182,7 +182,7 @@ static int ZIP_seek(FileHandle *handle, int offset)
|
||||||
} /* ZIP_seek */
|
} /* ZIP_seek */
|
||||||
|
|
||||||
|
|
||||||
static int ZIP_fileLength(FileHandle *handle)
|
static PHYSFS_sint64 ZIP_fileLength(FileHandle *handle)
|
||||||
{
|
{
|
||||||
ZIPfileinfo *finfo = (ZIPfileinfo *) (handle->opaque);
|
ZIPfileinfo *finfo = (ZIPfileinfo *) (handle->opaque);
|
||||||
unz_file_info info;
|
unz_file_info info;
|
||||||
|
|
|
@ -34,7 +34,7 @@ static int physfsrwops_seek(SDL_RWops *rw, int offset, int whence)
|
||||||
|
|
||||||
else if (whence == SEEK_CUR)
|
else if (whence == SEEK_CUR)
|
||||||
{
|
{
|
||||||
int current = PHYSFS_tell(handle);
|
PHYSFS_sint64 current = PHYSFS_tell(handle);
|
||||||
if (current == -1)
|
if (current == -1)
|
||||||
{
|
{
|
||||||
SDL_SetError("Can't find position in file: %s",
|
SDL_SetError("Can't find position in file: %s",
|
||||||
|
@ -42,22 +42,36 @@ static int physfsrwops_seek(SDL_RWops *rw, int offset, int whence)
|
||||||
return(-1);
|
return(-1);
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
if (offset == 0) /* this is a "tell" call. We're done. */
|
pos = (int) current;
|
||||||
return(offset);
|
if ( ((PHYSFS_sint64) pos) != current )
|
||||||
|
{
|
||||||
|
SDL_SetError("Can't fit current file position in an int!");
|
||||||
|
return(-1);
|
||||||
|
} /* if */
|
||||||
|
|
||||||
pos = current + offset;
|
if (offset == 0) /* this is a "tell" call. We're done. */
|
||||||
|
return(pos);
|
||||||
|
|
||||||
|
pos += offset;
|
||||||
} /* else if */
|
} /* else if */
|
||||||
|
|
||||||
else if (whence == SEEK_END)
|
else if (whence == SEEK_END)
|
||||||
{
|
{
|
||||||
int len = PHYSFS_fileLength(handle);
|
PHYSFS_sint64 len = PHYSFS_fileLength(handle);
|
||||||
if (len == -1)
|
if (len == -1)
|
||||||
{
|
{
|
||||||
SDL_SetError("Can't find end of file: %s", PHYSFS_getLastError());
|
SDL_SetError("Can't find end of file: %s", PHYSFS_getLastError());
|
||||||
return(-1);
|
return(-1);
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
pos = len + offset;
|
pos = (int) len;
|
||||||
|
if ( ((PHYSFS_sint64) pos) != len )
|
||||||
|
{
|
||||||
|
SDL_SetError("Can't fit end-of-file position in an int!");
|
||||||
|
return(-1);
|
||||||
|
} /* if */
|
||||||
|
|
||||||
|
pos += offset;
|
||||||
} /* else if */
|
} /* else if */
|
||||||
|
|
||||||
else
|
else
|
||||||
|
@ -66,7 +80,13 @@ static int physfsrwops_seek(SDL_RWops *rw, int offset, int whence)
|
||||||
return(-1);
|
return(-1);
|
||||||
} /* else */
|
} /* else */
|
||||||
|
|
||||||
if (!PHYSFS_seek(handle, pos))
|
if ( pos < 0 )
|
||||||
|
{
|
||||||
|
SDL_SetError("Attempt to seek past start of file.");
|
||||||
|
return(-1);
|
||||||
|
} /* if */
|
||||||
|
|
||||||
|
if (!PHYSFS_seek(handle, (PHYSFS_uint64) pos))
|
||||||
{
|
{
|
||||||
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
||||||
return(-1);
|
return(-1);
|
||||||
|
@ -79,25 +99,25 @@ static int physfsrwops_seek(SDL_RWops *rw, int offset, int whence)
|
||||||
static int physfsrwops_read(SDL_RWops *rw, void *ptr, int size, int maxnum)
|
static int physfsrwops_read(SDL_RWops *rw, void *ptr, int size, int maxnum)
|
||||||
{
|
{
|
||||||
PHYSFS_file *handle = (PHYSFS_file *) rw->hidden.unknown.data1;
|
PHYSFS_file *handle = (PHYSFS_file *) rw->hidden.unknown.data1;
|
||||||
int rc = PHYSFS_read(handle, ptr, size, maxnum);
|
PHYSFS_sint64 rc = PHYSFS_read(handle, ptr, size, maxnum);
|
||||||
if (rc != maxnum)
|
if (rc != maxnum)
|
||||||
{
|
{
|
||||||
if (!PHYSFS_eof(handle)) /* not EOF? Must be an error. */
|
if (!PHYSFS_eof(handle)) /* not EOF? Must be an error. */
|
||||||
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
return(rc);
|
return((int) rc);
|
||||||
} /* physfsrwops_read */
|
} /* physfsrwops_read */
|
||||||
|
|
||||||
|
|
||||||
static int physfsrwops_write(SDL_RWops *rw, const void *ptr, int size, int num)
|
static int physfsrwops_write(SDL_RWops *rw, const void *ptr, int size, int num)
|
||||||
{
|
{
|
||||||
PHYSFS_file *handle = (PHYSFS_file *) rw->hidden.unknown.data1;
|
PHYSFS_file *handle = (PHYSFS_file *) rw->hidden.unknown.data1;
|
||||||
int rc = PHYSFS_write(handle, ptr, size, num);
|
PHYSFS_sint64 rc = PHYSFS_write(handle, ptr, size, num);
|
||||||
if (rc != num)
|
if (rc != num)
|
||||||
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
SDL_SetError("PhysicsFS error: %s", PHYSFS_getLastError());
|
||||||
|
|
||||||
return(rc);
|
return((int) rc);
|
||||||
} /* physfsrwops_write */
|
} /* physfsrwops_write */
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -29,12 +29,6 @@
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if (defined _MSC_VER)
|
|
||||||
#define __EXPORT__ __declspec(dllexport)
|
|
||||||
#else
|
|
||||||
#define __EXPORT__
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Open a platform-independent filename for reading, and make it accessible
|
* Open a platform-independent filename for reading, and make it accessible
|
||||||
* via an SDL_RWops structure. The file will be closed in PhysicsFS when the
|
* via an SDL_RWops structure. The file will be closed in PhysicsFS when the
|
||||||
|
|
16
physfs.c
16
physfs.c
|
@ -803,7 +803,7 @@ char * __PHYSFS_convertToDependent(const char *prepend,
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
return(str);
|
return(str);
|
||||||
} /* __PHYSFS_convertToDependentNotation */
|
} /* __PHYSFS_convertToDependent */
|
||||||
|
|
||||||
|
|
||||||
int __PHYSFS_verifySecurity(DirHandle *h, const char *fname)
|
int __PHYSFS_verifySecurity(DirHandle *h, const char *fname)
|
||||||
|
@ -1231,8 +1231,8 @@ int PHYSFS_close(PHYSFS_file *handle)
|
||||||
} /* PHYSFS_close */
|
} /* PHYSFS_close */
|
||||||
|
|
||||||
|
|
||||||
int PHYSFS_read(PHYSFS_file *handle, void *buffer,
|
PHYSFS_sint64 PHYSFS_read(PHYSFS_file *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
FileHandle *h = (FileHandle *) handle->opaque;
|
FileHandle *h = (FileHandle *) handle->opaque;
|
||||||
assert(h != NULL);
|
assert(h != NULL);
|
||||||
|
@ -1242,8 +1242,8 @@ int PHYSFS_read(PHYSFS_file *handle, void *buffer,
|
||||||
} /* PHYSFS_read */
|
} /* PHYSFS_read */
|
||||||
|
|
||||||
|
|
||||||
int PHYSFS_write(PHYSFS_file *handle, const void *buffer,
|
PHYSFS_sint64 PHYSFS_write(PHYSFS_file *handle, const void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount)
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
|
||||||
{
|
{
|
||||||
FileHandle *h = (FileHandle *) handle->opaque;
|
FileHandle *h = (FileHandle *) handle->opaque;
|
||||||
assert(h != NULL);
|
assert(h != NULL);
|
||||||
|
@ -1263,7 +1263,7 @@ int PHYSFS_eof(PHYSFS_file *handle)
|
||||||
} /* PHYSFS_eof */
|
} /* PHYSFS_eof */
|
||||||
|
|
||||||
|
|
||||||
int PHYSFS_tell(PHYSFS_file *handle)
|
PHYSFS_sint64 PHYSFS_tell(PHYSFS_file *handle)
|
||||||
{
|
{
|
||||||
FileHandle *h = (FileHandle *) handle->opaque;
|
FileHandle *h = (FileHandle *) handle->opaque;
|
||||||
assert(h != NULL);
|
assert(h != NULL);
|
||||||
|
@ -1273,7 +1273,7 @@ int PHYSFS_tell(PHYSFS_file *handle)
|
||||||
} /* PHYSFS_tell */
|
} /* PHYSFS_tell */
|
||||||
|
|
||||||
|
|
||||||
int PHYSFS_seek(PHYSFS_file *handle, int pos)
|
int PHYSFS_seek(PHYSFS_file *handle, PHYSFS_uint64 pos)
|
||||||
{
|
{
|
||||||
FileHandle *h = (FileHandle *) handle->opaque;
|
FileHandle *h = (FileHandle *) handle->opaque;
|
||||||
assert(h != NULL);
|
assert(h != NULL);
|
||||||
|
@ -1284,7 +1284,7 @@ int PHYSFS_seek(PHYSFS_file *handle, int pos)
|
||||||
} /* PHYSFS_seek */
|
} /* PHYSFS_seek */
|
||||||
|
|
||||||
|
|
||||||
int PHYSFS_fileLength(PHYSFS_file *handle)
|
PHYSFS_sint64 PHYSFS_fileLength(PHYSFS_file *handle)
|
||||||
{
|
{
|
||||||
FileHandle *h = (FileHandle *) handle->opaque;
|
FileHandle *h = (FileHandle *) handle->opaque;
|
||||||
assert(h != NULL);
|
assert(h != NULL);
|
||||||
|
|
62
physfs.h
62
physfs.h
|
@ -148,6 +148,42 @@ extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
/* !!! FIXME: This is not universal. */
|
||||||
|
typedef unsigned char PHYSFS_uint8;
|
||||||
|
typedef signed char PHYSFS_sint8;
|
||||||
|
typedef unsigned short PHYSFS_uint16;
|
||||||
|
typedef signed short PHYSFS_sint16;
|
||||||
|
typedef unsigned int PHYSFS_uint32;
|
||||||
|
typedef signed int PHYSFS_sint32;
|
||||||
|
|
||||||
|
#ifdef PHYSFS_NO_64BIT_SUPPORT /* oh well. */
|
||||||
|
typedef PHYSFS_uint32 PHYSFS_uint64;
|
||||||
|
typedef PHYSFS_sint32 PHYSFS_sint64;
|
||||||
|
#else
|
||||||
|
typedef unsigned long long PHYSFS_uint64;
|
||||||
|
typedef signed long long PHYSFS_sint64;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Make sure the types really have the right sizes */
|
||||||
|
#define PHYSFS_COMPILE_TIME_ASSERT(name, x) \
|
||||||
|
typedef int PHYSFS_dummy_ ## name[(x) * 2 - 1]
|
||||||
|
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(uint8, sizeof(PHYSFS_uint8) == 1);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(sint8, sizeof(PHYSFS_sint8) == 1);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(uint16, sizeof(PHYSFS_uint16) == 2);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(sint16, sizeof(PHYSFS_sint16) == 2);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(uint32, sizeof(PHYSFS_uint32) == 4);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(sint32, sizeof(PHYSFS_sint32) == 4);
|
||||||
|
|
||||||
|
#ifndef PHYSFS_NO_64BIT_SUPPORT
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(uint64, sizeof(PHYSFS_uint64) == 8);
|
||||||
|
PHYSFS_COMPILE_TIME_ASSERT(sint64, sizeof(PHYSFS_sint64) == 8);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#undef PHYSFS_COMPILE_TIME_ASSERT
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
typedef struct __PHYSFS_FILE__
|
typedef struct __PHYSFS_FILE__
|
||||||
{
|
{
|
||||||
void *opaque;
|
void *opaque;
|
||||||
|
@ -166,9 +202,9 @@ typedef struct __PHYSFS_ARCHIVEINFO__
|
||||||
|
|
||||||
typedef struct __PHYSFS_VERSION__
|
typedef struct __PHYSFS_VERSION__
|
||||||
{
|
{
|
||||||
int major;
|
PHYSFS_uint8 major;
|
||||||
int minor;
|
PHYSFS_uint8 minor;
|
||||||
int patch;
|
PHYSFS_uint8 patch;
|
||||||
} PHYSFS_Version;
|
} PHYSFS_Version;
|
||||||
|
|
||||||
#define PHYSFS_VER_MAJOR 0
|
#define PHYSFS_VER_MAJOR 0
|
||||||
|
@ -758,9 +794,10 @@ __EXPORT__ int PHYSFS_close(PHYSFS_file *handle);
|
||||||
* the reason this might be < (objCount), as can PHYSFS_eof().
|
* the reason this might be < (objCount), as can PHYSFS_eof().
|
||||||
* -1 if complete failure.
|
* -1 if complete failure.
|
||||||
*/
|
*/
|
||||||
__EXPORT__ int PHYSFS_read(PHYSFS_file *handle, void *buffer,
|
__EXPORT__ PHYSFS_sint64 PHYSFS_read(PHYSFS_file *handle,
|
||||||
unsigned int objSize, unsigned int objCount);
|
void *buffer,
|
||||||
|
PHYSFS_uint32 objSize,
|
||||||
|
PHYSFS_uint32 objCount);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Write data to a PhysicsFS filehandle. The file must be opened for writing.
|
* Write data to a PhysicsFS filehandle. The file must be opened for writing.
|
||||||
|
@ -772,9 +809,10 @@ __EXPORT__ int PHYSFS_read(PHYSFS_file *handle, void *buffer,
|
||||||
* @return number of objects written. PHYSFS_getLastError() can shed light on
|
* @return number of objects written. PHYSFS_getLastError() can shed light on
|
||||||
* the reason this might be < (objCount). -1 if complete failure.
|
* the reason this might be < (objCount). -1 if complete failure.
|
||||||
*/
|
*/
|
||||||
__EXPORT__ int PHYSFS_write(PHYSFS_file *handle, const void *buffer,
|
__EXPORT__ PHYSFS_sint64 PHYSFS_write(PHYSFS_file *handle,
|
||||||
unsigned int objSize, unsigned int objCount);
|
const void *buffer,
|
||||||
|
PHYSFS_uint32 objSize,
|
||||||
|
PHYSFS_uint32 objCount);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Determine if the end of file has been reached in a PhysicsFS filehandle.
|
* Determine if the end of file has been reached in a PhysicsFS filehandle.
|
||||||
|
@ -792,7 +830,7 @@ __EXPORT__ int PHYSFS_eof(PHYSFS_file *handle);
|
||||||
* @return offset in bytes from start of file. -1 if error occurred.
|
* @return offset in bytes from start of file. -1 if error occurred.
|
||||||
* Specifics of the error can be gleaned from PHYSFS_getLastError().
|
* Specifics of the error can be gleaned from PHYSFS_getLastError().
|
||||||
*/
|
*/
|
||||||
__EXPORT__ int PHYSFS_tell(PHYSFS_file *handle);
|
__EXPORT__ PHYSFS_sint64 PHYSFS_tell(PHYSFS_file *handle);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -805,7 +843,7 @@ __EXPORT__ int PHYSFS_tell(PHYSFS_file *handle);
|
||||||
* @return nonzero on success, zero on error. Specifics of the error can be
|
* @return nonzero on success, zero on error. Specifics of the error can be
|
||||||
* gleaned from PHYSFS_getLastError().
|
* gleaned from PHYSFS_getLastError().
|
||||||
*/
|
*/
|
||||||
__EXPORT__ int PHYSFS_seek(PHYSFS_file *handle, int pos);
|
__EXPORT__ int PHYSFS_seek(PHYSFS_file *handle, PHYSFS_uint64 pos);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -819,7 +857,7 @@ __EXPORT__ int PHYSFS_seek(PHYSFS_file *handle, int pos);
|
||||||
* @param handle handle returned from PHYSFS_open*().
|
* @param handle handle returned from PHYSFS_open*().
|
||||||
* @return size in bytes of the file. -1 if can't be determined.
|
* @return size in bytes of the file. -1 if can't be determined.
|
||||||
*/
|
*/
|
||||||
__EXPORT__ int PHYSFS_fileLength(PHYSFS_file *handle);
|
__EXPORT__ PHYSFS_sint64 PHYSFS_fileLength(PHYSFS_file *handle);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,6 +14,12 @@
|
||||||
#error Do not include this header from your applications.
|
#error Do not include this header from your applications.
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include "physfs.h"
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
struct __PHYSFS_DIRHANDLE__;
|
struct __PHYSFS_DIRHANDLE__;
|
||||||
struct __PHYSFS_FILEFUNCTIONS__;
|
struct __PHYSFS_FILEFUNCTIONS__;
|
||||||
|
|
||||||
|
@ -52,8 +58,8 @@ typedef struct __PHYSFS_FILEFUNCTIONS__
|
||||||
* if complete failure.
|
* if complete failure.
|
||||||
* On failure, call __PHYSFS_setError().
|
* On failure, call __PHYSFS_setError().
|
||||||
*/
|
*/
|
||||||
int (*read)(FileHandle *handle, void *buffer,
|
PHYSFS_sint64 (*read)(FileHandle *handle, void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Write more to the file. Archives don't have to implement this.
|
* Write more to the file. Archives don't have to implement this.
|
||||||
|
@ -62,8 +68,8 @@ typedef struct __PHYSFS_FILEFUNCTIONS__
|
||||||
* if complete failure.
|
* if complete failure.
|
||||||
* On failure, call __PHYSFS_setError().
|
* On failure, call __PHYSFS_setError().
|
||||||
*/
|
*/
|
||||||
int (*write)(FileHandle *handle, const void *buffer,
|
PHYSFS_sint64 (*write)(FileHandle *handle, const void *buffer,
|
||||||
unsigned int objSize, unsigned int objCount);
|
PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Returns non-zero if at end of file.
|
* Returns non-zero if at end of file.
|
||||||
|
@ -73,21 +79,21 @@ typedef struct __PHYSFS_FILEFUNCTIONS__
|
||||||
/*
|
/*
|
||||||
* Returns byte offset from start of file.
|
* Returns byte offset from start of file.
|
||||||
*/
|
*/
|
||||||
int (*tell)(FileHandle *handle);
|
PHYSFS_sint64 (*tell)(FileHandle *handle);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Move read/write pointer to byte offset from start of file.
|
* Move read/write pointer to byte offset from start of file.
|
||||||
* Returns non-zero on success, zero on error.
|
* Returns non-zero on success, zero on error.
|
||||||
* On failure, call __PHYSFS_setError().
|
* On failure, call __PHYSFS_setError().
|
||||||
*/
|
*/
|
||||||
int (*seek)(FileHandle *handle, int offset);
|
int (*seek)(FileHandle *handle, PHYSFS_uint64 offset);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Return number of bytes available in the file, or -1 if you
|
* Return number of bytes available in the file, or -1 if you
|
||||||
* aren't able to determine.
|
* aren't able to determine.
|
||||||
* On failure, call __PHYSFS_setError().
|
* On failure, call __PHYSFS_setError().
|
||||||
*/
|
*/
|
||||||
int (*fileLength)(FileHandle *handle);
|
PHYSFS_sint64 (*fileLength)(FileHandle *handle);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Close the file, and free the FileHandle structure (including "opaque").
|
* Close the file, and free the FileHandle structure (including "opaque").
|
||||||
|
@ -340,6 +346,148 @@ int __PHYSFS_platformInit(void);
|
||||||
*/
|
*/
|
||||||
int __PHYSFS_platformDeinit(void);
|
int __PHYSFS_platformDeinit(void);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Open a file for reading. (filename) is in platform-dependent notation. The
|
||||||
|
* file pointer should be positioned on the first byte of the file.
|
||||||
|
*
|
||||||
|
* The return value will be some platform-specific datatype that is opaque to
|
||||||
|
* the caller; it could be a (FILE *) under Unix, or a (HANDLE *) under win32.
|
||||||
|
*
|
||||||
|
* The same file can be opened for read multiple times, and each should have
|
||||||
|
* a unique file handle; this is frequently employed to prevent race
|
||||||
|
* conditions in the archivers.
|
||||||
|
*
|
||||||
|
* Call __PHYSFS_setError() and return (NULL) if the file can't be opened.
|
||||||
|
*/
|
||||||
|
void *__PHYSFS_platformOpenRead(const char *filename);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Open a file for writing. (filename) is in platform-dependent notation. If
|
||||||
|
* the file exists, it should be truncated to zero bytes, and if it doesn't
|
||||||
|
* exist, it should be created as a zero-byte file. The file pointer should
|
||||||
|
* be positioned on the first byte of the file.
|
||||||
|
*
|
||||||
|
* The return value will be some platform-specific datatype that is opaque to
|
||||||
|
* the caller; it could be a (FILE *) under Unix, or a (HANDLE *) under win32,
|
||||||
|
* etc.
|
||||||
|
*
|
||||||
|
* Opening a file for write multiple times has undefined results.
|
||||||
|
*
|
||||||
|
* Call __PHYSFS_setError() and return (NULL) if the file can't be opened.
|
||||||
|
*/
|
||||||
|
void *__PHYSFS_platformOpenWrite(const char *filename);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Open a file for appending. (filename) is in platform-dependent notation. If
|
||||||
|
* the file exists, the file pointer should be place just past the end of the
|
||||||
|
* file, so that the first write will be one byte after the current end of
|
||||||
|
* the file. If the file doesn't exist, it should be created as a zero-byte
|
||||||
|
* file. The file pointer should be positioned on the first byte of the file.
|
||||||
|
*
|
||||||
|
* The return value will be some platform-specific datatype that is opaque to
|
||||||
|
* the caller; it could be a (FILE *) under Unix, or a (HANDLE *) under win32,
|
||||||
|
* etc.
|
||||||
|
*
|
||||||
|
* Opening a file for append multiple times has undefined results.
|
||||||
|
*
|
||||||
|
* Call __PHYSFS_setError() and return (NULL) if the file can't be opened.
|
||||||
|
*/
|
||||||
|
void *__PHYSFS_platformOpenAppend(const char *filename);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Read more data from a platform-specific file handle. (opaque) should be
|
||||||
|
* cast to whatever data type your platform uses. Read a maximum of (count)
|
||||||
|
* objects of (size) 8-bit bytes to the area pointed to by (buffer). If there
|
||||||
|
* isn't enough data available, return the number of full objects read, and
|
||||||
|
* position the file pointer at the start of the first incomplete object.
|
||||||
|
* On success, return (count) and position the file pointer one byte past
|
||||||
|
* the end of the last read object. Return (-1) if there is a catastrophic
|
||||||
|
* error, and call __PHYSFS_setError() to describe the problem; the file
|
||||||
|
* pointer should not move in such a case.
|
||||||
|
*/
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformRead(void *opaque, void *buffer,
|
||||||
|
PHYSFS_uint32 size, PHYSFS_uint32 count);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Write more data to a platform-specific file handle. (opaque) should be
|
||||||
|
* cast to whatever data type your platform uses. Write a maximum of (count)
|
||||||
|
* objects of (size) 8-bit bytes from the area pointed to by (buffer). If
|
||||||
|
* there isn't enough data available, return the number of full objects
|
||||||
|
* written, and position the file pointer at the start of the first
|
||||||
|
* incomplete object. Return (-1) if there is a catastrophic error, and call
|
||||||
|
* __PHYSFS_setError() to describe the problem; the file pointer should not
|
||||||
|
* move in such a case.
|
||||||
|
*/
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformWrite(void *opaque, void *buffer,
|
||||||
|
PHYSFS_uint32 size, PHYSFS_uint32 count);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Set the file pointer to a new position. (opaque) should be cast to
|
||||||
|
* whatever data type your platform uses. (pos) specifies the number
|
||||||
|
* of 8-bit bytes to seek to from the start of the file. Seeking past the
|
||||||
|
* end of the file is an error condition, and you should check for it.
|
||||||
|
*
|
||||||
|
* Not all file types can seek; this is to be expected by the caller.
|
||||||
|
*
|
||||||
|
* On error, call __PHYSFS_setError() and return zero. On success, return
|
||||||
|
* a non-zero value.
|
||||||
|
*/
|
||||||
|
int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Get the file pointer's position, in an 8-bit byte offset from the start of
|
||||||
|
* the file. (opaque) should be cast to whatever data type your platform
|
||||||
|
* uses.
|
||||||
|
*
|
||||||
|
* Not all file types can "tell"; this is to be expected by the caller.
|
||||||
|
*
|
||||||
|
* On error, call __PHYSFS_setError() and return zero. On success, return
|
||||||
|
* a non-zero value.
|
||||||
|
*/
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformTell(void *opaque);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Determine the current size of a file, in 8-bit bytes, from an open file.
|
||||||
|
*
|
||||||
|
* The caller expects that this information may not be available for all
|
||||||
|
* file types on all platforms.
|
||||||
|
*
|
||||||
|
* Return -1 if you can't do it, and call __PHYSFS_setError(). Otherwise,
|
||||||
|
* return the file length in 8-bit bytes.
|
||||||
|
*/
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformFileLength(void *handle);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Determine if a file is at EOF. (opaque) should be cast to whatever data
|
||||||
|
* type your platform uses.
|
||||||
|
*
|
||||||
|
* The caller expects that there was a short read before calling this.
|
||||||
|
*
|
||||||
|
* Return non-zero if EOF, zero if it is _not_ EOF.
|
||||||
|
*/
|
||||||
|
int __PHYSFS_platformEOF(void *opaque);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Flush any pending writes to disk. (opaque) should be cast to whatever data
|
||||||
|
* type your platform uses. Be sure to check for errors; the caller expects
|
||||||
|
* that this function can fail if there was a flushing error, etc.
|
||||||
|
*
|
||||||
|
* Return zero on failure, non-zero on success.
|
||||||
|
*/
|
||||||
|
int __PHYSFS_platformFlush(void *opaque);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Flush and close a file. (opaque) should be cast to whatever data type
|
||||||
|
* your platform uses. Be sure to check for errors when closing; the
|
||||||
|
* caller expects that this function can fail if there was a flushing
|
||||||
|
* error, etc.
|
||||||
|
*
|
||||||
|
* You should clean up all resources associated with (opaque).
|
||||||
|
*
|
||||||
|
* Return zero on failure, non-zero on success.
|
||||||
|
*/
|
||||||
|
int __PHYSFS_platformClose(void *opaque);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Platform implementation of PHYSFS_getCdRomDirs()...
|
* Platform implementation of PHYSFS_getCdRomDirs()...
|
||||||
* See physfs.h. The retval should be freeable via PHYSFS_freeList().
|
* See physfs.h. The retval should be freeable via PHYSFS_freeList().
|
||||||
|
@ -374,7 +522,7 @@ char *__PHYSFS_platformGetUserDir(void);
|
||||||
* arbitrary; the only requirement is that no two threads have the same
|
* arbitrary; the only requirement is that no two threads have the same
|
||||||
* number.
|
* number.
|
||||||
*/
|
*/
|
||||||
int __PHYSFS_platformGetThreadID(void);
|
PHYSFS_uint64 __PHYSFS_platformGetThreadID(void);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This is a pass-through to whatever stricmp() is called on your platform.
|
* This is a pass-through to whatever stricmp() is called on your platform.
|
||||||
|
@ -413,7 +561,8 @@ int __PHYSFS_platformIsDirectory(const char *fname);
|
||||||
* you can make assumptions about the size of strings, etc..
|
* you can make assumptions about the size of strings, etc..
|
||||||
*
|
*
|
||||||
* Platforms that choose not to implement this may just call
|
* Platforms that choose not to implement this may just call
|
||||||
* __PHYSFS_convertToDependent() as a passthrough.
|
* __PHYSFS_convertToDependent() as a passthrough, which may fit the bill
|
||||||
|
* already.
|
||||||
*
|
*
|
||||||
* Be sure to free() the return value when done with it.
|
* Be sure to free() the return value when done with it.
|
||||||
*/
|
*/
|
||||||
|
@ -440,13 +589,6 @@ LinkedStringList *__PHYSFS_platformEnumerateFiles(const char *dirname,
|
||||||
int omitSymLinks);
|
int omitSymLinks);
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Determine the current size of a file, in bytes, from a stdio FILE *.
|
|
||||||
* Return -1 if you can't do it, and call __PHYSFS_setError().
|
|
||||||
*/
|
|
||||||
int __PHYSFS_platformFileLength(FILE *handle);
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Get the current working directory. The return value should be an
|
* Get the current working directory. The return value should be an
|
||||||
* absolute path in platform-dependent notation. The caller will deallocate
|
* absolute path in platform-dependent notation. The caller will deallocate
|
||||||
|
@ -479,7 +621,7 @@ int __PHYSFS_platformMkDir(const char *path);
|
||||||
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C" {
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
150
platform/unix.c
150
platform/unix.c
|
@ -282,9 +282,9 @@ char *__PHYSFS_platformGetUserDir(void)
|
||||||
} /* __PHYSFS_platformGetUserDir */
|
} /* __PHYSFS_platformGetUserDir */
|
||||||
|
|
||||||
|
|
||||||
int __PHYSFS_platformGetThreadID(void)
|
PHYSFS_uint64 __PHYSFS_platformGetThreadID(void)
|
||||||
{
|
{
|
||||||
return((int) pthread_self());
|
return((PHYSFS_uint64) pthread_self());
|
||||||
} /* __PHYSFS_platformGetThreadID */
|
} /* __PHYSFS_platformGetThreadID */
|
||||||
|
|
||||||
|
|
||||||
|
@ -481,15 +481,6 @@ LinkedStringList *__PHYSFS_platformEnumerateFiles(const char *dirname,
|
||||||
} /* __PHYSFS_platformEnumerateFiles */
|
} /* __PHYSFS_platformEnumerateFiles */
|
||||||
|
|
||||||
|
|
||||||
int __PHYSFS_platformFileLength(FILE *handle)
|
|
||||||
{
|
|
||||||
struct stat statbuf;
|
|
||||||
errno = 0;
|
|
||||||
BAIL_IF_MACRO(fstat(fileno(handle), &statbuf) == -1, strerror(errno), -1);
|
|
||||||
return(statbuf.st_size);
|
|
||||||
} /* __PHYSFS_platformFileLength */
|
|
||||||
|
|
||||||
|
|
||||||
char *__PHYSFS_platformCurrentDir(void)
|
char *__PHYSFS_platformCurrentDir(void)
|
||||||
{
|
{
|
||||||
int allocSize = 0;
|
int allocSize = 0;
|
||||||
|
@ -504,20 +495,24 @@ char *__PHYSFS_platformCurrentDir(void)
|
||||||
{
|
{
|
||||||
if (retval != NULL)
|
if (retval != NULL)
|
||||||
free(retval);
|
free(retval);
|
||||||
BAIL_IF_MACRO(1, ERR_OUT_OF_MEMORY, NULL);
|
BAIL_MACRO(ERR_OUT_OF_MEMORY, NULL);
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
||||||
retval = ptr;
|
retval = ptr;
|
||||||
ptr = getcwd(retval, allocSize);
|
ptr = getcwd(retval, allocSize);
|
||||||
} while (ptr == NULL && errno == ERANGE);
|
} while (ptr == NULL && errno == ERANGE);
|
||||||
if(ptr == NULL && errno) {
|
|
||||||
/* getcwd() failed for some reason, for example current
|
if (ptr == NULL && errno)
|
||||||
* directory not existing.
|
{
|
||||||
*/
|
/*
|
||||||
if (retval != NULL)
|
* getcwd() failed for some reason, for example current
|
||||||
free(retval);
|
* directory not existing.
|
||||||
BAIL_IF_MACRO(1, ERR_NO_SUCH_FILE, NULL);
|
*/
|
||||||
}
|
if (retval != NULL)
|
||||||
|
free(retval);
|
||||||
|
BAIL_MACRO(ERR_NO_SUCH_FILE, NULL);
|
||||||
|
} /* if */
|
||||||
|
|
||||||
return(retval);
|
return(retval);
|
||||||
} /* __PHYSFS_platformCurrentDir */
|
} /* __PHYSFS_platformCurrentDir */
|
||||||
|
|
||||||
|
@ -545,5 +540,118 @@ int __PHYSFS_platformMkDir(const char *path)
|
||||||
return(1);
|
return(1);
|
||||||
} /* __PHYSFS_platformMkDir */
|
} /* __PHYSFS_platformMkDir */
|
||||||
|
|
||||||
|
|
||||||
|
static void *doOpen(const char *filename, const char *mode)
|
||||||
|
{
|
||||||
|
FILE *retval;
|
||||||
|
errno = 0;
|
||||||
|
|
||||||
|
retval = fopen(filename, mode);
|
||||||
|
if (retval == NULL)
|
||||||
|
__PHYSFS_setError(strerror(errno));
|
||||||
|
|
||||||
|
return((void *) retval);
|
||||||
|
} /* doOpen */
|
||||||
|
|
||||||
|
|
||||||
|
void *__PHYSFS_platformOpenRead(const char *filename)
|
||||||
|
{
|
||||||
|
return(doOpen(filename, "rb"));
|
||||||
|
} /* __PHYSFS_platformOpenRead */
|
||||||
|
|
||||||
|
|
||||||
|
void *__PHYSFS_platformOpenWrite(const char *filename)
|
||||||
|
{
|
||||||
|
return(doOpen(filename, "wb"));
|
||||||
|
} /* __PHYSFS_platformOpenWrite */
|
||||||
|
|
||||||
|
|
||||||
|
void *__PHYSFS_platformOpenAppend(const char *filename)
|
||||||
|
{
|
||||||
|
return(doOpen(filename, "wb+"));
|
||||||
|
} /* __PHYSFS_platformOpenAppend */
|
||||||
|
|
||||||
|
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformRead(void *opaque, void *buffer,
|
||||||
|
PHYSFS_uint32 size, PHYSFS_uint32 count)
|
||||||
|
{
|
||||||
|
FILE *io = (FILE *) opaque;
|
||||||
|
int rc = fread(buffer, size, count, io);
|
||||||
|
if (rc < count)
|
||||||
|
{
|
||||||
|
int err = errno;
|
||||||
|
BAIL_IF_MACRO(ferror(io), strerror(err), rc);
|
||||||
|
BAIL_MACRO(ERR_PAST_EOF, rc);
|
||||||
|
} /* if */
|
||||||
|
|
||||||
|
return(rc);
|
||||||
|
} /* __PHYSFS_platformRead */
|
||||||
|
|
||||||
|
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformWrite(void *opaque, void *buffer,
|
||||||
|
PHYSFS_uint32 size, PHYSFS_uint32 count)
|
||||||
|
{
|
||||||
|
FILE *io = (FILE *) opaque;
|
||||||
|
int rc = fwrite(buffer, size, count, io);
|
||||||
|
if (rc < count)
|
||||||
|
__PHYSFS_setError(strerror(errno));
|
||||||
|
|
||||||
|
return(rc);
|
||||||
|
} /* __PHYSFS_platformWrite */
|
||||||
|
|
||||||
|
|
||||||
|
int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos)
|
||||||
|
{
|
||||||
|
FILE *io = (FILE *) opaque;
|
||||||
|
|
||||||
|
/* !!! FIXME: Use llseek where available. */
|
||||||
|
errno = 0;
|
||||||
|
BAIL_IF_MACRO(fseek(io, pos, SEEK_SET) != 0, strerror(errno), 0);
|
||||||
|
|
||||||
|
return(1);
|
||||||
|
} /* __PHYSFS_platformSeek */
|
||||||
|
|
||||||
|
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformTell(void *opaque)
|
||||||
|
{
|
||||||
|
FILE *io = (FILE *) opaque;
|
||||||
|
PHYSFS_sint64 retval = ftell(io);
|
||||||
|
BAIL_IF_MACRO(retval == -1, strerror(errno), -1);
|
||||||
|
return(retval);
|
||||||
|
} /* __PHYSFS_platformTell */
|
||||||
|
|
||||||
|
|
||||||
|
PHYSFS_sint64 __PHYSFS_platformFileLength(void *opaque)
|
||||||
|
{
|
||||||
|
FILE *io = (FILE *) opaque;
|
||||||
|
struct stat statbuf;
|
||||||
|
errno = 0;
|
||||||
|
BAIL_IF_MACRO(fstat(fileno(io), &statbuf) == -1, strerror(errno), -1);
|
||||||
|
return((PHYSFS_sint64) statbuf.st_size);
|
||||||
|
} /* __PHYSFS_platformFileLength */
|
||||||
|
|
||||||
|
|
||||||
|
int __PHYSFS_platformEOF(void *opaque)
|
||||||
|
{
|
||||||
|
return(feof((FILE *) opaque));
|
||||||
|
} /* __PHYSFS_platformEOF */
|
||||||
|
|
||||||
|
|
||||||
|
int __PHYSFS_platformFlush(void *opaque)
|
||||||
|
{
|
||||||
|
int rc = fflush((FILE *) opaque);
|
||||||
|
BAIL_IF_MACRO(rc == EOF, strerror(errno), 0);
|
||||||
|
return(1);
|
||||||
|
} /* __PHYSFS_platformFlush */
|
||||||
|
|
||||||
|
|
||||||
|
int __PHYSFS_platformClose(void *opaque)
|
||||||
|
{
|
||||||
|
int rc = fclose((FILE *) opaque);
|
||||||
|
BAIL_IF_MACRO(rc == EOF, strerror(errno), 0);
|
||||||
|
return(1);
|
||||||
|
} /* __PHYSFS_platformClose */
|
||||||
|
|
||||||
|
|
||||||
/* end of unix.c ... */
|
/* end of unix.c ... */
|
||||||
|
|
||||||
|
|
|
@ -41,8 +41,8 @@ static void output_versions(void)
|
||||||
" Compiled against PhysicsFS version %d.%d.%d,\n"
|
" Compiled against PhysicsFS version %d.%d.%d,\n"
|
||||||
" and linked against %d.%d.%d.\n\n",
|
" and linked against %d.%d.%d.\n\n",
|
||||||
TEST_VERSION_MAJOR, TEST_VERSION_MINOR, TEST_VERSION_PATCH,
|
TEST_VERSION_MAJOR, TEST_VERSION_MINOR, TEST_VERSION_PATCH,
|
||||||
compiled.major, compiled.minor, compiled.patch,
|
(int) compiled.major, (int) compiled.minor, (int) compiled.patch,
|
||||||
linked.major, linked.minor, linked.patch);
|
(int) linked.major, (int) linked.minor, (int) linked.patch);
|
||||||
} /* output_versions */
|
} /* output_versions */
|
||||||
|
|
||||||
|
|
||||||
|
@ -336,8 +336,8 @@ static int cmd_cat(char *args)
|
||||||
while (1)
|
while (1)
|
||||||
{
|
{
|
||||||
char buffer[128];
|
char buffer[128];
|
||||||
int rc;
|
PHYSFS_sint64 rc;
|
||||||
int i;
|
PHYSFS_sint64 i;
|
||||||
rc = PHYSFS_read(f, buffer, 1, sizeof (buffer));
|
rc = PHYSFS_read(f, buffer, 1, sizeof (buffer));
|
||||||
|
|
||||||
for (i = 0; i < rc; i++)
|
for (i = 0; i < rc; i++)
|
||||||
|
@ -347,7 +347,10 @@ static int cmd_cat(char *args)
|
||||||
{
|
{
|
||||||
printf("\n\n");
|
printf("\n\n");
|
||||||
if (!PHYSFS_eof(f))
|
if (!PHYSFS_eof(f))
|
||||||
printf("\n (Error condition in reading.)\n\n");
|
{
|
||||||
|
printf("\n (Error condition in reading. Reason: [%s])\n\n",
|
||||||
|
PHYSFS_getLastError());
|
||||||
|
} /* if */
|
||||||
PHYSFS_close(f);
|
PHYSFS_close(f);
|
||||||
return(1);
|
return(1);
|
||||||
} /* if */
|
} /* if */
|
||||||
|
|
Loading…
Reference in New Issue