diff options
author | rsc <devnull@localhost> | 2005-02-21 15:03:01 +0000 |
---|---|---|
committer | rsc <devnull@localhost> | 2005-02-21 15:03:01 +0000 |
commit | f8d580d82be78a62ed75c348e2d487226992aa30 (patch) | |
tree | 7cfa73506a0e2dc1ec3725c0ceb47e7692268aa8 /src/cmd/gzip | |
parent | 98660df2502a6b2c92c651e6bc3f4a8be6143bb5 (diff) | |
download | plan9port-f8d580d82be78a62ed75c348e2d487226992aa30.tar.gz plan9port-f8d580d82be78a62ed75c348e2d487226992aa30.tar.bz2 plan9port-f8d580d82be78a62ed75c348e2d487226992aa30.zip |
make directories as neeeded
Diffstat (limited to 'src/cmd/gzip')
-rw-r--r-- | src/cmd/gzip/unzip.c | 34 |
1 files changed, 34 insertions, 0 deletions
diff --git a/src/cmd/gzip/unzip.c b/src/cmd/gzip/unzip.c index af9a4ed2..990e4b6d 100644 --- a/src/cmd/gzip/unzip.c +++ b/src/cmd/gzip/unzip.c @@ -331,6 +331,32 @@ sunzip(Biobuf *bin) } } +static int +makedir(char *s) +{ + int f; + + if (access(s, AEXIST) == 0) + return -1; + f = create(s, OREAD, DMDIR | 0777); + if (f >= 0) + close(f); + return f; +} + +static void +mkpdirs(char *s) +{ + int done = 0; + char *p = s; + + while (!done && (p = strchr(p + 1, '/')) != nil) { + *p = '\0'; + done = (access(s, AEXIST) < 0 && makedir(s) < 0); + *p = '/'; + } +} + /* * extracts a single entry from a zip file * czh is the optional corresponding central directory entry @@ -380,6 +406,10 @@ unzipEntry(Biobuf *bin, ZipHead *czh) }else if(isdir){ fd = create(zh.file, OREAD, DMDIR | 0775); if(fd < 0){ + mkpdirs(zh.file); + fd = create(zh.file, OREAD, DMDIR | 0775); + } + if(fd < 0){ d = dirstat(zh.file); if(d == nil || (d->mode & DMDIR) != DMDIR){ fprint(2, "unzip: can't create directory %s: %r\n", zh.file); @@ -390,6 +420,10 @@ unzipEntry(Biobuf *bin, ZipHead *czh) }else if(ok){ fd = create(zh.file, OWRITE, 0664); if(fd < 0){ + mkpdirs(zh.file); + fd = create(zh.file, OWRITE, 0664); + } + if(fd < 0){ fprint(2, "unzip: can't create %s: %r\n", zh.file); ok = 0; }else |