fixes for host gcc 4.6.1
[zpugcc/jano.git] / toolchain / gcc / fastjar / compress.c
blob5893bda937710178748ccaf0ee483d972e1b63fd
1 /* $Id: compress.c 119 2004-10-05 20:38:42Z oyvind $
3 $Log$
4 Revision 1.1 2004/10/05 20:31:35 oyvind
5 * added GCC to repository
7 Revision 1.2 2000/12/14 18:45:35 ghazi
8 Warning fixes:
10 * compress.c: Include stdlib.h and compress.h.
11 (rcsid): Delete.
12 (report_str_error): Make static.
13 (ez_inflate_str): Delete unused variable. Add parens in if-stmt.
14 (hrd_inflate_str): Likewise.
16 * compress.h (init_compression, end_compression, init_inflation,
17 end_inflation): Prototype void arguments.
19 * dostime.c (rcsid): Delete.
21 * jargrep.c: Include ctype.h, stdlib.h, zlib.h and compress.h.
22 Make functions static. Cast ctype function argument to `unsigned
23 char'. Add parens in if-stmts. Constify.
24 (Usage): Change into a macro.
25 (jargrep): Remove unused parameter.
27 * jartool.c: Constify. Add parens in if-stmts. Align
28 signed/unsigned char pointers in functions calls using casts.
29 (rcsid): Delete.
30 (list_jar): Fix printf format specifier.
31 (usage): Chop long string into bits. Reformat.
33 * pushback.c (rcsid): Delete.
35 Revision 1.1 2000/12/09 03:08:23 apbianco
36 2000-12-08 Alexandre Petit-Bianco <apbianco@cygnus.com>
38 * fastjar: Imported.
40 Revision 1.7 2000/09/13 14:02:02 cory
41 Reformatted some of the code to more closly match the layout of the orriginal
42 fastjar utility.
44 Revision 1.6 2000/09/12 22:29:36 cory
45 Jargrep now seems to do what I want it to do. Performs properly on Linux x86,
46 will test some other platforms later.
48 Revision 1.1.1.1 1999/12/06 03:09:16 toast
49 initial checkin..
53 Revision 1.7 1999/05/10 08:50:05 burnsbr
54 *** empty log message ***
56 Revision 1.6 1999/05/10 08:38:44 burnsbr
57 *** empty log message ***
59 Revision 1.5 1999/05/10 08:30:29 burnsbr
60 added inflation code
62 Revision 1.4 1999/04/27 10:03:33 burnsbr
63 added configure support
65 Revision 1.3 1999/04/26 02:35:32 burnsbr
66 compression now works.. yahoo
68 Revision 1.2 1999/04/23 12:01:59 burnsbr
69 added licence stuff.
71 Revision 1.1 1999/04/23 11:58:25 burnsbr
72 Initial revision
78 compress.c - code for handling deflation
79 Copyright (C) 1999 Bryan Burns
81 This program is free software; you can redistribute it and/or
82 modify it under the terms of the GNU General Public License
83 as published by the Free Software Foundation; either version 2
84 of the License, or (at your option) any later version.
86 This program is distributed in the hope that it will be useful,
87 but WITHOUT ANY WARRANTY; without even the implied warranty of
88 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
89 GNU General Public License for more details.
91 You should have received a copy of the GNU General Public License
92 along with this program; if not, write to the Free Software
93 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
96 #include "config.h"
98 #include <zlib.h>
99 #include <string.h>
100 #include <stdio.h>
101 #include <errno.h>
103 #ifdef HAVE_UNISTD_H
104 #include <unistd.h>
105 #endif
106 #ifdef STDC_HEADERS
107 #include <stdlib.h>
108 #endif
110 #include <sys/types.h>
112 #include "jartool.h"
113 #include "pushback.h"
114 #include "compress.h"
116 extern int seekable;
118 static z_stream zs;
120 void init_compression(){
122 memset(&zs, 0, sizeof(z_stream));
124 zs.zalloc = Z_NULL;
125 zs.zfree = Z_NULL;
126 zs.opaque = Z_NULL;
128 /* Why -MAX_WBITS? zlib has an undocumented feature, where if the windowbits
129 parameter is negative, it omits the zlib header, which seems to kill
130 any other zip/unzip program. This caused me SO much pain.. */
131 if(deflateInit2(&zs, Z_DEFAULT_COMPRESSION, Z_DEFLATED, -MAX_WBITS,
132 9, Z_DEFAULT_STRATEGY) != Z_OK){
134 fprintf(stderr, "Error initializing deflation!\n");
135 exit(1);
139 int compress_file(int in_fd, int out_fd, struct zipentry *ze){
140 Bytef in_buff[RDSZ];
141 Bytef out_buff[RDSZ];
142 unsigned int rdamt, wramt;
143 unsigned long tr = 0;
144 int rtval;
146 rdamt = 0;
148 zs.avail_in = 0;
149 zs.next_in = in_buff;
151 zs.next_out = out_buff;
152 zs.avail_out = (uInt)RDSZ;
154 ze->crc = crc32(0L, Z_NULL, 0);
156 for(; ;){
158 /* If deflate is out of input, fill the input buffer for it */
159 if(zs.avail_in == 0 && zs.avail_out > 0){
160 if((rtval = read(in_fd, in_buff, RDSZ)) == 0)
161 break;
163 if(rtval == -1){
164 perror("read");
165 exit(1);
168 rdamt = rtval;
170 /* compute the CRC while we're at it */
171 ze->crc = crc32(ze->crc, in_buff, rdamt);
173 /* update the total amount read sofar */
174 tr += rdamt;
176 zs.next_in = in_buff;
177 zs.avail_in = rdamt;
180 /* deflate the data */
181 if(deflate(&zs, 0) != Z_OK){
182 fprintf(stderr, "Error deflating! %s:%d\n", __FILE__, __LINE__);
183 exit(1);
186 /* If the output buffer is full, dump it to disk */
187 if(zs.avail_out == 0){
189 if(write(out_fd, out_buff, RDSZ) != RDSZ){
190 perror("write");
191 exit(1);
194 /* clear the output buffer */
195 zs.next_out = out_buff;
196 zs.avail_out = (uInt)RDSZ;
201 /* If we have any data waiting in the buffer after we're done with the file
202 we can flush it */
203 if(zs.avail_out < RDSZ){
205 wramt = RDSZ - zs.avail_out;
207 if(write(out_fd, out_buff, wramt) != (int)wramt){
208 perror("write");
209 exit(1);
211 /* clear the output buffer */
212 zs.next_out = out_buff;
213 zs.avail_out = (uInt)RDSZ;
217 /* finish deflation. This purges zlib's internal data buffers */
218 while(deflate(&zs, Z_FINISH) == Z_OK){
219 wramt = RDSZ - zs.avail_out;
221 if(write(out_fd, out_buff, wramt) != (int)wramt){
222 perror("write");
223 exit(1);
226 zs.next_out = out_buff;
227 zs.avail_out = (uInt)RDSZ;
230 /* If there's any data left in the buffer, write it out */
231 if(zs.avail_out != RDSZ){
232 wramt = RDSZ - zs.avail_out;
234 if(write(out_fd, out_buff, wramt) != (int)wramt){
235 perror("write");
236 exit(1);
240 /* update fastjar's entry information */
241 ze->usize = (ub4)zs.total_in;
242 ze->csize = (ub4)zs.total_out;
244 /* Reset the deflation for the next time around */
245 if(deflateReset(&zs) != Z_OK){
246 fprintf(stderr, "Error resetting deflation\n");
247 exit(1);
250 return 0;
253 void end_compression(){
254 int rtval;
256 /* Oddly enough, zlib always returns Z_DATA_ERROR if you specify no
257 zlib header. Go fig. */
258 if((rtval = deflateEnd(&zs)) != Z_OK && rtval != Z_DATA_ERROR){
259 fprintf(stderr, "Error calling deflateEnd\n");
260 fprintf(stderr, "error: (%d) %s\n", rtval, zs.msg);
261 exit(1);
266 void init_inflation(){
268 memset(&zs, 0, sizeof(z_stream));
270 zs.zalloc = Z_NULL;
271 zs.zfree = Z_NULL;
272 zs.opaque = Z_NULL;
274 if(inflateInit2(&zs, -15) != Z_OK){
275 fprintf(stderr, "Error initializing deflation!\n");
276 exit(1);
281 int inflate_file(pb_file *pbf, int out_fd, struct zipentry *ze){
282 Bytef in_buff[RDSZ];
283 Bytef out_buff[RDSZ];
284 unsigned int rdamt;
285 int rtval;
286 ub4 crc = 0;
288 zs.avail_in = 0;
290 crc = crc32(crc, NULL, 0); /* initialize crc */
292 /* loop until we've consumed all the compressed data */
293 for(;;){
295 if(zs.avail_in == 0){
296 if((rdamt = pb_read(pbf, in_buff, RDSZ)) == 0)
297 break;
298 else if((int)rdamt < 0){
299 perror("read");
300 exit(1);
303 #ifdef DEBUG
304 printf("%d bytes read\n", rdamt);
305 #endif
307 zs.next_in = in_buff;
308 zs.avail_in = rdamt;
311 zs.next_out = out_buff;
312 zs.avail_out = RDSZ;
314 if((rtval = inflate(&zs, 0)) != Z_OK){
315 if(rtval == Z_STREAM_END){
316 #ifdef DEBUG
317 printf("end of stream\n");
318 #endif
319 if(zs.avail_out != RDSZ){
320 crc = crc32(crc, out_buff, (RDSZ - zs.avail_out));
322 if(out_fd >= 0)
323 if(write(out_fd, out_buff, (RDSZ - zs.avail_out)) !=
324 (int)(RDSZ - zs.avail_out)){
325 perror("write");
326 exit(1);
330 break;
331 } else {
332 fprintf(stderr, "Error inflating file! (%d)\n", rtval);
333 exit(1);
335 } else {
336 if(zs.avail_out != RDSZ){
337 crc = crc32(crc, out_buff, (RDSZ - zs.avail_out));
339 if(out_fd >= 0)
340 if(write(out_fd, out_buff, (RDSZ - zs.avail_out)) !=
341 (int)(RDSZ - zs.avail_out)){
342 perror("write");
343 exit(1);
345 zs.next_out = out_buff;
346 zs.avail_out = RDSZ;
350 #ifdef DEBUG
351 printf("done inflating\n");
352 #endif
354 #ifdef DEBUG
355 printf("%d bytes left over\n", zs.avail_in);
356 #endif
358 #ifdef DEBUG
359 printf("CRC is %x\n", crc);
360 #endif
362 ze->crc = crc;
364 pb_push(pbf, zs.next_in, zs.avail_in);
366 ze->usize = zs.total_out;
368 inflateReset(&zs);
369 return 0;
373 Function name: report_str_error
374 args: val Error code returned from zlib.
375 purpose: Put out an error message corresponding to error code returned from zlib.
376 Be suitably cryptic seeing I don't really know exactly what these errors mean.
379 static void report_str_error(int val) {
380 switch(val) {
381 case Z_STREAM_END:
382 break;
383 case Z_NEED_DICT:
384 fprintf(stderr, "Need a dictionary?\n");
385 exit(1);
386 case Z_DATA_ERROR:
387 fprintf(stderr, "Z_DATA_ERROR\n");
388 exit(1);
389 case Z_STREAM_ERROR:
390 fprintf(stderr, "Z_STREAM_ERROR\n");
391 exit(1);
392 case Z_MEM_ERROR:
393 fprintf(stderr, "Z_MEM_ERROR\n");
394 exit(1);
395 case Z_BUF_ERROR:
396 fprintf(stderr, "Z_BUF_ERROR\n");
397 exit(1);
398 case Z_OK:
399 break;
400 default:
401 fprintf(stderr, "Unknown behavior from inflate\n");
402 exit(1);
407 Function name: ez_inflate_str
408 args: pbf Pointer to pushback handle for file.
409 csize Compressed size of embedded file.
410 usize Uncompressed size of embedded file.
411 purpose: Read in and decompress the contents of an embedded file and store it in a
412 byte array.
413 returns: Byte array of uncompressed embedded file.
416 static Bytef *ez_inflate_str(pb_file *pbf, ub4 csize, ub4 usize) {
417 Bytef *out_buff;
418 Bytef *in_buff;
419 unsigned int rdamt;
421 if((zs.next_in = in_buff = (Bytef *) malloc(csize))) {
422 if((zs.next_out = out_buff = (Bytef *) malloc(usize + 1))) {
423 if((rdamt = pb_read(pbf, zs.next_in, csize)) == csize) {
424 zs.avail_in = csize;
425 zs.avail_out = usize;
426 report_str_error(inflate(&zs, 0));
427 free(in_buff);
428 inflateReset(&zs);
429 out_buff[usize] = '\0';
431 else {
432 fprintf(stderr, "Read failed on input file.\n");
433 fprintf(stderr, "Tried to read %u but read %u instead.\n", csize, rdamt);
434 free(in_buff);
435 free(out_buff);
436 exit(1);
439 else {
440 fprintf(stderr, "Malloc of out_buff failed.\n");
441 fprintf(stderr, "Error: %s\n", strerror(errno));
442 free(in_buff);
443 exit(1);
446 else {
447 fprintf(stderr, "Malloc of in_buff failed.\n");
448 fprintf(stderr, "Error: %s\n", strerror(errno));
449 exit(1);
452 return out_buff;
456 Function name: hrd_inflate_str
457 args: pbf Pointer to pushback handle for file.
458 csize Pointer to compressed size of embedded file.
459 usize Pointer to uncompressed size of embedded file.
460 purpose: Read and decompress an embedded file into a string. Set csize and usize
461 accordingly. This function does the reading for us in the case there is not size
462 information in the header for the embedded file.
463 returns: Byte array of the contents of the embedded file.
466 static Bytef *hrd_inflate_str(pb_file *pbf, ub4 *csize, ub4 *usize) {
467 Bytef *out_buff;
468 Bytef *tmp;
469 Bytef in_buff[RDSZ];
470 unsigned int rdamt;
471 int i;
472 int zret;
474 i = 1;
475 out_buff = NULL;
476 zret = Z_OK;
477 while(zret != Z_STREAM_END && (rdamt = pb_read(pbf, in_buff, RDSZ)))
479 zs.avail_in = rdamt;
480 zs.avail_out = 0;
481 zs.next_in = in_buff;
482 do {
483 if((tmp = (Bytef *) realloc(out_buff, (RDSZ * i) + 1))) {
484 out_buff = tmp;
485 zs.next_out = &(out_buff[(RDSZ * (i - 1)) - zs.avail_out]);
486 zs.avail_out += RDSZ;
487 i++;
489 else {
490 fprintf(stderr, "Realloc of out_buff failed.\n");
491 fprintf(stderr, "Error: %s\n", strerror(errno));
492 exit(1);
494 } while((zret = inflate(&zs, 0)) == Z_OK);
495 report_str_error(zret);
497 pb_push(pbf, zs.next_in, zs.avail_in);
499 out_buff[(RDSZ * (i - 1)) - zs.avail_out] = '\0';
500 *usize = zs.total_out;
501 *csize = zs.total_in;
503 inflateReset(&zs);
505 return out_buff;
509 Function name: inflate_string
510 args: pbf Pointer to pushback handle for file.
511 csize Pointer to compressed size of embedded file. May be 0 if not set.
512 usize Pointer to uncompressed size of embedded file. May be 0 if not set.
513 purpose: Decide the easiest (in computer terms) methos of decompressing this embedded
514 file to a string.
515 returns: Pointer to a string containing the decompressed contents of the embedded file.
516 If csize and usize are not set set them to correct numbers.
519 Bytef *inflate_string(pb_file *pbf, ub4 *csize, ub4 *usize) {
520 Bytef *ret_buf;
522 if(*csize && *usize) ret_buf = ez_inflate_str(pbf, *csize, *usize);
523 else ret_buf = hrd_inflate_str(pbf, csize, usize);
525 return ret_buf;