1 /*
   2  * Copyright (c) 2001, 2013, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 /**
  27  * Note: Lifted from uncrunch.c from jdk sources
  28  */
  29 #include <stdio.h>
  30 #include <string.h>
  31 #include <errno.h>
  32 #include <time.h>
  33 
  34 #include <stdlib.h>
  35 
  36 #ifndef _MSC_VER
  37 #include <strings.h>
  38 #endif
  39 
  40 #include "defines.h"
  41 #include "bytes.h"
  42 #include "utils.h"
  43 
  44 #include "constants.h"
  45 #include "unpack.h"
  46 
  47 #include "zip.h"
  48 
  49 #ifdef NO_ZLIB
  50 
  51 inline bool jar::deflate_bytes(bytes& head, bytes& tail) {
  52   return false;
  53 }
  54 inline uint jar::get_crc32(uint c, uchar *ptr, uint len) { return 0; }
  55 #define Z_NULL NULL
  56 
  57 #else // Have ZLIB
  58 
  59 #include <zlib.h>
  60 
  61 inline uint jar::get_crc32(uint c, uchar *ptr, uint len) { return crc32(c, ptr, len); }
  62 
  63 #endif // End of ZLIB
  64 
  65 #ifdef _BIG_ENDIAN
  66 #define SWAP_BYTES(a) \
  67     ((((a) << 8) & 0xff00) | 0x00ff) & (((a) >> 8) | 0xff00)
  68 #else
  69 #define SWAP_BYTES(a)  (a)
  70 #endif
  71 
  72 #define GET_INT_LO(a) \
  73     SWAP_BYTES(a & 0xFFFF)
  74 
  75 #define GET_INT_HI(a) \
  76     SWAP_BYTES((a >> 16) & 0xFFFF);
  77 
  78 
  79 void jar::init(unpacker* u_) {
  80   BYTES_OF(*this).clear();
  81   u = u_;
  82   u->jarout = this;
  83 }
  84 
  85 // Write data to the ZIP output stream.
  86 void jar::write_data(void* buff, int len) {
  87   while (len > 0) {
  88     int rc = (int)fwrite(buff, 1, len, jarfp);
  89     if (rc <= 0) {
  90       fprintf(u->errstrm, "Error: write on output file failed err=%d\n",errno);
  91       exit(1); // Called only from the native standalone unpacker
  92     }
  93     output_file_offset += rc;
  94     buff = ((char *)buff) + rc;
  95     len -= rc;
  96   }
  97 }
  98 
  99 void jar::add_to_jar_directory(const char* fname, bool store, int modtime,
 100                                int len, int clen, uLong crc) {
 101   uint fname_length = (uint)strlen(fname);
 102   ushort header[23];
 103   if (modtime == 0)  modtime = default_modtime;
 104   uLong dostime = get_dostime(modtime);
 105 
 106   header[0] = (ushort)SWAP_BYTES(0x4B50);
 107   header[1] = (ushort)SWAP_BYTES(0x0201);
 108   header[2] = (ushort)SWAP_BYTES(0xA);
 109 
 110   // required version
 111   header[3] = (ushort)SWAP_BYTES(0xA);
 112 
 113   // flags 02 = maximum  sub-compression flag
 114   header[4] = ( store ) ? 0x0 : SWAP_BYTES(0x2);
 115 
 116   // Compression method 8=deflate.
 117   header[5] = ( store ) ? 0x0 : SWAP_BYTES(0x08);
 118 
 119   // Last modified date and time.
 120   header[6] = (ushort)GET_INT_LO(dostime);
 121   header[7] = (ushort)GET_INT_HI(dostime);
 122 
 123   // CRC
 124   header[8] = (ushort)GET_INT_LO(crc);
 125   header[9] = (ushort)GET_INT_HI(crc);
 126 
 127   // Compressed length:
 128   header[10] = (ushort)GET_INT_LO(clen);
 129   header[11] = (ushort)GET_INT_HI(clen);
 130 
 131   // Uncompressed length.
 132   header[12] = (ushort)GET_INT_LO(len);
 133   header[13] = (ushort)GET_INT_HI(len);
 134 
 135   // Filename length
 136   header[14] = (ushort)SWAP_BYTES(fname_length);
 137   // So called "extra field" length.
 138   header[15] = 0;
 139   // So called "comment" length.
 140   header[16] = 0;
 141   // Disk number start
 142   header[17] = 0;
 143   // File flags => binary
 144   header[18] = 0;
 145   // More file flags
 146   header[19] = 0;
 147   header[20] = 0;
 148   // Offset within ZIP file.
 149   header[21] = (ushort)GET_INT_LO(output_file_offset);
 150   header[22] = (ushort)GET_INT_HI(output_file_offset);
 151 
 152   // Copy the whole thing into the central directory.
 153   central_directory.append(header, sizeof(header));
 154 
 155   // Copy the fname to the header.
 156   central_directory.append(fname, fname_length);
 157 
 158   central_directory_count++;
 159 }
 160 
 161 void jar::write_jar_header(const char* fname, bool store, int modtime,
 162                            int len, int clen, uint crc) {
 163   uint fname_length = (uint)strlen(fname);
 164   ushort header[15];
 165   if (modtime == 0)  modtime = default_modtime;
 166   uLong dostime = get_dostime(modtime);
 167 
 168   // ZIP LOC magic.
 169   header[0] = (ushort)SWAP_BYTES(0x4B50);
 170   header[1] = (ushort)SWAP_BYTES(0x0403);
 171 
 172   // Version
 173   header[2] = (ushort)SWAP_BYTES(0xA);
 174 
 175   // flags 02 = maximum  sub-compression flag
 176   header[3] = ( store ) ? 0x0 : SWAP_BYTES(0x2);
 177 
 178   // Compression method = deflate
 179   header[4] = ( store ) ? 0x0 : SWAP_BYTES(0x08);
 180 
 181   // Last modified date and time.
 182   header[5] = (ushort)GET_INT_LO(dostime);
 183   header[6] = (ushort)GET_INT_HI(dostime);
 184 
 185   // CRC
 186   header[7] = (ushort)GET_INT_LO(crc);
 187   header[8] = (ushort)GET_INT_HI(crc);
 188 
 189   // Compressed length:
 190   header[9] = (ushort)GET_INT_LO(clen);
 191   header[10] = (ushort)GET_INT_HI(clen);
 192 
 193   // Uncompressed length.
 194   header[11] = (ushort)GET_INT_LO(len);
 195   header[12] = (ushort)GET_INT_HI(len);
 196 
 197   // Filename length
 198   header[13] = (ushort)SWAP_BYTES(fname_length);
 199   // So called "extra field" length.
 200   header[14] = 0;
 201 
 202   // Write the LOC header to the output file.
 203   write_data(header, (int)sizeof(header));
 204 
 205   // Copy the fname to the header.
 206   write_data((char*)fname, (int)fname_length);
 207 }
 208 
 209 static const char marker_comment[] = ZIP_ARCHIVE_MARKER_COMMENT;
 210 
 211 void jar::write_central_directory() {
 212   bytes mc; mc.set(marker_comment);
 213 
 214   ushort header[11];
 215 
 216   // Create the End of Central Directory structure.
 217   header[0] = (ushort)SWAP_BYTES(0x4B50);
 218   header[1] = (ushort)SWAP_BYTES(0x0605);
 219   // disk numbers
 220   header[2] = 0;
 221   header[3] = 0;
 222   // Number of entries in central directory.
 223   header[4] = (ushort)SWAP_BYTES(central_directory_count);
 224   header[5] = (ushort)SWAP_BYTES(central_directory_count);
 225   // Size of the central directory}
 226   header[6] = (ushort)GET_INT_LO((int)central_directory.size());
 227   header[7] = (ushort)GET_INT_HI((int)central_directory.size());
 228   // Offset of central directory within disk.
 229   header[8] = (ushort)GET_INT_LO(output_file_offset);
 230   header[9] = (ushort)GET_INT_HI(output_file_offset);
 231   // zipfile comment length;
 232   header [10] = (ushort)SWAP_BYTES((int)mc.len);
 233 
 234   // Write the central directory.
 235   PRINTCR((2, "Central directory at %d\n", output_file_offset));
 236   write_data(central_directory.b);
 237 
 238   // Write the End of Central Directory structure.
 239   PRINTCR((2, "end-of-directory at %d\n", output_file_offset));
 240   write_data(header, (int)sizeof(header));
 241 
 242   PRINTCR((2, "writing zip comment\n"));
 243   // Write the comment.
 244   write_data(mc);
 245 }
 246 
 247 // Public API
 248 
 249 // Open a Jar file and initialize.
 250 void jar::openJarFile(const char* fname) {
 251   if (!jarfp) {
 252     PRINTCR((1, "jar::openJarFile: opening %s\n",fname));
 253     jarfp = fopen(fname, "wb");
 254     if (!jarfp) {
 255       fprintf(u->errstrm, "Error: Could not open jar file: %s\n",fname);
 256       exit(3); // Called only from the native standalone unpacker
 257     }
 258   }
 259 }
 260 
 261 // Add a ZIP entry and copy the file data
 262 void jar::addJarEntry(const char* fname,
 263                       bool deflate_hint, int modtime,
 264                       bytes& head, bytes& tail) {
 265   int len = (int)(head.len + tail.len);
 266   int clen = 0;
 267 
 268   uint crc = get_crc32(0,Z_NULL,0);
 269   if (head.len != 0)
 270     crc = get_crc32(crc, (uchar *)head.ptr, (uint)head.len);
 271   if (tail.len != 0)
 272     crc = get_crc32(crc, (uchar *)tail.ptr, (uint)tail.len);
 273 
 274   bool deflate = (deflate_hint && len > 0);
 275 
 276   if (deflate) {
 277     if (deflate_bytes(head, tail) == false) {
 278       PRINTCR((2, "Reverting to store fn=%s\t%d -> %d\n",
 279               fname, len, deflated.size()));
 280       deflate = false;
 281     }
 282   }
 283   clen = (int)((deflate) ? deflated.size() : len);
 284   add_to_jar_directory(fname, !deflate, modtime, len, clen, crc);
 285   write_jar_header(    fname, !deflate, modtime, len, clen, crc);
 286 
 287   if (deflate) {
 288     write_data(deflated.b);
 289   } else {
 290     write_data(head);
 291     write_data(tail);
 292   }
 293 }
 294 
 295 // Add a ZIP entry for a directory name no data
 296 void jar::addDirectoryToJarFile(const char* dir_name) {
 297   bool store = true;
 298   add_to_jar_directory((const char*)dir_name, store, default_modtime, 0, 0, 0);
 299   write_jar_header(    (const char*)dir_name, store, default_modtime, 0, 0, 0);
 300 }
 301 
 302 // Write out the central directory and close the jar file.
 303 void jar::closeJarFile(bool central) {
 304   if (jarfp) {
 305     fflush(jarfp);
 306     if (central) write_central_directory();
 307     fflush(jarfp);
 308     fclose(jarfp);
 309     PRINTCR((2, "jar::closeJarFile:closed jar-file\n"));
 310   }
 311   reset();
 312 }
 313 
 314 /* Convert the date y/n/d and time h:m:s to a four byte DOS date and
 315  *  time (date in high two bytes, time in low two bytes allowing magnitude
 316  *  comparison).
 317  */
 318 inline
 319 uLong jar::dostime(int y, int n, int d, int h, int m, int s) {
 320   return y < 1980 ? dostime(1980, 1, 1, 0, 0, 0) :
 321     (((uLong)y - 1980) << 25) | ((uLong)n << 21) | ((uLong)d << 16) |
 322     ((uLong)h << 11) | ((uLong)m << 5) | ((uLong)s >> 1);
 323 }
 324 
 325 #ifdef _REENTRANT // solaris
 326 extern "C" struct tm *gmtime_r(const time_t *, struct tm *);
 327 #else
 328 #define gmtime_r(t, s) gmtime(t)
 329 #endif
 330 /*
 331  * Return the Unix time in DOS format
 332  */
 333 uLong jar::get_dostime(int modtime) {
 334   // see defines.h
 335   if (modtime != 0 && modtime == modtime_cache)
 336     return dostime_cache;
 337   if (modtime != 0 && default_modtime == 0)
 338     default_modtime = modtime;  // catch a reasonable default
 339   time_t t = modtime;
 340   struct tm sbuf;
 341   (void)memset((void*)&sbuf,0, sizeof(sbuf));
 342   struct tm* s = gmtime_r(&t, &sbuf);
 343   if (s == NULL) {
 344     fprintf(u->errstrm, "Error: gmtime failure, invalid input archive\n");
 345     exit(2);
 346   }
 347   modtime_cache = modtime;
 348   dostime_cache = dostime(s->tm_year + 1900, s->tm_mon + 1, s->tm_mday,
 349                           s->tm_hour, s->tm_min, s->tm_sec);
 350   //printf("modtime %d => %d\n", modtime_cache, dostime_cache);
 351   return dostime_cache;
 352 }
 353 
 354 
 355 
 356 #ifndef NO_ZLIB
 357 
 358 /* Returns true on success, and will set the clen to the compressed
 359    length, the caller should verify if true and clen less than the
 360    input data
 361 */
 362 bool jar::deflate_bytes(bytes& head, bytes& tail) {
 363   int len = (int)(head.len + tail.len);
 364 
 365   z_stream zs;
 366   BYTES_OF(zs).clear();
 367 
 368   // NOTE: the window size should always be -MAX_WBITS normally -15.
 369   // unzip/zipup.c and java/Deflater.c
 370 
 371   int error = deflateInit2(&zs, Z_BEST_COMPRESSION, Z_DEFLATED,
 372                            -MAX_WBITS, 8, Z_DEFAULT_STRATEGY);
 373   if (error != Z_OK) {
 374     switch (error) {
 375     case Z_MEM_ERROR:
 376       PRINTCR((2, "Error: deflate error : Out of memory \n"));
 377       break;
 378     case Z_STREAM_ERROR:
 379       PRINTCR((2,"Error: deflate error : Invalid compression level \n"));
 380       break;
 381     case Z_VERSION_ERROR:
 382       PRINTCR((2,"Error: deflate error : Invalid version\n"));
 383       break;
 384     default:
 385       PRINTCR((2,"Error: Internal deflate error error = %d\n", error));
 386     }
 387     return false;
 388   }
 389 
 390   deflated.empty();
 391   zs.next_out  = (uchar*) deflated.grow(add_size(len, (len/2)));
 392   zs.avail_out = (int)deflated.size();
 393 
 394   zs.next_in = (uchar*)head.ptr;
 395   zs.avail_in = (int)head.len;
 396 
 397   bytes* first = &head;
 398   bytes* last  = &tail;
 399   if (last->len == 0) {
 400     first = null;
 401     last = &head;
 402   } else if (first->len == 0) {
 403     first = null;
 404   }
 405 
 406   if (first != null && error == Z_OK) {
 407     zs.next_in = (uchar*) first->ptr;
 408     zs.avail_in = (int)first->len;
 409     error = deflate(&zs, Z_NO_FLUSH);
 410   }
 411   if (error == Z_OK) {
 412     zs.next_in = (uchar*) last->ptr;
 413     zs.avail_in = (int)last->len;
 414     error = deflate(&zs, Z_FINISH);
 415   }
 416   if (error == Z_STREAM_END) {
 417     if (len > (int)zs.total_out ) {
 418       PRINTCR((2, "deflate compressed data %d -> %d\n", len, zs.total_out));
 419       deflated.b.len = zs.total_out;
 420       deflateEnd(&zs);
 421       return true;
 422     }
 423     PRINTCR((2, "deflate expanded data %d -> %d\n", len, zs.total_out));
 424     deflateEnd(&zs);
 425     return false;
 426   }
 427 
 428   deflateEnd(&zs);
 429   PRINTCR((2, "Error: deflate error deflate did not finish error=%d\n",error));
 430   return false;
 431 }
 432 
 433 // Callback for fetching data from a GZIP input stream
 434 static jlong read_input_via_gzip(unpacker* u,
 435                                   void* buf, jlong minlen, jlong maxlen) {
 436   assert(minlen <= maxlen);  // don't talk nonsense
 437   jlong numread = 0;
 438   char* bufptr = (char*) buf;
 439   char* inbuf = u->gzin->inbuf;
 440   size_t inbuflen = sizeof(u->gzin->inbuf);
 441   unpacker::read_input_fn_t read_gzin_fn =
 442     (unpacker::read_input_fn_t) u->gzin->read_input_fn;
 443   z_stream& zs = *(z_stream*) u->gzin->zstream;
 444   while (numread < minlen) {
 445     int readlen = (1 << 16);  // pretty arbitrary
 446     if (readlen > (maxlen - numread))
 447       readlen = (int)(maxlen - numread);
 448     zs.next_out = (uchar*) bufptr;
 449     zs.avail_out = readlen;
 450     if (zs.avail_in == 0) {
 451       zs.avail_in = (int) read_gzin_fn(u, inbuf, 1, inbuflen);
 452       zs.next_in = (uchar*) inbuf;
 453     }
 454     int error = inflate(&zs, Z_NO_FLUSH);
 455     if (error != Z_OK && error != Z_STREAM_END) {
 456       u->abort("error inflating input");
 457       break;
 458     }
 459     int nr = readlen - zs.avail_out;
 460     numread += nr;
 461     bufptr += nr;
 462     assert(numread <= maxlen);
 463     if (error == Z_STREAM_END) {
 464       enum { TRAILER_LEN = 8 };
 465       // skip 8-byte trailer
 466       if (zs.avail_in >= TRAILER_LEN) {
 467         zs.avail_in -= TRAILER_LEN;
 468       } else {
 469         // Bug: 5023768,we read past the TRAILER_LEN to see if there is
 470         // any extraneous data, as we dont support concatenated .gz
 471         // files just yet.
 472         int extra = (int) read_gzin_fn(u, inbuf, 1, inbuflen);
 473         zs.avail_in += extra - TRAILER_LEN;
 474       }
 475       // %%% should check final CRC and length here
 476       // %%% should check for concatenated *.gz files here
 477       if (zs.avail_in > 0)
 478         u->abort("garbage after end of deflated input stream");
 479       // pop this filter off:
 480       u->gzin->free();
 481       break;
 482     }
 483   }
 484 
 485   //fprintf(u->errstrm, "readInputFn(%d,%d) => %d (gunzip)\n",
 486   //        (int)minlen, (int)maxlen, (int)numread);
 487   return numread;
 488 }
 489 
 490 void gunzip::init(unpacker* u_) {
 491   BYTES_OF(*this).clear();
 492   u = u_;
 493   assert(u->gzin == null);  // once only, please
 494   read_input_fn = (void*)u->read_input_fn;
 495   zstream = NEW(z_stream, 1);
 496   u->gzin = this;
 497   u->read_input_fn = read_input_via_gzip;
 498 }
 499 
 500 void gunzip::start(int magic) {
 501   assert((magic & GZIP_MAGIC_MASK) == GZIP_MAGIC);
 502   int gz_flg = (magic & 0xFF);  // keep "flg", discard other 3 bytes
 503   enum {
 504     FHCRC    = (1<<1),
 505     FEXTRA   = (1<<2),
 506     FNAME    = (1<<3),
 507     FCOMMENT = (1<<4)
 508   };
 509   char gz_mtime[4];
 510   char gz_xfl[1];
 511   char gz_os[1];
 512   char gz_extra_len[2];
 513   char gz_hcrc[2];
 514   char gz_ignore;
 515   // do not save extra, name, comment
 516   read_fixed_field(gz_mtime, sizeof(gz_mtime));
 517   read_fixed_field(gz_xfl, sizeof(gz_xfl));
 518   read_fixed_field(gz_os, sizeof(gz_os));
 519   if (gz_flg & FEXTRA) {
 520     read_fixed_field(gz_extra_len, sizeof(gz_extra_len));
 521     int extra_len = gz_extra_len[0] & 0xFF;
 522     extra_len += (gz_extra_len[1] & 0xFF) << 8;
 523     for (; extra_len > 0; extra_len--) {
 524       read_fixed_field(&gz_ignore, 1);
 525     }
 526   }
 527   int null_terms = 0;
 528   if (gz_flg & FNAME)     null_terms++;
 529   if (gz_flg & FCOMMENT)  null_terms++;
 530   for (; null_terms; null_terms--) {
 531     for (;;) {
 532       gz_ignore = 0;
 533       read_fixed_field(&gz_ignore, 1);
 534       if (gz_ignore == 0)  break;
 535     }
 536   }
 537   if (gz_flg & FHCRC)
 538     read_fixed_field(gz_hcrc, sizeof(gz_hcrc));
 539 
 540   if (aborting())  return;
 541 
 542   // now the input stream is ready to read into the inflater
 543   int error = inflateInit2((z_stream*) zstream, -MAX_WBITS);
 544   if (error != Z_OK) { abort("cannot create input"); return; }
 545 }
 546 
 547 void gunzip::free() {
 548   assert(u->gzin == this);
 549   u->gzin = null;
 550   u->read_input_fn = (unpacker::read_input_fn_t) this->read_input_fn;
 551   inflateEnd((z_stream*) zstream);
 552   mtrace('f', zstream, 0);
 553   ::free(zstream);
 554   zstream = null;
 555   mtrace('f', this, 0);
 556   ::free(this);
 557 }
 558 
 559 void gunzip::read_fixed_field(char* buf, size_t buflen) {
 560   if (aborting())  return;
 561   jlong nr = ((unpacker::read_input_fn_t)read_input_fn)
 562     (u, buf, buflen, buflen);
 563   if ((size_t)nr != buflen)
 564     u->abort("short stream header");
 565 }
 566 
 567 #else // NO_ZLIB
 568 
 569 void gunzip::free() {
 570 }
 571 
 572 #endif // NO_ZLIB