summaryrefslogtreecommitdiff
path: root/thirdparty/minizip/godot-zlib-1.2.4-minizip-seek.patch
blob: 2162bafbbc54fad65f7b997f529448baa149da08 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
diff --git a/thirdparty/minizip/ioapi.c b/thirdparty/minizip/ioapi.c
index 49958f61f..0afbdc06a 100644
--- a/thirdparty/minizip/ioapi.c
+++ b/thirdparty/minizip/ioapi.c
@@ -68,8 +68,15 @@ void fill_zlib_filefunc64_32_def_from_filefunc32(zlib_filefunc64_32_def* p_filef
     p_filefunc64_32->zfile_func64.opaque = p_filefunc32->opaque;
     p_filefunc64_32->zseek32_file = p_filefunc32->zseek_file;
     p_filefunc64_32->ztell32_file = p_filefunc32->ztell_file;
+    /* GODOT start */
+    p_filefunc64_32->zfile_func64.alloc_mem = p_filefunc32->alloc_mem;
+    p_filefunc64_32->zfile_func64.free_mem = p_filefunc32->free_mem;
+    /* GODOT end */
 }
 
+/* GODOT start */
+/*
+// GODOT end
 
 
 static voidpf  ZCALLBACK fopen_file_func OF((voidpf opaque, const char* filename, int mode));
@@ -233,3 +240,6 @@ void fill_fopen64_filefunc (zlib_filefunc64_def*  pzlib_filefunc_def)
     pzlib_filefunc_def->zerror_file = ferror_file_func;
     pzlib_filefunc_def->opaque = NULL;
 }
+// GODOT start
+*/
+/* GODOT end */
diff --git a/thirdparty/minizip/ioapi.h b/thirdparty/minizip/ioapi.h
index 8309c4cf8..f25ab6464 100644
--- a/thirdparty/minizip/ioapi.h
+++ b/thirdparty/minizip/ioapi.h
@@ -145,6 +145,10 @@ typedef struct zlib_filefunc_def_s
     close_file_func     zclose_file;
     testerror_file_func zerror_file;
     voidpf              opaque;
+    /* GODOT start */
+    alloc_func          alloc_mem;
+    free_func           free_mem;
+    /* GODOT end */
 } zlib_filefunc_def;
 
 typedef ZPOS64_T (ZCALLBACK *tell64_file_func)    OF((voidpf opaque, voidpf stream));
@@ -161,6 +165,10 @@ typedef struct zlib_filefunc64_def_s
     close_file_func     zclose_file;
     testerror_file_func zerror_file;
     voidpf              opaque;
+    /* GODOT start */
+    alloc_func          alloc_mem;
+    free_func           free_mem;
+    /* GODOT end */
 } zlib_filefunc64_def;
 
 void fill_fopen64_filefunc OF((zlib_filefunc64_def* pzlib_filefunc_def));
diff --git a/thirdparty/minizip/unzip.c b/thirdparty/minizip/unzip.c
index 7617f41f1..32e27bd65 100644
--- a/thirdparty/minizip/unzip.c
+++ b/thirdparty/minizip/unzip.c
@@ -157,6 +157,9 @@ typedef struct
     uLong compression_method;   /* compression method (0==store) */
     ZPOS64_T byte_before_the_zipfile;/* byte before the zipfile, (>0 for sfx)*/
     int   raw;
+    /* GODOT start */
+    int extra_size;
+    /* GODOT end */
 } file_in_zip64_read_info_s;
 
 
@@ -606,9 +609,10 @@ local unzFile unzOpenInternal (const void *path,
     us.z_filefunc.zseek32_file = NULL;
     us.z_filefunc.ztell32_file = NULL;
     if (pzlib_filefunc64_32_def==NULL)
-        fill_fopen64_filefunc(&us.z_filefunc.zfile_func64);
-    else
-        us.z_filefunc = *pzlib_filefunc64_32_def;
+        /* GODOT start */
+        return NULL; // standard i/o not supported
+    us.z_filefunc = *pzlib_filefunc64_32_def;
+    /* GODOT end */
     us.is64bitOpenFunction = is64bitOpenFunction;
 
 
@@ -800,6 +804,18 @@ extern unzFile ZEXPORT unzOpen64 (const void *path)
     return unzOpenInternal(path, NULL, 1);
 }
 
+/* GODOT start */
+extern void* unzGetOpaque(unzFile file) {
+
+    unz64_s* s;
+    if (file==NULL)
+        return NULL;
+    s=(unz64_s*)file;
+
+    return s->z_filefunc.zfile_func64.opaque;
+};
+/* GODOT end */
+
 /*
   Close a ZipFile opened with unzOpen.
   If there is files inside the .Zip opened with unzOpenCurrentFile (see later),
@@ -1018,10 +1034,20 @@ local int unz64local_GetCurrentFileInfoInternal (unzFile file,
 
         if (lSeek!=0)
         {
-            if (ZSEEK64(s->z_filefunc, s->filestream,lSeek,ZLIB_FILEFUNC_SEEK_CUR)==0)
-                lSeek=0;
-            else
-                err=UNZ_ERRNO;
+            /* GODOT start */
+            if (lSeek<0) {
+                // WORKAROUND for backwards seeking
+                z_off_t pos = ZTELL64(s->z_filefunc, s->filestream);
+                if (ZSEEK64(s->z_filefunc, s->filestream,pos+lSeek,ZLIB_FILEFUNC_SEEK_SET)==0)
+                    lSeek=0;
+                else
+                    err=UNZ_ERRNO;
+            } else {
+                if (ZSEEK64(s->z_filefunc, s->filestream,lSeek,ZLIB_FILEFUNC_SEEK_CUR)==0)
+                    lSeek=0;
+                else
+                    err=UNZ_ERRNO;
+            }
         }
 
         while(acc < file_info.size_file_extra)
@@ -1575,8 +1601,10 @@ extern int ZEXPORT unzOpenCurrentFile3 (unzFile file, int* method,
     }
     else if ((s->cur_file_info.compression_method==Z_DEFLATED) && (!raw))
     {
-      pfile_in_zip_read_info->stream.zalloc = (alloc_func)0;
-      pfile_in_zip_read_info->stream.zfree = (free_func)0;
+      /* GODOT start */
+      pfile_in_zip_read_info->stream.zalloc = s->z_filefunc.zfile_func64.alloc_mem;
+      pfile_in_zip_read_info->stream.zfree = s->z_filefunc.zfile_func64.free_mem;
+      /* GODOT end */
       pfile_in_zip_read_info->stream.opaque = (voidpf)0;
       pfile_in_zip_read_info->stream.next_in = 0;
       pfile_in_zip_read_info->stream.avail_in = 0;
@@ -1608,6 +1636,9 @@ extern int ZEXPORT unzOpenCurrentFile3 (unzFile file, int* method,
               iSizeVar;
 
     pfile_in_zip_read_info->stream.avail_in = (uInt)0;
+    /* GODOT start */
+    pfile_in_zip_read_info->extra_size = iSizeVar;
+    /* GODOT end */
 
     s->pfile_in_zip_read = pfile_in_zip_read_info;
                 s->encrypted = 0;
@@ -1638,6 +1669,85 @@ extern int ZEXPORT unzOpenCurrentFile3 (unzFile file, int* method,
     return UNZ_OK;
 }
 
+/* GODOT start */
+extern int ZEXPORT unzSeekCurrentFile(unzFile file, int pos) {
+
+    unz64_s* s;
+    file_in_zip64_read_info_s* pfile_in_zip_read_info;
+    if (file==NULL)
+        return UNZ_PARAMERROR;
+    s=(unz64_s*)file;
+    pfile_in_zip_read_info=s->pfile_in_zip_read;
+
+    if (pfile_in_zip_read_info==NULL)
+        return UNZ_PARAMERROR;
+
+    if (pfile_in_zip_read_info->compression_method==Z_BZIP2ED) { // don't know how to support bzip
+        return UNZ_INTERNALERROR;
+    };
+
+    if ((pfile_in_zip_read_info->compression_method==0) || (pfile_in_zip_read_info->raw)) {
+
+        pfile_in_zip_read_info->rest_read_compressed =
+                s->cur_file_info.compressed_size - pos;
+        pfile_in_zip_read_info->rest_read_uncompressed =
+                s->cur_file_info.uncompressed_size - pos;
+
+        pfile_in_zip_read_info->pos_in_zipfile =
+                s->cur_file_info_internal.offset_curfile + SIZEZIPLOCALHEADER +
+                        pfile_in_zip_read_info->extra_size + pos;
+
+        pfile_in_zip_read_info->stream.avail_in = (uInt)0;
+        pfile_in_zip_read_info->stream.total_out = pos;
+
+        return ZSEEK64(pfile_in_zip_read_info->z_filefunc,
+                       pfile_in_zip_read_info->filestream,
+                       pfile_in_zip_read_info->byte_before_the_zipfile + pfile_in_zip_read_info->pos_in_zipfile,
+                       ZLIB_FILEFUNC_SEEK_SET);
+
+    } else { // gzip
+
+        if (pos < pfile_in_zip_read_info->stream.total_out) { // negative seek, rewind
+
+            pfile_in_zip_read_info->rest_read_compressed =
+                    s->cur_file_info.compressed_size ;
+            pfile_in_zip_read_info->rest_read_uncompressed =
+                    s->cur_file_info.uncompressed_size ;
+
+            pfile_in_zip_read_info->pos_in_zipfile =
+                    s->cur_file_info_internal.offset_curfile + SIZEZIPLOCALHEADER +
+                            pfile_in_zip_read_info->extra_size;
+
+            (void)inflateReset(&pfile_in_zip_read_info->stream);
+
+            pfile_in_zip_read_info->stream.avail_in = (uInt)0;
+            pfile_in_zip_read_info->stream.total_out = 0;
+            pfile_in_zip_read_info->stream.next_in = 0;
+        };
+
+        // not sure where to read, so read on the stack
+        {
+            char buf[512];
+            int to_read = pos - pfile_in_zip_read_info->stream.total_out;
+            while (to_read) {
+
+                int len = to_read > sizeof(buf)?sizeof(buf):to_read;
+                int read = unzReadCurrentFile(file, buf, len);
+                if (read < 0) {
+                    return read;
+                };
+                to_read -= read;
+                if (read == UNZ_EOF) {
+                    return pos;
+                };
+            };
+        };
+    };
+
+    return pos;
+};
+/* GODOT end */
+
 extern int ZEXPORT unzOpenCurrentFile (unzFile file)
 {
     return unzOpenCurrentFile3(file, NULL, NULL, 0, NULL);
diff --git a/thirdparty/minizip/unzip.h b/thirdparty/minizip/unzip.h
index 3183968b7..54e65ad8a 100644
--- a/thirdparty/minizip/unzip.h
+++ b/thirdparty/minizip/unzip.h
@@ -202,6 +202,10 @@ extern int ZEXPORT unzClose OF((unzFile file));
     these files MUST be closed with unzCloseCurrentFile before call unzClose.
   return UNZ_OK if there is no problem. */
 
+/* GODOT start */
+extern void* unzGetOpaque(unzFile file);
+/* GODOT end */
+
 extern int ZEXPORT unzGetGlobalInfo OF((unzFile file,
                                         unz_global_info *pglobal_info));
 
@@ -390,6 +394,13 @@ extern int ZEXPORT unzReadCurrentFile OF((unzFile file,
     (UNZ_ERRNO for IO error, or zLib error for uncompress error)
 */
 
+/* GODOT start */
+extern int ZEXPORT unzSeekCurrentFile(unzFile file, int pos);
+/*
+  Seek to position in uncompressed data
+*/
+/* GODOT end */
+
 extern z_off_t ZEXPORT unztell OF((unzFile file));
 
 extern ZPOS64_T ZEXPORT unztell64 OF((unzFile file));
diff --git a/thirdparty/minizip/zip.c b/thirdparty/minizip/zip.c
index 3c34fc8bd..d7093e745 100644
--- a/thirdparty/minizip/zip.c
+++ b/thirdparty/minizip/zip.c
@@ -854,9 +854,11 @@ extern zipFile ZEXPORT zipOpen3 (const void *pathname, int append, zipcharpc* gl
 
     ziinit.z_filefunc.zseek32_file = NULL;
     ziinit.z_filefunc.ztell32_file = NULL;
-    if (pzlib_filefunc64_32_def==NULL)
-        fill_fopen64_filefunc(&ziinit.z_filefunc.zfile_func64);
-    else
+    /* GODOT start */
+    if (pzlib_filefunc64_32_def==NULL) {
+        //fill_fopen64_filefunc(&ziinit.z_filefunc.zfile_func64);
+    } else
+    /* GODOT end */
         ziinit.z_filefunc = *pzlib_filefunc64_32_def;
 
     ziinit.filestream = ZOPEN64(ziinit.z_filefunc,
@@ -1210,8 +1212,10 @@ extern int ZEXPORT zipOpenNewFileInZip4_64 (zipFile file, const char* filename,
     {
         if(zi->ci.method == Z_DEFLATED)
         {
-          zi->ci.stream.zalloc = (alloc_func)0;
-          zi->ci.stream.zfree = (free_func)0;
+          /* GODOT start */
+          zi->ci.stream.zalloc = zi->z_filefunc.zfile_func64.alloc_mem;
+          zi->ci.stream.zfree = zi->z_filefunc.zfile_func64.free_mem;
+          /* GODOT end */
           zi->ci.stream.opaque = (voidpf)0;
 
           if (windowBits>0)