diff options
author | Martin Matuska <mm@FreeBSD.org> | 2012-02-25 00:16:00 +0000 |
---|---|---|
committer | Martin Matuska <mm@FreeBSD.org> | 2012-02-25 00:16:00 +0000 |
commit | 132160f77407d2174d2bec0a8ba9c6eefc4429d7 (patch) | |
tree | 2668d05088fbc82cf0170e53f56d547365926031 /cpio | |
parent | 4d44c8d1829cfdaa134c3f88cad04f0c73b47ad8 (diff) | |
download | src-132160f77407d2174d2bec0a8ba9c6eefc4429d7.tar.gz src-132160f77407d2174d2bec0a8ba9c6eefc4429d7.zip |
Update libarchive's vendor dist to latest changes in release branch.
Git branch: release
Git commit: e2cc36190d7d733b3ac6744ec860d09776c9da02
Obtained from: https://github.com/libarchive/libarchive.git
Notes
Notes:
svn path=/vendor/libarchive/dist/; revision=232133
Diffstat (limited to 'cpio')
-rw-r--r-- | cpio/cpio.c | 66 | ||||
-rw-r--r-- | cpio/test/main.c | 13 |
2 files changed, 70 insertions, 9 deletions
diff --git a/cpio/cpio.c b/cpio/cpio.c index 025c50cfafd2..2c28d884dbe3 100644 --- a/cpio/cpio.c +++ b/cpio/cpio.c @@ -119,6 +119,7 @@ static void mode_in(struct cpio *); static void mode_list(struct cpio *); static void mode_out(struct cpio *); static void mode_pass(struct cpio *, const char *); +static const char *remove_leading_slash(const char *); static int restore_time(struct cpio *, struct archive_entry *, const char *, int fd); static void usage(void); @@ -155,9 +156,9 @@ main(int argc, char *argv[]) else { #if defined(_WIN32) && !defined(__CYGWIN__) lafe_progname = strrchr(*argv, '\\'); -#else - lafe_progname = strrchr(*argv, '/'); + if (strrchr(*argv, '/') > lafe_progname) #endif + lafe_progname = strrchr(*argv, '/'); if (lafe_progname != NULL) lafe_progname++; else @@ -574,6 +575,49 @@ mode_out(struct cpio *cpio) archive_write_free(cpio->archive); } +static const char * +remove_leading_slash(const char *p) +{ + const char *rp; + + /* Remove leading "//./" or "//?/" or "//?/UNC/" + * (absolute path prefixes used by Windows API) */ + if ((p[0] == '/' || p[0] == '\\') && + (p[1] == '/' || p[1] == '\\') && + (p[2] == '.' || p[2] == '?') && + (p[3] == '/' || p[3] == '\\')) + { + if (p[2] == '?' && + (p[4] == 'U' || p[4] == 'u') && + (p[5] == 'N' || p[5] == 'n') && + (p[6] == 'C' || p[6] == 'c') && + (p[7] == '/' || p[7] == '\\')) + p += 8; + else + p += 4; + } + do { + rp = p; + /* Remove leading drive letter from archives created + * on Windows. */ + if (((p[0] >= 'a' && p[0] <= 'z') || + (p[0] >= 'A' && p[0] <= 'Z')) && + p[1] == ':') { + p += 2; + } + /* Remove leading "/../", "//", etc. */ + while (p[0] == '/' || p[0] == '\\') { + if (p[1] == '.' && p[2] == '.' && + (p[3] == '/' || p[3] == '\\')) { + p += 3; /* Remove "/..", leave "/" + * for next pass. */ + } else + p += 1; /* Remove "/". */ + } + } while (rp != p); + return (p); +} + /* * This is used by both out mode (to copy objects from disk into * an archive) and pass mode (to copy objects from disk to @@ -585,7 +629,6 @@ file_to_archive(struct cpio *cpio, const char *srcpath) const char *destpath; struct archive_entry *entry, *spare; size_t len; - const char *p; int r; /* @@ -639,10 +682,7 @@ file_to_archive(struct cpio *cpio, const char *srcpath) "Can't allocate path buffer"); } strcpy(cpio->pass_destpath, cpio->destdir); - p = srcpath; - while (p[0] == '/') - ++p; - strcat(cpio->pass_destpath, p); + strcat(cpio->pass_destpath, remove_leading_slash(srcpath)); destpath = cpio->pass_destpath; } if (cpio->option_rename) @@ -1139,12 +1179,24 @@ cpio_rename(const char *name) static char buff[1024]; FILE *t; char *p, *ret; +#if defined(_WIN32) && !defined(__CYGWIN__) + FILE *to; + t = fopen("CONIN$", "r"); + if (t == NULL) + return (name); + to = fopen("CONOUT$", "w"); + if (to == NULL) + return (name); + fprintf(to, "%s (Enter/./(new name))? ", name); + fclose(to); +#else t = fopen("/dev/tty", "r+"); if (t == NULL) return (name); fprintf(t, "%s (Enter/./(new name))? ", name); fflush(t); +#endif p = fgets(buff, sizeof(buff), t); fclose(t); diff --git a/cpio/test/main.c b/cpio/test/main.c index a0c5295860c7..0e040591b4d7 100644 --- a/cpio/test/main.c +++ b/cpio/test/main.c @@ -2289,7 +2289,15 @@ main(int argc, char **argv) j++; } testprogdir[i] = '\0'; +#if defined(_WIN32) && !defined(__CYGWIN__) + if (testprogdir[0] != '/' && testprogdir[0] != '\\' && + !(((testprogdir[0] >= 'a' && testprogdir[0] <= 'z') || + (testprogdir[0] >= 'A' && testprogdir[0] <= 'Z')) && + testprogdir[1] == ':' && + (testprogdir[2] == '/' || testprogdir[2] == '\\'))) +#else if (testprogdir[0] != '/') +#endif { /* Fixup path for relative directories. */ if ((testprogdir = (char *)realloc(testprogdir, @@ -2298,8 +2306,9 @@ main(int argc, char **argv) fprintf(stderr, "ERROR: Out of memory."); exit(1); } - strcpy(testprogdir + strlen(pwd) + 1, testprogdir); - strcpy(testprogdir, pwd); + memmove(testprogdir + strlen(pwd) + 1, testprogdir, + strlen(testprogdir)); + memcpy(testprogdir, pwd, strlen(pwd)); testprogdir[strlen(pwd)] = '/'; } |