]> Dogcows Code - chaz/tar/blob - src/tar.c
Fix help output formatting. Thanks Benno Schulenberg.
[chaz/tar] / src / tar.c
1 /* A tar (tape archiver) program.
2
3 Copyright (C) 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1999, 2000,
4 2001, 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
5
6 Written by John Gilmore, starting 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
24 #include <fnmatch.h>
25 #include <getline.h>
26 #include <argp.h>
27 #include <argp-namefrob.h>
28 #include <argp-fmtstream.h>
29
30 #include <signal.h>
31 #if ! defined SIGCHLD && defined SIGCLD
32 # define SIGCHLD SIGCLD
33 #endif
34
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. */
39 #define GLOBAL
40 #include "common.h"
41
42 #include <argmatch.h>
43 #include <closeout.h>
44 #include <exitfail.h>
45 #include <getdate.h>
46 #include <localedir.h>
47 #include <rmt.h>
48 #include <prepargs.h>
49 #include <quotearg.h>
50 #include <version-etc.h>
51 #include <xstrtol.h>
52 #include <stdopen.h>
53
54 /* Local declarations. */
55
56 #ifndef DEFAULT_ARCHIVE_FORMAT
57 # define DEFAULT_ARCHIVE_FORMAT GNU_FORMAT
58 #endif
59
60 #ifndef DEFAULT_ARCHIVE
61 # define DEFAULT_ARCHIVE "tar.out"
62 #endif
63
64 #ifndef DEFAULT_BLOCKING
65 # define DEFAULT_BLOCKING 20
66 #endif
67
68 \f
69 /* Miscellaneous. */
70
71 /* Name of option using stdin. */
72 static const char *stdin_used_by;
73
74 /* Doesn't return if stdin already requested. */
75 void
76 request_stdin (const char *option)
77 {
78 if (stdin_used_by)
79 USAGE_ERROR ((0, 0, _("Options `-%s' and `-%s' both want standard input"),
80 stdin_used_by, option));
81
82 stdin_used_by = option;
83 }
84
85 extern int rpmatch (char const *response);
86
87 /* Returns true if and only if the user typed an affirmative response. */
88 int
89 confirm (const char *message_action, const char *message_name)
90 {
91 static FILE *confirm_file;
92 static int confirm_file_EOF;
93 bool status = false;
94
95 if (!confirm_file)
96 {
97 if (archive == 0 || stdin_used_by)
98 {
99 confirm_file = fopen (TTY_NAME, "r");
100 if (! confirm_file)
101 open_fatal (TTY_NAME);
102 }
103 else
104 {
105 request_stdin ("-w");
106 confirm_file = stdin;
107 }
108 }
109
110 fprintf (stdlis, "%s %s?", message_action, quote (message_name));
111 fflush (stdlis);
112
113 if (!confirm_file_EOF)
114 {
115 char *response = NULL;
116 size_t response_size = 0;
117 if (getline (&response, &response_size, confirm_file) < 0)
118 confirm_file_EOF = 1;
119 else
120 status = rpmatch (response) > 0;
121 free (response);
122 }
123
124 if (confirm_file_EOF)
125 {
126 fputc ('\n', stdlis);
127 fflush (stdlis);
128 }
129
130 return status;
131 }
132
133 static struct fmttab {
134 char const *name;
135 enum archive_format fmt;
136 } const fmttab[] = {
137 { "v7", V7_FORMAT },
138 { "oldgnu", OLDGNU_FORMAT },
139 { "ustar", USTAR_FORMAT },
140 { "posix", POSIX_FORMAT },
141 #if 0 /* not fully supported yet */
142 { "star", STAR_FORMAT },
143 #endif
144 { "gnu", GNU_FORMAT },
145 { "pax", POSIX_FORMAT }, /* An alias for posix */
146 { NULL, 0 }
147 };
148
149 static void
150 set_archive_format (char const *name)
151 {
152 struct fmttab const *p;
153
154 for (p = fmttab; strcmp (p->name, name) != 0; )
155 if (! (++p)->name)
156 USAGE_ERROR ((0, 0, _("%s: Invalid archive format"),
157 quotearg_colon (name)));
158
159 archive_format = p->fmt;
160 }
161
162 const char *
163 archive_format_string (enum archive_format fmt)
164 {
165 struct fmttab const *p;
166
167 for (p = fmttab; p->name; p++)
168 if (p->fmt == fmt)
169 return p->name;
170 return "unknown?";
171 }
172
173 #define FORMAT_MASK(n) (1<<(n))
174
175 static void
176 assert_format(unsigned fmt_mask)
177 {
178 if ((FORMAT_MASK (archive_format) & fmt_mask) == 0)
179 USAGE_ERROR ((0, 0,
180 _("GNU features wanted on incompatible archive format")));
181 }
182
183 const char *
184 subcommand_string (enum subcommand c)
185 {
186 switch (c)
187 {
188 case UNKNOWN_SUBCOMMAND:
189 return "unknown?";
190
191 case APPEND_SUBCOMMAND:
192 return "-r";
193
194 case CAT_SUBCOMMAND:
195 return "-A";
196
197 case CREATE_SUBCOMMAND:
198 return "-c";
199
200 case DELETE_SUBCOMMAND:
201 return "-D";
202
203 case DIFF_SUBCOMMAND:
204 return "-d";
205
206 case EXTRACT_SUBCOMMAND:
207 return "-x";
208
209 case LIST_SUBCOMMAND:
210 return "-t";
211
212 case UPDATE_SUBCOMMAND:
213 return "-u";
214
215 default:
216 abort ();
217 }
218 }
219
220 void
221 tar_list_quoting_styles (argp_fmtstream_t fs, char *prefix)
222 {
223 int i;
224
225 for (i = 0; quoting_style_args[i]; i++)
226 argp_fmtstream_printf (fs, "%s%s\n", prefix, quoting_style_args[i]);
227 }
228
229 void
230 tar_set_quoting_style (char *arg)
231 {
232 int i;
233
234 for (i = 0; quoting_style_args[i]; i++)
235 if (strcmp (arg, quoting_style_args[i]) == 0)
236 {
237 set_quoting_style (NULL, i);
238 return;
239 }
240 FATAL_ERROR ((0, 0,
241 _("Unknown quoting style `%s'. Try `%s --quoting-style=help' to get a list."), arg, program_invocation_short_name));
242 }
243
244 \f
245 /* Options. */
246
247 enum
248 {
249 ANCHORED_OPTION = CHAR_MAX + 1,
250 ATIME_PRESERVE_OPTION,
251 BACKUP_OPTION,
252 CHECKPOINT_OPTION,
253 DELAY_DIRECTORY_RESTORE_OPTION,
254 DELETE_OPTION,
255 EXCLUDE_CACHES_OPTION,
256 EXCLUDE_OPTION,
257 FORCE_LOCAL_OPTION,
258 GROUP_OPTION,
259 HANG_OPTION,
260 IGNORE_CASE_OPTION,
261 IGNORE_COMMAND_ERROR_OPTION,
262 IGNORE_FAILED_READ_OPTION,
263 INDEX_FILE_OPTION,
264 KEEP_NEWER_FILES_OPTION,
265 MODE_OPTION,
266 MTIME_OPTION,
267 NEWER_MTIME_OPTION,
268 NO_ANCHORED_OPTION,
269 NO_DELAY_DIRECTORY_RESTORE_OPTION,
270 NO_IGNORE_CASE_OPTION,
271 NO_IGNORE_COMMAND_ERROR_OPTION,
272 NO_OVERWRITE_DIR_OPTION,
273 NO_QUOTE_CHARS_OPTION,
274 NO_RECURSION_OPTION,
275 NO_SAME_OWNER_OPTION,
276 NO_SAME_PERMISSIONS_OPTION,
277 NO_UNQUOTE_OPTION,
278 NO_WILDCARDS_MATCH_SLASH_OPTION,
279 NO_WILDCARDS_OPTION,
280 NULL_OPTION,
281 NUMERIC_OWNER_OPTION,
282 OCCURRENCE_OPTION,
283 OLD_ARCHIVE_OPTION,
284 ONE_FILE_SYSTEM_OPTION,
285 OVERWRITE_DIR_OPTION,
286 OVERWRITE_OPTION,
287 OWNER_OPTION,
288 PAX_OPTION,
289 POSIX_OPTION,
290 PRESERVE_OPTION,
291 QUOTE_CHARS_OPTION,
292 QUOTING_STYLE_OPTION,
293 RECORD_SIZE_OPTION,
294 RECURSION_OPTION,
295 RECURSIVE_UNLINK_OPTION,
296 REMOVE_FILES_OPTION,
297 RESTRICT_OPTION,
298 RMT_COMMAND_OPTION,
299 RSH_COMMAND_OPTION,
300 SAME_OWNER_OPTION,
301 SHOW_DEFAULTS_OPTION,
302 SHOW_OMITTED_DIRS_OPTION,
303 SHOW_TRANSFORMED_NAMES_OPTION,
304 SPARSE_VERSION_OPTION,
305 STRIP_COMPONENTS_OPTION,
306 SUFFIX_OPTION,
307 TEST_LABEL_OPTION,
308 TOTALS_OPTION,
309 TO_COMMAND_OPTION,
310 TRANSFORM_OPTION,
311 UNQUOTE_OPTION,
312 USAGE_OPTION,
313 USE_COMPRESS_PROGRAM_OPTION,
314 UTC_OPTION,
315 VERSION_OPTION,
316 VOLNO_FILE_OPTION,
317 WILDCARDS_MATCH_SLASH_OPTION,
318 WILDCARDS_OPTION
319 };
320
321 const char *argp_program_version = "tar (" PACKAGE_NAME ") " VERSION;
322 const char *argp_program_bug_address = "<" PACKAGE_BUGREPORT ">";
323 static char const doc[] = N_("\
324 GNU `tar' saves many files together into a single tape or disk archive, \
325 and can restore individual files from the archive.\n\
326 \n\
327 Examples:\n\
328 tar -cf archive.tar foo bar # Create archive.tar from files foo and bar.\n\
329 tar -tvf archive.tar # List all files in archive.tar verbosely.\n\
330 tar -xf archive.tar # Extract all files from archive.tar.\n")
331 "\v"
332 N_("The backup suffix is `~', unless set with --suffix or SIMPLE_BACKUP_SUFFIX.\n\
333 The version control may be set with --backup or VERSION_CONTROL, values are:\n\n\
334 none, off never make backups\n\
335 t, numbered make numbered backups\n\
336 nil, existing numbered if numbered backups exist, simple otherwise\n\
337 never, simple always make simple backups\n");
338
339
340 /* NOTE:
341
342 Available option letters are DEIJQY and aeqy. Consider the following
343 assignments:
344
345 [For Solaris tar compatibility =/= Is it important at all?]
346 e exit immediately with a nonzero exit status if unexpected errors occur
347 E use extended headers (--format=posix)
348
349 [q alias for --occurrence=1 =/= this would better be used for quiet?]
350 [I same as T =/= will harm star compatibility]
351
352 y per-file gzip compression
353 Y per-block gzip compression */
354
355 static struct argp_option options[] = {
356 #define GRID 10
357 {NULL, 0, NULL, 0,
358 N_("Main operation mode:"), GRID },
359
360 {"list", 't', 0, 0,
361 N_("list the contents of an archive"), GRID+1 },
362 {"extract", 'x', 0, 0,
363 N_("extract files from an archive"), GRID+1 },
364 {"get", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
365 {"create", 'c', 0, 0,
366 N_("create a new archive"), GRID+1 },
367 {"diff", 'd', 0, 0,
368 N_("find differences between archive and file system"), GRID+1 },
369 {"compare", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
370 {"append", 'r', 0, 0,
371 N_("append files to the end of an archive"), GRID+1 },
372 {"update", 'u', 0, 0,
373 N_("only append files newer than copy in archive"), GRID+1 },
374 {"catenate", 'A', 0, 0,
375 N_("append tar files to an archive"), GRID+1 },
376 {"concatenate", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
377 {"delete", DELETE_OPTION, 0, 0,
378 N_("delete from the archive (not on mag tapes!)"), GRID+1 },
379 {"test-label", TEST_LABEL_OPTION, NULL, 0,
380 N_("test the archive volume label and exit"), GRID+1 },
381 #undef GRID
382
383 #define GRID 20
384 {NULL, 0, NULL, 0,
385 N_("Operation modifiers:"), GRID },
386
387 {"sparse", 'S', 0, 0,
388 N_("handle sparse files efficiently"), GRID+1 },
389 {"sparse-version", SPARSE_VERSION_OPTION, N_("MAJOR[.MINOR]"), 0,
390 N_("set version of the sparse format to use (implies --sparse)"), GRID+1},
391 {"incremental", 'G', 0, 0,
392 N_("handle old GNU-format incremental backup"), GRID+1 },
393 {"listed-incremental", 'g', N_("FILE"), 0,
394 N_("handle new GNU-format incremental backup"), GRID+1 },
395 {"ignore-failed-read", IGNORE_FAILED_READ_OPTION, 0, 0,
396 N_("do not exit with nonzero on unreadable files"), GRID+1 },
397 {"occurrence", OCCURRENCE_OPTION, N_("NUMBER"), OPTION_ARG_OPTIONAL,
398 N_("process only the NUMBERth occurrence of each file in the archive;"
399 " this option is valid only in conjunction with one of the subcommands"
400 " --delete, --diff, --extract or --list and when a list of files"
401 " is given either on the command line or via the -T option;"
402 " NUMBER defaults to 1"), GRID+1 },
403 {"seek", 'n', NULL, 0,
404 N_("archive is seekable"), GRID+1 },
405 #undef GRID
406
407 #define GRID 30
408 {NULL, 0, NULL, 0,
409 N_("Overwrite control:"), GRID },
410
411 {"verify", 'W', 0, 0,
412 N_("attempt to verify the archive after writing it"), GRID+1 },
413 {"remove-files", REMOVE_FILES_OPTION, 0, 0,
414 N_("remove files after adding them to the archive"), GRID+1 },
415 {"keep-old-files", 'k', 0, 0,
416 N_("don't replace existing files when extracting"), GRID+1 },
417 {"keep-newer-files", KEEP_NEWER_FILES_OPTION, 0, 0,
418 N_("don't replace existing files that are newer than their archive copies"), GRID+1 },
419 {"overwrite", OVERWRITE_OPTION, 0, 0,
420 N_("overwrite existing files when extracting"), GRID+1 },
421 {"unlink-first", 'U', 0, 0,
422 N_("remove each file prior to extracting over it"), GRID+1 },
423 {"recursive-unlink", RECURSIVE_UNLINK_OPTION, 0, 0,
424 N_("empty hierarchies prior to extracting directory"), GRID+1 },
425 {"no-overwrite-dir", NO_OVERWRITE_DIR_OPTION, 0, 0,
426 N_("preserve metadata of existing directories"), GRID+1 },
427 {"overwrite-dir", OVERWRITE_DIR_OPTION, 0, 0,
428 N_("overwrite metadata of existing directories when extracting (default)"),
429 GRID+1 },
430 #undef GRID
431
432 #define GRID 40
433 {NULL, 0, NULL, 0,
434 N_("Select output stream:"), GRID },
435
436 {"to-stdout", 'O', 0, 0,
437 N_("extract files to standard output"), GRID+1 },
438 {"to-command", TO_COMMAND_OPTION, N_("COMMAND"), 0,
439 N_("pipe extracted files to another program"), GRID+1 },
440 {"ignore-command-error", IGNORE_COMMAND_ERROR_OPTION, 0, 0,
441 N_("ignore exit codes of children"), GRID+1 },
442 {"no-ignore-command-error", NO_IGNORE_COMMAND_ERROR_OPTION, 0, 0,
443 N_("treat non-zero exit codes of children as error"), GRID+1 },
444 #undef GRID
445
446 #define GRID 50
447 {NULL, 0, NULL, 0,
448 N_("Handling of file attributes:"), GRID },
449
450 {"owner", OWNER_OPTION, N_("NAME"), 0,
451 N_("force NAME as owner for added files"), GRID+1 },
452 {"group", GROUP_OPTION, N_("NAME"), 0,
453 N_("force NAME as group for added files"), GRID+1 },
454 {"mtime", MTIME_OPTION, N_("DATE-OR-FILE"), 0,
455 N_("set mtime for added files from DATE-OR-FILE"), GRID+1 },
456 {"mode", MODE_OPTION, N_("CHANGES"), 0,
457 N_("force (symbolic) mode CHANGES for added files"), GRID+1 },
458 {"atime-preserve", ATIME_PRESERVE_OPTION,
459 N_("METHOD"), OPTION_ARG_OPTIONAL,
460 N_("preserve access times on dumped files, either by restoring the times"
461 " after reading (METHOD='replace'; default) or by not setting the times"
462 " in the first place (METHOD='system')"), GRID+1 },
463 {"touch", 'm', 0, 0,
464 N_("don't extract file modified time"), GRID+1 },
465 {"same-owner", SAME_OWNER_OPTION, 0, 0,
466 N_("try extracting files with the same ownership"), GRID+1 },
467 {"no-same-owner", NO_SAME_OWNER_OPTION, 0, 0,
468 N_("extract files as yourself"), GRID+1 },
469 {"numeric-owner", NUMERIC_OWNER_OPTION, 0, 0,
470 N_("always use numbers for user/group names"), GRID+1 },
471 {"preserve-permissions", 'p', 0, 0,
472 N_("extract information about file permissions (default for superuser)"),
473 GRID+1 },
474 {"same-permissions", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
475 {"no-same-permissions", NO_SAME_PERMISSIONS_OPTION, 0, 0,
476 N_("apply the user's umask when extracting permissions from the archive (default for ordinary users)"), GRID+1 },
477 {"preserve-order", 's', 0, 0,
478 N_("sort names to extract to match archive"), GRID+1 },
479 {"same-order", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
480 {"preserve", PRESERVE_OPTION, 0, 0,
481 N_("same as both -p and -s"), GRID+1 },
482 {"delay-directory-restore", DELAY_DIRECTORY_RESTORE_OPTION, 0, 0,
483 N_("delay setting modification times and permissions of extracted"
484 " directories until the end of extraction"), GRID+1 },
485 {"no-delay-directory-restore", NO_DELAY_DIRECTORY_RESTORE_OPTION, 0, 0,
486 N_("cancel the effect of --delay-directory-restore option"), GRID+1 },
487 #undef GRID
488
489 #define GRID 60
490 {NULL, 0, NULL, 0,
491 N_("Device selection and switching:"), GRID },
492
493 {"file", 'f', N_("ARCHIVE"), 0,
494 N_("use archive file or device ARCHIVE"), GRID+1 },
495 {"force-local", FORCE_LOCAL_OPTION, 0, 0,
496 N_("archive file is local even if it has a colon"), GRID+1 },
497 {"rmt-command", RMT_COMMAND_OPTION, N_("COMMAND"), 0,
498 N_("use given rmt COMMAND instead of rmt"), GRID+1 },
499 {"rsh-command", RSH_COMMAND_OPTION, N_("COMMAND"), 0,
500 N_("use remote COMMAND instead of rsh"), GRID+1 },
501 #ifdef DEVICE_PREFIX
502 {"-[0-7][lmh]", 0, NULL, OPTION_DOC, /* It is OK, since `name' will never be
503 translated */
504 N_("specify drive and density"), GRID+1 },
505 #endif
506 {NULL, '0', NULL, OPTION_HIDDEN, NULL, GRID+1 },
507 {NULL, '1', NULL, OPTION_HIDDEN, NULL, GRID+1 },
508 {NULL, '2', NULL, OPTION_HIDDEN, NULL, GRID+1 },
509 {NULL, '3', NULL, OPTION_HIDDEN, NULL, GRID+1 },
510 {NULL, '4', NULL, OPTION_HIDDEN, NULL, GRID+1 },
511 {NULL, '5', NULL, OPTION_HIDDEN, NULL, GRID+1 },
512 {NULL, '6', NULL, OPTION_HIDDEN, NULL, GRID+1 },
513 {NULL, '7', NULL, OPTION_HIDDEN, NULL, GRID+1 },
514 {NULL, '8', NULL, OPTION_HIDDEN, NULL, GRID+1 },
515 {NULL, '9', NULL, OPTION_HIDDEN, NULL, GRID+1 },
516
517 {"multi-volume", 'M', 0, 0,
518 N_("create/list/extract multi-volume archive"), GRID+1 },
519 {"tape-length", 'L', N_("NUMBER"), 0,
520 N_("change tape after writing NUMBER x 1024 bytes"), GRID+1 },
521 {"info-script", 'F', N_("NAME"), 0,
522 N_("run script at end of each tape (implies -M)"), GRID+1 },
523 {"new-volume-script", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
524 {"volno-file", VOLNO_FILE_OPTION, N_("FILE"), 0,
525 N_("use/update the volume number in FILE"), GRID+1 },
526 #undef GRID
527
528 #define GRID 70
529 {NULL, 0, NULL, 0,
530 N_("Device blocking:"), GRID },
531
532 {"blocking-factor", 'b', N_("BLOCKS"), 0,
533 N_("BLOCKS x 512 bytes per record"), GRID+1 },
534 {"record-size", RECORD_SIZE_OPTION, N_("NUMBER"), 0,
535 N_("NUMBER of bytes per record, multiple of 512"), GRID+1 },
536 {"ignore-zeros", 'i', 0, 0,
537 N_("ignore zeroed blocks in archive (means EOF)"), GRID+1 },
538 {"read-full-records", 'B', 0, 0,
539 N_("reblock as we read (for 4.2BSD pipes)"), GRID+1 },
540 #undef GRID
541
542 #define GRID 80
543 {NULL, 0, NULL, 0,
544 N_("Archive format selection:"), GRID },
545
546 {"format", 'H', N_("FORMAT"), 0,
547 N_("create archive of the given format"), GRID+1 },
548
549 {NULL, 0, NULL, 0, N_("FORMAT is one of the following:"), GRID+2 },
550 {" v7", 0, NULL, OPTION_DOC|OPTION_NO_TRANS, N_("old V7 tar format"),
551 GRID+3 },
552 {" oldgnu", 0, NULL, OPTION_DOC|OPTION_NO_TRANS,
553 N_("GNU format as per tar <= 1.12"), GRID+3 },
554 {" gnu", 0, NULL, OPTION_DOC|OPTION_NO_TRANS,
555 N_("GNU tar 1.13.x format"), GRID+3 },
556 {" ustar", 0, NULL, OPTION_DOC|OPTION_NO_TRANS,
557 N_("POSIX 1003.1-1988 (ustar) format"), GRID+3 },
558 {" pax", 0, NULL, OPTION_DOC|OPTION_NO_TRANS,
559 N_("POSIX 1003.1-2001 (pax) format"), GRID+3 },
560 {" posix", 0, NULL, OPTION_DOC|OPTION_NO_TRANS, N_("same as pax"), GRID+3 },
561
562 {"old-archive", OLD_ARCHIVE_OPTION, 0, 0, /* FIXME */
563 N_("same as --format=v7"), GRID+8 },
564 {"portability", 0, 0, OPTION_ALIAS, NULL, GRID+8 },
565 {"posix", POSIX_OPTION, 0, 0,
566 N_("same as --format=posix"), GRID+8 },
567 {"pax-option", PAX_OPTION, N_("keyword[[:]=value][,keyword[[:]=value]]..."), 0,
568 N_("control pax keywords"), GRID+8 },
569 {"label", 'V', N_("TEXT"), 0,
570 N_("create archive with volume name TEXT; at list/extract time, use TEXT as a globbing pattern for volume name"), GRID+8 },
571 {"bzip2", 'j', 0, 0,
572 N_("filter the archive through bzip2"), GRID+8 },
573 {"gzip", 'z', 0, 0,
574 N_("filter the archive through gzip"), GRID+8 },
575 {"gunzip", 0, 0, OPTION_ALIAS, NULL, GRID+8 },
576 {"ungzip", 0, 0, OPTION_ALIAS, NULL, GRID+8 },
577 {"compress", 'Z', 0, 0,
578 N_("filter the archive through compress"), GRID+8 },
579 {"uncompress", 0, 0, OPTION_ALIAS, NULL, GRID+8 },
580 {"use-compress-program", USE_COMPRESS_PROGRAM_OPTION, N_("PROG"), 0,
581 N_("filter through PROG (must accept -d)"), GRID+8 },
582 #undef GRID
583
584 #define GRID 90
585 {NULL, 0, NULL, 0,
586 N_("Local file selection:"), GRID },
587
588 {"add-file", ARGP_KEY_ARG, N_("FILE"), 0,
589 N_("add given FILE to the archive (useful if its name starts with a dash)"), GRID+1 },
590 {"directory", 'C', N_("DIR"), 0,
591 N_("change to directory DIR"), GRID+1 },
592 {"files-from", 'T', N_("FILE"), 0,
593 N_("get names to extract or create from FILE"), GRID+1 },
594 {"null", NULL_OPTION, 0, 0,
595 N_("-T reads null-terminated names, disable -C"), GRID+1 },
596 {"unquote", UNQUOTE_OPTION, 0, 0,
597 N_("unquote filenames read with -T (default)"), GRID+1 },
598 {"no-unquote", NO_UNQUOTE_OPTION, 0, 0,
599 N_("do not unquote filenames read with -T"), GRID+1 },
600 {"exclude", EXCLUDE_OPTION, N_("PATTERN"), 0,
601 N_("exclude files, given as a PATTERN"), GRID+1 },
602 {"exclude-from", 'X', N_("FILE"), 0,
603 N_("exclude patterns listed in FILE"), GRID+1 },
604 {"exclude-caches", EXCLUDE_CACHES_OPTION, 0, 0,
605 N_("exclude directories containing a cache tag"), GRID+1 },
606 {"no-recursion", NO_RECURSION_OPTION, 0, 0,
607 N_("avoid descending automatically in directories"), GRID+1 },
608 {"one-file-system", ONE_FILE_SYSTEM_OPTION, 0, 0,
609 N_("stay in local file system when creating archive"), GRID+1 },
610 {"recursion", RECURSION_OPTION, 0, 0,
611 N_("recurse into directories (default)"), GRID+1 },
612 {"absolute-names", 'P', 0, 0,
613 N_("don't strip leading `/'s from file names"), GRID+1 },
614 {"dereference", 'h', 0, 0,
615 N_("follow symlinks; archive and dump the files they point to"), GRID+1 },
616 {"starting-file", 'K', N_("MEMBER-NAME"), 0,
617 N_("begin at member MEMBER-NAME in the archive"), GRID+1 },
618 {"newer", 'N', N_("DATE-OR-FILE"), 0,
619 N_("only store files newer than DATE-OR-FILE"), GRID+1 },
620 {"after-date", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
621 {"newer-mtime", NEWER_MTIME_OPTION, N_("DATE"), 0,
622 N_("compare date and time when data changed only"), GRID+1 },
623 {"backup", BACKUP_OPTION, N_("CONTROL"), OPTION_ARG_OPTIONAL,
624 N_("backup before removal, choose version CONTROL"), GRID+1 },
625 {"suffix", SUFFIX_OPTION, N_("STRING"), 0,
626 N_("backup before removal, override usual suffix ('~' unless overridden by environment variable SIMPLE_BACKUP_SUFFIX)"), GRID+1 },
627 #undef GRID
628
629 #define GRID 92
630 {NULL, 0, NULL, 0,
631 N_("File name transformations:"), GRID },
632 {"strip-components", STRIP_COMPONENTS_OPTION, N_("NUMBER"), 0,
633 N_("strip NUMBER leading components from file names on extraction"),
634 GRID+1 },
635 {"transform", TRANSFORM_OPTION, N_("EXPRESSION"), 0,
636 N_("use sed replace EXPRESSION to transform file names"), GRID+1 },
637 #undef GRID
638
639 #define GRID 95
640 {NULL, 0, NULL, 0,
641 N_("File name matching options (affect both exclude and include patterns):"),
642 GRID },
643 {"ignore-case", IGNORE_CASE_OPTION, 0, 0,
644 N_("ignore case"), GRID+1 },
645 {"anchored", ANCHORED_OPTION, 0, 0,
646 N_("patterns match file name start"), GRID+1 },
647 {"no-anchored", NO_ANCHORED_OPTION, 0, 0,
648 N_("patterns match after any `/' (default for exclusion)"), GRID+1 },
649 {"no-ignore-case", NO_IGNORE_CASE_OPTION, 0, 0,
650 N_("case sensitive matching (default)"), GRID+1 },
651 {"wildcards", WILDCARDS_OPTION, 0, 0,
652 N_("use wildcards (default for exclusion)"), GRID+1 },
653 {"no-wildcards", NO_WILDCARDS_OPTION, 0, 0,
654 N_("verbatim string matching"), GRID+1 },
655 {"no-wildcards-match-slash", NO_WILDCARDS_MATCH_SLASH_OPTION, 0, 0,
656 N_("wildcards do not match `/'"), GRID+1 },
657 {"wildcards-match-slash", WILDCARDS_MATCH_SLASH_OPTION, 0, 0,
658 N_("wildcards match `/' (default for exclusion)"), GRID+1 },
659 #undef GRID
660
661 #define GRID 100
662 {NULL, 0, NULL, 0,
663 N_("Informative output:"), GRID },
664
665 {"verbose", 'v', 0, 0,
666 N_("verbosely list files processed"), GRID+1 },
667 {"checkpoint", CHECKPOINT_OPTION, N_("[.]NUMBER"), OPTION_ARG_OPTIONAL,
668 N_("display progress messages every NUMBERth record (default 10)"),
669 GRID+1 },
670 {"check-links", 'l', 0, 0,
671 N_("print a message if not all links are dumped"), GRID+1 },
672 {"totals", TOTALS_OPTION, N_("SIGNAL"), OPTION_ARG_OPTIONAL,
673 N_("print total bytes after processing the archive; "
674 "with an argument - print total bytes when this SIGNAL is delivered; "
675 "Allowed signals are: SIGHUP, SIGQUIT, SIGINT, SIGUSR1 and SIGUSR2; "
676 "the names without SIG prefix are also accepted"), GRID+1 },
677 {"utc", UTC_OPTION, 0, 0,
678 N_("print file modification dates in UTC"), GRID+1 },
679 {"index-file", INDEX_FILE_OPTION, N_("FILE"), 0,
680 N_("send verbose output to FILE"), GRID+1 },
681 {"block-number", 'R', 0, 0,
682 N_("show block number within archive with each message"), GRID+1 },
683 {"interactive", 'w', 0, 0,
684 N_("ask for confirmation for every action"), GRID+1 },
685 {"confirmation", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
686 {"show-defaults", SHOW_DEFAULTS_OPTION, 0, 0,
687 N_("show tar defaults"), GRID+1 },
688 {"show-omitted-dirs", SHOW_OMITTED_DIRS_OPTION, 0, 0,
689 N_("when listing or extracting, list each directory that does not match search criteria"), GRID+1 },
690 {"show-transformed-names", SHOW_TRANSFORMED_NAMES_OPTION, 0, 0,
691 N_("show file or archive names after transformation"),
692 GRID+1 },
693 {"show-stored-names", 0, 0, OPTION_ALIAS, NULL, GRID+1 },
694 {"quoting-style", QUOTING_STYLE_OPTION, N_("STYLE"), 0,
695 N_("set name quoting style; see below for valid STYLE values"), GRID+1 },
696 {"quote-chars", QUOTE_CHARS_OPTION, N_("STRING"), 0,
697 N_("additionally quote characters from STRING"), GRID+1 },
698 {"no-quote-chars", NO_QUOTE_CHARS_OPTION, N_("STRING"), 0,
699 N_("disable quoting for characters from STRING"), GRID+1 },
700 #undef GRID
701
702 #define GRID 110
703 {NULL, 0, NULL, 0,
704 N_("Compatibility options:"), GRID },
705
706 {NULL, 'o', 0, 0,
707 N_("when creating, same as --old-archive; when extracting, same as --no-same-owner"), GRID+1 },
708 #undef GRID
709
710 #define GRID 120
711 {NULL, 0, NULL, 0,
712 N_("Other options:"), GRID },
713
714 {"restrict", RESTRICT_OPTION, 0, 0,
715 N_("disable use of some potentially harmful options"), -1 },
716
717 {"help", '?', 0, 0, N_("give this help list"), -1},
718 {"usage", USAGE_OPTION, 0, 0, N_("give a short usage message"), -1},
719 {"version", VERSION_OPTION, 0, 0, N_("print program version"), -1},
720 /* FIXME -V (--label) conflicts with the default short option for
721 --version */
722 {"HANG", HANG_OPTION, "SECS", OPTION_ARG_OPTIONAL | OPTION_HIDDEN,
723 N_("hang for SECS seconds (default 3600)"), 0},
724 #undef GRID
725
726 {0, 0, 0, 0, 0, 0}
727 };
728
729 static char const *const atime_preserve_args[] =
730 {
731 "replace", "system", NULL
732 };
733
734 static enum atime_preserve const atime_preserve_types[] =
735 {
736 replace_atime_preserve, system_atime_preserve
737 };
738
739 /* Make sure atime_preserve_types has as much entries as atime_preserve_args
740 (minus 1 for NULL guard) */
741 ARGMATCH_VERIFY (atime_preserve_args, atime_preserve_types);
742
743 /* Wildcard matching settings */
744 enum wildcards
745 {
746 default_wildcards, /* For exclusion == enable_wildcards,
747 for inclusion == disable_wildcards */
748 disable_wildcards,
749 enable_wildcards
750 };
751
752 struct tar_args /* Variables used during option parsing */
753 {
754 struct textual_date *textual_date; /* Keeps the arguments to --newer-mtime
755 and/or --date option if they are
756 textual dates */
757 enum wildcards wildcards; /* Wildcard settings (--wildcards/
758 --no-wildcards) */
759 int matching_flags; /* exclude_fnmatch options */
760 int include_anchored; /* Pattern anchoring options used for
761 file inclusion */
762 bool o_option; /* True if -o option was given */
763 bool pax_option; /* True if --pax-option was given */
764 char const *backup_suffix_string; /* --suffix option argument */
765 char const *version_control_string; /* --backup option argument */
766 bool input_files; /* True if some input files where given */
767 };
768
769 #define MAKE_EXCL_OPTIONS(args) \
770 ((((args)->wildcards != disable_wildcards) ? EXCLUDE_WILDCARDS : 0) \
771 | (args)->matching_flags \
772 | recursion_option)
773
774 #define MAKE_INCL_OPTIONS(args) \
775 ((((args)->wildcards == enable_wildcards) ? EXCLUDE_WILDCARDS : 0) \
776 | (args)->include_anchored \
777 | (args)->matching_flags \
778 | recursion_option)
779
780 #ifdef REMOTE_SHELL
781 # define DECL_SHOW_DEFAULT_SETTINGS(stream, printer) \
782 { \
783 printer (stream, \
784 "--format=%s -f%s -b%d --quoting-style=%s --rmt-command=%s", \
785 archive_format_string (DEFAULT_ARCHIVE_FORMAT), \
786 DEFAULT_ARCHIVE, DEFAULT_BLOCKING, \
787 quoting_style_args[DEFAULT_QUOTING_STYLE], \
788 DEFAULT_RMT_COMMAND); \
789 printer (stream, " --rsh-command=%s", REMOTE_SHELL); \
790 printer (stream, "\n"); \
791 }
792 #else
793 # define DECL_SHOW_DEFAULT_SETTINGS(stream, printer) \
794 { \
795 printer (stream, \
796 "--format=%s -f%s -b%d --quoting-style=%s --rmt-command=%s", \
797 archive_format_string (DEFAULT_ARCHIVE_FORMAT), \
798 DEFAULT_ARCHIVE, DEFAULT_BLOCKING, \
799 quoting_style_args[DEFAULT_QUOTING_STYLE], \
800 DEFAULT_RMT_COMMAND); \
801 printer (stream, "\n"); \
802 }
803 #endif
804
805 static void
806 show_default_settings (FILE *fp)
807 DECL_SHOW_DEFAULT_SETTINGS(fp, fprintf)
808
809 static void
810 show_default_settings_fs (argp_fmtstream_t fs)
811 DECL_SHOW_DEFAULT_SETTINGS(fs, argp_fmtstream_printf)
812
813 static void
814 set_subcommand_option (enum subcommand subcommand)
815 {
816 if (subcommand_option != UNKNOWN_SUBCOMMAND
817 && subcommand_option != subcommand)
818 USAGE_ERROR ((0, 0,
819 _("You may not specify more than one `-Acdtrux' option")));
820
821 subcommand_option = subcommand;
822 }
823
824 static void
825 set_use_compress_program_option (const char *string)
826 {
827 if (use_compress_program_option
828 && strcmp (use_compress_program_option, string) != 0)
829 USAGE_ERROR ((0, 0, _("Conflicting compression options")));
830
831 use_compress_program_option = string;
832 }
833 \f
834 static RETSIGTYPE
835 sigstat (int signo)
836 {
837 compute_duration ();
838 print_total_stats ();
839 #ifndef HAVE_SIGACTION
840 signal (signo, sigstat);
841 #endif
842 }
843
844 static void
845 stat_on_signal (int signo)
846 {
847 #ifdef HAVE_SIGACTION
848 struct sigaction act;
849 act.sa_handler = sigstat;
850 sigemptyset (&act.sa_mask);
851 act.sa_flags = 0;
852 sigaction (signo, &act, NULL);
853 #else
854 signal (signo, sigstat);
855 #endif
856 }
857
858 void
859 set_stat_signal (const char *name)
860 {
861 static struct sigtab
862 {
863 char *name;
864 int signo;
865 } sigtab[] = {
866 { "SIGUSR1", SIGUSR1 },
867 { "USR1", SIGUSR1 },
868 { "SIGUSR2", SIGUSR2 },
869 { "USR2", SIGUSR2 },
870 { "SIGHUP", SIGHUP },
871 { "HUP", SIGHUP },
872 { "SIGINT", SIGINT },
873 { "INT", SIGINT },
874 { "SIGQUIT", SIGQUIT },
875 { "QUIT", SIGQUIT }
876 };
877 struct sigtab *p;
878
879 for (p = sigtab; p < sigtab + sizeof (sigtab) / sizeof (sigtab[0]); p++)
880 if (strcmp (p->name, name) == 0)
881 {
882 stat_on_signal (p->signo);
883 return;
884 }
885 FATAL_ERROR ((0, 0, _("Unknown signal name: %s"), name));
886 }
887
888 \f
889 struct textual_date
890 {
891 struct textual_date *next;
892 struct timespec *ts;
893 const char *option;
894 const char *date;
895 };
896
897 static void
898 get_date_or_file (struct tar_args *args, const char *option,
899 const char *str, struct timespec *ts)
900 {
901 if (FILE_SYSTEM_PREFIX_LEN (str) != 0
902 || ISSLASH (*str)
903 || *str == '.')
904 {
905 struct stat st;
906 if (deref_stat (dereference_option, str, &st) != 0)
907 {
908 stat_error (str);
909 USAGE_ERROR ((0, 0, _("Date sample file not found")));
910 }
911 *ts = get_stat_mtime (&st);
912 }
913 else
914 {
915 if (! get_date (ts, str, NULL))
916 {
917 WARN ((0, 0, _("Substituting %s for unknown date format %s"),
918 tartime (*ts, false), quote (str)));
919 ts->tv_nsec = 0;
920 }
921 else
922 {
923 struct textual_date *p = xmalloc (sizeof (*p));
924 p->ts = ts;
925 p->option = option;
926 p->date = str;
927 p->next = args->textual_date;
928 args->textual_date = p;
929 }
930 }
931 }
932
933 static void
934 report_textual_dates (struct tar_args *args)
935 {
936 struct textual_date *p;
937 for (p = args->textual_date; p; )
938 {
939 struct textual_date *next = p->next;
940 char const *treated_as = tartime (*p->ts, true);
941 if (strcmp (p->date, treated_as) != 0)
942 WARN ((0, 0, _("Option %s: Treating date `%s' as %s"),
943 p->option, p->date, treated_as));
944 free (p);
945 p = next;
946 }
947 }
948
949 \f
950 static volatile int _argp_hang;
951
952 enum read_file_list_state /* Result of reading file name from the list file */
953 {
954 file_list_success, /* OK, name read successfully */
955 file_list_end, /* End of list file */
956 file_list_zero /* Zero separator encountered where it should not */
957 };
958
959 /* Read from FP a sequence of characters up to FILENAME_TERMINATOR and put them
960 into STK.
961 */
962 static enum read_file_list_state
963 read_name_from_file (FILE *fp, struct obstack *stk)
964 {
965 int c;
966 size_t counter = 0;
967
968 for (c = getc (fp); c != EOF && c != filename_terminator; c = getc (fp))
969 {
970 if (c == 0)
971 {
972 /* We have read a zero separator. The file possibly is
973 zero-separated */
974 /* FATAL_ERROR((0, 0, N_("file name contains null character"))); */
975 return file_list_zero;
976 }
977 obstack_1grow (stk, c);
978 counter++;
979 }
980
981 obstack_1grow (stk, 0);
982
983 return (counter == 0 && c == EOF) ? file_list_end : file_list_success;
984 }
985
986 \f
987 static bool files_from_option; /* When set, tar will not refuse to create
988 empty archives */
989 static struct obstack argv_stk; /* Storage for additional command line options
990 read using -T option */
991
992 /* Prevent recursive inclusion of the same file */
993 struct file_id_list
994 {
995 struct file_id_list *next;
996 ino_t ino;
997 dev_t dev;
998 };
999
1000 static struct file_id_list *file_id_list;
1001
1002 static void
1003 add_file_id (const char *filename)
1004 {
1005 struct file_id_list *p;
1006 struct stat st;
1007
1008 if (stat (filename, &st))
1009 stat_fatal (filename);
1010 for (p = file_id_list; p; p = p->next)
1011 if (p->ino == st.st_ino && p->dev == st.st_dev)
1012 {
1013 FATAL_ERROR ((0, 0, _("%s: file list already read"),
1014 quotearg_colon (filename)));
1015 }
1016 p = xmalloc (sizeof *p);
1017 p->next = file_id_list;
1018 p->ino = st.st_ino;
1019 p->dev = st.st_dev;
1020 file_id_list = p;
1021 }
1022
1023 /* Default density numbers for [0-9][lmh] device specifications */
1024
1025 #ifndef LOW_DENSITY_NUM
1026 # define LOW_DENSITY_NUM 0
1027 #endif
1028
1029 #ifndef MID_DENSITY_NUM
1030 # define MID_DENSITY_NUM 8
1031 #endif
1032
1033 #ifndef HIGH_DENSITY_NUM
1034 # define HIGH_DENSITY_NUM 16
1035 #endif
1036
1037 static void
1038 update_argv (const char *filename, struct argp_state *state)
1039 {
1040 FILE *fp;
1041 size_t count = 0, i;
1042 char *start, *p;
1043 char **new_argv;
1044 size_t new_argc;
1045 bool is_stdin = false;
1046 enum read_file_list_state read_state;
1047
1048 if (!strcmp (filename, "-"))
1049 {
1050 is_stdin = true;
1051 request_stdin ("-T");
1052 fp = stdin;
1053 }
1054 else
1055 {
1056 add_file_id (filename);
1057 if ((fp = fopen (filename, "r")) == NULL)
1058 open_fatal (filename);
1059 }
1060
1061 while ((read_state = read_name_from_file (fp, &argv_stk)) == file_list_success)
1062 count++;
1063
1064 if (read_state == file_list_zero)
1065 {
1066 size_t size;
1067
1068 WARN ((0, 0, N_("%s: file name read contains nul character"),
1069 quotearg_colon (filename)));
1070
1071 /* Prepare new stack contents */
1072 size = obstack_object_size (&argv_stk);
1073 p = obstack_finish (&argv_stk);
1074 for (; size > 0; size--, p++)
1075 if (*p)
1076 obstack_1grow (&argv_stk, *p);
1077 else
1078 obstack_1grow (&argv_stk, '\n');
1079 obstack_1grow (&argv_stk, 0);
1080 count = 1;
1081
1082 /* Read rest of files using new filename terminator */
1083 filename_terminator = 0;
1084 while (read_name_from_file (fp, &argv_stk) == file_list_success)
1085 count++;
1086 }
1087
1088 if (!is_stdin)
1089 fclose (fp);
1090
1091 if (count == 0)
1092 return;
1093
1094 start = obstack_finish (&argv_stk);
1095
1096 if (filename_terminator == 0)
1097 for (p = start; *p; p += strlen (p) + 1)
1098 if (p[0] == '-')
1099 count++;
1100
1101 new_argc = state->argc + count;
1102 new_argv = xmalloc (sizeof (state->argv[0]) * (new_argc + 1));
1103 memcpy (new_argv, state->argv, sizeof (state->argv[0]) * (state->argc + 1));
1104 state->argv = new_argv;
1105 memmove (&state->argv[state->next + count], &state->argv[state->next],
1106 (state->argc - state->next + 1) * sizeof (state->argv[0]));
1107
1108 state->argc = new_argc;
1109
1110 for (i = state->next, p = start; *p; p += strlen (p) + 1, i++)
1111 {
1112 if (filename_terminator == 0 && p[0] == '-')
1113 state->argv[i++] = "--add-file";
1114 state->argv[i] = p;
1115 }
1116 }
1117
1118 \f
1119 static void
1120 tar_help (struct argp_state *state)
1121 {
1122 argp_fmtstream_t fs;
1123 state->flags |= ARGP_NO_EXIT;
1124 argp_state_help (state, state->out_stream,
1125 ARGP_HELP_STD_HELP & ~ARGP_HELP_BUG_ADDR);
1126 /* FIXME: use struct uparams.rmargin (from argp-help.c) instead of 79 */
1127 fs = argp_make_fmtstream (state->out_stream, 0, 79, 0);
1128
1129 argp_fmtstream_printf (fs, "\n%s\n\n",
1130 _("Valid arguments for --quoting-style options are:"));
1131 tar_list_quoting_styles (fs, " ");
1132
1133 argp_fmtstream_puts (fs, _("\n*This* tar defaults to:\n"));
1134 show_default_settings_fs (fs);
1135 argp_fmtstream_putc (fs, '\n');
1136 argp_fmtstream_printf (fs, _("Report bugs to %s.\n"),
1137 argp_program_bug_address);
1138 argp_fmtstream_free (fs);
1139 }
1140 \f
1141 static error_t
1142 parse_opt (int key, char *arg, struct argp_state *state)
1143 {
1144 struct tar_args *args = state->input;
1145
1146 switch (key)
1147 {
1148 case ARGP_KEY_ARG:
1149 /* File name or non-parsed option, because of ARGP_IN_ORDER */
1150 name_add_name (arg, MAKE_INCL_OPTIONS (args));
1151 args->input_files = true;
1152 break;
1153
1154 case 'A':
1155 set_subcommand_option (CAT_SUBCOMMAND);
1156 break;
1157
1158 case 'b':
1159 {
1160 uintmax_t u;
1161 if (! (xstrtoumax (arg, 0, 10, &u, "") == LONGINT_OK
1162 && u == (blocking_factor = u)
1163 && 0 < blocking_factor
1164 && u == (record_size = u * BLOCKSIZE) / BLOCKSIZE))
1165 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1166 _("Invalid blocking factor")));
1167 }
1168 break;
1169
1170 case 'B':
1171 /* Try to reblock input records. For reading 4.2BSD pipes. */
1172
1173 /* It would surely make sense to exchange -B and -R, but it seems
1174 that -B has been used for a long while in Sun tar and most
1175 BSD-derived systems. This is a consequence of the block/record
1176 terminology confusion. */
1177
1178 read_full_records_option = true;
1179 break;
1180
1181 case 'c':
1182 set_subcommand_option (CREATE_SUBCOMMAND);
1183 break;
1184
1185 case 'C':
1186 name_add_dir (arg);
1187 break;
1188
1189 case 'd':
1190 set_subcommand_option (DIFF_SUBCOMMAND);
1191 break;
1192
1193 case 'f':
1194 if (archive_names == allocated_archive_names)
1195 archive_name_array = x2nrealloc (archive_name_array,
1196 &allocated_archive_names,
1197 sizeof (archive_name_array[0]));
1198
1199 archive_name_array[archive_names++] = arg;
1200 break;
1201
1202 case 'F':
1203 /* Since -F is only useful with -M, make it implied. Run this
1204 script at the end of each tape. */
1205
1206 info_script_option = arg;
1207 multi_volume_option = true;
1208 break;
1209
1210 case 'g':
1211 listed_incremental_option = arg;
1212 after_date_option = true;
1213 /* Fall through. */
1214
1215 case 'G':
1216 /* We are making an incremental dump (FIXME: are we?); save
1217 directories at the beginning of the archive, and include in each
1218 directory its contents. */
1219
1220 incremental_option = true;
1221 break;
1222
1223 case 'h':
1224 /* Follow symbolic links. */
1225 dereference_option = true;
1226 break;
1227
1228 case 'i':
1229 /* Ignore zero blocks (eofs). This can't be the default,
1230 because Unix tar writes two blocks of zeros, then pads out
1231 the record with garbage. */
1232
1233 ignore_zeros_option = true;
1234 break;
1235
1236 case 'I':
1237 USAGE_ERROR ((0, 0,
1238 _("Warning: the -I option is not supported;"
1239 " perhaps you meant -j or -T?")));
1240 break;
1241
1242 case 'j':
1243 set_use_compress_program_option ("bzip2");
1244 break;
1245
1246 case 'k':
1247 /* Don't replace existing files. */
1248 old_files_option = KEEP_OLD_FILES;
1249 break;
1250
1251 case 'K':
1252 starting_file_option = true;
1253 addname (arg, 0);
1254 break;
1255
1256 case ONE_FILE_SYSTEM_OPTION:
1257 /* When dumping directories, don't dump files/subdirectories
1258 that are on other filesystems. */
1259 one_file_system_option = true;
1260 break;
1261
1262 case 'l':
1263 check_links_option = 1;
1264 break;
1265
1266 case 'L':
1267 {
1268 uintmax_t u;
1269 if (xstrtoumax (arg, 0, 10, &u, "") != LONGINT_OK)
1270 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1271 _("Invalid tape length")));
1272 tape_length_option = 1024 * (tarlong) u;
1273 multi_volume_option = true;
1274 }
1275 break;
1276
1277 case 'm':
1278 touch_option = true;
1279 break;
1280
1281 case 'M':
1282 /* Make multivolume archive: when we can't write any more into
1283 the archive, re-open it, and continue writing. */
1284
1285 multi_volume_option = true;
1286 break;
1287
1288 case MTIME_OPTION:
1289 get_date_or_file (args, "--mtime", arg, &mtime_option);
1290 set_mtime_option = true;
1291 break;
1292
1293 case 'n':
1294 seekable_archive = true;
1295 break;
1296
1297 case 'N':
1298 after_date_option = true;
1299 /* Fall through. */
1300
1301 case NEWER_MTIME_OPTION:
1302 if (NEWER_OPTION_INITIALIZED (newer_mtime_option))
1303 USAGE_ERROR ((0, 0, _("More than one threshold date")));
1304 get_date_or_file (args,
1305 key == NEWER_MTIME_OPTION ? "--newer-mtime"
1306 : "--after-date", arg, &newer_mtime_option);
1307 break;
1308
1309 case 'o':
1310 args->o_option = true;
1311 break;
1312
1313 case 'O':
1314 to_stdout_option = true;
1315 break;
1316
1317 case 'p':
1318 same_permissions_option = true;
1319 break;
1320
1321 case 'P':
1322 absolute_names_option = true;
1323 break;
1324
1325 case 'r':
1326 set_subcommand_option (APPEND_SUBCOMMAND);
1327 break;
1328
1329 case 'R':
1330 /* Print block numbers for debugging bad tar archives. */
1331
1332 /* It would surely make sense to exchange -B and -R, but it seems
1333 that -B has been used for a long while in Sun tar and most
1334 BSD-derived systems. This is a consequence of the block/record
1335 terminology confusion. */
1336
1337 block_number_option = true;
1338 break;
1339
1340 case 's':
1341 /* Names to extract are sorted. */
1342
1343 same_order_option = true;
1344 break;
1345
1346 case 'S':
1347 sparse_option = true;
1348 break;
1349
1350 case SPARSE_VERSION_OPTION:
1351 sparse_option = true;
1352 {
1353 char *p;
1354 tar_sparse_major = strtoul (arg, &p, 10);
1355 if (*p)
1356 {
1357 if (*p != '.')
1358 USAGE_ERROR ((0, 0, _("Invalid sparse version value")));
1359 tar_sparse_minor = strtoul (p + 1, &p, 10);
1360 if (*p)
1361 USAGE_ERROR ((0, 0, _("Invalid sparse version value")));
1362 }
1363 }
1364 break;
1365
1366 case 't':
1367 set_subcommand_option (LIST_SUBCOMMAND);
1368 verbose_option++;
1369 break;
1370
1371 case TEST_LABEL_OPTION:
1372 set_subcommand_option (LIST_SUBCOMMAND);
1373 test_label_option = true;
1374 break;
1375
1376 case 'T':
1377 update_argv (arg, state);
1378 /* Indicate we've been given -T option. This is for backward
1379 compatibility only, so that `tar cfT archive /dev/null will
1380 succeed */
1381 files_from_option = true;
1382 break;
1383
1384 case 'u':
1385 set_subcommand_option (UPDATE_SUBCOMMAND);
1386 break;
1387
1388 case 'U':
1389 old_files_option = UNLINK_FIRST_OLD_FILES;
1390 break;
1391
1392 case UTC_OPTION:
1393 utc_option = true;
1394 break;
1395
1396 case 'v':
1397 verbose_option++;
1398 break;
1399
1400 case 'V':
1401 volume_label_option = arg;
1402 break;
1403
1404 case 'w':
1405 interactive_option = true;
1406 break;
1407
1408 case 'W':
1409 verify_option = true;
1410 break;
1411
1412 case 'x':
1413 set_subcommand_option (EXTRACT_SUBCOMMAND);
1414 break;
1415
1416 case 'X':
1417 if (add_exclude_file (add_exclude, excluded, arg,
1418 MAKE_EXCL_OPTIONS (args), '\n')
1419 != 0)
1420 {
1421 int e = errno;
1422 FATAL_ERROR ((0, e, "%s", quotearg_colon (arg)));
1423 }
1424 break;
1425
1426 case 'z':
1427 set_use_compress_program_option ("gzip");
1428 break;
1429
1430 case 'Z':
1431 set_use_compress_program_option ("compress");
1432 break;
1433
1434 case ANCHORED_OPTION:
1435 args->matching_flags |= EXCLUDE_ANCHORED;
1436 break;
1437
1438 case ATIME_PRESERVE_OPTION:
1439 atime_preserve_option =
1440 (arg
1441 ? XARGMATCH ("--atime-preserve", arg,
1442 atime_preserve_args, atime_preserve_types)
1443 : replace_atime_preserve);
1444 if (! O_NOATIME && atime_preserve_option == system_atime_preserve)
1445 FATAL_ERROR ((0, 0,
1446 _("--atime-preserve='system' is not supported"
1447 " on this platform")));
1448 break;
1449
1450 case CHECKPOINT_OPTION:
1451 if (arg)
1452 {
1453 char *p;
1454
1455 if (*arg == '.')
1456 {
1457 checkpoint_style = checkpoint_dot;
1458 arg++;
1459 }
1460 checkpoint_option = strtoul (arg, &p, 0);
1461 if (*p)
1462 FATAL_ERROR ((0, 0,
1463 _("--checkpoint value is not an integer")));
1464 }
1465 else
1466 checkpoint_option = 10;
1467 break;
1468
1469 case BACKUP_OPTION:
1470 backup_option = true;
1471 if (arg)
1472 args->version_control_string = arg;
1473 break;
1474
1475 case DELAY_DIRECTORY_RESTORE_OPTION:
1476 delay_directory_restore_option = true;
1477 break;
1478
1479 case NO_DELAY_DIRECTORY_RESTORE_OPTION:
1480 delay_directory_restore_option = false;
1481 break;
1482
1483 case DELETE_OPTION:
1484 set_subcommand_option (DELETE_SUBCOMMAND);
1485 break;
1486
1487 case EXCLUDE_OPTION:
1488 add_exclude (excluded, arg, MAKE_EXCL_OPTIONS (args));
1489 break;
1490
1491 case EXCLUDE_CACHES_OPTION:
1492 exclude_caches_option = true;
1493 break;
1494
1495 case FORCE_LOCAL_OPTION:
1496 force_local_option = true;
1497 break;
1498
1499 case 'H':
1500 set_archive_format (arg);
1501 break;
1502
1503 case INDEX_FILE_OPTION:
1504 index_file_name = arg;
1505 break;
1506
1507 case IGNORE_CASE_OPTION:
1508 args->matching_flags |= FNM_CASEFOLD;
1509 break;
1510
1511 case IGNORE_COMMAND_ERROR_OPTION:
1512 ignore_command_error_option = true;
1513 break;
1514
1515 case IGNORE_FAILED_READ_OPTION:
1516 ignore_failed_read_option = true;
1517 break;
1518
1519 case KEEP_NEWER_FILES_OPTION:
1520 old_files_option = KEEP_NEWER_FILES;
1521 break;
1522
1523 case GROUP_OPTION:
1524 if (! (strlen (arg) < GNAME_FIELD_SIZE
1525 && gname_to_gid (arg, &group_option)))
1526 {
1527 uintmax_t g;
1528 if (xstrtoumax (arg, 0, 10, &g, "") == LONGINT_OK
1529 && g == (gid_t) g)
1530 group_option = g;
1531 else
1532 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1533 _("%s: Invalid group")));
1534 }
1535 break;
1536
1537 case MODE_OPTION:
1538 mode_option = mode_compile (arg);
1539 if (!mode_option)
1540 FATAL_ERROR ((0, 0, _("Invalid mode given on option")));
1541 initial_umask = umask (0);
1542 umask (initial_umask);
1543 break;
1544
1545 case NO_ANCHORED_OPTION:
1546 args->include_anchored = 0; /* Clear the default for comman line args */
1547 args->matching_flags &= ~ EXCLUDE_ANCHORED;
1548 break;
1549
1550 case NO_IGNORE_CASE_OPTION:
1551 args->matching_flags &= ~ FNM_CASEFOLD;
1552 break;
1553
1554 case NO_IGNORE_COMMAND_ERROR_OPTION:
1555 ignore_command_error_option = false;
1556 break;
1557
1558 case NO_OVERWRITE_DIR_OPTION:
1559 old_files_option = NO_OVERWRITE_DIR_OLD_FILES;
1560 break;
1561
1562 case NO_QUOTE_CHARS_OPTION:
1563 for (;*arg; arg++)
1564 set_char_quoting (NULL, *arg, 0);
1565 break;
1566
1567 case NO_WILDCARDS_OPTION:
1568 args->wildcards = disable_wildcards;
1569 break;
1570
1571 case NO_WILDCARDS_MATCH_SLASH_OPTION:
1572 args->matching_flags |= FNM_FILE_NAME;
1573 break;
1574
1575 case NULL_OPTION:
1576 filename_terminator = '\0';
1577 break;
1578
1579 case NUMERIC_OWNER_OPTION:
1580 numeric_owner_option = true;
1581 break;
1582
1583 case OCCURRENCE_OPTION:
1584 if (!arg)
1585 occurrence_option = 1;
1586 else
1587 {
1588 uintmax_t u;
1589 if (xstrtoumax (arg, 0, 10, &u, "") == LONGINT_OK)
1590 occurrence_option = u;
1591 else
1592 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1593 _("Invalid number")));
1594 }
1595 break;
1596
1597 case OVERWRITE_DIR_OPTION:
1598 old_files_option = DEFAULT_OLD_FILES;
1599 break;
1600
1601 case OVERWRITE_OPTION:
1602 old_files_option = OVERWRITE_OLD_FILES;
1603 break;
1604
1605 case OWNER_OPTION:
1606 if (! (strlen (arg) < UNAME_FIELD_SIZE
1607 && uname_to_uid (arg, &owner_option)))
1608 {
1609 uintmax_t u;
1610 if (xstrtoumax (arg, 0, 10, &u, "") == LONGINT_OK
1611 && u == (uid_t) u)
1612 owner_option = u;
1613 else
1614 FATAL_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1615 _("Invalid owner")));
1616 }
1617 break;
1618
1619 case QUOTE_CHARS_OPTION:
1620 for (;*arg; arg++)
1621 set_char_quoting (NULL, *arg, 1);
1622 break;
1623
1624 case QUOTING_STYLE_OPTION:
1625 tar_set_quoting_style (arg);
1626 break;
1627
1628 case PAX_OPTION:
1629 args->pax_option = true;
1630 xheader_set_option (arg);
1631 break;
1632
1633 case POSIX_OPTION:
1634 set_archive_format ("posix");
1635 break;
1636
1637 case PRESERVE_OPTION:
1638 /* FIXME: What it is good for? */
1639 same_permissions_option = true;
1640 same_order_option = true;
1641 break;
1642
1643 case RECORD_SIZE_OPTION:
1644 {
1645 uintmax_t u;
1646 if (! (xstrtoumax (arg, 0, 10, &u, "") == LONGINT_OK
1647 && u == (size_t) u))
1648 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1649 _("Invalid record size")));
1650 record_size = u;
1651 if (record_size % BLOCKSIZE != 0)
1652 USAGE_ERROR ((0, 0, _("Record size must be a multiple of %d."),
1653 BLOCKSIZE));
1654 blocking_factor = record_size / BLOCKSIZE;
1655 }
1656 break;
1657
1658 case RECURSIVE_UNLINK_OPTION:
1659 recursive_unlink_option = true;
1660 break;
1661
1662 case REMOVE_FILES_OPTION:
1663 remove_files_option = true;
1664 break;
1665
1666 case RESTRICT_OPTION:
1667 restrict_option = true;
1668 break;
1669
1670 case RMT_COMMAND_OPTION:
1671 rmt_command = arg;
1672 break;
1673
1674 case RSH_COMMAND_OPTION:
1675 rsh_command_option = arg;
1676 break;
1677
1678 case SHOW_DEFAULTS_OPTION:
1679 show_default_settings (stdout);
1680 close_stdout ();
1681 exit (0);
1682
1683 case STRIP_COMPONENTS_OPTION:
1684 {
1685 uintmax_t u;
1686 if (! (xstrtoumax (arg, 0, 10, &u, "") == LONGINT_OK
1687 && u == (size_t) u))
1688 USAGE_ERROR ((0, 0, "%s: %s", quotearg_colon (arg),
1689 _("Invalid number of elements")));
1690 strip_name_components = u;
1691 }
1692 break;
1693
1694 case SHOW_OMITTED_DIRS_OPTION:
1695 show_omitted_dirs_option = true;
1696 break;
1697
1698 case SHOW_TRANSFORMED_NAMES_OPTION:
1699 show_transformed_names_option = true;
1700 break;
1701
1702 case SUFFIX_OPTION:
1703 backup_option = true;
1704 args->backup_suffix_string = arg;
1705 break;
1706
1707 case TO_COMMAND_OPTION:
1708 if (to_command_option)
1709 USAGE_ERROR ((0, 0, _("Only one --to-command option allowed")));
1710 to_command_option = arg;
1711 break;
1712
1713 case TOTALS_OPTION:
1714 if (arg)
1715 set_stat_signal (arg);
1716 else
1717 totals_option = true;
1718 break;
1719
1720 case TRANSFORM_OPTION:
1721 set_transform_expr (arg);
1722 break;
1723
1724 case USE_COMPRESS_PROGRAM_OPTION:
1725 set_use_compress_program_option (arg);
1726 break;
1727
1728 case VOLNO_FILE_OPTION:
1729 volno_file_option = arg;
1730 break;
1731
1732 case WILDCARDS_OPTION:
1733 args->wildcards = enable_wildcards;
1734 break;
1735
1736 case WILDCARDS_MATCH_SLASH_OPTION:
1737 args->matching_flags &= ~ FNM_FILE_NAME;
1738 break;
1739
1740 case NO_RECURSION_OPTION:
1741 recursion_option = 0;
1742 break;
1743
1744 case NO_SAME_OWNER_OPTION:
1745 same_owner_option = -1;
1746 break;
1747
1748 case NO_SAME_PERMISSIONS_OPTION:
1749 same_permissions_option = -1;
1750 break;
1751
1752 case RECURSION_OPTION:
1753 recursion_option = FNM_LEADING_DIR;
1754 break;
1755
1756 case SAME_OWNER_OPTION:
1757 same_owner_option = 1;
1758 break;
1759
1760 case UNQUOTE_OPTION:
1761 unquote_option = true;
1762 break;
1763
1764 case NO_UNQUOTE_OPTION:
1765 unquote_option = false;
1766 break;
1767
1768 case '0':
1769 case '1':
1770 case '2':
1771 case '3':
1772 case '4':
1773 case '5':
1774 case '6':
1775 case '7':
1776
1777 #ifdef DEVICE_PREFIX
1778 {
1779 int device = key - '0';
1780 int density;
1781 static char buf[sizeof DEVICE_PREFIX + 10];
1782 char *cursor;
1783
1784 if (arg[1])
1785 argp_error (state, _("Malformed density argument: %s"), quote (arg));
1786
1787 strcpy (buf, DEVICE_PREFIX);
1788 cursor = buf + strlen (buf);
1789
1790 #ifdef DENSITY_LETTER
1791
1792 sprintf (cursor, "%d%c", device, arg[0]);
1793
1794 #else /* not DENSITY_LETTER */
1795
1796 switch (arg[0])
1797 {
1798 case 'l':
1799 device += LOW_DENSITY_NUM;
1800 break;
1801
1802 case 'm':
1803 device += MID_DENSITY_NUM;
1804 break;
1805
1806 case 'h':
1807 device += HIGH_DENSITY_NUM;
1808 break;
1809
1810 default:
1811 argp_error (state, _("Unknown density: `%c'"), arg[0]);
1812 }
1813 sprintf (cursor, "%d", device);
1814
1815 #endif /* not DENSITY_LETTER */
1816
1817 if (archive_names == allocated_archive_names)
1818 archive_name_array = x2nrealloc (archive_name_array,
1819 &allocated_archive_names,
1820 sizeof (archive_name_array[0]));
1821 archive_name_array[archive_names++] = xstrdup (buf);
1822 }
1823 break;
1824
1825 #else /* not DEVICE_PREFIX */
1826
1827 argp_error (state,
1828 _("Options `-[0-7][lmh]' not supported by *this* tar"));
1829
1830 #endif /* not DEVICE_PREFIX */
1831
1832 case '?':
1833 tar_help (state);
1834 close_stdout ();
1835 exit (0);
1836
1837 case USAGE_OPTION:
1838 argp_state_help (state, state->out_stream, ARGP_HELP_USAGE);
1839 close_stdout ();
1840 exit (0);
1841
1842 case VERSION_OPTION:
1843 version_etc (state->out_stream, "tar", PACKAGE_NAME, VERSION,
1844 "John Gilmore", "Jay Fenlason", (char *) NULL);
1845 close_stdout ();
1846 exit (0);
1847
1848 case HANG_OPTION:
1849 _argp_hang = atoi (arg ? arg : "3600");
1850 while (_argp_hang-- > 0)
1851 sleep (1);
1852 break;
1853
1854 default:
1855 return ARGP_ERR_UNKNOWN;
1856 }
1857 return 0;
1858 }
1859
1860 static struct argp argp = {
1861 options,
1862 parse_opt,
1863 N_("[FILE]..."),
1864 doc,
1865 NULL,
1866 NULL,
1867 NULL
1868 };
1869
1870 void
1871 usage (int status)
1872 {
1873 argp_help (&argp, stderr, ARGP_HELP_SEE, (char*) program_name);
1874 close_stdout ();
1875 exit (status);
1876 }
1877
1878 /* Parse the options for tar. */
1879
1880 static struct argp_option *
1881 find_argp_option (struct argp_option *options, int letter)
1882 {
1883 for (;
1884 !(options->name == NULL
1885 && options->key == 0
1886 && options->arg == 0
1887 && options->flags == 0
1888 && options->doc == NULL); options++)
1889 if (options->key == letter)
1890 return options;
1891 return NULL;
1892 }
1893
1894 static void
1895 decode_options (int argc, char **argv)
1896 {
1897 int index;
1898 struct tar_args args;
1899
1900 /* Set some default option values. */
1901 args.textual_date = NULL;
1902 args.wildcards = default_wildcards;
1903 args.matching_flags = 0;
1904 args.include_anchored = EXCLUDE_ANCHORED;
1905 args.o_option = false;
1906 args.pax_option = false;
1907 args.backup_suffix_string = getenv ("SIMPLE_BACKUP_SUFFIX");
1908 args.version_control_string = 0;
1909 args.input_files = false;
1910
1911 subcommand_option = UNKNOWN_SUBCOMMAND;
1912 archive_format = DEFAULT_FORMAT;
1913 blocking_factor = DEFAULT_BLOCKING;
1914 record_size = DEFAULT_BLOCKING * BLOCKSIZE;
1915 excluded = new_exclude ();
1916 newer_mtime_option.tv_sec = TYPE_MINIMUM (time_t);
1917 newer_mtime_option.tv_nsec = -1;
1918 recursion_option = FNM_LEADING_DIR;
1919 unquote_option = true;
1920 tar_sparse_major = 1;
1921 tar_sparse_minor = 0;
1922
1923 owner_option = -1;
1924 group_option = -1;
1925
1926 /* Convert old-style tar call by exploding option element and rearranging
1927 options accordingly. */
1928
1929 if (argc > 1 && argv[1][0] != '-')
1930 {
1931 int new_argc; /* argc value for rearranged arguments */
1932 char **new_argv; /* argv value for rearranged arguments */
1933 char *const *in; /* cursor into original argv */
1934 char **out; /* cursor into rearranged argv */
1935 const char *letter; /* cursor into old option letters */
1936 char buffer[3]; /* constructed option buffer */
1937
1938 /* Initialize a constructed option. */
1939
1940 buffer[0] = '-';
1941 buffer[2] = '\0';
1942
1943 /* Allocate a new argument array, and copy program name in it. */
1944
1945 new_argc = argc - 1 + strlen (argv[1]);
1946 new_argv = xmalloc ((new_argc + 1) * sizeof (char *));
1947 in = argv;
1948 out = new_argv;
1949 *out++ = *in++;
1950
1951 /* Copy each old letter option as a separate option, and have the
1952 corresponding argument moved next to it. */
1953
1954 for (letter = *in++; *letter; letter++)
1955 {
1956 struct argp_option *opt;
1957
1958 buffer[1] = *letter;
1959 *out++ = xstrdup (buffer);
1960 opt = find_argp_option (options, *letter);
1961 if (opt && opt->arg)
1962 {
1963 if (in < argv + argc)
1964 *out++ = *in++;
1965 else
1966 USAGE_ERROR ((0, 0, _("Old option `%c' requires an argument."),
1967 *letter));
1968 }
1969 }
1970
1971 /* Copy all remaining options. */
1972
1973 while (in < argv + argc)
1974 *out++ = *in++;
1975 *out = 0;
1976
1977 /* Replace the old option list by the new one. */
1978
1979 argc = new_argc;
1980 argv = new_argv;
1981 }
1982
1983 /* Parse all options and non-options as they appear. */
1984
1985 prepend_default_options (getenv ("TAR_OPTIONS"), &argc, &argv);
1986
1987 if (argp_parse (&argp, argc, argv, ARGP_IN_ORDER|ARGP_NO_HELP,
1988 &index, &args))
1989 exit (TAREXIT_FAILURE);
1990
1991
1992 /* Special handling for 'o' option:
1993
1994 GNU tar used to say "output old format".
1995 UNIX98 tar says don't chown files after extracting (we use
1996 "--no-same-owner" for this).
1997
1998 The old GNU tar semantics is retained when used with --create
1999 option, otherwise UNIX98 semantics is assumed */
2000
2001 if (args.o_option)
2002 {
2003 if (subcommand_option == CREATE_SUBCOMMAND)
2004 {
2005 /* GNU Tar <= 1.13 compatibility */
2006 set_archive_format ("v7");
2007 }
2008 else
2009 {
2010 /* UNIX98 compatibility */
2011 same_owner_option = -1;
2012 }
2013 }
2014
2015 /* Handle operands after any "--" argument. */
2016 for (; index < argc; index++)
2017 {
2018 name_add_name (argv[index], MAKE_INCL_OPTIONS (&args));
2019 args.input_files = true;
2020 }
2021
2022 /* Warn about implicit use of the wildcards in command line arguments.
2023 See TODO */
2024 warn_regex_usage = args.wildcards == default_wildcards;
2025
2026 /* Derive option values and check option consistency. */
2027
2028 if (archive_format == DEFAULT_FORMAT)
2029 {
2030 if (args.pax_option)
2031 archive_format = POSIX_FORMAT;
2032 else
2033 archive_format = DEFAULT_ARCHIVE_FORMAT;
2034 }
2035
2036 if ((volume_label_option && subcommand_option == CREATE_SUBCOMMAND)
2037 || incremental_option
2038 || multi_volume_option
2039 || sparse_option)
2040 assert_format (FORMAT_MASK (OLDGNU_FORMAT)
2041 | FORMAT_MASK (GNU_FORMAT)
2042 | FORMAT_MASK (POSIX_FORMAT));
2043
2044 if (occurrence_option)
2045 {
2046 if (!args.input_files)
2047 USAGE_ERROR ((0, 0,
2048 _("--occurrence is meaningless without a file list")));
2049 if (subcommand_option != DELETE_SUBCOMMAND
2050 && subcommand_option != DIFF_SUBCOMMAND
2051 && subcommand_option != EXTRACT_SUBCOMMAND
2052 && subcommand_option != LIST_SUBCOMMAND)
2053 USAGE_ERROR ((0, 0,
2054 _("--occurrence cannot be used in the requested operation mode")));
2055 }
2056
2057 if (seekable_archive && subcommand_option == DELETE_SUBCOMMAND)
2058 {
2059 /* The current code in delete.c is based on the assumption that
2060 skip_member() reads all data from the archive. So, we should
2061 make sure it won't use seeks. On the other hand, the same code
2062 depends on the ability to backspace a record in the archive,
2063 so setting seekable_archive to false is technically incorrect.
2064 However, it is tested only in skip_member(), so it's not a
2065 problem. */
2066 seekable_archive = false;
2067 }
2068
2069 if (archive_names == 0)
2070 {
2071 /* If no archive file name given, try TAPE from the environment, or
2072 else, DEFAULT_ARCHIVE from the configuration process. */
2073
2074 archive_names = 1;
2075 archive_name_array[0] = getenv ("TAPE");
2076 if (! archive_name_array[0])
2077 archive_name_array[0] = DEFAULT_ARCHIVE;
2078 }
2079
2080 /* Allow multiple archives only with `-M'. */
2081
2082 if (archive_names > 1 && !multi_volume_option)
2083 USAGE_ERROR ((0, 0,
2084 _("Multiple archive files require `-M' option")));
2085
2086 if (listed_incremental_option
2087 && NEWER_OPTION_INITIALIZED (newer_mtime_option))
2088 USAGE_ERROR ((0, 0,
2089 _("Cannot combine --listed-incremental with --newer")));
2090
2091 if (volume_label_option)
2092 {
2093 if (archive_format == GNU_FORMAT || archive_format == OLDGNU_FORMAT)
2094 {
2095 size_t volume_label_max_len =
2096 (sizeof current_header->header.name
2097 - 1 /* for trailing '\0' */
2098 - (multi_volume_option
2099 ? (sizeof " Volume "
2100 - 1 /* for null at end of " Volume " */
2101 + INT_STRLEN_BOUND (int) /* for volume number */
2102 - 1 /* for sign, as 0 <= volno */)
2103 : 0));
2104 if (volume_label_max_len < strlen (volume_label_option))
2105 USAGE_ERROR ((0, 0,
2106 ngettext ("%s: Volume label is too long (limit is %lu byte)",
2107 "%s: Volume label is too long (limit is %lu bytes)",
2108 volume_label_max_len),
2109 quotearg_colon (volume_label_option),
2110 (unsigned long) volume_label_max_len));
2111 }
2112 /* else FIXME
2113 Label length in PAX format is limited by the volume size. */
2114 }
2115
2116 if (verify_option)
2117 {
2118 if (multi_volume_option)
2119 USAGE_ERROR ((0, 0, _("Cannot verify multi-volume archives")));
2120 if (use_compress_program_option)
2121 USAGE_ERROR ((0, 0, _("Cannot verify compressed archives")));
2122 }
2123
2124 if (use_compress_program_option)
2125 {
2126 if (multi_volume_option)
2127 USAGE_ERROR ((0, 0, _("Cannot use multi-volume compressed archives")));
2128 if (subcommand_option == UPDATE_SUBCOMMAND
2129 || subcommand_option == APPEND_SUBCOMMAND
2130 || subcommand_option == DELETE_SUBCOMMAND)
2131 USAGE_ERROR ((0, 0, _("Cannot update compressed archives")));
2132 if (subcommand_option == CAT_SUBCOMMAND)
2133 USAGE_ERROR ((0, 0, _("Cannot concatenate compressed archives")));
2134 }
2135
2136 /* It is no harm to use --pax-option on non-pax archives in archive
2137 reading mode. It may even be useful, since it allows to override
2138 file attributes from tar headers. Therefore I allow such usage.
2139 --gray */
2140 if (args.pax_option
2141 && archive_format != POSIX_FORMAT
2142 && (subcommand_option != EXTRACT_SUBCOMMAND
2143 || subcommand_option != DIFF_SUBCOMMAND
2144 || subcommand_option != LIST_SUBCOMMAND))
2145 USAGE_ERROR ((0, 0, _("--pax-option can be used only on POSIX archives")));
2146
2147 /* If ready to unlink hierarchies, so we are for simpler files. */
2148 if (recursive_unlink_option)
2149 old_files_option = UNLINK_FIRST_OLD_FILES;
2150
2151
2152 if (test_label_option)
2153 {
2154 /* --test-label is silent if the user has specified the label name to
2155 compare against. */
2156 if (!args.input_files)
2157 verbose_option++;
2158 }
2159 else if (utc_option)
2160 verbose_option = 2;
2161
2162 /* Forbid using -c with no input files whatsoever. Check that `-f -',
2163 explicit or implied, is used correctly. */
2164
2165 switch (subcommand_option)
2166 {
2167 case CREATE_SUBCOMMAND:
2168 if (!args.input_files && !files_from_option)
2169 USAGE_ERROR ((0, 0,
2170 _("Cowardly refusing to create an empty archive")));
2171 break;
2172
2173 case EXTRACT_SUBCOMMAND:
2174 case LIST_SUBCOMMAND:
2175 case DIFF_SUBCOMMAND:
2176 for (archive_name_cursor = archive_name_array;
2177 archive_name_cursor < archive_name_array + archive_names;
2178 archive_name_cursor++)
2179 if (!strcmp (*archive_name_cursor, "-"))
2180 request_stdin ("-f");
2181 break;
2182
2183 case CAT_SUBCOMMAND:
2184 case UPDATE_SUBCOMMAND:
2185 case APPEND_SUBCOMMAND:
2186 for (archive_name_cursor = archive_name_array;
2187 archive_name_cursor < archive_name_array + archive_names;
2188 archive_name_cursor++)
2189 if (!strcmp (*archive_name_cursor, "-"))
2190 USAGE_ERROR ((0, 0,
2191 _("Options `-Aru' are incompatible with `-f -'")));
2192
2193 default:
2194 break;
2195 }
2196
2197 /* Initialize stdlis */
2198 if (index_file_name)
2199 {
2200 stdlis = fopen (index_file_name, "w");
2201 if (! stdlis)
2202 open_error (index_file_name);
2203 }
2204 else
2205 stdlis = to_stdout_option ? stderr : stdout;
2206
2207 archive_name_cursor = archive_name_array;
2208
2209 /* Prepare for generating backup names. */
2210
2211 if (args.backup_suffix_string)
2212 simple_backup_suffix = xstrdup (args.backup_suffix_string);
2213
2214 if (backup_option)
2215 {
2216 backup_type = xget_version ("--backup", args.version_control_string);
2217 /* No backup is needed either if explicitely disabled or if
2218 the extracted files are not being written to disk. */
2219 if (backup_type == no_backups || EXTRACT_OVER_PIPE)
2220 backup_option = false;
2221 }
2222
2223 if (verbose_option)
2224 report_textual_dates (&args);
2225 }
2226
2227 \f
2228 /* Tar proper. */
2229
2230 /* Main routine for tar. */
2231 int
2232 main (int argc, char **argv)
2233 {
2234 set_start_time ();
2235 program_name = argv[0];
2236
2237 setlocale (LC_ALL, "");
2238 bindtextdomain (PACKAGE, LOCALEDIR);
2239 textdomain (PACKAGE);
2240
2241 exit_failure = TAREXIT_FAILURE;
2242 exit_status = TAREXIT_SUCCESS;
2243 filename_terminator = '\n';
2244 set_quoting_style (0, DEFAULT_QUOTING_STYLE);
2245
2246 /* Make sure we have first three descriptors available */
2247 stdopen ();
2248
2249 /* Close all inherited open descriptors, except for the first three */
2250 closeopen ();
2251
2252 /* Pre-allocate a few structures. */
2253
2254 allocated_archive_names = 10;
2255 archive_name_array =
2256 xmalloc (sizeof (const char *) * allocated_archive_names);
2257 archive_names = 0;
2258
2259 obstack_init (&argv_stk);
2260
2261 #ifdef SIGCHLD
2262 /* System V fork+wait does not work if SIGCHLD is ignored. */
2263 signal (SIGCHLD, SIG_DFL);
2264 #endif
2265
2266 /* Decode options. */
2267
2268 decode_options (argc, argv);
2269 name_init ();
2270
2271 /* Main command execution. */
2272
2273 if (volno_file_option)
2274 init_volume_number ();
2275
2276 switch (subcommand_option)
2277 {
2278 case UNKNOWN_SUBCOMMAND:
2279 USAGE_ERROR ((0, 0,
2280 _("You must specify one of the `-Acdtrux' options")));
2281
2282 case CAT_SUBCOMMAND:
2283 case UPDATE_SUBCOMMAND:
2284 case APPEND_SUBCOMMAND:
2285 update_archive ();
2286 break;
2287
2288 case DELETE_SUBCOMMAND:
2289 delete_archive_members ();
2290 break;
2291
2292 case CREATE_SUBCOMMAND:
2293 create_archive ();
2294 break;
2295
2296 case EXTRACT_SUBCOMMAND:
2297 extr_init ();
2298 read_and (extract_archive);
2299
2300 /* FIXME: should extract_finish () even if an ordinary signal is
2301 received. */
2302 extract_finish ();
2303
2304 break;
2305
2306 case LIST_SUBCOMMAND:
2307 read_and (list_archive);
2308 break;
2309
2310 case DIFF_SUBCOMMAND:
2311 diff_init ();
2312 read_and (diff_archive);
2313 break;
2314 }
2315
2316 if (totals_option)
2317 print_total_stats ();
2318
2319 if (check_links_option)
2320 check_links ();
2321
2322 if (volno_file_option)
2323 closeout_volume_number ();
2324
2325 /* Dispose of allocated memory, and return. */
2326
2327 free (archive_name_array);
2328 name_term ();
2329
2330 if (exit_status == TAREXIT_FAILURE)
2331 error (0, 0, _("Error exit delayed from previous errors"));
2332
2333 if (stdlis == stdout)
2334 close_stdout ();
2335 else if (ferror (stderr) || fclose (stderr) != 0)
2336 exit_status = TAREXIT_FAILURE;
2337
2338 return exit_status;
2339 }
2340
2341 void
2342 tar_stat_init (struct tar_stat_info *st)
2343 {
2344 memset (st, 0, sizeof (*st));
2345 }
2346
2347 void
2348 tar_stat_destroy (struct tar_stat_info *st)
2349 {
2350 free (st->orig_file_name);
2351 free (st->file_name);
2352 free (st->link_name);
2353 free (st->uname);
2354 free (st->gname);
2355 free (st->sparse_map);
2356 free (st->dumpdir);
2357 memset (st, 0, sizeof (*st));
2358 }
2359
2360 /* Format mask for all available formats that support nanosecond
2361 timestamp resolution. */
2362 #define NS_PRECISION_FORMAT_MASK FORMAT_MASK (POSIX_FORMAT)
2363
2364 /* Same as timespec_cmp, but ignore nanoseconds if current archive
2365 format does not provide sufficient resolution. */
2366 int
2367 tar_timespec_cmp (struct timespec a, struct timespec b)
2368 {
2369 if (!(FORMAT_MASK (current_format) & NS_PRECISION_FORMAT_MASK))
2370 a.tv_nsec = b.tv_nsec = 0;
2371 return timespec_cmp (a, b);
2372 }
This page took 0.143807 seconds and 5 git commands to generate.