1 /* List a tar archive, with support routines for reading a tar archive.
2 Copyright 1988,92,93,94,96,97,98,1999 Free Software Foundation, Inc.
3 Written by John Gilmore, on 1985-08-26.
5 This program is free software; you can redistribute it and/or modify it
6 under the terms of the GNU General Public License as published by the
7 Free Software Foundation; either version 2, or (at your option) any later
10 This program is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
13 Public License for more details.
15 You should have received a copy of the GNU General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
19 /* Define to non-zero for forcing old ctime() instead of isotime(). */
29 #define max(a, b) ((a) < (b) ? (b) : (a))
31 union block
*current_header
; /* points to current archive header */
32 struct stat current_stat
; /* stat struct corresponding */
33 enum archive_format current_format
; /* recognized format */
35 static uintmax_t from_chars
PARAMS ((const char *, size_t, const char *,
36 uintmax_t, uintmax_t));
38 /* Table of base 64 digit values indexed by unsigned chars.
39 The value is 64 for unsigned chars that are not base 64 digits. */
40 static char base64_map
[1 + (unsigned char) -1];
46 memset (base64_map
, 64, sizeof base64_map
);
47 for (i
= 0; i
< 64; i
++)
48 base64_map
[(int) base_64_digits
[i
]] = i
;
51 /*-----------------------------------.
52 | Main loop for reading an archive. |
53 `-----------------------------------*/
56 read_and (void (*do_something
) ())
58 enum read_header status
= HEADER_STILL_UNREAD
;
59 enum read_header prev_status
;
63 open_archive (ACCESS_READ
);
68 status
= read_header ();
71 case HEADER_STILL_UNREAD
:
76 /* Valid header. We should decode next field (mode) first.
77 Ensure incoming names are null terminated. */
79 /* FIXME: This is a quick kludge before 1.12 goes out. */
81 = TIME_FROM_CHARS (current_header
->header
.mtime
);
83 if (!name_match (current_file_name
)
84 || current_stat
.st_mtime
< newer_mtime_option
85 || excluded_name (current_file_name
))
89 if (current_header
->header
.typeflag
== GNUTYPE_VOLHDR
90 || current_header
->header
.typeflag
== GNUTYPE_MULTIVOL
91 || current_header
->header
.typeflag
== GNUTYPE_NAMES
)
96 if (show_omitted_dirs_option
97 && current_header
->header
.typeflag
== DIRTYPE
)
98 WARN ((0, 0, _("Omitting %s"), current_file_name
));
100 /* Skip past it in the archive. */
102 save_typeflag
= current_header
->header
.typeflag
;
103 set_next_block_after (current_header
);
104 if (current_header
->oldgnu_header
.isextended
)
105 skip_extended_headers ();
107 /* Skip to the next header on the archive. */
109 if (save_typeflag
!= DIRTYPE
)
110 skip_file (current_stat
.st_size
);
117 case HEADER_ZERO_BLOCK
:
118 if (block_number_option
)
120 char buf
[UINTMAX_STRSIZE_BOUND
];
121 fprintf (stdlis
, _("block %s: ** Block of NULs **\n"),
122 STRINGIFY_BIGINT (current_block_ordinal (), buf
));
125 set_next_block_after (current_header
);
126 status
= prev_status
;
127 if (ignore_zeros_option
)
131 case HEADER_END_OF_FILE
:
132 if (block_number_option
)
134 char buf
[UINTMAX_STRSIZE_BOUND
];
135 fprintf (stdlis
, _("block %s: ** End of File **\n"),
136 STRINGIFY_BIGINT (current_block_ordinal (), buf
));
141 /* If the previous header was good, tell them that we are
142 skipping bad ones. */
143 set_next_block_after (current_header
);
146 case HEADER_STILL_UNREAD
:
147 WARN ((0, 0, _("Hmm, this doesn't look like a tar archive")));
150 case HEADER_ZERO_BLOCK
:
152 WARN ((0, 0, _("Skipping to next file header")));
155 case HEADER_END_OF_FILE
:
157 /* We are in the middle of a cascade of errors. */
165 apply_delayed_set_stat ();
167 names_notfound (); /* print names not found */
170 /*---------------------------------------------.
171 | Print a header block, based on tar options. |
172 `---------------------------------------------*/
177 /* Print the header block. */
181 if (verbose_option
> 1)
182 decode_header (current_header
, ¤t_stat
, ¤t_format
, 0);
186 if (incremental_option
&& current_header
->header
.typeflag
== GNUTYPE_DUMPDIR
)
189 size_t written
, check
;
190 union block
*data_block
;
192 set_next_block_after (current_header
);
193 if (multi_volume_option
)
195 assign_string (&save_name
, current_file_name
);
196 save_totsize
= current_stat
.st_size
;
198 for (size
= current_stat
.st_size
; size
> 0; size
-= written
)
200 if (multi_volume_option
)
201 save_sizeleft
= size
;
202 data_block
= find_next_block ();
205 ERROR ((0, 0, _("EOF in archive file")));
206 break; /* FIXME: What happens, then? */
208 written
= available_space_after (data_block
);
211 errno
= 0; /* FIXME: errno should be read-only */
212 check
= fwrite (data_block
->buffer
, sizeof (char), written
, stdlis
);
213 set_next_block_after ((union block
*)
214 (data_block
->buffer
+ written
- 1));
215 if (check
!= written
)
217 ERROR ((0, errno
, _("Only wrote %lu of %lu bytes to file %s"),
218 (unsigned long) check
,
219 (unsigned long) written
, current_file_name
));
220 skip_file (size
- written
);
224 if (multi_volume_option
)
225 assign_string (&save_name
, 0);
226 fputc ('\n', stdlis
);
232 /* Skip past the header in the archive, and past any extended headers. */
234 set_next_block_after (current_header
);
235 if (current_header
->oldgnu_header
.isextended
)
236 skip_extended_headers ();
238 if (multi_volume_option
)
239 assign_string (&save_name
, current_file_name
);
241 /* Skip to the next header on the archive. */
243 skip_file (current_stat
.st_size
);
245 if (multi_volume_option
)
246 assign_string (&save_name
, 0);
249 /*-----------------------------------------------------------------------.
250 | Read a block that's supposed to be a header block. Return its address |
251 | in "current_header", and if it is good, the file's size in |
252 | current_stat.st_size. |
254 | Return 1 for success, 0 if the checksum is bad, EOF on eof, 2 for a |
255 | block full of zeros (EOF marker). |
257 | You must always set_next_block_after(current_header) to skip past the |
258 | header which this routine reads. |
259 `-----------------------------------------------------------------------*/
261 /* The standard BSD tar sources create the checksum by adding up the
262 bytes in the header as type char. I think the type char was unsigned
263 on the PDP-11, but it's signed on the Next and Sun. It looks like the
264 sources to BSD tar were never changed to compute the checksum
265 correctly, so both the Sun and Next add the bytes of the header as
266 signed chars. This doesn't cause a problem until you get a file with
267 a name containing characters with the high bit set. So read_header
268 computes two checksums -- signed and unsigned. */
274 int unsigned_sum
; /* the POSIX one :-) */
275 int signed_sum
; /* the Sun one :-( */
277 uintmax_t parsed_sum
;
282 union block
*data_block
;
283 size_t size
, written
;
284 static char *next_long_name
, *next_long_link
;
288 header
= find_next_block ();
289 current_header
= header
;
291 return HEADER_END_OF_FILE
;
296 for (i
= sizeof *header
; i
-- != 0;)
298 unsigned_sum
+= (unsigned char) *p
;
299 signed_sum
+= signed_char (*p
++);
302 if (unsigned_sum
== 0)
303 return HEADER_ZERO_BLOCK
;
305 /* Adjust checksum to count the "chksum" field as blanks. */
307 for (i
= sizeof header
->header
.chksum
; i
-- != 0;)
309 unsigned_sum
-= (unsigned char) header
->header
.chksum
[i
];
310 signed_sum
-= signed_char (header
->header
.chksum
[i
]);
312 unsigned_sum
+= ' ' * sizeof header
->header
.chksum
;
313 signed_sum
+= ' ' * sizeof header
->header
.chksum
;
315 parsed_sum
= from_chars (header
->header
.chksum
,
316 sizeof header
->header
.chksum
, 0,
317 (uintmax_t) 0, (uintmax_t) TYPE_MAXIMUM (int));
318 if (parsed_sum
== (uintmax_t) -1)
319 return HEADER_FAILURE
;
321 recorded_sum
= parsed_sum
;
323 if (unsigned_sum
!= recorded_sum
&& signed_sum
!= recorded_sum
)
324 return HEADER_FAILURE
;
326 /* Good block. Decode file size and return. */
328 if (header
->header
.typeflag
== LNKTYPE
)
329 current_stat
.st_size
= 0; /* links 0 size on tape */
331 current_stat
.st_size
= OFF_FROM_CHARS (header
->header
.size
);
333 if (header
->header
.typeflag
== GNUTYPE_LONGNAME
334 || header
->header
.typeflag
== GNUTYPE_LONGLINK
)
336 longp
= ((header
->header
.typeflag
== GNUTYPE_LONGNAME
)
340 set_next_block_after (header
);
343 size
= current_stat
.st_size
;
344 if (size
!= current_stat
.st_size
)
345 FATAL_ERROR ((0, 0, _("Memory exhausted")));
346 bp
= *longp
= xmalloc (size
);
348 for (; size
> 0; size
-= written
)
350 data_block
= find_next_block ();
353 ERROR ((0, 0, _("Unexpected EOF on archive file")));
356 written
= available_space_after (data_block
);
360 memcpy (bp
, data_block
->buffer
, written
);
362 set_next_block_after ((union block
*)
363 (data_block
->buffer
+ written
- 1));
372 struct posix_header
*h
= ¤t_header
->header
;
373 char namebuf
[sizeof h
->prefix
+ 1 + NAME_FIELD_SIZE
+ 1];
375 name
= next_long_name
;
378 /* Accept file names as specified by POSIX.1-1996
380 int posix_header
= strcmp (h
->magic
, TMAGIC
) == 0;
383 if (posix_header
&& h
->prefix
[0])
385 memcpy (np
, h
->prefix
, sizeof h
->prefix
);
386 np
[sizeof h
->prefix
] = '\0';
390 memcpy (np
, h
->name
, sizeof h
->name
);
391 np
[sizeof h
->name
] = '\0';
394 assign_string (¤t_file_name
, name
);
397 free (next_long_name
);
401 name
= next_long_link
;
404 memcpy (namebuf
, h
->linkname
, sizeof h
->linkname
);
405 namebuf
[sizeof h
->linkname
] = '\0';
408 assign_string (¤t_link_name
, name
);
411 free (next_long_link
);
415 return HEADER_SUCCESS
;
420 /*-------------------------------------------------------------------------.
421 | Decode things from a file HEADER block into STAT_INFO, also setting |
422 | *FORMAT_POINTER depending on the header block format. If DO_USER_GROUP, |
423 | decode the user/group information (this is useful for extraction, but |
424 | waste time when merely listing). |
426 | read_header() has already decoded the checksum and length, so we don't. |
428 | This routine should *not* be called twice for the same block, since the |
429 | two calls might use different DO_USER_GROUP values and thus might end up |
430 | with different uid/gid for the two calls. If anybody wants the uid/gid |
431 | they should decode it first, and other callers should decode it without |
432 | uid/gid before calling a routine, e.g. print_header, that assumes |
434 `-------------------------------------------------------------------------*/
437 decode_header (union block
*header
, struct stat
*stat_info
,
438 enum archive_format
*format_pointer
, int do_user_group
)
440 enum archive_format format
;
442 if (strcmp (header
->header
.magic
, TMAGIC
) == 0)
443 format
= POSIX_FORMAT
;
444 else if (strcmp (header
->header
.magic
, OLDGNU_MAGIC
) == 0)
445 format
= OLDGNU_FORMAT
;
448 *format_pointer
= format
;
450 stat_info
->st_mode
= MODE_FROM_CHARS (header
->header
.mode
);
451 stat_info
->st_mtime
= TIME_FROM_CHARS (header
->header
.mtime
);
453 if (format
== OLDGNU_FORMAT
&& incremental_option
)
455 stat_info
->st_atime
= TIME_FROM_CHARS (header
->oldgnu_header
.atime
);
456 stat_info
->st_ctime
= TIME_FROM_CHARS (header
->oldgnu_header
.ctime
);
459 if (format
== V7_FORMAT
)
461 stat_info
->st_uid
= UID_FROM_CHARS (header
->header
.uid
);
462 stat_info
->st_gid
= GID_FROM_CHARS (header
->header
.gid
);
463 stat_info
->st_rdev
= 0;
469 /* FIXME: Decide if this should somewhat depend on -p. */
471 if (numeric_owner_option
472 || !*header
->header
.uname
473 || !uname_to_uid (header
->header
.uname
, &stat_info
->st_uid
))
474 stat_info
->st_uid
= UID_FROM_CHARS (header
->header
.uid
);
476 if (numeric_owner_option
477 || !*header
->header
.gname
478 || !gname_to_gid (header
->header
.gname
, &stat_info
->st_gid
))
479 stat_info
->st_gid
= GID_FROM_CHARS (header
->header
.gid
);
481 switch (header
->header
.typeflag
)
485 = makedev (MAJOR_FROM_CHARS (header
->header
.devmajor
),
486 MINOR_FROM_CHARS (header
->header
.devminor
));
491 = makedev (MAJOR_FROM_CHARS (header
->header
.devmajor
),
492 MINOR_FROM_CHARS (header
->header
.devminor
));
496 stat_info
->st_rdev
= 0;
501 /*------------------------------------------------------------------------.
502 | Convert buffer at WHERE0 of size DIGS from external format to uintmax_t.|
503 | The data is of type TYPE. The buffer must represent a value in the |
504 | range -MINUS_MINVAL through MAXVAL. |
505 `------------------------------------------------------------------------*/
508 from_chars (char const *where0
, size_t digs
, char const *type
,
509 uintmax_t minus_minval
, uintmax_t maxval
)
512 char const *where
= where0
;
513 char const *lim
= where
+ digs
;
516 /* Accommodate buggy tar of unknown vintage, which outputs leading
517 NUL if the previous field overflows. */
520 /* Accommodate older tars, which output leading spaces. */
527 _("Blanks in header where numeric %s value expected"),
531 if (!ISSPACE ((unsigned char) *where
))
537 if (ISODIGIT (*where
))
541 if (value
<< LG_8
>> LG_8
!= value
)
544 _("Archive octal string `%.*s' is out of %s range"),
545 (int) digs
, where0
, type
));
548 value
= (value
<< LG_8
) | (*where
++ - '0');
550 while (where
!= lim
&& ISODIGIT (*where
));
552 /* Parse the output of older tars, which output negative values
553 in two's complement octal. This method works only if the
554 type has the same number of bits as it did on the host that
555 created the tar file, but that's the best we can do. */
556 if (maxval
< value
&& value
- maxval
<= minus_minval
)
558 value
= minus_minval
- (value
- maxval
);
562 else if (*where
== '-' || *where
== '+')
565 negative
= *where
++ == '-';
567 && (dig
= base64_map
[(unsigned char) *where
]) < 64)
569 if (value
<< LG_64
>> LG_64
!= value
)
572 _("Archive signed base 64 string `%.*s' is out of %s range"),
573 (int) digs
, where0
, type
));
576 value
= (value
<< LG_64
) | dig
;
581 if (where
!= lim
&& *where
&& !ISSPACE ((unsigned char) *where
))
585 char buf
[1000]; /* Big enough to represent any header. */
586 static struct quoting_options
*o
;
590 o
= clone_quoting_options (0);
591 set_quoting_style (o
, c_quoting_style
);
594 while (where0
!= lim
&& ! lim
[-1])
596 quotearg_buffer (buf
, sizeof buf
, where0
, lim
- where
, o
);
598 _("Archive contains `%.*s' where numeric %s value expected"),
599 (int) sizeof buf
, buf
, type
));
605 if (value
<= (negative
? minus_minval
: maxval
))
606 return negative
? -value
: value
;
610 char minval_buf
[UINTMAX_STRSIZE_BOUND
+ 1];
611 char maxval_buf
[UINTMAX_STRSIZE_BOUND
];
612 char value_buf
[UINTMAX_STRSIZE_BOUND
+ 1];
613 char *minval_string
= STRINGIFY_BIGINT (minus_minval
, minval_buf
+ 1);
614 char *value_string
= STRINGIFY_BIGINT (value
, value_buf
+ 1);
616 *--value_string
= '-';
618 *--minval_string
= '-';
619 ERROR ((0, 0, _("Archive value %s is out of %s range %s..%s"),
621 minval_string
, STRINGIFY_BIGINT (maxval
, maxval_buf
)));
628 gid_from_chars (const char *p
, size_t s
)
630 return from_chars (p
, s
, "gid_t",
631 - (uintmax_t) TYPE_MINIMUM (gid_t
),
632 (uintmax_t) TYPE_MAXIMUM (gid_t
));
636 major_from_chars (const char *p
, size_t s
)
638 return from_chars (p
, s
, "major_t",
639 - (uintmax_t) TYPE_MINIMUM (major_t
),
640 (uintmax_t) TYPE_MAXIMUM (major_t
));
644 minor_from_chars (const char *p
, size_t s
)
646 return from_chars (p
, s
, "minor_t",
647 - (uintmax_t) TYPE_MINIMUM (minor_t
),
648 (uintmax_t) TYPE_MAXIMUM (minor_t
));
652 mode_from_chars (const char *p
, size_t s
)
654 /* Do not complain about unrecognized mode bits. */
655 unsigned u
= from_chars (p
, s
, "mode_t",
656 - (uintmax_t) TYPE_MINIMUM (mode_t
),
657 TYPE_MAXIMUM (uintmax_t));
658 return ((u
& TSUID
? S_ISUID
: 0)
659 | (u
& TSGID
? S_ISGID
: 0)
660 | (u
& TSVTX
? S_ISVTX
: 0)
661 | (u
& TUREAD
? S_IRUSR
: 0)
662 | (u
& TUWRITE
? S_IWUSR
: 0)
663 | (u
& TUEXEC
? S_IXUSR
: 0)
664 | (u
& TGREAD
? S_IRGRP
: 0)
665 | (u
& TGWRITE
? S_IWGRP
: 0)
666 | (u
& TGEXEC
? S_IXGRP
: 0)
667 | (u
& TOREAD
? S_IROTH
: 0)
668 | (u
& TOWRITE
? S_IWOTH
: 0)
669 | (u
& TOEXEC
? S_IXOTH
: 0));
673 off_from_chars (const char *p
, size_t s
)
675 /* Negative offsets are not allowed in tar files, so invoke
676 from_chars with minimum value 0, not TYPE_MINIMUM (off_t). */
677 return from_chars (p
, s
, "off_t", (uintmax_t) 0,
678 (uintmax_t) TYPE_MAXIMUM (off_t
));
682 size_from_chars (const char *p
, size_t s
)
684 return from_chars (p
, s
, "size_t", (uintmax_t) 0,
685 (uintmax_t) TYPE_MAXIMUM (size_t));
689 time_from_chars (const char *p
, size_t s
)
691 return from_chars (p
, s
, "time_t",
692 - (uintmax_t) TYPE_MINIMUM (time_t),
693 (uintmax_t) TYPE_MAXIMUM (time_t));
697 uid_from_chars (const char *p
, size_t s
)
699 return from_chars (p
, s
, "uid_t",
700 - (uintmax_t) TYPE_MINIMUM (uid_t
),
701 (uintmax_t) TYPE_MAXIMUM (uid_t
));
705 uintmax_from_chars (const char *p
, size_t s
)
707 return from_chars (p
, s
, "uintmax_t", (uintmax_t) 0,
708 TYPE_MAXIMUM (uintmax_t));
712 /*----------------------------------------------------------------------.
713 | Format O as a null-terminated decimal string into BUF _backwards_; |
714 | return pointer to start of result. |
715 `----------------------------------------------------------------------*/
717 stringify_uintmax_t_backwards (uintmax_t o
, char *buf
)
721 *--buf
= '0' + (int) (o
% 10);
722 while ((o
/= 10) != 0);
728 /*-------------------------------------------.
729 | Return the time formatted along ISO 8601. |
730 `-------------------------------------------*/
732 /* Also, see http://www.ft.uni-erlangen.de/~mskuhn/iso-time.html. */
735 isotime (time_t time
)
737 static char buffer
[max (UINTMAX_STRSIZE_BOUND
+ 1,
738 INT_STRLEN_BOUND (int) + 16)];
739 struct tm
*tm
= localtime (&time
);
742 sprintf (buffer
, "%04d-%02d-%02d %02d:%02d:%02d",
743 tm
->tm_year
+ 1900, tm
->tm_mon
+ 1, tm
->tm_mday
,
744 tm
->tm_hour
, tm
->tm_min
, tm
->tm_sec
);
749 /* The time stamp cannot be broken down, most likely because it
750 is out of range. Convert it as an integer,
751 right-adjusted in a field with the same width as the usual
752 19-byte 4-year ISO time format. */
753 uintmax_t abstime
= time
< 0 ? - (uintmax_t) time
: time
;
754 char *p
= stringify_uintmax_t_backwards (abstime
,
755 buffer
+ sizeof buffer
);
758 while (buffer
+ sizeof buffer
- 19 - 1 < p
)
764 #endif /* not USE_OLD_CTIME */
766 /*-------------------------------------------------------------------------.
767 | Decode MODE from its binary form in a stat structure, and encode it into |
768 | a 9 characters string STRING, terminated with a NUL. |
769 `-------------------------------------------------------------------------*/
772 decode_mode (mode_t mode
, char *string
)
774 *string
++ = mode
& S_IRUSR
? 'r' : '-';
775 *string
++ = mode
& S_IWUSR
? 'w' : '-';
776 *string
++ = (mode
& S_ISUID
777 ? (mode
& S_IXUSR
? 's' : 'S')
778 : (mode
& S_IXUSR
? 'x' : '-'));
779 *string
++ = mode
& S_IRGRP
? 'r' : '-';
780 *string
++ = mode
& S_IWGRP
? 'w' : '-';
781 *string
++ = (mode
& S_ISGID
782 ? (mode
& S_IXGRP
? 's' : 'S')
783 : (mode
& S_IXGRP
? 'x' : '-'));
784 *string
++ = mode
& S_IROTH
? 'r' : '-';
785 *string
++ = mode
& S_IWOTH
? 'w' : '-';
786 *string
++ = (mode
& S_ISVTX
787 ? (mode
& S_IXOTH
? 't' : 'T')
788 : (mode
& S_IXOTH
? 'x' : '-'));
792 /*-------------------------------------------------------------------------.
793 | Actually print it. |
795 | Plain and fancy file header block logging. Non-verbose just prints the |
796 | name, e.g. for "tar t" or "tar x". This should just contain file names, |
797 | so it can be fed back into tar with xargs or the "-T" option. The |
798 | verbose option can give a bunch of info, one line per file. I doubt |
799 | anybody tries to parse its format, or if they do, they shouldn't. Unix |
800 | tar is pretty random here anyway. |
801 `-------------------------------------------------------------------------*/
803 /* FIXME: Note that print_header uses the globals HEAD, HSTAT, and
804 HEAD_STANDARD, which must be set up in advance. Not very clean... */
806 /* UGSWIDTH starts with 18, so with user and group names <= 8 chars, the
807 columns never shift during the listing. */
809 static int ugswidth
= UGSWIDTH
; /* maximum width encountered so far */
811 /* DATEWIDTH is the number of columns taken by the date and time fields. */
813 # define DATEWIDTH 19
815 # define DATEWIDTH 18
822 char const *time_stamp
;
823 /* These hold formatted ints. */
824 char uform
[UINTMAX_STRSIZE_BOUND
], gform
[UINTMAX_STRSIZE_BOUND
];
826 char size
[2 * UINTMAX_STRSIZE_BOUND
];
827 /* holds formatted size or major,minor */
828 char uintbuf
[UINTMAX_STRSIZE_BOUND
];
829 time_t longie
; /* to make ctime() call portable */
833 if (block_number_option
)
835 char buf
[UINTMAX_STRSIZE_BOUND
];
836 fprintf (stdlis
, _("block %s: "),
837 STRINGIFY_BIGINT (current_block_ordinal (), buf
));
840 if (verbose_option
<= 1)
842 /* Just the fax, mam. */
844 char *quoted_name
= quote_copy_string (current_file_name
);
848 fprintf (stdlis
, "%s\n", quoted_name
);
852 fprintf (stdlis
, "%s\n", current_file_name
);
856 /* File type and modes. */
859 switch (current_header
->header
.typeflag
)
865 case GNUTYPE_MULTIVOL
:
873 case GNUTYPE_LONGNAME
:
874 case GNUTYPE_LONGLINK
:
875 ERROR ((0, 0, _("Visible longname error")));
883 if (current_file_name
[strlen (current_file_name
) - 1] == '/')
886 case GNUTYPE_DUMPDIR
:
909 decode_mode (current_stat
.st_mode
, modes
+ 1);
913 longie
= current_stat
.st_mtime
;
916 char *ct
= ctime (&longie
);
920 for (ct
+= 16; ct
[4] != '\n'; ct
++)
925 time_stamp
= "??? ?? ??:?? ????";
928 time_stamp
= isotime (longie
);
931 /* User and group names. */
933 if (*current_header
->header
.uname
&& current_format
!= V7_FORMAT
934 && !numeric_owner_option
)
935 user
= current_header
->header
.uname
;
937 user
= STRINGIFY_BIGINT (UINTMAX_FROM_CHARS
938 (current_header
->header
.uid
),
941 if (*current_header
->header
.gname
&& current_format
!= V7_FORMAT
942 && !numeric_owner_option
)
943 group
= current_header
->header
.gname
;
945 group
= STRINGIFY_BIGINT (UINTMAX_FROM_CHARS
946 (current_header
->header
.gid
),
949 /* Format the file size or major/minor device numbers. */
951 switch (current_header
->header
.typeflag
)
956 STRINGIFY_BIGINT (major (current_stat
.st_rdev
), uintbuf
));
959 STRINGIFY_BIGINT (minor (current_stat
.st_rdev
), uintbuf
));
964 (UINTMAX_FROM_CHARS (current_header
->oldgnu_header
.realsize
),
968 strcpy (size
, STRINGIFY_BIGINT (current_stat
.st_size
, uintbuf
));
972 /* Figure out padding and print the whole line. */
974 pad
= strlen (user
) + strlen (group
) + strlen (size
) + 1;
978 fprintf (stdlis
, "%s %s/%s %*s%s %s",
979 modes
, user
, group
, ugswidth
- pad
, "", size
, time_stamp
);
981 name
= quote_copy_string (current_file_name
);
984 fprintf (stdlis
, " %s", name
);
988 fprintf (stdlis
, " %s", current_file_name
);
990 switch (current_header
->header
.typeflag
)
993 name
= quote_copy_string (current_link_name
);
996 fprintf (stdlis
, " -> %s\n", name
);
1000 fprintf (stdlis
, " -> %s\n", current_link_name
);
1004 name
= quote_copy_string (current_link_name
);
1007 fprintf (stdlis
, _(" link to %s\n"), name
);
1011 fprintf (stdlis
, _(" link to %s\n"), current_link_name
);
1015 fprintf (stdlis
, _(" unknown file type `%c'\n"),
1016 current_header
->header
.typeflag
);
1021 case GNUTYPE_SPARSE
:
1027 case GNUTYPE_DUMPDIR
:
1028 putc ('\n', stdlis
);
1031 case GNUTYPE_VOLHDR
:
1032 fprintf (stdlis
, _("--Volume Header--\n"));
1035 case GNUTYPE_MULTIVOL
:
1038 (UINTMAX_FROM_CHARS (current_header
->oldgnu_header
.offset
),
1040 fprintf (stdlis
, _("--Continued at byte %s--\n"), size
);
1044 fprintf (stdlis
, _("--Mangled file names--\n"));
1051 /*--------------------------------------------------------------.
1052 | Print a similar line when we make a directory automatically. |
1053 `--------------------------------------------------------------*/
1056 print_for_mkdir (char *pathname
, int length
, mode_t mode
)
1061 if (verbose_option
> 1)
1063 /* File type and modes. */
1066 decode_mode (mode
, modes
+ 1);
1068 if (block_number_option
)
1070 char buf
[UINTMAX_STRSIZE_BOUND
];
1071 fprintf (stdlis
, _("block %s: "),
1072 STRINGIFY_BIGINT (current_block_ordinal (), buf
));
1074 name
= quote_copy_string (pathname
);
1077 fprintf (stdlis
, "%s %*s %.*s\n", modes
, ugswidth
+ DATEWIDTH
,
1078 _("Creating directory:"), length
, name
);
1082 fprintf (stdlis
, "%s %*s %.*s\n", modes
, ugswidth
+ DATEWIDTH
,
1083 _("Creating directory:"), length
, pathname
);
1087 /*--------------------------------------------------------.
1088 | Skip over SIZE bytes of data in blocks in the archive. |
1089 `--------------------------------------------------------*/
1092 skip_file (off_t size
)
1096 if (multi_volume_option
)
1098 save_totsize
= size
;
1099 save_sizeleft
= size
;
1104 x
= find_next_block ();
1106 FATAL_ERROR ((0, 0, _("Unexpected EOF on archive file")));
1108 set_next_block_after (x
);
1110 if (multi_volume_option
)
1111 save_sizeleft
-= BLOCKSIZE
;
1120 skip_extended_headers (void)
1126 exhdr
= find_next_block ();
1128 FATAL_ERROR ((0, 0, _("Unexpected EOF on archive file")));
1129 set_next_block_after (exhdr
);
1131 while (exhdr
->sparse_header
.isextended
);