English Language flag
// Log In
// CVSweb
Project: FreeWRT
// Summary // Activity // Search // Tracker // Lists // News // SCM // Wiki

SCM Repository

ViewVC logotype

Contents of /branches/freewrt_1_0/tools/paxmirabilis/src/ar_io.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2715 - (show annotations) (download)
Tue Jun 5 14:52:44 2007 UTC (6 years, 8 months ago) by tg
File MIME type: text/plain
File size: 33073 byte(s)
• 1.0 -> scripts/param.h, paxmirabilis: MFC the new version from trunk
• both 1.0 and trunk: implement “make targz”, “make tarbz2”
  (I like the gzip(1)d versions better though)
• 1.0 -> package/config/Makefile: quieten the “clean” target to be consistent
1 /** $MirOS: src/bin/pax/ar_io.c,v 1.8 2007/02/17 04:52:39 tg Exp $ */
2 /* $OpenBSD: ar_io.c,v 1.37 2005/08/04 10:02:44 mpf Exp $ */
3 /* $NetBSD: ar_io.c,v 1.5 1996/03/26 23:54:13 mrg Exp $ */
4
5 /*-
6 * Copyright (c) 1992 Keith Muller.
7 * Copyright (c) 1992, 1993
8 * The Regents of the University of California. All rights reserved.
9 *
10 * This code is derived from software contributed to Berkeley by
11 * Keith Muller of the University of California, San Diego.
12 *
13 * Redistribution and use in source and binary forms, with or without
14 * modification, are permitted provided that the following conditions
15 * are met:
16 * 1. Redistributions of source code must retain the above copyright
17 * notice, this list of conditions and the following disclaimer.
18 * 2. Redistributions in binary form must reproduce the above copyright
19 * notice, this list of conditions and the following disclaimer in the
20 * documentation and/or other materials provided with the distribution.
21 * 3. 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
38 #include <sys/param.h>
39 #include <sys/time.h>
40 #include <sys/stat.h>
41 #include <sys/ioctl.h>
42 #ifndef __INTERIX
43 #include <sys/mtio.h>
44 #endif
45 #include <sys/wait.h>
46 #include <signal.h>
47 #include <string.h>
48 #include <fcntl.h>
49 #include <unistd.h>
50 #include <stdio.h>
51 #include <errno.h>
52 #include <stdlib.h>
53 #include <err.h>
54 #include "pax.h"
55 #include "options.h"
56 #include "extern.h"
57
58 __SCCSID("@(#)ar_io.c 8.2 (Berkeley) 4/18/94");
59 __RCSID("$MirOS: src/bin/pax/ar_io.c,v 1.8 2007/02/17 04:52:39 tg Exp $");
60
61 /*
62 * Routines which deal directly with the archive I/O device/file.
63 */
64
65 #define DMOD 0666 /* default mode of created archives */
66 #define EXT_MODE O_RDONLY /* open mode for list/extract */
67 #define AR_MODE (O_WRONLY | O_CREAT | O_TRUNC) /* mode for archive */
68 #define APP_MODE O_RDWR /* mode for append */
69 #define STDO "<STDOUT>" /* pseudo name for stdout */
70 #define STDN "<STDIN>" /* pseudo name for stdin */
71 static int arfd = -1; /* archive file descriptor */
72 static int artyp = ISREG; /* archive type: file/FIFO/tape */
73 static int arvol = 1; /* archive volume number */
74 static int lstrval = -1; /* return value from last i/o */
75 static int io_ok; /* i/o worked on volume after resync */
76 static int did_io; /* did i/o ever occur on volume? */
77 static int done; /* set via tty termination */
78 static struct stat arsb; /* stat of archive device at open */
79 static int invld_rec; /* tape has out of spec record size */
80 static int wr_trail = 1; /* trailer was rewritten in append */
81 static int can_unlnk = 0; /* do we unlink null archives? */
82 const char *arcname; /* printable name of archive */
83 static char *arcname_; /* this is so we can free(3) it */
84 const char *gzip_program; /* name of gzip program */
85 static pid_t zpid = -1; /* pid of child process */
86 int force_one_volume; /* 1 if we ignore volume changes */
87
88 #ifndef __INTERIX
89 static int get_phys(void);
90 #endif
91 extern sigset_t s_mask;
92 static void ar_start_gzip(int, int);
93
94 /*
95 * ar_open()
96 * Opens the next archive volume. Determines the type of the device and
97 * sets up block sizes as required by the archive device and the format.
98 * Note: we may be called with name == NULL on the first open only.
99 * Return:
100 * -1 on failure, 0 otherwise
101 */
102
103 int
104 ar_open(const char *name)
105 {
106 #ifndef __INTERIX
107 struct mtget mb;
108 #endif
109
110 if (arfd != -1)
111 (void)close(arfd);
112 arfd = -1;
113 can_unlnk = did_io = io_ok = invld_rec = 0;
114 artyp = ISREG;
115 flcnt = 0;
116
117 /*
118 * open based on overall operation mode
119 */
120 switch (act) {
121 case LIST:
122 case EXTRACT:
123 if (name == NULL) {
124 arfd = STDIN_FILENO;
125 arcname = STDN;
126 } else if ((arfd = open(name, EXT_MODE, DMOD)) < 0)
127 syswarn(1, errno, "Failed open to read on %s", name);
128 if (arfd != -1 && gzip_program != NULL)
129 ar_start_gzip(arfd, 0);
130 break;
131 case ARCHIVE:
132 if (name == NULL) {
133 arfd = STDOUT_FILENO;
134 arcname = STDO;
135 } else if ((arfd = open(name, AR_MODE, DMOD)) < 0)
136 syswarn(1, errno, "Failed open to write on %s", name);
137 else
138 can_unlnk = 1;
139 if (arfd != -1 && gzip_program != NULL)
140 ar_start_gzip(arfd, 1);
141 break;
142 case APPND:
143 if (name == NULL) {
144 arfd = STDOUT_FILENO;
145 arcname = STDO;
146 } else if ((arfd = open(name, APP_MODE, DMOD)) < 0)
147 syswarn(1, errno, "Failed open to read/write on %s",
148 name);
149 break;
150 case COPY:
151 /*
152 * arfd not used in COPY mode
153 */
154 arcname = "<NONE>";
155 lstrval = 1;
156 return(0);
157 }
158 if (arfd < 0)
159 return(-1);
160
161 if (chdname != NULL)
162 if (chdir(chdname) != 0) {
163 syswarn(1, errno, "Failed chdir to %s", chdname);
164 return(-1);
165 }
166 /*
167 * set up is based on device type
168 */
169 if (fstat(arfd, &arsb) < 0) {
170 syswarn(1, errno, "Failed stat on %s", arcname);
171 (void)close(arfd);
172 arfd = -1;
173 can_unlnk = 0;
174 return(-1);
175 }
176 if (S_ISDIR(arsb.st_mode)) {
177 paxwarn(0, "Cannot write an archive on top of a directory %s",
178 arcname);
179 (void)close(arfd);
180 arfd = -1;
181 can_unlnk = 0;
182 return(-1);
183 }
184
185 if (S_ISCHR(arsb.st_mode))
186 #ifndef __INTERIX
187 artyp = ioctl(arfd, MTIOCGET, &mb) ? ISCHR : ISTAPE;
188 #else
189 artyp = ISCHR;
190 #endif
191 else if (S_ISBLK(arsb.st_mode))
192 artyp = ISBLK;
193 else if ((lseek(arfd, (off_t)0L, SEEK_CUR) == -1) && (errno == ESPIPE))
194 artyp = ISPIPE;
195 else
196 artyp = ISREG;
197
198 /*
199 * make sure we beyond any doubt that we only can unlink regular files
200 * we created
201 */
202 if (artyp != ISREG)
203 can_unlnk = 0;
204 /*
205 * if we are writing, we are done
206 */
207 if (act == ARCHIVE) {
208 blksz = rdblksz = wrblksz;
209 lstrval = 1;
210 return(0);
211 }
212
213 /*
214 * set default blksz on read. APPNDs writes rdblksz on the last volume
215 * On all new archive volumes, we shift to wrblksz (if the user
216 * specified one, otherwise we will continue to use rdblksz). We
217 * must set blocksize based on what kind of device the archive is
218 * stored.
219 */
220 switch (artyp) {
221 case ISTAPE:
222 /*
223 * Tape drives come in at least two flavors. Those that support
224 * variable sized records and those that have fixed sized
225 * records. They must be treated differently. For tape drives
226 * that support variable sized records, we must make large
227 * reads to make sure we get the entire record, otherwise we
228 * will just get the first part of the record (up to size we
229 * asked). Tapes with fixed sized records may or may not return
230 * multiple records in a single read. We really do not care
231 * what the physical record size is UNLESS we are going to
232 * append. (We will need the physical block size to rewrite
233 * the trailer). Only when we are appending do we go to the
234 * effort to figure out the true PHYSICAL record size.
235 */
236 blksz = rdblksz = MAXBLK;
237 break;
238 case ISPIPE:
239 case ISBLK:
240 case ISCHR:
241 /*
242 * Blocksize is not a major issue with these devices (but must
243 * be kept a multiple of 512). If the user specified a write
244 * block size, we use that to read. Under append, we must
245 * always keep blksz == rdblksz. Otherwise we go ahead and use
246 * the device optimal blocksize as (and if) returned by stat
247 * and if it is within pax specs.
248 */
249 if ((act == APPND) && wrblksz) {
250 blksz = rdblksz = wrblksz;
251 break;
252 }
253
254 if ((arsb.st_blksize > 0) && (arsb.st_blksize < MAXBLK) &&
255 ((arsb.st_blksize % BLKMULT) == 0))
256 rdblksz = arsb.st_blksize;
257 else
258 rdblksz = DEVBLK;
259 /*
260 * For performance go for large reads when we can without harm
261 */
262 if ((act == APPND) || (artyp == ISCHR))
263 blksz = rdblksz;
264 else
265 blksz = MAXBLK;
266 break;
267 case ISREG:
268 /*
269 * if the user specified wrblksz works, use it. Under appends
270 * we must always keep blksz == rdblksz
271 */
272 if ((act == APPND) && wrblksz && ((arsb.st_size%wrblksz)==0)){
273 blksz = rdblksz = wrblksz;
274 break;
275 }
276 /*
277 * See if we can find the blocking factor from the file size
278 */
279 for (rdblksz = MAXBLK; rdblksz > 0; rdblksz -= BLKMULT)
280 if ((arsb.st_size % rdblksz) == 0)
281 break;
282 /*
283 * When we cannot find a match, we may have a flawed archive.
284 */
285 if (rdblksz <= 0)
286 rdblksz = FILEBLK;
287 /*
288 * for performance go for large reads when we can
289 */
290 if (act == APPND)
291 blksz = rdblksz;
292 else
293 blksz = MAXBLK;
294 break;
295 default:
296 /*
297 * should never happen, worst case, slow...
298 */
299 blksz = rdblksz = BLKMULT;
300 break;
301 }
302 lstrval = 1;
303 return(0);
304 }
305
306 /*
307 * ar_close()
308 * closes archive device, increments volume number, and prints i/o summary
309 */
310 void
311 ar_close(void)
312 {
313 int status;
314
315 if (arfd < 0) {
316 did_io = io_ok = flcnt = 0;
317 return;
318 }
319
320 /*
321 * Close archive file. This may take a LONG while on tapes (we may be
322 * forced to wait for the rewind to complete) so tell the user what is
323 * going on (this avoids the user hitting control-c thinking pax is
324 * broken).
325 */
326 if (vflag && (artyp == ISTAPE)) {
327 if (vfpart)
328 (void)putc('\n', listf);
329 (void)fprintf(listf,
330 "%s: Waiting for tape drive close to complete...",
331 argv0);
332 (void)fflush(listf);
333 }
334
335 /*
336 * if nothing was written to the archive (and we created it), we remove
337 * it
338 */
339 if (can_unlnk && (fstat(arfd, &arsb) == 0) && (S_ISREG(arsb.st_mode)) &&
340 (arsb.st_size == 0)) {
341 (void)unlink(arcname);
342 can_unlnk = 0;
343 }
344
345 /*
346 * for a quick extract/list, pax frequently exits before the child
347 * process is done
348 */
349 if ((act == LIST || act == EXTRACT) && nflag && zpid > 0)
350 kill(zpid, SIGINT);
351
352 (void)close(arfd);
353
354 /* Do not exit before child to ensure data integrity */
355 if (zpid > 0)
356 waitpid(zpid, &status, 0);
357
358 if (vflag && (artyp == ISTAPE)) {
359 (void)fputs("done.\n", listf);
360 vfpart = 0;
361 (void)fflush(listf);
362 }
363 arfd = -1;
364
365 if (!io_ok && !did_io) {
366 flcnt = 0;
367 return;
368 }
369 did_io = io_ok = 0;
370
371 /*
372 * The volume number is only increased when the last device has data
373 * and we have already determined the archive format.
374 */
375 if (frmt != NULL)
376 ++arvol;
377
378 if (!vflag) {
379 flcnt = 0;
380 return;
381 }
382
383 /*
384 * Print out a summary of I/O for this archive volume.
385 */
386 if (vfpart) {
387 (void)putc('\n', listf);
388 vfpart = 0;
389 }
390
391 /*
392 * If we have not determined the format yet, we just say how many bytes
393 * we have skipped over looking for a header to id. there is no way we
394 * could have written anything yet.
395 */
396 if (frmt == NULL) {
397 # ifdef LONG_OFF_T
398 (void)fprintf(listf, "%s: unknown format, %lu bytes skipped.\n",
399 # else
400 (void)fprintf(listf, "%s: unknown format, %llu bytes skipped.\n",
401 # endif
402 argv0, rdcnt);
403 (void)fflush(listf);
404 flcnt = 0;
405 return;
406 }
407
408 if (strcmp(NM_CPIO, argv0) == 0)
409 # ifdef LONG_OFF_T
410 (void)fprintf(listf, "%lu blocks\n", (rdcnt ? rdcnt : wrcnt) / 5120);
411 # else
412 (void)fprintf(listf, "%llu blocks\n", (rdcnt ? rdcnt : wrcnt) / 5120);
413 # endif
414 else if (strcmp(NM_TAR, argv0) != 0)
415 (void)fprintf(listf,
416 # ifdef LONG_OFF_T
417 "%s: %s vol %d, %lu files, %lu bytes read, %lu bytes written.\n",
418 # else
419 "%s: %s vol %d, %lu files, %llu bytes read, %llu bytes written.\n",
420 # endif
421 argv0, frmt->name, arvol-1, flcnt, rdcnt, wrcnt);
422 (void)fflush(listf);
423 flcnt = 0;
424 }
425
426 /*
427 * ar_drain()
428 * drain any archive format independent padding from an archive read
429 * from a socket or a pipe. This is to prevent the process on the
430 * other side of the pipe from getting a SIGPIPE (pax will stop
431 * reading an archive once a format dependent trailer is detected).
432 */
433 void
434 ar_drain(void)
435 {
436 int res;
437 char drbuf[MAXBLK];
438
439 /*
440 * we only drain from a pipe/socket. Other devices can be closed
441 * without reading up to end of file. We sure hope that pipe is closed
442 * on the other side so we will get an EOF.
443 */
444 if ((artyp != ISPIPE) || (lstrval <= 0))
445 return;
446
447 /*
448 * keep reading until pipe is drained
449 */
450 while ((res = read(arfd, drbuf, sizeof(drbuf))) > 0)
451 ;
452 lstrval = res;
453 }
454
455 /*
456 * ar_set_wr()
457 * Set up device right before switching from read to write in an append.
458 * device dependent code (if required) to do this should be added here.
459 * For all archive devices we are already positioned at the place we want
460 * to start writing when this routine is called.
461 * Return:
462 * 0 if all ready to write, -1 otherwise
463 */
464
465 int
466 ar_set_wr(void)
467 {
468 off_t cpos;
469
470 /*
471 * we must make sure the trailer is rewritten on append, ar_next()
472 * will stop us if the archive containing the trailer was not written
473 */
474 wr_trail = 0;
475
476 /*
477 * Add any device dependent code as required here
478 */
479 if (artyp != ISREG)
480 return(0);
481 /*
482 * Ok we have an archive in a regular file. If we were rewriting a
483 * file, we must get rid of all the stuff after the current offset
484 * (it was not written by pax).
485 */
486 if (((cpos = lseek(arfd, (off_t)0L, SEEK_CUR)) < 0) ||
487 (ftruncate(arfd, cpos) < 0)) {
488 syswarn(1, errno, "Unable to truncate archive file");
489 return(-1);
490 }
491 return(0);
492 }
493
494 /*
495 * ar_app_ok()
496 * check if the last volume in the archive allows appends. We cannot check
497 * this until we are ready to write since there is no spec that says all
498 * volumes in a single archive have to be of the same type...
499 * Return:
500 * 0 if we can append, -1 otherwise.
501 */
502
503 int
504 ar_app_ok(void)
505 {
506 if (artyp == ISPIPE) {
507 paxwarn(1, "Cannot append to an archive obtained from a pipe.");
508 return(-1);
509 }
510
511 if (!invld_rec)
512 return(0);
513 paxwarn(1,"Cannot append, device record size %d does not support %s spec",
514 rdblksz, argv0);
515 return(-1);
516 }
517
518 /*
519 * ar_read()
520 * read up to a specified number of bytes from the archive into the
521 * supplied buffer. When dealing with tapes we may not always be able to
522 * read what we want.
523 * Return:
524 * Number of bytes in buffer. 0 for end of file, -1 for a read error.
525 */
526
527 int
528 ar_read(char *buf, int cnt)
529 {
530 int res = 0;
531
532 /*
533 * if last i/o was in error, no more reads until reset or new volume
534 */
535 if (lstrval <= 0)
536 return(lstrval);
537
538 /*
539 * how we read must be based on device type
540 */
541 switch (artyp) {
542 case ISTAPE:
543 if ((res = read(arfd, buf, cnt)) > 0) {
544 /*
545 * CAUTION: tape systems may not always return the same
546 * sized records so we leave blksz == MAXBLK. The
547 * physical record size that a tape drive supports is
548 * very hard to determine in a uniform and portable
549 * manner.
550 */
551 io_ok = 1;
552 if (res != rdblksz) {
553 /*
554 * Record size changed. If this happens on
555 * any record after the first, we probably have
556 * a tape drive which has a fixed record size
557 * (we are getting multiple records in a single
558 * read). Watch out for record blocking that
559 * violates pax spec (must be a multiple of
560 * BLKMULT).
561 */
562 rdblksz = res;
563 if (rdblksz % BLKMULT)
564 invld_rec = 1;
565 }
566 return(res);
567 }
568 break;
569 case ISREG:
570 case ISBLK:
571 case ISCHR:
572 case ISPIPE:
573 default:
574 /*
575 * Files are so easy to deal with. These other things cannot
576 * be trusted at all. So when we are dealing with character
577 * devices and pipes we just take what they have ready for us
578 * and return. Trying to do anything else with them runs the
579 * risk of failure.
580 */
581 if ((res = read(arfd, buf, cnt)) > 0) {
582 io_ok = 1;
583 return(res);
584 }
585 break;
586 }
587
588 /*
589 * We are in trouble at this point, something is broken...
590 */
591 lstrval = res;
592 if (res < 0)
593 syswarn(1, errno, "Failed read on archive volume %d", arvol);
594 else
595 paxwarn(0, "End of archive volume %d reached", arvol);
596 return(res);
597 }
598
599 /*
600 * ar_write()
601 * Write a specified number of bytes in supplied buffer to the archive
602 * device so it appears as a single "block". Deals with errors and tries
603 * to recover when faced with short writes.
604 * Return:
605 * Number of bytes written. 0 indicates end of volume reached and with no
606 * flaws (as best that can be detected). A -1 indicates an unrecoverable
607 * error in the archive occurred.
608 */
609
610 int
611 ar_write(char *buf, int bsz)
612 {
613 int res;
614 off_t cpos;
615
616 /*
617 * do not allow pax to create a "bad" archive. Once a write fails on
618 * an archive volume prevent further writes to it.
619 */
620 if (lstrval <= 0)
621 return(lstrval);
622
623 if ((res = write(arfd, buf, bsz)) == bsz) {
624 wr_trail = 1;
625 io_ok = 1;
626 return(bsz);
627 }
628 /*
629 * write broke, see what we can do with it. We try to send any partial
630 * writes that may violate pax spec to the next archive volume.
631 */
632 if (res < 0)
633 lstrval = res;
634 else
635 lstrval = 0;
636
637 switch (artyp) {
638 case ISREG:
639 if ((res > 0) && (res % BLKMULT)) {
640 /*
641 * try to fix up partial writes which are not BLKMULT
642 * in size by forcing the runt record to next archive
643 * volume
644 */
645 if ((cpos = lseek(arfd, (off_t)0L, SEEK_CUR)) < 0)
646 break;
647 cpos -= (off_t)res;
648 if (ftruncate(arfd, cpos) < 0)
649 break;
650 res = lstrval = 0;
651 break;
652 }
653 if (res >= 0)
654 break;
655 /*
656 * if file is out of space, handle it like a return of 0
657 */
658 if ((errno == ENOSPC) || (errno == EFBIG) || (errno == EDQUOT))
659 res = lstrval = 0;
660 break;
661 case ISTAPE:
662 case ISCHR:
663 case ISBLK:
664 if (res >= 0)
665 break;
666 if (errno == EACCES) {
667 paxwarn(0, "Write failed, archive is write protected.");
668 res = lstrval = 0;
669 return(0);
670 }
671 /*
672 * see if we reached the end of media, if so force a change to
673 * the next volume
674 */
675 if ((errno == ENOSPC) || (errno == EIO) || (errno == ENXIO))
676 res = lstrval = 0;
677 break;
678 case ISPIPE:
679 default:
680 /*
681 * we cannot fix errors to these devices
682 */
683 break;
684 }
685
686 /*
687 * Better tell the user the bad news...
688 * if this is a block aligned archive format, we may have a bad archive
689 * if the format wants the header to start at a BLKMULT boundary.. While
690 * we can deal with the mis-aligned data, it violates spec and other
691 * archive readers will likely fail. if the format is not block
692 * aligned, the user may be lucky (and the archive is ok).
693 */
694 if (res >= 0) {
695 if (res > 0)
696 wr_trail = 1;
697 io_ok = 1;
698 }
699
700 /*
701 * If we were trying to rewrite the trailer and it didn't work, we
702 * must quit right away.
703 */
704 if (!wr_trail && (res <= 0)) {
705 paxwarn(1,"Unable to append, trailer re-write failed. Quitting.");
706 return(res);
707 }
708
709 if (res == 0)
710 paxwarn(0, "End of archive volume %d reached", arvol);
711 else if (res < 0)
712 syswarn(1, errno, "Failed write to archive volume: %d", arvol);
713 else if (!frmt->blkalgn || ((res % frmt->blkalgn) == 0))
714 paxwarn(0,"WARNING: partial archive write. Archive MAY BE FLAWED");
715 else
716 paxwarn(1,"WARNING: partial archive write. Archive IS FLAWED");
717 return(res);
718 }
719
720 /*
721 * ar_rdsync()
722 * Try to move past a bad spot on a flawed archive as needed to continue
723 * I/O. Clears error flags to allow I/O to continue.
724 * Return:
725 * 0 when ok to try i/o again, -1 otherwise.
726 */
727
728 int
729 ar_rdsync(void)
730 {
731 long fsbz;
732 off_t cpos;
733 off_t mpos;
734 #ifndef __INTERIX
735 struct mtop mb;
736 #endif
737
738 /*
739 * Fail resync attempts at user request (done) or if this is going to be
740 * an update/append to a existing archive. if last i/o hit media end,
741 * we need to go to the next volume not try a resync
742 */
743 if ((done > 0) || (lstrval == 0))
744 return(-1);
745
746 if ((act == APPND) || (act == ARCHIVE)) {
747 paxwarn(1, "Cannot allow updates to an archive with flaws.");
748 return(-1);
749 }
750 if (io_ok)
751 did_io = 1;
752
753 switch (artyp) {
754 #ifndef __INTERIX
755 case ISTAPE:
756 /*
757 * if the last i/o was a successful data transfer, we assume
758 * the fault is just a bad record on the tape that we are now
759 * past. If we did not get any data since the last resync try
760 * to move the tape forward one PHYSICAL record past any
761 * damaged tape section. Some tape drives are stubborn and need
762 * to be pushed.
763 */
764 if (io_ok) {
765 io_ok = 0;
766 lstrval = 1;
767 break;
768 }
769 mb.mt_op = MTFSR;
770 mb.mt_count = 1;
771 if (ioctl(arfd, MTIOCTOP, &mb) < 0)
772 break;
773 lstrval = 1;
774 break;
775 #endif
776 case ISREG:
777 case ISCHR:
778 case ISBLK:
779 /*
780 * try to step over the bad part of the device.
781 */
782 io_ok = 0;
783 if (((fsbz = arsb.st_blksize) <= 0) || (artyp != ISREG))
784 fsbz = BLKMULT;
785 if ((cpos = lseek(arfd, (off_t)0L, SEEK_CUR)) < 0)
786 break;
787 mpos = fsbz - (cpos % (off_t)fsbz);
788 if (lseek(arfd, mpos, SEEK_CUR) < 0)
789 break;
790 lstrval = 1;
791 break;
792 case ISPIPE:
793 default:
794 /*
795 * cannot recover on these archive device types
796 */
797 io_ok = 0;
798 break;
799 }
800 if (lstrval <= 0) {
801 paxwarn(1, "Unable to recover from an archive read failure.");
802 return(-1);
803 }
804 paxwarn(0, "Attempting to recover from an archive read failure.");
805 return(0);
806 }
807
808 /*
809 * ar_fow()
810 * Move the I/O position within the archive forward the specified number of
811 * bytes as supported by the device. If we cannot move the requested
812 * number of bytes, return the actual number of bytes moved in skipped.
813 * Return:
814 * 0 if moved the requested distance, -1 on complete failure, 1 on
815 * partial move (the amount moved is in skipped)
816 */
817
818 int
819 ar_fow(off_t sksz, off_t *skipped)
820 {
821 off_t cpos;
822 off_t mpos;
823
824 *skipped = 0;
825 if (sksz <= 0)
826 return(0);
827
828 /*
829 * we cannot move forward at EOF or error
830 */
831 if (lstrval <= 0)
832 return(lstrval);
833
834 /*
835 * Safer to read forward on devices where it is hard to find the end of
836 * the media without reading to it. With tapes we cannot be sure of the
837 * number of physical blocks to skip (we do not know physical block
838 * size at this point), so we must only read forward on tapes!
839 */
840 if (artyp != ISREG)
841 return(0);
842
843 /*
844 * figure out where we are in the archive
845 */
846 if ((cpos = lseek(arfd, (off_t)0L, SEEK_CUR)) >= 0) {
847 /*
848 * we can be asked to move farther than there are bytes in this
849 * volume, if so, just go to file end and let normal buf_fill()
850 * deal with the end of file (it will go to next volume by
851 * itself)
852 */
853 if ((mpos = cpos + sksz) > arsb.st_size) {
854 *skipped = arsb.st_size - cpos;
855 mpos = arsb.st_size;
856 } else
857 *skipped = sksz;
858 if (lseek(arfd, mpos, SEEK_SET) >= 0)
859 return(0);
860 }
861 syswarn(1, errno, "Forward positioning operation on archive failed");
862 lstrval = -1;
863 return(-1);
864 }
865
866 /*
867 * ar_rev()
868 * move the i/o position within the archive backwards the specified byte
869 * count as supported by the device. With tapes drives we RESET rdblksz to
870 * the PHYSICAL blocksize.
871 * NOTE: We should only be called to move backwards so we can rewrite the
872 * last records (the trailer) of an archive (APPEND).
873 * Return:
874 * 0 if moved the requested distance, -1 on complete failure
875 */
876
877 int
878 ar_rev(off_t sksz)
879 {
880 off_t cpos;
881 #ifndef __INTERIX
882 struct mtop mb;
883 #endif
884 int phyblk;
885
886 /*
887 * make sure we do not have try to reverse on a flawed archive
888 */
889 if (lstrval < 0)
890 return(lstrval);
891
892 switch (artyp) {
893 case ISPIPE:
894 if (sksz <= 0)
895 break;
896 /*
897 * cannot go backwards on these critters
898 */
899 paxwarn(1, "Reverse positioning on pipes is not supported.");
900 lstrval = -1;
901 return(-1);
902 case ISREG:
903 case ISBLK:
904 case ISCHR:
905 default:
906 if (sksz <= 0)
907 break;
908
909 /*
910 * For things other than files, backwards movement has a very
911 * high probability of failure as we really do not know the
912 * true attributes of the device we are talking to (the device
913 * may not even have the ability to lseek() in any direction).
914 * First we figure out where we are in the archive.
915 */
916 if ((cpos = lseek(arfd, (off_t)0L, SEEK_CUR)) < 0) {
917 syswarn(1, errno,
918 "Unable to obtain current archive byte offset");
919 lstrval = -1;
920 return(-1);
921 }
922
923 /*
924 * we may try to go backwards past the start when the archive
925 * is only a single record. If this happens and we are on a
926 * multi-volume archive, we need to go to the end of the
927 * previous volume and continue our movement backwards from
928 * there.
929 */
930 if ((cpos -= sksz) < (off_t)0L) {
931 if (arvol > 1) {
932 /*
933 * this should never happen
934 */
935 paxwarn(1,"Reverse position on previous volume.");
936 lstrval = -1;
937 return(-1);
938 }
939 cpos = (off_t)0L;
940 }
941 if (lseek(arfd, cpos, SEEK_SET) < 0) {
942 syswarn(1, errno, "Unable to seek archive backwards");
943 lstrval = -1;
944 return(-1);
945 }
946 break;
947 #ifndef __INTERIX
948 case ISTAPE:
949 /*
950 * Calculate and move the proper number of PHYSICAL tape
951 * blocks. If the sksz is not an even multiple of the physical
952 * tape size, we cannot do the move (this should never happen).
953 * (We also cannot handle trailers spread over two vols.)
954 * get_phys() also makes sure we are in front of the filemark.
955 */
956 if ((phyblk = get_phys()) <= 0) {
957 lstrval = -1;
958 return(-1);
959 }
960
961 /*
962 * make sure future tape reads only go by physical tape block
963 * size (set rdblksz to the real size).
964 */
965 rdblksz = phyblk;
966
967 /*
968 * if no movement is required, just return (we must be after
969 * get_phys() so the physical blocksize is properly set)
970 */
971 if (sksz <= 0)
972 break;
973
974 /*
975 * ok we have to move. Make sure the tape drive can do it.
976 */
977 if (sksz % phyblk) {
978 paxwarn(1,
979 "Tape drive unable to backspace requested amount");
980 lstrval = -1;
981 return(-1);
982 }
983
984 /*
985 * move backwards the requested number of bytes
986 */
987 mb.mt_op = MTBSR;
988 mb.mt_count = sksz/phyblk;
989 if (ioctl(arfd, MTIOCTOP, &mb) < 0) {
990 syswarn(1,errno, "Unable to backspace tape %d blocks.",
991 mb.mt_count);
992 lstrval = -1;
993 return(-1);
994 }
995 break;
996 #endif
997 }
998 lstrval = 1;
999 return(0);
1000 }
1001
1002 #ifndef __INTERIX
1003 /*
1004 * get_phys()
1005 * Determine the physical block size on a tape drive. We need the physical
1006 * block size so we know how many bytes we skip over when we move with
1007 * mtio commands. We also make sure we are BEFORE THE TAPE FILEMARK when
1008 * return.
1009 * This is one really SLOW routine...
1010 * Return:
1011 * physical block size if ok (ok > 0), -1 otherwise
1012 */
1013
1014 static int
1015 get_phys(void)
1016 {
1017 int padsz = 0;
1018 int res;
1019 int phyblk;
1020 struct mtop mb;
1021 char scbuf[MAXBLK];
1022
1023 /*
1024 * move to the file mark, and then back up one record and read it.
1025 * this should tell us the physical record size the tape is using.
1026 */
1027 if (lstrval == 1) {
1028 /*
1029 * we know we are at file mark when we get back a 0 from
1030 * read()
1031 */
1032 while ((res = read(arfd, scbuf, sizeof(scbuf))) > 0)
1033 padsz += res;
1034 if (res < 0) {
1035 syswarn(1, errno, "Unable to locate tape filemark.");
1036 return(-1);
1037 }
1038 }
1039
1040 /*
1041 * move backwards over the file mark so we are at the end of the
1042 * last record.
1043 */
1044 mb.mt_op = MTBSF;
1045 mb.mt_count = 1;
1046 if (ioctl(arfd, MTIOCTOP, &mb) < 0) {
1047 syswarn(1, errno, "Unable to backspace over tape filemark.");
1048 return(-1);
1049 }
1050
1051 /*
1052 * move backwards so we are in front of the last record and read it to
1053 * get physical tape blocksize.
1054 */
1055 mb.mt_op = MTBSR;
1056 mb.mt_count = 1;
1057 if (ioctl(arfd, MTIOCTOP, &mb) < 0) {
1058 syswarn(1, errno, "Unable to backspace over last tape block.");
1059 return(-1);
1060 }
1061 if ((phyblk = read(arfd, scbuf, sizeof(scbuf))) <= 0) {
1062 syswarn(1, errno, "Cannot determine archive tape blocksize.");
1063 return(-1);
1064 }
1065
1066 /*
1067 * read forward to the file mark, then back up in front of the filemark
1068 * (this is a bit paranoid, but should be safe to do).
1069 */
1070 while ((res = read(arfd, scbuf, sizeof(scbuf))) > 0)
1071 ;
1072 if (res < 0) {
1073 syswarn(1, errno, "Unable to locate tape filemark.");
1074 return(-1);
1075 }
1076 mb.mt_op = MTBSF;
1077 mb.mt_count = 1;
1078 if (ioctl(arfd, MTIOCTOP, &mb) < 0) {
1079 syswarn(1, errno, "Unable to backspace over tape filemark.");
1080 return(-1);
1081 }
1082
1083 /*
1084 * set lstrval so we know that the filemark has not been seen
1085 */
1086 lstrval = 1;
1087
1088 /*
1089 * return if there was no padding
1090 */
1091 if (padsz == 0)
1092 return(phyblk);
1093
1094 /*
1095 * make sure we can move backwards over the padding. (this should
1096 * never fail).
1097 */
1098 if (padsz % phyblk) {
1099 paxwarn(1, "Tape drive unable to backspace requested amount");
1100 return(-1);
1101 }
1102
1103 /*
1104 * move backwards over the padding so the head is where it was when
1105 * we were first called (if required).
1106 */
1107 mb.mt_op = MTBSR;
1108 mb.mt_count = padsz/phyblk;
1109 if (ioctl(arfd, MTIOCTOP, &mb) < 0) {
1110 syswarn(1,errno,"Unable to backspace tape over %d pad blocks",
1111 mb.mt_count);
1112 return(-1);
1113 }
1114 return(phyblk);
1115 }
1116 #endif
1117
1118 /*
1119 * ar_next()
1120 * prompts the user for the next volume in this archive. For some devices
1121 * we may allow the media to be changed. Otherwise a new archive is
1122 * prompted for. By pax spec, if there is no controlling tty or an eof is
1123 * read on tty input, we must quit pax.
1124 * Return:
1125 * 0 when ready to continue, -1 when all done
1126 */
1127
1128 int
1129 ar_next(void)
1130 {
1131 char buf[PAXPATHLEN+2];
1132 static int freeit = 0;
1133 sigset_t o_mask;
1134
1135 /*
1136 * WE MUST CLOSE THE DEVICE. A lot of devices must see last close, (so
1137 * things like writing EOF etc will be done) (Watch out ar_close() can
1138 * also be called via a signal handler, so we must prevent a race.
1139 */
1140 if (sigprocmask(SIG_BLOCK, &s_mask, &o_mask) < 0)
1141 syswarn(0, errno, "Unable to set signal mask");
1142 ar_close();
1143 if (sigprocmask(SIG_SETMASK, &o_mask, NULL) < 0)
1144 syswarn(0, errno, "Unable to restore signal mask");
1145
1146 if (done || !wr_trail || force_one_volume || strcmp(NM_TAR, argv0) == 0)
1147 return(-1);
1148
1149 tty_prnt("\nATTENTION! %s archive volume change required.\n", argv0);
1150
1151 /*
1152 * if i/o is on stdin or stdout, we cannot reopen it (we do not know
1153 * the name), the user will be forced to type it in.
1154 */
1155 if (strcmp(arcname, STDO) && strcmp(arcname, STDN) && (artyp != ISREG)
1156 && (artyp != ISPIPE)) {
1157 if (artyp == ISTAPE) {
1158 tty_prnt("%s ready for archive tape volume: %d\n",
1159 arcname, arvol);
1160 tty_prnt("Load the NEXT TAPE on the tape drive");
1161 } else {
1162 tty_prnt("%s ready for archive volume: %d\n",
1163 arcname, arvol);
1164 tty_prnt("Load the NEXT STORAGE MEDIA (if required)");
1165 }
1166
1167 if ((act == ARCHIVE) || (act == APPND))
1168 tty_prnt(" and make sure it is WRITE ENABLED.\n");
1169 else
1170 tty_prnt("\n");
1171
1172 for (;;) {
1173 tty_prnt("Type \"y\" to continue, \".\" to quit %s,",
1174 argv0);
1175 tty_prnt(" or \"s\" to switch to new device.\nIf you");
1176 tty_prnt(" cannot change storage media, type \"s\"\n");
1177 tty_prnt("Is the device ready and online? > ");
1178
1179 if ((tty_read(buf,sizeof(buf))<0) || !strcmp(buf,".")){
1180 done = 1;
1181 lstrval = -1;
1182 tty_prnt("Quitting %s!\n", argv0);
1183 vfpart = 0;
1184 return(-1);
1185 }
1186
1187 if ((buf[0] == '\0') || (buf[1] != '\0')) {
1188 tty_prnt("%s unknown command, try again\n",buf);
1189 continue;
1190 }
1191
1192 switch (buf[0]) {
1193 case 'y':
1194 case 'Y':
1195 /*
1196 * we are to continue with the same device
1197 */
1198 if (ar_open(arcname) >= 0)
1199 return(0);
1200 tty_prnt("Cannot re-open %s, try again\n",
1201 arcname);
1202 continue;
1203 case 's':
1204 case 'S':
1205 /*
1206 * user wants to open a different device
1207 */
1208 tty_prnt("Switching to a different archive\n");
1209 break;
1210 default:
1211 tty_prnt("%s unknown command, try again\n",buf);
1212 continue;
1213 }
1214 break;
1215 }
1216 } else
1217 tty_prnt("Ready for archive volume: %d\n", arvol);
1218
1219 /*
1220 * have to go to a different archive
1221 */
1222 for (;;) {
1223 tty_prnt("Input archive name or \".\" to quit %s.\n", argv0);
1224 tty_prnt("Archive name > ");
1225
1226 if ((tty_read(buf, sizeof(buf)) < 0) || !strcmp(buf, ".")) {
1227 done = 1;
1228 lstrval = -1;
1229 tty_prnt("Quitting %s!\n", argv0);
1230 vfpart = 0;
1231 return(-1);
1232 }
1233 if (buf[0] == '\0') {
1234 tty_prnt("Empty file name, try again\n");
1235 continue;
1236 }
1237 if (!strcmp(buf, "..")) {
1238 tty_prnt("Illegal file name: .. try again\n");
1239 continue;
1240 }
1241 if (strlen(buf) > PAXPATHLEN) {
1242 tty_prnt("File name too long, try again\n");
1243 continue;
1244 }
1245
1246 /*
1247 * try to open new archive
1248 */
1249 if (ar_open(buf) >= 0) {
1250 if (freeit) {
1251 free(arcname_);
1252 freeit = 0;
1253 }
1254 if ((arcname = arcname_ = strdup(buf)) == NULL) {
1255 done = 1;
1256 lstrval = -1;
1257 paxwarn(0, "Cannot save archive name.");
1258 return(-1);
1259 }
1260 freeit = 1;
1261 break;
1262 }
1263 tty_prnt("Cannot open %s, try again\n", buf);
1264 continue;
1265 }
1266 return(0);
1267 }
1268
1269 /*
1270 * ar_start_gzip()
1271 * starts the gzip compression/decompression process as a child, using magic
1272 * to keep the fd the same in the calling function (parent).
1273 */
1274 void
1275 ar_start_gzip(int fd, int wr)
1276 {
1277 int fds[2];
1278 const char *gzip_flags;
1279
1280 if (pipe(fds) < 0)
1281 err(1, "could not pipe");
1282 zpid = fork();
1283 if (zpid < 0)
1284 err(1, "could not fork");
1285
1286 /* parent */
1287 if (zpid) {
1288 if (wr)
1289 dup2(fds[1], fd);
1290 else
1291 dup2(fds[0], fd);
1292 close(fds[0]);
1293 close(fds[1]);
1294 } else {
1295 if (wr) {
1296 dup2(fds[0], STDIN_FILENO);
1297 dup2(fd, STDOUT_FILENO);
1298 gzip_flags = "-c";
1299 } else {
1300 dup2(fds[1], STDOUT_FILENO);
1301 dup2(fd, STDIN_FILENO);
1302 gzip_flags = "-dc";
1303 }
1304 close(fds[0]);
1305 close(fds[1]);
1306 if (execlp(gzip_program, gzip_program, gzip_flags, NULL) < 0)
1307 err(1, "could not exec");
1308 /* NOTREACHED */
1309 }
1310 }

root@freewrt.org:443
ViewVC Help
Powered by ViewVC 1.1.20