1 /*- 2 * Copyright (c) 2007-2014, Juniper Networks, Inc. 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 AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 */ 26 27 #include <sys/cdefs.h> 28 __FBSDID("$FreeBSD$"); 29 30 #include "stand.h" 31 32 #include <sys/stat.h> 33 #include <sys/stdint.h> 34 #include <string.h> 35 #include <zlib.h> 36 37 #ifdef PKGFS_DEBUG 38 #define DBG(x) printf x 39 #else 40 #define DBG(x) 41 #endif 42 43 static int pkg_open(const char *, struct open_file *); 44 static int pkg_close(struct open_file *); 45 static int pkg_read(struct open_file *, void *, size_t, size_t *); 46 static off_t pkg_seek(struct open_file *, off_t, int); 47 static int pkg_stat(struct open_file *, struct stat *); 48 static int pkg_readdir(struct open_file *, struct dirent *); 49 50 struct fs_ops pkgfs_fsops = { 51 "pkg", 52 pkg_open, 53 pkg_close, 54 pkg_read, 55 null_write, 56 pkg_seek, 57 pkg_stat, 58 pkg_readdir 59 }; 60 61 #define PKG_BUFSIZE 512 62 #define PKG_MAXCACHESZ 4096 63 64 #define PKG_FILEEXT ".tgz" 65 66 /* 67 * Layout of POSIX 'ustar' header. 68 */ 69 struct ustar_hdr { 70 char ut_name[100]; 71 char ut_mode[8]; 72 char ut_uid[8]; 73 char ut_gid[8]; 74 char ut_size[12]; 75 char ut_mtime[12]; 76 char ut_checksum[8]; 77 char ut_typeflag[1]; 78 char ut_linkname[100]; 79 char ut_magic[6]; /* For POSIX: "ustar\0" */ 80 char ut_version[2]; /* For POSIX: "00" */ 81 char ut_uname[32]; 82 char ut_gname[32]; 83 char ut_rdevmajor[8]; 84 char ut_rdevminor[8]; 85 union { 86 struct { 87 char prefix[155]; 88 } posix; 89 struct { 90 char atime[12]; 91 char ctime[12]; 92 char offset[12]; 93 char longnames[4]; 94 char unused[1]; 95 struct gnu_sparse { 96 char offset[12]; 97 char numbytes[12]; 98 } sparse[4]; 99 char isextended[1]; 100 char realsize[12]; 101 } gnu; 102 } u; 103 u_char __padding[12]; 104 }; 105 106 struct package; 107 108 struct tarfile 109 { 110 struct package *tf_pkg; 111 struct tarfile *tf_next; 112 struct ustar_hdr tf_hdr; 113 off_t tf_ofs; 114 off_t tf_size; 115 off_t tf_fp; 116 size_t tf_cachesz; 117 void *tf_cache; 118 }; 119 120 struct package 121 { 122 struct package *pkg_chain; 123 int pkg_fd; 124 off_t pkg_ofs; 125 z_stream pkg_zs; 126 struct tarfile *pkg_first; 127 struct tarfile *pkg_last; 128 u_char pkg_buf[PKG_BUFSIZE]; 129 }; 130 131 static struct package *package = NULL; 132 133 static int new_package(int, struct package **); 134 135 void 136 pkgfs_cleanup(void) 137 { 138 struct package *chain; 139 struct tarfile *tf, *tfn; 140 141 while (package != NULL) { 142 inflateEnd(&package->pkg_zs); 143 close(package->pkg_fd); 144 145 tf = package->pkg_first; 146 while (tf != NULL) { 147 tfn = tf->tf_next; 148 if (tf->tf_cachesz > 0) 149 free(tf->tf_cache); 150 free(tf); 151 tf = tfn; 152 } 153 154 chain = package->pkg_chain; 155 free(package); 156 package = chain; 157 } 158 } 159 160 int 161 pkgfs_init(const char *pkgname, struct fs_ops *proto) 162 { 163 struct package *pkg; 164 int error, fd; 165 166 pkg = NULL; 167 if (proto != &pkgfs_fsops) 168 pkgfs_cleanup(); 169 170 exclusive_file_system = proto; 171 172 fd = open(pkgname, O_RDONLY); 173 174 exclusive_file_system = NULL; 175 176 if (fd == -1) 177 return (errno); 178 179 error = new_package(fd, &pkg); 180 if (error) { 181 close(fd); 182 return (error); 183 } 184 185 if (pkg == NULL) 186 return (EDOOFUS); 187 188 pkg->pkg_chain = package; 189 package = pkg; 190 exclusive_file_system = &pkgfs_fsops; 191 return (0); 192 } 193 194 static int get_mode(struct tarfile *); 195 static int get_zipped(struct package *, void *, size_t); 196 static int new_package(int, struct package **); 197 static struct tarfile *scan_tarfile(struct package *, struct tarfile *); 198 199 static int 200 pkg_open(const char *fn, struct open_file *f) 201 { 202 struct tarfile *tf; 203 204 if (fn == NULL || f == NULL) 205 return (EINVAL); 206 207 if (package == NULL) 208 return (ENXIO); 209 210 /* 211 * We can only read from a package, so reject request to open 212 * for write-only or read-write. 213 */ 214 if (f->f_flags != F_READ) 215 return (EPERM); 216 217 /* 218 * Scan the file headers for the named file. We stop scanning 219 * at the first filename that has the .pkg extension. This is 220 * a package within a package. We assume we have all the files 221 * we need up-front and without having to dig within nested 222 * packages. 223 * 224 * Note that we preserve streaming properties as much as possible. 225 */ 226 while (*fn == '/') 227 fn++; 228 229 /* 230 * Allow opening of the root directory for use by readdir() 231 * to support listing files in the package. 232 */ 233 if (*fn == '\0') { 234 f->f_fsdata = NULL; 235 return (0); 236 } 237 238 tf = scan_tarfile(package, NULL); 239 while (tf != NULL) { 240 if (strcmp(fn, tf->tf_hdr.ut_name) == 0) { 241 f->f_fsdata = tf; 242 tf->tf_fp = 0; /* Reset the file pointer. */ 243 return (0); 244 } 245 tf = scan_tarfile(package, tf); 246 } 247 return (errno); 248 } 249 250 static int 251 pkg_close(struct open_file *f) 252 { 253 struct tarfile *tf; 254 255 tf = (struct tarfile *)f->f_fsdata; 256 if (tf == NULL) 257 return (0); 258 259 /* 260 * Free up the cache if we read all of the file. 261 */ 262 if (tf->tf_fp == tf->tf_size && tf->tf_cachesz > 0) { 263 free(tf->tf_cache); 264 tf->tf_cachesz = 0; 265 } 266 return (0); 267 } 268 269 static int 270 pkg_read(struct open_file *f, void *buf, size_t size, size_t *res) 271 { 272 struct tarfile *tf; 273 char *p; 274 off_t fp; 275 size_t sz; 276 277 tf = (struct tarfile *)f->f_fsdata; 278 if (tf == NULL) { 279 if (res != NULL) 280 *res = size; 281 return (EBADF); 282 } 283 284 fp = tf->tf_fp; 285 p = buf; 286 sz = 0; 287 while (size > 0) { 288 sz = tf->tf_size - fp; 289 if (fp < tf->tf_cachesz && tf->tf_cachesz < tf->tf_size) 290 sz = tf->tf_cachesz - fp; 291 if (size < sz) 292 sz = size; 293 if (sz == 0) 294 break; 295 296 if (fp < tf->tf_cachesz) { 297 /* Satisfy the request from cache. */ 298 memcpy(p, tf->tf_cache + fp, sz); 299 fp += sz; 300 p += sz; 301 size -= sz; 302 continue; 303 } 304 305 if (get_zipped(tf->tf_pkg, p, sz) == -1) { 306 sz = -1; 307 break; 308 } 309 310 fp += sz; 311 p += sz; 312 size -= sz; 313 314 if (tf->tf_cachesz != 0) 315 continue; 316 317 tf->tf_cachesz = (sz <= PKG_MAXCACHESZ) ? sz : PKG_MAXCACHESZ; 318 tf->tf_cache = malloc(tf->tf_cachesz); 319 if (tf->tf_cache != NULL) 320 memcpy(tf->tf_cache, buf, tf->tf_cachesz); 321 else 322 tf->tf_cachesz = 0; 323 } 324 325 tf->tf_fp = fp; 326 if (res != NULL) 327 *res = size; 328 return ((sz == -1) ? errno : 0); 329 } 330 331 static off_t 332 pkg_seek(struct open_file *f, off_t ofs, int whence) 333 { 334 char buf[512]; 335 struct tarfile *tf; 336 off_t delta; 337 size_t sz, res; 338 int error; 339 340 tf = (struct tarfile *)f->f_fsdata; 341 if (tf == NULL) { 342 errno = EBADF; 343 return (-1); 344 } 345 346 switch (whence) { 347 case SEEK_SET: 348 delta = ofs - tf->tf_fp; 349 break; 350 case SEEK_CUR: 351 delta = ofs; 352 break; 353 case SEEK_END: 354 delta = tf->tf_size - tf->tf_fp + ofs; 355 break; 356 default: 357 errno = EINVAL; 358 return (-1); 359 } 360 361 if (delta < 0) { 362 DBG(("%s: negative file seek (%jd)\n", __func__, 363 (intmax_t)delta)); 364 errno = ESPIPE; 365 return (-1); 366 } 367 368 while (delta > 0 && tf->tf_fp < tf->tf_size) { 369 sz = (delta > sizeof(buf)) ? sizeof(buf) : delta; 370 error = pkg_read(f, buf, sz, &res); 371 if (error != 0) { 372 errno = error; 373 return (-1); 374 } 375 delta -= sz - res; 376 } 377 378 return (tf->tf_fp); 379 } 380 381 static int 382 pkg_stat(struct open_file *f, struct stat *sb) 383 { 384 struct tarfile *tf; 385 386 tf = (struct tarfile *)f->f_fsdata; 387 if (tf == NULL) 388 return (EBADF); 389 memset(sb, 0, sizeof(*sb)); 390 sb->st_mode = get_mode(tf); 391 sb->st_size = tf->tf_size; 392 sb->st_blocks = (tf->tf_size + 511) / 512; 393 return (0); 394 } 395 396 static int 397 pkg_readdir(struct open_file *f, struct dirent *d) 398 { 399 struct tarfile *tf; 400 401 tf = (struct tarfile *)f->f_fsdata; 402 if (tf != NULL) 403 return (EBADF); 404 405 tf = scan_tarfile(package, NULL); 406 if (tf == NULL) 407 return (ENOENT); 408 409 d->d_fileno = 0; 410 d->d_reclen = sizeof(*d); 411 d->d_type = DT_REG; 412 memcpy(d->d_name, tf->tf_hdr.ut_name, sizeof(d->d_name)); 413 return (0); 414 } 415 416 /* 417 * Low-level support functions. 418 */ 419 420 static int 421 get_byte(struct package *pkg, off_t *op) 422 { 423 int c; 424 425 if (pkg->pkg_zs.avail_in == 0) { 426 c = read(pkg->pkg_fd, pkg->pkg_buf, PKG_BUFSIZE); 427 if (c <= 0) 428 return (-1); 429 pkg->pkg_zs.avail_in = c; 430 pkg->pkg_zs.next_in = pkg->pkg_buf; 431 } 432 433 c = *pkg->pkg_zs.next_in; 434 pkg->pkg_zs.next_in++; 435 pkg->pkg_zs.avail_in--; 436 (*op)++; 437 return (c); 438 } 439 440 static int 441 get_zipped(struct package *pkg, void *buf, size_t bufsz) 442 { 443 int c; 444 445 pkg->pkg_zs.next_out = buf; 446 pkg->pkg_zs.avail_out = bufsz; 447 448 while (pkg->pkg_zs.avail_out) { 449 if (pkg->pkg_zs.avail_in == 0) { 450 c = read(pkg->pkg_fd, pkg->pkg_buf, PKG_BUFSIZE); 451 if (c <= 0) { 452 errno = EIO; 453 return (-1); 454 } 455 pkg->pkg_zs.avail_in = c; 456 pkg->pkg_zs.next_in = pkg->pkg_buf; 457 } 458 459 c = inflate(&pkg->pkg_zs, Z_SYNC_FLUSH); 460 if (c != Z_OK && c != Z_STREAM_END) { 461 errno = EIO; 462 return (-1); 463 } 464 } 465 466 pkg->pkg_ofs += bufsz; 467 return (0); 468 } 469 470 static int 471 cache_data(struct tarfile *tf) 472 { 473 struct package *pkg; 474 size_t sz; 475 476 if (tf == NULL) { 477 DBG(("%s: no file to cache data for?\n", __func__)); 478 errno = EINVAL; 479 return (-1); 480 } 481 482 pkg = tf->tf_pkg; 483 if (pkg == NULL) { 484 DBG(("%s: no package associated with file?\n", __func__)); 485 errno = EINVAL; 486 return (-1); 487 } 488 489 if (tf->tf_ofs != pkg->pkg_ofs) { 490 DBG(("%s: caching after partial read of file %s?\n", 491 __func__, tf->tf_hdr.ut_name)); 492 errno = EINVAL; 493 return (-1); 494 } 495 496 /* We don't cache everything... */ 497 if (tf->tf_size > PKG_MAXCACHESZ) { 498 errno = ENOMEM; 499 return (-1); 500 } 501 502 /* All files are padded to a multiple of 512 bytes. */ 503 sz = (tf->tf_size + 0x1ff) & ~0x1ff; 504 505 tf->tf_cache = malloc(sz); 506 if (tf->tf_cache == NULL) { 507 DBG(("%s: could not allocate %d bytes\n", __func__, (int)sz)); 508 errno = ENOMEM; 509 return (-1); 510 } 511 512 tf->tf_cachesz = sz; 513 return (get_zipped(pkg, tf->tf_cache, sz)); 514 } 515 516 /* 517 * Note that this implementation does not (and should not!) obey 518 * locale settings; you cannot simply substitute strtol here, since 519 * it does obey locale. 520 */ 521 static off_t 522 pkg_atol8(const char *p, unsigned char_cnt) 523 { 524 int64_t l, limit, last_digit_limit; 525 int digit, sign, base; 526 527 base = 8; 528 limit = INT64_MAX / base; 529 last_digit_limit = INT64_MAX % base; 530 531 while (*p == ' ' || *p == '\t') 532 p++; 533 if (*p == '-') { 534 sign = -1; 535 p++; 536 } else 537 sign = 1; 538 539 l = 0; 540 digit = *p - '0'; 541 while (digit >= 0 && digit < base && char_cnt-- > 0) { 542 if (l>limit || (l == limit && digit > last_digit_limit)) { 543 l = UINT64_MAX; /* Truncate on overflow. */ 544 break; 545 } 546 l = (l * base) + digit; 547 digit = *++p - '0'; 548 } 549 return (sign < 0) ? -l : l; 550 } 551 552 /* 553 * Parse a base-256 integer. This is just a straight signed binary 554 * value in big-endian order, except that the high-order bit is 555 * ignored. Remember that "int64_t" may or may not be exactly 64 556 * bits; the implementation here tries to avoid making any assumptions 557 * about the actual size of an int64_t. It does assume we're using 558 * twos-complement arithmetic, though. 559 */ 560 static int64_t 561 pkg_atol256(const char *_p, unsigned char_cnt) 562 { 563 int64_t l, upper_limit, lower_limit; 564 const unsigned char *p = (const unsigned char *)_p; 565 566 upper_limit = INT64_MAX / 256; 567 lower_limit = INT64_MIN / 256; 568 569 /* Pad with 1 or 0 bits, depending on sign. */ 570 if ((0x40 & *p) == 0x40) 571 l = (int64_t)-1; 572 else 573 l = 0; 574 l = (l << 6) | (0x3f & *p++); 575 while (--char_cnt > 0) { 576 if (l > upper_limit) { 577 l = INT64_MAX; /* Truncate on overflow */ 578 break; 579 } else if (l < lower_limit) { 580 l = INT64_MIN; 581 break; 582 } 583 l = (l << 8) | (0xff & (int64_t)*p++); 584 } 585 return (l); 586 } 587 588 static off_t 589 pkg_atol(const char *p, unsigned char_cnt) 590 { 591 /* 592 * Technically, GNU pkg considers a field to be in base-256 593 * only if the first byte is 0xff or 0x80. 594 */ 595 if (*p & 0x80) 596 return (pkg_atol256(p, char_cnt)); 597 return (pkg_atol8(p, char_cnt)); 598 } 599 600 static int 601 get_mode(struct tarfile *tf) 602 { 603 return (pkg_atol(tf->tf_hdr.ut_mode, sizeof(tf->tf_hdr.ut_mode))); 604 } 605 606 /* GZip flag byte */ 607 #define ASCII_FLAG 0x01 /* bit 0 set: file probably ascii text */ 608 #define HEAD_CRC 0x02 /* bit 1 set: header CRC present */ 609 #define EXTRA_FIELD 0x04 /* bit 2 set: extra field present */ 610 #define ORIG_NAME 0x08 /* bit 3 set: original file name present */ 611 #define COMMENT 0x10 /* bit 4 set: file comment present */ 612 #define RESERVED 0xE0 /* bits 5..7: reserved */ 613 614 static int 615 new_package(int fd, struct package **pp) 616 { 617 struct package *pkg; 618 off_t ofs; 619 int flags, i, error; 620 621 pkg = malloc(sizeof(*pkg)); 622 if (pkg == NULL) 623 return (ENOMEM); 624 625 bzero(pkg, sizeof(*pkg)); 626 pkg->pkg_fd = fd; 627 628 /* 629 * Parse the header. 630 */ 631 error = EFTYPE; 632 ofs = 0; 633 634 /* Check megic. */ 635 if (get_byte(pkg, &ofs) != 0x1f || get_byte(pkg, &ofs) != 0x8b) 636 goto fail; 637 /* Check method. */ 638 if (get_byte(pkg, &ofs) != Z_DEFLATED) 639 goto fail; 640 /* Check flags. */ 641 flags = get_byte(pkg, &ofs); 642 if (flags & RESERVED) 643 goto fail; 644 645 /* Skip time, xflags and OS code. */ 646 for (i = 0; i < 6; i++) { 647 if (get_byte(pkg, &ofs) == -1) 648 goto fail; 649 } 650 651 /* Skip extra field. */ 652 if (flags & EXTRA_FIELD) { 653 i = (get_byte(pkg, &ofs) & 0xff) | 654 ((get_byte(pkg, &ofs) << 8) & 0xff); 655 while (i-- > 0) { 656 if (get_byte(pkg, &ofs) == -1) 657 goto fail; 658 } 659 } 660 661 /* Skip original file name. */ 662 if (flags & ORIG_NAME) { 663 do { 664 i = get_byte(pkg, &ofs); 665 } while (i != 0 && i != -1); 666 if (i == -1) 667 goto fail; 668 } 669 670 /* Print the comment if it's there. */ 671 if (flags & COMMENT) { 672 while (1) { 673 i = get_byte(pkg, &ofs); 674 if (i == -1) 675 goto fail; 676 if (i == 0) 677 break; 678 putchar(i); 679 } 680 } 681 682 /* Skip the CRC. */ 683 if (flags & HEAD_CRC) { 684 if (get_byte(pkg, &ofs) == -1) 685 goto fail; 686 if (get_byte(pkg, &ofs) == -1) 687 goto fail; 688 } 689 690 /* 691 * Done parsing the ZIP header. Spkgt the inflation engine. 692 */ 693 error = inflateInit2(&pkg->pkg_zs, -15); 694 if (error != Z_OK) 695 goto fail; 696 697 *pp = pkg; 698 return (0); 699 700 fail: 701 free(pkg); 702 return (error); 703 } 704 705 static struct tarfile * 706 scan_tarfile(struct package *pkg, struct tarfile *last) 707 { 708 char buf[512]; 709 struct tarfile *cur; 710 off_t ofs; 711 size_t sz; 712 713 cur = (last != NULL) ? last->tf_next : pkg->pkg_first; 714 if (cur == NULL) { 715 ofs = (last != NULL) ? last->tf_ofs + last->tf_size : 716 pkg->pkg_ofs; 717 ofs = (ofs + 0x1ff) & ~0x1ff; 718 719 /* Check if we've reached EOF. */ 720 if (ofs < pkg->pkg_ofs) { 721 errno = ENOSPC; 722 return (NULL); 723 } 724 725 if (ofs != pkg->pkg_ofs) { 726 if (last != NULL && pkg->pkg_ofs == last->tf_ofs) { 727 if (cache_data(last) == -1) 728 return (NULL); 729 } else { 730 sz = ofs - pkg->pkg_ofs; 731 while (sz != 0) { 732 if (sz > sizeof(buf)) 733 sz = sizeof(buf); 734 if (get_zipped(pkg, buf, sz) == -1) 735 return (NULL); 736 sz = ofs - pkg->pkg_ofs; 737 } 738 } 739 } 740 741 cur = malloc(sizeof(*cur)); 742 if (cur == NULL) 743 return (NULL); 744 memset(cur, 0, sizeof(*cur)); 745 cur->tf_pkg = pkg; 746 747 while (1) { 748 if (get_zipped(pkg, &cur->tf_hdr, 749 sizeof(cur->tf_hdr)) == -1) { 750 free(cur); 751 return (NULL); 752 } 753 754 /* 755 * There are always 2 empty blocks appended to 756 * a PKG. It marks the end of the archive. 757 */ 758 if (strncmp(cur->tf_hdr.ut_magic, "ustar", 5) != 0) { 759 free(cur); 760 errno = ENOSPC; 761 return (NULL); 762 } 763 764 cur->tf_ofs = pkg->pkg_ofs; 765 cur->tf_size = pkg_atol(cur->tf_hdr.ut_size, 766 sizeof(cur->tf_hdr.ut_size)); 767 768 if (cur->tf_hdr.ut_name[0] != '+') 769 break; 770 771 /* 772 * Skip package meta-files. 773 */ 774 ofs = cur->tf_ofs + cur->tf_size; 775 ofs = (ofs + 0x1ff) & ~0x1ff; 776 while (pkg->pkg_ofs < ofs) { 777 if (get_zipped(pkg, buf, sizeof(buf)) == -1) { 778 free(cur); 779 return (NULL); 780 } 781 } 782 } 783 784 if (last != NULL) 785 last->tf_next = cur; 786 else 787 pkg->pkg_first = cur; 788 pkg->pkg_last = cur; 789 } 790 791 return (cur); 792 } 793