1 /* A tar (tape archiver) program.
3 Copyright (C) 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1999, 2000,
4 2001, 2003, 2004, 2005, 2006, 2007, 2009 Free Software Foundation, Inc.
6 Written by John Gilmore, starting 1985-08-25.
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 3, or (at your option) any later
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.
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. */
26 #include <argp-namefrob.h>
27 #include <argp-fmtstream.h>
28 #include <argp-version-etc.h>
31 #if ! defined SIGCHLD && defined SIGCLD
32 # define SIGCHLD SIGCLD
35 /* The following causes "common.h" to produce definitions of all the global
36 variables, rather than just "extern" declarations of them. GNU tar does
37 depend on the system loader to preset all GLOBAL variables to neutral (or
38 zero) values; explicit initialization is usually not done. */
44 #include <configmake.h>
48 #include <rmt-command.h>
51 #include <version-etc.h>
56 /* Local declarations. */
58 #ifndef DEFAULT_ARCHIVE_FORMAT
59 # define DEFAULT_ARCHIVE_FORMAT GNU_FORMAT
62 #ifndef DEFAULT_ARCHIVE
63 # define DEFAULT_ARCHIVE "tar.out"
66 #ifndef DEFAULT_BLOCKING
67 # define DEFAULT_BLOCKING 20
73 /* Name of option using stdin. */
74 static const char *stdin_used_by
;
76 /* Doesn't return if stdin already requested. */
78 request_stdin (const char *option
)
81 USAGE_ERROR ((0, 0, _("Options `-%s' and `-%s' both want standard input"),
82 stdin_used_by
, option
));
84 stdin_used_by
= option
;
87 extern int rpmatch (char const *response
);
89 /* Returns true if and only if the user typed an affirmative response. */
91 confirm (const char *message_action
, const char *message_name
)
93 static FILE *confirm_file
;
94 static int confirm_file_EOF
;
99 if (archive
== 0 || stdin_used_by
)
101 confirm_file
= fopen (TTY_NAME
, "r");
103 open_fatal (TTY_NAME
);
107 request_stdin ("-w");
108 confirm_file
= stdin
;
112 fprintf (stdlis
, "%s %s?", message_action
, quote (message_name
));
115 if (!confirm_file_EOF
)
117 char *response
= NULL
;
118 size_t response_size
= 0;
119 if (getline (&response
, &response_size
, confirm_file
) < 0)
120 confirm_file_EOF
= 1;
122 status
= rpmatch (response
) > 0;
126 if (confirm_file_EOF
)
128 fputc ('\n', stdlis
);
135 static struct fmttab
{
137 enum archive_format fmt
;
140 { "oldgnu", OLDGNU_FORMAT
},
141 { "ustar", USTAR_FORMAT
},
142 { "posix", POSIX_FORMAT
},
143 #if 0 /* not fully supported yet */
144 { "star", STAR_FORMAT
},
146 { "gnu", GNU_FORMAT
},
147 { "pax", POSIX_FORMAT
}, /* An alias for posix */
152 set_archive_format (char const *name
)
154 struct fmttab
const *p
;
156 for (p
= fmttab
; strcmp (p
->name
, name
) != 0; )
158 USAGE_ERROR ((0, 0, _("%s: Invalid archive format"),
159 quotearg_colon (name
)));
161 archive_format
= p
->fmt
;
165 archive_format_string (enum archive_format fmt
)
167 struct fmttab
const *p
;
169 for (p
= fmttab
; p
->name
; p
++)
175 #define FORMAT_MASK(n) (1<<(n))
178 assert_format(unsigned fmt_mask
)
180 if ((FORMAT_MASK (archive_format
) & fmt_mask
) == 0)
182 _("GNU features wanted on incompatible archive format")));
186 subcommand_string (enum subcommand c
)
190 case UNKNOWN_SUBCOMMAND
:
193 case APPEND_SUBCOMMAND
:
199 case CREATE_SUBCOMMAND
:
202 case DELETE_SUBCOMMAND
:
205 case DIFF_SUBCOMMAND
:
208 case EXTRACT_SUBCOMMAND
:
211 case LIST_SUBCOMMAND
:
214 case UPDATE_SUBCOMMAND
:
217 case TEST_LABEL_SUBCOMMAND
:
218 return "--test-label";
224 tar_list_quoting_styles (struct obstack
*stk
, char const *prefix
)
227 size_t prefixlen
= strlen (prefix
);
229 for (i
= 0; quoting_style_args
[i
]; i
++)
231 obstack_grow (stk
, prefix
, prefixlen
);
232 obstack_grow (stk
, quoting_style_args
[i
],
233 strlen (quoting_style_args
[i
]));
234 obstack_1grow (stk
, '\n');
239 tar_set_quoting_style (char *arg
)
243 for (i
= 0; quoting_style_args
[i
]; i
++)
244 if (strcmp (arg
, quoting_style_args
[i
]) == 0)
246 set_quoting_style (NULL
, i
);
250 _("Unknown quoting style `%s'. Try `%s --quoting-style=help' to get a list."), arg
, program_invocation_short_name
));
258 ANCHORED_OPTION
= CHAR_MAX
+ 1,
259 ATIME_PRESERVE_OPTION
,
263 CHECKPOINT_ACTION_OPTION
,
264 DELAY_DIRECTORY_RESTORE_OPTION
,
265 HARD_DEREFERENCE_OPTION
,
267 EXCLUDE_BACKUPS_OPTION
,
268 EXCLUDE_CACHES_OPTION
,
269 EXCLUDE_CACHES_UNDER_OPTION
,
270 EXCLUDE_CACHES_ALL_OPTION
,
273 EXCLUDE_TAG_UNDER_OPTION
,
274 EXCLUDE_TAG_ALL_OPTION
,
280 IGNORE_COMMAND_ERROR_OPTION
,
281 IGNORE_FAILED_READ_OPTION
,
283 KEEP_NEWER_FILES_OPTION
,
292 NO_AUTO_COMPRESS_OPTION
,
293 NO_CHECK_DEVICE_OPTION
,
294 NO_DELAY_DIRECTORY_RESTORE_OPTION
,
295 NO_IGNORE_CASE_OPTION
,
296 NO_IGNORE_COMMAND_ERROR_OPTION
,
298 NO_OVERWRITE_DIR_OPTION
,
299 NO_QUOTE_CHARS_OPTION
,
301 NO_SAME_OWNER_OPTION
,
302 NO_SAME_PERMISSIONS_OPTION
,
305 NO_WILDCARDS_MATCH_SLASH_OPTION
,
308 NUMERIC_OWNER_OPTION
,
311 ONE_FILE_SYSTEM_OPTION
,
312 OVERWRITE_DIR_OPTION
,
319 QUOTING_STYLE_OPTION
,
322 RECURSIVE_UNLINK_OPTION
,
328 SHOW_DEFAULTS_OPTION
,
329 SHOW_OMITTED_DIRS_OPTION
,
330 SHOW_TRANSFORMED_NAMES_OPTION
,
331 SPARSE_VERSION_OPTION
,
332 STRIP_COMPONENTS_OPTION
,
342 WILDCARDS_MATCH_SLASH_OPTION
,
346 const char *argp_program_version
= "tar (" PACKAGE_NAME
") " VERSION
;
347 const char *argp_program_bug_address
= "<" PACKAGE_BUGREPORT
">";
348 static char const doc
[] = N_("\
349 GNU `tar' saves many files together into a single tape or disk archive, \
350 and can restore individual files from the archive.\n\
353 tar -cf archive.tar foo bar # Create archive.tar from files foo and bar.\n\
354 tar -tvf archive.tar # List all files in archive.tar verbosely.\n\
355 tar -xf archive.tar # Extract all files from archive.tar.\n")
357 N_("The backup suffix is `~', unless set with --suffix or SIMPLE_BACKUP_SUFFIX.\n\
358 The version control may be set with --backup or VERSION_CONTROL, values are:\n\n\
359 none, off never make backups\n\
360 t, numbered make numbered backups\n\
361 nil, existing numbered if numbered backups exist, simple otherwise\n\
362 never, simple always make simple backups\n");
367 Available option letters are DEQY and eqy. Consider the following
370 [For Solaris tar compatibility =/= Is it important at all?]
371 e exit immediately with a nonzero exit status if unexpected errors occur
372 E use extended headers (--format=posix)
374 [q alias for --occurrence=1 =/= this would better be used for quiet?]
376 y per-file gzip compression
377 Y per-block gzip compression.
379 Additionally, the 'n' letter is assigned for option --seek, which
380 is probably not needed and should be marked as deprecated, so that
381 -n may become available in the future.
384 static struct argp_option options
[] = {
387 N_("Main operation mode:"), GRID
},
390 N_("list the contents of an archive"), GRID
+1 },
391 {"extract", 'x', 0, 0,
392 N_("extract files from an archive"), GRID
+1 },
393 {"get", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
394 {"create", 'c', 0, 0,
395 N_("create a new archive"), GRID
+1 },
397 N_("find differences between archive and file system"), GRID
+1 },
398 {"compare", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
399 {"append", 'r', 0, 0,
400 N_("append files to the end of an archive"), GRID
+1 },
401 {"update", 'u', 0, 0,
402 N_("only append files newer than copy in archive"), GRID
+1 },
403 {"catenate", 'A', 0, 0,
404 N_("append tar files to an archive"), GRID
+1 },
405 {"concatenate", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
406 {"delete", DELETE_OPTION
, 0, 0,
407 N_("delete from the archive (not on mag tapes!)"), GRID
+1 },
408 {"test-label", TEST_LABEL_OPTION
, NULL
, 0,
409 N_("test the archive volume label and exit"), GRID
+1 },
414 N_("Operation modifiers:"), GRID
},
416 {"sparse", 'S', 0, 0,
417 N_("handle sparse files efficiently"), GRID
+1 },
418 {"sparse-version", SPARSE_VERSION_OPTION
, N_("MAJOR[.MINOR]"), 0,
419 N_("set version of the sparse format to use (implies --sparse)"), GRID
+1},
420 {"incremental", 'G', 0, 0,
421 N_("handle old GNU-format incremental backup"), GRID
+1 },
422 {"listed-incremental", 'g', N_("FILE"), 0,
423 N_("handle new GNU-format incremental backup"), GRID
+1 },
424 {"level", LEVEL_OPTION
, N_("NUMBER"), 0,
425 N_("dump level for created listed-incremental archive"), GRID
+1 },
426 {"ignore-failed-read", IGNORE_FAILED_READ_OPTION
, 0, 0,
427 N_("do not exit with nonzero on unreadable files"), GRID
+1 },
428 {"occurrence", OCCURRENCE_OPTION
, N_("NUMBER"), OPTION_ARG_OPTIONAL
,
429 N_("process only the NUMBERth occurrence of each file in the archive;"
430 " this option is valid only in conjunction with one of the subcommands"
431 " --delete, --diff, --extract or --list and when a list of files"
432 " is given either on the command line or via the -T option;"
433 " NUMBER defaults to 1"), GRID
+1 },
434 {"seek", 'n', NULL
, 0,
435 N_("archive is seekable"), GRID
+1 },
436 {"no-seek", NO_SEEK_OPTION
, NULL
, 0,
437 N_("archive is not seekable"), GRID
+1 },
438 {"no-check-device", NO_CHECK_DEVICE_OPTION
, NULL
, 0,
439 N_("do not check device numbers when creating incremental archives"),
441 {"check-device", CHECK_DEVICE_OPTION
, NULL
, 0,
442 N_("check device numbers when creating incremental archives (default)"),
448 N_("Overwrite control:"), GRID
},
450 {"verify", 'W', 0, 0,
451 N_("attempt to verify the archive after writing it"), GRID
+1 },
452 {"remove-files", REMOVE_FILES_OPTION
, 0, 0,
453 N_("remove files after adding them to the archive"), GRID
+1 },
454 {"keep-old-files", 'k', 0, 0,
455 N_("don't replace existing files when extracting"), GRID
+1 },
456 {"keep-newer-files", KEEP_NEWER_FILES_OPTION
, 0, 0,
457 N_("don't replace existing files that are newer than their archive copies"), GRID
+1 },
458 {"overwrite", OVERWRITE_OPTION
, 0, 0,
459 N_("overwrite existing files when extracting"), GRID
+1 },
460 {"unlink-first", 'U', 0, 0,
461 N_("remove each file prior to extracting over it"), GRID
+1 },
462 {"recursive-unlink", RECURSIVE_UNLINK_OPTION
, 0, 0,
463 N_("empty hierarchies prior to extracting directory"), GRID
+1 },
464 {"no-overwrite-dir", NO_OVERWRITE_DIR_OPTION
, 0, 0,
465 N_("preserve metadata of existing directories"), GRID
+1 },
466 {"overwrite-dir", OVERWRITE_DIR_OPTION
, 0, 0,
467 N_("overwrite metadata of existing directories when extracting (default)"),
473 N_("Select output stream:"), GRID
},
475 {"to-stdout", 'O', 0, 0,
476 N_("extract files to standard output"), GRID
+1 },
477 {"to-command", TO_COMMAND_OPTION
, N_("COMMAND"), 0,
478 N_("pipe extracted files to another program"), GRID
+1 },
479 {"ignore-command-error", IGNORE_COMMAND_ERROR_OPTION
, 0, 0,
480 N_("ignore exit codes of children"), GRID
+1 },
481 {"no-ignore-command-error", NO_IGNORE_COMMAND_ERROR_OPTION
, 0, 0,
482 N_("treat non-zero exit codes of children as error"), GRID
+1 },
487 N_("Handling of file attributes:"), GRID
},
489 {"owner", OWNER_OPTION
, N_("NAME"), 0,
490 N_("force NAME as owner for added files"), GRID
+1 },
491 {"group", GROUP_OPTION
, N_("NAME"), 0,
492 N_("force NAME as group for added files"), GRID
+1 },
493 {"mtime", MTIME_OPTION
, N_("DATE-OR-FILE"), 0,
494 N_("set mtime for added files from DATE-OR-FILE"), GRID
+1 },
495 {"mode", MODE_OPTION
, N_("CHANGES"), 0,
496 N_("force (symbolic) mode CHANGES for added files"), GRID
+1 },
497 {"atime-preserve", ATIME_PRESERVE_OPTION
,
498 N_("METHOD"), OPTION_ARG_OPTIONAL
,
499 N_("preserve access times on dumped files, either by restoring the times"
500 " after reading (METHOD='replace'; default) or by not setting the times"
501 " in the first place (METHOD='system')"), GRID
+1 },
503 N_("don't extract file modified time"), GRID
+1 },
504 {"same-owner", SAME_OWNER_OPTION
, 0, 0,
505 N_("try extracting files with the same ownership as exists in the archive (default for superuser)"), GRID
+1 },
506 {"no-same-owner", NO_SAME_OWNER_OPTION
, 0, 0,
507 N_("extract files as yourself (default for ordinary users)"), GRID
+1 },
508 {"numeric-owner", NUMERIC_OWNER_OPTION
, 0, 0,
509 N_("always use numbers for user/group names"), GRID
+1 },
510 {"preserve-permissions", 'p', 0, 0,
511 N_("extract information about file permissions (default for superuser)"),
513 {"same-permissions", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
514 {"no-same-permissions", NO_SAME_PERMISSIONS_OPTION
, 0, 0,
515 N_("apply the user's umask when extracting permissions from the archive (default for ordinary users)"), GRID
+1 },
516 {"preserve-order", 's', 0, 0,
517 N_("sort names to extract to match archive"), GRID
+1 },
518 {"same-order", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
519 {"preserve", PRESERVE_OPTION
, 0, 0,
520 N_("same as both -p and -s"), GRID
+1 },
521 {"delay-directory-restore", DELAY_DIRECTORY_RESTORE_OPTION
, 0, 0,
522 N_("delay setting modification times and permissions of extracted"
523 " directories until the end of extraction"), GRID
+1 },
524 {"no-delay-directory-restore", NO_DELAY_DIRECTORY_RESTORE_OPTION
, 0, 0,
525 N_("cancel the effect of --delay-directory-restore option"), GRID
+1 },
530 N_("Device selection and switching:"), GRID
},
532 {"file", 'f', N_("ARCHIVE"), 0,
533 N_("use archive file or device ARCHIVE"), GRID
+1 },
534 {"force-local", FORCE_LOCAL_OPTION
, 0, 0,
535 N_("archive file is local even if it has a colon"), GRID
+1 },
536 {"rmt-command", RMT_COMMAND_OPTION
, N_("COMMAND"), 0,
537 N_("use given rmt COMMAND instead of rmt"), GRID
+1 },
538 {"rsh-command", RSH_COMMAND_OPTION
, N_("COMMAND"), 0,
539 N_("use remote COMMAND instead of rsh"), GRID
+1 },
541 {"-[0-7][lmh]", 0, NULL
, OPTION_DOC
, /* It is OK, since `name' will never be
543 N_("specify drive and density"), GRID
+1 },
545 {NULL
, '0', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
546 {NULL
, '1', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
547 {NULL
, '2', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
548 {NULL
, '3', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
549 {NULL
, '4', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
550 {NULL
, '5', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
551 {NULL
, '6', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
552 {NULL
, '7', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
553 {NULL
, '8', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
554 {NULL
, '9', NULL
, OPTION_HIDDEN
, NULL
, GRID
+1 },
556 {"multi-volume", 'M', 0, 0,
557 N_("create/list/extract multi-volume archive"), GRID
+1 },
558 {"tape-length", 'L', N_("NUMBER"), 0,
559 N_("change tape after writing NUMBER x 1024 bytes"), GRID
+1 },
560 {"info-script", 'F', N_("NAME"), 0,
561 N_("run script at end of each tape (implies -M)"), GRID
+1 },
562 {"new-volume-script", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
563 {"volno-file", VOLNO_FILE_OPTION
, N_("FILE"), 0,
564 N_("use/update the volume number in FILE"), GRID
+1 },
569 N_("Device blocking:"), GRID
},
571 {"blocking-factor", 'b', N_("BLOCKS"), 0,
572 N_("BLOCKS x 512 bytes per record"), GRID
+1 },
573 {"record-size", RECORD_SIZE_OPTION
, N_("NUMBER"), 0,
574 N_("NUMBER of bytes per record, multiple of 512"), GRID
+1 },
575 {"ignore-zeros", 'i', 0, 0,
576 N_("ignore zeroed blocks in archive (means EOF)"), GRID
+1 },
577 {"read-full-records", 'B', 0, 0,
578 N_("reblock as we read (for 4.2BSD pipes)"), GRID
+1 },
583 N_("Archive format selection:"), GRID
},
585 {"format", 'H', N_("FORMAT"), 0,
586 N_("create archive of the given format"), GRID
+1 },
588 {NULL
, 0, NULL
, 0, N_("FORMAT is one of the following:"), GRID
+2 },
589 {" v7", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
, N_("old V7 tar format"),
591 {" oldgnu", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
,
592 N_("GNU format as per tar <= 1.12"), GRID
+3 },
593 {" gnu", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
,
594 N_("GNU tar 1.13.x format"), GRID
+3 },
595 {" ustar", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
,
596 N_("POSIX 1003.1-1988 (ustar) format"), GRID
+3 },
597 {" pax", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
,
598 N_("POSIX 1003.1-2001 (pax) format"), GRID
+3 },
599 {" posix", 0, NULL
, OPTION_DOC
|OPTION_NO_TRANS
, N_("same as pax"), GRID
+3 },
601 {"old-archive", OLD_ARCHIVE_OPTION
, 0, 0, /* FIXME */
602 N_("same as --format=v7"), GRID
+8 },
603 {"portability", 0, 0, OPTION_ALIAS
, NULL
, GRID
+8 },
604 {"posix", POSIX_OPTION
, 0, 0,
605 N_("same as --format=posix"), GRID
+8 },
606 {"pax-option", PAX_OPTION
, N_("keyword[[:]=value][,keyword[[:]=value]]..."), 0,
607 N_("control pax keywords"), GRID
+8 },
608 {"label", 'V', N_("TEXT"), 0,
609 N_("create archive with volume name TEXT; at list/extract time, use TEXT as a globbing pattern for volume name"), GRID
+8 },
614 N_("Compression options:"), GRID
},
615 {"auto-compress", 'a', 0, 0,
616 N_("use archive suffix to determine the compression program"), GRID
+1 },
617 {"no-auto-compress", NO_AUTO_COMPRESS_OPTION
, 0, 0,
618 N_("do not use archive suffix to determine the compression program"),
620 {"use-compress-program", 'I', N_("PROG"), 0,
621 N_("filter through PROG (must accept -d)"), GRID
+1 },
622 /* Note: docstrings for the options below are generated by tar_help_filter */
623 {"bzip2", 'j', 0, 0, NULL
, GRID
+1 },
624 {"gzip", 'z', 0, 0, NULL
, GRID
+1 },
625 {"gunzip", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
626 {"ungzip", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
627 {"compress", 'Z', 0, 0, NULL
, GRID
+1 },
628 {"uncompress", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
629 {"lzip", LZIP_OPTION
, 0, 0, NULL
, GRID
+1 },
630 {"lzma", LZMA_OPTION
, 0, 0, NULL
, GRID
+1 },
631 {"lzop", LZOP_OPTION
, 0, 0, NULL
, GRID
+1 },
632 {"xz", 'J', 0, 0, NULL
, GRID
+1 },
637 N_("Local file selection:"), GRID
},
639 {"add-file", ARGP_KEY_ARG
, N_("FILE"), 0,
640 N_("add given FILE to the archive (useful if its name starts with a dash)"), GRID
+1 },
641 {"directory", 'C', N_("DIR"), 0,
642 N_("change to directory DIR"), GRID
+1 },
643 {"files-from", 'T', N_("FILE"), 0,
644 N_("get names to extract or create from FILE"), GRID
+1 },
645 {"null", NULL_OPTION
, 0, 0,
646 N_("-T reads null-terminated names, disable -C"), GRID
+1 },
647 {"no-null", NO_NULL_OPTION
, 0, 0,
648 N_("disable the effect of the previous --null option"), GRID
+1 },
649 {"unquote", UNQUOTE_OPTION
, 0, 0,
650 N_("unquote filenames read with -T (default)"), GRID
+1 },
651 {"no-unquote", NO_UNQUOTE_OPTION
, 0, 0,
652 N_("do not unquote filenames read with -T"), GRID
+1 },
653 {"exclude", EXCLUDE_OPTION
, N_("PATTERN"), 0,
654 N_("exclude files, given as a PATTERN"), GRID
+1 },
655 {"exclude-from", 'X', N_("FILE"), 0,
656 N_("exclude patterns listed in FILE"), GRID
+1 },
657 {"exclude-caches", EXCLUDE_CACHES_OPTION
, 0, 0,
658 N_("exclude contents of directories containing CACHEDIR.TAG, "
659 "except for the tag file itself"), GRID
+1 },
660 {"exclude-caches-under", EXCLUDE_CACHES_UNDER_OPTION
, 0, 0,
661 N_("exclude everything under directories containing CACHEDIR.TAG"),
663 {"exclude-caches-all", EXCLUDE_CACHES_ALL_OPTION
, 0, 0,
664 N_("exclude directories containing CACHEDIR.TAG"), GRID
+1 },
665 {"exclude-tag", EXCLUDE_TAG_OPTION
, N_("FILE"), 0,
666 N_("exclude contents of directories containing FILE, except"
667 " for FILE itself"), GRID
+1 },
668 {"exclude-tag-under", EXCLUDE_TAG_UNDER_OPTION
, N_("FILE"), 0,
669 N_("exclude everything under directories containing FILE"), GRID
+1 },
670 {"exclude-tag-all", EXCLUDE_TAG_ALL_OPTION
, N_("FILE"), 0,
671 N_("exclude directories containing FILE"), GRID
+1 },
672 {"exclude-vcs", EXCLUDE_VCS_OPTION
, NULL
, 0,
673 N_("exclude version control system directories"), GRID
+1 },
674 {"exclude-backups", EXCLUDE_BACKUPS_OPTION
, NULL
, 0,
675 N_("exclude backup and lock files"), GRID
+1 },
676 {"no-recursion", NO_RECURSION_OPTION
, 0, 0,
677 N_("avoid descending automatically in directories"), GRID
+1 },
678 {"one-file-system", ONE_FILE_SYSTEM_OPTION
, 0, 0,
679 N_("stay in local file system when creating archive"), GRID
+1 },
680 {"recursion", RECURSION_OPTION
, 0, 0,
681 N_("recurse into directories (default)"), GRID
+1 },
682 {"absolute-names", 'P', 0, 0,
683 N_("don't strip leading `/'s from file names"), GRID
+1 },
684 {"dereference", 'h', 0, 0,
685 N_("follow symlinks; archive and dump the files they point to"), GRID
+1 },
686 {"hard-dereference", HARD_DEREFERENCE_OPTION
, 0, 0,
687 N_("follow hard links; archive and dump the files they refer to"), GRID
+1 },
688 {"starting-file", 'K', N_("MEMBER-NAME"), 0,
689 N_("begin at member MEMBER-NAME in the archive"), GRID
+1 },
690 {"newer", 'N', N_("DATE-OR-FILE"), 0,
691 N_("only store files newer than DATE-OR-FILE"), GRID
+1 },
692 {"after-date", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
693 {"newer-mtime", NEWER_MTIME_OPTION
, N_("DATE"), 0,
694 N_("compare date and time when data changed only"), GRID
+1 },
695 {"backup", BACKUP_OPTION
, N_("CONTROL"), OPTION_ARG_OPTIONAL
,
696 N_("backup before removal, choose version CONTROL"), GRID
+1 },
697 {"suffix", SUFFIX_OPTION
, N_("STRING"), 0,
698 N_("backup before removal, override usual suffix ('~' unless overridden by environment variable SIMPLE_BACKUP_SUFFIX)"), GRID
+1 },
703 N_("File name transformations:"), GRID
},
704 {"strip-components", STRIP_COMPONENTS_OPTION
, N_("NUMBER"), 0,
705 N_("strip NUMBER leading components from file names on extraction"),
707 {"transform", TRANSFORM_OPTION
, N_("EXPRESSION"), 0,
708 N_("use sed replace EXPRESSION to transform file names"), GRID
+1 },
709 {"xform", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
714 N_("File name matching options (affect both exclude and include patterns):"),
716 {"ignore-case", IGNORE_CASE_OPTION
, 0, 0,
717 N_("ignore case"), GRID
+1 },
718 {"anchored", ANCHORED_OPTION
, 0, 0,
719 N_("patterns match file name start"), GRID
+1 },
720 {"no-anchored", NO_ANCHORED_OPTION
, 0, 0,
721 N_("patterns match after any `/' (default for exclusion)"), GRID
+1 },
722 {"no-ignore-case", NO_IGNORE_CASE_OPTION
, 0, 0,
723 N_("case sensitive matching (default)"), GRID
+1 },
724 {"wildcards", WILDCARDS_OPTION
, 0, 0,
725 N_("use wildcards (default for exclusion)"), GRID
+1 },
726 {"no-wildcards", NO_WILDCARDS_OPTION
, 0, 0,
727 N_("verbatim string matching"), GRID
+1 },
728 {"no-wildcards-match-slash", NO_WILDCARDS_MATCH_SLASH_OPTION
, 0, 0,
729 N_("wildcards do not match `/'"), GRID
+1 },
730 {"wildcards-match-slash", WILDCARDS_MATCH_SLASH_OPTION
, 0, 0,
731 N_("wildcards match `/' (default for exclusion)"), GRID
+1 },
736 N_("Informative output:"), GRID
},
738 {"verbose", 'v', 0, 0,
739 N_("verbosely list files processed"), GRID
+1 },
740 {"warning", WARNING_OPTION
, N_("KEYWORD"), 0,
741 N_("warning control"), GRID
+1 },
742 {"checkpoint", CHECKPOINT_OPTION
, N_("NUMBER"), OPTION_ARG_OPTIONAL
,
743 N_("display progress messages every NUMBERth record (default 10)"),
745 {"checkpoint-action", CHECKPOINT_ACTION_OPTION
, N_("ACTION"), 0,
746 N_("execute ACTION on each checkpoint"),
748 {"check-links", 'l', 0, 0,
749 N_("print a message if not all links are dumped"), GRID
+1 },
750 {"totals", TOTALS_OPTION
, N_("SIGNAL"), OPTION_ARG_OPTIONAL
,
751 N_("print total bytes after processing the archive; "
752 "with an argument - print total bytes when this SIGNAL is delivered; "
753 "Allowed signals are: SIGHUP, SIGQUIT, SIGINT, SIGUSR1 and SIGUSR2; "
754 "the names without SIG prefix are also accepted"), GRID
+1 },
755 {"utc", UTC_OPTION
, 0, 0,
756 N_("print file modification times in UTC"), GRID
+1 },
757 {"full-time", FULL_TIME_OPTION
, 0, 0,
758 N_("print file time to its full resolution"), GRID
+1 },
759 {"index-file", INDEX_FILE_OPTION
, N_("FILE"), 0,
760 N_("send verbose output to FILE"), GRID
+1 },
761 {"block-number", 'R', 0, 0,
762 N_("show block number within archive with each message"), GRID
+1 },
763 {"interactive", 'w', 0, 0,
764 N_("ask for confirmation for every action"), GRID
+1 },
765 {"confirmation", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
766 {"show-defaults", SHOW_DEFAULTS_OPTION
, 0, 0,
767 N_("show tar defaults"), GRID
+1 },
768 {"show-omitted-dirs", SHOW_OMITTED_DIRS_OPTION
, 0, 0,
769 N_("when listing or extracting, list each directory that does not match search criteria"), GRID
+1 },
770 {"show-transformed-names", SHOW_TRANSFORMED_NAMES_OPTION
, 0, 0,
771 N_("show file or archive names after transformation"),
773 {"show-stored-names", 0, 0, OPTION_ALIAS
, NULL
, GRID
+1 },
774 {"quoting-style", QUOTING_STYLE_OPTION
, N_("STYLE"), 0,
775 N_("set name quoting style; see below for valid STYLE values"), GRID
+1 },
776 {"quote-chars", QUOTE_CHARS_OPTION
, N_("STRING"), 0,
777 N_("additionally quote characters from STRING"), GRID
+1 },
778 {"no-quote-chars", NO_QUOTE_CHARS_OPTION
, N_("STRING"), 0,
779 N_("disable quoting for characters from STRING"), GRID
+1 },
784 N_("Compatibility options:"), GRID
},
787 N_("when creating, same as --old-archive; when extracting, same as --no-same-owner"), GRID
+1 },
792 N_("Other options:"), GRID
},
794 {"restrict", RESTRICT_OPTION
, 0, 0,
795 N_("disable use of some potentially harmful options"), -1 },
801 static char const *const atime_preserve_args
[] =
803 "replace", "system", NULL
806 static enum atime_preserve
const atime_preserve_types
[] =
808 replace_atime_preserve
, system_atime_preserve
811 /* Make sure atime_preserve_types has as much entries as atime_preserve_args
812 (minus 1 for NULL guard) */
813 ARGMATCH_VERIFY (atime_preserve_args
, atime_preserve_types
);
815 /* Wildcard matching settings */
818 default_wildcards
, /* For exclusion == enable_wildcards,
819 for inclusion == disable_wildcards */
824 struct tar_args
/* Variables used during option parsing */
826 struct textual_date
*textual_date
; /* Keeps the arguments to --newer-mtime
827 and/or --date option if they are
829 enum wildcards wildcards
; /* Wildcard settings (--wildcards/
831 int matching_flags
; /* exclude_fnmatch options */
832 int include_anchored
; /* Pattern anchoring options used for
834 bool o_option
; /* True if -o option was given */
835 bool pax_option
; /* True if --pax-option was given */
836 char const *backup_suffix_string
; /* --suffix option argument */
837 char const *version_control_string
; /* --backup option argument */
838 bool input_files
; /* True if some input files where given */
839 int compress_autodetect
; /* True if compression autodetection should
840 be attempted when creating archives */
844 #define MAKE_EXCL_OPTIONS(args) \
845 ((((args)->wildcards != disable_wildcards) ? EXCLUDE_WILDCARDS : 0) \
846 | (args)->matching_flags \
849 #define MAKE_INCL_OPTIONS(args) \
850 ((((args)->wildcards == enable_wildcards) ? EXCLUDE_WILDCARDS : 0) \
851 | (args)->include_anchored \
852 | (args)->matching_flags \
855 static char const * const vcs_file_table
[] = {
887 static char const * const backup_file_table
[] = {
895 add_exclude_array (char const * const * fv
)
899 for (i
= 0; fv
[i
]; i
++)
900 add_exclude (excluded
, fv
[i
], 0);
905 format_default_settings (void)
908 "--format=%s -f%s -b%d --quoting-style=%s --rmt-command=%s"
913 archive_format_string (DEFAULT_ARCHIVE_FORMAT
),
914 DEFAULT_ARCHIVE
, DEFAULT_BLOCKING
,
915 quoting_style_args
[DEFAULT_QUOTING_STYLE
],
925 set_subcommand_option (enum subcommand subcommand
)
927 if (subcommand_option
!= UNKNOWN_SUBCOMMAND
928 && subcommand_option
!= subcommand
)
930 _("You may not specify more than one `-Acdtrux' or `--test-label' option")));
932 subcommand_option
= subcommand
;
936 set_use_compress_program_option (const char *string
)
938 if (use_compress_program_option
939 && strcmp (use_compress_program_option
, string
) != 0)
940 USAGE_ERROR ((0, 0, _("Conflicting compression options")));
942 use_compress_program_option
= string
;
949 print_total_stats ();
950 #ifndef HAVE_SIGACTION
951 signal (signo
, sigstat
);
956 stat_on_signal (int signo
)
958 #ifdef HAVE_SIGACTION
959 struct sigaction act
;
960 act
.sa_handler
= sigstat
;
961 sigemptyset (&act
.sa_mask
);
963 sigaction (signo
, &act
, NULL
);
965 signal (signo
, sigstat
);
970 set_stat_signal (const char *name
)
977 { "SIGUSR1", SIGUSR1
},
979 { "SIGUSR2", SIGUSR2
},
981 { "SIGHUP", SIGHUP
},
983 { "SIGINT", SIGINT
},
985 { "SIGQUIT", SIGQUIT
},
988 struct sigtab
const *p
;
990 for (p
= sigtab
; p
< sigtab
+ sizeof (sigtab
) / sizeof (sigtab
[0]); p
++)
991 if (strcmp (p
->name
, name
) == 0)
993 stat_on_signal (p
->signo
);
996 FATAL_ERROR ((0, 0, _("Unknown signal name: %s"), name
));
1002 struct textual_date
*next
;
1009 get_date_or_file (struct tar_args
*args
, const char *option
,
1010 const char *str
, struct timespec
*ts
)
1012 if (FILE_SYSTEM_PREFIX_LEN (str
) != 0
1017 if (deref_stat (dereference_option
, str
, &st
) != 0)
1020 USAGE_ERROR ((0, 0, _("Date sample file not found")));
1022 *ts
= get_stat_mtime (&st
);
1026 if (! get_date (ts
, str
, NULL
))
1028 WARN ((0, 0, _("Substituting %s for unknown date format %s"),
1029 tartime (*ts
, false), quote (str
)));
1035 struct textual_date
*p
= xmalloc (sizeof (*p
));
1038 p
->date
= xstrdup (str
);
1039 p
->next
= args
->textual_date
;
1040 args
->textual_date
= p
;
1047 report_textual_dates (struct tar_args
*args
)
1049 struct textual_date
*p
;
1050 for (p
= args
->textual_date
; p
; )
1052 struct textual_date
*next
= p
->next
;
1055 char const *treated_as
= tartime (p
->ts
, true);
1056 if (strcmp (p
->date
, treated_as
) != 0)
1057 WARN ((0, 0, _("Option %s: Treating date `%s' as %s"),
1058 p
->option
, p
->date
, treated_as
));
1068 /* Either NL or NUL, as decided by the --null option. */
1069 static char filename_terminator
;
1071 enum read_file_list_state
/* Result of reading file name from the list file */
1073 file_list_success
, /* OK, name read successfully */
1074 file_list_end
, /* End of list file */
1075 file_list_zero
, /* Zero separator encountered where it should not */
1076 file_list_skip
/* Empty (zero-length) entry encountered, skip it */
1079 /* Read from FP a sequence of characters up to TERM and put them
1082 static enum read_file_list_state
1083 read_name_from_file (FILE *fp
, struct obstack
*stk
, int term
)
1088 for (c
= getc (fp
); c
!= EOF
&& c
!= term
; c
= getc (fp
))
1092 /* We have read a zero separator. The file possibly is
1094 return file_list_zero
;
1096 obstack_1grow (stk
, c
);
1100 if (counter
== 0 && c
!= EOF
)
1101 return file_list_skip
;
1103 obstack_1grow (stk
, 0);
1105 return (counter
== 0 && c
== EOF
) ? file_list_end
: file_list_success
;
1109 static bool files_from_option
; /* When set, tar will not refuse to create
1111 static struct obstack argv_stk
; /* Storage for additional command line options
1112 read using -T option */
1114 /* Prevent recursive inclusion of the same file */
1117 struct file_id_list
*next
;
1122 static struct file_id_list
*file_id_list
;
1125 add_file_id (const char *filename
)
1127 struct file_id_list
*p
;
1130 if (stat (filename
, &st
))
1131 stat_fatal (filename
);
1132 for (p
= file_id_list
; p
; p
= p
->next
)
1133 if (p
->ino
== st
.st_ino
&& p
->dev
== st
.st_dev
)
1135 FATAL_ERROR ((0, 0, _("%s: file list already read"),
1136 quotearg_colon (filename
)));
1138 p
= xmalloc (sizeof *p
);
1139 p
->next
= file_id_list
;
1145 /* Default density numbers for [0-9][lmh] device specifications */
1147 #ifndef LOW_DENSITY_NUM
1148 # define LOW_DENSITY_NUM 0
1151 #ifndef MID_DENSITY_NUM
1152 # define MID_DENSITY_NUM 8
1155 #ifndef HIGH_DENSITY_NUM
1156 # define HIGH_DENSITY_NUM 16
1160 update_argv (const char *filename
, struct argp_state
*state
)
1163 size_t count
= 0, i
;
1167 bool is_stdin
= false;
1168 enum read_file_list_state read_state
;
1169 int term
= filename_terminator
;
1171 if (!strcmp (filename
, "-"))
1174 request_stdin ("-T");
1179 add_file_id (filename
);
1180 if ((fp
= fopen (filename
, "r")) == NULL
)
1181 open_fatal (filename
);
1184 while ((read_state
= read_name_from_file (fp
, &argv_stk
, term
))
1189 case file_list_success
:
1193 case file_list_end
: /* won't happen, just to pacify gcc */
1196 case file_list_zero
:
1200 WARNOPT (WARN_FILENAME_WITH_NULS
,
1201 (0, 0, N_("%s: file name read contains nul character"),
1202 quotearg_colon (filename
)));
1204 /* Prepare new stack contents */
1205 size
= obstack_object_size (&argv_stk
);
1206 p
= obstack_finish (&argv_stk
);
1207 for (; size
> 0; size
--, p
++)
1209 obstack_1grow (&argv_stk
, *p
);
1211 obstack_1grow (&argv_stk
, '\n');
1212 obstack_1grow (&argv_stk
, 0);
1214 /* Read rest of files using new filename terminator */
1219 case file_list_skip
:
1230 start
= obstack_finish (&argv_stk
);
1233 for (p
= start
; *p
; p
+= strlen (p
) + 1)
1237 new_argc
= state
->argc
+ count
;
1238 new_argv
= xmalloc (sizeof (state
->argv
[0]) * (new_argc
+ 1));
1239 memcpy (new_argv
, state
->argv
, sizeof (state
->argv
[0]) * (state
->argc
+ 1));
1240 state
->argv
= new_argv
;
1241 memmove (&state
->argv
[state
->next
+ count
], &state
->argv
[state
->next
],
1242 (state
->argc
- state
->next
+ 1) * sizeof (state
->argv
[0]));
1244 state
->argc
= new_argc
;
1246 for (i
= state
->next
, p
= start
; *p
; p
+= strlen (p
) + 1, i
++)
1248 if (term
== 0 && p
[0] == '-')
1249 state
->argv
[i
++] = "--add-file";
1256 tar_help_filter (int key
, const char *text
, void *input
)
1268 s
= xasprintf (_("filter the archive through %s"), BZIP2_PROGRAM
);
1272 s
= xasprintf (_("filter the archive through %s"), GZIP_PROGRAM
);
1276 s
= xasprintf (_("filter the archive through %s"), COMPRESS_PROGRAM
);
1280 s
= xasprintf (_("filter the archive through %s"), LZIP_PROGRAM
);
1284 s
= xasprintf (_("filter the archive through %s"), LZMA_PROGRAM
);
1288 s
= xasprintf (_("filter the archive through %s"), XZ_PROGRAM
);
1291 case ARGP_KEY_HELP_EXTRA
:
1295 obstack_init (&stk
);
1296 tstr
= _("Valid arguments for the --quoting-style option are:");
1297 obstack_grow (&stk
, tstr
, strlen (tstr
));
1298 obstack_grow (&stk
, "\n\n", 2);
1299 tar_list_quoting_styles (&stk
, " ");
1300 tstr
= _("\n*This* tar defaults to:\n");
1301 obstack_grow (&stk
, tstr
, strlen (tstr
));
1302 s
= format_default_settings ();
1303 obstack_grow (&stk
, s
, strlen (s
));
1304 obstack_1grow (&stk
, '\n');
1305 obstack_1grow (&stk
, 0);
1306 s
= xstrdup (obstack_finish (&stk
));
1307 obstack_free (&stk
, NULL
);
1314 expand_pax_option (struct tar_args
*targs
, const char *arg
)
1319 obstack_init (&stk
);
1322 size_t seglen
= strcspn (arg
, ",");
1323 char *p
= memchr (arg
, '=', seglen
);
1326 size_t len
= p
- arg
+ 1;
1327 obstack_grow (&stk
, arg
, len
);
1329 for (++p
; *p
&& isspace ((unsigned char) *p
); p
++)
1331 if (*p
== '{' && p
[len
-1] == '}')
1334 char *tmp
= xmalloc (len
);
1335 memcpy (tmp
, p
+ 1, len
-2);
1337 if (get_date_or_file (targs
, "--pax-option", tmp
, &ts
) == 0)
1339 char buf
[UINTMAX_STRSIZE_BOUND
], *s
;
1340 s
= umaxtostr (ts
.tv_sec
, buf
);
1341 obstack_grow (&stk
, s
, strlen (s
));
1344 obstack_grow (&stk
, p
, len
);
1348 obstack_grow (&stk
, p
, len
);
1351 obstack_grow (&stk
, arg
, seglen
);
1356 obstack_1grow (&stk
, *arg
);
1360 obstack_1grow (&stk
, 0);
1361 res
= xstrdup (obstack_finish (&stk
));
1362 obstack_free (&stk
, NULL
);
1368 parse_opt (int key
, char *arg
, struct argp_state
*state
)
1370 struct tar_args
*args
= state
->input
;
1375 /* File name or non-parsed option, because of ARGP_IN_ORDER */
1376 name_add_name (arg
, MAKE_INCL_OPTIONS (args
));
1377 args
->input_files
= true;
1381 set_subcommand_option (CAT_SUBCOMMAND
);
1385 args
->compress_autodetect
= true;
1388 case NO_AUTO_COMPRESS_OPTION
:
1389 args
->compress_autodetect
= false;
1395 if (! (xstrtoumax (arg
, 0, 10, &u
, "") == LONGINT_OK
1396 && u
== (blocking_factor
= u
)
1397 && 0 < blocking_factor
1398 && u
== (record_size
= u
* BLOCKSIZE
) / BLOCKSIZE
))
1399 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1400 _("Invalid blocking factor")));
1405 /* Try to reblock input records. For reading 4.2BSD pipes. */
1407 /* It would surely make sense to exchange -B and -R, but it seems
1408 that -B has been used for a long while in Sun tar and most
1409 BSD-derived systems. This is a consequence of the block/record
1410 terminology confusion. */
1412 read_full_records_option
= true;
1416 set_subcommand_option (CREATE_SUBCOMMAND
);
1424 set_subcommand_option (DIFF_SUBCOMMAND
);
1428 if (archive_names
== allocated_archive_names
)
1429 archive_name_array
= x2nrealloc (archive_name_array
,
1430 &allocated_archive_names
,
1431 sizeof (archive_name_array
[0]));
1433 archive_name_array
[archive_names
++] = arg
;
1437 /* Since -F is only useful with -M, make it implied. Run this
1438 script at the end of each tape. */
1440 info_script_option
= arg
;
1441 multi_volume_option
= true;
1444 case FULL_TIME_OPTION
:
1445 full_time_option
= true;
1449 listed_incremental_option
= arg
;
1450 after_date_option
= true;
1454 /* We are making an incremental dump (FIXME: are we?); save
1455 directories at the beginning of the archive, and include in each
1456 directory its contents. */
1458 incremental_option
= true;
1462 /* Follow symbolic links. */
1463 dereference_option
= true;
1466 case HARD_DEREFERENCE_OPTION
:
1467 hard_dereference_option
= true;
1471 /* Ignore zero blocks (eofs). This can't be the default,
1472 because Unix tar writes two blocks of zeros, then pads out
1473 the record with garbage. */
1475 ignore_zeros_option
= true;
1479 set_use_compress_program_option (BZIP2_PROGRAM
);
1483 set_use_compress_program_option (XZ_PROGRAM
);
1487 /* Don't replace existing files. */
1488 old_files_option
= KEEP_OLD_FILES
;
1492 starting_file_option
= true;
1493 addname (arg
, 0, true, NULL
);
1496 case ONE_FILE_SYSTEM_OPTION
:
1497 /* When dumping directories, don't dump files/subdirectories
1498 that are on other filesystems. */
1499 one_file_system_option
= true;
1503 check_links_option
= 1;
1509 if (xstrtoumax (arg
, 0, 10, &u
, "") != LONGINT_OK
)
1510 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1511 _("Invalid tape length")));
1512 tape_length_option
= 1024 * (tarlong
) u
;
1513 multi_volume_option
= true;
1520 incremental_level
= strtoul (arg
, &p
, 10);
1522 USAGE_ERROR ((0, 0, _("Invalid incremental level value")));
1527 set_use_compress_program_option (LZIP_PROGRAM
);
1531 set_use_compress_program_option (LZMA_PROGRAM
);
1535 set_use_compress_program_option (LZOP_PROGRAM
);
1539 touch_option
= true;
1543 /* Make multivolume archive: when we can't write any more into
1544 the archive, re-open it, and continue writing. */
1546 multi_volume_option
= true;
1550 get_date_or_file (args
, "--mtime", arg
, &mtime_option
);
1551 set_mtime_option
= true;
1558 case NO_SEEK_OPTION
:
1563 after_date_option
= true;
1566 case NEWER_MTIME_OPTION
:
1567 if (NEWER_OPTION_INITIALIZED (newer_mtime_option
))
1568 USAGE_ERROR ((0, 0, _("More than one threshold date")));
1569 get_date_or_file (args
,
1570 key
== NEWER_MTIME_OPTION
? "--newer-mtime"
1571 : "--after-date", arg
, &newer_mtime_option
);
1575 args
->o_option
= true;
1579 to_stdout_option
= true;
1583 same_permissions_option
= true;
1587 absolute_names_option
= true;
1591 set_subcommand_option (APPEND_SUBCOMMAND
);
1595 /* Print block numbers for debugging bad tar archives. */
1597 /* It would surely make sense to exchange -B and -R, but it seems
1598 that -B has been used for a long while in Sun tar and most
1599 BSD-derived systems. This is a consequence of the block/record
1600 terminology confusion. */
1602 block_number_option
= true;
1606 /* Names to extract are sorted. */
1608 same_order_option
= true;
1612 sparse_option
= true;
1615 case SPARSE_VERSION_OPTION
:
1616 sparse_option
= true;
1619 tar_sparse_major
= strtoul (arg
, &p
, 10);
1623 USAGE_ERROR ((0, 0, _("Invalid sparse version value")));
1624 tar_sparse_minor
= strtoul (p
+ 1, &p
, 10);
1626 USAGE_ERROR ((0, 0, _("Invalid sparse version value")));
1632 set_subcommand_option (LIST_SUBCOMMAND
);
1636 case TEST_LABEL_OPTION
:
1637 set_subcommand_option (TEST_LABEL_SUBCOMMAND
);
1641 update_argv (arg
, state
);
1642 /* Indicate we've been given -T option. This is for backward
1643 compatibility only, so that `tar cfT archive /dev/null will
1645 files_from_option
= true;
1649 set_subcommand_option (UPDATE_SUBCOMMAND
);
1653 old_files_option
= UNLINK_FIRST_OLD_FILES
;
1662 warning_option
|= WARN_VERBOSE_WARNINGS
;
1666 volume_label_option
= arg
;
1670 interactive_option
= true;
1674 verify_option
= true;
1678 set_subcommand_option (EXTRACT_SUBCOMMAND
);
1682 if (add_exclude_file (add_exclude
, excluded
, arg
,
1683 MAKE_EXCL_OPTIONS (args
), '\n')
1687 FATAL_ERROR ((0, e
, "%s", quotearg_colon (arg
)));
1692 set_use_compress_program_option (GZIP_PROGRAM
);
1696 set_use_compress_program_option (COMPRESS_PROGRAM
);
1699 case ANCHORED_OPTION
:
1700 args
->matching_flags
|= EXCLUDE_ANCHORED
;
1703 case ATIME_PRESERVE_OPTION
:
1704 atime_preserve_option
=
1706 ? XARGMATCH ("--atime-preserve", arg
,
1707 atime_preserve_args
, atime_preserve_types
)
1708 : replace_atime_preserve
);
1709 if (! O_NOATIME
&& atime_preserve_option
== system_atime_preserve
)
1711 _("--atime-preserve='system' is not supported"
1712 " on this platform")));
1715 case CHECK_DEVICE_OPTION
:
1716 check_device_option
= true;
1719 case NO_CHECK_DEVICE_OPTION
:
1720 check_device_option
= false;
1723 case CHECKPOINT_OPTION
:
1730 checkpoint_compile_action (".");
1733 checkpoint_option
= strtoul (arg
, &p
, 0);
1736 _("--checkpoint value is not an integer")));
1739 checkpoint_option
= DEFAULT_CHECKPOINT
;
1742 case CHECKPOINT_ACTION_OPTION
:
1743 checkpoint_compile_action (arg
);
1747 backup_option
= true;
1749 args
->version_control_string
= arg
;
1752 case DELAY_DIRECTORY_RESTORE_OPTION
:
1753 delay_directory_restore_option
= true;
1756 case NO_DELAY_DIRECTORY_RESTORE_OPTION
:
1757 delay_directory_restore_option
= false;
1761 set_subcommand_option (DELETE_SUBCOMMAND
);
1764 case EXCLUDE_BACKUPS_OPTION
:
1765 add_exclude_array (backup_file_table
);
1768 case EXCLUDE_OPTION
:
1769 add_exclude (excluded
, arg
, MAKE_EXCL_OPTIONS (args
));
1772 case EXCLUDE_CACHES_OPTION
:
1773 add_exclusion_tag ("CACHEDIR.TAG", exclusion_tag_contents
,
1777 case EXCLUDE_CACHES_UNDER_OPTION
:
1778 add_exclusion_tag ("CACHEDIR.TAG", exclusion_tag_under
,
1782 case EXCLUDE_CACHES_ALL_OPTION
:
1783 add_exclusion_tag ("CACHEDIR.TAG", exclusion_tag_all
,
1787 case EXCLUDE_TAG_OPTION
:
1788 add_exclusion_tag (arg
, exclusion_tag_contents
, NULL
);
1791 case EXCLUDE_TAG_UNDER_OPTION
:
1792 add_exclusion_tag (arg
, exclusion_tag_under
, NULL
);
1795 case EXCLUDE_TAG_ALL_OPTION
:
1796 add_exclusion_tag (arg
, exclusion_tag_all
, NULL
);
1799 case EXCLUDE_VCS_OPTION
:
1800 add_exclude_array (vcs_file_table
);
1803 case FORCE_LOCAL_OPTION
:
1804 force_local_option
= true;
1808 set_archive_format (arg
);
1811 case INDEX_FILE_OPTION
:
1812 index_file_name
= arg
;
1815 case IGNORE_CASE_OPTION
:
1816 args
->matching_flags
|= FNM_CASEFOLD
;
1819 case IGNORE_COMMAND_ERROR_OPTION
:
1820 ignore_command_error_option
= true;
1823 case IGNORE_FAILED_READ_OPTION
:
1824 ignore_failed_read_option
= true;
1827 case KEEP_NEWER_FILES_OPTION
:
1828 old_files_option
= KEEP_NEWER_FILES
;
1832 if (! (strlen (arg
) < GNAME_FIELD_SIZE
1833 && gname_to_gid (arg
, &group_option
)))
1836 if (xstrtoumax (arg
, 0, 10, &g
, "") == LONGINT_OK
1840 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1841 _("Invalid group")));
1846 mode_option
= mode_compile (arg
);
1848 FATAL_ERROR ((0, 0, _("Invalid mode given on option")));
1849 initial_umask
= umask (0);
1850 umask (initial_umask
);
1853 case NO_ANCHORED_OPTION
:
1854 args
->include_anchored
= 0; /* Clear the default for comman line args */
1855 args
->matching_flags
&= ~ EXCLUDE_ANCHORED
;
1858 case NO_IGNORE_CASE_OPTION
:
1859 args
->matching_flags
&= ~ FNM_CASEFOLD
;
1862 case NO_IGNORE_COMMAND_ERROR_OPTION
:
1863 ignore_command_error_option
= false;
1866 case NO_OVERWRITE_DIR_OPTION
:
1867 old_files_option
= NO_OVERWRITE_DIR_OLD_FILES
;
1870 case NO_QUOTE_CHARS_OPTION
:
1872 set_char_quoting (NULL
, *arg
, 0);
1875 case NO_WILDCARDS_OPTION
:
1876 args
->wildcards
= disable_wildcards
;
1879 case NO_WILDCARDS_MATCH_SLASH_OPTION
:
1880 args
->matching_flags
|= FNM_FILE_NAME
;
1884 filename_terminator
= '\0';
1887 case NO_NULL_OPTION
:
1888 filename_terminator
= '\n';
1891 case NUMERIC_OWNER_OPTION
:
1892 numeric_owner_option
= true;
1895 case OCCURRENCE_OPTION
:
1897 occurrence_option
= 1;
1901 if (xstrtoumax (arg
, 0, 10, &u
, "") == LONGINT_OK
)
1902 occurrence_option
= u
;
1904 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1905 _("Invalid number")));
1909 case OVERWRITE_DIR_OPTION
:
1910 old_files_option
= DEFAULT_OLD_FILES
;
1913 case OVERWRITE_OPTION
:
1914 old_files_option
= OVERWRITE_OLD_FILES
;
1918 if (! (strlen (arg
) < UNAME_FIELD_SIZE
1919 && uname_to_uid (arg
, &owner_option
)))
1922 if (xstrtoumax (arg
, 0, 10, &u
, "") == LONGINT_OK
1926 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1927 _("Invalid owner")));
1931 case QUOTE_CHARS_OPTION
:
1933 set_char_quoting (NULL
, *arg
, 1);
1936 case QUOTING_STYLE_OPTION
:
1937 tar_set_quoting_style (arg
);
1942 char *tmp
= expand_pax_option (args
, arg
);
1943 args
->pax_option
= true;
1944 xheader_set_option (tmp
);
1950 set_archive_format ("posix");
1953 case PRESERVE_OPTION
:
1954 /* FIXME: What it is good for? */
1955 same_permissions_option
= true;
1956 same_order_option
= true;
1957 WARN ((0, 0, _("The --preserve option is deprecated, "
1958 "use --preserve-permissions --preserve-order instead")));
1961 case RECORD_SIZE_OPTION
:
1964 if (! (xstrtoumax (arg
, 0, 10, &u
, "") == LONGINT_OK
1965 && u
== (size_t) u
))
1966 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
1967 _("Invalid record size")));
1969 if (record_size
% BLOCKSIZE
!= 0)
1970 USAGE_ERROR ((0, 0, _("Record size must be a multiple of %d."),
1972 blocking_factor
= record_size
/ BLOCKSIZE
;
1976 case RECURSIVE_UNLINK_OPTION
:
1977 recursive_unlink_option
= true;
1980 case REMOVE_FILES_OPTION
:
1981 remove_files_option
= true;
1984 case RESTRICT_OPTION
:
1985 restrict_option
= true;
1988 case RMT_COMMAND_OPTION
:
1992 case RSH_COMMAND_OPTION
:
1993 rsh_command_option
= arg
;
1996 case SHOW_DEFAULTS_OPTION
:
1998 char *s
= format_default_settings ();
2005 case STRIP_COMPONENTS_OPTION
:
2008 if (! (xstrtoumax (arg
, 0, 10, &u
, "") == LONGINT_OK
2009 && u
== (size_t) u
))
2010 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg
),
2011 _("Invalid number of elements")));
2012 strip_name_components
= u
;
2016 case SHOW_OMITTED_DIRS_OPTION
:
2017 show_omitted_dirs_option
= true;
2020 case SHOW_TRANSFORMED_NAMES_OPTION
:
2021 show_transformed_names_option
= true;
2025 backup_option
= true;
2026 args
->backup_suffix_string
= arg
;
2029 case TO_COMMAND_OPTION
:
2030 if (to_command_option
)
2031 USAGE_ERROR ((0, 0, _("Only one --to-command option allowed")));
2032 to_command_option
= arg
;
2037 set_stat_signal (arg
);
2039 totals_option
= true;
2042 case TRANSFORM_OPTION
:
2043 set_transform_expr (arg
);
2047 set_use_compress_program_option (arg
);
2050 case VOLNO_FILE_OPTION
:
2051 volno_file_option
= arg
;
2054 case WILDCARDS_OPTION
:
2055 args
->wildcards
= enable_wildcards
;
2058 case WILDCARDS_MATCH_SLASH_OPTION
:
2059 args
->matching_flags
&= ~ FNM_FILE_NAME
;
2062 case NO_RECURSION_OPTION
:
2063 recursion_option
= 0;
2066 case NO_SAME_OWNER_OPTION
:
2067 same_owner_option
= -1;
2070 case NO_SAME_PERMISSIONS_OPTION
:
2071 same_permissions_option
= -1;
2074 case RECURSION_OPTION
:
2075 recursion_option
= FNM_LEADING_DIR
;
2078 case SAME_OWNER_OPTION
:
2079 same_owner_option
= 1;
2082 case UNQUOTE_OPTION
:
2083 unquote_option
= true;
2086 case NO_UNQUOTE_OPTION
:
2087 unquote_option
= false;
2090 case WARNING_OPTION
:
2091 set_warning_option (arg
);
2103 #ifdef DEVICE_PREFIX
2105 int device
= key
- '0';
2107 static char buf
[sizeof DEVICE_PREFIX
+ 10];
2111 argp_error (state
, _("Malformed density argument: %s"), quote (arg
));
2113 strcpy (buf
, DEVICE_PREFIX
);
2114 cursor
= buf
+ strlen (buf
);
2116 #ifdef DENSITY_LETTER
2118 sprintf (cursor
, "%d%c", device
, arg
[0]);
2120 #else /* not DENSITY_LETTER */
2125 device
+= LOW_DENSITY_NUM
;
2129 device
+= MID_DENSITY_NUM
;
2133 device
+= HIGH_DENSITY_NUM
;
2137 argp_error (state
, _("Unknown density: `%c'"), arg
[0]);
2139 sprintf (cursor
, "%d", device
);
2141 #endif /* not DENSITY_LETTER */
2143 if (archive_names
== allocated_archive_names
)
2144 archive_name_array
= x2nrealloc (archive_name_array
,
2145 &allocated_archive_names
,
2146 sizeof (archive_name_array
[0]));
2147 archive_name_array
[archive_names
++] = xstrdup (buf
);
2151 #else /* not DEVICE_PREFIX */
2154 _("Options `-[0-7][lmh]' not supported by *this* tar"));
2156 #endif /* not DEVICE_PREFIX */
2159 return ARGP_ERR_UNKNOWN
;
2164 static struct argp argp
= {
2177 argp_help (&argp
, stderr
, ARGP_HELP_SEE
, (char*) program_name
);
2182 /* Parse the options for tar. */
2184 static struct argp_option
*
2185 find_argp_option (struct argp_option
*o
, int letter
)
2192 && o
->doc
== NULL
); o
++)
2193 if (o
->key
== letter
)
2198 static const char *tar_authors
[] = {
2205 decode_options (int argc
, char **argv
)
2208 struct tar_args args
;
2210 argp_version_setup ("tar", tar_authors
);
2212 /* Set some default option values. */
2213 args
.textual_date
= NULL
;
2214 args
.wildcards
= default_wildcards
;
2215 args
.matching_flags
= 0;
2216 args
.include_anchored
= EXCLUDE_ANCHORED
;
2217 args
.o_option
= false;
2218 args
.pax_option
= false;
2219 args
.backup_suffix_string
= getenv ("SIMPLE_BACKUP_SUFFIX");
2220 args
.version_control_string
= 0;
2221 args
.input_files
= false;
2222 args
.compress_autodetect
= false;
2224 subcommand_option
= UNKNOWN_SUBCOMMAND
;
2225 archive_format
= DEFAULT_FORMAT
;
2226 blocking_factor
= DEFAULT_BLOCKING
;
2227 record_size
= DEFAULT_BLOCKING
* BLOCKSIZE
;
2228 excluded
= new_exclude ();
2229 newer_mtime_option
.tv_sec
= TYPE_MINIMUM (time_t);
2230 newer_mtime_option
.tv_nsec
= -1;
2231 recursion_option
= FNM_LEADING_DIR
;
2232 unquote_option
= true;
2233 tar_sparse_major
= 1;
2234 tar_sparse_minor
= 0;
2239 check_device_option
= true;
2241 incremental_level
= -1;
2245 /* Convert old-style tar call by exploding option element and rearranging
2246 options accordingly. */
2248 if (argc
> 1 && argv
[1][0] != '-')
2250 int new_argc
; /* argc value for rearranged arguments */
2251 char **new_argv
; /* argv value for rearranged arguments */
2252 char *const *in
; /* cursor into original argv */
2253 char **out
; /* cursor into rearranged argv */
2254 const char *letter
; /* cursor into old option letters */
2255 char buffer
[3]; /* constructed option buffer */
2257 /* Initialize a constructed option. */
2262 /* Allocate a new argument array, and copy program name in it. */
2264 new_argc
= argc
- 1 + strlen (argv
[1]);
2265 new_argv
= xmalloc ((new_argc
+ 1) * sizeof (char *));
2270 /* Copy each old letter option as a separate option, and have the
2271 corresponding argument moved next to it. */
2273 for (letter
= *in
++; *letter
; letter
++)
2275 struct argp_option
*opt
;
2277 buffer
[1] = *letter
;
2278 *out
++ = xstrdup (buffer
);
2279 opt
= find_argp_option (options
, *letter
);
2280 if (opt
&& opt
->arg
)
2282 if (in
< argv
+ argc
)
2285 USAGE_ERROR ((0, 0, _("Old option `%c' requires an argument."),
2290 /* Copy all remaining options. */
2292 while (in
< argv
+ argc
)
2296 /* Replace the old option list by the new one. */
2302 /* Parse all options and non-options as they appear. */
2304 prepend_default_options (getenv ("TAR_OPTIONS"), &argc
, &argv
);
2306 if (argp_parse (&argp
, argc
, argv
, ARGP_IN_ORDER
, &idx
, &args
))
2307 exit (TAREXIT_FAILURE
);
2310 /* Special handling for 'o' option:
2312 GNU tar used to say "output old format".
2313 UNIX98 tar says don't chown files after extracting (we use
2314 "--no-same-owner" for this).
2316 The old GNU tar semantics is retained when used with --create
2317 option, otherwise UNIX98 semantics is assumed */
2321 if (subcommand_option
== CREATE_SUBCOMMAND
)
2323 /* GNU Tar <= 1.13 compatibility */
2324 set_archive_format ("v7");
2328 /* UNIX98 compatibility */
2329 same_owner_option
= -1;
2333 /* Handle operands after any "--" argument. */
2334 for (; idx
< argc
; idx
++)
2336 name_add_name (argv
[idx
], MAKE_INCL_OPTIONS (&args
));
2337 args
.input_files
= true;
2340 /* Warn about implicit use of the wildcards in command line arguments.
2342 warn_regex_usage
= args
.wildcards
== default_wildcards
;
2344 /* Derive option values and check option consistency. */
2346 if (archive_format
== DEFAULT_FORMAT
)
2348 if (args
.pax_option
)
2349 archive_format
= POSIX_FORMAT
;
2351 archive_format
= DEFAULT_ARCHIVE_FORMAT
;
2354 if ((volume_label_option
&& subcommand_option
== CREATE_SUBCOMMAND
)
2355 || incremental_option
2356 || multi_volume_option
2358 assert_format (FORMAT_MASK (OLDGNU_FORMAT
)
2359 | FORMAT_MASK (GNU_FORMAT
)
2360 | FORMAT_MASK (POSIX_FORMAT
));
2362 if (occurrence_option
)
2364 if (!args
.input_files
)
2366 _("--occurrence is meaningless without a file list")));
2367 if (subcommand_option
!= DELETE_SUBCOMMAND
2368 && subcommand_option
!= DIFF_SUBCOMMAND
2369 && subcommand_option
!= EXTRACT_SUBCOMMAND
2370 && subcommand_option
!= LIST_SUBCOMMAND
)
2372 _("--occurrence cannot be used in the requested operation mode")));
2375 if (archive_names
== 0)
2377 /* If no archive file name given, try TAPE from the environment, or
2378 else, DEFAULT_ARCHIVE from the configuration process. */
2381 archive_name_array
[0] = getenv ("TAPE");
2382 if (! archive_name_array
[0])
2383 archive_name_array
[0] = DEFAULT_ARCHIVE
;
2386 /* Allow multiple archives only with `-M'. */
2388 if (archive_names
> 1 && !multi_volume_option
)
2390 _("Multiple archive files require `-M' option")));
2392 if (listed_incremental_option
2393 && NEWER_OPTION_INITIALIZED (newer_mtime_option
))
2395 _("Cannot combine --listed-incremental with --newer")));
2396 if (incremental_level
!= -1 && !listed_incremental_option
)
2398 _("--level is meaningless without --listed-incremental")));
2400 if (volume_label_option
)
2402 if (archive_format
== GNU_FORMAT
|| archive_format
== OLDGNU_FORMAT
)
2404 size_t volume_label_max_len
=
2405 (sizeof current_header
->header
.name
2406 - 1 /* for trailing '\0' */
2407 - (multi_volume_option
2408 ? (sizeof " Volume "
2409 - 1 /* for null at end of " Volume " */
2410 + INT_STRLEN_BOUND (int) /* for volume number */
2411 - 1 /* for sign, as 0 <= volno */)
2413 if (volume_label_max_len
< strlen (volume_label_option
))
2415 ngettext ("%s: Volume label is too long (limit is %lu byte)",
2416 "%s: Volume label is too long (limit is %lu bytes)",
2417 volume_label_max_len
),
2418 quotearg_colon (volume_label_option
),
2419 (unsigned long) volume_label_max_len
));
2422 Label length in PAX format is limited by the volume size. */
2427 if (multi_volume_option
)
2428 USAGE_ERROR ((0, 0, _("Cannot verify multi-volume archives")));
2429 if (use_compress_program_option
)
2430 USAGE_ERROR ((0, 0, _("Cannot verify compressed archives")));
2433 if (use_compress_program_option
)
2435 if (multi_volume_option
)
2436 USAGE_ERROR ((0, 0, _("Cannot use multi-volume compressed archives")));
2437 if (subcommand_option
== UPDATE_SUBCOMMAND
2438 || subcommand_option
== APPEND_SUBCOMMAND
2439 || subcommand_option
== DELETE_SUBCOMMAND
)
2440 USAGE_ERROR ((0, 0, _("Cannot update compressed archives")));
2441 if (subcommand_option
== CAT_SUBCOMMAND
)
2442 USAGE_ERROR ((0, 0, _("Cannot concatenate compressed archives")));
2445 /* It is no harm to use --pax-option on non-pax archives in archive
2446 reading mode. It may even be useful, since it allows to override
2447 file attributes from tar headers. Therefore I allow such usage.
2450 && archive_format
!= POSIX_FORMAT
2451 && (subcommand_option
!= EXTRACT_SUBCOMMAND
2452 || subcommand_option
!= DIFF_SUBCOMMAND
2453 || subcommand_option
!= LIST_SUBCOMMAND
))
2454 USAGE_ERROR ((0, 0, _("--pax-option can be used only on POSIX archives")));
2456 /* If ready to unlink hierarchies, so we are for simpler files. */
2457 if (recursive_unlink_option
)
2458 old_files_option
= UNLINK_FIRST_OLD_FILES
;
2461 if (subcommand_option
== TEST_LABEL_SUBCOMMAND
)
2463 /* --test-label is silent if the user has specified the label name to
2465 if (!args
.input_files
)
2468 else if (utc_option
)
2471 if (tape_length_option
&& tape_length_option
< record_size
)
2472 USAGE_ERROR ((0, 0, _("Volume length cannot be less than record size")));
2474 if (same_order_option
&& listed_incremental_option
)
2475 USAGE_ERROR ((0, 0, _("--preserve-order is not compatible with "
2476 "--listed-incremental")));
2478 /* Forbid using -c with no input files whatsoever. Check that `-f -',
2479 explicit or implied, is used correctly. */
2481 switch (subcommand_option
)
2483 case CREATE_SUBCOMMAND
:
2484 if (!args
.input_files
&& !files_from_option
)
2486 _("Cowardly refusing to create an empty archive")));
2487 if (args
.compress_autodetect
&& archive_names
2488 && strcmp (archive_name_array
[0], "-"))
2489 set_comression_program_by_suffix (archive_name_array
[0],
2490 use_compress_program_option
);
2493 case EXTRACT_SUBCOMMAND
:
2494 case LIST_SUBCOMMAND
:
2495 case DIFF_SUBCOMMAND
:
2496 case TEST_LABEL_SUBCOMMAND
:
2497 for (archive_name_cursor
= archive_name_array
;
2498 archive_name_cursor
< archive_name_array
+ archive_names
;
2499 archive_name_cursor
++)
2500 if (!strcmp (*archive_name_cursor
, "-"))
2501 request_stdin ("-f");
2504 case CAT_SUBCOMMAND
:
2505 case UPDATE_SUBCOMMAND
:
2506 case APPEND_SUBCOMMAND
:
2507 for (archive_name_cursor
= archive_name_array
;
2508 archive_name_cursor
< archive_name_array
+ archive_names
;
2509 archive_name_cursor
++)
2510 if (!strcmp (*archive_name_cursor
, "-"))
2512 _("Options `-Aru' are incompatible with `-f -'")));
2518 /* Initialize stdlis */
2519 if (index_file_name
)
2521 stdlis
= fopen (index_file_name
, "w");
2523 open_error (index_file_name
);
2526 stdlis
= to_stdout_option
? stderr
: stdout
;
2528 archive_name_cursor
= archive_name_array
;
2530 /* Prepare for generating backup names. */
2532 if (args
.backup_suffix_string
)
2533 simple_backup_suffix
= xstrdup (args
.backup_suffix_string
);
2537 backup_type
= xget_version ("--backup", args
.version_control_string
);
2538 /* No backup is needed either if explicitely disabled or if
2539 the extracted files are not being written to disk. */
2540 if (backup_type
== no_backups
|| EXTRACT_OVER_PIPE
)
2541 backup_option
= false;
2544 checkpoint_finish_compile ();
2546 report_textual_dates (&args
);
2552 /* Main routine for tar. */
2554 main (int argc
, char **argv
)
2557 set_program_name (argv
[0]);
2559 setlocale (LC_ALL
, "");
2560 bindtextdomain (PACKAGE
, LOCALEDIR
);
2561 textdomain (PACKAGE
);
2563 exit_failure
= TAREXIT_FAILURE
;
2564 exit_status
= TAREXIT_SUCCESS
;
2565 filename_terminator
= '\n';
2566 set_quoting_style (0, DEFAULT_QUOTING_STYLE
);
2568 /* Make sure we have first three descriptors available */
2571 /* Pre-allocate a few structures. */
2573 allocated_archive_names
= 10;
2574 archive_name_array
=
2575 xmalloc (sizeof (const char *) * allocated_archive_names
);
2578 obstack_init (&argv_stk
);
2580 /* System V fork+wait does not work if SIGCHLD is ignored. */
2581 signal (SIGCHLD
, SIG_DFL
);
2583 /* Try to disable the ability to unlink a directory. */
2584 priv_set_remove_linkdir ();
2586 /* Decode options. */
2588 decode_options (argc
, argv
);
2592 /* Main command execution. */
2594 if (volno_file_option
)
2595 init_volume_number ();
2597 switch (subcommand_option
)
2599 case UNKNOWN_SUBCOMMAND
:
2601 _("You must specify one of the `-Acdtrux' or `--test-label' options")));
2603 case CAT_SUBCOMMAND
:
2604 case UPDATE_SUBCOMMAND
:
2605 case APPEND_SUBCOMMAND
:
2609 case DELETE_SUBCOMMAND
:
2610 delete_archive_members ();
2613 case CREATE_SUBCOMMAND
:
2617 case EXTRACT_SUBCOMMAND
:
2619 read_and (extract_archive
);
2621 /* FIXME: should extract_finish () even if an ordinary signal is
2627 case LIST_SUBCOMMAND
:
2628 read_and (list_archive
);
2631 case DIFF_SUBCOMMAND
:
2633 read_and (diff_archive
);
2636 case TEST_LABEL_SUBCOMMAND
:
2637 test_archive_label ();
2641 print_total_stats ();
2643 if (check_links_option
)
2646 if (volno_file_option
)
2647 closeout_volume_number ();
2649 /* Dispose of allocated memory, and return. */
2651 free (archive_name_array
);
2654 if (exit_status
== TAREXIT_FAILURE
)
2655 error (0, 0, _("Exiting with failure status due to previous errors"));
2657 if (stdlis
== stdout
)
2659 else if (ferror (stderr
) || fclose (stderr
) != 0)
2660 set_exit_status (TAREXIT_FAILURE
);
2666 tar_stat_init (struct tar_stat_info
*st
)
2668 memset (st
, 0, sizeof (*st
));
2672 tar_stat_destroy (struct tar_stat_info
*st
)
2674 free (st
->orig_file_name
);
2675 free (st
->file_name
);
2676 free (st
->link_name
);
2679 free (st
->sparse_map
);
2681 xheader_destroy (&st
->xhdr
);
2682 memset (st
, 0, sizeof (*st
));
2685 /* Format mask for all available formats that support nanosecond
2686 timestamp resolution. */
2687 #define NS_PRECISION_FORMAT_MASK FORMAT_MASK (POSIX_FORMAT)
2689 /* Same as timespec_cmp, but ignore nanoseconds if current archive
2690 format does not provide sufficient resolution. */
2692 tar_timespec_cmp (struct timespec a
, struct timespec b
)
2694 if (!(FORMAT_MASK (current_format
) & NS_PRECISION_FORMAT_MASK
))
2695 a
.tv_nsec
= b
.tv_nsec
= 0;
2696 return timespec_cmp (a
, b
);
2699 /* Set tar exit status to VAL, unless it is already indicating
2700 a more serious condition. This relies on the fact that the
2701 values of TAREXIT_ constants are ranged by severity. */
2703 set_exit_status (int val
)
2705 if (val
> exit_status
)