[5c5752c] | 1 | Submitted By: Ken Moffat <ken at linuxfromscratch dot org>
|
---|
| 2 | Date: 2006-04-14
|
---|
| 3 | Initial Package Version: 1.15.1
|
---|
| 4 | Origin: gentoo, backported from CVS, rediffed to apply with -p1
|
---|
| 5 | Description: addresses vulnerability CVE-2006-0300
|
---|
| 6 |
|
---|
| 7 | diff -Naurp tar-1.15.1-vanilla/src/xheader.c tar-1.15.1/src/xheader.c
|
---|
| 8 | --- tar-1.15.1-vanilla/src/xheader.c 2004-09-06 12:31:14.000000000 +0100
|
---|
| 9 | +++ tar-1.15.1/src/xheader.c 2006-04-14 16:26:26.000000000 +0100
|
---|
| 10 | @@ -783,6 +783,32 @@ code_num (uintmax_t value, char const *k
|
---|
| 11 | xheader_print (xhdr, keyword, sbuf);
|
---|
| 12 | }
|
---|
| 13 |
|
---|
| 14 | +static bool
|
---|
| 15 | +decode_num (uintmax_t *num, char const *arg, uintmax_t maxval,
|
---|
| 16 | + char const *keyword)
|
---|
| 17 | +{
|
---|
| 18 | + uintmax_t u;
|
---|
| 19 | + char *arg_lim;
|
---|
| 20 | +
|
---|
| 21 | + if (! (ISDIGIT (*arg)
|
---|
| 22 | + && (errno = 0, u = strtoumax (arg, &arg_lim, 10), !*arg_lim)))
|
---|
| 23 | + {
|
---|
| 24 | + ERROR ((0, 0, _("Malformed extended header: invalid %s=%s"),
|
---|
| 25 | + keyword, arg));
|
---|
| 26 | + return false;
|
---|
| 27 | + }
|
---|
| 28 | +
|
---|
| 29 | + if (! (u <= maxval && errno != ERANGE))
|
---|
| 30 | + {
|
---|
| 31 | + ERROR ((0, 0, _("Extended header %s=%s is out of range"),
|
---|
| 32 | + keyword, arg));
|
---|
| 33 | + return false;
|
---|
| 34 | + }
|
---|
| 35 | +
|
---|
| 36 | + *num = u;
|
---|
| 37 | + return true;
|
---|
| 38 | +}
|
---|
| 39 | +
|
---|
| 40 | static void
|
---|
| 41 | dummy_coder (struct tar_stat_info const *st __attribute__ ((unused)),
|
---|
| 42 | char const *keyword __attribute__ ((unused)),
|
---|
| 43 | @@ -821,7 +847,7 @@ static void
|
---|
| 44 | gid_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 45 | {
|
---|
| 46 | uintmax_t u;
|
---|
| 47 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 48 | + if (decode_num (&u, arg, TYPE_MAXIMUM (gid_t), "gid"))
|
---|
| 49 | st->stat.st_gid = u;
|
---|
| 50 | }
|
---|
| 51 |
|
---|
| 52 | @@ -903,7 +929,7 @@ static void
|
---|
| 53 | size_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 54 | {
|
---|
| 55 | uintmax_t u;
|
---|
| 56 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 57 | + if (decode_num (&u, arg, TYPE_MAXIMUM (off_t), "size"))
|
---|
| 58 | st->archive_file_size = st->stat.st_size = u;
|
---|
| 59 | }
|
---|
| 60 |
|
---|
| 61 | @@ -918,7 +944,7 @@ static void
|
---|
| 62 | uid_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 63 | {
|
---|
| 64 | uintmax_t u;
|
---|
| 65 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 66 | + if (decode_num (&u, arg, TYPE_MAXIMUM (uid_t), "uid"))
|
---|
| 67 | st->stat.st_uid = u;
|
---|
| 68 | }
|
---|
| 69 |
|
---|
| 70 | @@ -946,7 +972,7 @@ static void
|
---|
| 71 | sparse_size_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 72 | {
|
---|
| 73 | uintmax_t u;
|
---|
| 74 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 75 | + if (decode_num (&u, arg, TYPE_MAXIMUM (off_t), "GNU.sparse.size"))
|
---|
| 76 | st->stat.st_size = u;
|
---|
| 77 | }
|
---|
| 78 |
|
---|
| 79 | @@ -962,10 +988,10 @@ static void
|
---|
| 80 | sparse_numblocks_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 81 | {
|
---|
| 82 | uintmax_t u;
|
---|
| 83 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 84 | + if (decode_num (&u, arg, SIZE_MAX, "GNU.sparse.numblocks"))
|
---|
| 85 | {
|
---|
| 86 | st->sparse_map_size = u;
|
---|
| 87 | - st->sparse_map = calloc(st->sparse_map_size, sizeof(st->sparse_map[0]));
|
---|
| 88 | + st->sparse_map = xcalloc (u, sizeof st->sparse_map[0]);
|
---|
| 89 | st->sparse_map_avail = 0;
|
---|
| 90 | }
|
---|
| 91 | }
|
---|
| 92 | @@ -982,8 +1008,14 @@ static void
|
---|
| 93 | sparse_offset_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 94 | {
|
---|
| 95 | uintmax_t u;
|
---|
| 96 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 97 | + if (decode_num (&u, arg, TYPE_MAXIMUM (off_t), "GNU.sparse.offset"))
|
---|
| 98 | + {
|
---|
| 99 | + if (st->sparse_map_avail < st->sparse_map_size)
|
---|
| 100 | st->sparse_map[st->sparse_map_avail].offset = u;
|
---|
| 101 | + else
|
---|
| 102 | + ERROR ((0, 0, _("Malformed extended header: excess %s=%s"),
|
---|
| 103 | + "GNU.sparse.offset", arg));
|
---|
| 104 | + }
|
---|
| 105 | }
|
---|
| 106 |
|
---|
| 107 | static void
|
---|
| 108 | @@ -998,15 +1030,13 @@ static void
|
---|
| 109 | sparse_numbytes_decoder (struct tar_stat_info *st, char const *arg)
|
---|
| 110 | {
|
---|
| 111 | uintmax_t u;
|
---|
| 112 | - if (xstrtoumax (arg, NULL, 10, &u, "") == LONGINT_OK)
|
---|
| 113 | + if (decode_num (&u, arg, SIZE_MAX, "GNU.sparse.numbytes"))
|
---|
| 114 | {
|
---|
| 115 | if (st->sparse_map_avail == st->sparse_map_size)
|
---|
| 116 | - {
|
---|
| 117 | - st->sparse_map_size *= 2;
|
---|
| 118 | - st->sparse_map = xrealloc (st->sparse_map,
|
---|
| 119 | - st->sparse_map_size
|
---|
| 120 | - * sizeof st->sparse_map[0]);
|
---|
| 121 | - }
|
---|
| 122 | + st->sparse_map = x2nrealloc (st->sparse_map,
|
---|
| 123 | + &st->sparse_map_size,
|
---|
| 124 | + sizeof st->sparse_map[0]);
|
---|
| 125 | +
|
---|
| 126 | st->sparse_map[st->sparse_map_avail++].numbytes = u;
|
---|
| 127 | }
|
---|
| 128 | }
|
---|