src/archiver_zip.c
author Ryan C. Gordon <icculus@icculus.org>
Thu, 25 Mar 2010 16:00:21 -0400
changeset 1085 1ad575ce53c8
parent 1054 57f4af811ffb
child 1098 4e86cec1143f
permissions -rw-r--r--
Merged changeset 1084:ee3d2e6e1161 from stable-2.0: unitialized array fix.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
17
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     1
/*
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     2
 * ZIP support routines for PhysicsFS.
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     3
 *
809
116b8fe30371 Renamed LICENSE to LICENSE.txt
Ryan C. Gordon <icculus@icculus.org>
parents: 808
diff changeset
     4
 * Please see the file LICENSE.txt in the source's root directory.
17
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     5
 *
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
     6
 *  This file written by Ryan C. Gordon, with some peeking at "unzip.c"
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
     7
 *   by Gilles Vollant.
17
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     8
 */
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
     9
214
19846c18071b Initial autoconf support.
Ryan C. Gordon <icculus@icculus.org>
parents: 194
diff changeset
    10
#if (defined PHYSFS_SUPPORTS_ZIP)
19846c18071b Initial autoconf support.
Ryan C. Gordon <icculus@icculus.org>
parents: 194
diff changeset
    11
17
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    12
#include <stdio.h>
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    13
#include <stdlib.h>
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
    14
#include <string.h>
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
    15
#ifndef _WIN32_WCE
504
3420d82f9b01 Some cleanups for PocketPC port.
Ryan C. Gordon <icculus@icculus.org>
parents: 494
diff changeset
    16
#include <errno.h>
254
c66bbbe50f14 Implemeted getLastModTime method.
Ryan C. Gordon <icculus@icculus.org>
parents: 240
diff changeset
    17
#include <time.h>
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
    18
#endif
22
49f6101707b4 More tweaks; GRP completely implemented. Everything builds clean.
Ryan C. Gordon <icculus@icculus.org>
parents: 21
diff changeset
    19
#include "physfs.h"
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    20
#include "zlib.h"
17
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    21
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    22
#define __PHYSICSFS_INTERNAL__
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    23
#include "physfs_internal.h"
7337737f5120 Moved from root source dir.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
    24
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    25
/*
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
    26
 * A buffer of ZIP_READBUFSIZE is allocated for each compressed file opened,
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
    27
 *  and is freed when you close the file; compressed data is read into
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    28
 *  this buffer, and then is decompressed into the buffer passed to
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    29
 *  PHYSFS_read().
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    30
 *
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    31
 * Uncompressed entries in a zipfile do not allocate this buffer; they just
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    32
 *  read data directly into the buffer passed to PHYSFS_read().
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    33
 *
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    34
 * Depending on your speed and memory requirements, you should tweak this
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    35
 *  value.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    36
 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    37
#define ZIP_READBUFSIZE   (16 * 1024)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    38
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    39
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    40
/*
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    41
 * Entries are "unresolved" until they are first opened. At that time,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    42
 *  local file headers parsed/validated, data offsets will be updated to look
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    43
 *  at the actual file data instead of the header, and symlinks will be
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    44
 *  followed and optimized. This means that we don't seek and read around the
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    45
 *  archive until forced to do so, and after the first time, we had to do
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    46
 *  less reading and parsing, which is very CD-ROM friendly.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    47
 */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    48
typedef enum
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    49
{
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    50
    ZIP_UNRESOLVED_FILE,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    51
    ZIP_UNRESOLVED_SYMLINK,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    52
    ZIP_RESOLVING,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    53
    ZIP_RESOLVED,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    54
    ZIP_BROKEN_FILE,
538
8752e3c0dbf9 Now compiles on CodeWarrior 6 for MacOS Classic again.
Ryan C. Gordon <icculus@icculus.org>
parents: 504
diff changeset
    55
    ZIP_BROKEN_SYMLINK
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    56
} ZipResolveType;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    57
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    58
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    59
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    60
 * One ZIPentry is kept for each file in an open ZIP archive.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    61
 */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    62
typedef struct _ZIPentry
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
    63
{
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    64
    char *name;                         /* Name of file in archive        */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    65
    struct _ZIPentry *symlink;          /* NULL or file we symlink to     */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    66
    ZipResolveType resolved;            /* Have we resolved file/symlink? */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    67
    PHYSFS_uint32 offset;               /* offset of data in archive      */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    68
    PHYSFS_uint16 version;              /* version made by                */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    69
    PHYSFS_uint16 version_needed;       /* version needed to extract      */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    70
    PHYSFS_uint16 compression_method;   /* compression method             */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    71
    PHYSFS_uint32 crc;                  /* crc-32                         */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    72
    PHYSFS_uint32 compressed_size;      /* compressed size                */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    73
    PHYSFS_uint32 uncompressed_size;    /* uncompressed size              */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
    74
    PHYSFS_sint64 last_mod_time;        /* last file mod time             */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
    75
} ZIPentry;
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
    76
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    77
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    78
 * One ZIPinfo is kept for each open ZIP archive.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    79
 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    80
typedef struct
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    81
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    82
    char *archiveName;        /* path to ZIP in platform-dependent notation. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    83
    PHYSFS_uint16 entryCount; /* Number of files in ZIP.                     */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    84
    ZIPentry *entries;        /* info on all files in ZIP.                   */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    85
} ZIPinfo;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    86
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    87
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    88
 * One ZIPfileinfo is kept for each open file in a ZIP archive.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    89
 */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
    90
typedef struct
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
    91
{
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    92
    ZIPentry *entry;                      /* Info on file.              */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    93
    void *handle;                         /* physical file handle.      */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    94
    PHYSFS_uint32 compressed_position;    /* offset in compressed data. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    95
    PHYSFS_uint32 uncompressed_position;  /* tell() position.           */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    96
    PHYSFS_uint8 *buffer;                 /* decompression buffer.      */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    97
    z_stream stream;                      /* zlib stream state.         */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    98
} ZIPfileinfo;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
    99
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   100
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   101
/* Magic numbers... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   102
#define ZIP_LOCAL_FILE_SIG          0x04034b50
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   103
#define ZIP_CENTRAL_DIR_SIG         0x02014b50
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   104
#define ZIP_END_OF_CENTRAL_DIR_SIG  0x06054b50
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   105
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   106
/* compression methods... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   107
#define COMPMETH_NONE 0
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   108
/* ...and others... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   109
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   110
342
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   111
#define UNIX_FILETYPE_MASK    0170000
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   112
#define UNIX_FILETYPE_SYMLINK 0120000
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   113
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   114
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   115
/*
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   116
 * Bridge physfs allocation functions to zlib's format...
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   117
 */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   118
static voidpf zlibPhysfsAlloc(voidpf opaque, uInt items, uInt size)
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   119
{
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   120
    return ((PHYSFS_Allocator *) opaque)->Malloc(items * size);
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   121
} /* zlibPhysfsAlloc */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   122
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   123
/*
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   124
 * Bridge physfs allocation functions to zlib's format...
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   125
 */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   126
static void zlibPhysfsFree(voidpf opaque, voidpf address)
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   127
{
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   128
    ((PHYSFS_Allocator *) opaque)->Free(address);
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   129
} /* zlibPhysfsFree */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   130
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   131
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   132
/*
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   133
 * Construct a new z_stream to a sane state.
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   134
 */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   135
static void initializeZStream(z_stream *pstr)
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   136
{
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   137
    memset(pstr, '\0', sizeof (z_stream));
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   138
    pstr->zalloc = zlibPhysfsAlloc;
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   139
    pstr->zfree = zlibPhysfsFree;
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   140
    pstr->opaque = &allocator;
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   141
} /* initializeZStream */
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   142
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   143
427
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   144
static const char *zlib_error_string(int rc)
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   145
{
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   146
    switch (rc)
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   147
    {
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   148
        case Z_OK: return NULL;  /* not an error. */
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   149
        case Z_STREAM_END: return NULL; /* not an error. */
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   150
#ifndef _WIN32_WCE
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   151
        case Z_ERRNO: return strerror(errno);
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   152
#endif
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   153
        case Z_NEED_DICT: return ERR_NEED_DICT;
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   154
        case Z_DATA_ERROR: return ERR_DATA_ERROR;
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   155
        case Z_MEM_ERROR: return ERR_MEMORY_ERROR;
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   156
        case Z_BUF_ERROR: return ERR_BUFFER_ERROR;
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   157
        case Z_VERSION_ERROR: return ERR_VERSION_ERROR;
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   158
        default: return ERR_UNKNOWN_ERROR;
427
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   159
    } /* switch */
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   160
} /* zlib_error_string */
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   161
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   162
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   163
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   164
 * Wrap all zlib calls in this, so the physfs error state is set appropriately.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   165
 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   166
static int zlib_err(int rc)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   167
{
427
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   168
    const char *str = zlib_error_string(rc);
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   169
    if (str != NULL)
c38ace41039f Natural language #defines and build system support.
Ryan C. Gordon <icculus@icculus.org>
parents: 413
diff changeset
   170
        __PHYSFS_setError(str);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   171
    return rc;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   172
} /* zlib_err */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   173
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   174
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   175
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   176
 * Read an unsigned 32-bit int and swap to native byte order.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   177
 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   178
static int readui32(void *in, PHYSFS_uint32 *val)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   179
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   180
    PHYSFS_uint32 v;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   181
    BAIL_IF_MACRO(__PHYSFS_platformRead(in, &v, sizeof (v), 1) != 1, NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   182
    *val = PHYSFS_swapULE32(v);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   183
    return 1;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   184
} /* readui32 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   185
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   186
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   187
/*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   188
 * Read an unsigned 16-bit int and swap to native byte order.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   189
 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   190
static int readui16(void *in, PHYSFS_uint16 *val)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   191
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   192
    PHYSFS_uint16 v;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   193
    BAIL_IF_MACRO(__PHYSFS_platformRead(in, &v, sizeof (v), 1) != 1, NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   194
    *val = PHYSFS_swapULE16(v);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   195
    return 1;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   196
} /* readui16 */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   197
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   198
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   199
static PHYSFS_sint64 ZIP_read(fvoid *opaque, void *buf,
132
b53fa5093749 Added typedefs and platform-specific i/o.
Ryan C. Gordon <icculus@icculus.org>
parents: 95
diff changeset
   200
                              PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   201
{
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   202
    ZIPfileinfo *finfo = (ZIPfileinfo *) opaque;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   203
    ZIPentry *entry = finfo->entry;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   204
    PHYSFS_sint64 retval = 0;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   205
    PHYSFS_sint64 maxread = ((PHYSFS_sint64) objSize) * objCount;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   206
    PHYSFS_sint64 avail = entry->uncompressed_size -
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   207
                          finfo->uncompressed_position;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   208
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   209
    BAIL_IF_MACRO(maxread == 0, NULL, 0);    /* quick rejection. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   210
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   211
    if (avail < maxread)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   212
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   213
        maxread = avail - (avail % objSize);
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   214
        objCount = (PHYSFS_uint32) (maxread / objSize);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   215
        BAIL_IF_MACRO(objCount == 0, ERR_PAST_EOF, 0);  /* quick rejection. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   216
        __PHYSFS_setError(ERR_PAST_EOF);   /* this is always true here. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   217
    } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   218
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   219
    if (entry->compression_method == COMPMETH_NONE)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   220
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   221
        retval = __PHYSFS_platformRead(finfo->handle, buf, objSize, objCount);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   222
    } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   223
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   224
    else
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   225
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   226
        finfo->stream.next_out = buf;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   227
        finfo->stream.avail_out = objSize * objCount;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   228
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   229
        while (retval < maxread)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   230
        {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   231
            PHYSFS_uint32 before = finfo->stream.total_out;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   232
            int rc;
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   233
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   234
            if (finfo->stream.avail_in == 0)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   235
            {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   236
                PHYSFS_sint64 br;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   237
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   238
                br = entry->compressed_size - finfo->compressed_position;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   239
                if (br > 0)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   240
                {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   241
                    if (br > ZIP_READBUFSIZE)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   242
                        br = ZIP_READBUFSIZE;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   243
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   244
                    br = __PHYSFS_platformRead(finfo->handle,
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   245
                                               finfo->buffer,
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   246
                                               1, (PHYSFS_uint32) br);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   247
                    if (br <= 0)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   248
                        break;
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   249
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   250
                    finfo->compressed_position += (PHYSFS_uint32) br;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   251
                    finfo->stream.next_in = finfo->buffer;
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   252
                    finfo->stream.avail_in = (PHYSFS_uint32) br;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   253
                } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   254
            } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   255
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   256
            rc = zlib_err(inflate(&finfo->stream, Z_SYNC_FLUSH));
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   257
            retval += (finfo->stream.total_out - before);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   258
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   259
            if (rc != Z_OK)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   260
                break;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   261
        } /* while */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   262
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   263
        retval /= objSize;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   264
    } /* else */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   265
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   266
    if (retval > 0)
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   267
        finfo->uncompressed_position += (PHYSFS_uint32) (retval * objSize);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   268
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   269
    return retval;
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   270
} /* ZIP_read */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   271
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   272
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   273
static PHYSFS_sint64 ZIP_write(fvoid *opaque, const void *buf,
467
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   274
                               PHYSFS_uint32 objSize, PHYSFS_uint32 objCount)
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   275
{
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   276
    BAIL_MACRO(ERR_NOT_SUPPORTED, -1);
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   277
} /* ZIP_write */
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   278
99664d9842cb Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents: 464
diff changeset
   279
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   280
static int ZIP_eof(fvoid *opaque)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   281
{
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   282
    ZIPfileinfo *finfo = (ZIPfileinfo *) opaque;
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   283
    return (finfo->uncompressed_position >= finfo->entry->uncompressed_size);
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   284
} /* ZIP_eof */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   285
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   286
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   287
static PHYSFS_sint64 ZIP_tell(fvoid *opaque)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   288
{
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   289
    return ((ZIPfileinfo *) opaque)->uncompressed_position;
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   290
} /* ZIP_tell */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   291
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   292
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   293
static int ZIP_seek(fvoid *opaque, PHYSFS_uint64 offset)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   294
{
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   295
    ZIPfileinfo *finfo = (ZIPfileinfo *) opaque;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   296
    ZIPentry *entry = finfo->entry;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   297
    void *in = finfo->handle;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   298
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   299
    BAIL_IF_MACRO(offset > entry->uncompressed_size, ERR_PAST_EOF, 0);
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   300
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   301
    if (entry->compression_method == COMPMETH_NONE)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   302
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   303
        PHYSFS_sint64 newpos = offset + entry->offset;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   304
        BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, newpos), NULL, 0);
551
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   305
        finfo->uncompressed_position = (PHYSFS_uint32) offset;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   306
    } /* if */
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   307
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   308
    else
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   309
    {
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   310
        /*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   311
         * If seeking backwards, we need to redecode the file
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   312
         *  from the start and throw away the compressed bits until we hit
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   313
         *  the offset we need. If seeking forward, we still need to
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   314
         *  decode, but we don't rewind first.
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   315
         */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   316
        if (offset < finfo->uncompressed_position)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   317
        {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   318
            /* we do a copy so state is sane if inflateInit2() fails. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   319
            z_stream str;
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   320
            initializeZStream(&str);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   321
            if (zlib_err(inflateInit2(&str, -MAX_WBITS)) != Z_OK)
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   322
                return 0;
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   323
345
cbcb27547864 Seeking backwards in ZIP_seek() works now.
Ryan C. Gordon <icculus@icculus.org>
parents: 342
diff changeset
   324
            if (!__PHYSFS_platformSeek(in, entry->offset))
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   325
                return 0;
345
cbcb27547864 Seeking backwards in ZIP_seek() works now.
Ryan C. Gordon <icculus@icculus.org>
parents: 342
diff changeset
   326
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   327
            inflateEnd(&finfo->stream);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   328
            memcpy(&finfo->stream, &str, sizeof (z_stream));
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   329
            finfo->uncompressed_position = finfo->compressed_position = 0;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   330
        } /* if */
50
989b413188e5 Added individual file i/o code. Untested.
Ryan C. Gordon <icculus@icculus.org>
parents: 46
diff changeset
   331
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   332
        while (finfo->uncompressed_position != offset)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   333
        {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   334
            PHYSFS_uint8 buf[512];
540
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   335
            PHYSFS_uint32 maxread;
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   336
a6b6f0a54cd2 Attempt at type correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 538
diff changeset
   337
            maxread = (PHYSFS_uint32) (offset - finfo->uncompressed_position);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   338
            if (maxread > sizeof (buf))
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   339
                maxread = sizeof (buf);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   340
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   341
            if (ZIP_read(finfo, buf, maxread, 1) != 1)
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   342
                return 0;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   343
        } /* while */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   344
    } /* else */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   345
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   346
    return 1;
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   347
} /* ZIP_seek */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   348
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   349
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   350
static PHYSFS_sint64 ZIP_fileLength(fvoid *opaque)
28
529214f57d1b Added PHYSFS_fileLength(). Bleh.
Ryan C. Gordon <icculus@icculus.org>
parents: 22
diff changeset
   351
{
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   352
    ZIPfileinfo *finfo = (ZIPfileinfo *) opaque;
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   353
    return finfo->entry->uncompressed_size;
28
529214f57d1b Added PHYSFS_fileLength(). Bleh.
Ryan C. Gordon <icculus@icculus.org>
parents: 22
diff changeset
   354
} /* ZIP_fileLength */
529214f57d1b Added PHYSFS_fileLength(). Bleh.
Ryan C. Gordon <icculus@icculus.org>
parents: 22
diff changeset
   355
529214f57d1b Added PHYSFS_fileLength(). Bleh.
Ryan C. Gordon <icculus@icculus.org>
parents: 22
diff changeset
   356
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   357
static int ZIP_fileClose(fvoid *opaque)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   358
{
650
298b8bb26775 Did the same thing to FileHandles than I did to DirHandles, but this
Ryan C. Gordon <icculus@icculus.org>
parents: 648
diff changeset
   359
    ZIPfileinfo *finfo = (ZIPfileinfo *) opaque;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   360
    BAIL_IF_MACRO(!__PHYSFS_platformClose(finfo->handle), NULL, 0);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   361
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   362
    if (finfo->entry->compression_method != COMPMETH_NONE)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   363
        inflateEnd(&finfo->stream);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   364
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   365
    if (finfo->buffer != NULL)
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   366
        allocator.Free(finfo->buffer);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   367
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   368
    allocator.Free(finfo);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   369
    return 1;
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   370
} /* ZIP_fileClose */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   371
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   372
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   373
static PHYSFS_sint64 zip_find_end_of_central_dir(void *in, PHYSFS_sint64 *len)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   374
{
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   375
    PHYSFS_uint8 buf[256];
1085
1ad575ce53c8 Merged changeset 1084:ee3d2e6e1161 from stable-2.0: unitialized array fix.
Ryan C. Gordon <icculus@icculus.org>
parents: 1054
diff changeset
   376
    PHYSFS_uint8 extra[4] = { 0, 0, 0, 0 };
413
d669d303317d Initialized some variables to stop compiler whining.
Ryan C. Gordon <icculus@icculus.org>
parents: 402
diff changeset
   377
    PHYSFS_sint32 i = 0;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   378
    PHYSFS_sint64 filelen;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   379
    PHYSFS_sint64 filepos;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   380
    PHYSFS_sint32 maxread;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   381
    PHYSFS_sint32 totalread = 0;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   382
    int found = 0;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   383
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   384
    filelen = __PHYSFS_platformFileLength(in);
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   385
    BAIL_IF_MACRO(filelen == -1, NULL, 0);  /* !!! FIXME: unlocalized string */
541
2be2fff14b7a Another attempt at type size correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 540
diff changeset
   386
    BAIL_IF_MACRO(filelen > 0xFFFFFFFF, "ZIP bigger than 2 gigs?!", 0);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   387
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   388
    /*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   389
     * Jump to the end of the file and start reading backwards.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   390
     *  The last thing in the file is the zipfile comment, which is variable
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   391
     *  length, and the field that specifies its size is before it in the
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   392
     *  file (argh!)...this means that we need to scan backwards until we
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   393
     *  hit the end-of-central-dir signature. We can then sanity check that
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   394
     *  the comment was as big as it should be to make sure we're in the
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   395
     *  right place. The comment length field is 16 bits, so we can stop
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   396
     *  searching for that signature after a little more than 64k at most,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   397
     *  and call it a corrupted zipfile.
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   398
     */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   399
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   400
    if (sizeof (buf) < filelen)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   401
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   402
        filepos = filelen - sizeof (buf);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   403
        maxread = sizeof (buf);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   404
    } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   405
    else
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   406
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   407
        filepos = 0;
541
2be2fff14b7a Another attempt at type size correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 540
diff changeset
   408
        maxread = (PHYSFS_uint32) filelen;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   409
    } /* else */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   410
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   411
    while ((totalread < filelen) && (totalread < 65557))
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   412
    {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   413
        BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, filepos), NULL, -1);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   414
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   415
        /* make sure we catch a signature between buffers. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   416
        if (totalread != 0)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   417
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   418
            if (__PHYSFS_platformRead(in, buf, maxread - 4, 1) != 1)
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   419
                return -1;
996
0410dc655d45 Fixed strict-aliasing issue that gcc 4.4 complains about.
Ryan C. Gordon <icculus@icculus.org>
parents: 928
diff changeset
   420
            memcpy(&buf[maxread - 4], &extra, sizeof (extra));
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   421
            totalread += maxread - 4;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   422
        } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   423
        else
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   424
        {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   425
            if (__PHYSFS_platformRead(in, buf, maxread, 1) != 1)
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   426
                return -1;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   427
            totalread += maxread;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   428
        } /* else */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   429
996
0410dc655d45 Fixed strict-aliasing issue that gcc 4.4 complains about.
Ryan C. Gordon <icculus@icculus.org>
parents: 928
diff changeset
   430
        memcpy(&extra, buf, sizeof (extra));
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   431
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   432
        for (i = maxread - 4; i > 0; i--)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   433
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   434
            if ((buf[i + 0] == 0x50) &&
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   435
                (buf[i + 1] == 0x4B) &&
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   436
                (buf[i + 2] == 0x05) &&
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   437
                (buf[i + 3] == 0x06) )
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   438
            {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   439
                found = 1;  /* that's the signature! */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   440
                break;  
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   441
            } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   442
        } /* for */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   443
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   444
        if (found)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   445
            break;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   446
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   447
        filepos -= (maxread - 4);
895
8bf07c014a43 Fixed zip archiver: could do bogus seek if a small, non-zip file got put
Ryan C. Gordon <icculus@icculus.org>
parents: 894
diff changeset
   448
        if (filepos < 0)
8bf07c014a43 Fixed zip archiver: could do bogus seek if a small, non-zip file got put
Ryan C. Gordon <icculus@icculus.org>
parents: 894
diff changeset
   449
            filepos = 0;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   450
    } /* while */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   451
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   452
    BAIL_IF_MACRO(!found, ERR_NOT_AN_ARCHIVE, -1);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   453
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   454
    if (len != NULL)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   455
        *len = filelen;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   456
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   457
    return (filepos + i);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   458
} /* zip_find_end_of_central_dir */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   459
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   460
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   461
static int ZIP_isArchive(const char *filename, int forWriting)
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   462
{
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   463
    PHYSFS_uint32 sig;
446
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   464
    int retval = 0;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   465
    void *in;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   466
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   467
    in = __PHYSFS_platformOpenRead(filename);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   468
    BAIL_IF_MACRO(in == NULL, NULL, 0);
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   469
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   470
    /*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   471
     * The first thing in a zip file might be the signature of the
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   472
     *  first local file record, so it makes for a quick determination.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   473
     */
446
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   474
    if (readui32(in, &sig))
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   475
    {
446
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   476
        retval = (sig == ZIP_LOCAL_FILE_SIG);
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   477
        if (!retval)
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   478
        {
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   479
            /*
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   480
             * No sig...might be a ZIP with data at the start
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   481
             *  (a self-extracting executable, etc), so we'll have to do
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   482
             *  it the hard way...
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   483
             */
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   484
            retval = (zip_find_end_of_central_dir(in, NULL) != -1);
e1f7fe003b70 Fix for correct cleanup on read error.
Ryan C. Gordon <icculus@icculus.org>
parents: 429
diff changeset
   485
        } /* if */
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   486
    } /* if */
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   487
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   488
    __PHYSFS_platformClose(in);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   489
    return retval;
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   490
} /* ZIP_isArchive */
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   491
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   492
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   493
static void zip_free_entries(ZIPentry *entries, PHYSFS_uint32 max)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   494
{
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   495
    PHYSFS_uint32 i;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   496
    for (i = 0; i < max; i++)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   497
    {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   498
        ZIPentry *entry = &entries[i];
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   499
        if (entry->name != NULL)
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   500
            allocator.Free(entry->name);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   501
    } /* for */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   502
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   503
    allocator.Free(entries);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   504
} /* zip_free_entries */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   505
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   506
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   507
/*
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   508
 * This will find the ZIPentry associated with a path in platform-independent
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   509
 *  notation. Directories don't have ZIPentries associated with them, but 
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   510
 *  (*isDir) will be set to non-zero if a dir was hit.
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   511
 */
1054
57f4af811ffb THIS is Christoph's PHYSFS_stat() work.
Ryan C. Gordon <icculus@icculus.org>
parents: 1053
diff changeset
   512
static ZIPentry *zip_find_entry(const ZIPinfo *info, const char *path,
57f4af811ffb THIS is Christoph's PHYSFS_stat() work.
Ryan C. Gordon <icculus@icculus.org>
parents: 1053
diff changeset
   513
                                int *isDir)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   514
{
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   515
    ZIPentry *a = info->entries;
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   516
    PHYSFS_sint32 pathlen = strlen(path);
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   517
    PHYSFS_sint32 lo = 0;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   518
    PHYSFS_sint32 hi = (PHYSFS_sint32) (info->entryCount - 1);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   519
    PHYSFS_sint32 middle;
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   520
    const char *thispath = NULL;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   521
    int rc;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   522
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   523
    while (lo <= hi)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   524
    {
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   525
        middle = lo + ((hi - lo) / 2);
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   526
        thispath = a[middle].name;
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   527
        rc = strncmp(path, thispath, pathlen);
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   528
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   529
        if (rc > 0)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   530
            lo = middle + 1;
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   531
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   532
        else if (rc < 0)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   533
            hi = middle - 1;
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   534
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   535
        else /* substring match...might be dir or entry or nothing. */
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   536
        {
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   537
            if (isDir != NULL)
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   538
            {
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   539
                *isDir = (thispath[pathlen] == '/');
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   540
                if (*isDir)
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   541
                    return NULL;
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   542
            } /* if */
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   543
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   544
            if (thispath[pathlen] == '\0') /* found entry? */
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   545
                return &a[middle];
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   546
            else
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   547
                hi = middle - 1;  /* adjust search params, try again. */
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   548
        } /* if */
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
   549
    } /* while */
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   550
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   551
    if (isDir != NULL)
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   552
        *isDir = 0;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   553
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   554
    BAIL_MACRO(ERR_NO_SUCH_FILE, NULL);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   555
} /* zip_find_entry */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   556
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   557
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   558
/* Convert paths from old, buggy DOS zippers... */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   559
static void zip_convert_dos_path(ZIPentry *entry, char *path)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   560
{
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   561
    PHYSFS_uint8 hosttype = (PHYSFS_uint8) ((entry->version >> 8) & 0xFF);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   562
    if (hosttype == 0)  /* FS_FAT_ */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   563
    {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   564
        while (*path)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   565
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   566
            if (*path == '\\')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   567
                *path = '/';
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   568
            path++;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   569
        } /* while */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   570
    } /* if */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   571
} /* zip_convert_dos_path */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   572
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   573
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   574
static void zip_expand_symlink_path(char *path)
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   575
{
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   576
    char *ptr = path;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   577
    char *prevptr = path;
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   578
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   579
    while (1)
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   580
    {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   581
        ptr = strchr(ptr, '/');
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   582
        if (ptr == NULL)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   583
            break;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   584
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   585
        if (*(ptr + 1) == '.')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   586
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   587
            if (*(ptr + 2) == '/')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   588
            {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   589
                /* current dir in middle of string: ditch it. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   590
                memmove(ptr, ptr + 2, strlen(ptr + 2) + 1);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   591
            } /* else if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   592
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   593
            else if (*(ptr + 2) == '\0')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   594
            {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   595
                /* current dir at end of string: ditch it. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   596
                *ptr = '\0';
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   597
            } /* else if */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   598
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   599
            else if (*(ptr + 2) == '.')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   600
            {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   601
                if (*(ptr + 3) == '/')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   602
                {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   603
                    /* parent dir in middle: move back one, if possible. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   604
                    memmove(prevptr, ptr + 4, strlen(ptr + 4) + 1);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   605
                    ptr = prevptr;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   606
                    while (prevptr != path)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   607
                    {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   608
                        prevptr--;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   609
                        if (*prevptr == '/')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   610
                        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   611
                            prevptr++;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   612
                            break;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   613
                        } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   614
                    } /* while */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   615
                } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   616
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   617
                if (*(ptr + 3) == '\0')
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   618
                {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   619
                    /* parent dir at end: move back one, if possible. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   620
                    *prevptr = '\0';
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   621
                } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   622
            } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   623
        } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   624
        else
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   625
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   626
            prevptr = ptr;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   627
        } /* else */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   628
    } /* while */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   629
} /* zip_expand_symlink_path */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   630
658
1981818c6170 Removed all the forward declaration cruft from the archivers.
Ryan C. Gordon <icculus@icculus.org>
parents: 657
diff changeset
   631
/* (forward reference: zip_follow_symlink and zip_resolve call each other.) */
1981818c6170 Removed all the forward declaration cruft from the archivers.
Ryan C. Gordon <icculus@icculus.org>
parents: 657
diff changeset
   632
static int zip_resolve(void *in, ZIPinfo *info, ZIPentry *entry);
32
09a8197fad3b Initial work on ZIPfile support. Not complete. Not very pleased with this
Ryan C. Gordon <icculus@icculus.org>
parents: 29
diff changeset
   633
143
337505f94c10 Platform abstracted i/o, other bugfixes.
Ryan C. Gordon <icculus@icculus.org>
parents: 132
diff changeset
   634
/*
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   635
 * Look for the entry named by (path). If it exists, resolve it, and return
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   636
 *  a pointer to that entry. If it's another symlink, keep resolving until you
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   637
 *  hit a real file and then return a pointer to the final non-symlink entry.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   638
 *  If there's a problem, return NULL. (path) is always free()'d by this
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   639
 *  function.
143
337505f94c10 Platform abstracted i/o, other bugfixes.
Ryan C. Gordon <icculus@icculus.org>
parents: 132
diff changeset
   640
 */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   641
static ZIPentry *zip_follow_symlink(void *in, ZIPinfo *info, char *path)
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   642
{
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   643
    ZIPentry *entry;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   644
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   645
    zip_expand_symlink_path(path);
483
d788c84d8694 Fixed bug that prevented use when symlinks were disallowed.
Ryan C. Gordon <icculus@icculus.org>
parents: 478
diff changeset
   646
    entry = zip_find_entry(info, path, NULL);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   647
    if (entry != NULL)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   648
    {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   649
        if (!zip_resolve(in, info, entry))  /* recursive! */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   650
            entry = NULL;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   651
        else
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   652
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   653
            if (entry->symlink != NULL)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   654
                entry = entry->symlink;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   655
        } /* else */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   656
    } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   657
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   658
    allocator.Free(path);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   659
    return entry;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   660
} /* zip_follow_symlink */
20
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   661
efdde0d21521 Implementation compiles and links with no actual archive support. No test
Ryan C. Gordon <icculus@icculus.org>
parents: 17
diff changeset
   662
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   663
static int zip_resolve_symlink(void *in, ZIPinfo *info, ZIPentry *entry)
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   664
{
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   665
    char *path;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   666
    PHYSFS_uint32 size = entry->uncompressed_size;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   667
    int rc = 0;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   668
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   669
    /*
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   670
     * We've already parsed the local file header of the symlink at this
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   671
     *  point. Now we need to read the actual link from the file data and
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   672
     *  follow it.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   673
     */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   674
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   675
    BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, entry->offset), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   676
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   677
    path = (char *) allocator.Malloc(size + 1);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   678
    BAIL_IF_MACRO(path == NULL, ERR_OUT_OF_MEMORY, 0);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   679
    
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   680
    if (entry->compression_method == COMPMETH_NONE)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   681
        rc = (__PHYSFS_platformRead(in, path, size, 1) == 1);
143
337505f94c10 Platform abstracted i/o, other bugfixes.
Ryan C. Gordon <icculus@icculus.org>
parents: 132
diff changeset
   682
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   683
    else  /* symlink target path is compressed... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   684
    {
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   685
        z_stream stream;
852
9467e96abdf1 Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents: 809
diff changeset
   686
        PHYSFS_uint32 complen = entry->compressed_size;
9467e96abdf1 Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents: 809
diff changeset
   687
        PHYSFS_uint8 *compressed = (PHYSFS_uint8*) __PHYSFS_smallAlloc(complen);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   688
        if (compressed != NULL)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   689
        {
852
9467e96abdf1 Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents: 809
diff changeset
   690
            if (__PHYSFS_platformRead(in, compressed, complen, 1) == 1)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   691
            {
644
1cb5533d369c Initial structure for replacable allocator work.
Ryan C. Gordon <icculus@icculus.org>
parents: 579
diff changeset
   692
                initializeZStream(&stream);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   693
                stream.next_in = compressed;
852
9467e96abdf1 Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents: 809
diff changeset
   694
                stream.avail_in = complen;
538
8752e3c0dbf9 Now compiles on CodeWarrior 6 for MacOS Classic again.
Ryan C. Gordon <icculus@icculus.org>
parents: 504
diff changeset
   695
                stream.next_out = (unsigned char *) path;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   696
                stream.avail_out = size;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   697
                if (zlib_err(inflateInit2(&stream, -MAX_WBITS)) == Z_OK)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   698
                {
340
24a11f8566f8 Symlink fixes. Still broken, though.
Ryan C. Gordon <icculus@icculus.org>
parents: 337
diff changeset
   699
                    rc = zlib_err(inflate(&stream, Z_FINISH));
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   700
                    inflateEnd(&stream);
340
24a11f8566f8 Symlink fixes. Still broken, though.
Ryan C. Gordon <icculus@icculus.org>
parents: 337
diff changeset
   701
24a11f8566f8 Symlink fixes. Still broken, though.
Ryan C. Gordon <icculus@icculus.org>
parents: 337
diff changeset
   702
                    /* both are acceptable outcomes... */
24a11f8566f8 Symlink fixes. Still broken, though.
Ryan C. Gordon <icculus@icculus.org>
parents: 337
diff changeset
   703
                    rc = ((rc == Z_OK) || (rc == Z_STREAM_END));
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   704
                } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   705
            } /* if */
852
9467e96abdf1 Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents: 809
diff changeset
   706
            __PHYSFS_smallFree(compressed);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   707
        } /* if */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   708
    } /* else */
143
337505f94c10 Platform abstracted i/o, other bugfixes.
Ryan C. Gordon <icculus@icculus.org>
parents: 132
diff changeset
   709
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   710
    if (!rc)
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   711
        allocator.Free(path);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   712
    else
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   713
    {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   714
        path[entry->uncompressed_size] = '\0';    /* null-terminate it. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   715
        zip_convert_dos_path(entry, path);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   716
        entry->symlink = zip_follow_symlink(in, info, path);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   717
    } /* else */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   718
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   719
    return (entry->symlink != NULL);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   720
} /* zip_resolve_symlink */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   721
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   722
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   723
/*
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   724
 * Parse the local file header of an entry, and update entry->offset.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   725
 */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   726
static int zip_parse_local(void *in, ZIPentry *entry)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   727
{
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   728
    PHYSFS_uint32 ui32;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   729
    PHYSFS_uint16 ui16;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   730
    PHYSFS_uint16 fnamelen;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   731
    PHYSFS_uint16 extralen;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   732
551
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   733
    /*
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   734
     * crc and (un)compressed_size are always zero if this is a "JAR"
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   735
     *  archive created with Sun's Java tools, apparently. We only
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   736
     *  consider this archive corrupted if those entries don't match and
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   737
     *  aren't zero. That seems to work well.
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   738
     */
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   739
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   740
    BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, entry->offset), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   741
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   742
    BAIL_IF_MACRO(ui32 != ZIP_LOCAL_FILE_SIG, ERR_CORRUPTED, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   743
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   744
    BAIL_IF_MACRO(ui16 != entry->version_needed, ERR_CORRUPTED, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   745
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);  /* general bits. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   746
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   747
    BAIL_IF_MACRO(ui16 != entry->compression_method, ERR_CORRUPTED, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   748
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);  /* date/time */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   749
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
551
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   750
    BAIL_IF_MACRO(ui32 && (ui32 != entry->crc), ERR_CORRUPTED, 0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   751
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
551
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   752
    BAIL_IF_MACRO(ui32 && (ui32 != entry->compressed_size), ERR_CORRUPTED, 0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   753
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
551
f0fc464fd51b Fixed seeking in uncompressed zip entries and handle Java-created JAR files.
Ryan C. Gordon <icculus@icculus.org>
parents: 541
diff changeset
   754
    BAIL_IF_MACRO(ui32 && (ui32 != entry->uncompressed_size),ERR_CORRUPTED,0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   755
    BAIL_IF_MACRO(!readui16(in, &fnamelen), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   756
    BAIL_IF_MACRO(!readui16(in, &extralen), NULL, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   757
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   758
    entry->offset += fnamelen + extralen + 30;
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   759
    return 1;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   760
} /* zip_parse_local */
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   761
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   762
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   763
static int zip_resolve(void *in, ZIPinfo *info, ZIPentry *entry)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   764
{
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   765
    int retval = 1;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   766
    ZipResolveType resolve_type = entry->resolved;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   767
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   768
    /* Don't bother if we've failed to resolve this entry before. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   769
    BAIL_IF_MACRO(resolve_type == ZIP_BROKEN_FILE, ERR_CORRUPTED, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   770
    BAIL_IF_MACRO(resolve_type == ZIP_BROKEN_SYMLINK, ERR_CORRUPTED, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   771
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   772
    /* uhoh...infinite symlink loop! */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   773
    BAIL_IF_MACRO(resolve_type == ZIP_RESOLVING, ERR_SYMLINK_LOOP, 0);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   774
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   775
    /*
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   776
     * We fix up the offset to point to the actual data on the
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   777
     *  first open, since we don't want to seek across the whole file on
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   778
     *  archive open (can be SLOW on large, CD-stored files), but we
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   779
     *  need to check the local file header...not just for corruption,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   780
     *  but since it stores offset info the central directory does not.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   781
     */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   782
    if (resolve_type != ZIP_RESOLVED)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   783
    {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   784
        entry->resolved = ZIP_RESOLVING;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   785
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   786
        retval = zip_parse_local(in, entry);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   787
        if (retval)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   788
        {
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   789
            /*
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   790
             * If it's a symlink, find the original file. This will cause
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   791
             *  resolution of other entries (other symlinks and, eventually,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   792
             *  the real file) if all goes well.
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   793
             */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   794
            if (resolve_type == ZIP_UNRESOLVED_SYMLINK)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   795
                retval = zip_resolve_symlink(in, info, entry);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   796
        } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   797
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   798
        if (resolve_type == ZIP_UNRESOLVED_SYMLINK)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   799
            entry->resolved = ((retval) ? ZIP_RESOLVED : ZIP_BROKEN_SYMLINK);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   800
        else if (resolve_type == ZIP_UNRESOLVED_FILE)
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   801
            entry->resolved = ((retval) ? ZIP_RESOLVED : ZIP_BROKEN_FILE);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   802
    } /* if */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   803
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   804
    return retval;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   805
} /* zip_resolve */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   806
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   807
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   808
static int zip_version_does_symlinks(PHYSFS_uint32 version)
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   809
{
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   810
    int retval = 0;
163
fc2b8ee5b420 Approved zeph's comments, fixed a few of my screwups.
Ryan C. Gordon <icculus@icculus.org>
parents: 161
diff changeset
   811
    PHYSFS_uint8 hosttype = (PHYSFS_uint8) ((version >> 8) & 0xFF);
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   812
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   813
    switch (hosttype)
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   814
    {
342
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   815
            /*
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   816
             * These are the platforms that can NOT build an archive with
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   817
             *  symlinks, according to the Info-ZIP project.
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   818
             */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   819
        case 0:  /* FS_FAT_  */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   820
        case 1:  /* AMIGA_   */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   821
        case 2:  /* VMS_     */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   822
        case 4:  /* VM_CSM_  */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   823
        case 6:  /* FS_HPFS_ */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   824
        case 11: /* FS_NTFS_ */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   825
        case 14: /* FS_VFAT_ */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   826
        case 13: /* ACORN_   */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   827
        case 15: /* MVS_     */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   828
        case 18: /* THEOS_   */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   829
            break;  /* do nothing. */
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   830
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   831
        default:  /* assume the rest to be unix-like. */
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   832
            retval = 1;
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   833
            break;
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   834
    } /* switch */
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   835
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   836
    return retval;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   837
} /* zip_version_does_symlinks */
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   838
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   839
894
6d152b4900ea Minor const correctness tweak in zip archiver.
Ryan C. Gordon <icculus@icculus.org>
parents: 852
diff changeset
   840
static int zip_entry_is_symlink(const ZIPentry *entry)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   841
{
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   842
    return ((entry->resolved == ZIP_UNRESOLVED_SYMLINK) ||
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   843
            (entry->resolved == ZIP_BROKEN_SYMLINK) ||
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   844
            (entry->symlink));
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   845
} /* zip_entry_is_symlink */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   846
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   847
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   848
static int zip_has_symlink_attr(ZIPentry *entry, PHYSFS_uint32 extern_attr)
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   849
{
342
cef50576cb0b Fixed symlink detection.
Ryan C. Gordon <icculus@icculus.org>
parents: 340
diff changeset
   850
    PHYSFS_uint16 xattr = ((extern_attr >> 16) & 0xFFFF);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   851
    return ( (zip_version_does_symlinks(entry->version)) &&
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   852
             (entry->uncompressed_size > 0) &&
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   853
             ((xattr & UNIX_FILETYPE_MASK) == UNIX_FILETYPE_SYMLINK) );
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   854
} /* zip_has_symlink_attr */
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   855
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   856
538
8752e3c0dbf9 Now compiles on CodeWarrior 6 for MacOS Classic again.
Ryan C. Gordon <icculus@icculus.org>
parents: 504
diff changeset
   857
static PHYSFS_sint64 zip_dos_time_to_physfs_time(PHYSFS_uint32 dostime)
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   858
{
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   859
#ifdef _WIN32_WCE
578
bff1af8455ca Tabs-to-spaces patch by James Turk.
Ryan C. Gordon <icculus@icculus.org>
parents: 566
diff changeset
   860
    /* We have no struct tm and no mktime right now.
bff1af8455ca Tabs-to-spaces patch by James Turk.
Ryan C. Gordon <icculus@icculus.org>
parents: 566
diff changeset
   861
       FIXME: This should probably be fixed at some point.
bff1af8455ca Tabs-to-spaces patch by James Turk.
Ryan C. Gordon <icculus@icculus.org>
parents: 566
diff changeset
   862
    */
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   863
    return -1;
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   864
#else
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   865
    PHYSFS_uint32 dosdate;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   866
    struct tm unixtime;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   867
    memset(&unixtime, '\0', sizeof (unixtime));
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   868
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   869
    dosdate = (PHYSFS_uint32) ((dostime >> 16) & 0xFFFF);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   870
    dostime &= 0xFFFF;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   871
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   872
    /* dissect date */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   873
    unixtime.tm_year = ((dosdate >> 9) & 0x7F) + 80;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   874
    unixtime.tm_mon  = ((dosdate >> 5) & 0x0F) - 1;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   875
    unixtime.tm_mday = ((dosdate     ) & 0x1F);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   876
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   877
    /* dissect time */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   878
    unixtime.tm_hour = ((dostime >> 11) & 0x1F);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   879
    unixtime.tm_min  = ((dostime >>  5) & 0x3F);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   880
    unixtime.tm_sec  = ((dostime <<  1) & 0x3E);
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   881
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   882
    /* let mktime calculate daylight savings time. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   883
    unixtime.tm_isdst = -1;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   884
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   885
    return ((PHYSFS_sint64) mktime(&unixtime));
566
1e640d4acab9 PocketPC fixes (thanks, David Hedbor!)
Ryan C. Gordon <icculus@icculus.org>
parents: 551
diff changeset
   886
#endif
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   887
} /* zip_dos_time_to_physfs_time */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   888
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   889
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   890
static int zip_load_entry(void *in, ZIPentry *entry, PHYSFS_uint32 ofs_fixup)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   891
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   892
    PHYSFS_uint16 fnamelen, extralen, commentlen;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   893
    PHYSFS_uint32 external_attr;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   894
    PHYSFS_uint16 ui16;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   895
    PHYSFS_uint32 ui32;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   896
    PHYSFS_sint64 si64;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   897
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   898
    /* sanity check with central directory signature... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   899
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   900
    BAIL_IF_MACRO(ui32 != ZIP_CENTRAL_DIR_SIG, ERR_CORRUPTED, 0);
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   901
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   902
    /* Get the pertinent parts of the record... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   903
    BAIL_IF_MACRO(!readui16(in, &entry->version), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   904
    BAIL_IF_MACRO(!readui16(in, &entry->version_needed), NULL, 0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   905
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);  /* general bits */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   906
    BAIL_IF_MACRO(!readui16(in, &entry->compression_method), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   907
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   908
    entry->last_mod_time = zip_dos_time_to_physfs_time(ui32);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   909
    BAIL_IF_MACRO(!readui32(in, &entry->crc), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   910
    BAIL_IF_MACRO(!readui32(in, &entry->compressed_size), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   911
    BAIL_IF_MACRO(!readui32(in, &entry->uncompressed_size), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   912
    BAIL_IF_MACRO(!readui16(in, &fnamelen), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   913
    BAIL_IF_MACRO(!readui16(in, &extralen), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   914
    BAIL_IF_MACRO(!readui16(in, &commentlen), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   915
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);  /* disk number start */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   916
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);  /* internal file attribs */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   917
    BAIL_IF_MACRO(!readui32(in, &external_attr), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   918
    BAIL_IF_MACRO(!readui32(in, &entry->offset), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   919
    entry->offset += ofs_fixup;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   920
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   921
    entry->symlink = NULL;  /* will be resolved later, if necessary. */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   922
    entry->resolved = (zip_has_symlink_attr(entry, external_attr)) ?
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   923
                            ZIP_UNRESOLVED_SYMLINK : ZIP_UNRESOLVED_FILE;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   924
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   925
    entry->name = (char *) allocator.Malloc(fnamelen + 1);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   926
    BAIL_IF_MACRO(entry->name == NULL, ERR_OUT_OF_MEMORY, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   927
    if (__PHYSFS_platformRead(in, entry->name, fnamelen, 1) != 1)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   928
        goto zip_load_entry_puked;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   929
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   930
    entry->name[fnamelen] = '\0';  /* null-terminate the filename. */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   931
    zip_convert_dos_path(entry, entry->name);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   932
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   933
    si64 = __PHYSFS_platformTell(in);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   934
    if (si64 == -1)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   935
        goto zip_load_entry_puked;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   936
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   937
        /* seek to the start of the next entry in the central directory... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   938
    if (!__PHYSFS_platformSeek(in, si64 + extralen + commentlen))
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   939
        goto zip_load_entry_puked;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   940
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   941
    return 1;  /* success. */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   942
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   943
zip_load_entry_puked:
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   944
    allocator.Free(entry->name);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   945
    return 0;  /* failure. */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   946
} /* zip_load_entry */
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   947
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   948
464
21c8e0d1578c Generalized sorting routines, and removed individual implementations.
Ryan C. Gordon <icculus@icculus.org>
parents: 446
diff changeset
   949
static int zip_entry_cmp(void *_a, PHYSFS_uint32 one, PHYSFS_uint32 two)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   950
{
928
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   951
    if (one != two)
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   952
    {
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   953
        const ZIPentry *a = (const ZIPentry *) _a;
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   954
        return strcmp(a[one].name, a[two].name);
928
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   955
    } /* if */
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   956
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   957
    return 0;
464
21c8e0d1578c Generalized sorting routines, and removed individual implementations.
Ryan C. Gordon <icculus@icculus.org>
parents: 446
diff changeset
   958
} /* zip_entry_cmp */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   959
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   960
464
21c8e0d1578c Generalized sorting routines, and removed individual implementations.
Ryan C. Gordon <icculus@icculus.org>
parents: 446
diff changeset
   961
static void zip_entry_swap(void *_a, PHYSFS_uint32 one, PHYSFS_uint32 two)
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   962
{
928
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   963
    if (one != two)
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   964
    {
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   965
        ZIPentry tmp;
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   966
        ZIPentry *first = &(((ZIPentry *) _a)[one]);
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   967
        ZIPentry *second = &(((ZIPentry *) _a)[two]);
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   968
        memcpy(&tmp, first, sizeof (ZIPentry));
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   969
        memcpy(first, second, sizeof (ZIPentry));
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   970
        memcpy(second, &tmp, sizeof (ZIPentry));
0e37b8163248 Various archiver swap and compare functions now check if they are
Ryan C. Gordon <icculus@icculus.org>
parents: 895
diff changeset
   971
    } /* if */
464
21c8e0d1578c Generalized sorting routines, and removed individual implementations.
Ryan C. Gordon <icculus@icculus.org>
parents: 446
diff changeset
   972
} /* zip_entry_swap */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   973
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   974
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
   975
static int zip_load_entries(void *in, ZIPinfo *info,
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   976
                            PHYSFS_uint32 data_ofs, PHYSFS_uint32 central_ofs)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   977
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   978
    PHYSFS_uint32 max = info->entryCount;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   979
    PHYSFS_uint32 i;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   980
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   981
    BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, central_ofs), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
   982
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
   983
    info->entries = (ZIPentry *) allocator.Malloc(sizeof (ZIPentry) * max);
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   984
    BAIL_IF_MACRO(info->entries == NULL, ERR_OUT_OF_MEMORY, 0);
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   985
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   986
    for (i = 0; i < max; i++)
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   987
    {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   988
        if (!zip_load_entry(in, &info->entries[i], data_ofs))
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   989
        {
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   990
            zip_free_entries(info->entries, i);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   991
            return 0;
46
66d9a112b0f7 Now with all directory functions implemented (and debugged?). No file
Ryan C. Gordon <icculus@icculus.org>
parents: 41
diff changeset
   992
        } /* if */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   993
    } /* for */
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   994
464
21c8e0d1578c Generalized sorting routines, and removed individual implementations.
Ryan C. Gordon <icculus@icculus.org>
parents: 446
diff changeset
   995
    __PHYSFS_sort(info->entries, max, zip_entry_cmp, zip_entry_swap);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
   996
    return 1;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
   997
} /* zip_load_entries */
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   998
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
   999
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1000
static int zip_parse_end_of_central_dir(void *in, ZIPinfo *info,
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1001
                                        PHYSFS_uint32 *data_start,
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1002
                                        PHYSFS_uint32 *central_dir_ofs)
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
  1003
{
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1004
    PHYSFS_uint32 ui32;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1005
    PHYSFS_uint16 ui16;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1006
    PHYSFS_sint64 len;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1007
    PHYSFS_sint64 pos;
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1008
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1009
    /* find the end-of-central-dir record, and seek to it. */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1010
    pos = zip_find_end_of_central_dir(in, &len);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1011
    BAIL_IF_MACRO(pos == -1, NULL, 0);
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1012
    BAIL_IF_MACRO(!__PHYSFS_platformSeek(in, pos), NULL, 0);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1013
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1014
    /* check signature again, just in case. */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1015
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1016
    BAIL_IF_MACRO(ui32 != ZIP_END_OF_CENTRAL_DIR_SIG, ERR_NOT_AN_ARCHIVE, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1017
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1018
    /* number of this disk */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1019
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1020
    BAIL_IF_MACRO(ui16 != 0, ERR_UNSUPPORTED_ARCHIVE, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1021
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1022
    /* number of the disk with the start of the central directory */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1023
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1024
    BAIL_IF_MACRO(ui16 != 0, ERR_UNSUPPORTED_ARCHIVE, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1025
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1026
    /* total number of entries in the central dir on this disk */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1027
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1028
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1029
    /* total number of entries in the central dir */
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1030
    BAIL_IF_MACRO(!readui16(in, &info->entryCount), NULL, 0);
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1031
    BAIL_IF_MACRO(ui16 != info->entryCount, ERR_UNSUPPORTED_ARCHIVE, 0);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1032
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1033
    /* size of the central directory */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1034
    BAIL_IF_MACRO(!readui32(in, &ui32), NULL, 0);
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
  1035
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1036
    /* offset of central directory */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1037
    BAIL_IF_MACRO(!readui32(in, central_dir_ofs), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1038
    BAIL_IF_MACRO(pos < *central_dir_ofs + ui32, ERR_UNSUPPORTED_ARCHIVE, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1039
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1040
    /*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1041
     * For self-extracting archives, etc, there's crapola in the file
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1042
     *  before the zipfile records; we calculate how much data there is
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1043
     *  prepended by determining how far the central directory offset is
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1044
     *  from where it is supposed to be (start of end-of-central-dir minus
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1045
     *  sizeof central dir)...the difference in bytes is how much arbitrary
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1046
     *  data is at the start of the physical file.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1047
     */
541
2be2fff14b7a Another attempt at type size correctness.
Ryan C. Gordon <icculus@icculus.org>
parents: 540
diff changeset
  1048
    *data_start = (PHYSFS_uint32) (pos - (*central_dir_ofs + ui32));
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1049
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1050
    /* Now that we know the difference, fix up the central dir offset... */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1051
    *central_dir_ofs += *data_start;
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
  1052
491
b8853d8a09cb Fixed infinite loop bug, cleaned out tab chars.
Ryan C. Gordon <icculus@icculus.org>
parents: 483
diff changeset
  1053
    /* zipfile comment length */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1054
    BAIL_IF_MACRO(!readui16(in, &ui16), NULL, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1055
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1056
    /*
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1057
     * Make sure that the comment length matches to the end of file...
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1058
     *  If it doesn't, we're either in the wrong part of the file, or the
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1059
     *  file is corrupted, but we give up either way.
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1060
     */
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1061
    BAIL_IF_MACRO((pos + 22 + ui16) != len, ERR_UNSUPPORTED_ARCHIVE, 0);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1062
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
  1063
    return 1;  /* made it. */
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1064
} /* zip_parse_end_of_central_dir */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1065
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1066
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1067
static ZIPinfo *zip_create_zipinfo(const char *name)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1068
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1069
    char *ptr;
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
  1070
    ZIPinfo *info = (ZIPinfo *) allocator.Malloc(sizeof (ZIPinfo));
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1071
    BAIL_IF_MACRO(info == NULL, ERR_OUT_OF_MEMORY, 0);
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1072
    memset(info, '\0', sizeof (ZIPinfo));
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1073
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
  1074
    ptr = (char *) allocator.Malloc(strlen(name) + 1);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1075
    if (ptr == NULL)
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1076
    {
691
71d9affe0d8a All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents: 658
diff changeset
  1077
        allocator.Free(info);
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1078
        BAIL_MACRO(ERR_OUT_OF_MEMORY, NULL);
53
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
  1079
    } /* if */
6c3c990f006e ZIP entries are now cached at openArchive time, which cleans up the race
Ryan C. Gordon <icculus@icculus.org>
parents: 52
diff changeset
  1080
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1081
    info->archiveName = ptr;
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1082
    strcpy(info->archiveName, name);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset
  1083
    return info;
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1084
} /* zip_create_zipinfo */
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1085
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1086
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1087
static void *ZIP_openArchive(const char *name, int forWriting)
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1088
{
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1089
    void *in = NULL;
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1090
    ZIPinfo *info = NULL;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1091
    PHYSFS_uint32 data_start;
365
3d087cde1252 My rewrite continues. I'm mostly satisfied with this code now, minus debugging.
Ryan C. Gordon <icculus@icculus.org>
parents: 345
diff changeset
  1092
    PHYSFS_uint32 cent_dir_ofs;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1093
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1094
    BAIL_IF_MACRO(forWriting, ERR_ARC_IS_READ_ONLY, NULL);
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1095
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1096
    if ((in = __PHYSFS_platformOpenRead(name)) == NULL)
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1097
        goto zip_openarchive_failed;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1098
    
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1099
    if ((info = zip_create_zipinfo(name)) == NULL)
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1100
        goto zip_openarchive_failed;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1101
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1102
    if (!zip_parse_end_of_central_dir(in, info, &data_start, &cent_dir_ofs))
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1103
        goto zip_openarchive_failed;
337
28500f02eb87 ZIP archiver rewrite.
Ryan C. Gordon <icculus@icculus.org>
parents: 335
diff changeset
  1104
648
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1105
    if (!zip_load_entries(in, info, data_start, cent_dir_ofs))
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1106
        goto zip_openarchive_failed;
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1107
5c993684b8f2 Cleaned up archiver interface to not deal with DirHandles anymore,
Ryan C. Gordon <icculus@icculus.org>
parents: 646
diff changeset
  1108
    __PHYSFS_platformClose(in);
1016
957c97389257 Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents: 997
diff changeset