source: vendor/tar/1.16.1/src/buffer.c

Last change on this file was 3342, checked in by bird, 19 years ago

tar 1.16.1

File size: 39.5 KB
Line 
1/* Buffer management for tar.
2
3 Copyright (C) 1988, 1992, 1993, 1994, 1996, 1997, 1999, 2000, 2001,
4 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
5
6 Written by John Gilmore, on 1985-08-25.
7
8 This program is free software; you can redistribute it and/or modify it
9 under the terms of the GNU General Public License as published by the
10 Free Software Foundation; either version 2, or (at your option) any later
11 version.
12
13 This program is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
16 Public License for more details.
17
18 You should have received a copy of the GNU General Public License along
19 with this program; if not, write to the Free Software Foundation, Inc.,
20 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */
21
22#include <system.h>
23#include <system-ioctl.h>
24
25#include <signal.h>
26
27#include <closeout.h>
28#include <fnmatch.h>
29#include <getline.h>
30#include <human.h>
31#include <quotearg.h>
32
33#include "common.h"
34#include <rmt.h>
35
36/* Number of retries before giving up on read. */
37#define READ_ERROR_MAX 10
38
39/* Globbing pattern to append to volume label if initial match failed. */
40#define VOLUME_LABEL_APPEND " Volume [1-9]*"
41
42/* Variables. */
43
44static tarlong prev_written; /* bytes written on previous volumes */
45static tarlong bytes_written; /* bytes written on this volume */
46static void *record_buffer[2]; /* allocated memory */
47union block *record_buffer_aligned[2];
48static int record_index;
49
50/* FIXME: The following variables should ideally be static to this
51 module. However, this cannot be done yet. The cleanup continues! */
52
53union block *record_start; /* start of record of archive */
54union block *record_end; /* last+1 block of archive record */
55union block *current_block; /* current block of archive */
56enum access_mode access_mode; /* how do we handle the archive */
57off_t records_read; /* number of records read from this archive */
58off_t records_written; /* likewise, for records written */
59extern off_t records_skipped; /* number of records skipped at the start
60 of the archive, defined in delete.c */
61
62static off_t record_start_block; /* block ordinal at record_start */
63
64/* Where we write list messages (not errors, not interactions) to. */
65FILE *stdlis;
66
67static void backspace_output (void);
68
69/* PID of child program, if compress_option or remote archive access. */
70static pid_t child_pid;
71
72/* Error recovery stuff */
73static int read_error_count;
74
75/* Have we hit EOF yet? */
76static bool hit_eof;
77
78/* Checkpointing counter */
79static unsigned checkpoint;
80
81static bool read_full_records = false;
82
83/* We're reading, but we just read the last block and it's time to update.
84 Declared in update.c
85
86 As least EXTERN like this one as possible. (?? --gray)
87 FIXME: Either eliminate it or move it to common.h.
88*/
89extern bool time_to_start_writing;
90
91bool write_archive_to_stdout;
92
93void (*flush_write_ptr) (size_t);
94void (*flush_read_ptr) (void);
95
96
97
98char *volume_label;
99char *continued_file_name;
100uintmax_t continued_file_size;
101uintmax_t continued_file_offset;
102
103
104
105static int volno = 1; /* which volume of a multi-volume tape we're
106 on */
107static int global_volno = 1; /* volume number to print in external
108 messages */
109
110bool write_archive_to_stdout;
111
112/* Used by flush_read and flush_write to store the real info about saved
113 names. */
114static char *real_s_name;
115static off_t real_s_totsize;
116static off_t real_s_sizeleft;
117
118
119
120/* Multi-volume tracking support */
121static char *save_name; /* name of the file we are currently writing */
122static off_t save_totsize; /* total size of file we are writing, only
123 valid if save_name is nonzero */
124static off_t save_sizeleft; /* where we are in the file we are writing,
125 only valid if save_name is nonzero */
126
127void
128mv_begin (struct tar_stat_info *st)
129{
130 if (multi_volume_option)
131 {
132 assign_string (&save_name, st->orig_file_name);
133 save_totsize = save_sizeleft = st->stat.st_size;
134 }
135}
136
137void
138mv_end ()
139{
140 if (multi_volume_option)
141 assign_string (&save_name, 0);
142}
143
144void
145mv_total_size (off_t size)
146{
147 save_totsize = size;
148}
149
150void
151mv_size_left (off_t size)
152{
153 save_sizeleft = size;
154}
155
156
157
158/* Functions. */
159
160void
161clear_read_error_count (void)
162{
163 read_error_count = 0;
164}
165
166
167
168/* Time-related functions */
169
170double duration;
171
172void
173set_start_time ()
174{
175 gettime (&start_time);
176 volume_start_time = start_time;
177 last_stat_time = start_time;
178}
179
180void
181set_volume_start_time ()
182{
183 gettime (&volume_start_time);
184 last_stat_time = volume_start_time;
185}
186
187void
188compute_duration ()
189{
190 struct timespec now;
191 gettime (&now);
192 duration += ((now.tv_sec - last_stat_time.tv_sec)
193 + (now.tv_nsec - last_stat_time.tv_nsec) / 1e9);
194 gettime (&last_stat_time);
195}
196
197
198
199/* Compression detection */
200
201enum compress_type {
202 ct_none,
203 ct_compress,
204 ct_gzip,
205 ct_bzip2
206};
207
208struct zip_magic
209{
210 enum compress_type type;
211 size_t length;
212 char *magic;
213 char *program;
214 char *option;
215};
216
217static struct zip_magic const magic[] = {
218 { ct_none, },
219 { ct_compress, 2, "\037\235", "compress", "-Z" },
220 { ct_gzip, 2, "\037\213", "gzip", "-z" },
221 { ct_bzip2, 3, "BZh", "bzip2", "-j" },
222};
223
224#define NMAGIC (sizeof(magic)/sizeof(magic[0]))
225
226#define compress_option(t) magic[t].option
227#define compress_program(t) magic[t].program
228
229/* Check if the file ARCHIVE is a compressed archive. */
230enum compress_type
231check_compressed_archive ()
232{
233 struct zip_magic const *p;
234 bool sfr;
235
236 /* Prepare global data needed for find_next_block: */
237 record_end = record_start; /* set up for 1st record = # 0 */
238 sfr = read_full_records;
239 read_full_records = true; /* Suppress fatal error on reading a partial
240 record */
241 find_next_block ();
242
243 /* Restore global values */
244 read_full_records = sfr;
245
246 if (tar_checksum (record_start, true) == HEADER_SUCCESS)
247 /* Probably a valid header */
248 return ct_none;
249
250 for (p = magic + 1; p < magic + NMAGIC; p++)
251 if (memcmp (record_start->buffer, p->magic, p->length) == 0)
252 return p->type;
253
254 return ct_none;
255}
256
257/* Open an archive named archive_name_array[0]. Detect if it is
258 a compressed archive of known type and use corresponding decompression
259 program if so */
260int
261open_compressed_archive ()
262{
263 archive = rmtopen (archive_name_array[0], O_RDONLY | O_BINARY,
264 MODE_RW, rsh_command_option);
265 if (archive == -1)
266 return archive;
267
268 if (!multi_volume_option)
269 {
270 enum compress_type type = check_compressed_archive ();
271
272 if (type == ct_none)
273 return archive;
274
275 /* FD is not needed any more */
276 rmtclose (archive);
277
278 hit_eof = false; /* It might have been set by find_next_block in
279 check_compressed_archive */
280
281 /* Open compressed archive */
282 use_compress_program_option = compress_program (type);
283 child_pid = sys_child_open_for_uncompress ();
284 read_full_records = true;
285 }
286
287 records_read = 0;
288 record_end = record_start; /* set up for 1st record = # 0 */
289
290 return archive;
291}
292
293
294
295static void
296print_stats (FILE *fp, const char *text, tarlong numbytes)
297{
298 char bytes[sizeof (tarlong) * CHAR_BIT];
299 char abbr[LONGEST_HUMAN_READABLE + 1];
300 char rate[LONGEST_HUMAN_READABLE + 1];
301
302 int human_opts = human_autoscale | human_base_1024 | human_SI | human_B;
303
304 sprintf (bytes, TARLONG_FORMAT, numbytes);
305
306 fprintf (fp, "%s: %s (%s, %s/s)\n",
307 text, bytes,
308 human_readable (numbytes, abbr, human_opts, 1, 1),
309 (0 < duration && numbytes / duration < (uintmax_t) -1
310 ? human_readable (numbytes / duration, rate, human_opts, 1, 1)
311 : "?"));
312}
313
314void
315print_total_stats ()
316{
317 switch (subcommand_option)
318 {
319 case CREATE_SUBCOMMAND:
320 case CAT_SUBCOMMAND:
321 case UPDATE_SUBCOMMAND:
322 case APPEND_SUBCOMMAND:
323 /* Amanda 2.4.1p1 looks for "Total bytes written: [0-9][0-9]*". */
324 print_stats (stderr, _("Total bytes written"),
325 prev_written + bytes_written);
326 break;
327
328 case DELETE_SUBCOMMAND:
329 {
330 char buf[UINTMAX_STRSIZE_BOUND];
331 print_stats (stderr, _("Total bytes read"),
332 records_read * record_size);
333 print_stats (stderr, _("Total bytes written"),
334 prev_written + bytes_written);
335 fprintf (stderr, _("Total bytes deleted: %s\n"),
336 STRINGIFY_BIGINT ((records_read - records_skipped)
337 * record_size
338 - (prev_written + bytes_written), buf));
339 }
340 break;
341
342 case EXTRACT_SUBCOMMAND:
343 case LIST_SUBCOMMAND:
344 case DIFF_SUBCOMMAND:
345 print_stats (stderr, _("Total bytes read"),
346 records_read * record_size);
347 break;
348
349 default:
350 abort ();
351 }
352}
353
354/* Compute and return the block ordinal at current_block. */
355off_t
356current_block_ordinal (void)
357{
358 return record_start_block + (current_block - record_start);
359}
360
361/* If the EOF flag is set, reset it, as well as current_block, etc. */
362void
363reset_eof (void)
364{
365 if (hit_eof)
366 {
367 hit_eof = false;
368 current_block = record_start;
369 record_end = record_start + blocking_factor;
370 access_mode = ACCESS_WRITE;
371 }
372}
373
374/* Return the location of the next available input or output block.
375 Return zero for EOF. Once we have returned zero, we just keep returning
376 it, to avoid accidentally going on to the next file on the tape. */
377union block *
378find_next_block (void)
379{
380 if (current_block == record_end)
381 {
382 if (hit_eof)
383 return 0;
384 flush_archive ();
385 if (current_block == record_end)
386 {
387 hit_eof = true;
388 return 0;
389 }
390 }
391 return current_block;
392}
393
394/* Indicate that we have used all blocks up thru BLOCK. */
395void
396set_next_block_after (union block *block)
397{
398 while (block >= current_block)
399 current_block++;
400
401 /* Do *not* flush the archive here. If we do, the same argument to
402 set_next_block_after could mean the next block (if the input record
403 is exactly one block long), which is not what is intended. */
404
405 if (current_block > record_end)
406 abort ();
407}
408
409/* Return the number of bytes comprising the space between POINTER
410 through the end of the current buffer of blocks. This space is
411 available for filling with data, or taking data from. POINTER is
412 usually (but not always) the result of previous find_next_block call. */
413size_t
414available_space_after (union block *pointer)
415{
416 return record_end->buffer - pointer->buffer;
417}
418
419/* Close file having descriptor FD, and abort if close unsuccessful. */
420void
421xclose (int fd)
422{
423 if (close (fd) != 0)
424 close_error (_("(pipe)"));
425}
426
427static void
428init_buffer ()
429{
430 if (! record_buffer_aligned[record_index])
431 record_buffer_aligned[record_index] =
432 page_aligned_alloc (&record_buffer[record_index], record_size);
433
434 record_start = record_buffer_aligned[record_index];
435 current_block = record_start;
436 record_end = record_start + blocking_factor;
437}
438
439/* Open an archive file. The argument specifies whether we are
440 reading or writing, or both. */
441static void
442_open_archive (enum access_mode wanted_access)
443{
444 int backed_up_flag = 0;
445
446 if (record_size == 0)
447 FATAL_ERROR ((0, 0, _("Invalid value for record_size")));
448
449 if (archive_names == 0)
450 FATAL_ERROR ((0, 0, _("No archive name given")));
451
452 tar_stat_destroy (&current_stat_info);
453 save_name = 0;
454 real_s_name = 0;
455
456 record_index = 0;
457 init_buffer ();
458
459 /* When updating the archive, we start with reading. */
460 access_mode = wanted_access == ACCESS_UPDATE ? ACCESS_READ : wanted_access;
461
462 read_full_records = read_full_records_option;
463
464 records_read = 0;
465
466 if (use_compress_program_option)
467 {
468 switch (wanted_access)
469 {
470 case ACCESS_READ:
471 child_pid = sys_child_open_for_uncompress ();
472 read_full_records = true;
473 record_end = record_start; /* set up for 1st record = # 0 */
474 break;
475
476 case ACCESS_WRITE:
477 child_pid = sys_child_open_for_compress ();
478 break;
479
480 case ACCESS_UPDATE:
481 abort (); /* Should not happen */
482 break;
483 }
484
485 if (!index_file_name
486 && wanted_access == ACCESS_WRITE
487 && strcmp (archive_name_array[0], "-") == 0)
488 stdlis = stderr;
489 }
490 else if (strcmp (archive_name_array[0], "-") == 0)
491 {
492 read_full_records = true; /* could be a pipe, be safe */
493 if (verify_option)
494 FATAL_ERROR ((0, 0, _("Cannot verify stdin/stdout archive")));
495
496 switch (wanted_access)
497 {
498 case ACCESS_READ:
499 {
500 enum compress_type type;
501
502 archive = STDIN_FILENO;
503
504 type = check_compressed_archive ();
505 if (type != ct_none)
506 FATAL_ERROR ((0, 0,
507 _("Archive is compressed. Use %s option"),
508 compress_option (type)));
509 }
510 break;
511
512 case ACCESS_WRITE:
513 archive = STDOUT_FILENO;
514 if (!index_file_name)
515 stdlis = stderr;
516 break;
517
518 case ACCESS_UPDATE:
519 archive = STDIN_FILENO;
520 write_archive_to_stdout = true;
521 record_end = record_start; /* set up for 1st record = # 0 */
522 if (!index_file_name)
523 stdlis = stderr;
524 break;
525 }
526 }
527 else if (verify_option)
528 archive = rmtopen (archive_name_array[0], O_RDWR | O_CREAT | O_BINARY,
529 MODE_RW, rsh_command_option);
530 else
531 switch (wanted_access)
532 {
533 case ACCESS_READ:
534 archive = open_compressed_archive ();
535 break;
536
537 case ACCESS_WRITE:
538 if (backup_option)
539 {
540 maybe_backup_file (archive_name_array[0], 1);
541 backed_up_flag = 1;
542 }
543 archive = rmtcreat (archive_name_array[0], MODE_RW,
544 rsh_command_option);
545 break;
546
547 case ACCESS_UPDATE:
548 archive = rmtopen (archive_name_array[0],
549 O_RDWR | O_CREAT | O_BINARY,
550 MODE_RW, rsh_command_option);
551
552 if (check_compressed_archive () != ct_none)
553 FATAL_ERROR ((0, 0,
554 _("Cannot update compressed archives")));
555 break;
556 }
557
558 if (archive < 0
559 || (! _isrmt (archive) && !sys_get_archive_stat ()))
560 {
561 int saved_errno = errno;
562
563 if (backed_up_flag)
564 undo_last_backup ();
565 errno = saved_errno;
566 open_fatal (archive_name_array[0]);
567 }
568
569 sys_detect_dev_null_output ();
570 sys_save_archive_dev_ino ();
571 SET_BINARY_MODE (archive);
572
573 switch (wanted_access)
574 {
575 case ACCESS_READ:
576 find_next_block (); /* read it in, check for EOF */
577 break;
578
579 case ACCESS_UPDATE:
580 case ACCESS_WRITE:
581 records_written = 0;
582 break;
583 }
584}
585
586static void
587do_checkpoint (bool write)
588{
589 if (checkpoint_option && !(++checkpoint % checkpoint_option))
590 {
591 switch (checkpoint_style)
592 {
593 case checkpoint_dot:
594 fputc ('.', stdlis);
595 fflush (stdlis);
596 break;
597
598 case checkpoint_text:
599 if (write)
600 /* TRANSLATORS: This is a ``checkpoint of write operation'',
601 *not* ``Writing a checkpoint''.
602 E.g. in Spanish ``Punto de comprobaci@'on de escritura'',
603 *not* ``Escribiendo un punto de comprobaci@'on'' */
604 WARN ((0, 0, _("Write checkpoint %u"), checkpoint));
605 else
606 /* TRANSLATORS: This is a ``checkpoint of read operation'',
607 *not* ``Reading a checkpoint''.
608 E.g. in Spanish ``Punto de comprobaci@'on de lectura'',
609 *not* ``Leyendo un punto de comprobaci@'on'' */
610 WARN ((0, 0, _("Read checkpoint %u"), checkpoint));
611 break;
612 }
613 }
614}
615
616/* Perform a write to flush the buffer. */
617ssize_t
618_flush_write (void)
619{
620 ssize_t status;
621
622 do_checkpoint (true);
623 if (tape_length_option && tape_length_option <= bytes_written)
624 {
625 errno = ENOSPC;
626 status = 0;
627 }
628 else if (dev_null_output)
629 status = record_size;
630 else
631 status = sys_write_archive_buffer ();
632
633 return status;
634}
635
636/* Handle write errors on the archive. Write errors are always fatal.
637 Hitting the end of a volume does not cause a write error unless the
638 write was the first record of the volume. */
639void
640archive_write_error (ssize_t status)
641{
642 /* It might be useful to know how much was written before the error
643 occurred. */
644 if (totals_option)
645 {
646 int e = errno;
647 print_total_stats ();
648 errno = e;
649 }
650
651 write_fatal_details (*archive_name_cursor, status, record_size);
652}
653
654/* Handle read errors on the archive. If the read should be retried,
655 return to the caller. */
656void
657archive_read_error (void)
658{
659 read_error (*archive_name_cursor);
660
661 if (record_start_block == 0)
662 FATAL_ERROR ((0, 0, _("At beginning of tape, quitting now")));
663
664 /* Read error in mid archive. We retry up to READ_ERROR_MAX times and
665 then give up on reading the archive. */
666
667 if (read_error_count++ > READ_ERROR_MAX)
668 FATAL_ERROR ((0, 0, _("Too many errors, quitting")));
669 return;
670}
671
672static void
673short_read (size_t status)
674{
675 size_t left; /* bytes left */
676 char *more; /* pointer to next byte to read */
677
678 more = record_start->buffer + status;
679 left = record_size - status;
680
681 while (left % BLOCKSIZE != 0
682 || (left && status && read_full_records))
683 {
684 if (status)
685 while ((status = rmtread (archive, more, left)) == SAFE_READ_ERROR)
686 archive_read_error ();
687
688 if (status == 0)
689 break;
690
691 if (! read_full_records)
692 {
693 unsigned long rest = record_size - left;
694
695 FATAL_ERROR ((0, 0,
696 ngettext ("Unaligned block (%lu byte) in archive",
697 "Unaligned block (%lu bytes) in archive",
698 rest),
699 rest));
700 }
701
702 /* User warned us about this. Fix up. */
703
704 left -= status;
705 more += status;
706 }
707
708 /* FIXME: for size=0, multi-volume support. On the first record, warn
709 about the problem. */
710
711 if (!read_full_records && verbose_option > 1
712 && record_start_block == 0 && status != 0)
713 {
714 unsigned long rsize = (record_size - left) / BLOCKSIZE;
715 WARN ((0, 0,
716 ngettext ("Record size = %lu block",
717 "Record size = %lu blocks",
718 rsize),
719 rsize));
720 }
721
722 record_end = record_start + (record_size - left) / BLOCKSIZE;
723 records_read++;
724}
725
726/* Flush the current buffer to/from the archive. */
727void
728flush_archive (void)
729{
730 size_t buffer_level = current_block->buffer - record_start->buffer;
731 record_start_block += record_end - record_start;
732 current_block = record_start;
733 record_end = record_start + blocking_factor;
734
735 if (access_mode == ACCESS_READ && time_to_start_writing)
736 {
737 access_mode = ACCESS_WRITE;
738 time_to_start_writing = false;
739 backspace_output ();
740 }
741
742 switch (access_mode)
743 {
744 case ACCESS_READ:
745 flush_read ();
746 break;
747
748 case ACCESS_WRITE:
749 flush_write_ptr (buffer_level);
750 break;
751
752 case ACCESS_UPDATE:
753 abort ();
754 }
755}
756
757/* Backspace the archive descriptor by one record worth. If it's a
758 tape, MTIOCTOP will work. If it's something else, try to seek on
759 it. If we can't seek, we lose! */
760static void
761backspace_output (void)
762{
763#ifdef MTIOCTOP
764 {
765 struct mtop operation;
766
767 operation.mt_op = MTBSR;
768 operation.mt_count = 1;
769 if (rmtioctl (archive, MTIOCTOP, (char *) &operation) >= 0)
770 return;
771 if (errno == EIO && rmtioctl (archive, MTIOCTOP, (char *) &operation) >= 0)
772 return;
773 }
774#endif
775
776 {
777 off_t position = rmtlseek (archive, (off_t) 0, SEEK_CUR);
778
779 /* Seek back to the beginning of this record and start writing there. */
780
781 position -= record_size;
782 if (position < 0)
783 position = 0;
784 if (rmtlseek (archive, position, SEEK_SET) != position)
785 {
786 /* Lseek failed. Try a different method. */
787
788 WARN ((0, 0,
789 _("Cannot backspace archive file; it may be unreadable without -i")));
790
791 /* Replace the first part of the record with NULs. */
792
793 if (record_start->buffer != output_start)
794 memset (record_start->buffer, 0,
795 output_start - record_start->buffer);
796 }
797 }
798}
799
800off_t
801seek_archive (off_t size)
802{
803 off_t start = current_block_ordinal ();
804 off_t offset;
805 off_t nrec, nblk;
806 off_t skipped = (blocking_factor - (current_block - record_start));
807
808 size -= skipped * BLOCKSIZE;
809
810 if (size < record_size)
811 return 0;
812 /* FIXME: flush? */
813
814 /* Compute number of records to skip */
815 nrec = size / record_size;
816 offset = rmtlseek (archive, nrec * record_size, SEEK_CUR);
817 if (offset < 0)
818 return offset;
819
820 if (offset % record_size)
821 FATAL_ERROR ((0, 0, _("rmtlseek not stopped at a record boundary")));
822
823 /* Convert to number of records */
824 offset /= BLOCKSIZE;
825 /* Compute number of skipped blocks */
826 nblk = offset - start;
827
828 /* Update buffering info */
829 records_read += nblk / blocking_factor;
830 record_start_block = offset - blocking_factor;
831 current_block = record_end;
832
833 return nblk;
834}
835
836/* Close the archive file. */
837void
838close_archive (void)
839{
840 if (time_to_start_writing || access_mode == ACCESS_WRITE)
841 {
842 flush_archive ();
843 if (current_block > record_start)
844 flush_archive ();
845 }
846
847 sys_drain_input_pipe ();
848
849 compute_duration ();
850 if (verify_option)
851 verify_volume ();
852
853 if (rmtclose (archive) != 0)
854 close_warn (*archive_name_cursor);
855
856 sys_wait_for_child (child_pid);
857
858 tar_stat_destroy (&current_stat_info);
859 if (save_name)
860 free (save_name);
861 if (real_s_name)
862 free (real_s_name);
863 free (record_buffer[0]);
864 free (record_buffer[1]);
865}
866
867/* Called to initialize the global volume number. */
868void
869init_volume_number (void)
870{
871 FILE *file = fopen (volno_file_option, "r");
872
873 if (file)
874 {
875 if (fscanf (file, "%d", &global_volno) != 1
876 || global_volno < 0)
877 FATAL_ERROR ((0, 0, _("%s: contains invalid volume number"),
878 quotearg_colon (volno_file_option)));
879 if (ferror (file))
880 read_error (volno_file_option);
881 if (fclose (file) != 0)
882 close_error (volno_file_option);
883 }
884 else if (errno != ENOENT)
885 open_error (volno_file_option);
886}
887
888/* Called to write out the closing global volume number. */
889void
890closeout_volume_number (void)
891{
892 FILE *file = fopen (volno_file_option, "w");
893
894 if (file)
895 {
896 fprintf (file, "%d\n", global_volno);
897 if (ferror (file))
898 write_error (volno_file_option);
899 if (fclose (file) != 0)
900 close_error (volno_file_option);
901 }
902 else
903 open_error (volno_file_option);
904}
905
906
907
908static void
909increase_volume_number ()
910{
911 global_volno++;
912 if (global_volno < 0)
913 FATAL_ERROR ((0, 0, _("Volume number overflow")));
914 volno++;
915}
916
917void
918change_tape_menu (FILE *read_file)
919{
920 char *input_buffer = NULL;
921 size_t size = 0;
922 bool stop = false;
923
924 while (!stop)
925 {
926 fputc ('\007', stderr);
927 fprintf (stderr,
928 _("Prepare volume #%d for %s and hit return: "),
929 global_volno + 1, quote (*archive_name_cursor));
930 fflush (stderr);
931
932 if (getline (&input_buffer, &size, read_file) <= 0)
933 {
934 WARN ((0, 0, _("EOF where user reply was expected")));
935
936 if (subcommand_option != EXTRACT_SUBCOMMAND
937 && subcommand_option != LIST_SUBCOMMAND
938 && subcommand_option != DIFF_SUBCOMMAND)
939 WARN ((0, 0, _("WARNING: Archive is incomplete")));
940
941 fatal_exit ();
942 }
943
944 if (input_buffer[0] == '\n'
945 || input_buffer[0] == 'y'
946 || input_buffer[0] == 'Y')
947 break;
948
949 switch (input_buffer[0])
950 {
951 case '?':
952 {
953 fprintf (stderr, _("\
954 n name Give a new file name for the next (and subsequent) volume(s)\n\
955 q Abort tar\n\
956 y or newline Continue operation\n"));
957 if (!restrict_option)
958 fprintf (stderr, _(" ! Spawn a subshell\n"));
959 fprintf (stderr, _(" ? Print this list\n"));
960 }
961 break;
962
963 case 'q':
964 /* Quit. */
965
966 WARN ((0, 0, _("No new volume; exiting.\n")));
967
968 if (subcommand_option != EXTRACT_SUBCOMMAND
969 && subcommand_option != LIST_SUBCOMMAND
970 && subcommand_option != DIFF_SUBCOMMAND)
971 WARN ((0, 0, _("WARNING: Archive is incomplete")));
972
973 fatal_exit ();
974
975 case 'n':
976 /* Get new file name. */
977
978 {
979 char *name;
980 char *cursor;
981
982 for (name = input_buffer + 1;
983 *name == ' ' || *name == '\t';
984 name++)
985 ;
986
987 for (cursor = name; *cursor && *cursor != '\n'; cursor++)
988 ;
989 *cursor = '\0';
990
991 if (name[0])
992 {
993 /* FIXME: the following allocation is never reclaimed. */
994 *archive_name_cursor = xstrdup (name);
995 stop = true;
996 }
997 else
998 fprintf (stderr, "%s",
999 _("File name not specified. Try again.\n"));
1000 }
1001 break;
1002
1003 case '!':
1004 if (!restrict_option)
1005 {
1006 sys_spawn_shell ();
1007 break;
1008 }
1009 /* FALL THROUGH */
1010
1011 default:
1012 fprintf (stderr, _("Invalid input. Type ? for help.\n"));
1013 }
1014 }
1015 free (input_buffer);
1016}
1017
1018/* We've hit the end of the old volume. Close it and open the next one.
1019 Return nonzero on success.
1020*/
1021static bool
1022new_volume (enum access_mode mode)
1023{
1024 static FILE *read_file;
1025 static int looped;
1026 int prompt;
1027
1028 if (!read_file && !info_script_option)
1029 /* FIXME: if fopen is used, it will never be closed. */
1030 read_file = archive == STDIN_FILENO ? fopen (TTY_NAME, "r") : stdin;
1031
1032 if (now_verifying)
1033 return false;
1034 if (verify_option)
1035 verify_volume ();
1036
1037 assign_string (&volume_label, NULL);
1038 assign_string (&continued_file_name, NULL);
1039 continued_file_size = continued_file_offset = 0;
1040 current_block = record_start;
1041
1042 if (rmtclose (archive) != 0)
1043 close_warn (*archive_name_cursor);
1044
1045 archive_name_cursor++;
1046 if (archive_name_cursor == archive_name_array + archive_names)
1047 {
1048 archive_name_cursor = archive_name_array;
1049 looped = 1;
1050 }
1051 prompt = looped;
1052
1053 tryagain:
1054 if (prompt)
1055 {
1056 /* We have to prompt from now on. */
1057
1058 if (info_script_option)
1059 {
1060 if (volno_file_option)
1061 closeout_volume_number ();
1062 if (sys_exec_info_script (archive_name_cursor, global_volno+1))
1063 FATAL_ERROR ((0, 0, _("%s command failed"),
1064 quote (info_script_option)));
1065 }
1066 else
1067 change_tape_menu (read_file);
1068 }
1069
1070 if (strcmp (archive_name_cursor[0], "-") == 0)
1071 {
1072 read_full_records = true;
1073 archive = STDIN_FILENO;
1074 }
1075 else if (verify_option)
1076 archive = rmtopen (*archive_name_cursor, O_RDWR | O_CREAT, MODE_RW,
1077 rsh_command_option);
1078 else
1079 switch (mode)
1080 {
1081 case ACCESS_READ:
1082 archive = rmtopen (*archive_name_cursor, O_RDONLY, MODE_RW,
1083 rsh_command_option);
1084 break;
1085
1086 case ACCESS_WRITE:
1087 if (backup_option)
1088 maybe_backup_file (*archive_name_cursor, 1);
1089 archive = rmtcreat (*archive_name_cursor, MODE_RW,
1090 rsh_command_option);
1091 break;
1092
1093 case ACCESS_UPDATE:
1094 archive = rmtopen (*archive_name_cursor, O_RDWR | O_CREAT, MODE_RW,
1095 rsh_command_option);
1096 break;
1097 }
1098
1099 if (archive < 0)
1100 {
1101 open_warn (*archive_name_cursor);
1102 if (!verify_option && mode == ACCESS_WRITE && backup_option)
1103 undo_last_backup ();
1104 prompt = 1;
1105 goto tryagain;
1106 }
1107
1108 SET_BINARY_MODE (archive);
1109
1110 return true;
1111}
1112
1113static bool
1114read_header0 (struct tar_stat_info *info)
1115{
1116 enum read_header rc;
1117
1118 tar_stat_init (info);
1119 rc = read_header_primitive (false, info);
1120 if (rc == HEADER_SUCCESS)
1121 {
1122 set_next_block_after (current_header);
1123 return true;
1124 }
1125 ERROR ((0, 0, _("This does not look like a tar archive")));
1126 return false;
1127}
1128
1129bool
1130try_new_volume ()
1131{
1132 size_t status;
1133 union block *header;
1134 struct tar_stat_info dummy;
1135 int access;
1136
1137 switch (subcommand_option)
1138 {
1139 case APPEND_SUBCOMMAND:
1140 case CAT_SUBCOMMAND:
1141 case UPDATE_SUBCOMMAND:
1142 access = ACCESS_UPDATE;
1143 break;
1144
1145 default:
1146 access = ACCESS_READ;
1147 break;
1148 }
1149
1150 if (!new_volume (access))
1151 return true;
1152
1153 while ((status = rmtread (archive, record_start->buffer, record_size))
1154 == SAFE_READ_ERROR)
1155 archive_read_error ();
1156
1157 if (status != record_size)
1158 short_read (status);
1159
1160 header = find_next_block ();
1161 if (!header)
1162 return false;
1163
1164 switch (header->header.typeflag)
1165 {
1166 case XGLTYPE:
1167 {
1168 if (!read_header0 (&dummy))
1169 return false;
1170 xheader_decode (&dummy); /* decodes values from the global header */
1171 tar_stat_destroy (&dummy);
1172 if (!real_s_name)
1173 {
1174 /* We have read the extended header of the first member in
1175 this volume. Put it back, so next read_header works as
1176 expected. */
1177 current_block = record_start;
1178 }
1179 break;
1180 }
1181
1182 case GNUTYPE_VOLHDR:
1183 if (!read_header0 (&dummy))
1184 return false;
1185 tar_stat_destroy (&dummy);
1186 assign_string (&volume_label, current_header->header.name);
1187 set_next_block_after (header);
1188 header = find_next_block ();
1189 if (header->header.typeflag != GNUTYPE_MULTIVOL)
1190 break;
1191 /* FALL THROUGH */
1192
1193 case GNUTYPE_MULTIVOL:
1194 if (!read_header0 (&dummy))
1195 return false;
1196 tar_stat_destroy (&dummy);
1197 assign_string (&continued_file_name, current_header->header.name);
1198 continued_file_size =
1199 UINTMAX_FROM_HEADER (current_header->header.size);
1200 continued_file_offset =
1201 UINTMAX_FROM_HEADER (current_header->oldgnu_header.offset);
1202 break;
1203
1204 default:
1205 break;
1206 }
1207
1208 if (real_s_name)
1209 {
1210 uintmax_t s;
1211 if (!continued_file_name
1212 || strcmp (continued_file_name, real_s_name))
1213 {
1214 if ((archive_format == GNU_FORMAT || archive_format == OLDGNU_FORMAT)
1215 && strlen (real_s_name) >= NAME_FIELD_SIZE
1216 && strncmp (continued_file_name, real_s_name,
1217 NAME_FIELD_SIZE) == 0)
1218 WARN ((0, 0,
1219 _("%s is possibly continued on this volume: header contains truncated name"),
1220 quote (real_s_name)));
1221 else
1222 {
1223 WARN ((0, 0, _("%s is not continued on this volume"),
1224 quote (real_s_name)));
1225 return false;
1226 }
1227 }
1228
1229 s = continued_file_size + continued_file_offset;
1230
1231 if (real_s_totsize != s || s < continued_file_offset)
1232 {
1233 char totsizebuf[UINTMAX_STRSIZE_BOUND];
1234 char s1buf[UINTMAX_STRSIZE_BOUND];
1235 char s2buf[UINTMAX_STRSIZE_BOUND];
1236
1237 WARN ((0, 0, _("%s is the wrong size (%s != %s + %s)"),
1238 quote (continued_file_name),
1239 STRINGIFY_BIGINT (save_totsize, totsizebuf),
1240 STRINGIFY_BIGINT (continued_file_size, s1buf),
1241 STRINGIFY_BIGINT (continued_file_offset, s2buf)));
1242 return false;
1243 }
1244
1245 if (real_s_totsize - real_s_sizeleft != continued_file_offset)
1246 {
1247 WARN ((0, 0, _("This volume is out of sequence")));
1248 return false;
1249 }
1250 }
1251
1252 increase_volume_number ();
1253 return true;
1254}
1255
1256
1257
1258/* Check the LABEL block against the volume label, seen as a globbing
1259 pattern. Return true if the pattern matches. In case of failure,
1260 retry matching a volume sequence number before giving up in
1261 multi-volume mode. */
1262static bool
1263check_label_pattern (union block *label)
1264{
1265 char *string;
1266 bool result;
1267
1268 if (! memchr (label->header.name, '\0', sizeof label->header.name))
1269 return false;
1270
1271 if (fnmatch (volume_label_option, label->header.name, 0) == 0)
1272 return true;
1273
1274 if (!multi_volume_option)
1275 return false;
1276
1277 string = xmalloc (strlen (volume_label_option)
1278 + sizeof VOLUME_LABEL_APPEND + 1);
1279 strcpy (string, volume_label_option);
1280 strcat (string, VOLUME_LABEL_APPEND);
1281 result = fnmatch (string, label->header.name, 0) == 0;
1282 free (string);
1283 return result;
1284}
1285
1286/* Check if the next block contains a volume label and if this matches
1287 the one given in the command line */
1288static void
1289match_volume_label (void)
1290{
1291 union block *label = find_next_block ();
1292
1293 if (!label)
1294 FATAL_ERROR ((0, 0, _("Archive not labeled to match %s"),
1295 quote (volume_label_option)));
1296 if (!check_label_pattern (label))
1297 FATAL_ERROR ((0, 0, _("Volume %s does not match %s"),
1298 quote_n (0, label->header.name),
1299 quote_n (1, volume_label_option)));
1300}
1301
1302/* Mark the archive with volume label STR. */
1303static void
1304_write_volume_label (const char *str)
1305{
1306 if (archive_format == POSIX_FORMAT)
1307 xheader_store ("GNU.volume.label", NULL, str);
1308 else
1309 {
1310 union block *label = find_next_block ();
1311
1312 memset (label, 0, BLOCKSIZE);
1313
1314 strcpy (label->header.name, volume_label_option);
1315 assign_string (&current_stat_info.file_name,
1316 label->header.name);
1317 current_stat_info.had_trailing_slash =
1318 strip_trailing_slashes (current_stat_info.file_name);
1319
1320 label->header.typeflag = GNUTYPE_VOLHDR;
1321 TIME_TO_CHARS (start_time.tv_sec, label->header.mtime);
1322 finish_header (&current_stat_info, label, -1);
1323 set_next_block_after (label);
1324 }
1325}
1326
1327#define VOL_SUFFIX "Volume"
1328
1329/* Add a volume label to a part of multi-volume archive */
1330static void
1331add_volume_label (void)
1332{
1333 char buf[UINTMAX_STRSIZE_BOUND];
1334 char *p = STRINGIFY_BIGINT (volno, buf);
1335 char *s = xmalloc (strlen (volume_label_option) + sizeof VOL_SUFFIX
1336 + strlen (p) + 2);
1337 sprintf (s, "%s %s %s", volume_label_option, VOL_SUFFIX, p);
1338 _write_volume_label (s);
1339 free (s);
1340}
1341
1342static void
1343add_chunk_header ()
1344{
1345 if (archive_format == POSIX_FORMAT)
1346 {
1347 off_t block_ordinal;
1348 union block *blk;
1349 struct tar_stat_info st;
1350 static size_t real_s_part_no; /* FIXME */
1351
1352 real_s_part_no++;
1353 memset (&st, 0, sizeof st);
1354 st.orig_file_name = st.file_name = real_s_name;
1355 st.stat.st_mode = S_IFREG|S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH;
1356 st.stat.st_uid = getuid ();
1357 st.stat.st_gid = getgid ();
1358 st.orig_file_name = xheader_format_name (&st,
1359 "%d/GNUFileParts.%p/%f.%n",
1360 real_s_part_no);
1361 st.file_name = st.orig_file_name;
1362 st.archive_file_size = st.stat.st_size = real_s_sizeleft;
1363
1364 block_ordinal = current_block_ordinal ();
1365 blk = start_header (&st);
1366 if (!blk)
1367 abort (); /* FIXME */
1368 finish_header (&st, blk, block_ordinal);
1369 free (st.orig_file_name);
1370 }
1371}
1372
1373
1374/* Add a volume label to the current archive */
1375static void
1376write_volume_label (void)
1377{
1378 if (multi_volume_option)
1379 add_volume_label ();
1380 else
1381 _write_volume_label (volume_label_option);
1382}
1383
1384/* Write GNU multi-volume header */
1385static void
1386gnu_add_multi_volume_header (void)
1387{
1388 int tmp;
1389 union block *block = find_next_block ();
1390
1391 if (strlen (real_s_name) > NAME_FIELD_SIZE)
1392 WARN ((0, 0,
1393 _("%s: file name too long to be stored in a GNU multivolume header, truncated"),
1394 quotearg_colon (real_s_name)));
1395
1396 memset (block, 0, BLOCKSIZE);
1397
1398 /* FIXME: Michael P Urban writes: [a long name file] is being written
1399 when a new volume rolls around [...] Looks like the wrong value is
1400 being preserved in real_s_name, though. */
1401
1402 strncpy (block->header.name, real_s_name, NAME_FIELD_SIZE);
1403 block->header.typeflag = GNUTYPE_MULTIVOL;
1404
1405 OFF_TO_CHARS (real_s_sizeleft, block->header.size);
1406 OFF_TO_CHARS (real_s_totsize - real_s_sizeleft,
1407 block->oldgnu_header.offset);
1408
1409 tmp = verbose_option;
1410 verbose_option = 0;
1411 finish_header (&current_stat_info, block, -1);
1412 verbose_option = tmp;
1413 set_next_block_after (block);
1414}
1415
1416/* Add a multi volume header to the current archive. The exact header format
1417 depends on the archive format. */
1418static void
1419add_multi_volume_header (void)
1420{
1421 if (archive_format == POSIX_FORMAT)
1422 {
1423 off_t d = real_s_totsize - real_s_sizeleft;
1424 xheader_store ("GNU.volume.filename", NULL, real_s_name);
1425 xheader_store ("GNU.volume.size", NULL, &real_s_sizeleft);
1426 xheader_store ("GNU.volume.offset", NULL, &d);
1427 }
1428 else
1429 gnu_add_multi_volume_header ();
1430}
1431
1432/* Synchronize multi-volume globals */
1433static void
1434multi_volume_sync ()
1435{
1436 if (multi_volume_option)
1437 {
1438 if (save_name)
1439 {
1440 assign_string (&real_s_name,
1441 safer_name_suffix (save_name, false,
1442 absolute_names_option));
1443 real_s_totsize = save_totsize;
1444 real_s_sizeleft = save_sizeleft;
1445 }
1446 else
1447 {
1448 assign_string (&real_s_name, 0);
1449 real_s_totsize = 0;
1450 real_s_sizeleft = 0;
1451 }
1452 }
1453}
1454
1455
1456
1457/* Low-level flush functions */
1458
1459/* Simple flush read (no multi-volume or label extensions) */
1460static void
1461simple_flush_read (void)
1462{
1463 size_t status; /* result from system call */
1464
1465 do_checkpoint (false);
1466
1467 /* Clear the count of errors. This only applies to a single call to
1468 flush_read. */
1469
1470 read_error_count = 0; /* clear error count */
1471
1472 if (write_archive_to_stdout && record_start_block != 0)
1473 {
1474 archive = STDOUT_FILENO;
1475 status = sys_write_archive_buffer ();
1476 archive = STDIN_FILENO;
1477 if (status != record_size)
1478 archive_write_error (status);
1479 }
1480
1481 for (;;)
1482 {
1483 status = rmtread (archive, record_start->buffer, record_size);
1484 if (status == record_size)
1485 {
1486 records_read++;
1487 return;
1488 }
1489 if (status == SAFE_READ_ERROR)
1490 {
1491 archive_read_error ();
1492 continue; /* try again */
1493 }
1494 break;
1495 }
1496 short_read (status);
1497}
1498
1499/* Simple flush write (no multi-volume or label extensions) */
1500static void
1501simple_flush_write (size_t level __attribute__((unused)))
1502{
1503 ssize_t status;
1504
1505 status = _flush_write ();
1506 if (status != record_size)
1507 archive_write_error (status);
1508 else
1509 {
1510 records_written++;
1511 bytes_written += status;
1512 }
1513}
1514
1515
1516
1517/* GNU flush functions. These support multi-volume and archive labels in
1518 GNU and PAX archive formats. */
1519
1520static void
1521_gnu_flush_read (void)
1522{
1523 size_t status; /* result from system call */
1524
1525 do_checkpoint (false);
1526
1527 /* Clear the count of errors. This only applies to a single call to
1528 flush_read. */
1529
1530 read_error_count = 0; /* clear error count */
1531
1532 if (write_archive_to_stdout && record_start_block != 0)
1533 {
1534 archive = STDOUT_FILENO;
1535 status = sys_write_archive_buffer ();
1536 archive = STDIN_FILENO;
1537 if (status != record_size)
1538 archive_write_error (status);
1539 }
1540
1541 multi_volume_sync ();
1542
1543 for (;;)
1544 {
1545 status = rmtread (archive, record_start->buffer, record_size);
1546 if (status == record_size)
1547 {
1548 records_read++;
1549 return;
1550 }
1551
1552 /* The condition below used to include
1553 || (status > 0 && !read_full_records)
1554 This is incorrect since even if new_volume() succeeds, the
1555 subsequent call to rmtread will overwrite the chunk of data
1556 already read in the buffer, so the processing will fail */
1557 if ((status == 0
1558 || (status == SAFE_READ_ERROR && errno == ENOSPC))
1559 && multi_volume_option)
1560 {
1561 while (!try_new_volume ())
1562 ;
1563 return;
1564 }
1565 else if (status == SAFE_READ_ERROR)
1566 {
1567 archive_read_error ();
1568 continue;
1569 }
1570 break;
1571 }
1572 short_read (status);
1573}
1574
1575static void
1576gnu_flush_read (void)
1577{
1578 flush_read_ptr = simple_flush_read; /* Avoid recursion */
1579 _gnu_flush_read ();
1580 flush_read_ptr = gnu_flush_read;
1581}
1582
1583static void
1584_gnu_flush_write (size_t buffer_level)
1585{
1586 ssize_t status;
1587 union block *header;
1588 char *copy_ptr;
1589 size_t copy_size;
1590 size_t bufsize;
1591
1592 status = _flush_write ();
1593 if (status != record_size && !multi_volume_option)
1594 archive_write_error (status);
1595 else
1596 {
1597 records_written++;
1598 bytes_written += status;
1599 }
1600
1601 if (status == record_size)
1602 {
1603 multi_volume_sync ();
1604 return;
1605 }
1606
1607 /* In multi-volume mode. */
1608 /* ENXIO is for the UNIX PC. */
1609 if (status < 0 && errno != ENOSPC && errno != EIO && errno != ENXIO)
1610 archive_write_error (status);
1611
1612 if (!new_volume (ACCESS_WRITE))
1613 return;
1614
1615 xheader_destroy (&extended_header);
1616
1617 increase_volume_number ();
1618 prev_written += bytes_written;
1619 bytes_written = 0;
1620
1621 copy_ptr = record_start->buffer + status;
1622 copy_size = buffer_level - status;
1623 /* Switch to the next buffer */
1624 record_index = !record_index;
1625 init_buffer ();
1626
1627 if (volume_label_option)
1628 add_volume_label ();
1629
1630 if (real_s_name)
1631 add_multi_volume_header ();
1632
1633 write_extended (true, NULL, find_next_block ());
1634 if (real_s_name)
1635 add_chunk_header ();
1636 header = find_next_block ();
1637 bufsize = available_space_after (header);
1638 while (bufsize < copy_size)
1639 {
1640 memcpy (header->buffer, copy_ptr, bufsize);
1641 copy_ptr += bufsize;
1642 copy_size -= bufsize;
1643 set_next_block_after (header + (bufsize - 1) / BLOCKSIZE);
1644 header = find_next_block ();
1645 bufsize = available_space_after (header);
1646 }
1647 memcpy (header->buffer, copy_ptr, copy_size);
1648 memset (header->buffer + copy_size, 0, bufsize - copy_size);
1649 set_next_block_after (header + (copy_size - 1) / BLOCKSIZE);
1650 find_next_block ();
1651}
1652
1653static void
1654gnu_flush_write (size_t buffer_level)
1655{
1656 flush_write_ptr = simple_flush_write; /* Avoid recursion */
1657 _gnu_flush_write (buffer_level);
1658 flush_write_ptr = gnu_flush_write;
1659}
1660
1661void
1662flush_read ()
1663{
1664 flush_read_ptr ();
1665}
1666
1667void
1668flush_write ()
1669{
1670 flush_write_ptr (record_size);
1671}
1672
1673void
1674open_archive (enum access_mode wanted_access)
1675{
1676 flush_read_ptr = gnu_flush_read;
1677 flush_write_ptr = gnu_flush_write;
1678
1679 _open_archive (wanted_access);
1680 switch (wanted_access)
1681 {
1682 case ACCESS_READ:
1683 if (volume_label_option)
1684 match_volume_label ();
1685 break;
1686
1687 case ACCESS_WRITE:
1688 records_written = 0;
1689 if (volume_label_option)
1690 write_volume_label ();
1691 break;
1692
1693 default:
1694 break;
1695 }
1696 set_volume_start_time ();
1697}
Note: See TracBrowser for help on using the repository browser.