Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Implementation compiles and links with no actual archive support. No …
…test

 case available at this moment.  :)
  • Loading branch information
icculus committed Jul 8, 2001
1 parent f053b90 commit 2622be3
Show file tree
Hide file tree
Showing 6 changed files with 685 additions and 73 deletions.
2 changes: 1 addition & 1 deletion Makefile
Expand Up @@ -182,7 +182,7 @@ $(MAINLIB) : $(BINDIR) $(MAINOBJS)

$(BINDIR):
mkdir -p $(BINDIR)
mkdir -p $(BINDIR)/archive_drivers
mkdir -p $(BINDIR)/archivers
mkdir -p $(BINDIR)/platform

distclean: clean
Expand Down
311 changes: 287 additions & 24 deletions archivers/dir.c
Expand Up @@ -8,46 +8,309 @@

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>

#define __PHYSICSFS_INTERNAL__
#include "physfs_internal.h"

extern const DirFunctions __PHYSFS_DirFunctions_DIR;
static const FileFunctions __PHYSFS_FileHandle_DIR;
static const FileFunctions __PHYSFS_FileHandle_DIRW;

static int DIR_read(FileHandle *handle, void *buffer,
unsigned int objSize, unsigned int objCount)
{
FILE *h = (FILE *) (handle->opaque);
int retval;

errno = 0;
retval = fread(buffer, objSize, objCount, h);
if ( (retval < objCount) && (ferror(h)) )
__PHYSFS_setError(strerror(errno));

return(retval);
} /* DIR_read */


static int DIR_write(FileHandle *handle, void *buffer,
unsigned int objSize, unsigned int objCount)
{
FILE *h = (FILE *) (handle->opaque);
int retval;

errno = 0;
retval = fwrite(buffer, objSize, objCount, h);
if ( (retval < objCount) && (ferror(h)) )
__PHYSFS_setError(strerror(errno));

return(retval);
} /* DIR_write */


static int DIR_eof(FileHandle *handle)
{
return(feof((FILE *) (handle->opaque)));
} /* DIR_eof */


static int DIR_tell(FileHandle *handle)
{
return(ftell((FILE *) (handle->opaque)));
} /* DIR_tell */


static int DIR_seek(FileHandle *handle, int offset)
{
return(fseek((FILE *) (handle->opaque), offset, SEEK_SET) == 0);
} /* DIR_seek */


static int DIR_fileClose(FileHandle *handle)
{
FILE *h = (FILE *) (handle->opaque);

/*
* we manually fflush() the buffer, since that's the place fclose() will
* most likely fail, but that will leave the file handle in an undefined
* state if it fails. fflush() failures we can recover from.
*/

/* keep trying until there's success or an unrecoverable error... */
do {
__PHYSFS_platformTimeslice();
errno = 0;
} while ( (fflush(h) == EOF) && ((errno == EAGAIN) || (errno == EINTR)) );

/* EBADF == "Not open for writing". That's fine. */
BAIL_IF_MACRO((errno != 0) && (errno != EBADF), strerror(errno), 0);

/* if fclose fails anyhow, we just have to pray that it's still usable. */
errno = 0;
BAIL_IF_MACRO(fclose(h) == EOF, strerror(errno), 0); /* (*shrug*) */

free(handle);
return(1);
} /* DIR_fileClose */


static int DIR_isArchive(const char *filename, int forWriting)
{
/* directories ARE archives in this driver... */
return(__PHYSFS_platformIsDirectory(filename));
} /* DIR_isArchive */


static DirHandle *DIR_openArchive(const char *name, int forWriting)
{
const char *dirsep = __PHYSFS_platformDirSeparator;
DirHandle *retval = NULL;
int namelen = strlen(name);
int seplen = strlen(dirsep);

BAIL_IF_MACRO(!DIR_isArchive(name, 0), ERR_UNSUPPORTED_ARCHIVE, NULL);

retval = malloc(sizeof (DirHandle));
BAIL_IF_MACRO(retval == NULL, ERR_OUT_OF_MEMORY, NULL);
retval->opaque = malloc(namelen + seplen + 1);
if (retval->opaque == NULL)
{
free(retval);
BAIL_IF_MACRO(0, ERR_OUT_OF_MEMORY, NULL);
} /* if */

/* make sure there's a dir separator at the end of the string */
strcpy((char *) (retval->opaque), name);
if (strcmp((name + namelen) - seplen, dirsep) != 0)
strcat((char *) (retval->opaque), dirsep);

retval->funcs = &__PHYSFS_DirFunctions_DIR;
return(retval);
} /* DIR_openArchive */


static LinkedStringList *DIR_enumerateFiles(DirHandle *h, const char *dname)
{
char *d = __PHYSFS_platformCvtToDependent((char *)(h->opaque),dname,NULL);
LinkedStringList *retval;

BAIL_IF_MACRO(d == NULL, NULL, NULL);
retval = __PHYSFS_platformEnumerateFiles(d);
free(d);
return(retval);
} /* DIR_enumerateFiles */


static int DIR_exists(DirHandle *h, const char *name)
{
char *f = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
int retval;

BAIL_IF_MACRO(f == NULL, NULL, 0);
retval = __PHYSFS_platformExists(f);
free(f);
return(retval);
} /* DIR_exists */


static int DIR_isDirectory(DirHandle *h, const char *name)
{
char *d = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
int retval;

BAIL_IF_MACRO(d == NULL, NULL, 0);
retval = __PHYSFS_platformIsDirectory(d);
free(d);
return(retval);
} /* DIR_isDirectory */


static int DIR_isSymLink(DirHandle *h, const char *name)
{
char *f = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
int retval;

BAIL_IF_MACRO(f == NULL, NULL, 0); /* !!! might be a problem. */
retval = __PHYSFS_platformIsSymLink(f);
free(f);
return(retval);
} /* DIR_isSymLink */


static FileHandle *doOpen(DirHandle *h, const char *name, const char *mode)
{
char *f = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
FILE *rc;
FileHandle *retval;
char *str;

BAIL_IF_MACRO(f == NULL, NULL, NULL);

retval = (FileHandle *) malloc(sizeof (FileHandle));
if (!retval)
{
free(f);
BAIL_IF_MACRO(0, ERR_OUT_OF_MEMORY, NULL);
} /* if */

errno = 0;
rc = fopen(f, mode);
str = strerror(errno);
free(f);

if (!rc)
{
free(retval);
BAIL_IF_MACRO(0, str, NULL);
} /* if */

retval->opaque = (void *) rc;
retval->dirHandle = h;
retval->funcs = &__PHYSFS_FileHandle_DIR;
return(retval);
} /* doOpen */


static FileHandle *DIR_openRead(DirHandle *h, const char *filename)
{
return(doOpen(h, filename, "rb"));
} /* DIR_openRead */


static FileHandle *DIR_openWrite(DirHandle *h, const char *filename)
{
return(doOpen(h, filename, "wb"));
} /* DIR_openWrite */


static FileHandle *DIR_openAppend(DirHandle *h, const char *filename)
{
return(doOpen(h, filename, "ab"));
} /* DIR_openAppend */


static int DIR_remove(DirHandle *h, const char *name)
{
char *f = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
int retval;

BAIL_IF_MACRO(f == NULL, NULL, 0);

errno = 0;
retval = (remove(f) == 0);
if (!retval)
__PHYSFS_setError(strerror(errno));

free(f);
return(retval);
} /* DIR_remove */


static int DIR_mkdir(DirHandle *h, const char *name)
{
char *f = __PHYSFS_platformCvtToDependent((char *)(h->opaque), name, NULL);
int retval;

BAIL_IF_MACRO(f == NULL, NULL, 0);

errno = 0;
retval = (mkdir(f, S_IRWXU) == 0);
if (!retval)
__PHYSFS_setError(strerror(errno));

free(f);
return(retval);
} /* DIR_mkdir */


static void DIR_dirClose(DirHandle *h)
{
free(h->opaque);
free(h);
} /* DIR_dirClose */



static const FileFunctions __PHYSFS_FileHandle_DIR =
{
DIR_read, /* read() method */
NULL, /* write() method */
DIR_eof, /* eof() method */
DIR_tell, /* tell() method */
DIR_seek, /* seek() method */
DIR_close, /* close() method */
DIR_read, /* read() method */
NULL, /* write() method */
DIR_eof, /* eof() method */
DIR_tell, /* tell() method */
DIR_seek, /* seek() method */
DIR_fileClose, /* fileClose() method */
};


static const FileFunctions __PHYSFS_FileHandle_DIRW =
{
NULL, /* read() method */
DIR_write, /* write() method */
DIR_eof, /* eof() method */
DIR_tell, /* tell() method */
DIR_seek, /* seek() method */
DIR_close, /* close() method */
NULL, /* read() method */
DIR_write, /* write() method */
DIR_eof, /* eof() method */
DIR_tell, /* tell() method */
DIR_seek, /* seek() method */
DIR_fileClose, /* fileClose() method */
};


const DirFunctions __PHYSFS_DirFunctions_DIR =
{
DIR_isArchive, /* isArchive() method */
DIR_openArchive, /* openArchive() method */
DIR_enumerate, /* enumerateFiles() method */
DIR_exists, /* exists() method */
DIR_isDirectory, /* isDirectory() method */
DIR_isSymLink, /* isSymLink() method */
DIR_openRead, /* openRead() method */
DIR_openWrite, /* openWrite() method */
DIR_openAppend, /* openAppend() method */
DIR_remove, /* remove() method */
DIR_mkdir, /* mkdir() method */
DIR_close, /* close() method */
DIR_isArchive, /* isArchive() method */
DIR_openArchive, /* openArchive() method */
DIR_enumerateFiles, /* enumerateFiles() method */
DIR_exists, /* exists() method */
DIR_isDirectory, /* isDirectory() method */
DIR_isSymLink, /* isSymLink() method */
DIR_openRead, /* openRead() method */
DIR_openWrite, /* openWrite() method */
DIR_openAppend, /* openAppend() method */
DIR_remove, /* remove() method */
DIR_mkdir, /* mkdir() method */
DIR_dirClose, /* dirClose() method */
};


Expand Down

0 comments on commit 2622be3

Please sign in to comment.