3 * Copyright (C) 2006 Exophase <exophase@gmail.com>
4 * Copyright (C) 2006 SiberianSTAR
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License as
8 * published by the Free Software Foundation; either version 2 of
9 * the License, or (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
24 #define ZIP_BUFFER_SIZE (128 * 1024)
26 struct SZIPFileDataDescriptor
31 } __attribute__((packed));
35 char Sig[4]; // EDIT: Used to be s32 Sig;
38 s16 CompressionMethod;
41 struct SZIPFileDataDescriptor DataDescriptor;
44 } __attribute__((packed));
46 u32 load_file_zip(char *filename)
48 struct SZIPFileHeader data;
56 file_open(fd, filename, read);
58 if(!file_check_valid(fd))
63 ret = file_read(fd, &data, sizeof(data));
64 if (ret != sizeof(data))
67 // It checks for the following: 0x50 0x4B 0x03 0x04 (PK..)
68 if( data.Sig[0] != 0x50 || data.Sig[1] != 0x4B ||
69 data.Sig[2] != 0x03 || data.Sig[3] != 0x04 )
74 ret = file_read(fd, tmp, data.FilenameLength);
75 if (ret != data.FilenameLength)
78 tmp[data.FilenameLength] = 0; // end string
80 if(data.ExtraFieldLength)
81 file_seek(fd, data.ExtraFieldLength, SEEK_CUR);
83 if(data.GeneralBitFlag & 0x0008)
85 file_read(fd, &data.DataDescriptor,
86 sizeof(struct SZIPFileDataDescriptor));
89 ext = strrchr(tmp, '.') + 1;
92 if(data.DataDescriptor.UncompressedSize > gamepak_ram_buffer_size)
95 if(!strcasecmp(ext, "bin") || !strcasecmp(ext, "gba"))
100 switch(data.CompressionMethod)
103 retval = data.DataDescriptor.UncompressedSize;
104 file_read(fd, buffer, retval);
112 cbuffer = malloc(ZIP_BUFFER_SIZE);
114 stream.next_in = (Bytef*)cbuffer;
115 stream.avail_in = (u32)ZIP_BUFFER_SIZE;
117 stream.next_out = (Bytef*)buffer;
119 // EDIT: Now uses proper conversion of data types for retval.
120 retval = (u32)data.DataDescriptor.UncompressedSize;
121 stream.avail_out = data.DataDescriptor.UncompressedSize;
123 stream.zalloc = (alloc_func)0;
124 stream.zfree = (free_func)0;
126 err = inflateInit2(&stream, -MAX_WBITS);
128 file_read(fd, cbuffer, ZIP_BUFFER_SIZE);
132 while(err != Z_STREAM_END)
134 err = inflate(&stream, Z_SYNC_FLUSH);
135 if(err == Z_BUF_ERROR)
137 stream.avail_in = ZIP_BUFFER_SIZE;
138 stream.next_in = (Bytef*)cbuffer;
139 file_read(fd, cbuffer, ZIP_BUFFER_SIZE);
152 file_seek(fd, data.DataDescriptor.CompressedSize, SEEK_CUR);