Репозитории ALT
S: | 2.14.0.4.e3cc-alt1 |
5.1: | 2.10-alt3 |
4.1: | 2.10-alt2.M41.2 |
4.0: | 2.6-alt17.M40.1 |
3.0: | 2.6-alt14 |
Другие репозитории
Upstream: | 2.9 |
Группа :: Архивирование/Резервное копирование
Пакет: cpio
Главная Изменения Спек Патчи Sources Загрузить Gear Bugs and FR Repocop
Патч: cpio-2.6-alt-safer_name_suffix.patch
Скачать
Скачать
2005-05-03 Dmitry V. Levin <ldv@altlinux.org>
Fix directory traversal issues in copy-in and copy-pass modes
(CAN-2005-1229).
The approach and safer_name_suffix() implementation is taken
from tar-1.15.1 with minimal adoptions.
* src/copyin.c: Include "dirname.h".
(safer_name_suffix): New function.
(process_copy_in): Use it.
* src/extern.h: Replace no_abs_paths_flag variable with
abs_paths_flag.
* src/global.c: Likewise.
(abs_paths_flag): Initialize to false.
* src/main.c: (cpio_options): New constant:
ABSOLUTE_FILENAMES_OPTION.
(options): New option: --absolute-filenames.
(parse_opt): Handle it.
(process_args): Replace --no-absolute-filenames with
--absolute-filenames in usage checks.
diff -uprk.orig cpio-2.6.orig/src/copyin.c cpio-2.6/src/copyin.c
--- cpio-2.6.orig/src/copyin.c 2004-09-08 11:10:02 +0000
+++ cpio-2.6/src/copyin.c 2005-05-03 17:27:09 +0000
@@ -25,6 +25,7 @@
#include "dstring.h"
#include "extern.h"
#include "defer.h"
+#include "dirname.h"
#include <rmt.h>
#ifndef FNM_PATHNAME
#include <fnmatch.h>
@@ -1335,6 +1336,47 @@ swab_array (char *ptr, int count)
}
}
+/* Return a safer suffix of FILE_NAME, or "." if it has no safer
+ suffix. Check for fully specified file names and other atrocities. */
+
+static const char *
+safer_name_suffix (char const *file_name)
+{
+ char const *p;
+
+ /* Skip file system prefixes, leading file name components that contain
+ "..", and leading slashes. */
+
+ size_t prefix_len = FILE_SYSTEM_PREFIX_LEN (file_name);
+
+ for (p = file_name + prefix_len; *p;)
+ {
+ if (p[0] == '.' && p[1] == '.' && (ISSLASH (p[2]) || !p[2]))
+ prefix_len = p + 2 - file_name;
+
+ do
+ {
+ char c = *p++;
+ if (ISSLASH (c))
+ break;
+ }
+ while (*p);
+ }
+
+ for (p = file_name + prefix_len; ISSLASH (*p); p++)
+ continue;
+ prefix_len = p - file_name;
+
+ if (prefix_len)
+ error (0, 0, _("Removing leading `%.*s' from member names"),
+ (unsigned)prefix_len, file_name);
+
+ if (!*p)
+ p = ".";
+
+ return p;
+}
+
/* Read the collection from standard input and create files
in the file system. */
@@ -1445,18 +1487,11 @@ process_copy_in ()
/* Do we have to ignore absolute paths, and if so, does the filename
have an absolute path? */
- if (no_abs_paths_flag && file_hdr.c_name && file_hdr.c_name [0] == '/')
+ if (!abs_paths_flag && file_hdr.c_name && file_hdr.c_name [0])
{
- char *p;
+ const char *p = safer_name_suffix (file_hdr.c_name);
- p = file_hdr.c_name;
- while (*p == '/')
- ++p;
- if (*p == '\0')
- {
- strcpy (file_hdr.c_name, ".");
- }
- else
+ if (p != file_hdr.c_name)
{
/* Debian hack: file_hrd.c_name is sometimes set to
point to static memory by code in tar.c. This
diff -uprk.orig cpio-2.6.orig/src/extern.h cpio-2.6/src/extern.h
--- cpio-2.6.orig/src/extern.h 2004-09-08 10:49:57 +0000
+++ cpio-2.6/src/extern.h 2005-05-03 17:27:09 +0000
@@ -46,7 +46,7 @@ extern int no_chown_flag;
extern int sparse_flag;
extern int quiet_flag;
extern int only_verify_crc_flag;
-extern int no_abs_paths_flag;
+extern int abs_paths_flag;
extern unsigned int warn_option;
/* Values for warn_option */
diff -uprk.orig cpio-2.6.orig/src/global.c cpio-2.6/src/global.c
--- cpio-2.6.orig/src/global.c 2004-09-08 10:23:44 +0000
+++ cpio-2.6/src/global.c 2005-04-26 18:19:27 +0000
@@ -100,7 +100,7 @@ int quiet_flag = false;
int only_verify_crc_flag = false;
/* If true, don't use any absolute paths, prefix them by `./'. */
-int no_abs_paths_flag = false;
+int abs_paths_flag = false;
#ifdef DEBUG_CPIO
/* If true, print debugging information. */
diff -uprk.orig cpio-2.6.orig/src/main.c cpio-2.6/src/main.c
--- cpio-2.6.orig/src/main.c 2004-11-23 00:42:18 +0000
+++ cpio-2.6/src/main.c 2005-05-03 17:27:09 +0000
@@ -41,6 +41,7 @@
enum cpio_options {
NO_ABSOLUTE_FILENAMES_OPTION=256,
+ ABSOLUTE_FILENAMES_OPTION,
NO_PRESERVE_OWNER_OPTION,
ONLY_VERIFY_CRC_OPTION,
RENAME_BATCH_FILE_OPTION,
@@ -134,6 +135,8 @@ static struct argp_option options[] = {
N_("In copy-in mode, read additional patterns specifying filenames to extract or list from FILE"), 210},
{"no-absolute-filenames", NO_ABSOLUTE_FILENAMES_OPTION, 0, 0,
N_("Create all files relative to the current directory"), 210},
+ {"absolute-filenames", ABSOLUTE_FILENAMES_OPTION, 0, 0,
+ N_("do not strip leading file name components that contain \"..\" and leading slashes from file names"), 210},
{"only-verify-crc", ONLY_VERIFY_CRC_OPTION, 0, 0,
N_("When reading a CRC format archive in copy-in mode, only verify the CRC's of each file in the archive, don't actually extract the files"), 210},
{"rename", 'r', 0, 0,
@@ -392,7 +395,11 @@ crc newc odc bin ustar tar (all-caps als
break;
case NO_ABSOLUTE_FILENAMES_OPTION: /* --no-absolute-filenames */
- no_abs_paths_flag = true;
+ abs_paths_flag = false;
+ break;
+
+ case ABSOLUTE_FILENAMES_OPTION: /* --absolute-filenames */
+ abs_paths_flag = true;
break;
case NO_PRESERVE_OWNER_OPTION: /* --no-preserve-owner */
@@ -631,7 +638,7 @@ process_args (int argc, char *argv[])
_("--append is used but no archive file name is given (use -F or -O options")));
CHECK_USAGE(rename_batch_file, "--rename-batch-file", "--create");
- CHECK_USAGE(no_abs_paths_flag, "--no-absolute-pathnames", "--create");
+ CHECK_USAGE(abs_paths_flag, "--absolute-pathnames", "--create");
CHECK_USAGE(input_archive_name, "-I", "--create");
if (archive_name && output_archive_name)
USAGE_ERROR ((0, 0, _("Both -O and -F are used in copy-out mode")));
@@ -658,7 +665,7 @@ process_args (int argc, char *argv[])
CHECK_USAGE(rename_flag, "--rename", "--pass-through");
CHECK_USAGE(append_flag, "--append", "--pass-through");
CHECK_USAGE(rename_batch_file, "--rename-batch-file", "--pass-through");
- CHECK_USAGE(no_abs_paths_flag, "--no-absolute-pathnames",
+ CHECK_USAGE(abs_paths_flag, "--absolute-pathnames",
"--pass-through");
CHECK_USAGE(to_stdout_option, "--to-stdout", "--pass-through");