[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: FW: GNU tar 1.13.17 --overwrite works "wrong"
From: |
Paul Eggert |
Subject: |
Re: FW: GNU tar 1.13.17 --overwrite works "wrong" |
Date: |
Tue, 13 Mar 2001 17:48:08 -0800 (PST) |
> From: "Patterson, Ross" <address@hidden>
> Date: Tue, 13 Mar 2001 15:03:00 -0500
>
> So, what's a poor boy to do? I can't ask for a tar patch, I've got
> to be able to install on systems already in the field today.
Create your tar files so that instead of this:
$ tar tvf tar
drwxrwsr-x eggert/eggert 0 2001-03-13 15:33:19 a/
-rw-rw-r-- eggert/eggert 4 2001-03-13 15:33:19 a/x
drwxrwsr-x eggert/eggert 0 2001-03-13 15:33:22 b/
-rw-rw-r-- eggert/eggert 4 2001-03-13 15:33:22 b/x
You see this:
$ tar tvf tar1
drwxrwsr-x eggert/eggert 0 2001-03-13 15:33:19 a/./
-rw-rw-r-- eggert/eggert 4 2001-03-13 15:33:19 a/./x
drwxrwsr-x eggert/eggert 0 2001-03-13 15:33:22 b/./
-rw-rw-r-- eggert/eggert 4 2001-03-13 15:33:22 b/./x
The extra "/." will cause the symlink to be dereferenced.
You didn't ask for a patch, but you might try the following one anyway,
(relative to tar 1.13.19).
--- extract.c 2001/01/13 05:59:29 1.12.0.22
+++ extract.c 2001/03/14 01:42:31
@@ -282,7 +282,6 @@ delay_set_stat (char const *file_name, s
/* Update the delayed_set_stat info for an intermediate directory
created on the path to DIR_NAME. The intermediate directory turned
- out to be the same as this directory, e.g. due trailing slash or
- ".." or symbolic links. *DIR_STAT_INFO is the status of the
- directory. */
+ out to be the same as this directory, e.g. due to ".." or symbolic
+ links. *DIR_STAT_INFO is the status of the directory. */
static void
repair_delayed_set_stat (char const *dir_name,
@@ -1019,4 +1018,9 @@ extract_archive (void)
really_dir:
+ /* Remove any redundant trailing "/"s. */
+ while (FILESYSTEM_PREFIX_LEN (CURRENT_FILE_NAME) < name_length
+ && CURRENT_FILE_NAME[name_length - 1] == '/')
+ name_length--;
+ CURRENT_FILE_NAME[name_length] = '\0';
if (incremental_option)
@@ -1038,26 +1042,24 @@ extract_archive (void)
again_dir:
- {
- /* Do not pass redundant trailing "/" to mkdir, as POSIX does
- not allow mkdir to ignore it. */
- size_t len = name_length;
- char ch = '\0';
- while (FILESYSTEM_PREFIX_LEN (CURRENT_FILE_NAME) < len
- && CURRENT_FILE_NAME[len - 1] == '/')
- len--, ch = '/';
- CURRENT_FILE_NAME[len] = '\0';
- status = mkdir (CURRENT_FILE_NAME, mode);
- CURRENT_FILE_NAME[len] = ch;
- }
+ status = mkdir (CURRENT_FILE_NAME, mode);
if (status != 0)
{
- if (errno == EEXIST && interdir_made)
+ if (errno == EEXIST
+ && (interdir_made || old_files_option == OVERWRITE_OLD_FILES))
{
struct stat st;
if (stat (CURRENT_FILE_NAME, &st) == 0)
{
- repair_delayed_set_stat (CURRENT_FILE_NAME, &st);
- break;
+ if (interdir_made)
+ {
+ repair_delayed_set_stat (CURRENT_FILE_NAME, &st);
+ break;
+ }
+ if (S_ISDIR (st.st_mode))
+ {
+ mode = st.st_mode & ~ current_umask;
+ goto directory_exists;
+ }
}
errno = EEXIST;
@@ -1076,8 +1078,9 @@ extract_archive (void)
}
+ directory_exists:
if (status == 0
|| old_files_option == OVERWRITE_OLD_FILES)
delay_set_stat (CURRENT_FILE_NAME, ¤t_stat,
- mode & ~ current_stat.st_mode,
+ MODE_RWX & (mode ^ current_stat.st_mode),
(status == 0
? ARCHIVED_PERMSTATUS