archivers/mvl.c
changeset 650 298b8bb26775
parent 648 5c993684b8f2
child 657 dad3b5c307a9
equal deleted inserted replaced
649:85aeb90378bc 650:298b8bb26775
    62     MVLentry *entry;
    62     MVLentry *entry;
    63     PHYSFS_uint32 curPos;
    63     PHYSFS_uint32 curPos;
    64 } MVLfileinfo;
    64 } MVLfileinfo;
    65 
    65 
    66 
    66 
    67 static void MVL_dirClose(void *opaque);
    67 static PHYSFS_sint64 MVL_read(fvoid *opaque, void *buffer,
    68 static PHYSFS_sint64 MVL_read(FileHandle *handle, void *buffer,
       
    69                               PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
    68                               PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
    70 static PHYSFS_sint64 MVL_write(FileHandle *handle, const void *buffer,
    69 static PHYSFS_sint64 MVL_write(fvoid *opaque, const void *buffer,
    71                                PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
    70                                PHYSFS_uint32 objSize, PHYSFS_uint32 objCount);
    72 static int MVL_eof(FileHandle *handle);
    71 static int MVL_eof(fvoid *opaque);
    73 static PHYSFS_sint64 MVL_tell(FileHandle *handle);
    72 static PHYSFS_sint64 MVL_tell(fvoid *opaque);
    74 static int MVL_seek(FileHandle *handle, PHYSFS_uint64 offset);
    73 static int MVL_seek(fvoid *opaque, PHYSFS_uint64 offset);
    75 static PHYSFS_sint64 MVL_fileLength(FileHandle *handle);
    74 static PHYSFS_sint64 MVL_fileLength(fvoid *opaque);
    76 static int MVL_fileClose(FileHandle *handle);
    75 static int MVL_fileClose(fvoid *opaque);
    77 static int MVL_isArchive(const char *filename, int forWriting);
    76 static int MVL_isArchive(const char *filename, int forWriting);
    78 static void *MVL_openArchive(const char *name, int forWriting);
    77 static void *MVL_openArchive(const char *name, int forWriting);
    79 static LinkedStringList *MVL_enumerateFiles(void *opaque,
    78 static LinkedStringList *MVL_enumerateFiles(dvoid *opaque,
    80                                             const char *dirname,
    79                                             const char *dirname,
    81                                             int omitSymLinks);
    80                                             int omitSymLinks);
    82 static int MVL_exists(void *opaque, const char *name);
    81 static int MVL_exists(dvoid *opaque, const char *name);
    83 static int MVL_isDirectory(void *opaque, const char *name, int *fileExists);
    82 static int MVL_isDirectory(dvoid *opaque, const char *name, int *fileExists);
    84 static int MVL_isSymLink(void *opaque, const char *name, int *fileExists);
    83 static int MVL_isSymLink(dvoid *opaque, const char *name, int *fileExists);
    85 static PHYSFS_sint64 MVL_getLastModTime(void *opaque, const char *n, int *e);
    84 static PHYSFS_sint64 MVL_getLastModTime(dvoid *opaque, const char *n, int *e);
    86 static FileHandle *MVL_openRead(void *opaque, const char *name, int *exist);
    85 static fvoid *MVL_openRead(dvoid *opaque, const char *name, int *exist);
    87 static FileHandle *MVL_openWrite(void *opaque, const char *name);
    86 static fvoid *MVL_openWrite(dvoid *opaque, const char *name);
    88 static FileHandle *MVL_openAppend(void *opaque, const char *name);
    87 static fvoid *MVL_openAppend(dvoid *opaque, const char *name);
    89 static int MVL_remove(void *opaque, const char *name);
    88 static int MVL_remove(dvoid *opaque, const char *name);
    90 static int MVL_mkdir(void *opaque, const char *name);
    89 static int MVL_mkdir(dvoid *opaque, const char *name);
       
    90 static void MVL_dirClose(dvoid *opaque);
    91 
    91 
    92 const PHYSFS_ArchiveInfo __PHYSFS_ArchiveInfo_MVL =
    92 const PHYSFS_ArchiveInfo __PHYSFS_ArchiveInfo_MVL =
    93 {
    93 {
    94     "MVL",
    94     "MVL",
    95     MVL_ARCHIVE_DESCRIPTION,
    95     MVL_ARCHIVE_DESCRIPTION,
    96     "Bradley Bell <btb@icculus.org>",
    96     "Bradley Bell <btb@icculus.org>",
    97     "http://icculus.org/physfs/",
    97     "http://icculus.org/physfs/",
    98 };
    98 };
    99 
    99 
   100 
   100 
   101 static const FileFunctions __PHYSFS_FileFunctions_MVL =
   101 const PHYSFS_Archiver __PHYSFS_Archiver_MVL =
   102 {
       
   103     MVL_read,       /* read() method       */
       
   104     MVL_write,      /* write() method      */
       
   105     MVL_eof,        /* eof() method        */
       
   106     MVL_tell,       /* tell() method       */
       
   107     MVL_seek,       /* seek() method       */
       
   108     MVL_fileLength, /* fileLength() method */
       
   109     MVL_fileClose   /* fileClose() method  */
       
   110 };
       
   111 
       
   112 
       
   113 const DirFunctions __PHYSFS_DirFunctions_MVL =
       
   114 {
   102 {
   115     &__PHYSFS_ArchiveInfo_MVL,
   103     &__PHYSFS_ArchiveInfo_MVL,
   116     MVL_isArchive,          /* isArchive() method      */
   104     MVL_isArchive,          /* isArchive() method      */
   117     MVL_openArchive,        /* openArchive() method    */
   105     MVL_openArchive,        /* openArchive() method    */
   118     MVL_enumerateFiles,     /* enumerateFiles() method */
   106     MVL_enumerateFiles,     /* enumerateFiles() method */
   123     MVL_openRead,           /* openRead() method       */
   111     MVL_openRead,           /* openRead() method       */
   124     MVL_openWrite,          /* openWrite() method      */
   112     MVL_openWrite,          /* openWrite() method      */
   125     MVL_openAppend,         /* openAppend() method     */
   113     MVL_openAppend,         /* openAppend() method     */
   126     MVL_remove,             /* remove() method         */
   114     MVL_remove,             /* remove() method         */
   127     MVL_mkdir,              /* mkdir() method          */
   115     MVL_mkdir,              /* mkdir() method          */
   128     MVL_dirClose            /* dirClose() method       */
   116     MVL_dirClose,           /* dirClose() method       */
       
   117     MVL_read,               /* read() method           */
       
   118     MVL_write,              /* write() method          */
       
   119     MVL_eof,                /* eof() method            */
       
   120     MVL_tell,               /* tell() method           */
       
   121     MVL_seek,               /* seek() method           */
       
   122     MVL_fileLength,         /* fileLength() method     */
       
   123     MVL_fileClose           /* fileClose() method      */
   129 };
   124 };
   130 
   125 
   131 
   126 
   132 
   127 
   133 static void MVL_dirClose(void *opaque)
   128 static void MVL_dirClose(dvoid *opaque)
   134 {
   129 {
   135     MVLinfo *info = ((MVLinfo *) opaque);
   130     MVLinfo *info = ((MVLinfo *) opaque);
   136     free(info->filename);
   131     free(info->filename);
   137     free(info->entries);
   132     free(info->entries);
   138     free(info);
   133     free(info);
   139 } /* MVL_dirClose */
   134 } /* MVL_dirClose */
   140 
   135 
   141 
   136 
   142 static PHYSFS_sint64 MVL_read(FileHandle *handle, void *buffer,
   137 static PHYSFS_sint64 MVL_read(fvoid *opaque, void *buffer,
   143                               PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
   138                               PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
   144 {
   139 {
   145     MVLfileinfo *finfo = (MVLfileinfo *) (handle->opaque);
   140     MVLfileinfo *finfo = (MVLfileinfo *) opaque;
   146     MVLentry *entry = finfo->entry;
   141     MVLentry *entry = finfo->entry;
   147     PHYSFS_uint32 bytesLeft = entry->size - finfo->curPos;
   142     PHYSFS_uint32 bytesLeft = entry->size - finfo->curPos;
   148     PHYSFS_uint32 objsLeft = (bytesLeft / objSize);
   143     PHYSFS_uint32 objsLeft = (bytesLeft / objSize);
   149     PHYSFS_sint64 rc;
   144     PHYSFS_sint64 rc;
   150 
   145 
   157 
   152 
   158     return(rc);
   153     return(rc);
   159 } /* MVL_read */
   154 } /* MVL_read */
   160 
   155 
   161 
   156 
   162 static PHYSFS_sint64 MVL_write(FileHandle *handle, const void *buffer,
   157 static PHYSFS_sint64 MVL_write(fvoid *opaque, const void *buffer,
   163                                PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
   158                                PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
   164 {
   159 {
   165     BAIL_MACRO(ERR_NOT_SUPPORTED, -1);
   160     BAIL_MACRO(ERR_NOT_SUPPORTED, -1);
   166 } /* MVL_write */
   161 } /* MVL_write */
   167 
   162 
   168 
   163 
   169 static int MVL_eof(FileHandle *handle)
   164 static int MVL_eof(fvoid *opaque)
   170 {
   165 {
   171     MVLfileinfo *finfo = (MVLfileinfo *) (handle->opaque);
   166     MVLfileinfo *finfo = (MVLfileinfo *) opaque;
   172     MVLentry *entry = finfo->entry;
   167     MVLentry *entry = finfo->entry;
   173     return(finfo->curPos >= entry->size);
   168     return(finfo->curPos >= entry->size);
   174 } /* MVL_eof */
   169 } /* MVL_eof */
   175 
   170 
   176 
   171 
   177 static PHYSFS_sint64 MVL_tell(FileHandle *handle)
   172 static PHYSFS_sint64 MVL_tell(fvoid *opaque)
   178 {
   173 {
   179     return(((MVLfileinfo *) (handle->opaque))->curPos);
   174     return(((MVLfileinfo *) opaque)->curPos);
   180 } /* MVL_tell */
   175 } /* MVL_tell */
   181 
   176 
   182 
   177 
   183 static int MVL_seek(FileHandle *handle, PHYSFS_uint64 offset)
   178 static int MVL_seek(fvoid *opaque, PHYSFS_uint64 offset)
   184 {
   179 {
   185     MVLfileinfo *finfo = (MVLfileinfo *) (handle->opaque);
   180     MVLfileinfo *finfo = (MVLfileinfo *) opaque;
   186     MVLentry *entry = finfo->entry;
   181     MVLentry *entry = finfo->entry;
   187     int rc;
   182     int rc;
   188 
   183 
   189     BAIL_IF_MACRO(offset < 0, ERR_INVALID_ARGUMENT, 0);
   184     BAIL_IF_MACRO(offset < 0, ERR_INVALID_ARGUMENT, 0);
   190     BAIL_IF_MACRO(offset >= entry->size, ERR_PAST_EOF, 0);
   185     BAIL_IF_MACRO(offset >= entry->size, ERR_PAST_EOF, 0);
   194 
   189 
   195     return(rc);
   190     return(rc);
   196 } /* MVL_seek */
   191 } /* MVL_seek */
   197 
   192 
   198 
   193 
   199 static PHYSFS_sint64 MVL_fileLength(FileHandle *handle)
   194 static PHYSFS_sint64 MVL_fileLength(fvoid *opaque)
   200 {
   195 {
   201     MVLfileinfo *finfo = ((MVLfileinfo *) handle->opaque);
   196     MVLfileinfo *finfo = (MVLfileinfo *) opaque;
   202     return((PHYSFS_sint64) finfo->entry->size);
   197     return((PHYSFS_sint64) finfo->entry->size);
   203 } /* MVL_fileLength */
   198 } /* MVL_fileLength */
   204 
   199 
   205 
   200 
   206 static int MVL_fileClose(FileHandle *handle)
   201 static int MVL_fileClose(fvoid *opaque)
   207 {
   202 {
   208     MVLfileinfo *finfo = ((MVLfileinfo *) handle->opaque);
   203     MVLfileinfo *finfo = (MVLfileinfo *) opaque;
   209     BAIL_IF_MACRO(!__PHYSFS_platformClose(finfo->handle), NULL, 0);
   204     BAIL_IF_MACRO(!__PHYSFS_platformClose(finfo->handle), NULL, 0);
   210     free(finfo);
   205     free(finfo);
   211     free(handle);
       
   212     return(1);
   206     return(1);
   213 } /* MVL_fileClose */
   207 } /* MVL_fileClose */
   214 
   208 
   215 
   209 
   216 static int mvl_open(const char *filename, int forWriting,
   210 static int mvl_open(const char *filename, int forWriting,
   360 
   354 
   361     return(NULL);
   355     return(NULL);
   362 } /* MVL_openArchive */
   356 } /* MVL_openArchive */
   363 
   357 
   364 
   358 
   365 static LinkedStringList *MVL_enumerateFiles(void *opaque,
   359 static LinkedStringList *MVL_enumerateFiles(dvoid *opaque,
   366                                             const char *dirname,
   360                                             const char *dirname,
   367                                             int omitSymLinks)
   361                                             int omitSymLinks)
   368 {
   362 {
   369     MVLinfo *info = ((MVLinfo *) opaque);
   363     MVLinfo *info = ((MVLinfo *) opaque);
   370     MVLentry *entry = info->entries;
   364     MVLentry *entry = info->entries;
   413 
   407 
   414     BAIL_MACRO(ERR_NO_SUCH_FILE, NULL);
   408     BAIL_MACRO(ERR_NO_SUCH_FILE, NULL);
   415 } /* mvl_find_entry */
   409 } /* mvl_find_entry */
   416 
   410 
   417 
   411 
   418 static int MVL_exists(void *opaque, const char *name)
   412 static int MVL_exists(dvoid *opaque, const char *name)
   419 {
   413 {
   420     return(mvl_find_entry(((MVLinfo *) opaque), name) != NULL);
   414     return(mvl_find_entry(((MVLinfo *) opaque), name) != NULL);
   421 } /* MVL_exists */
   415 } /* MVL_exists */
   422 
   416 
   423 
   417 
   424 static int MVL_isDirectory(void *opaque, const char *name, int *fileExists)
   418 static int MVL_isDirectory(dvoid *opaque, const char *name, int *fileExists)
   425 {
   419 {
   426     *fileExists = MVL_exists(opaque, name);
   420     *fileExists = MVL_exists(opaque, name);
   427     return(0);  /* never directories in a groupfile. */
   421     return(0);  /* never directories in a groupfile. */
   428 } /* MVL_isDirectory */
   422 } /* MVL_isDirectory */
   429 
   423 
   430 
   424 
   431 static int MVL_isSymLink(void *opaque, const char *name, int *fileExists)
   425 static int MVL_isSymLink(dvoid *opaque, const char *name, int *fileExists)
   432 {
   426 {
   433     *fileExists = MVL_exists(opaque, name);
   427     *fileExists = MVL_exists(opaque, name);
   434     return(0);  /* never symlinks in a groupfile. */
   428     return(0);  /* never symlinks in a groupfile. */
   435 } /* MVL_isSymLink */
   429 } /* MVL_isSymLink */
   436 
   430 
   437 
   431 
   438 static PHYSFS_sint64 MVL_getLastModTime(void *opaque,
   432 static PHYSFS_sint64 MVL_getLastModTime(dvoid *opaque,
   439                                         const char *name,
   433                                         const char *name,
   440                                         int *fileExists)
   434                                         int *fileExists)
   441 {
   435 {
   442     MVLinfo *info = ((MVLinfo *) opaque);
   436     MVLinfo *info = ((MVLinfo *) opaque);
   443     PHYSFS_sint64 retval = -1;
   437     PHYSFS_sint64 retval = -1;
   448 
   442 
   449     return(retval);
   443     return(retval);
   450 } /* MVL_getLastModTime */
   444 } /* MVL_getLastModTime */
   451 
   445 
   452 
   446 
   453 static FileHandle *MVL_openRead(void *opaque, const char *fnm, int *fileExists)
   447 static fvoid *MVL_openRead(dvoid *opaque, const char *fnm, int *fileExists)
   454 {
   448 {
   455     MVLinfo *info = ((MVLinfo *) opaque);
   449     MVLinfo *info = ((MVLinfo *) opaque);
   456     FileHandle *retval;
       
   457     MVLfileinfo *finfo;
   450     MVLfileinfo *finfo;
   458     MVLentry *entry;
   451     MVLentry *entry;
   459 
   452 
   460     entry = mvl_find_entry(info, fnm);
   453     entry = mvl_find_entry(info, fnm);
   461     *fileExists = (entry != NULL);
   454     *fileExists = (entry != NULL);
   462     BAIL_IF_MACRO(entry == NULL, NULL, NULL);
   455     BAIL_IF_MACRO(entry == NULL, NULL, NULL);
   463 
   456 
   464     retval = (FileHandle *) malloc(sizeof (FileHandle));
       
   465     BAIL_IF_MACRO(retval == NULL, ERR_OUT_OF_MEMORY, NULL);
       
   466     finfo = (MVLfileinfo *) malloc(sizeof (MVLfileinfo));
   457     finfo = (MVLfileinfo *) malloc(sizeof (MVLfileinfo));
   467     if (finfo == NULL)
   458     BAIL_IF_MACRO(finfo == NULL, ERR_OUT_OF_MEMORY, NULL);
   468     {
       
   469         free(retval);
       
   470         BAIL_MACRO(ERR_OUT_OF_MEMORY, NULL);
       
   471     } /* if */
       
   472 
   459 
   473     finfo->handle = __PHYSFS_platformOpenRead(info->filename);
   460     finfo->handle = __PHYSFS_platformOpenRead(info->filename);
   474     if ( (finfo->handle == NULL) ||
   461     if ( (finfo->handle == NULL) ||
   475          (!__PHYSFS_platformSeek(finfo->handle, entry->startPos)) )
   462          (!__PHYSFS_platformSeek(finfo->handle, entry->startPos)) )
   476     {
   463     {
   477         free(finfo);
   464         free(finfo);
   478         free(retval);
       
   479         return(NULL);
   465         return(NULL);
   480     } /* if */
   466     } /* if */
   481 
   467 
   482     finfo->curPos = 0;
   468     finfo->curPos = 0;
   483     finfo->entry = entry;
   469     finfo->entry = entry;
   484     retval->opaque = (void *) finfo;
   470     return(finfo);
   485     retval->funcs = &__PHYSFS_FileFunctions_MVL;
       
   486     return(retval);
       
   487 } /* MVL_openRead */
   471 } /* MVL_openRead */
   488 
   472 
   489 
   473 
   490 static FileHandle *MVL_openWrite(void *opaque, const char *name)
   474 static fvoid *MVL_openWrite(dvoid *opaque, const char *name)
   491 {
   475 {
   492     BAIL_MACRO(ERR_NOT_SUPPORTED, NULL);
   476     BAIL_MACRO(ERR_NOT_SUPPORTED, NULL);
   493 } /* MVL_openWrite */
   477 } /* MVL_openWrite */
   494 
   478 
   495 
   479 
   496 static FileHandle *MVL_openAppend(void *opaque, const char *name)
   480 static fvoid *MVL_openAppend(dvoid *opaque, const char *name)
   497 {
   481 {
   498     BAIL_MACRO(ERR_NOT_SUPPORTED, NULL);
   482     BAIL_MACRO(ERR_NOT_SUPPORTED, NULL);
   499 } /* MVL_openAppend */
   483 } /* MVL_openAppend */
   500 
   484 
   501 
   485 
   502 static int MVL_remove(void *opaque, const char *name)
   486 static int MVL_remove(dvoid *opaque, const char *name)
   503 {
   487 {
   504     BAIL_MACRO(ERR_NOT_SUPPORTED, 0);
   488     BAIL_MACRO(ERR_NOT_SUPPORTED, 0);
   505 } /* MVL_remove */
   489 } /* MVL_remove */
   506 
   490 
   507 
   491 
   508 static int MVL_mkdir(void *opaque, const char *name)
   492 static int MVL_mkdir(dvoid *opaque, const char *name)
   509 {
   493 {
   510     BAIL_MACRO(ERR_NOT_SUPPORTED, 0);
   494     BAIL_MACRO(ERR_NOT_SUPPORTED, 0);
   511 } /* MVL_mkdir */
   495 } /* MVL_mkdir */
   512 
   496 
   513 #endif  /* defined PHYSFS_SUPPORTS_MVL */
   497 #endif  /* defined PHYSFS_SUPPORTS_MVL */