]> Dogcows Code - chaz/tar/blob - src/extract.c
(struct delayed_symlinks, extract_archive, apply_delayed_symlinks):
[chaz/tar] / src / extract.c
1 /* Extract files from a tar archive.
2
3 Copyright 1988, 1992, 1993, 1994, 1996, 1997, 1998, 1999, 2000,
4 2001 Free Software Foundation, Inc.
5
6 Written by John Gilmore, on 1985-11-19.
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 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
21
22 #include "system.h"
23 #include <quotearg.h>
24
25 #if HAVE_UTIME_H
26 # include <utime.h>
27 #else
28 struct utimbuf
29 {
30 long actime;
31 long modtime;
32 };
33 #endif
34
35 #include "common.h"
36
37 int we_are_root; /* true if our effective uid == 0 */
38 static mode_t newdir_umask; /* umask when creating new directories */
39 static mode_t current_umask; /* current umask (which is set to 0 if -p) */
40
41 /* Status of the permissions of a file that we are extracting. */
42 enum permstatus
43 {
44 /* This file may have existed already; its permissions are unknown. */
45 UNKNOWN_PERMSTATUS,
46
47 /* This file was created using the permissions from the archive. */
48 ARCHIVED_PERMSTATUS,
49
50 /* This is an intermediate directory; the archive did not specify
51 its permissions. */
52 INTERDIR_PERMSTATUS
53 };
54
55 /* List of directories whose statuses we need to extract after we've
56 finished extracting their subsidiary files. The head of the list
57 has the longest name; each non-head element in the list is an
58 ancestor (in the directory hierarchy) of the preceding element. */
59 struct delayed_set_stat
60 {
61 struct delayed_set_stat *next;
62 struct stat stat_info;
63 size_t file_name_len;
64 mode_t invert_permissions;
65 enum permstatus permstatus;
66 char file_name[1];
67 };
68
69 static struct delayed_set_stat *delayed_set_stat_head;
70
71 /* List of symbolic links whose creation we have delayed. */
72 struct delayed_symlink
73 {
74 /* The next delayed symbolic link in the list. */
75 struct delayed_symlink *next;
76
77 /* The device, inode number and last-modified time of the placeholder. */
78 dev_t dev;
79 ino_t ino;
80 time_t mtime;
81
82 /* The desired owner and group of the symbolic link. */
83 uid_t uid;
84 gid_t gid;
85
86 /* A list of sources for this symlink. The sources are all to be
87 hard-linked together. */
88 struct string_list *sources;
89
90 /* The desired target of the desired link. */
91 char target[1];
92 };
93
94 static struct delayed_symlink *delayed_symlink_head;
95
96 struct string_list
97 {
98 struct string_list *next;
99 char string[1];
100 };
101
102 /* Set up to extract files. */
103 void
104 extr_init (void)
105 {
106 we_are_root = geteuid () == 0;
107 same_permissions_option += we_are_root;
108 same_owner_option += we_are_root;
109 xalloc_fail_func = extract_finish;
110
111 /* Option -p clears the kernel umask, so it does not affect proper
112 restoration of file permissions. New intermediate directories will
113 comply with umask at start of program. */
114
115 newdir_umask = umask (0);
116 if (0 < same_permissions_option)
117 current_umask = 0;
118 else
119 {
120 umask (newdir_umask); /* restore the kernel umask */
121 current_umask = newdir_umask;
122 }
123 }
124
125 /* If restoring permissions, restore the mode for FILE_NAME from
126 information given in *STAT_INFO; otherwise invert the
127 INVERT_PERMISSIONS bits from the file's current permissions.
128 PERMSTATUS specifies the status of the file's permissions.
129 TYPEFLAG specifies the type of the file. */
130 static void
131 set_mode (char const *file_name, struct stat const *stat_info,
132 mode_t invert_permissions, enum permstatus permstatus,
133 char typeflag)
134 {
135 mode_t mode;
136
137 if (0 < same_permissions_option
138 && permstatus != INTERDIR_PERMSTATUS)
139 {
140 mode = stat_info->st_mode;
141
142 /* If we created the file and it has a usual mode, then its mode
143 is normally set correctly already. But on many hosts, some
144 directories inherit the setgid bits from their parents, so we
145 we must set directories' modes explicitly. */
146 if (permstatus == ARCHIVED_PERMSTATUS
147 && ! (mode & ~ MODE_RWX)
148 && typeflag != DIRTYPE
149 && typeflag != GNUTYPE_DUMPDIR)
150 return;
151 }
152 else if (! invert_permissions)
153 return;
154 else
155 {
156 /* We must inspect a directory's current permissions, since the
157 directory may have inherited its setgid bit from its parent.
158
159 INVERT_PERMISSIONS happens to be nonzero only for directories
160 that we created, so there's no point optimizing this code for
161 other cases. */
162 struct stat st;
163 if (stat (file_name, &st) != 0)
164 {
165 stat_error (file_name);
166 return;
167 }
168 mode = st.st_mode ^ invert_permissions;
169 }
170
171 if (chmod (file_name, mode) != 0)
172 chmod_error_details (file_name, mode);
173 }
174
175 /* Check time after successfully setting FILE_NAME's time stamp to T. */
176 static void
177 check_time (char const *file_name, time_t t)
178 {
179 time_t now;
180 if (start_time < t && (now = time (0)) < t)
181 WARN ((0, 0, _("%s: time stamp %s is %lu s in the future"),
182 file_name, tartime (t), (unsigned long) (t - now)));
183 }
184
185 /* Restore stat attributes (owner, group, mode and times) for
186 FILE_NAME, using information given in *STAT_INFO.
187 If not restoring permissions, invert the
188 INVERT_PERMISSIONS bits from the file's current permissions.
189 PERMSTATUS specifies the status of the file's permissions.
190 TYPEFLAG specifies the type of the file. */
191
192 /* FIXME: About proper restoration of symbolic link attributes, we still do
193 not have it right. Pretesters' reports tell us we need further study and
194 probably more configuration. For now, just use lchown if it exists, and
195 punt for the rest. Sigh! */
196
197 static void
198 set_stat (char const *file_name, struct stat const *stat_info,
199 mode_t invert_permissions, enum permstatus permstatus,
200 char typeflag)
201 {
202 struct utimbuf utimbuf;
203
204 if (typeflag != SYMTYPE)
205 {
206 /* We do the utime before the chmod because some versions of utime are
207 broken and trash the modes of the file. */
208
209 if (! touch_option && permstatus != INTERDIR_PERMSTATUS)
210 {
211 /* We set the accessed time to `now', which is really the time we
212 started extracting files, unless incremental_option is used, in
213 which case .st_atime is used. */
214
215 /* FIXME: incremental_option should set ctime too, but how? */
216
217 if (incremental_option)
218 utimbuf.actime = stat_info->st_atime;
219 else
220 utimbuf.actime = start_time;
221
222 utimbuf.modtime = stat_info->st_mtime;
223
224 if (utime (file_name, &utimbuf) < 0)
225 utime_error (file_name);
226 else
227 {
228 check_time (file_name, stat_info->st_atime);
229 check_time (file_name, stat_info->st_mtime);
230 }
231 }
232
233 /* Some systems allow non-root users to give files away. Once this
234 done, it is not possible anymore to change file permissions, so we
235 have to set permissions prior to possibly giving files away. */
236
237 set_mode (file_name, stat_info,
238 invert_permissions, permstatus, typeflag);
239 }
240
241 if (0 < same_owner_option && permstatus != INTERDIR_PERMSTATUS)
242 {
243 /* When lchown exists, it should be used to change the attributes of
244 the symbolic link itself. In this case, a mere chown would change
245 the attributes of the file the symbolic link is pointing to, and
246 should be avoided. */
247
248 if (typeflag == SYMTYPE)
249 {
250 #if HAVE_LCHOWN
251 if (lchown (file_name, stat_info->st_uid, stat_info->st_gid) < 0)
252 chown_error_details (file_name,
253 stat_info->st_uid, stat_info->st_gid);
254 #endif
255 }
256 else
257 {
258 if (chown (file_name, stat_info->st_uid, stat_info->st_gid) < 0)
259 chown_error_details (file_name,
260 stat_info->st_uid, stat_info->st_gid);
261
262 /* On a few systems, and in particular, those allowing to give files
263 away, changing the owner or group destroys the suid or sgid bits.
264 So let's attempt setting these bits once more. */
265 if (stat_info->st_mode & (S_ISUID | S_ISGID | S_ISVTX))
266 set_mode (file_name, stat_info,
267 invert_permissions, permstatus, typeflag);
268 }
269 }
270 }
271
272 /* Remember to restore stat attributes (owner, group, mode and times)
273 for the directory FILE_NAME, using information given in *STAT_INFO,
274 once we stop extracting files into that directory.
275 If not restoring permissions, remember to invert the
276 INVERT_PERMISSIONS bits from the file's current permissions.
277 PERMSTATUS specifies the status of the file's permissions. */
278 static void
279 delay_set_stat (char const *file_name, struct stat const *stat_info,
280 mode_t invert_permissions, enum permstatus permstatus)
281 {
282 size_t file_name_len = strlen (file_name);
283 struct delayed_set_stat *data =
284 xmalloc (offsetof (struct delayed_set_stat, file_name) + file_name_len);
285 data->file_name_len = file_name_len;
286 strcpy (data->file_name, file_name);
287 data->invert_permissions = invert_permissions;
288 data->permstatus = permstatus;
289 data->stat_info = *stat_info;
290 data->next = delayed_set_stat_head;
291 delayed_set_stat_head = data;
292 }
293
294 /* Update the delayed_set_stat info for an intermediate directory
295 created on the path to DIR_NAME. The intermediate directory turned
296 out to be the same as this directory, e.g. due to ".." or symbolic
297 links. *DIR_STAT_INFO is the status of the directory. */
298 static void
299 repair_delayed_set_stat (char const *dir_name,
300 struct stat const *dir_stat_info)
301 {
302 struct delayed_set_stat *data;
303 for (data = delayed_set_stat_head; data; data = data->next)
304 {
305 struct stat st;
306 if (stat (data->file_name, &st) != 0)
307 {
308 stat_error (data->file_name);
309 return;
310 }
311
312 if (st.st_dev == dir_stat_info->st_dev
313 && st.st_ino == dir_stat_info->st_ino)
314 {
315 data->stat_info = current_stat;
316 data->invert_permissions = (MODE_RWX
317 & (current_stat.st_mode ^ st.st_mode));
318 data->permstatus = ARCHIVED_PERMSTATUS;
319 return;
320 }
321 }
322
323 ERROR ((0, 0, _("%s: Unexpected inconsistency when making directory"),
324 quotearg_colon (dir_name)));
325 }
326
327 /* After a file/link/symlink/directory creation has failed, see if
328 it's because some required directory was not present, and if so,
329 create all required directories. Return non-zero if a directory
330 was created. */
331 static int
332 make_directories (char *file_name)
333 {
334 char *cursor0 = file_name + FILESYSTEM_PREFIX_LEN (file_name);
335 char *cursor; /* points into path */
336 int did_something = 0; /* did we do anything yet? */
337 int mode;
338 int invert_permissions;
339 int status;
340
341
342 for (cursor = cursor0; *cursor; cursor++)
343 {
344 if (! ISSLASH (*cursor))
345 continue;
346
347 /* Avoid mkdir of empty string, if leading or double '/'. */
348
349 if (cursor == cursor0 || ISSLASH (cursor[-1]))
350 continue;
351
352 /* Avoid mkdir where last part of path is "." or "..". */
353
354 if (cursor[-1] == '.'
355 && (cursor == cursor0 + 1 || ISSLASH (cursor[-2])
356 || (cursor[-2] == '.'
357 && (cursor == cursor0 + 2 || ISSLASH (cursor[-3])))))
358 continue;
359
360 *cursor = '\0'; /* truncate the path there */
361 mode = MODE_RWX & ~ newdir_umask;
362 invert_permissions = we_are_root ? 0 : MODE_WXUSR & ~ mode;
363 status = mkdir (file_name, mode ^ invert_permissions);
364
365 if (status == 0)
366 {
367 /* Create a struct delayed_set_stat even if
368 invert_permissions is zero, because
369 repair_delayed_set_stat may need to update the struct. */
370 delay_set_stat (file_name,
371 &current_stat /* ignored */,
372 invert_permissions, INTERDIR_PERMSTATUS);
373
374 print_for_mkdir (file_name, cursor - file_name, mode);
375 did_something = 1;
376
377 *cursor = '/';
378 continue;
379 }
380
381 *cursor = '/';
382
383 if (errno == EEXIST
384 #if MSDOS
385 /* Turbo C mkdir gives a funny errno. */
386 || errno == EACCES
387 #endif
388 )
389 /* Directory already exists. */
390 continue;
391
392 /* Some other error in the mkdir. We return to the caller. */
393 break;
394 }
395
396 return did_something; /* tell them to retry if we made one */
397 }
398
399 /* Prepare to extract a file.
400 Return zero if extraction should not proceed. */
401
402 static int
403 prepare_to_extract (char const *file_name)
404 {
405 if (to_stdout_option)
406 return 0;
407
408 if (old_files_option == UNLINK_FIRST_OLD_FILES
409 && !remove_any_file (file_name, recursive_unlink_option)
410 && errno && errno != ENOENT)
411 {
412 unlink_error (file_name);
413 return 0;
414 }
415
416 return 1;
417 }
418
419 /* Attempt repairing what went wrong with the extraction. Delete an
420 already existing file or create missing intermediate directories.
421 Return nonzero if we somewhat increased our chances at a successful
422 extraction. errno is properly restored on zero return. */
423 static int
424 maybe_recoverable (char *file_name, int *interdir_made)
425 {
426 if (*interdir_made)
427 return 0;
428
429 switch (errno)
430 {
431 case EEXIST:
432 /* Remove an old file, if the options allow this. */
433
434 switch (old_files_option)
435 {
436 default:
437 return 0;
438
439 case DEFAULT_OLD_FILES:
440 case OVERWRITE_OLD_FILES:
441 {
442 int r = remove_any_file (file_name, 0);
443 errno = EEXIST;
444 return r;
445 }
446 }
447
448 case ENOENT:
449 /* Attempt creating missing intermediate directories. */
450 if (! make_directories (file_name))
451 {
452 errno = ENOENT;
453 return 0;
454 }
455 *interdir_made = 1;
456 return 1;
457
458 default:
459 /* Just say we can't do anything about it... */
460
461 return 0;
462 }
463 }
464
465 static void
466 extract_sparse_file (int fd, off_t *sizeleft, off_t totalsize, char *name)
467 {
468 int sparse_ind = 0;
469
470 /* assuming sizeleft is initially totalsize */
471
472 while (*sizeleft > 0)
473 {
474 size_t written;
475 size_t count;
476 union block *data_block = find_next_block ();
477 if (! data_block)
478 {
479 ERROR ((0, 0, _("Unexpected EOF in archive")));
480 return;
481 }
482 if (lseek (fd, sparsearray[sparse_ind].offset, SEEK_SET) < 0)
483 {
484 seek_error_details (name, sparsearray[sparse_ind].offset);
485 return;
486 }
487 written = sparsearray[sparse_ind++].numbytes;
488 while (written > BLOCKSIZE)
489 {
490 count = full_write (fd, data_block->buffer, BLOCKSIZE);
491 written -= count;
492 *sizeleft -= count;
493 if (count != BLOCKSIZE)
494 {
495 write_error_details (name, count, BLOCKSIZE);
496 return;
497 }
498 set_next_block_after (data_block);
499 data_block = find_next_block ();
500 if (! data_block)
501 {
502 ERROR ((0, 0, _("Unexpected EOF in archive")));
503 return;
504 }
505 }
506
507 count = full_write (fd, data_block->buffer, written);
508 *sizeleft -= count;
509
510 if (count != written)
511 {
512 write_error_details (name, count, written);
513 return;
514 }
515
516 set_next_block_after (data_block);
517 }
518 }
519
520 /* Fix the statuses of all directories whose statuses need fixing, and
521 which are not ancestors of FILE_NAME. */
522 static void
523 apply_nonancestor_delayed_set_stat (char const *file_name)
524 {
525 size_t file_name_len = strlen (file_name);
526
527 while (delayed_set_stat_head)
528 {
529 struct delayed_set_stat *data = delayed_set_stat_head;
530 if (data->file_name_len < file_name_len
531 && file_name[data->file_name_len]
532 && (ISSLASH (file_name[data->file_name_len])
533 || ISSLASH (file_name[data->file_name_len - 1]))
534 && memcmp (file_name, data->file_name, data->file_name_len) == 0)
535 break;
536 delayed_set_stat_head = data->next;
537 set_stat (data->file_name, &data->stat_info,
538 data->invert_permissions, data->permstatus, DIRTYPE);
539 free (data);
540 }
541 }
542
543 /* Extract a file from the archive. */
544 void
545 extract_archive (void)
546 {
547 union block *data_block;
548 int fd;
549 int status;
550 size_t count;
551 size_t name_length;
552 size_t written;
553 int openflag;
554 mode_t mode;
555 off_t size;
556 size_t skipcrud;
557 int counter;
558 int interdir_made = 0;
559 char typeflag;
560 union block *exhdr;
561
562 #define CURRENT_FILE_NAME (skipcrud + current_file_name)
563
564 set_next_block_after (current_header);
565 decode_header (current_header, &current_stat, &current_format, 1);
566
567 if (interactive_option && !confirm ("extract", current_file_name))
568 {
569 skip_member ();
570 return;
571 }
572
573 /* Print the block from current_header and current_stat. */
574
575 if (verbose_option)
576 print_header ();
577
578 /* Check for fully specified file names and other atrocities. */
579
580 skipcrud = 0;
581 if (! absolute_names_option)
582 {
583 if (contains_dot_dot (CURRENT_FILE_NAME))
584 {
585 ERROR ((0, 0, _("%s: Member name contains `..'"),
586 quotearg_colon (CURRENT_FILE_NAME)));
587 skip_member ();
588 return;
589 }
590
591 skipcrud = FILESYSTEM_PREFIX_LEN (current_file_name);
592 while (ISSLASH (CURRENT_FILE_NAME[0]))
593 skipcrud++;
594
595 if (skipcrud)
596 {
597 static int warned_once;
598
599 if (!warned_once)
600 {
601 warned_once = 1;
602 WARN ((0, 0, _("Removing leading `%.*s' from member names"),
603 (int) skipcrud, current_file_name));
604 }
605 }
606 }
607
608 apply_nonancestor_delayed_set_stat (CURRENT_FILE_NAME);
609
610 /* Take a safety backup of a previously existing file. */
611
612 if (backup_option && !to_stdout_option)
613 if (!maybe_backup_file (CURRENT_FILE_NAME, 0))
614 {
615 int e = errno;
616 ERROR ((0, e, _("%s: Was unable to backup this file"),
617 quotearg_colon (CURRENT_FILE_NAME)));
618 skip_member ();
619 return;
620 }
621
622 /* Extract the archive entry according to its type. */
623
624 typeflag = current_header->header.typeflag;
625 switch (typeflag)
626 {
627 /* JK - What we want to do if the file is sparse is loop through
628 the array of sparse structures in the header and read in and
629 translate the character strings representing 1) the offset at
630 which to write and 2) how many bytes to write into numbers,
631 which we store into the scratch array, "sparsearray". This
632 array makes our life easier the same way it did in creating the
633 tar file that had to deal with a sparse file.
634
635 After we read in the first five (at most) sparse structures, we
636 check to see if the file has an extended header, i.e., if more
637 sparse structures are needed to describe the contents of the new
638 file. If so, we read in the extended headers and continue to
639 store their contents into the sparsearray. */
640
641 case GNUTYPE_SPARSE:
642 sp_array_size = 10;
643 sparsearray =
644 xmalloc (sp_array_size * sizeof (struct sp_array));
645
646 for (counter = 0; counter < SPARSES_IN_OLDGNU_HEADER; counter++)
647 {
648 struct sparse const *s = &current_header->oldgnu_header.sp[counter];
649 sparsearray[counter].offset = OFF_FROM_HEADER (s->offset);
650 sparsearray[counter].numbytes = SIZE_FROM_HEADER (s->numbytes);
651 if (!sparsearray[counter].numbytes)
652 break;
653 }
654
655 if (current_header->oldgnu_header.isextended)
656 {
657 /* Read in the list of extended headers and translate them
658 into the sparsearray as before. Note that this
659 invalidates current_header. */
660
661 /* static */ int ind = SPARSES_IN_OLDGNU_HEADER;
662
663 while (1)
664 {
665 exhdr = find_next_block ();
666 if (! exhdr)
667 {
668 ERROR ((0, 0, _("Unexpected EOF in archive")));
669 return;
670 }
671 for (counter = 0; counter < SPARSES_IN_SPARSE_HEADER; counter++)
672 {
673 struct sparse const *s = &exhdr->sparse_header.sp[counter];
674 if (counter + ind > sp_array_size - 1)
675 {
676 /* Realloc the scratch area since we've run out of
677 room. */
678
679 sp_array_size *= 2;
680 sparsearray =
681 xrealloc (sparsearray,
682 sp_array_size * sizeof (struct sp_array));
683 }
684 if (s->numbytes[0] == 0)
685 break;
686 sparsearray[counter + ind].offset =
687 OFF_FROM_HEADER (s->offset);
688 sparsearray[counter + ind].numbytes =
689 SIZE_FROM_HEADER (s->numbytes);
690 }
691 if (!exhdr->sparse_header.isextended)
692 break;
693 else
694 {
695 ind += SPARSES_IN_SPARSE_HEADER;
696 set_next_block_after (exhdr);
697 }
698 }
699 set_next_block_after (exhdr);
700 }
701 /* Fall through. */
702
703 case AREGTYPE:
704 case REGTYPE:
705 case CONTTYPE:
706
707 /* Appears to be a file. But BSD tar uses the convention that a slash
708 suffix means a directory. */
709
710 name_length = strlen (CURRENT_FILE_NAME);
711 if (FILESYSTEM_PREFIX_LEN (CURRENT_FILE_NAME) < name_length
712 && CURRENT_FILE_NAME[name_length - 1] == '/')
713 goto really_dir;
714
715 /* FIXME: deal with protection issues. */
716
717 again_file:
718 openflag = (O_WRONLY | O_BINARY | O_CREAT
719 | (old_files_option == OVERWRITE_OLD_FILES
720 ? O_TRUNC
721 : O_EXCL));
722 mode = current_stat.st_mode & MODE_RWX & ~ current_umask;
723
724 if (to_stdout_option)
725 {
726 fd = STDOUT_FILENO;
727 goto extract_file;
728 }
729
730 if (! prepare_to_extract (CURRENT_FILE_NAME))
731 {
732 skip_member ();
733 if (backup_option)
734 undo_last_backup ();
735 break;
736 }
737
738 #if O_CTG
739 /* Contiguous files (on the Masscomp) have to specify the size in
740 the open call that creates them. */
741
742 if (typeflag == CONTTYPE)
743 fd = open (CURRENT_FILE_NAME, openflag | O_CTG,
744 mode, current_stat.st_size);
745 else
746 fd = open (CURRENT_FILE_NAME, openflag, mode);
747
748 #else /* not O_CTG */
749 if (typeflag == CONTTYPE)
750 {
751 static int conttype_diagnosed;
752
753 if (!conttype_diagnosed)
754 {
755 conttype_diagnosed = 1;
756 WARN ((0, 0, _("Extracting contiguous files as regular files")));
757 }
758 }
759 fd = open (CURRENT_FILE_NAME, openflag, mode);
760
761 #endif /* not O_CTG */
762
763 if (fd < 0)
764 {
765 if (maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
766 goto again_file;
767
768 open_error (CURRENT_FILE_NAME);
769 skip_member ();
770 if (backup_option)
771 undo_last_backup ();
772 break;
773 }
774
775 extract_file:
776 if (typeflag == GNUTYPE_SPARSE)
777 {
778 char *name;
779 size_t name_length_bis;
780
781 /* Kludge alert. NAME is assigned to header.name because
782 during the extraction, the space that contains the header
783 will get scribbled on, and the name will get munged, so any
784 error messages that happen to contain the filename will look
785 REAL interesting unless we do this. */
786
787 name_length_bis = strlen (CURRENT_FILE_NAME) + 1;
788 name = xmalloc (name_length_bis);
789 memcpy (name, CURRENT_FILE_NAME, name_length_bis);
790 size = current_stat.st_size;
791 extract_sparse_file (fd, &size, current_stat.st_size, name);
792 free (sparsearray);
793 }
794 else
795 for (size = current_stat.st_size; size > 0; )
796 {
797 if (multi_volume_option)
798 {
799 assign_string (&save_name, current_file_name);
800 save_totsize = current_stat.st_size;
801 save_sizeleft = size;
802 }
803
804 /* Locate data, determine max length writeable, write it,
805 block that we have used the data, then check if the write
806 worked. */
807
808 data_block = find_next_block ();
809 if (! data_block)
810 {
811 ERROR ((0, 0, _("Unexpected EOF in archive")));
812 break; /* FIXME: What happens, then? */
813 }
814
815 written = available_space_after (data_block);
816
817 if (written > size)
818 written = size;
819 errno = 0;
820 count = full_write (fd, data_block->buffer, written);
821 size -= count;
822
823 set_next_block_after ((union block *)
824 (data_block->buffer + written - 1));
825 if (count != written)
826 {
827 write_error_details (CURRENT_FILE_NAME, count, written);
828 break;
829 }
830 }
831
832 skip_file (size);
833
834 if (multi_volume_option)
835 assign_string (&save_name, 0);
836
837 /* If writing to stdout, don't try to do anything to the filename;
838 it doesn't exist, or we don't want to touch it anyway. */
839
840 if (to_stdout_option)
841 break;
842
843 status = close (fd);
844 if (status < 0)
845 {
846 close_error (CURRENT_FILE_NAME);
847 if (backup_option)
848 undo_last_backup ();
849 }
850
851 set_stat (CURRENT_FILE_NAME, &current_stat, 0,
852 (old_files_option == OVERWRITE_OLD_FILES
853 ? UNKNOWN_PERMSTATUS
854 : ARCHIVED_PERMSTATUS),
855 typeflag);
856 break;
857
858 case SYMTYPE:
859 #ifdef HAVE_SYMLINK
860 if (! prepare_to_extract (CURRENT_FILE_NAME))
861 break;
862
863 if (absolute_names_option
864 || ! (ISSLASH (current_link_name
865 [FILESYSTEM_PREFIX_LEN (current_link_name)])
866 || contains_dot_dot (current_link_name)))
867 {
868 while (status = symlink (current_link_name, CURRENT_FILE_NAME),
869 status != 0)
870 if (!maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
871 break;
872
873 if (status == 0)
874 set_stat (CURRENT_FILE_NAME, &current_stat, 0, 0, SYMTYPE);
875 else
876 symlink_error (current_link_name, CURRENT_FILE_NAME);
877 }
878 else
879 {
880 /* This symbolic link is potentially dangerous. Don't
881 create it now; instead, create a placeholder file, which
882 will be replaced after other extraction is done. */
883 struct stat st;
884
885 while (fd = open (CURRENT_FILE_NAME, O_WRONLY | O_CREAT | O_EXCL, 0),
886 fd < 0)
887 if (! maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
888 break;
889
890 status = -1;
891 if (fd < 0)
892 open_error (CURRENT_FILE_NAME);
893 else if (fstat (fd, &st) != 0)
894 {
895 stat_error (CURRENT_FILE_NAME);
896 close (fd);
897 }
898 else if (close (fd) != 0)
899 close_error (CURRENT_FILE_NAME);
900 else
901 {
902 size_t filelen = strlen (CURRENT_FILE_NAME);
903 size_t linklen = strlen (current_link_name);
904 struct delayed_symlink *p =
905 xmalloc (offsetof (struct delayed_symlink, target)
906 + linklen + 1);
907 p->next = delayed_symlink_head;
908 delayed_symlink_head = p;
909 p->dev = st.st_dev;
910 p->ino = st.st_ino;
911 p->mtime = st.st_mtime;
912 p->uid = current_stat.st_uid;
913 p->gid = current_stat.st_gid;
914 p->sources = xmalloc (offsetof (struct string_list, string)
915 + filelen + 1);
916 p->sources->next = 0;
917 memcpy (p->sources->string, CURRENT_FILE_NAME, filelen + 1);
918 memcpy (p->target, current_link_name, linklen + 1);
919 status = 0;
920 }
921 }
922
923 if (status != 0 && backup_option)
924 undo_last_backup ();
925 break;
926
927 #else
928 {
929 static int warned_once;
930
931 if (!warned_once)
932 {
933 warned_once = 1;
934 WARN ((0, 0,
935 _("Attempting extraction of symbolic links as hard links")));
936 }
937 }
938 typeflag = LNKTYPE;
939 /* Fall through. */
940 #endif
941
942 case LNKTYPE:
943 if (! prepare_to_extract (CURRENT_FILE_NAME))
944 break;
945
946 again_link:
947 {
948 struct stat st1, st2;
949 int e;
950
951 /* MSDOS does not implement links. However, djgpp's link() actually
952 copies the file. */
953 status = link (current_link_name, CURRENT_FILE_NAME);
954
955 if (status == 0)
956 {
957 struct delayed_symlink *ds = delayed_symlink_head;
958 if (ds && stat (current_link_name, &st1) == 0)
959 for (; ds; ds = ds->next)
960 if (ds->dev == st1.st_dev
961 && ds->ino == st1.st_ino
962 && ds->mtime == st1.st_mtime)
963 {
964 struct string_list *p =
965 xmalloc (offsetof (struct string_list, string)
966 + strlen (CURRENT_FILE_NAME) + 1);
967 strcpy (p->string, CURRENT_FILE_NAME);
968 p->next = ds->sources;
969 ds->sources = p;
970 break;
971 }
972 break;
973 }
974 if (maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
975 goto again_link;
976
977 if (incremental_option && errno == EEXIST)
978 break;
979 e = errno;
980 if (stat (current_link_name, &st1) == 0
981 && stat (CURRENT_FILE_NAME, &st2) == 0
982 && st1.st_dev == st2.st_dev
983 && st1.st_ino == st2.st_ino)
984 break;
985
986 link_error (current_link_name, CURRENT_FILE_NAME);
987 if (backup_option)
988 undo_last_backup ();
989 }
990 break;
991
992 #if S_IFCHR
993 case CHRTYPE:
994 current_stat.st_mode |= S_IFCHR;
995 goto make_node;
996 #endif
997
998 #if S_IFBLK
999 case BLKTYPE:
1000 current_stat.st_mode |= S_IFBLK;
1001 #endif
1002
1003 #if S_IFCHR || S_IFBLK
1004 make_node:
1005 if (! prepare_to_extract (CURRENT_FILE_NAME))
1006 break;
1007
1008 status = mknod (CURRENT_FILE_NAME, current_stat.st_mode,
1009 current_stat.st_rdev);
1010 if (status != 0)
1011 {
1012 if (maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
1013 goto make_node;
1014 mknod_error (CURRENT_FILE_NAME);
1015 if (backup_option)
1016 undo_last_backup ();
1017 break;
1018 };
1019 set_stat (CURRENT_FILE_NAME, &current_stat, 0,
1020 ARCHIVED_PERMSTATUS, typeflag);
1021 break;
1022 #endif
1023
1024 #if HAVE_MKFIFO || defined mkfifo
1025 case FIFOTYPE:
1026 if (! prepare_to_extract (CURRENT_FILE_NAME))
1027 break;
1028
1029 while (status = mkfifo (CURRENT_FILE_NAME, current_stat.st_mode),
1030 status != 0)
1031 if (!maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
1032 break;
1033
1034 if (status == 0)
1035 set_stat (CURRENT_FILE_NAME, &current_stat, 0,
1036 ARCHIVED_PERMSTATUS, typeflag);
1037 else
1038 {
1039 mkfifo_error (CURRENT_FILE_NAME);
1040 if (backup_option)
1041 undo_last_backup ();
1042 }
1043 break;
1044 #endif
1045
1046 case DIRTYPE:
1047 case GNUTYPE_DUMPDIR:
1048 name_length = strlen (CURRENT_FILE_NAME);
1049
1050 really_dir:
1051 /* Remove any redundant trailing "/"s. */
1052 while (FILESYSTEM_PREFIX_LEN (CURRENT_FILE_NAME) < name_length
1053 && CURRENT_FILE_NAME[name_length - 1] == '/')
1054 name_length--;
1055 CURRENT_FILE_NAME[name_length] = '\0';
1056
1057 if (incremental_option)
1058 {
1059 /* Read the entry and delete files that aren't listed in the
1060 archive. */
1061
1062 gnu_restore (skipcrud);
1063 }
1064 else if (typeflag == GNUTYPE_DUMPDIR)
1065 skip_member ();
1066
1067 if (! prepare_to_extract (CURRENT_FILE_NAME))
1068 break;
1069
1070 mode = ((current_stat.st_mode
1071 | (we_are_root ? 0 : MODE_WXUSR))
1072 & MODE_RWX);
1073
1074 again_dir:
1075 status = mkdir (CURRENT_FILE_NAME, mode);
1076
1077 if (status != 0)
1078 {
1079 if (errno == EEXIST
1080 && (interdir_made || old_files_option == OVERWRITE_OLD_FILES))
1081 {
1082 struct stat st;
1083 if (stat (CURRENT_FILE_NAME, &st) == 0)
1084 {
1085 if (interdir_made)
1086 {
1087 repair_delayed_set_stat (CURRENT_FILE_NAME, &st);
1088 break;
1089 }
1090 if (S_ISDIR (st.st_mode))
1091 {
1092 mode = st.st_mode & ~ current_umask;
1093 goto directory_exists;
1094 }
1095 }
1096 errno = EEXIST;
1097 }
1098
1099 if (maybe_recoverable (CURRENT_FILE_NAME, &interdir_made))
1100 goto again_dir;
1101
1102 if (errno != EEXIST)
1103 {
1104 mkdir_error (CURRENT_FILE_NAME);
1105 if (backup_option)
1106 undo_last_backup ();
1107 break;
1108 }
1109 }
1110
1111 directory_exists:
1112 if (status == 0
1113 || old_files_option == OVERWRITE_OLD_FILES)
1114 delay_set_stat (CURRENT_FILE_NAME, &current_stat,
1115 MODE_RWX & (mode ^ current_stat.st_mode),
1116 (status == 0
1117 ? ARCHIVED_PERMSTATUS
1118 : UNKNOWN_PERMSTATUS));
1119 break;
1120
1121 case GNUTYPE_VOLHDR:
1122 if (verbose_option)
1123 fprintf (stdlis, _("Reading %s\n"), quote (current_file_name));
1124 break;
1125
1126 case GNUTYPE_NAMES:
1127 extract_mangle ();
1128 break;
1129
1130 case GNUTYPE_MULTIVOL:
1131 ERROR ((0, 0,
1132 _("%s: Cannot extract -- file is continued from another volume"),
1133 quotearg_colon (current_file_name)));
1134 skip_member ();
1135 if (backup_option)
1136 undo_last_backup ();
1137 break;
1138
1139 case GNUTYPE_LONGNAME:
1140 case GNUTYPE_LONGLINK:
1141 ERROR ((0, 0, _("Visible long name error")));
1142 skip_member ();
1143 if (backup_option)
1144 undo_last_backup ();
1145 break;
1146
1147 default:
1148 WARN ((0, 0,
1149 _("%s: Unknown file type '%c', extracted as normal file"),
1150 quotearg_colon (CURRENT_FILE_NAME), typeflag));
1151 goto again_file;
1152 }
1153
1154 #undef CURRENT_FILE_NAME
1155 }
1156
1157 /* Extract the symbolic links whose final extraction were delayed. */
1158 static void
1159 apply_delayed_symlinks (void)
1160 {
1161 struct delayed_symlink *ds;
1162
1163 for (ds = delayed_symlink_head; ds; )
1164 {
1165 struct string_list *sources = ds->sources;
1166 char const *valid_source = 0;
1167
1168 for (sources = ds->sources; sources; sources = sources->next)
1169 {
1170 char const *source = sources->string;
1171 struct stat st;
1172
1173 /* Make sure the placeholder file is still there. If not,
1174 don't create a symlink, as the placeholder was probably
1175 removed by a later extraction. */
1176 if (lstat (source, &st) == 0
1177 && st.st_dev == ds->dev
1178 && st.st_ino == ds->ino
1179 && st.st_mtime == ds->mtime)
1180 {
1181 /* Unlink the placeholder, then create a hard link if possible,
1182 a symbolic link otherwise. */
1183 if (unlink (source) != 0)
1184 unlink_error (source);
1185 else if (valid_source && link (valid_source, source) == 0)
1186 ;
1187 else if (symlink (ds->target, source) != 0)
1188 symlink_error (ds->target, source);
1189 else
1190 {
1191 valid_source = source;
1192 st.st_uid = ds->uid;
1193 st.st_gid = ds->gid;
1194 set_stat (source, &st, 0, 0, SYMTYPE);
1195 }
1196 }
1197 }
1198
1199 for (sources = ds->sources; sources; )
1200 {
1201 struct string_list *next = sources->next;
1202 free (sources);
1203 sources = next;
1204 }
1205
1206 {
1207 struct delayed_symlink *next = ds->next;
1208 free (ds);
1209 ds = next;
1210 }
1211 }
1212
1213 delayed_symlink_head = 0;
1214 }
1215
1216 /* Finish the extraction of an archive. */
1217 void
1218 extract_finish (void)
1219 {
1220 /* Apply delayed symlinks last, so that they don't affect
1221 delayed directory status-setting. */
1222 apply_nonancestor_delayed_set_stat ("");
1223 apply_delayed_symlinks ();
1224 }
1225
1226 void
1227 fatal_exit (void)
1228 {
1229 extract_finish ();
1230 error (TAREXIT_FAILURE, 0, _("Error is not recoverable: exiting now"));
1231 abort ();
1232 }
This page took 0.082935 seconds and 5 git commands to generate.