1 /*- 2 * Copyright (c) 1992 Keith Muller. 3 * Copyright (c) 1992, 1993 4 * The Regents of the University of California. All rights reserved. 5 * 6 * This code is derived from software contributed to Berkeley by 7 * Keith Muller of the University of California, San Diego. 8 * 9 * Redistribution and use in source and binary forms, with or without 10 * modification, are permitted provided that the following conditions 11 * are met: 12 * 1. Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * 2. Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in the 16 * documentation and/or other materials provided with the distribution. 17 * 3. All advertising materials mentioning features or use of this software 18 * must display the following acknowledgement: 19 * This product includes software developed by the University of 20 * California, Berkeley and its contributors. 21 * 4. Neither the name of the University nor the names of its contributors 22 * may be used to endorse or promote products derived from this software 23 * without specific prior written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 26 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 27 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 28 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 29 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 30 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 31 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 32 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 33 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 34 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 35 * SUCH DAMAGE. 36 * 37 * @(#)ar_subs.c 8.2 (Berkeley) 4/18/94 38 * $FreeBSD: src/bin/pax/ar_subs.c,v 1.13.2.1 2001/08/01 05:03:11 obrien Exp $ 39 * $DragonFly: src/bin/pax/ar_subs.c,v 1.2 2003/06/17 04:22:50 dillon Exp $ 40 */ 41 42 #include <sys/types.h> 43 #include <sys/time.h> 44 #include <sys/stat.h> 45 #include <signal.h> 46 #include <string.h> 47 #include <stdio.h> 48 #include <fcntl.h> 49 #include <errno.h> 50 #include <unistd.h> 51 #include <stdlib.h> 52 #include "pax.h" 53 #include "extern.h" 54 55 static void wr_archive __P((register ARCHD *, int is_app)); 56 static int get_arc __P((void)); 57 static int next_head __P((register ARCHD *)); 58 extern sigset_t s_mask; 59 60 /* 61 * Routines which control the overall operation modes of pax as specified by 62 * the user: list, append, read ... 63 */ 64 65 static char hdbuf[BLKMULT]; /* space for archive header on read */ 66 u_long flcnt; /* number of files processed */ 67 68 /* 69 * list() 70 * list the contents of an archive which match user supplied pattern(s) 71 * (no pattern matches all). 72 */ 73 74 #ifdef __STDC__ 75 void 76 list(void) 77 #else 78 void 79 list() 80 #endif 81 { 82 register ARCHD *arcn; 83 register int res; 84 ARCHD archd; 85 time_t now; 86 87 arcn = &archd; 88 /* 89 * figure out archive type; pass any format specific options to the 90 * archive option processing routine; call the format init routine. We 91 * also save current time for ls_list() so we do not make a system 92 * call for each file we need to print. If verbose (vflag) start up 93 * the name and group caches. 94 */ 95 if ((get_arc() < 0) || ((*frmt->options)() < 0) || 96 ((*frmt->st_rd)() < 0)) 97 return; 98 99 if (vflag && ((uidtb_start() < 0) || (gidtb_start() < 0))) 100 return; 101 102 now = time(NULL); 103 104 /* 105 * step through the archive until the format says it is done 106 */ 107 while (next_head(arcn) == 0) { 108 /* 109 * check for pattern, and user specified options match. 110 * When all patterns are matched we are done. 111 */ 112 if ((res = pat_match(arcn)) < 0) 113 break; 114 115 if ((res == 0) && (sel_chk(arcn) == 0)) { 116 /* 117 * pattern resulted in a selected file 118 */ 119 if (pat_sel(arcn) < 0) 120 break; 121 122 /* 123 * modify the name as requested by the user if name 124 * survives modification, do a listing of the file 125 */ 126 if ((res = mod_name(arcn)) < 0) 127 break; 128 if (res == 0) 129 ls_list(arcn, now, stdout); 130 } 131 132 /* 133 * skip to next archive format header using values calculated 134 * by the format header read routine 135 */ 136 if (rd_skip(arcn->skip + arcn->pad) == 1) 137 break; 138 } 139 140 /* 141 * all done, let format have a chance to cleanup, and make sure that 142 * the patterns supplied by the user were all matched 143 */ 144 (void)(*frmt->end_rd)(); 145 (void)sigprocmask(SIG_BLOCK, &s_mask, NULL); 146 ar_close(); 147 pat_chk(); 148 } 149 150 /* 151 * extract() 152 * extract the member(s) of an archive as specified by user supplied 153 * pattern(s) (no patterns extracts all members) 154 */ 155 156 #ifdef __STDC__ 157 void 158 extract(void) 159 #else 160 void 161 extract() 162 #endif 163 { 164 register ARCHD *arcn; 165 register int res; 166 off_t cnt; 167 ARCHD archd; 168 struct stat sb; 169 int fd; 170 time_t now; 171 172 arcn = &archd; 173 /* 174 * figure out archive type; pass any format specific options to the 175 * archive option processing routine; call the format init routine; 176 * start up the directory modification time and access mode database 177 */ 178 if ((get_arc() < 0) || ((*frmt->options)() < 0) || 179 ((*frmt->st_rd)() < 0) || (dir_start() < 0)) 180 return; 181 182 /* 183 * When we are doing interactive rename, we store the mapping of names 184 * so we can fix up hard links files later in the archive. 185 */ 186 if (iflag && (name_start() < 0)) 187 return; 188 189 now = time(NULL); 190 191 /* 192 * step through each entry on the archive until the format read routine 193 * says it is done 194 */ 195 while (next_head(arcn) == 0) { 196 197 /* 198 * check for pattern, and user specified options match. When 199 * all the patterns are matched we are done 200 */ 201 if ((res = pat_match(arcn)) < 0) 202 break; 203 204 if ((res > 0) || (sel_chk(arcn) != 0)) { 205 /* 206 * file is not selected. skip past any file data and 207 * padding and go back for the next archive member 208 */ 209 (void)rd_skip(arcn->skip + arcn->pad); 210 continue; 211 } 212 213 /* 214 * with -u or -D only extract when the archive member is newer 215 * than the file with the same name in the file system (nos 216 * test of being the same type is required). 217 * NOTE: this test is done BEFORE name modifications as 218 * specified by pax. this operation can be confusing to the 219 * user who might expect the test to be done on an existing 220 * file AFTER the name mod. In honesty the pax spec is probably 221 * flawed in this respect. 222 */ 223 if ((uflag || Dflag) && ((lstat(arcn->name, &sb) == 0))) { 224 if (uflag && Dflag) { 225 if ((arcn->sb.st_mtime <= sb.st_mtime) && 226 (arcn->sb.st_ctime <= sb.st_ctime)) { 227 (void)rd_skip(arcn->skip + arcn->pad); 228 continue; 229 } 230 } else if (Dflag) { 231 if (arcn->sb.st_ctime <= sb.st_ctime) { 232 (void)rd_skip(arcn->skip + arcn->pad); 233 continue; 234 } 235 } else if (arcn->sb.st_mtime <= sb.st_mtime) { 236 (void)rd_skip(arcn->skip + arcn->pad); 237 continue; 238 } 239 } 240 241 /* 242 * this archive member is now been selected. modify the name. 243 */ 244 if ((pat_sel(arcn) < 0) || ((res = mod_name(arcn)) < 0)) 245 break; 246 if (res > 0) { 247 /* 248 * a bad name mod, skip and purge name from link table 249 */ 250 purg_lnk(arcn); 251 (void)rd_skip(arcn->skip + arcn->pad); 252 continue; 253 } 254 255 /* 256 * Non standard -Y and -Z flag. When the existing file is 257 * same age or newer skip 258 */ 259 if ((Yflag || Zflag) && ((lstat(arcn->name, &sb) == 0))) { 260 if (Yflag && Zflag) { 261 if ((arcn->sb.st_mtime <= sb.st_mtime) && 262 (arcn->sb.st_ctime <= sb.st_ctime)) { 263 (void)rd_skip(arcn->skip + arcn->pad); 264 continue; 265 } 266 } else if (Yflag) { 267 if (arcn->sb.st_ctime <= sb.st_ctime) { 268 (void)rd_skip(arcn->skip + arcn->pad); 269 continue; 270 } 271 } else if (arcn->sb.st_mtime <= sb.st_mtime) { 272 (void)rd_skip(arcn->skip + arcn->pad); 273 continue; 274 } 275 } 276 277 if (vflag) { 278 if (vflag > 1) 279 ls_list(arcn, now, listf); 280 else { 281 (void)fputs(arcn->name, listf); 282 vfpart = 1; 283 } 284 } 285 286 /* 287 * if required, chdir around. 288 */ 289 if ((arcn->pat != NULL) && (arcn->pat->chdname != NULL)) 290 if (chdir(arcn->pat->chdname) != 0) 291 syswarn(1, errno, "Cannot chdir to %s", 292 arcn->pat->chdname); 293 294 /* 295 * all ok, extract this member based on type 296 */ 297 if ((arcn->type != PAX_REG) && (arcn->type != PAX_CTG)) { 298 /* 299 * process archive members that are not regular files. 300 * throw out padding and any data that might follow the 301 * header (as determined by the format). 302 */ 303 if ((arcn->type == PAX_HLK) || (arcn->type == PAX_HRG)) 304 res = lnk_creat(arcn); 305 else 306 res = node_creat(arcn); 307 308 (void)rd_skip(arcn->skip + arcn->pad); 309 if (res < 0) 310 purg_lnk(arcn); 311 312 if (vflag && vfpart) { 313 (void)putc('\n', listf); 314 vfpart = 0; 315 } 316 continue; 317 } 318 /* 319 * we have a file with data here. If we can not create it, skip 320 * over the data and purge the name from hard link table 321 */ 322 if ((fd = file_creat(arcn)) < 0) { 323 (void)rd_skip(arcn->skip + arcn->pad); 324 purg_lnk(arcn); 325 continue; 326 } 327 /* 328 * extract the file from the archive and skip over padding and 329 * any unprocessed data 330 */ 331 res = (*frmt->rd_data)(arcn, fd, &cnt); 332 file_close(arcn, fd); 333 if (vflag && vfpart) { 334 (void)putc('\n', listf); 335 vfpart = 0; 336 } 337 if (!res) 338 (void)rd_skip(cnt + arcn->pad); 339 340 /* 341 * if required, chdir around. 342 */ 343 if ((arcn->pat != NULL) && (arcn->pat->chdname != NULL)) 344 if (fchdir(cwdfd) != 0) 345 syswarn(1, errno, 346 "Can't fchdir to starting directory"); 347 } 348 349 /* 350 * all done, restore directory modes and times as required; make sure 351 * all patterns supplied by the user were matched; block off signals 352 * to avoid chance for multiple entry into the cleanup code. 353 */ 354 (void)(*frmt->end_rd)(); 355 (void)sigprocmask(SIG_BLOCK, &s_mask, NULL); 356 ar_close(); 357 proc_dir(); 358 pat_chk(); 359 } 360 361 /* 362 * wr_archive() 363 * Write an archive. used in both creating a new archive and appends on 364 * previously written archive. 365 */ 366 367 #ifdef __STDC__ 368 static void 369 wr_archive(register ARCHD *arcn, int is_app) 370 #else 371 static void 372 wr_archive(arcn, is_app) 373 register ARCHD *arcn; 374 int is_app; 375 #endif 376 { 377 register int res; 378 register int hlk; 379 register int wr_one; 380 off_t cnt; 381 int (*wrf)(); 382 int fd = -1; 383 time_t now; 384 385 /* 386 * if this format supports hard link storage, start up the database 387 * that detects them. 388 */ 389 if (((hlk = frmt->hlk) == 1) && (lnk_start() < 0)) 390 return; 391 392 /* 393 * start up the file traversal code and format specific write 394 */ 395 if ((ftree_start() < 0) || ((*frmt->st_wr)() < 0)) 396 return; 397 wrf = frmt->wr; 398 399 /* 400 * When we are doing interactive rename, we store the mapping of names 401 * so we can fix up hard links files later in the archive. 402 */ 403 if (iflag && (name_start() < 0)) 404 return; 405 406 /* 407 * if this not append, and there are no files, we do no write a trailer 408 */ 409 wr_one = is_app; 410 411 now = time(NULL); 412 413 /* 414 * while there are files to archive, process them one at at time 415 */ 416 while (next_file(arcn) == 0) { 417 /* 418 * check if this file meets user specified options match. 419 */ 420 if (sel_chk(arcn) != 0) 421 continue; 422 fd = -1; 423 if (uflag) { 424 /* 425 * only archive if this file is newer than a file with 426 * the same name that is already stored on the archive 427 */ 428 if ((res = chk_ftime(arcn)) < 0) 429 break; 430 if (res > 0) 431 continue; 432 } 433 434 /* 435 * this file is considered selected now. see if this is a hard 436 * link to a file already stored 437 */ 438 ftree_sel(arcn); 439 if (hlk && (chk_lnk(arcn) < 0)) 440 break; 441 442 if ((arcn->type == PAX_REG) || (arcn->type == PAX_HRG) || 443 (arcn->type == PAX_CTG)) { 444 /* 445 * we will have to read this file. by opening it now we 446 * can avoid writing a header to the archive for a file 447 * we were later unable to read (we also purge it from 448 * the link table). 449 */ 450 if ((fd = open(arcn->org_name, O_RDONLY, 0)) < 0) { 451 syswarn(1,errno, "Unable to open %s to read", 452 arcn->org_name); 453 purg_lnk(arcn); 454 continue; 455 } 456 } 457 458 /* 459 * Now modify the name as requested by the user 460 */ 461 if ((res = mod_name(arcn)) < 0) { 462 /* 463 * name modification says to skip this file, close the 464 * file and purge link table entry 465 */ 466 rdfile_close(arcn, &fd); 467 purg_lnk(arcn); 468 break; 469 } 470 471 if ((res > 0) || (docrc && (set_crc(arcn, fd) < 0))) { 472 /* 473 * unable to obtain the crc we need, close the file, 474 * purge link table entry 475 */ 476 rdfile_close(arcn, &fd); 477 purg_lnk(arcn); 478 continue; 479 } 480 481 if (vflag) { 482 if (vflag > 1) 483 ls_list(arcn, now, listf); 484 else { 485 (void)fputs(arcn->name, listf); 486 vfpart = 1; 487 } 488 } 489 ++flcnt; 490 491 /* 492 * looks safe to store the file, have the format specific 493 * routine write routine store the file header on the archive 494 */ 495 if ((res = (*wrf)(arcn)) < 0) { 496 rdfile_close(arcn, &fd); 497 break; 498 } 499 wr_one = 1; 500 if (res > 0) { 501 /* 502 * format write says no file data needs to be stored 503 * so we are done messing with this file 504 */ 505 if (vflag && vfpart) { 506 (void)putc('\n', listf); 507 vfpart = 0; 508 } 509 rdfile_close(arcn, &fd); 510 continue; 511 } 512 513 /* 514 * Add file data to the archive, quit on write error. if we 515 * cannot write the entire file contents to the archive we 516 * must pad the archive to replace the missing file data 517 * (otherwise during an extract the file header for the file 518 * which FOLLOWS this one will not be where we expect it to 519 * be). 520 */ 521 res = (*frmt->wr_data)(arcn, fd, &cnt); 522 rdfile_close(arcn, &fd); 523 if (vflag && vfpart) { 524 (void)putc('\n', listf); 525 vfpart = 0; 526 } 527 if (res < 0) 528 break; 529 530 /* 531 * pad as required, cnt is number of bytes not written 532 */ 533 if (((cnt > 0) && (wr_skip(cnt) < 0)) || 534 ((arcn->pad > 0) && (wr_skip(arcn->pad) < 0))) 535 break; 536 } 537 538 /* 539 * tell format to write trailer; pad to block boundary; reset directory 540 * mode/access times, and check if all patterns supplied by the user 541 * were matched. block off signals to avoid chance for multiple entry 542 * into the cleanup code 543 */ 544 if (wr_one) { 545 (*frmt->end_wr)(); 546 wr_fin(); 547 } 548 (void)sigprocmask(SIG_BLOCK, &s_mask, NULL); 549 ar_close(); 550 if (tflag) 551 proc_dir(); 552 ftree_chk(); 553 } 554 555 /* 556 * append() 557 * Add file to previously written archive. Archive format specified by the 558 * user must agree with archive. The archive is read first to collect 559 * modification times (if -u) and locate the archive trailer. The archive 560 * is positioned in front of the record with the trailer and wr_archive() 561 * is called to add the new members. 562 * PAX IMPLEMENTATION DETAIL NOTE: 563 * -u is implemented by adding the new members to the end of the archive. 564 * Care is taken so that these do not end up as links to the older 565 * version of the same file already stored in the archive. It is expected 566 * when extraction occurs these newer versions will over-write the older 567 * ones stored "earlier" in the archive (this may be a bad assumption as 568 * it depends on the implementation of the program doing the extraction). 569 * It is really difficult to splice in members without either re-writing 570 * the entire archive (from the point were the old version was), or having 571 * assistance of the format specification in terms of a special update 572 * header that invalidates a previous archive record. The POSIX spec left 573 * the method used to implement -u unspecified. This pax is able to 574 * over write existing files that it creates. 575 */ 576 577 #ifdef __STDC__ 578 void 579 append(void) 580 #else 581 void 582 append() 583 #endif 584 { 585 register ARCHD *arcn; 586 register int res; 587 ARCHD archd; 588 FSUB *orgfrmt; 589 int udev; 590 off_t tlen; 591 592 arcn = &archd; 593 orgfrmt = frmt; 594 595 /* 596 * Do not allow an append operation if the actual archive is of a 597 * different format than the user specified format. 598 */ 599 if (get_arc() < 0) 600 return; 601 if ((orgfrmt != NULL) && (orgfrmt != frmt)) { 602 paxwarn(1, "Cannot mix current archive format %s with %s", 603 frmt->name, orgfrmt->name); 604 return; 605 } 606 607 /* 608 * pass the format any options and start up format 609 */ 610 if (((*frmt->options)() < 0) || ((*frmt->st_rd)() < 0)) 611 return; 612 613 /* 614 * if we only are adding members that are newer, we need to save the 615 * mod times for all files we see. 616 */ 617 if (uflag && (ftime_start() < 0)) 618 return; 619 620 /* 621 * some archive formats encode hard links by recording the device and 622 * file serial number (inode) but copy the file anyway (multiple times) 623 * to the archive. When we append, we run the risk that newly added 624 * files may have the same device and inode numbers as those recorded 625 * on the archive but during a previous run. If this happens, when the 626 * archive is extracted we get INCORRECT hard links. We avoid this by 627 * remapping the device numbers so that newly added files will never 628 * use the same device number as one found on the archive. remapping 629 * allows new members to safely have links among themselves. remapping 630 * also avoids problems with file inode (serial number) truncations 631 * when the inode number is larger than storage space in the archive 632 * header. See the remap routines for more details. 633 */ 634 if ((udev = frmt->udev) && (dev_start() < 0)) 635 return; 636 637 /* 638 * reading the archive may take a long time. If verbose tell the user 639 */ 640 if (vflag) { 641 (void)fprintf(listf, 642 "%s: Reading archive to position at the end...", argv0); 643 vfpart = 1; 644 } 645 646 /* 647 * step through the archive until the format says it is done 648 */ 649 while (next_head(arcn) == 0) { 650 /* 651 * check if this file meets user specified options. 652 */ 653 if (sel_chk(arcn) != 0) { 654 if (rd_skip(arcn->skip + arcn->pad) == 1) 655 break; 656 continue; 657 } 658 659 if (uflag) { 660 /* 661 * see if this is the newest version of this file has 662 * already been seen, if so skip. 663 */ 664 if ((res = chk_ftime(arcn)) < 0) 665 break; 666 if (res > 0) { 667 if (rd_skip(arcn->skip + arcn->pad) == 1) 668 break; 669 continue; 670 } 671 } 672 673 /* 674 * Store this device number. Device numbers seen during the 675 * read phase of append will cause newly appended files with a 676 * device number seen in the old part of the archive to be 677 * remapped to an unused device number. 678 */ 679 if ((udev && (add_dev(arcn) < 0)) || 680 (rd_skip(arcn->skip + arcn->pad) == 1)) 681 break; 682 } 683 684 /* 685 * done, finish up read and get the number of bytes to back up so we 686 * can add new members. The format might have used the hard link table, 687 * purge it. 688 */ 689 tlen = (*frmt->end_rd)(); 690 lnk_end(); 691 692 /* 693 * try to position for write, if this fails quit. if any error occurs, 694 * we will refuse to write 695 */ 696 if (appnd_start(tlen) < 0) 697 return; 698 699 /* 700 * tell the user we are done reading. 701 */ 702 if (vflag && vfpart) { 703 (void)fputs("done.\n", listf); 704 vfpart = 0; 705 } 706 707 /* 708 * go to the writing phase to add the new members 709 */ 710 wr_archive(arcn, 1); 711 } 712 713 /* 714 * archive() 715 * write a new archive 716 */ 717 718 #ifdef __STDC__ 719 void 720 archive(void) 721 #else 722 void 723 archive() 724 #endif 725 { 726 ARCHD archd; 727 728 /* 729 * if we only are adding members that are newer, we need to save the 730 * mod times for all files; set up for writing; pass the format any 731 * options write the archive 732 */ 733 if ((uflag && (ftime_start() < 0)) || (wr_start() < 0)) 734 return; 735 if ((*frmt->options)() < 0) 736 return; 737 738 wr_archive(&archd, 0); 739 } 740 741 /* 742 * copy() 743 * copy files from one part of the file system to another. this does not 744 * use any archive storage. The EFFECT OF THE COPY IS THE SAME as if an 745 * archive was written and then extracted in the destination directory 746 * (except the files are forced to be under the destination directory). 747 */ 748 749 #ifdef __STDC__ 750 void 751 copy(void) 752 #else 753 void 754 copy() 755 #endif 756 { 757 register ARCHD *arcn; 758 register int res; 759 register int fddest; 760 register char *dest_pt; 761 register int dlen; 762 register int drem; 763 int fdsrc = -1; 764 struct stat sb; 765 ARCHD archd; 766 char dirbuf[PAXPATHLEN+1]; 767 768 arcn = &archd; 769 /* 770 * set up the destination dir path and make sure it is a directory. We 771 * make sure we have a trailing / on the destination 772 */ 773 dlen = l_strncpy(dirbuf, dirptr, sizeof(dirbuf) - 1); 774 dest_pt = dirbuf + dlen; 775 if (*(dest_pt-1) != '/') { 776 *dest_pt++ = '/'; 777 ++dlen; 778 } 779 *dest_pt = '\0'; 780 drem = PAXPATHLEN - dlen; 781 782 if (stat(dirptr, &sb) < 0) { 783 syswarn(1, errno, "Cannot access destination directory %s", 784 dirptr); 785 return; 786 } 787 if (!S_ISDIR(sb.st_mode)) { 788 paxwarn(1, "Destination is not a directory %s", dirptr); 789 return; 790 } 791 792 /* 793 * start up the hard link table; file traversal routines and the 794 * modification time and access mode database 795 */ 796 if ((lnk_start() < 0) || (ftree_start() < 0) || (dir_start() < 0)) 797 return; 798 799 /* 800 * When we are doing interactive rename, we store the mapping of names 801 * so we can fix up hard links files later in the archive. 802 */ 803 if (iflag && (name_start() < 0)) 804 return; 805 806 /* 807 * set up to cp file trees 808 */ 809 cp_start(); 810 811 /* 812 * while there are files to archive, process them 813 */ 814 while (next_file(arcn) == 0) { 815 fdsrc = -1; 816 817 /* 818 * check if this file meets user specified options 819 */ 820 if (sel_chk(arcn) != 0) 821 continue; 822 823 /* 824 * if there is already a file in the destination directory with 825 * the same name and it is newer, skip the one stored on the 826 * archive. 827 * NOTE: this test is done BEFORE name modifications as 828 * specified by pax. this can be confusing to the user who 829 * might expect the test to be done on an existing file AFTER 830 * the name mod. In honesty the pax spec is probably flawed in 831 * this respect 832 */ 833 if (uflag || Dflag) { 834 /* 835 * create the destination name 836 */ 837 if (*(arcn->name) == '/') 838 res = 1; 839 else 840 res = 0; 841 if ((arcn->nlen - res) > drem) { 842 paxwarn(1, "Destination pathname too long %s", 843 arcn->name); 844 continue; 845 } 846 (void)strncpy(dest_pt, arcn->name + res, drem); 847 dirbuf[PAXPATHLEN] = '\0'; 848 849 /* 850 * if existing file is same age or newer skip 851 */ 852 res = lstat(dirbuf, &sb); 853 *dest_pt = '\0'; 854 855 if (res == 0) { 856 if (uflag && Dflag) { 857 if ((arcn->sb.st_mtime<=sb.st_mtime) && 858 (arcn->sb.st_ctime<=sb.st_ctime)) 859 continue; 860 } else if (Dflag) { 861 if (arcn->sb.st_ctime <= sb.st_ctime) 862 continue; 863 } else if (arcn->sb.st_mtime <= sb.st_mtime) 864 continue; 865 } 866 } 867 868 /* 869 * this file is considered selected. See if this is a hard link 870 * to a previous file; modify the name as requested by the 871 * user; set the final destination. 872 */ 873 ftree_sel(arcn); 874 if ((chk_lnk(arcn) < 0) || ((res = mod_name(arcn)) < 0)) 875 break; 876 if ((res > 0) || (set_dest(arcn, dirbuf, dlen) < 0)) { 877 /* 878 * skip file, purge from link table 879 */ 880 purg_lnk(arcn); 881 continue; 882 } 883 884 /* 885 * Non standard -Y and -Z flag. When the exisiting file is 886 * same age or newer skip 887 */ 888 if ((Yflag || Zflag) && ((lstat(arcn->name, &sb) == 0))) { 889 if (Yflag && Zflag) { 890 if ((arcn->sb.st_mtime <= sb.st_mtime) && 891 (arcn->sb.st_ctime <= sb.st_ctime)) 892 continue; 893 } else if (Yflag) { 894 if (arcn->sb.st_ctime <= sb.st_ctime) 895 continue; 896 } else if (arcn->sb.st_mtime <= sb.st_mtime) 897 continue; 898 } 899 900 if (vflag) { 901 (void)fputs(arcn->name, listf); 902 vfpart = 1; 903 } 904 ++flcnt; 905 906 /* 907 * try to create a hard link to the src file if requested 908 * but make sure we are not trying to overwrite ourselves. 909 */ 910 if (lflag) 911 res = cross_lnk(arcn); 912 else 913 res = chk_same(arcn); 914 if (res <= 0) { 915 if (vflag && vfpart) { 916 (void)putc('\n', listf); 917 vfpart = 0; 918 } 919 continue; 920 } 921 922 /* 923 * have to create a new file 924 */ 925 if ((arcn->type != PAX_REG) && (arcn->type != PAX_CTG)) { 926 /* 927 * create a link or special file 928 */ 929 if ((arcn->type == PAX_HLK) || (arcn->type == PAX_HRG)) 930 res = lnk_creat(arcn); 931 else 932 res = node_creat(arcn); 933 if (res < 0) 934 purg_lnk(arcn); 935 if (vflag && vfpart) { 936 (void)putc('\n', listf); 937 vfpart = 0; 938 } 939 continue; 940 } 941 942 /* 943 * have to copy a regular file to the destination directory. 944 * first open source file and then create the destination file 945 */ 946 if ((fdsrc = open(arcn->org_name, O_RDONLY, 0)) < 0) { 947 syswarn(1, errno, "Unable to open %s to read", 948 arcn->org_name); 949 purg_lnk(arcn); 950 continue; 951 } 952 if ((fddest = file_creat(arcn)) < 0) { 953 rdfile_close(arcn, &fdsrc); 954 purg_lnk(arcn); 955 continue; 956 } 957 958 /* 959 * copy source file data to the destination file 960 */ 961 cp_file(arcn, fdsrc, fddest); 962 file_close(arcn, fddest); 963 rdfile_close(arcn, &fdsrc); 964 965 if (vflag && vfpart) { 966 (void)putc('\n', listf); 967 vfpart = 0; 968 } 969 } 970 971 /* 972 * restore directory modes and times as required; make sure all 973 * patterns were selected block off signals to avoid chance for 974 * multiple entry into the cleanup code. 975 */ 976 (void)sigprocmask(SIG_BLOCK, &s_mask, NULL); 977 ar_close(); 978 proc_dir(); 979 ftree_chk(); 980 } 981 982 /* 983 * next_head() 984 * try to find a valid header in the archive. Uses format specific 985 * routines to extract the header and id the trailer. Trailers may be 986 * located within a valid header or in an invalid header (the location 987 * is format specific. The inhead field from the option table tells us 988 * where to look for the trailer). 989 * We keep reading (and resyncing) until we get enough contiguous data 990 * to check for a header. If we cannot find one, we shift by a byte 991 * add a new byte from the archive to the end of the buffer and try again. 992 * If we get a read error, we throw out what we have (as we must have 993 * contiguous data) and start over again. 994 * ASSUMED: headers fit within a BLKMULT header. 995 * Return: 996 * 0 if we got a header, -1 if we are unable to ever find another one 997 * (we reached the end of input, or we reached the limit on retries. see 998 * the specs for rd_wrbuf() for more details) 999 */ 1000 1001 #ifdef __STDC__ 1002 static int 1003 next_head(register ARCHD *arcn) 1004 #else 1005 static int 1006 next_head(arcn) 1007 register ARCHD *arcn; 1008 #endif 1009 { 1010 register int ret; 1011 register char *hdend; 1012 register int res; 1013 register int shftsz; 1014 register int hsz; 1015 register int in_resync = 0; /* set when we are in resync mode */ 1016 int cnt = 0; /* counter for trailer function */ 1017 int first = 1; /* on 1st read, EOF isn't premature. */ 1018 1019 /* 1020 * set up initial conditions, we want a whole frmt->hsz block as we 1021 * have no data yet. 1022 */ 1023 res = hsz = frmt->hsz; 1024 hdend = hdbuf; 1025 shftsz = hsz - 1; 1026 for(;;) { 1027 /* 1028 * keep looping until we get a contiguous FULL buffer 1029 * (frmt->hsz is the proper size) 1030 */ 1031 for (;;) { 1032 if ((ret = rd_wrbuf(hdend, res)) == res) 1033 break; 1034 1035 /* 1036 * If we read 0 bytes (EOF) from an archive when we 1037 * expect to find a header, we have stepped upon 1038 * an archive without the customary block of zeroes 1039 * end marker. It's just stupid to error out on 1040 * them, so exit gracefully. 1041 */ 1042 if (first && ret == 0) 1043 return(-1); 1044 first = 0; 1045 1046 /* 1047 * some kind of archive read problem, try to resync the 1048 * storage device, better give the user the bad news. 1049 */ 1050 if ((ret == 0) || (rd_sync() < 0)) { 1051 paxwarn(1,"Premature end of file on archive read"); 1052 return(-1); 1053 } 1054 if (!in_resync) { 1055 if (act == APPND) { 1056 paxwarn(1, 1057 "Archive I/O error, cannot continue"); 1058 return(-1); 1059 } 1060 paxwarn(1,"Archive I/O error. Trying to recover."); 1061 ++in_resync; 1062 } 1063 1064 /* 1065 * oh well, throw it all out and start over 1066 */ 1067 res = hsz; 1068 hdend = hdbuf; 1069 } 1070 1071 /* 1072 * ok we have a contiguous buffer of the right size. Call the 1073 * format read routine. If this was not a valid header and this 1074 * format stores trailers outside of the header, call the 1075 * format specific trailer routine to check for a trailer. We 1076 * have to watch out that we do not mis-identify file data or 1077 * block padding as a header or trailer. Format specific 1078 * trailer functions must NOT check for the trailer while we 1079 * are running in resync mode. Some trailer functions may tell 1080 * us that this block cannot contain a valid header either, so 1081 * we then throw out the entire block and start over. 1082 */ 1083 if ((*frmt->rd)(arcn, hdbuf) == 0) 1084 break; 1085 1086 if (!frmt->inhead) { 1087 /* 1088 * this format has trailers outside of valid headers 1089 */ 1090 if ((ret = (*frmt->trail)(hdbuf,in_resync,&cnt)) == 0){ 1091 /* 1092 * valid trailer found, drain input as required 1093 */ 1094 ar_drain(); 1095 return(-1); 1096 } 1097 1098 if (ret == 1) { 1099 /* 1100 * we are in resync and we were told to throw 1101 * the whole block out because none of the 1102 * bytes in this block can be used to form a 1103 * valid header 1104 */ 1105 res = hsz; 1106 hdend = hdbuf; 1107 continue; 1108 } 1109 } 1110 1111 /* 1112 * Brute force section. 1113 * not a valid header. We may be able to find a header yet. So 1114 * we shift over by one byte, and set up to read one byte at a 1115 * time from the archive and place it at the end of the buffer. 1116 * We will keep moving byte at a time until we find a header or 1117 * get a read error and have to start over. 1118 */ 1119 if (!in_resync) { 1120 if (act == APPND) { 1121 paxwarn(1,"Unable to append, archive header flaw"); 1122 return(-1); 1123 } 1124 paxwarn(1,"Invalid header, starting valid header search."); 1125 ++in_resync; 1126 } 1127 memmove(hdbuf, hdbuf+1, shftsz); 1128 res = 1; 1129 hdend = hdbuf + shftsz; 1130 } 1131 1132 /* 1133 * ok got a valid header, check for trailer if format encodes it in the 1134 * the header. NOTE: the parameters are different than trailer routines 1135 * which encode trailers outside of the header! 1136 */ 1137 if (frmt->inhead && ((*frmt->trail)(arcn) == 0)) { 1138 /* 1139 * valid trailer found, drain input as required 1140 */ 1141 ar_drain(); 1142 return(-1); 1143 } 1144 1145 ++flcnt; 1146 return(0); 1147 } 1148 1149 /* 1150 * get_arc() 1151 * Figure out what format an archive is. Handles archive with flaws by 1152 * brute force searches for a legal header in any supported format. The 1153 * format id routines have to be careful to NOT mis-identify a format. 1154 * ASSUMED: headers fit within a BLKMULT header. 1155 * Return: 1156 * 0 if archive found -1 otherwise 1157 */ 1158 1159 #ifdef __STDC__ 1160 static int 1161 get_arc(void) 1162 #else 1163 static int 1164 get_arc() 1165 #endif 1166 { 1167 register int i; 1168 register int hdsz = 0; 1169 register int res; 1170 register int minhd = BLKMULT; 1171 char *hdend; 1172 int notice = 0; 1173 1174 /* 1175 * find the smallest header size in all archive formats and then set up 1176 * to read the archive. 1177 */ 1178 for (i = 0; ford[i] >= 0; ++i) { 1179 if (fsub[ford[i]].hsz < minhd) 1180 minhd = fsub[ford[i]].hsz; 1181 } 1182 if (rd_start() < 0) 1183 return(-1); 1184 res = BLKMULT; 1185 hdsz = 0; 1186 hdend = hdbuf; 1187 for(;;) { 1188 for (;;) { 1189 /* 1190 * fill the buffer with at least the smallest header 1191 */ 1192 i = rd_wrbuf(hdend, res); 1193 if (i > 0) 1194 hdsz += i; 1195 if (hdsz >= minhd) 1196 break; 1197 1198 /* 1199 * if we cannot recover from a read error quit 1200 */ 1201 if ((i == 0) || (rd_sync() < 0)) 1202 goto out; 1203 1204 /* 1205 * when we get an error none of the data we already 1206 * have can be used to create a legal header (we just 1207 * got an error in the middle), so we throw it all out 1208 * and refill the buffer with fresh data. 1209 */ 1210 res = BLKMULT; 1211 hdsz = 0; 1212 hdend = hdbuf; 1213 if (!notice) { 1214 if (act == APPND) 1215 return(-1); 1216 paxwarn(1,"Cannot identify format. Searching..."); 1217 ++notice; 1218 } 1219 } 1220 1221 /* 1222 * we have at least the size of the smallest header in any 1223 * archive format. Look to see if we have a match. The array 1224 * ford[] is used to specify the header id order to reduce the 1225 * chance of incorrectly id'ing a valid header (some formats 1226 * may be subsets of each other and the order would then be 1227 * important). 1228 */ 1229 for (i = 0; ford[i] >= 0; ++i) { 1230 if ((*fsub[ford[i]].id)(hdbuf, hdsz) < 0) 1231 continue; 1232 frmt = &(fsub[ford[i]]); 1233 /* 1234 * yuck, to avoid slow special case code in the extract 1235 * routines, just push this header back as if it was 1236 * not seen. We have left extra space at start of the 1237 * buffer for this purpose. This is a bit ugly, but 1238 * adding all the special case code is far worse. 1239 */ 1240 pback(hdbuf, hdsz); 1241 return(0); 1242 } 1243 1244 /* 1245 * We have a flawed archive, no match. we start searching, but 1246 * we never allow additions to flawed archives 1247 */ 1248 if (!notice) { 1249 if (act == APPND) 1250 return(-1); 1251 paxwarn(1, "Cannot identify format. Searching..."); 1252 ++notice; 1253 } 1254 1255 /* 1256 * brute force search for a header that we can id. 1257 * we shift through byte at a time. this is slow, but we cannot 1258 * determine the nature of the flaw in the archive in a 1259 * portable manner 1260 */ 1261 if (--hdsz > 0) { 1262 memmove(hdbuf, hdbuf+1, hdsz); 1263 res = BLKMULT - hdsz; 1264 hdend = hdbuf + hdsz; 1265 } else { 1266 res = BLKMULT; 1267 hdend = hdbuf; 1268 hdsz = 0; 1269 } 1270 } 1271 1272 out: 1273 /* 1274 * we cannot find a header, bow, apologize and quit 1275 */ 1276 paxwarn(1, "Sorry, unable to determine archive format."); 1277 return(-1); 1278 } 1279