1 /*- 2 * Copyright (c) 2011-2012 Michihiro NAKAJIMA 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR 15 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 16 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 17 * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT, 18 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 19 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 20 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 21 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 23 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 26 #include "archive_platform.h" 27 __FBSDID("$FreeBSD$"); 28 29 #ifdef HAVE_ERRNO_H 30 #include <errno.h> 31 #endif 32 #include <stdlib.h> 33 #ifdef HAVE_BZLIB_H 34 #include <bzlib.h> 35 #endif 36 #if HAVE_LZMA_H 37 #include <lzma.h> 38 #endif 39 #ifdef HAVE_ZLIB_H 40 #include <zlib.h> 41 #endif 42 43 #include "archive.h" 44 #ifndef HAVE_ZLIB_H 45 #include "archive_crc32.h" 46 #endif 47 #include "archive_endian.h" 48 #include "archive_entry.h" 49 #include "archive_entry_locale.h" 50 #include "archive_ppmd7_private.h" 51 #include "archive_private.h" 52 #include "archive_rb.h" 53 #include "archive_string.h" 54 #include "archive_write_private.h" 55 56 /* 57 * Codec ID 58 */ 59 #define _7Z_COPY 0 60 #define _7Z_LZMA1 0x030101 61 #define _7Z_LZMA2 0x21 62 #define _7Z_DEFLATE 0x040108 63 #define _7Z_BZIP2 0x040202 64 #define _7Z_PPMD 0x030401 65 66 /* 67 * 7-Zip header property IDs. 68 */ 69 #define kEnd 0x00 70 #define kHeader 0x01 71 #define kArchiveProperties 0x02 72 #define kAdditionalStreamsInfo 0x03 73 #define kMainStreamsInfo 0x04 74 #define kFilesInfo 0x05 75 #define kPackInfo 0x06 76 #define kUnPackInfo 0x07 77 #define kSubStreamsInfo 0x08 78 #define kSize 0x09 79 #define kCRC 0x0A 80 #define kFolder 0x0B 81 #define kCodersUnPackSize 0x0C 82 #define kNumUnPackStream 0x0D 83 #define kEmptyStream 0x0E 84 #define kEmptyFile 0x0F 85 #define kAnti 0x10 86 #define kName 0x11 87 #define kCTime 0x12 88 #define kATime 0x13 89 #define kMTime 0x14 90 #define kAttributes 0x15 91 #define kEncodedHeader 0x17 92 93 enum la_zaction { 94 ARCHIVE_Z_FINISH, 95 ARCHIVE_Z_RUN 96 }; 97 98 /* 99 * A stream object of universal compressor. 100 */ 101 struct la_zstream { 102 const uint8_t *next_in; 103 size_t avail_in; 104 uint64_t total_in; 105 106 uint8_t *next_out; 107 size_t avail_out; 108 uint64_t total_out; 109 110 uint32_t prop_size; 111 uint8_t *props; 112 113 int valid; 114 void *real_stream; 115 int (*code) (struct archive *a, 116 struct la_zstream *lastrm, 117 enum la_zaction action); 118 int (*end)(struct archive *a, 119 struct la_zstream *lastrm); 120 }; 121 122 #define PPMD7_DEFAULT_ORDER 6 123 #define PPMD7_DEFAULT_MEM_SIZE (1 << 24) 124 125 struct ppmd_stream { 126 int stat; 127 CPpmd7 ppmd7_context; 128 CPpmd7z_RangeEnc range_enc; 129 IByteOut byteout; 130 uint8_t *buff; 131 uint8_t *buff_ptr; 132 uint8_t *buff_end; 133 size_t buff_bytes; 134 }; 135 136 struct coder { 137 unsigned codec; 138 size_t prop_size; 139 uint8_t *props; 140 }; 141 142 struct file { 143 struct archive_rb_node rbnode; 144 145 struct file *next; 146 unsigned name_len; 147 uint8_t *utf16name;/* UTF16-LE name. */ 148 uint64_t size; 149 unsigned flg; 150 #define MTIME_IS_SET (1<<0) 151 #define ATIME_IS_SET (1<<1) 152 #define CTIME_IS_SET (1<<2) 153 #define CRC32_IS_SET (1<<3) 154 #define HAS_STREAM (1<<4) 155 156 struct { 157 time_t time; 158 long time_ns; 159 } times[3]; 160 #define MTIME 0 161 #define ATIME 1 162 #define CTIME 2 163 164 mode_t mode; 165 uint32_t crc32; 166 167 int dir:1; 168 }; 169 170 struct _7zip { 171 int temp_fd; 172 uint64_t temp_offset; 173 174 struct file *cur_file; 175 size_t total_number_entry; 176 size_t total_number_nonempty_entry; 177 size_t total_number_empty_entry; 178 size_t total_number_dir_entry; 179 size_t total_bytes_entry_name; 180 size_t total_number_time_defined[3]; 181 uint64_t total_bytes_compressed; 182 uint64_t total_bytes_uncompressed; 183 uint64_t entry_bytes_remaining; 184 uint32_t entry_crc32; 185 uint32_t precode_crc32; 186 uint32_t encoded_crc32; 187 int crc32flg; 188 #define PRECODE_CRC32 1 189 #define ENCODED_CRC32 2 190 191 unsigned opt_compression; 192 int opt_compression_level; 193 194 struct la_zstream stream; 195 struct coder coder; 196 197 struct archive_string_conv *sconv; 198 199 /* 200 * Compressed data buffer. 201 */ 202 unsigned char wbuff[512 * 20 * 6]; 203 size_t wbuff_remaining; 204 205 /* 206 * The list of the file entries which has its contents is used to 207 * manage struct file objects. 208 * We use 'next' a menber of struct file to chain. 209 */ 210 struct { 211 struct file *first; 212 struct file **last; 213 } file_list, empty_list; 214 struct archive_rb_tree rbtree;/* for empty files */ 215 }; 216 217 static int _7z_options(struct archive_write *, 218 const char *, const char *); 219 static int _7z_write_header(struct archive_write *, 220 struct archive_entry *); 221 static ssize_t _7z_write_data(struct archive_write *, 222 const void *, size_t); 223 static int _7z_finish_entry(struct archive_write *); 224 static int _7z_close(struct archive_write *); 225 static int _7z_free(struct archive_write *); 226 static int file_cmp_node(const struct archive_rb_node *, 227 const struct archive_rb_node *); 228 static int file_cmp_key(const struct archive_rb_node *, const void *); 229 static int file_new(struct archive_write *a, struct archive_entry *, 230 struct file **); 231 static void file_free(struct file *); 232 static void file_register(struct _7zip *, struct file *); 233 static void file_register_empty(struct _7zip *, struct file *); 234 static void file_init_register(struct _7zip *); 235 static void file_init_register_empty(struct _7zip *); 236 static void file_free_register(struct _7zip *); 237 static ssize_t compress_out(struct archive_write *, const void *, size_t , 238 enum la_zaction); 239 static int compression_init_encoder_copy(struct archive *, 240 struct la_zstream *); 241 static int compression_code_copy(struct archive *, 242 struct la_zstream *, enum la_zaction); 243 static int compression_end_copy(struct archive *, struct la_zstream *); 244 static int compression_init_encoder_deflate(struct archive *, 245 struct la_zstream *, int, int); 246 #ifdef HAVE_ZLIB_H 247 static int compression_code_deflate(struct archive *, 248 struct la_zstream *, enum la_zaction); 249 static int compression_end_deflate(struct archive *, struct la_zstream *); 250 #endif 251 static int compression_init_encoder_bzip2(struct archive *, 252 struct la_zstream *, int); 253 #if defined(HAVE_BZLIB_H) && defined(BZ_CONFIG_ERROR) 254 static int compression_code_bzip2(struct archive *, 255 struct la_zstream *, enum la_zaction); 256 static int compression_end_bzip2(struct archive *, struct la_zstream *); 257 #endif 258 static int compression_init_encoder_lzma1(struct archive *, 259 struct la_zstream *, int); 260 static int compression_init_encoder_lzma2(struct archive *, 261 struct la_zstream *, int); 262 #if defined(HAVE_LZMA_H) 263 static int compression_code_lzma(struct archive *, 264 struct la_zstream *, enum la_zaction); 265 static int compression_end_lzma(struct archive *, struct la_zstream *); 266 #endif 267 static int compression_init_encoder_ppmd(struct archive *, 268 struct la_zstream *, unsigned, uint32_t); 269 static int compression_code_ppmd(struct archive *, 270 struct la_zstream *, enum la_zaction); 271 static int compression_end_ppmd(struct archive *, struct la_zstream *); 272 static int _7z_compression_init_encoder(struct archive_write *, unsigned, 273 int); 274 static int compression_code(struct archive *, 275 struct la_zstream *, enum la_zaction); 276 static int compression_end(struct archive *, 277 struct la_zstream *); 278 static int enc_uint64(struct archive_write *, uint64_t); 279 static int make_header(struct archive_write *, uint64_t, uint64_t, 280 uint64_t, int, struct coder *); 281 static int make_streamsInfo(struct archive_write *, uint64_t, uint64_t, 282 uint64_t, int, struct coder *, int, uint32_t); 283 284 int 285 archive_write_set_format_7zip(struct archive *_a) 286 { 287 static const struct archive_rb_tree_ops rb_ops = { 288 file_cmp_node, file_cmp_key 289 }; 290 struct archive_write *a = (struct archive_write *)_a; 291 struct _7zip *zip; 292 293 archive_check_magic(_a, ARCHIVE_WRITE_MAGIC, 294 ARCHIVE_STATE_NEW, "archive_write_set_format_7zip"); 295 296 /* If another format was already registered, unregister it. */ 297 if (a->format_free != NULL) 298 (a->format_free)(a); 299 300 zip = calloc(1, sizeof(*zip)); 301 if (zip == NULL) { 302 archive_set_error(&a->archive, ENOMEM, 303 "Can't allocate 7-Zip data"); 304 return (ARCHIVE_FATAL); 305 } 306 zip->temp_fd = -1; 307 __archive_rb_tree_init(&(zip->rbtree), &rb_ops); 308 file_init_register(zip); 309 file_init_register_empty(zip); 310 311 /* Set default compression type and its level. */ 312 #if HAVE_LZMA_H 313 zip->opt_compression = _7Z_LZMA1; 314 #elif defined(HAVE_BZLIB_H) && defined(BZ_CONFIG_ERROR) 315 zip->opt_compression = _7Z_BZIP2; 316 #elif defined(HAVE_ZLIB_H) 317 zip->opt_compression = _7Z_DEFLATE; 318 #else 319 zip->opt_compression = _7Z_COPY; 320 #endif 321 zip->opt_compression_level = 6; 322 323 a->format_data = zip; 324 325 a->format_name = "7zip"; 326 a->format_options = _7z_options; 327 a->format_write_header = _7z_write_header; 328 a->format_write_data = _7z_write_data; 329 a->format_finish_entry = _7z_finish_entry; 330 a->format_close = _7z_close; 331 a->format_free = _7z_free; 332 a->archive.archive_format = ARCHIVE_FORMAT_7ZIP; 333 a->archive.archive_format_name = "7zip"; 334 335 return (ARCHIVE_OK); 336 } 337 338 static int 339 _7z_options(struct archive_write *a, const char *key, const char *value) 340 { 341 struct _7zip *zip; 342 343 zip = (struct _7zip *)a->format_data; 344 345 if (strcmp(key, "compression") == 0) { 346 const char *name = NULL; 347 348 if (value == NULL || strcmp(value, "copy") == 0 || 349 strcmp(value, "COPY") == 0 || 350 strcmp(value, "store") == 0 || 351 strcmp(value, "STORE") == 0) 352 zip->opt_compression = _7Z_COPY; 353 else if (strcmp(value, "deflate") == 0 || 354 strcmp(value, "DEFLATE") == 0) 355 #if HAVE_ZLIB_H 356 zip->opt_compression = _7Z_DEFLATE; 357 #else 358 name = "deflate"; 359 #endif 360 else if (strcmp(value, "bzip2") == 0 || 361 strcmp(value, "BZIP2") == 0) 362 #if defined(HAVE_BZLIB_H) && defined(BZ_CONFIG_ERROR) 363 zip->opt_compression = _7Z_BZIP2; 364 #else 365 name = "bzip2"; 366 #endif 367 else if (strcmp(value, "lzma1") == 0 || 368 strcmp(value, "LZMA1") == 0) 369 #if HAVE_LZMA_H 370 zip->opt_compression = _7Z_LZMA1; 371 #else 372 name = "lzma1"; 373 #endif 374 else if (strcmp(value, "lzma2") == 0 || 375 strcmp(value, "LZMA2") == 0) 376 #if HAVE_LZMA_H 377 zip->opt_compression = _7Z_LZMA2; 378 #else 379 name = "lzma2"; 380 #endif 381 else if (strcmp(value, "ppmd") == 0 || 382 strcmp(value, "PPMD") == 0 || 383 strcmp(value, "PPMd") == 0) 384 zip->opt_compression = _7Z_PPMD; 385 else { 386 archive_set_error(&(a->archive), 387 ARCHIVE_ERRNO_MISC, 388 "Unknown compression name: `%s'", 389 value); 390 return (ARCHIVE_FAILED); 391 } 392 if (name != NULL) { 393 archive_set_error(&(a->archive), 394 ARCHIVE_ERRNO_MISC, 395 "`%s' compression not supported " 396 "on this platform", 397 name); 398 return (ARCHIVE_FAILED); 399 } 400 return (ARCHIVE_OK); 401 } 402 if (strcmp(key, "compression-level") == 0) { 403 if (value == NULL || 404 !(value[0] >= '0' && value[0] <= '9') || 405 value[1] != '\0') { 406 archive_set_error(&(a->archive), 407 ARCHIVE_ERRNO_MISC, 408 "Illegal value `%s'", 409 value); 410 return (ARCHIVE_FAILED); 411 } 412 zip->opt_compression_level = value[0] - '0'; 413 return (ARCHIVE_OK); 414 } 415 416 /* Note: The "warn" return is just to inform the options 417 * supervisor that we didn't handle it. It will generate 418 * a suitable error if no one used this option. */ 419 return (ARCHIVE_WARN); 420 } 421 422 static int 423 _7z_write_header(struct archive_write *a, struct archive_entry *entry) 424 { 425 struct _7zip *zip; 426 struct file *file; 427 int r; 428 429 zip = (struct _7zip *)a->format_data; 430 zip->cur_file = NULL; 431 zip->entry_bytes_remaining = 0; 432 433 if (zip->sconv == NULL) { 434 zip->sconv = archive_string_conversion_to_charset( 435 &a->archive, "UTF-16LE", 1); 436 if (zip->sconv == NULL) 437 return (ARCHIVE_FATAL); 438 } 439 440 r = file_new(a, entry, &file); 441 if (r < ARCHIVE_WARN) { 442 file_free(file); 443 return (r); 444 } 445 if (file->size == 0 && file->dir) { 446 if (!__archive_rb_tree_insert_node(&(zip->rbtree), 447 (struct archive_rb_node *)file)) { 448 /* We have already had the same file. */ 449 file_free(file); 450 return (ARCHIVE_OK); 451 } 452 } 453 454 if (file->flg & MTIME_IS_SET) 455 zip->total_number_time_defined[MTIME]++; 456 if (file->flg & CTIME_IS_SET) 457 zip->total_number_time_defined[CTIME]++; 458 if (file->flg & ATIME_IS_SET) 459 zip->total_number_time_defined[ATIME]++; 460 461 zip->total_number_entry++; 462 zip->total_bytes_entry_name += file->name_len + 2; 463 if (file->size == 0) { 464 /* Count up the number of empty files. */ 465 zip->total_number_empty_entry++; 466 if (file->dir) 467 zip->total_number_dir_entry++; 468 else 469 file_register_empty(zip, file); 470 return (r); 471 } 472 473 /* 474 * Init compression. 475 */ 476 if ((zip->total_number_entry - zip->total_number_empty_entry) == 1) { 477 r = _7z_compression_init_encoder(a, zip->opt_compression, 478 zip->opt_compression_level); 479 if (r < 0) { 480 file_free(file); 481 return (ARCHIVE_FATAL); 482 } 483 } 484 485 /* Register a non-empty file. */ 486 file_register(zip, file); 487 488 /* 489 * Set the current file to cur_file to read its contents. 490 */ 491 zip->cur_file = file; 492 493 494 /* Save a offset of current file in temporary file. */ 495 zip->entry_bytes_remaining = file->size; 496 zip->entry_crc32 = 0; 497 498 /* 499 * Store a symbolic link name as file contents. 500 */ 501 if (archive_entry_filetype(entry) == AE_IFLNK) { 502 ssize_t bytes; 503 const void *p = (const void *)archive_entry_symlink(entry); 504 bytes = compress_out(a, p, (size_t)file->size, ARCHIVE_Z_RUN); 505 if (bytes < 0) 506 return ((int)bytes); 507 zip->entry_crc32 = crc32(zip->entry_crc32, p, (unsigned)bytes); 508 zip->entry_bytes_remaining -= bytes; 509 } 510 511 return (r); 512 } 513 514 /* 515 * Write data to a temporary file. 516 */ 517 static int 518 write_to_temp(struct archive_write *a, const void *buff, size_t s) 519 { 520 struct _7zip *zip; 521 const unsigned char *p; 522 ssize_t ws; 523 524 zip = (struct _7zip *)a->format_data; 525 526 /* 527 * Open a temporary file. 528 */ 529 if (zip->temp_fd == -1) { 530 zip->temp_offset = 0; 531 zip->temp_fd = __archive_mktemp(NULL); 532 if (zip->temp_fd < 0) { 533 archive_set_error(&a->archive, errno, 534 "Couldn't create temporary file"); 535 return (ARCHIVE_FATAL); 536 } 537 } 538 539 p = (const unsigned char *)buff; 540 while (s) { 541 ws = write(zip->temp_fd, p, s); 542 if (ws < 0) { 543 archive_set_error(&(a->archive), errno, 544 "fwrite function failed"); 545 return (ARCHIVE_FATAL); 546 } 547 s -= ws; 548 p += ws; 549 zip->temp_offset += ws; 550 } 551 return (ARCHIVE_OK); 552 } 553 554 static ssize_t 555 compress_out(struct archive_write *a, const void *buff, size_t s, 556 enum la_zaction run) 557 { 558 struct _7zip *zip = (struct _7zip *)a->format_data; 559 int r; 560 561 if (run == ARCHIVE_Z_FINISH && zip->stream.total_in == 0 && s == 0) 562 return (0); 563 564 if ((zip->crc32flg & PRECODE_CRC32) && s) 565 zip->precode_crc32 = crc32(zip->precode_crc32, buff, 566 (unsigned)s); 567 zip->stream.next_in = (const unsigned char *)buff; 568 zip->stream.avail_in = s; 569 for (;;) { 570 /* Compress file data. */ 571 r = compression_code(&(a->archive), &(zip->stream), run); 572 if (r != ARCHIVE_OK && r != ARCHIVE_EOF) 573 return (ARCHIVE_FATAL); 574 if (zip->stream.avail_out == 0) { 575 if (write_to_temp(a, zip->wbuff, sizeof(zip->wbuff)) 576 != ARCHIVE_OK) 577 return (ARCHIVE_FATAL); 578 zip->stream.next_out = zip->wbuff; 579 zip->stream.avail_out = sizeof(zip->wbuff); 580 if (zip->crc32flg & ENCODED_CRC32) 581 zip->encoded_crc32 = crc32(zip->encoded_crc32, 582 zip->wbuff, sizeof(zip->wbuff)); 583 if (run == ARCHIVE_Z_FINISH && r != ARCHIVE_EOF) 584 continue; 585 } 586 if (zip->stream.avail_in == 0) 587 break; 588 } 589 if (run == ARCHIVE_Z_FINISH) { 590 uint64_t bytes = sizeof(zip->wbuff) - zip->stream.avail_out; 591 if (write_to_temp(a, zip->wbuff, (size_t)bytes) != ARCHIVE_OK) 592 return (ARCHIVE_FATAL); 593 if ((zip->crc32flg & ENCODED_CRC32) && bytes) 594 zip->encoded_crc32 = crc32(zip->encoded_crc32, 595 zip->wbuff, (unsigned)bytes); 596 } 597 598 return (s); 599 } 600 601 static ssize_t 602 _7z_write_data(struct archive_write *a, const void *buff, size_t s) 603 { 604 struct _7zip *zip; 605 ssize_t bytes; 606 607 zip = (struct _7zip *)a->format_data; 608 609 if (s > zip->entry_bytes_remaining) 610 s = (size_t)zip->entry_bytes_remaining; 611 if (s == 0 || zip->cur_file == NULL) 612 return (0); 613 bytes = compress_out(a, buff, s, ARCHIVE_Z_RUN); 614 if (bytes < 0) 615 return (bytes); 616 zip->entry_crc32 = crc32(zip->entry_crc32, buff, (unsigned)bytes); 617 zip->entry_bytes_remaining -= bytes; 618 return (bytes); 619 } 620 621 static int 622 _7z_finish_entry(struct archive_write *a) 623 { 624 struct _7zip *zip; 625 size_t s; 626 ssize_t r; 627 628 zip = (struct _7zip *)a->format_data; 629 if (zip->cur_file == NULL) 630 return (ARCHIVE_OK); 631 632 while (zip->entry_bytes_remaining > 0) { 633 s = (size_t)zip->entry_bytes_remaining; 634 if (s > a->null_length) 635 s = a->null_length; 636 r = _7z_write_data(a, a->nulls, s); 637 if (r < 0) 638 return ((int)r); 639 } 640 zip->total_bytes_compressed += zip->stream.total_in; 641 zip->total_bytes_uncompressed += zip->stream.total_out; 642 zip->cur_file->crc32 = zip->entry_crc32; 643 zip->cur_file = NULL; 644 645 return (ARCHIVE_OK); 646 } 647 648 static int 649 flush_wbuff(struct archive_write *a) 650 { 651 struct _7zip *zip; 652 int r; 653 size_t s; 654 655 zip = (struct _7zip *)a->format_data; 656 s = sizeof(zip->wbuff) - zip->wbuff_remaining; 657 r = __archive_write_output(a, zip->wbuff, s); 658 if (r != ARCHIVE_OK) 659 return (r); 660 zip->wbuff_remaining = sizeof(zip->wbuff); 661 return (r); 662 } 663 664 static int 665 copy_out(struct archive_write *a, uint64_t offset, uint64_t length) 666 { 667 struct _7zip *zip; 668 int r; 669 670 zip = (struct _7zip *)a->format_data; 671 if (zip->temp_offset > 0 && 672 lseek(zip->temp_fd, offset, SEEK_SET) < 0) { 673 archive_set_error(&(a->archive), errno, "lseek failed"); 674 return (ARCHIVE_FATAL); 675 } 676 while (length) { 677 size_t rsize; 678 ssize_t rs; 679 unsigned char *wb; 680 681 if (length > zip->wbuff_remaining) 682 rsize = zip->wbuff_remaining; 683 else 684 rsize = (size_t)length; 685 wb = zip->wbuff + (sizeof(zip->wbuff) - zip->wbuff_remaining); 686 rs = read(zip->temp_fd, wb, rsize); 687 if (rs < 0) { 688 archive_set_error(&(a->archive), errno, 689 "Can't read temporary file(%jd)", 690 (intmax_t)rs); 691 return (ARCHIVE_FATAL); 692 } 693 if (rs == 0) { 694 archive_set_error(&(a->archive), 0, 695 "Truncated 7-Zip archive"); 696 return (ARCHIVE_FATAL); 697 } 698 zip->wbuff_remaining -= rs; 699 length -= rs; 700 if (zip->wbuff_remaining == 0) { 701 r = flush_wbuff(a); 702 if (r != ARCHIVE_OK) 703 return (r); 704 } 705 } 706 return (ARCHIVE_OK); 707 } 708 709 static int 710 _7z_close(struct archive_write *a) 711 { 712 struct _7zip *zip; 713 unsigned char *wb; 714 uint64_t header_offset, header_size, header_unpacksize; 715 uint64_t length; 716 uint32_t header_crc32; 717 int r; 718 719 zip = (struct _7zip *)a->format_data; 720 721 if (zip->total_number_entry > 0) { 722 struct archive_rb_node *n; 723 uint64_t data_offset, data_size, data_unpacksize; 724 unsigned header_compression; 725 726 r = (int)compress_out(a, NULL, 0, ARCHIVE_Z_FINISH); 727 if (r < 0) 728 return (r); 729 data_offset = 0; 730 data_size = zip->stream.total_out; 731 data_unpacksize = zip->stream.total_in; 732 zip->coder.codec = zip->opt_compression; 733 zip->coder.prop_size = zip->stream.prop_size; 734 zip->coder.props = zip->stream.props; 735 zip->stream.prop_size = 0; 736 zip->stream.props = NULL; 737 zip->total_number_nonempty_entry = 738 zip->total_number_entry - zip->total_number_empty_entry; 739 740 /* Connect an empty file list. */ 741 if (zip->empty_list.first != NULL) { 742 *zip->file_list.last = zip->empty_list.first; 743 zip->file_list.last = zip->empty_list.last; 744 } 745 /* Connect a directory file list. */ 746 ARCHIVE_RB_TREE_FOREACH(n, &(zip->rbtree)) { 747 file_register(zip, (struct file *)n); 748 } 749 750 /* 751 * NOTE: 7z command supports just LZMA1, LZMA2 and COPY for 752 * the compression type for encoding the header. 753 */ 754 #if HAVE_LZMA_H 755 header_compression = _7Z_LZMA1; 756 /* If the stored file is only one, do not encode the header. 757 * This is the same way 7z command does. */ 758 if (zip->total_number_entry == 1) 759 header_compression = _7Z_COPY; 760 #else 761 header_compression = _7Z_COPY; 762 #endif 763 r = _7z_compression_init_encoder(a, header_compression, 6); 764 if (r < 0) 765 return (r); 766 zip->crc32flg = PRECODE_CRC32; 767 zip->precode_crc32 = 0; 768 r = make_header(a, data_offset, data_size, data_unpacksize, 769 1, &(zip->coder)); 770 if (r < 0) 771 return (r); 772 r = (int)compress_out(a, NULL, 0, ARCHIVE_Z_FINISH); 773 if (r < 0) 774 return (r); 775 header_offset = data_offset + data_size; 776 header_size = zip->stream.total_out; 777 header_crc32 = zip->precode_crc32; 778 header_unpacksize = zip->stream.total_in; 779 780 if (header_compression != _7Z_COPY) { 781 /* 782 * Encode the header in order to reduce the size 783 * of the archive. 784 */ 785 free(zip->coder.props); 786 zip->coder.codec = header_compression; 787 zip->coder.prop_size = zip->stream.prop_size; 788 zip->coder.props = zip->stream.props; 789 zip->stream.prop_size = 0; 790 zip->stream.props = NULL; 791 792 r = _7z_compression_init_encoder(a, _7Z_COPY, 0); 793 if (r < 0) 794 return (r); 795 zip->crc32flg = ENCODED_CRC32; 796 zip->encoded_crc32 = 0; 797 798 /* 799 * Make EncodedHeader. 800 */ 801 r = enc_uint64(a, kEncodedHeader); 802 if (r < 0) 803 return (r); 804 r = make_streamsInfo(a, header_offset, header_size, 805 header_unpacksize, 1, &(zip->coder), 0, 806 header_crc32); 807 if (r < 0) 808 return (r); 809 r = (int)compress_out(a, NULL, 0, ARCHIVE_Z_FINISH); 810 if (r < 0) 811 return (r); 812 header_offset = header_offset + header_size; 813 header_size = zip->stream.total_out; 814 header_crc32 = zip->encoded_crc32; 815 } 816 zip->crc32flg = 0; 817 } else { 818 header_offset = header_size = 0; 819 header_crc32 = 0; 820 } 821 822 length = zip->temp_offset; 823 824 /* 825 * Make the zip header on wbuff(write buffer). 826 */ 827 wb = zip->wbuff; 828 zip->wbuff_remaining = sizeof(zip->wbuff); 829 memcpy(&wb[0], "7z\xBC\xAF\x27\x1C", 6); 830 wb[6] = 0;/* Major version. */ 831 wb[7] = 3;/* Minor version. */ 832 archive_le64enc(&wb[12], header_offset);/* Next Header Offset */ 833 archive_le64enc(&wb[20], header_size);/* Next Header Size */ 834 archive_le32enc(&wb[28], header_crc32);/* Next Header CRC */ 835 archive_le32enc(&wb[8], crc32(0, &wb[12], 20));/* Start Header CRC */ 836 zip->wbuff_remaining -= 32; 837 838 /* 839 * Read all file contents and an encoded header from the temporary 840 * file and write out it. 841 */ 842 r = copy_out(a, 0, length); 843 if (r != ARCHIVE_OK) 844 return (r); 845 r = flush_wbuff(a); 846 return (r); 847 } 848 849 /* 850 * Encode 64 bits value into 7-Zip's encoded UINT64 value. 851 */ 852 static int 853 enc_uint64(struct archive_write *a, uint64_t val) 854 { 855 unsigned mask = 0x80; 856 uint8_t numdata[9]; 857 int i; 858 859 numdata[0] = 0; 860 for (i = 1; i < (int)sizeof(numdata); i++) { 861 if (val < mask) { 862 numdata[0] |= (uint8_t)val; 863 break; 864 } 865 numdata[i] = (uint8_t)val; 866 val >>= 8; 867 numdata[0] |= mask; 868 mask >>= 1; 869 } 870 return ((int)compress_out(a, numdata, i, ARCHIVE_Z_RUN)); 871 } 872 873 static int 874 make_substreamsInfo(struct archive_write *a, struct coder *coders) 875 { 876 struct _7zip *zip = (struct _7zip *)a->format_data; 877 struct file *file; 878 int r; 879 880 /* 881 * Make SubStreamsInfo. 882 */ 883 r = enc_uint64(a, kSubStreamsInfo); 884 if (r < 0) 885 return (r); 886 887 if (zip->total_number_nonempty_entry > 1 && coders->codec != _7Z_COPY) { 888 /* 889 * Make NumUnPackStream. 890 */ 891 r = enc_uint64(a, kNumUnPackStream); 892 if (r < 0) 893 return (r); 894 895 /* Write numUnpackStreams */ 896 r = enc_uint64(a, zip->total_number_nonempty_entry); 897 if (r < 0) 898 return (r); 899 900 /* 901 * Make kSize. 902 */ 903 r = enc_uint64(a, kSize); 904 if (r < 0) 905 return (r); 906 file = zip->file_list.first; 907 for (;file != NULL; file = file->next) { 908 if (file->next == NULL || 909 file->next->size == 0) 910 break; 911 r = enc_uint64(a, file->size); 912 if (r < 0) 913 return (r); 914 } 915 } 916 917 /* 918 * Make CRC. 919 */ 920 r = enc_uint64(a, kCRC); 921 if (r < 0) 922 return (r); 923 924 925 /* All are defined */ 926 r = enc_uint64(a, 1); 927 if (r < 0) 928 return (r); 929 file = zip->file_list.first; 930 for (;file != NULL; file = file->next) { 931 uint8_t crc[4]; 932 if (file->size == 0) 933 break; 934 archive_le32enc(crc, file->crc32); 935 r = (int)compress_out(a, crc, 4, ARCHIVE_Z_RUN); 936 if (r < 0) 937 return (r); 938 } 939 940 /* Write End. */ 941 r = enc_uint64(a, kEnd); 942 if (r < 0) 943 return (r); 944 return (ARCHIVE_OK); 945 } 946 947 static int 948 make_streamsInfo(struct archive_write *a, uint64_t offset, uint64_t pack_size, 949 uint64_t unpack_size, int num_coder, struct coder *coders, int substrm, 950 uint32_t header_crc) 951 { 952 struct _7zip *zip = (struct _7zip *)a->format_data; 953 uint8_t codec_buff[8]; 954 int numFolders, fi; 955 int codec_size; 956 int i, r; 957 958 if (coders->codec == _7Z_COPY) 959 numFolders = (int)zip->total_number_nonempty_entry; 960 else 961 numFolders = 1; 962 963 /* 964 * Make PackInfo. 965 */ 966 r = enc_uint64(a, kPackInfo); 967 if (r < 0) 968 return (r); 969 970 /* Write PackPos. */ 971 r = enc_uint64(a, offset); 972 if (r < 0) 973 return (r); 974 975 /* Write NumPackStreams. */ 976 r = enc_uint64(a, numFolders); 977 if (r < 0) 978 return (r); 979 980 /* Make Size. */ 981 r = enc_uint64(a, kSize); 982 if (r < 0) 983 return (r); 984 985 if (numFolders > 1) { 986 struct file *file = zip->file_list.first; 987 for (;file != NULL; file = file->next) { 988 if (file->size == 0) 989 break; 990 r = enc_uint64(a, file->size); 991 if (r < 0) 992 return (r); 993 } 994 } else { 995 /* Write size. */ 996 r = enc_uint64(a, pack_size); 997 if (r < 0) 998 return (r); 999 } 1000 1001 r = enc_uint64(a, kEnd); 1002 if (r < 0) 1003 return (r); 1004 1005 /* 1006 * Make UnPackInfo. 1007 */ 1008 r = enc_uint64(a, kUnPackInfo); 1009 if (r < 0) 1010 return (r); 1011 1012 /* 1013 * Make Folder. 1014 */ 1015 r = enc_uint64(a, kFolder); 1016 if (r < 0) 1017 return (r); 1018 1019 /* Write NumFolders. */ 1020 r = enc_uint64(a, numFolders); 1021 if (r < 0) 1022 return (r); 1023 1024 /* Write External. */ 1025 r = enc_uint64(a, 0); 1026 if (r < 0) 1027 return (r); 1028 1029 for (fi = 0; fi < numFolders; fi++) { 1030 /* Write NumCoders. */ 1031 r = enc_uint64(a, num_coder); 1032 if (r < 0) 1033 return (r); 1034 1035 for (i = 0; i < num_coder; i++) { 1036 unsigned codec_id = coders[i].codec; 1037 1038 /* Write Codec flag. */ 1039 archive_be64enc(codec_buff, codec_id); 1040 for (codec_size = 8; codec_size > 0; codec_size--) { 1041 if (codec_buff[8 - codec_size]) 1042 break; 1043 } 1044 if (codec_size == 0) 1045 codec_size = 1; 1046 if (coders[i].prop_size) 1047 r = enc_uint64(a, codec_size | 0x20); 1048 else 1049 r = enc_uint64(a, codec_size); 1050 if (r < 0) 1051 return (r); 1052 1053 /* Write Codec ID. */ 1054 codec_size &= 0x0f; 1055 r = (int)compress_out(a, &codec_buff[8-codec_size], 1056 codec_size, ARCHIVE_Z_RUN); 1057 if (r < 0) 1058 return (r); 1059 1060 if (coders[i].prop_size) { 1061 /* Write Codec property size. */ 1062 r = enc_uint64(a, coders[i].prop_size); 1063 if (r < 0) 1064 return (r); 1065 1066 /* Write Codec properties. */ 1067 r = (int)compress_out(a, coders[i].props, 1068 coders[i].prop_size, ARCHIVE_Z_RUN); 1069 if (r < 0) 1070 return (r); 1071 } 1072 } 1073 } 1074 1075 /* 1076 * Make CodersUnPackSize. 1077 */ 1078 r = enc_uint64(a, kCodersUnPackSize); 1079 if (r < 0) 1080 return (r); 1081 1082 if (numFolders > 1) { 1083 struct file *file = zip->file_list.first; 1084 for (;file != NULL; file = file->next) { 1085 if (file->size == 0) 1086 break; 1087 r = enc_uint64(a, file->size); 1088 if (r < 0) 1089 return (r); 1090 } 1091 1092 } else { 1093 /* Write UnPackSize. */ 1094 r = enc_uint64(a, unpack_size); 1095 if (r < 0) 1096 return (r); 1097 } 1098 1099 if (!substrm) { 1100 uint8_t crc[4]; 1101 /* 1102 * Make CRC. 1103 */ 1104 r = enc_uint64(a, kCRC); 1105 if (r < 0) 1106 return (r); 1107 1108 /* All are defined */ 1109 r = enc_uint64(a, 1); 1110 if (r < 0) 1111 return (r); 1112 archive_le32enc(crc, header_crc); 1113 r = (int)compress_out(a, crc, 4, ARCHIVE_Z_RUN); 1114 if (r < 0) 1115 return (r); 1116 } 1117 1118 /* Write End. */ 1119 r = enc_uint64(a, kEnd); 1120 if (r < 0) 1121 return (r); 1122 1123 if (substrm) { 1124 /* 1125 * Make SubStreamsInfo. 1126 */ 1127 r = make_substreamsInfo(a, coders); 1128 if (r < 0) 1129 return (r); 1130 } 1131 1132 1133 /* Write End. */ 1134 r = enc_uint64(a, kEnd); 1135 if (r < 0) 1136 return (r); 1137 1138 return (ARCHIVE_OK); 1139 } 1140 1141 1142 #define EPOC_TIME ARCHIVE_LITERAL_ULL(116444736000000000) 1143 static uint64_t 1144 utcToFiletime(time_t t, long ns) 1145 { 1146 uint64_t fileTime; 1147 1148 fileTime = t; 1149 fileTime *= 10000000; 1150 fileTime += ns / 100; 1151 fileTime += EPOC_TIME; 1152 return (fileTime); 1153 } 1154 1155 static int 1156 make_time(struct archive_write *a, uint8_t type, unsigned flg, int ti) 1157 { 1158 uint8_t filetime[8]; 1159 struct _7zip *zip = (struct _7zip *)a->format_data; 1160 struct file *file; 1161 int r; 1162 uint8_t b, mask; 1163 1164 /* 1165 * Make Time Bools. 1166 */ 1167 if (zip->total_number_time_defined[ti] == zip->total_number_entry) { 1168 /* Write Time Type. */ 1169 r = enc_uint64(a, type); 1170 if (r < 0) 1171 return (r); 1172 /* Write EmptyStream Size. */ 1173 r = enc_uint64(a, 2 + zip->total_number_entry * 8); 1174 if (r < 0) 1175 return (r); 1176 /* All are defined. */ 1177 r = enc_uint64(a, 1); 1178 if (r < 0) 1179 return (r); 1180 } else { 1181 if (zip->total_number_time_defined[ti] == 0) 1182 return (ARCHIVE_OK); 1183 1184 /* Write Time Type. */ 1185 r = enc_uint64(a, type); 1186 if (r < 0) 1187 return (r); 1188 /* Write EmptyStream Size. */ 1189 r = enc_uint64(a, 2 + ((zip->total_number_entry + 7) >> 3) 1190 + zip->total_number_time_defined[ti] * 8); 1191 if (r < 0) 1192 return (r); 1193 1194 /* All are not defined. */ 1195 r = enc_uint64(a, 0); 1196 if (r < 0) 1197 return (r); 1198 1199 b = 0; 1200 mask = 0x80; 1201 file = zip->file_list.first; 1202 for (;file != NULL; file = file->next) { 1203 if (file->flg & flg) 1204 b |= mask; 1205 mask >>= 1; 1206 if (mask == 0) { 1207 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1208 if (r < 0) 1209 return (r); 1210 mask = 0x80; 1211 b = 0; 1212 } 1213 } 1214 if (mask != 0x80) { 1215 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1216 if (r < 0) 1217 return (r); 1218 } 1219 } 1220 1221 /* External. */ 1222 r = enc_uint64(a, 0); 1223 if (r < 0) 1224 return (r); 1225 1226 1227 /* 1228 * Make Times. 1229 */ 1230 file = zip->file_list.first; 1231 for (;file != NULL; file = file->next) { 1232 if ((file->flg & flg) == 0) 1233 continue; 1234 archive_le64enc(filetime, utcToFiletime(file->times[ti].time, 1235 file->times[ti].time_ns)); 1236 r = (int)compress_out(a, filetime, 8, ARCHIVE_Z_RUN); 1237 if (r < 0) 1238 return (r); 1239 } 1240 1241 return (ARCHIVE_OK); 1242 } 1243 1244 static int 1245 make_header(struct archive_write *a, uint64_t offset, uint64_t pack_size, 1246 uint64_t unpack_size, int codernum, struct coder *coders) 1247 { 1248 struct _7zip *zip = (struct _7zip *)a->format_data; 1249 struct file *file; 1250 int r; 1251 uint8_t b, mask; 1252 1253 /* 1254 * Make FilesInfo. 1255 */ 1256 r = enc_uint64(a, kHeader); 1257 if (r < 0) 1258 return (r); 1259 1260 /* 1261 * If there are empty files only, do not write MainStreamInfo. 1262 */ 1263 if (zip->total_number_nonempty_entry) { 1264 /* 1265 * Make MainStreamInfo. 1266 */ 1267 r = enc_uint64(a, kMainStreamsInfo); 1268 if (r < 0) 1269 return (r); 1270 r = make_streamsInfo(a, offset, pack_size, unpack_size, 1271 codernum, coders, 1, 0); 1272 if (r < 0) 1273 return (r); 1274 } 1275 1276 /* 1277 * Make FilesInfo. 1278 */ 1279 r = enc_uint64(a, kFilesInfo); 1280 if (r < 0) 1281 return (r); 1282 1283 /* Write numFiles. */ 1284 r = enc_uint64(a, zip->total_number_entry); 1285 if (r < 0) 1286 return (r); 1287 1288 if (zip->total_number_empty_entry > 0) { 1289 /* Make EmptyStream. */ 1290 r = enc_uint64(a, kEmptyStream); 1291 if (r < 0) 1292 return (r); 1293 1294 /* Write EmptyStream Size. */ 1295 r = enc_uint64(a, (zip->total_number_entry+7)>>3); 1296 if (r < 0) 1297 return (r); 1298 1299 b = 0; 1300 mask = 0x80; 1301 file = zip->file_list.first; 1302 for (;file != NULL; file = file->next) { 1303 if (file->size == 0) 1304 b |= mask; 1305 mask >>= 1; 1306 if (mask == 0) { 1307 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1308 if (r < 0) 1309 return (r); 1310 mask = 0x80; 1311 b = 0; 1312 } 1313 } 1314 if (mask != 0x80) { 1315 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1316 if (r < 0) 1317 return (r); 1318 } 1319 } 1320 1321 if (zip->total_number_empty_entry > zip->total_number_dir_entry) { 1322 /* Make EmptyFile. */ 1323 r = enc_uint64(a, kEmptyFile); 1324 if (r < 0) 1325 return (r); 1326 1327 /* Write EmptyFile Size. */ 1328 r = enc_uint64(a, (zip->total_number_empty_entry + 7) >> 3); 1329 if (r < 0) 1330 return (r); 1331 1332 b = 0; 1333 mask = 0x80; 1334 file = zip->file_list.first; 1335 for (;file != NULL; file = file->next) { 1336 if (file->size) 1337 continue; 1338 if (!file->dir) 1339 b |= mask; 1340 mask >>= 1; 1341 if (mask == 0) { 1342 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1343 if (r < 0) 1344 return (r); 1345 mask = 0x80; 1346 b = 0; 1347 } 1348 } 1349 if (mask != 0x80) { 1350 r = (int)compress_out(a, &b, 1, ARCHIVE_Z_RUN); 1351 if (r < 0) 1352 return (r); 1353 } 1354 } 1355 1356 /* Make Name. */ 1357 r = enc_uint64(a, kName); 1358 if (r < 0) 1359 return (r); 1360 1361 /* Write Nume size. */ 1362 r = enc_uint64(a, zip->total_bytes_entry_name+1); 1363 if (r < 0) 1364 return (r); 1365 1366 /* Write dmy byte. */ 1367 r = enc_uint64(a, 0); 1368 if (r < 0) 1369 return (r); 1370 1371 file = zip->file_list.first; 1372 for (;file != NULL; file = file->next) { 1373 r = (int)compress_out(a, file->utf16name, file->name_len+2, 1374 ARCHIVE_Z_RUN); 1375 if (r < 0) 1376 return (r); 1377 } 1378 1379 /* Make MTime. */ 1380 r = make_time(a, kMTime, MTIME_IS_SET, MTIME); 1381 if (r < 0) 1382 return (r); 1383 1384 /* Make CTime. */ 1385 r = make_time(a, kCTime, CTIME_IS_SET, CTIME); 1386 if (r < 0) 1387 return (r); 1388 1389 /* Make ATime. */ 1390 r = make_time(a, kATime, ATIME_IS_SET, ATIME); 1391 if (r < 0) 1392 return (r); 1393 1394 /* Make Attributes. */ 1395 r = enc_uint64(a, kAttributes); 1396 if (r < 0) 1397 return (r); 1398 1399 /* Write Attributes size. */ 1400 r = enc_uint64(a, 2 + zip->total_number_entry * 4); 1401 if (r < 0) 1402 return (r); 1403 1404 /* Write "All Are Defined". */ 1405 r = enc_uint64(a, 1); 1406 if (r < 0) 1407 return (r); 1408 1409 /* Write dmy byte. */ 1410 r = enc_uint64(a, 0); 1411 if (r < 0) 1412 return (r); 1413 1414 file = zip->file_list.first; 1415 for (;file != NULL; file = file->next) { 1416 /* 1417 * High 16bits is unix mode. 1418 * Low 16bits is Windows attributes. 1419 */ 1420 uint32_t encattr, attr; 1421 if (file->dir) 1422 attr = 0x8010; 1423 else 1424 attr = 0x8020; 1425 if ((file->mode & 0222) == 0) 1426 attr |= 1;/* Read Only. */ 1427 attr |= ((uint32_t)file->mode) << 16; 1428 archive_le32enc(&encattr, attr); 1429 r = (int)compress_out(a, &encattr, 4, ARCHIVE_Z_RUN); 1430 if (r < 0) 1431 return (r); 1432 } 1433 1434 /* Write End. */ 1435 r = enc_uint64(a, kEnd); 1436 if (r < 0) 1437 return (r); 1438 1439 /* Write End. */ 1440 r = enc_uint64(a, kEnd); 1441 if (r < 0) 1442 return (r); 1443 1444 return (ARCHIVE_OK); 1445 } 1446 1447 1448 static int 1449 _7z_free(struct archive_write *a) 1450 { 1451 struct _7zip *zip = (struct _7zip *)a->format_data; 1452 1453 file_free_register(zip); 1454 compression_end(&(a->archive), &(zip->stream)); 1455 free(zip->coder.props); 1456 free(zip); 1457 1458 return (ARCHIVE_OK); 1459 } 1460 1461 static int 1462 file_cmp_node(const struct archive_rb_node *n1, 1463 const struct archive_rb_node *n2) 1464 { 1465 const struct file *f1 = (const struct file *)n1; 1466 const struct file *f2 = (const struct file *)n2; 1467 1468 if (f1->name_len == f2->name_len) 1469 return (memcmp(f1->utf16name, f2->utf16name, f1->name_len)); 1470 return (f1->name_len > f2->name_len)?1:-1; 1471 } 1472 1473 static int 1474 file_cmp_key(const struct archive_rb_node *n, const void *key) 1475 { 1476 const struct file *f = (const struct file *)n; 1477 1478 return (f->name_len - *(const char *)key); 1479 } 1480 1481 static int 1482 file_new(struct archive_write *a, struct archive_entry *entry, 1483 struct file **newfile) 1484 { 1485 struct _7zip *zip; 1486 struct file *file; 1487 const char *u16; 1488 size_t u16len; 1489 int ret = ARCHIVE_OK; 1490 1491 zip = (struct _7zip *)a->format_data; 1492 *newfile = NULL; 1493 1494 file = calloc(1, sizeof(*file)); 1495 if (file == NULL) { 1496 archive_set_error(&a->archive, ENOMEM, 1497 "Can't allocate memory"); 1498 return (ARCHIVE_FATAL); 1499 } 1500 1501 if (0 > archive_entry_pathname_l(entry, &u16, &u16len, zip->sconv)) { 1502 if (errno == ENOMEM) { 1503 free(file); 1504 archive_set_error(&a->archive, ENOMEM, 1505 "Can't allocate memory for UTF-16LE"); 1506 return (ARCHIVE_FATAL); 1507 } 1508 archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC, 1509 "A filename cannot be converted to UTF-16LE;" 1510 "You should disable making Joliet extension"); 1511 ret = ARCHIVE_WARN; 1512 } 1513 file->utf16name = malloc(u16len + 2); 1514 if (file->utf16name == NULL) { 1515 free(file); 1516 archive_set_error(&a->archive, ENOMEM, 1517 "Can't allocate memory for Name"); 1518 return (ARCHIVE_FATAL); 1519 } 1520 memcpy(file->utf16name, u16, u16len); 1521 file->utf16name[u16len+0] = 0; 1522 file->utf16name[u16len+1] = 0; 1523 file->name_len = (unsigned)u16len; 1524 file->mode = archive_entry_mode(entry); 1525 if (archive_entry_filetype(entry) == AE_IFREG) 1526 file->size = archive_entry_size(entry); 1527 else 1528 archive_entry_set_size(entry, 0); 1529 if (archive_entry_filetype(entry) == AE_IFDIR) 1530 file->dir = 1; 1531 else if (archive_entry_filetype(entry) == AE_IFLNK) 1532 file->size = strlen(archive_entry_symlink(entry)); 1533 if (archive_entry_mtime_is_set(entry)) { 1534 file->flg |= MTIME_IS_SET; 1535 file->times[MTIME].time = archive_entry_mtime(entry); 1536 file->times[MTIME].time_ns = archive_entry_mtime_nsec(entry); 1537 } 1538 if (archive_entry_atime_is_set(entry)) { 1539 file->flg |= ATIME_IS_SET; 1540 file->times[ATIME].time = archive_entry_atime(entry); 1541 file->times[ATIME].time_ns = archive_entry_atime_nsec(entry); 1542 } 1543 if (archive_entry_ctime_is_set(entry)) { 1544 file->flg |= CTIME_IS_SET; 1545 file->times[CTIME].time = archive_entry_ctime(entry); 1546 file->times[CTIME].time_ns = archive_entry_ctime_nsec(entry); 1547 } 1548 1549 *newfile = file; 1550 return (ret); 1551 } 1552 1553 static void 1554 file_free(struct file *file) 1555 { 1556 free(file->utf16name); 1557 free(file); 1558 } 1559 1560 static void 1561 file_register(struct _7zip *zip, struct file *file) 1562 { 1563 file->next = NULL; 1564 *zip->file_list.last = file; 1565 zip->file_list.last = &(file->next); 1566 } 1567 1568 static void 1569 file_init_register(struct _7zip *zip) 1570 { 1571 zip->file_list.first = NULL; 1572 zip->file_list.last = &(zip->file_list.first); 1573 } 1574 1575 static void 1576 file_free_register(struct _7zip *zip) 1577 { 1578 struct file *file, *file_next; 1579 1580 file = zip->file_list.first; 1581 while (file != NULL) { 1582 file_next = file->next; 1583 file_free(file); 1584 file = file_next; 1585 } 1586 } 1587 1588 static void 1589 file_register_empty(struct _7zip *zip, struct file *file) 1590 { 1591 file->next = NULL; 1592 *zip->empty_list.last = file; 1593 zip->empty_list.last = &(file->next); 1594 } 1595 1596 static void 1597 file_init_register_empty(struct _7zip *zip) 1598 { 1599 zip->empty_list.first = NULL; 1600 zip->empty_list.last = &(zip->empty_list.first); 1601 } 1602 1603 #if !defined(HAVE_ZLIB_H) || !defined(HAVE_BZLIB_H) ||\ 1604 !defined(BZ_CONFIG_ERROR) || !defined(HAVE_LZMA_H) 1605 static int 1606 compression_unsupported_encoder(struct archive *a, 1607 struct la_zstream *lastrm, const char *name) 1608 { 1609 1610 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1611 "%s compression not supported on this platform", name); 1612 lastrm->valid = 0; 1613 lastrm->real_stream = NULL; 1614 return (ARCHIVE_FAILED); 1615 } 1616 #endif 1617 1618 /* 1619 * _7_COPY compressor. 1620 */ 1621 static int 1622 compression_init_encoder_copy(struct archive *a, struct la_zstream *lastrm) 1623 { 1624 1625 if (lastrm->valid) 1626 compression_end(a, lastrm); 1627 lastrm->valid = 1; 1628 lastrm->code = compression_code_copy; 1629 lastrm->end = compression_end_copy; 1630 return (ARCHIVE_OK); 1631 } 1632 1633 static int 1634 compression_code_copy(struct archive *a, 1635 struct la_zstream *lastrm, enum la_zaction action) 1636 { 1637 size_t bytes; 1638 1639 (void)a; /* UNUSED */ 1640 if (lastrm->avail_out > lastrm->avail_in) 1641 bytes = lastrm->avail_in; 1642 else 1643 bytes = lastrm->avail_out; 1644 if (bytes) { 1645 memcpy(lastrm->next_out, lastrm->next_in, bytes); 1646 lastrm->next_in += bytes; 1647 lastrm->avail_in -= bytes; 1648 lastrm->total_in += bytes; 1649 lastrm->next_out += bytes; 1650 lastrm->avail_out -= bytes; 1651 lastrm->total_out += bytes; 1652 } 1653 if (action == ARCHIVE_Z_FINISH && lastrm->avail_in == 0) 1654 return (ARCHIVE_EOF); 1655 return (ARCHIVE_OK); 1656 } 1657 1658 static int 1659 compression_end_copy(struct archive *a, struct la_zstream *lastrm) 1660 { 1661 (void)a; /* UNUSED */ 1662 lastrm->valid = 0; 1663 return (ARCHIVE_OK); 1664 } 1665 1666 /* 1667 * _7_DEFLATE compressor. 1668 */ 1669 #ifdef HAVE_ZLIB_H 1670 static int 1671 compression_init_encoder_deflate(struct archive *a, 1672 struct la_zstream *lastrm, int level, int withheader) 1673 { 1674 z_stream *strm; 1675 1676 if (lastrm->valid) 1677 compression_end(a, lastrm); 1678 strm = calloc(1, sizeof(*strm)); 1679 if (strm == NULL) { 1680 archive_set_error(a, ENOMEM, 1681 "Can't allocate memory for gzip stream"); 1682 return (ARCHIVE_FATAL); 1683 } 1684 /* zlib.h is not const-correct, so we need this one bit 1685 * of ugly hackery to convert a const * pointer to 1686 * a non-const pointer. */ 1687 strm->next_in = (Bytef *)(uintptr_t)(const void *)lastrm->next_in; 1688 strm->avail_in = (uInt)lastrm->avail_in; 1689 strm->total_in = (uLong)lastrm->total_in; 1690 strm->next_out = lastrm->next_out; 1691 strm->avail_out = (uInt)lastrm->avail_out; 1692 strm->total_out = (uLong)lastrm->total_out; 1693 if (deflateInit2(strm, level, Z_DEFLATED, 1694 (withheader)?15:-15, 1695 8, Z_DEFAULT_STRATEGY) != Z_OK) { 1696 free(strm); 1697 lastrm->real_stream = NULL; 1698 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1699 "Internal error initializing compression library"); 1700 return (ARCHIVE_FATAL); 1701 } 1702 lastrm->real_stream = strm; 1703 lastrm->valid = 1; 1704 lastrm->code = compression_code_deflate; 1705 lastrm->end = compression_end_deflate; 1706 return (ARCHIVE_OK); 1707 } 1708 1709 static int 1710 compression_code_deflate(struct archive *a, 1711 struct la_zstream *lastrm, enum la_zaction action) 1712 { 1713 z_stream *strm; 1714 int r; 1715 1716 strm = (z_stream *)lastrm->real_stream; 1717 /* zlib.h is not const-correct, so we need this one bit 1718 * of ugly hackery to convert a const * pointer to 1719 * a non-const pointer. */ 1720 strm->next_in = (Bytef *)(uintptr_t)(const void *)lastrm->next_in; 1721 strm->avail_in = (uInt)lastrm->avail_in; 1722 strm->total_in = (uLong)lastrm->total_in; 1723 strm->next_out = lastrm->next_out; 1724 strm->avail_out = (uInt)lastrm->avail_out; 1725 strm->total_out = (uLong)lastrm->total_out; 1726 r = deflate(strm, 1727 (action == ARCHIVE_Z_FINISH)? Z_FINISH: Z_NO_FLUSH); 1728 lastrm->next_in = strm->next_in; 1729 lastrm->avail_in = strm->avail_in; 1730 lastrm->total_in = strm->total_in; 1731 lastrm->next_out = strm->next_out; 1732 lastrm->avail_out = strm->avail_out; 1733 lastrm->total_out = strm->total_out; 1734 switch (r) { 1735 case Z_OK: 1736 return (ARCHIVE_OK); 1737 case Z_STREAM_END: 1738 return (ARCHIVE_EOF); 1739 default: 1740 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1741 "GZip compression failed:" 1742 " deflate() call returned status %d", r); 1743 return (ARCHIVE_FATAL); 1744 } 1745 } 1746 1747 static int 1748 compression_end_deflate(struct archive *a, struct la_zstream *lastrm) 1749 { 1750 z_stream *strm; 1751 int r; 1752 1753 strm = (z_stream *)lastrm->real_stream; 1754 r = deflateEnd(strm); 1755 free(strm); 1756 lastrm->real_stream = NULL; 1757 lastrm->valid = 0; 1758 if (r != Z_OK) { 1759 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1760 "Failed to clean up compressor"); 1761 return (ARCHIVE_FATAL); 1762 } 1763 return (ARCHIVE_OK); 1764 } 1765 #else 1766 static int 1767 compression_init_encoder_deflate(struct archive *a, 1768 struct la_zstream *lastrm, int level, int withheader) 1769 { 1770 1771 (void) level; /* UNUSED */ 1772 (void) withheader; /* UNUSED */ 1773 if (lastrm->valid) 1774 compression_end(a, lastrm); 1775 return (compression_unsupported_encoder(a, lastrm, "deflate")); 1776 } 1777 #endif 1778 1779 /* 1780 * _7_BZIP2 compressor. 1781 */ 1782 #if defined(HAVE_BZLIB_H) && defined(BZ_CONFIG_ERROR) 1783 static int 1784 compression_init_encoder_bzip2(struct archive *a, 1785 struct la_zstream *lastrm, int level) 1786 { 1787 bz_stream *strm; 1788 1789 if (lastrm->valid) 1790 compression_end(a, lastrm); 1791 strm = calloc(1, sizeof(*strm)); 1792 if (strm == NULL) { 1793 archive_set_error(a, ENOMEM, 1794 "Can't allocate memory for bzip2 stream"); 1795 return (ARCHIVE_FATAL); 1796 } 1797 /* bzlib.h is not const-correct, so we need this one bit 1798 * of ugly hackery to convert a const * pointer to 1799 * a non-const pointer. */ 1800 strm->next_in = (char *)(uintptr_t)(const void *)lastrm->next_in; 1801 strm->avail_in = lastrm->avail_in; 1802 strm->total_in_lo32 = (uint32_t)(lastrm->total_in & 0xffffffff); 1803 strm->total_in_hi32 = (uint32_t)(lastrm->total_in >> 32); 1804 strm->next_out = (char *)lastrm->next_out; 1805 strm->avail_out = lastrm->avail_out; 1806 strm->total_out_lo32 = (uint32_t)(lastrm->total_out & 0xffffffff); 1807 strm->total_out_hi32 = (uint32_t)(lastrm->total_out >> 32); 1808 if (BZ2_bzCompressInit(strm, level, 0, 30) != BZ_OK) { 1809 free(strm); 1810 lastrm->real_stream = NULL; 1811 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1812 "Internal error initializing compression library"); 1813 return (ARCHIVE_FATAL); 1814 } 1815 lastrm->real_stream = strm; 1816 lastrm->valid = 1; 1817 lastrm->code = compression_code_bzip2; 1818 lastrm->end = compression_end_bzip2; 1819 return (ARCHIVE_OK); 1820 } 1821 1822 static int 1823 compression_code_bzip2(struct archive *a, 1824 struct la_zstream *lastrm, enum la_zaction action) 1825 { 1826 bz_stream *strm; 1827 int r; 1828 1829 strm = (bz_stream *)lastrm->real_stream; 1830 /* bzlib.h is not const-correct, so we need this one bit 1831 * of ugly hackery to convert a const * pointer to 1832 * a non-const pointer. */ 1833 strm->next_in = (char *)(uintptr_t)(const void *)lastrm->next_in; 1834 strm->avail_in = lastrm->avail_in; 1835 strm->total_in_lo32 = (uint32_t)(lastrm->total_in & 0xffffffff); 1836 strm->total_in_hi32 = (uint32_t)(lastrm->total_in >> 32); 1837 strm->next_out = (char *)lastrm->next_out; 1838 strm->avail_out = lastrm->avail_out; 1839 strm->total_out_lo32 = (uint32_t)(lastrm->total_out & 0xffffffff); 1840 strm->total_out_hi32 = (uint32_t)(lastrm->total_out >> 32); 1841 r = BZ2_bzCompress(strm, 1842 (action == ARCHIVE_Z_FINISH)? BZ_FINISH: BZ_RUN); 1843 lastrm->next_in = (const unsigned char *)strm->next_in; 1844 lastrm->avail_in = strm->avail_in; 1845 lastrm->total_in = 1846 (((uint64_t)(uint32_t)strm->total_in_hi32) << 32) 1847 + (uint64_t)(uint32_t)strm->total_in_lo32; 1848 lastrm->next_out = (unsigned char *)strm->next_out; 1849 lastrm->avail_out = strm->avail_out; 1850 lastrm->total_out = 1851 (((uint64_t)(uint32_t)strm->total_out_hi32) << 32) 1852 + (uint64_t)(uint32_t)strm->total_out_lo32; 1853 switch (r) { 1854 case BZ_RUN_OK: /* Non-finishing */ 1855 case BZ_FINISH_OK: /* Finishing: There's more work to do */ 1856 return (ARCHIVE_OK); 1857 case BZ_STREAM_END: /* Finishing: all done */ 1858 /* Only occurs in finishing case */ 1859 return (ARCHIVE_EOF); 1860 default: 1861 /* Any other return value indicates an error */ 1862 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1863 "Bzip2 compression failed:" 1864 " BZ2_bzCompress() call returned status %d", r); 1865 return (ARCHIVE_FATAL); 1866 } 1867 } 1868 1869 static int 1870 compression_end_bzip2(struct archive *a, struct la_zstream *lastrm) 1871 { 1872 bz_stream *strm; 1873 int r; 1874 1875 strm = (bz_stream *)lastrm->real_stream; 1876 r = BZ2_bzCompressEnd(strm); 1877 free(strm); 1878 lastrm->real_stream = NULL; 1879 lastrm->valid = 0; 1880 if (r != BZ_OK) { 1881 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1882 "Failed to clean up compressor"); 1883 return (ARCHIVE_FATAL); 1884 } 1885 return (ARCHIVE_OK); 1886 } 1887 1888 #else 1889 static int 1890 compression_init_encoder_bzip2(struct archive *a, 1891 struct la_zstream *lastrm, int level) 1892 { 1893 1894 (void) level; /* UNUSED */ 1895 if (lastrm->valid) 1896 compression_end(a, lastrm); 1897 return (compression_unsupported_encoder(a, lastrm, "bzip2")); 1898 } 1899 #endif 1900 1901 /* 1902 * _7_LZMA1, _7_LZMA2 compressor. 1903 */ 1904 #if defined(HAVE_LZMA_H) 1905 static int 1906 compression_init_encoder_lzma(struct archive *a, 1907 struct la_zstream *lastrm, int level, uint64_t filter_id) 1908 { 1909 static const lzma_stream lzma_init_data = LZMA_STREAM_INIT; 1910 lzma_stream *strm; 1911 lzma_filter *lzmafilters; 1912 lzma_options_lzma lzma_opt; 1913 int r; 1914 1915 if (lastrm->valid) 1916 compression_end(a, lastrm); 1917 strm = calloc(1, sizeof(*strm) + sizeof(*lzmafilters) * 2); 1918 if (strm == NULL) { 1919 archive_set_error(a, ENOMEM, 1920 "Can't allocate memory for lzma stream"); 1921 return (ARCHIVE_FATAL); 1922 } 1923 lzmafilters = (lzma_filter *)(strm+1); 1924 if (level > 6) 1925 level = 6; 1926 if (lzma_lzma_preset(&lzma_opt, level)) { 1927 free(strm); 1928 lastrm->real_stream = NULL; 1929 archive_set_error(a, ENOMEM, 1930 "Internal error initializing compression library"); 1931 return (ARCHIVE_FATAL); 1932 } 1933 lzmafilters[0].id = filter_id; 1934 lzmafilters[0].options = &lzma_opt; 1935 lzmafilters[1].id = LZMA_VLI_UNKNOWN;/* Terminate */ 1936 1937 r = lzma_properties_size(&(lastrm->prop_size), lzmafilters); 1938 if (r != LZMA_OK) { 1939 free(strm); 1940 lastrm->real_stream = NULL; 1941 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1942 "lzma_properties_size failed"); 1943 return (ARCHIVE_FATAL); 1944 } 1945 if (lastrm->prop_size) { 1946 lastrm->props = malloc(lastrm->prop_size); 1947 if (lastrm->props == NULL) { 1948 free(strm); 1949 lastrm->real_stream = NULL; 1950 archive_set_error(a, ENOMEM, 1951 "Cannot allocate memory"); 1952 return (ARCHIVE_FATAL); 1953 } 1954 r = lzma_properties_encode(lzmafilters, lastrm->props); 1955 if (r != LZMA_OK) { 1956 free(strm); 1957 lastrm->real_stream = NULL; 1958 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1959 "lzma_properties_encode failed"); 1960 return (ARCHIVE_FATAL); 1961 } 1962 } 1963 1964 *strm = lzma_init_data; 1965 r = lzma_raw_encoder(strm, lzmafilters); 1966 switch (r) { 1967 case LZMA_OK: 1968 lastrm->real_stream = strm; 1969 lastrm->valid = 1; 1970 lastrm->code = compression_code_lzma; 1971 lastrm->end = compression_end_lzma; 1972 r = ARCHIVE_OK; 1973 break; 1974 case LZMA_MEM_ERROR: 1975 free(strm); 1976 lastrm->real_stream = NULL; 1977 archive_set_error(a, ENOMEM, 1978 "Internal error initializing compression library: " 1979 "Cannot allocate memory"); 1980 r = ARCHIVE_FATAL; 1981 break; 1982 default: 1983 free(strm); 1984 lastrm->real_stream = NULL; 1985 archive_set_error(a, ARCHIVE_ERRNO_MISC, 1986 "Internal error initializing compression library: " 1987 "It's a bug in liblzma"); 1988 r = ARCHIVE_FATAL; 1989 break; 1990 } 1991 return (r); 1992 } 1993 1994 static int 1995 compression_init_encoder_lzma1(struct archive *a, 1996 struct la_zstream *lastrm, int level) 1997 { 1998 return compression_init_encoder_lzma(a, lastrm, level, 1999 LZMA_FILTER_LZMA1); 2000 } 2001 2002 static int 2003 compression_init_encoder_lzma2(struct archive *a, 2004 struct la_zstream *lastrm, int level) 2005 { 2006 return compression_init_encoder_lzma(a, lastrm, level, 2007 LZMA_FILTER_LZMA2); 2008 } 2009 2010 static int 2011 compression_code_lzma(struct archive *a, 2012 struct la_zstream *lastrm, enum la_zaction action) 2013 { 2014 lzma_stream *strm; 2015 int r; 2016 2017 strm = (lzma_stream *)lastrm->real_stream; 2018 strm->next_in = lastrm->next_in; 2019 strm->avail_in = lastrm->avail_in; 2020 strm->total_in = lastrm->total_in; 2021 strm->next_out = lastrm->next_out; 2022 strm->avail_out = lastrm->avail_out; 2023 strm->total_out = lastrm->total_out; 2024 r = lzma_code(strm, 2025 (action == ARCHIVE_Z_FINISH)? LZMA_FINISH: LZMA_RUN); 2026 lastrm->next_in = strm->next_in; 2027 lastrm->avail_in = strm->avail_in; 2028 lastrm->total_in = strm->total_in; 2029 lastrm->next_out = strm->next_out; 2030 lastrm->avail_out = strm->avail_out; 2031 lastrm->total_out = strm->total_out; 2032 switch (r) { 2033 case LZMA_OK: 2034 /* Non-finishing case */ 2035 return (ARCHIVE_OK); 2036 case LZMA_STREAM_END: 2037 /* This return can only occur in finishing case. */ 2038 return (ARCHIVE_EOF); 2039 case LZMA_MEMLIMIT_ERROR: 2040 archive_set_error(a, ENOMEM, 2041 "lzma compression error:" 2042 " %ju MiB would have been needed", 2043 (uintmax_t)((lzma_memusage(strm) + 1024 * 1024 -1) 2044 / (1024 * 1024))); 2045 return (ARCHIVE_FATAL); 2046 default: 2047 /* Any other return value indicates an error */ 2048 archive_set_error(a, ARCHIVE_ERRNO_MISC, 2049 "lzma compression failed:" 2050 " lzma_code() call returned status %d", r); 2051 return (ARCHIVE_FATAL); 2052 } 2053 } 2054 2055 static int 2056 compression_end_lzma(struct archive *a, struct la_zstream *lastrm) 2057 { 2058 lzma_stream *strm; 2059 2060 (void)a; /* UNUSED */ 2061 strm = (lzma_stream *)lastrm->real_stream; 2062 lzma_end(strm); 2063 free(strm); 2064 lastrm->valid = 0; 2065 lastrm->real_stream = NULL; 2066 return (ARCHIVE_OK); 2067 } 2068 #else 2069 static int 2070 compression_init_encoder_lzma1(struct archive *a, 2071 struct la_zstream *lastrm, int level) 2072 { 2073 2074 (void) level; /* UNUSED */ 2075 if (lastrm->valid) 2076 compression_end(a, lastrm); 2077 return (compression_unsupported_encoder(a, lastrm, "lzma")); 2078 } 2079 static int 2080 compression_init_encoder_lzma2(struct archive *a, 2081 struct la_zstream *lastrm, int level) 2082 { 2083 2084 (void) level; /* UNUSED */ 2085 if (lastrm->valid) 2086 compression_end(a, lastrm); 2087 return (compression_unsupported_encoder(a, lastrm, "lzma")); 2088 } 2089 #endif 2090 2091 /* 2092 * _7_PPMD compressor. 2093 */ 2094 static void * 2095 ppmd_alloc(void *p, size_t size) 2096 { 2097 (void)p; 2098 return malloc(size); 2099 } 2100 static void 2101 ppmd_free(void *p, void *address) 2102 { 2103 (void)p; 2104 free(address); 2105 } 2106 static ISzAlloc g_szalloc = { ppmd_alloc, ppmd_free }; 2107 static void 2108 ppmd_write(void *p, Byte b) 2109 { 2110 struct archive_write *a = ((IByteOut *)p)->a; 2111 struct _7zip *zip = (struct _7zip *)(a->format_data); 2112 struct la_zstream *lastrm = &(zip->stream); 2113 struct ppmd_stream *strm; 2114 2115 if (lastrm->avail_out) { 2116 *lastrm->next_out++ = b; 2117 lastrm->avail_out--; 2118 lastrm->total_out++; 2119 return; 2120 } 2121 strm = (struct ppmd_stream *)lastrm->real_stream; 2122 if (strm->buff_ptr < strm->buff_end) { 2123 *strm->buff_ptr++ = b; 2124 strm->buff_bytes++; 2125 } 2126 } 2127 2128 static int 2129 compression_init_encoder_ppmd(struct archive *a, 2130 struct la_zstream *lastrm, unsigned maxOrder, uint32_t msize) 2131 { 2132 struct ppmd_stream *strm; 2133 uint8_t *props; 2134 int r; 2135 2136 if (lastrm->valid) 2137 compression_end(a, lastrm); 2138 strm = calloc(1, sizeof(*strm)); 2139 if (strm == NULL) { 2140 archive_set_error(a, ENOMEM, 2141 "Can't allocate memory for PPMd"); 2142 return (ARCHIVE_FATAL); 2143 } 2144 strm->buff = malloc(32); 2145 if (strm->buff == NULL) { 2146 free(strm); 2147 archive_set_error(a, ENOMEM, 2148 "Can't allocate memory for PPMd"); 2149 return (ARCHIVE_FATAL); 2150 } 2151 strm->buff_ptr = strm->buff; 2152 strm->buff_end = strm->buff + 32; 2153 2154 props = malloc(1+4); 2155 if (props == NULL) { 2156 free(strm->buff); 2157 free(strm); 2158 archive_set_error(a, ENOMEM, 2159 "Coludn't allocate memory for PPMd"); 2160 return (ARCHIVE_FATAL); 2161 } 2162 props[0] = maxOrder; 2163 archive_le32enc(props+1, msize); 2164 __archive_ppmd7_functions.Ppmd7_Construct(&strm->ppmd7_context); 2165 r = __archive_ppmd7_functions.Ppmd7_Alloc( 2166 &strm->ppmd7_context, msize, &g_szalloc); 2167 if (r == 0) { 2168 free(strm->buff); 2169 free(strm); 2170 free(props); 2171 archive_set_error(a, ENOMEM, 2172 "Coludn't allocate memory for PPMd"); 2173 return (ARCHIVE_FATAL); 2174 } 2175 __archive_ppmd7_functions.Ppmd7_Init(&(strm->ppmd7_context), maxOrder); 2176 strm->byteout.a = (struct archive_write *)a; 2177 strm->byteout.Write = ppmd_write; 2178 strm->range_enc.Stream = &(strm->byteout); 2179 __archive_ppmd7_functions.Ppmd7z_RangeEnc_Init(&(strm->range_enc)); 2180 strm->stat = 0; 2181 2182 lastrm->real_stream = strm; 2183 lastrm->valid = 1; 2184 lastrm->code = compression_code_ppmd; 2185 lastrm->end = compression_end_ppmd; 2186 lastrm->prop_size = 5; 2187 lastrm->props = props; 2188 return (ARCHIVE_OK); 2189 } 2190 2191 static int 2192 compression_code_ppmd(struct archive *a, 2193 struct la_zstream *lastrm, enum la_zaction action) 2194 { 2195 struct ppmd_stream *strm; 2196 2197 (void)a; /* UNUSED */ 2198 2199 strm = (struct ppmd_stream *)lastrm->real_stream; 2200 2201 /* Copy encoded data if there are remaining bytes from previous call. */ 2202 if (strm->buff_bytes) { 2203 uint8_t *p = strm->buff_ptr - strm->buff_bytes; 2204 while (lastrm->avail_out && strm->buff_bytes) { 2205 *lastrm->next_out++ = *p++; 2206 lastrm->avail_out--; 2207 lastrm->total_out++; 2208 strm->buff_bytes--; 2209 } 2210 if (strm->buff_bytes) 2211 return (ARCHIVE_OK); 2212 if (strm->stat == 1) 2213 return (ARCHIVE_EOF); 2214 strm->buff_ptr = strm->buff; 2215 } 2216 while (lastrm->avail_in && lastrm->avail_out) { 2217 __archive_ppmd7_functions.Ppmd7_EncodeSymbol( 2218 &(strm->ppmd7_context), &(strm->range_enc), 2219 *lastrm->next_in++); 2220 lastrm->avail_in--; 2221 lastrm->total_in++; 2222 } 2223 if (lastrm->avail_in == 0 && action == ARCHIVE_Z_FINISH) { 2224 __archive_ppmd7_functions.Ppmd7z_RangeEnc_FlushData( 2225 &(strm->range_enc)); 2226 strm->stat = 1; 2227 /* Return EOF if there are no remaining bytes. */ 2228 if (strm->buff_bytes == 0) 2229 return (ARCHIVE_EOF); 2230 } 2231 return (ARCHIVE_OK); 2232 } 2233 2234 static int 2235 compression_end_ppmd(struct archive *a, struct la_zstream *lastrm) 2236 { 2237 struct ppmd_stream *strm; 2238 2239 (void)a; /* UNUSED */ 2240 2241 strm = (struct ppmd_stream *)lastrm->real_stream; 2242 __archive_ppmd7_functions.Ppmd7_Free(&strm->ppmd7_context, &g_szalloc); 2243 free(strm->buff); 2244 free(strm); 2245 lastrm->real_stream = NULL; 2246 lastrm->valid = 0; 2247 return (ARCHIVE_OK); 2248 } 2249 2250 /* 2251 * Universal compressor initializer. 2252 */ 2253 static int 2254 _7z_compression_init_encoder(struct archive_write *a, unsigned compression, 2255 int compression_level) 2256 { 2257 struct _7zip *zip; 2258 int r; 2259 2260 zip = (struct _7zip *)a->format_data; 2261 switch (compression) { 2262 case _7Z_DEFLATE: 2263 r = compression_init_encoder_deflate( 2264 &(a->archive), &(zip->stream), 2265 compression_level, 0); 2266 break; 2267 case _7Z_BZIP2: 2268 r = compression_init_encoder_bzip2( 2269 &(a->archive), &(zip->stream), 2270 compression_level); 2271 break; 2272 case _7Z_LZMA1: 2273 r = compression_init_encoder_lzma1( 2274 &(a->archive), &(zip->stream), 2275 compression_level); 2276 break; 2277 case _7Z_LZMA2: 2278 r = compression_init_encoder_lzma2( 2279 &(a->archive), &(zip->stream), 2280 compression_level); 2281 break; 2282 case _7Z_PPMD: 2283 r = compression_init_encoder_ppmd( 2284 &(a->archive), &(zip->stream), 2285 PPMD7_DEFAULT_ORDER, PPMD7_DEFAULT_MEM_SIZE); 2286 break; 2287 case _7Z_COPY: 2288 default: 2289 r = compression_init_encoder_copy( 2290 &(a->archive), &(zip->stream)); 2291 break; 2292 } 2293 if (r == ARCHIVE_OK) { 2294 zip->stream.total_in = 0; 2295 zip->stream.next_out = zip->wbuff; 2296 zip->stream.avail_out = sizeof(zip->wbuff); 2297 zip->stream.total_out = 0; 2298 } 2299 2300 return (r); 2301 } 2302 2303 static int 2304 compression_code(struct archive *a, struct la_zstream *lastrm, 2305 enum la_zaction action) 2306 { 2307 if (lastrm->valid) 2308 return (lastrm->code(a, lastrm, action)); 2309 return (ARCHIVE_OK); 2310 } 2311 2312 static int 2313 compression_end(struct archive *a, struct la_zstream *lastrm) 2314 { 2315 if (lastrm->valid) { 2316 lastrm->prop_size = 0; 2317 free(lastrm->props); 2318 lastrm->props = NULL; 2319 return (lastrm->end(a, lastrm)); 2320 } 2321 return (ARCHIVE_OK); 2322 } 2323 2324 2325