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