diff options
author | Mark A. Hershberger <mah@debian.(none)> | 2009-03-25 00:37:27 -0400 |
---|---|---|
committer | Mark A. Hershberger <mah@debian.(none)> | 2009-03-25 00:37:27 -0400 |
commit | 2d4e5b09576bb4f0ba716cc82cdf29ea04d9184b (patch) | |
tree | 41ccc042009cba53e4ce43e727fcba4c1cfbf7f3 /ext/zip | |
parent | d29a4fd2dd3b5d4cf6e80b602544d7b71d794e76 (diff) | |
download | php-2d4e5b09576bb4f0ba716cc82cdf29ea04d9184b.tar.gz |
Imported Upstream version 5.2.2upstream/5.2.2
Diffstat (limited to 'ext/zip')
37 files changed, 929 insertions, 257 deletions
diff --git a/ext/zip/TODO b/ext/zip/TODO index cb540ce7a..c1baba97e 100644 --- a/ext/zip/TODO +++ b/ext/zip/TODO @@ -1,4 +1,3 @@ -- fix _zip_replace (add two entries with the same name segfaults) - add pattern support to extract or add files - stream to add or modify entries - crypt support for zip (read and write) diff --git a/ext/zip/config.m4 b/ext/zip/config.m4 index 1ff064c97..9d265eaf3 100644 --- a/ext/zip/config.m4 +++ b/ext/zip/config.m4 @@ -1,5 +1,5 @@ dnl -dnl $Id: config.m4,v 1.8 2006/07/24 16:58:58 pajoye Exp $ +dnl $Id: config.m4,v 1.8.2.2 2006/12/26 09:52:05 pajoye Exp $ dnl PHP_ARG_ENABLE(zip, for zip archive read/writesupport, @@ -40,7 +40,7 @@ if test "$PHP_ZIP" != "no"; then AC_MSG_ERROR([zip support requires ZLIB. Use --with-zlib-dir=<DIR> to specify prefix where ZLIB include and library are located]) else AC_MSG_RESULT([$PHP_ZLIB_DIR]) - PHP_ADD_LIBRARY_WITH_PATH(z, $PHP_ZLIB_DIR/lib, ZIP_SHARED_LIBADD) + PHP_ADD_LIBRARY_WITH_PATH(z, $PHP_ZLIB_DIR/$PHP_LIBDIR, ZIP_SHARED_LIBADD) PHP_ADD_INCLUDE($PHP_ZLIB_INCDIR) fi @@ -59,7 +59,8 @@ if test "$PHP_ZIP" != "no"; then lib/zip_entry_new.c lib/zip_err_str.c lib/zip_fopen_index.c \ lib/zip_new.c lib/zip_source_file.c lib/zip_stat_index.c lib/zip_get_archive_comment.c \ lib/zip_get_file_comment.c lib/zip_set_archive_comment.c lib/zip_set_file_comment.c \ - lib/zip_unchange_archive.c lib/zip_memdup.c" + lib/zip_unchange_archive.c lib/zip_memdup.c lib/zip_stat_init.c lib/zip_add_dir.c \ + lib/zip_error_clear.c lib/zip_file_error_clear.c" AC_DEFINE(HAVE_ZIP,1,[ ]) PHP_NEW_EXTENSION(zip, php_zip.c zip_stream.c $PHP_ZIP_SOURCES, $ext_shared) diff --git a/ext/zip/config.w32 b/ext/zip/config.w32 index 2047ec0f6..a68e0505a 100644 --- a/ext/zip/config.w32 +++ b/ext/zip/config.w32 @@ -1,4 +1,4 @@ -// $Id: config.w32,v 1.1 2006/07/24 16:58:58 pajoye Exp $ +// $Id: config.w32,v 1.1.2.1 2006/11/03 16:46:18 pajoye Exp $ // vim:ft=javascript ARG_ENABLE("zip", "ZIP support", "no"); @@ -26,7 +26,8 @@ if (PHP_ZIP != "no") { zip_new.c zip_source_file.c zip_stat_index.c \ zip_get_archive_comment.c zip_get_file_comment.c \ zip_set_archive_comment.c zip_set_file_comment.c \ - zip_unchange_archive.c zip_memdup.c", "zip"); + zip_unchange_archive.c zip_memdup.c zip_stat_init.c \ + zip_add_dir.c zip_file_error_clear.c zip_error_clear.c", "zip"); AC_DEFINE('HAVE_ZLIB', 1); AC_DEFINE('HAVE_ZIP', 1); diff --git a/ext/zip/lib/zip.h b/ext/zip/lib/zip.h index 8cf690cad..de115d38a 100644 --- a/ext/zip/lib/zip.h +++ b/ext/zip/lib/zip.h @@ -5,7 +5,7 @@ $NiH: zip.h,v 1.57 2006/04/24 14:04:19 dillo Exp $ zip.h -- exported declarations. - Copyright (C) 1999-2006 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <nih@giga.or.at> @@ -163,12 +163,15 @@ struct zip_source; int zip_add(struct zip *, const char *, struct zip_source *); +int zip_add_dir(struct zip *, const char *); int zip_close(struct zip *); int zip_delete(struct zip *, int); +void zip_error_clear(struct zip *); void zip_error_get(struct zip *, int *, int *); int zip_error_get_sys_type(int); int zip_error_to_str(char *, size_t, int, int); int zip_fclose(struct zip_file *); +void zip_file_error_clear(struct zip_file *); void zip_file_error_get(struct zip_file *, int *, int *); const char *zip_file_strerror(struct zip_file *); struct zip_file *zip_fopen(struct zip *, const char *, int); @@ -194,6 +197,7 @@ struct zip_source *zip_source_zip(struct zip *, struct zip *, int, int, off_t, off_t); int zip_stat(struct zip *, const char *, int, struct zip_stat *); int zip_stat_index(struct zip *, int, int, struct zip_stat *); +void zip_stat_init(struct zip_stat *); const char *zip_strerror(struct zip *); int zip_unchange(struct zip *, int); int zip_unchange_all(struct zip *); diff --git a/ext/zip/lib/zip_add_dir.c b/ext/zip/lib/zip_add_dir.c new file mode 100644 index 000000000..957aaf1d2 --- /dev/null +++ b/ext/zip/lib/zip_add_dir.c @@ -0,0 +1,83 @@ +/* + $NiH: zip_add_dir.c,v 1.1 2006/10/03 12:23:13 dillo Exp $ + + zip_add_dir.c -- add directory + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner + + This file is part of libzip, a library to manipulate ZIP archives. + The authors can be contacted at <nih@giga.or.at> + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + 3. The names of the authors may not be used to endorse or promote + products derived from this software without specific prior + written permission. + + THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS + OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + + + +#include <stdlib.h> +#include <string.h> + +#include "zip.h" +#include "zipint.h" + + + +int +zip_add_dir(struct zip *za, const char *name) +{ + int len, ret; + char *s; + struct zip_source *source; + + if (name == NULL) { + _zip_error_set(&za->error, ZIP_ER_INVAL, 0); + return -1; + } + + s = NULL; + len = strlen(name); + + if (name[len-1] != '/') { + if ((s=(char *)malloc(len+2)) == NULL) { + _zip_error_set(&za->error, ZIP_ER_MEMORY, 0); + return -1; + } + strcpy(s, name); + s[len] = '/'; + s[len+1] = '\0'; + } + + if ((source=zip_source_buffer(za, NULL, 0, 0)) == NULL) { + free(s); + return -1; + } + + ret = _zip_replace(za, -1, s ? s : name, source); + + free(s); + if (ret < 0) + zip_source_free(source); + + return ret; +} diff --git a/ext/zip/lib/zip_close.c b/ext/zip/lib/zip_close.c index 3cb324d9c..e701321a8 100644 --- a/ext/zip/lib/zip_close.c +++ b/ext/zip/lib/zip_close.c @@ -247,7 +247,7 @@ zip_close(struct zip *za) chmod(za->zn, 0666&~mask); _zip_free(za); - + free(temp); return 0; } @@ -527,13 +527,14 @@ _zip_create_temp_output(struct zip *za, FILE **outp) char *temp; int tfd; FILE *tfp; + int len = strlen(za->zn) + 8; - if ((temp=(char *)malloc(strlen(za->zn)+8)) == NULL) { + if ((temp=(char *)malloc(len)) == NULL) { _zip_error_set(&za->error, ZIP_ER_MEMORY, 0); return NULL; } - sprintf(temp, "%s.XXXXXX", za->zn); + snprintf(temp, len, "%s.XXXXXX", za->zn); if ((tfd=mkstemp(temp)) == -1) { _zip_error_set(&za->error, ZIP_ER_TMPOPEN, errno); @@ -548,6 +549,9 @@ _zip_create_temp_output(struct zip *za, FILE **outp) free(temp); return NULL; } +#ifdef PHP_WIN32 + _setmode(_fileno(tfp), _O_BINARY ); +#endif *outp = tfp; return temp; diff --git a/ext/zip/lib/zip_dirent.c b/ext/zip/lib/zip_dirent.c index f0c988bc7..8423ad534 100644 --- a/ext/zip/lib/zip_dirent.c +++ b/ext/zip/lib/zip_dirent.c @@ -33,8 +33,7 @@ IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ - - +#include "main/php_reentrancy.h" #include <stdio.h> #include <stdlib.h> #include <string.h> @@ -391,11 +390,11 @@ _zip_dirent_write(struct zip_dirent *zde, FILE *fp, int localp, static time_t _zip_d2u_time(int dtime, int ddate) { - struct tm *tm; + struct tm *tm, tmbuf; time_t now; now = time(NULL); - tm = localtime(&now); + tm = php_localtime_r(&now, &tmbuf); tm->tm_year = ((ddate>>9)&127) + 1980 - 1900; tm->tm_mon = ((ddate>>5)&15) - 1; @@ -520,9 +519,9 @@ _zip_write4(unsigned int i, FILE *fp) static void _zip_u2d_time(time_t time, unsigned short *dtime, unsigned short *ddate) { - struct tm *tm; + struct tm *tm, tmbuf; - tm = localtime(&time); + tm = php_localtime_r(&time, &tmbuf); *ddate = ((tm->tm_year+1900-1980)<<9) + ((tm->tm_mon+1)<<5) + tm->tm_mday; *dtime = ((tm->tm_hour)<<11) + ((tm->tm_min)<<5) diff --git a/ext/zip/lib/zip_error.c b/ext/zip/lib/zip_error.c index 33a8f3374..aec1638de 100644 --- a/ext/zip/lib/zip_error.c +++ b/ext/zip/lib/zip_error.c @@ -2,7 +2,7 @@ $NiH: zip_error.c,v 1.7 2005/06/09 19:57:09 dillo Exp $ zip_error.c -- struct zip_error helper functions - Copyright (C) 1999, 2003, 2004, 2005 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <nih@giga.or.at> @@ -43,6 +43,15 @@ void +_zip_error_clear(struct zip_error *err) +{ + err->zip_err = ZIP_ER_OK; + err->sys_err = 0; +} + + + +void _zip_error_copy(struct zip_error *dst, struct zip_error *src) { dst->zip_err = src->zip_err; @@ -78,7 +87,7 @@ _zip_error_get(struct zip_error *err, int *zep, int *sep) void _zip_error_init(struct zip_error *err) { - err->zip_err = 0; + err->zip_err = ZIP_ER_OK; err->sys_err = 0; err->str = NULL; } diff --git a/ext/zip/lib/zip_error_clear.c b/ext/zip/lib/zip_error_clear.c new file mode 100644 index 000000000..e3c81eb31 --- /dev/null +++ b/ext/zip/lib/zip_error_clear.c @@ -0,0 +1,47 @@ +/* + $NiH: zip_error_clear.c,v 1.1 2006/10/04 15:21:09 dillo Exp $ + + zip_error_clear.c -- clear zip error + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner + + This file is part of libzip, a library to manipulate ZIP archives. + The authors can be contacted at <nih@giga.or.at> + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + 3. The names of the authors may not be used to endorse or promote + products derived from this software without specific prior + written permission. + + THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS + OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + + + +#include "zip.h" +#include "zipint.h" + + + +void +zip_error_clear(struct zip *za) +{ + _zip_error_clear(&za->error); +} diff --git a/ext/zip/lib/zip_error_strerror.c b/ext/zip/lib/zip_error_strerror.c index f14f7190e..e6eee081d 100644 --- a/ext/zip/lib/zip_error_strerror.c +++ b/ext/zip/lib/zip_error_strerror.c @@ -54,7 +54,7 @@ _zip_error_strerror(struct zip_error *err) _zip_error_fini(err); if (err->zip_err < 0 || err->zip_err >= _zip_nerr_str) { - sprintf(buf, "Unknown error %d", err->zip_err); + snprintf(buf, sizeof(buf), "Unknown error %d", err->zip_err); zs = NULL; ss = buf; } @@ -78,11 +78,11 @@ _zip_error_strerror(struct zip_error *err) if (ss == NULL) return zs; else { - if ((s=(char *)malloc(strlen(ss) - + (zs ? strlen(zs)+2 : 0) + 1)) == NULL) + int l = strlen(ss) + (zs ? strlen(zs)+2 : 0) + 1; + if ((s=(char *)malloc(l)) == NULL) return _zip_err_str[ZIP_ER_MEMORY]; - sprintf(s, "%s%s%s", + snprintf(s, l, "%s%s%s", (zs ? zs : ""), (zs ? ": " : ""), ss); diff --git a/ext/zip/lib/zip_fclose.c b/ext/zip/lib/zip_fclose.c index cf4f35c71..c0105a929 100644 --- a/ext/zip/lib/zip_fclose.c +++ b/ext/zip/lib/zip_fclose.c @@ -52,13 +52,15 @@ zip_fclose(struct zip_file *zf) free(zf->buffer); free(zf->zstr); - for (i=0; i<zf->za->nfile; i++) { - if (zf->za->file[i] == zf) { - zf->za->file[i] = zf->za->file[zf->za->nfile-1]; - zf->za->nfile--; - break; + if (zf->za) { + for (i=0; i<zf->za->nfile; i++) { + if (zf->za->file[i] == zf) { + zf->za->file[i] = zf->za->file[zf->za->nfile-1]; + zf->za->nfile--; + break; + } + } } - } ret = 0; if (zf->error.zip_err) diff --git a/ext/zip/lib/zip_file_error_clear.c b/ext/zip/lib/zip_file_error_clear.c new file mode 100644 index 000000000..86ed68f27 --- /dev/null +++ b/ext/zip/lib/zip_file_error_clear.c @@ -0,0 +1,47 @@ +/* + $NiH: zip_file_error_clear.c,v 1.4 2006/10/04 18:37:54 wiz Exp $ + + zip_file_error_clear.c -- clear zip file error + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner + + This file is part of libzip, a library to manipulate ZIP archives. + The authors can be contacted at <nih@giga.or.at> + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + 3. The names of the authors may not be used to endorse or promote + products derived from this software without specific prior + written permission. + + THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS + OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + + + +#include "zip.h" +#include "zipint.h" + + + +void +zip_file_error_clear(struct zip_file *zf) +{ + _zip_error_clear(&zf->error); +} diff --git a/ext/zip/lib/zip_free.c b/ext/zip/lib/zip_free.c index cbead2a6b..c78697d25 100644 --- a/ext/zip/lib/zip_free.c +++ b/ext/zip/lib/zip_free.c @@ -59,6 +59,9 @@ _zip_free(struct zip *za) if (za->zp) fclose(za->zp); + if (za->ch_comment) + free(za->ch_comment); + _zip_cdir_free(za->cdir); if (za->entry) { diff --git a/ext/zip/lib/zip_get_archive_comment.c b/ext/zip/lib/zip_get_archive_comment.c index 40feb4eba..7844c5e19 100644 --- a/ext/zip/lib/zip_get_archive_comment.c +++ b/ext/zip/lib/zip_get_archive_comment.c @@ -47,7 +47,7 @@ zip_get_archive_comment(struct zip *za, int *lenp, int flags) || (za->ch_comment_len == -1)) { if (za->cdir) { if (lenp != NULL) - *lenp = za->cdir->comment_len; + *lenp = za->cdir->comment_len; return za->cdir->comment; } } diff --git a/ext/zip/lib/zip_open.c b/ext/zip/lib/zip_open.c index 0a14abda5..60526e8c9 100644 --- a/ext/zip/lib/zip_open.c +++ b/ext/zip/lib/zip_open.c @@ -2,7 +2,7 @@ $NiH: zip_open.c,v 1.38 2006/05/04 00:01:26 dillo Exp $ zip_open.c -- open zip archive - Copyright (C) 1999-2006 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <nih@giga.or.at> @@ -100,7 +100,6 @@ zip_open(const char *fn, int flags, int *zep) return NULL; } - /* ZIP_CREATE gets ignored if file exists and not ZIP_EXCL, just like open() */ if ((fp=fopen(fn, "rb")) == NULL) { @@ -108,6 +107,10 @@ zip_open(const char *fn, int flags, int *zep) return NULL; } +#ifdef PHP_WIN32 + _setmode(_fileno(fp), _O_BINARY ); +#endif + clearerr(fp); fseek(fp, 0, SEEK_END); len = ftell(fp); diff --git a/ext/zip/lib/zip_set_archive_comment.c b/ext/zip/lib/zip_set_archive_comment.c index 51a8416da..b0929e56b 100644 --- a/ext/zip/lib/zip_set_archive_comment.c +++ b/ext/zip/lib/zip_set_archive_comment.c @@ -60,7 +60,7 @@ zip_set_archive_comment(struct zip *za, const char *comment, int len) else tmpcom = NULL; - free(za->ch_comment); + if (za->ch_comment) free(za->ch_comment); za->ch_comment = tmpcom; za->ch_comment_len = len; diff --git a/ext/zip/lib/zip_source_buffer.c b/ext/zip/lib/zip_source_buffer.c index ada9ae85f..a01f18d3f 100644 --- a/ext/zip/lib/zip_source_buffer.c +++ b/ext/zip/lib/zip_source_buffer.c @@ -2,7 +2,7 @@ $NiH: zip_source_buffer.c,v 1.8 2006/04/23 14:50:49 wiz Exp $ zip_source_buffer.c -- create zip data source from buffer - Copyright (C) 1999, 2003, 2004, 2005 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <nih@giga.or.at> @@ -125,11 +125,9 @@ read_data(void *state, void *data, size_t len, enum zip_source_cmd cmd) st = (struct zip_stat *)data; + zip_stat_init(st); st->mtime = z->mtime; - st->crc = 0; st->size = z->end - z->data; - st->comp_size = -1; - st->comp_method = ZIP_CM_STORE; return sizeof(*st); } diff --git a/ext/zip/lib/zip_source_file.c b/ext/zip/lib/zip_source_file.c index f06b32fec..d635da342 100644 --- a/ext/zip/lib/zip_source_file.c +++ b/ext/zip/lib/zip_source_file.c @@ -62,6 +62,10 @@ zip_source_file(struct zip *za, const char *fname, off_t start, off_t len) return NULL; } +#ifdef PHP_WIN32 + _setmode(_fileno(fp), _O_BINARY ); +#endif + if ((zs=zip_source_filep(za, fp, start, len)) == NULL) { fclose(fp); return NULL; diff --git a/ext/zip/lib/zip_source_filep.c b/ext/zip/lib/zip_source_filep.c index 9c7383cf2..efc702686 100644 --- a/ext/zip/lib/zip_source_filep.c +++ b/ext/zip/lib/zip_source_filep.c @@ -2,7 +2,7 @@ $NiH: zip_source_filep.c,v 1.6 2005/06/09 19:57:10 dillo Exp $ zip_source_filep.c -- create data source from FILE * - Copyright (C) 1999, 2003, 2004, 2005 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2007 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <nih@giga.or.at> @@ -138,24 +138,20 @@ read_file(void *state, void *data, size_t len, enum zip_source_cmd cmd) if (len < sizeof(*st)) return -1; - st = (struct zip_stat *)data; - if (fstat(fileno(z->f), &fst) != 0) { z->e[0] = ZIP_ER_READ; /* best match */ z->e[1] = errno; return -1; } + st = (struct zip_stat *)data; + + zip_stat_init(st); st->mtime = fst.st_mtime; - st->crc = 0; if (z->len != -1) st->size = z->len; else if ((fst.st_mode&S_IFMT) == S_IFREG) st->size = fst.st_size; - else - st->size = -1; - st->comp_size = -1; - st->comp_method = ZIP_CM_STORE; return sizeof(*st); } diff --git a/ext/zip/lib/zip_stat_index.c b/ext/zip/lib/zip_stat_index.c index 837d63907..bab79a74b 100644 --- a/ext/zip/lib/zip_stat_index.c +++ b/ext/zip/lib/zip_stat_index.c @@ -67,8 +67,7 @@ zip_stat_index(struct zip *za, int index, int flags, struct zip_stat *st) _zip_error_set(&za->error, ZIP_ER_INVAL, 0); return -1; } - - st->index = index; + st->crc = za->cdir->entry[index].crc; st->size = za->cdir->entry[index].uncomp_size; st->mtime = za->cdir->entry[index].last_mod; @@ -87,6 +86,7 @@ zip_stat_index(struct zip *za, int index, int flags, struct zip_stat *st) /* st->bitflags = za->cdir->entry[index].bitflags; */ } + st->index = index; st->name = name; return 0; diff --git a/ext/zip/lib/zip_stat_init.c b/ext/zip/lib/zip_stat_init.c new file mode 100644 index 000000000..7ab0f4da7 --- /dev/null +++ b/ext/zip/lib/zip_stat_init.c @@ -0,0 +1,53 @@ +/* + $NiH: zip_stat_init.c,v 1.1 2006/10/31 12:03:04 dillo Exp $ + + zip_stat_init.c -- initialize struct zip_stat. + Copyright (C) 2006 Dieter Baron and Thomas Klausner + + This file is part of libzip, a library to manipulate ZIP archives. + The authors can be contacted at <nih@giga.or.at> + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + 3. The names of the authors may not be used to endorse or promote + products derived from this software without specific prior + written permission. + + THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS + OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER + IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + + + +#include "zipint.h" + + + +void +zip_stat_init(struct zip_stat *st) +{ + st->name = NULL; + st->index = -1; + st->crc = 0; + st->mtime = (time_t)-1; + st->size = -1; + st->comp_size = -1; + st->comp_method = ZIP_CM_STORE; + st->encryption_method = ZIP_EM_NONE; +} diff --git a/ext/zip/lib/zipint.h b/ext/zip/lib/zipint.h index 9efaf06a3..ebf2743f9 100644 --- a/ext/zip/lib/zipint.h +++ b/ext/zip/lib/zipint.h @@ -199,6 +199,7 @@ void _zip_entry_free(struct zip_entry *); void _zip_entry_init(struct zip *, int); struct zip_entry *_zip_entry_new(struct zip *); +void _zip_error_clear(struct zip_error *); void _zip_error_copy(struct zip_error *, struct zip_error *); void _zip_error_fini(struct zip_error *); void _zip_error_get(struct zip_error *, int *, int *); diff --git a/ext/zip/php_zip.c b/ext/zip/php_zip.c index 45ecdb951..0ddf9501b 100644 --- a/ext/zip/php_zip.c +++ b/ext/zip/php_zip.c @@ -2,7 +2,7 @@ +----------------------------------------------------------------------+ | PHP Version 5 | +----------------------------------------------------------------------+ - | Copyright (c) 1997-2006 The PHP Group | + | Copyright (c) 1997-2007 The PHP Group | +----------------------------------------------------------------------+ | This source file is subject to version 3.01 of the PHP license, | | that is bundled with this package in the file LICENSE, and is | @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: php_zip.c,v 1.1.2.15 2006/09/24 22:27:57 pajoye Exp $ */ +/* $Id: php_zip.c,v 1.1.2.31 2007/03/14 15:02:20 iliaa Exp $ */ #ifdef HAVE_CONFIG_H #include "config.h" @@ -31,6 +31,17 @@ #include "lib/zip.h" #include "lib/zipint.h" +static PHP_FUNCTION(zip_open); +static PHP_FUNCTION(zip_read); +static PHP_FUNCTION(zip_close); +static PHP_FUNCTION(zip_entry_read); +static PHP_FUNCTION(zip_entry_filesize); +static PHP_FUNCTION(zip_entry_name); +static PHP_FUNCTION(zip_entry_compressedsize); +static PHP_FUNCTION(zip_entry_compressionmethod); +static PHP_FUNCTION(zip_entry_open); +static PHP_FUNCTION(zip_entry_close); + /* {{{ Resource le */ static int le_zip_dir; #define le_zip_dir_name "Zip Directory" @@ -38,11 +49,6 @@ static int le_zip_entry; #define le_zip_entry_name "Zip Entry" /* }}} */ -/* {{{ SAFEMODE_CHECKFILE(filename) */ -#define SAFEMODE_CHECKFILE(filename) \ - (PG(safe_mode) && (!php_checkuid(filename, NULL, CHECKUID_CHECK_FILE_AND_DIR))) || php_check_open_basedir(filename TSRMLS_CC) -/* }}} */ - /* {{{ PHP_ZIP_STAT_INDEX(za, index, flags, sb) */ #define PHP_ZIP_STAT_INDEX(za, index, flags, sb) \ if (zip_stat_index(za, index, flags, &sb) != 0) { \ @@ -70,53 +76,57 @@ static int le_zip_entry; } \ } else if (zip_set_file_comment(intern, index, comment, comment_len) < 0) { \ RETURN_FALSE; \ - } + } \ + RETURN_TRUE; /* }}} */ -#ifdef ZEND_ENGINE_2_1 /* {{{ php_zip_extract_file */ /* TODO: Simplify it */ -static int php_zip_extract_file(struct zip * za, char *dest, char *file TSRMLS_DC) +static int php_zip_extract_file(struct zip * za, char *dest, char *file, int file_len TSRMLS_DC) { php_stream_statbuf ssb; struct zip_file *zf; struct zip_stat sb; - char b[8192]; + char b[8192]; - int n, len, ret, file_len; + int n, len, ret; php_stream *stream; char *fullpath; char *file_dirname_fullpath; - char file_dirname[MAXPATHLEN + 1]; + char file_dirname[MAXPATHLEN]; size_t dir_len; char *file_basename; size_t file_basename_len; + int is_dir_only = 0; - if (zip_stat(za, file, 0, &sb)) { + if (file_len >= MAXPATHLEN || zip_stat(za, file, 0, &sb)) { return 0; } - file_len = strlen(file); - memcpy(file_dirname, file, file_len); - - dir_len = php_dirname(file_dirname, file_len); - - if (dir_len > 0) { - len = spprintf(&file_dirname_fullpath, 0, "%s/%s", dest, file_dirname); + if (file_len > 1 && file[file_len - 1] == '/') { + len = spprintf(&file_dirname_fullpath, 0, "%s/%s", dest, file); + is_dir_only = 1; } else { - len = spprintf(&file_dirname_fullpath, 0, "%s", dest); - } + memcpy(file_dirname, file, file_len); + dir_len = php_dirname(file_dirname, file_len); - php_basename(file, file_len, NULL, 0, &file_basename, &file_basename_len TSRMLS_CC); + if (dir_len > 0) { + len = spprintf(&file_dirname_fullpath, 0, "%s/%s", dest, file_dirname); + } else { + len = spprintf(&file_dirname_fullpath, 0, "%s", dest); + } - if (SAFEMODE_CHECKFILE(file_dirname_fullpath)) { - efree(file_dirname_fullpath); - efree(file_basename); - return 0; + php_basename(file, file_len, NULL, 0, &file_basename, (unsigned int *)&file_basename_len TSRMLS_CC); + + if (OPENBASEDIR_CHECKPATH(file_dirname_fullpath)) { + efree(file_dirname_fullpath); + efree(file_basename); + return 0; + } } /* let see if the path already exists */ @@ -132,7 +142,9 @@ static int php_zip_extract_file(struct zip * za, char *dest, char *file TSRMLS_D /* it is a standalone directory, job done */ if (file[file_len - 1] == '/') { efree(file_dirname_fullpath); - efree(file_basename); + if (!is_dir_only) { + efree(file_basename); + } return 1; } @@ -147,7 +159,8 @@ static int php_zip_extract_file(struct zip * za, char *dest, char *file TSRMLS_D * is required, does a file can have a different * safemode status as its parent folder? */ - if (SAFEMODE_CHECKFILE(fullpath)) { + if (OPENBASEDIR_CHECKPATH(fullpath)) { + efree(fullpath); efree(file_dirname_fullpath); efree(file_basename); return 0; @@ -202,7 +215,7 @@ static int php_zip_extract_file(struct zip * za, char *dest, char *file TSRMLS_D #define RETURN_SB(sb) \ { \ array_init(return_value); \ - add_assoc_string(return_value, "name", estrdup((sb)->name), 0); \ + add_assoc_string(return_value, "name", (char *)(sb)->name, 1); \ add_assoc_long(return_value, "index", (long) (sb)->index); \ add_assoc_long(return_value, "crc", (long) (sb)->crc); \ add_assoc_long(return_value, "size", (long) (sb)->size); \ @@ -258,8 +271,6 @@ static char * php_zipobj_get_zip_comment(struct zip *za, int *len TSRMLS_DC) /* } /* }}} */ -#endif - /* {{{ zend_function_entry */ static zend_function_entry zip_functions[] = { PHP_FE(zip_open, NULL) @@ -278,8 +289,7 @@ static zend_function_entry zip_functions[] = { /* }}} */ /* {{{ ZE2 OO definitions */ -#ifdef ZEND_ENGINE_2_1 -zend_class_entry *zip_class_entry; +static zend_class_entry *zip_class_entry; static zend_object_handlers zip_object_handlers; static HashTable zip_prop_handlers; @@ -295,10 +305,8 @@ typedef struct _zip_prop_handler { int type; } zip_prop_handler; -#endif /* }}} */ -#ifdef ZEND_ENGINE_2_1 static void php_zip_register_prop_handler(HashTable *prop_handler, char *name, zip_read_int_t read_int_func, zip_read_const_char_t read_char_func, zip_read_const_char_from_ze_t read_char_from_obj_func, int rettype TSRMLS_DC) /* {{{ */ { zip_prop_handler hnd; @@ -361,7 +369,7 @@ static int php_zip_property_reader(ze_zip_object *obj, zip_prop_handler *hnd, zv } /* }}} */ -zval **php_zip_get_property_ptr_ptr(zval *object, zval *member TSRMLS_DC) /* {{{ */ +static zval **php_zip_get_property_ptr_ptr(zval *object, zval *member TSRMLS_DC) /* {{{ */ { ze_zip_object *obj; zval tmp_member; @@ -398,7 +406,7 @@ zval **php_zip_get_property_ptr_ptr(zval *object, zval *member TSRMLS_DC) /* {{{ } /* }}} */ -zval* php_zip_read_property(zval *object, zval *member, int type TSRMLS_DC) /* {{{ */ +static zval* php_zip_read_property(zval *object, zval *member, int type TSRMLS_DC) /* {{{ */ { ze_zip_object *obj; zval tmp_member; @@ -484,7 +492,9 @@ static void php_zip_object_free_storage(void *object TSRMLS_DC) /* {{{ */ return; } if (intern->za) { - zip_close(intern->za); + if (zip_close(intern->za) != 0) { + _zip_free(intern->za); + } intern->za = NULL; } @@ -496,20 +506,7 @@ static void php_zip_object_free_storage(void *object TSRMLS_DC) /* {{{ */ } intern->za = NULL; - -#if (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION == 1 && PHP_RELEASE_VERSION > 2) || (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION > 1) || (PHP_MAJOR_VERSION > 5) zend_object_std_dtor(&intern->zo TSRMLS_CC); -#else - if (intern->zo.guards) { - zend_hash_destroy(intern->zo.guards); - FREE_HASHTABLE(intern->zo.guards); - } - - if (intern->zo.properties) { - zend_hash_destroy(intern->zo.properties); - FREE_HASHTABLE(intern->zo.properties); - } -#endif if (intern->filename) { efree(intern->filename); @@ -518,7 +515,7 @@ static void php_zip_object_free_storage(void *object TSRMLS_DC) /* {{{ */ } /* }}} */ -PHP_ZIP_API zend_object_value php_zip_object_new(zend_class_entry *class_type TSRMLS_DC) /* {{{ */ +static zend_object_value php_zip_object_new(zend_class_entry *class_type TSRMLS_DC) /* {{{ */ { ze_zip_object *intern; zval *tmp; @@ -547,7 +544,6 @@ PHP_ZIP_API zend_object_value php_zip_object_new(zend_class_entry *class_type TS return retval; } /* }}} */ -#endif /* {{{ Resource dtors */ @@ -558,7 +554,10 @@ static void php_zip_free_dir(zend_rsrc_list_entry *rsrc TSRMLS_DC) if (zip_int) { if (zip_int->za) { - zip_close(zip_int->za); + if (zip_close(zip_int->za) != 0) { + _zip_free(zip_int->za); + } + zip_int->za = NULL; } efree(rsrc->ptr); @@ -573,17 +572,23 @@ static void php_zip_free_entry(zend_rsrc_list_entry *rsrc TSRMLS_DC) { zip_read_rsrc *zr_rsrc = (zip_read_rsrc *) rsrc->ptr; - efree(zr_rsrc); - rsrc->ptr = NULL; + if (zr_rsrc) { + if (zr_rsrc->zf) { + zip_fclose(zr_rsrc->zf); + zr_rsrc->zf = NULL; + } + efree(zr_rsrc); + rsrc->ptr = NULL; + } } /* }}} */ /* }}}*/ /* {{{ function prototypes */ -PHP_MINIT_FUNCTION(zip); -PHP_MSHUTDOWN_FUNCTION(zip); -PHP_MINFO_FUNCTION(zip); +static PHP_MINIT_FUNCTION(zip); +static PHP_MSHUTDOWN_FUNCTION(zip); +static PHP_MINFO_FUNCTION(zip); /* }}} */ /* {{{ zip_module_entry @@ -608,17 +613,28 @@ ZEND_GET_MODULE(zip) /* {{{ proto resource zip_open(string filename) Create new zip using source uri for output */ -PHP_FUNCTION(zip_open) +static PHP_FUNCTION(zip_open) { char *filename; int filename_len; + char resolved_path[MAXPATHLEN + 1]; zip_rsrc *rsrc_int; int err = 0; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &filename, &filename_len) == FAILURE) { return; } - if (SAFEMODE_CHECKFILE(filename)) { + + if (filename_len == 0) { + php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty string as source"); + RETURN_FALSE; + } + + if (OPENBASEDIR_CHECKPATH(filename)) { + RETURN_FALSE; + } + + if(!expand_filepath(filename, resolved_path TSRMLS_CC)) { RETURN_FALSE; } @@ -639,7 +655,7 @@ PHP_FUNCTION(zip_open) /* {{{ proto void zip_close(resource zip) Close a Zip archive */ -PHP_FUNCTION(zip_close) +static PHP_FUNCTION(zip_close) { zval * zip; zip_rsrc *z_rsrc = NULL; @@ -656,7 +672,7 @@ PHP_FUNCTION(zip_close) /* {{{ proto resource zip_read(resource zip) Returns the next file in the archive */ -PHP_FUNCTION(zip_read) +static PHP_FUNCTION(zip_read) { zval *zip_dp; zip_read_rsrc *zr_rsrc; @@ -687,6 +703,7 @@ PHP_FUNCTION(zip_read) rsrc_int->index_current++; ZEND_REGISTER_RESOURCE(return_value, zr_rsrc, le_zip_entry); } else { + efree(zr_rsrc); RETURN_FALSE; } @@ -699,7 +716,7 @@ PHP_FUNCTION(zip_read) /* {{{ proto bool zip_entry_open(resource zip_dp, resource zip_entry [, string mode]) Open a Zip File, pointed by the resource entry */ /* Dummy function to follow the old API */ -PHP_FUNCTION(zip_entry_open) +static PHP_FUNCTION(zip_entry_open) { zval * zip; zval * zip_entry; @@ -726,7 +743,7 @@ PHP_FUNCTION(zip_entry_open) /* {{{ proto void zip_entry_close(resource zip_ent) Close a zip entry */ /* another dummy function to fit in the old api*/ -PHP_FUNCTION(zip_entry_close) +static PHP_FUNCTION(zip_entry_close) { zval * zip_entry; zip_read_rsrc * zr_rsrc; @@ -743,7 +760,7 @@ PHP_FUNCTION(zip_entry_close) /* {{{ proto mixed zip_entry_read(resource zip_entry [, int len]) Read from an open directory entry */ -PHP_FUNCTION(zip_entry_read) +static PHP_FUNCTION(zip_entry_read) { zval * zip_entry; long len = 0; @@ -768,6 +785,7 @@ PHP_FUNCTION(zip_entry_read) buffer[n] = 0; RETURN_STRINGL(buffer, n, 0); } else { + efree(buffer); RETURN_EMPTY_STRING() } } else { @@ -842,7 +860,7 @@ static void php_zip_entry_get_info(INTERNAL_FUNCTION_PARAMETERS, int opt) /* {{{ /* {{{ proto string zip_entry_name(resource zip_entry) Return the name given a ZZip entry */ -PHP_FUNCTION(zip_entry_name) +static PHP_FUNCTION(zip_entry_name) { php_zip_entry_get_info(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0); } @@ -850,7 +868,7 @@ PHP_FUNCTION(zip_entry_name) /* {{{ proto int zip_entry_compressedsize(resource zip_entry) Return the compressed size of a ZZip entry */ -PHP_FUNCTION(zip_entry_compressedsize) +static PHP_FUNCTION(zip_entry_compressedsize) { php_zip_entry_get_info(INTERNAL_FUNCTION_PARAM_PASSTHRU, 1); } @@ -858,7 +876,7 @@ PHP_FUNCTION(zip_entry_compressedsize) /* {{{ proto int zip_entry_filesize(resource zip_entry) Return the actual filesize of a ZZip entry */ -PHP_FUNCTION(zip_entry_filesize) +static PHP_FUNCTION(zip_entry_filesize) { php_zip_entry_get_info(INTERNAL_FUNCTION_PARAM_PASSTHRU, 2); } @@ -866,29 +884,27 @@ PHP_FUNCTION(zip_entry_filesize) /* {{{ proto string zip_entry_compressionmethod(resource zip_entry) Return a string containing the compression method used on a particular entry */ -PHP_FUNCTION(zip_entry_compressionmethod) +static PHP_FUNCTION(zip_entry_compressionmethod) { php_zip_entry_get_info(INTERNAL_FUNCTION_PARAM_PASSTHRU, 3); } /* }}} */ -#ifdef ZEND_ENGINE_2_1 /* {{{ proto mixed open(string source [, int flags]) Create new zip using source uri for output, return TRUE on success or the error code */ -ZIPARCHIVE_METHOD(open) +static ZIPARCHIVE_METHOD(open) { struct zip *intern; char *filename; int filename_len; int err = 0; long flags = 0; - char resolved_path[MAXPATHLEN + 1]; + char resolved_path[MAXPATHLEN]; zval *this = getThis(); ze_zip_object *ze_obj = NULL; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &filename, &filename_len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -902,31 +918,39 @@ ZIPARCHIVE_METHOD(open) RETURN_FALSE; } + if (OPENBASEDIR_CHECKPATH(filename)) { + RETURN_FALSE; + } + if (!expand_filepath(filename, resolved_path TSRMLS_CC)) { RETURN_FALSE; } if (ze_obj->za) { /* we already have an opened zip, free it */ - zip_close(ze_obj->za); + if (zip_close(ze_obj->za) != 0) { + _zip_free(ze_obj->za); + } + ze_obj->za = NULL; } if (ze_obj->filename) { efree(ze_obj->filename); + ze_obj->filename = NULL; } intern = zip_open(resolved_path, flags, &err); if (!intern || err) { RETURN_LONG((long)err); } - ze_obj->filename = estrndup(resolved_path, strlen(resolved_path)); + ze_obj->filename = estrdup(resolved_path); ze_obj->filename_len = filename_len; ze_obj->za = intern; RETURN_TRUE; } /* }}} */ -/* {{{ proto resource close() +/* {{{ proto bool close() close the zip archive */ -ZIPARCHIVE_METHOD(close) +static ZIPARCHIVE_METHOD(close) { struct zip *intern; zval *this = getThis(); @@ -953,9 +977,39 @@ ZIPARCHIVE_METHOD(close) } /* }}} */ +/* {{{ proto bool createEmptyDir(string dirname) U +Returns the index of the entry named filename in the archive */ +static ZIPARCHIVE_METHOD(addEmptyDir) +{ + struct zip *intern; + zval *this = getThis(); + char *dirname; + int dirname_len; + + if (!this) { + RETURN_FALSE; + } + + ZIP_FROM_OBJECT(intern, this); + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", + &dirname, &dirname_len) == FAILURE) { + return; + } + if (dirname_len<1) { + RETURN_FALSE; + } + + if (zip_add_dir(intern, (const char *)dirname) < 0) { + RETURN_FALSE; + } + RETURN_TRUE; +} +/* }}} */ + /* {{{ proto bool addFile(string filepath[, string entryname[, int start [, int length]]]) Add a file in a Zip archive using its path and the name to use. */ -ZIPARCHIVE_METHOD(addFile) +static ZIPARCHIVE_METHOD(addFile) { struct zip *intern; zval *this = getThis(); @@ -966,7 +1020,7 @@ ZIPARCHIVE_METHOD(addFile) struct zip_source *zs; long offset_start = 0, offset_len = 0; int cur_idx; - char resolved_path[MAXPATHLEN + 1]; + char resolved_path[MAXPATHLEN]; if (!this) { RETURN_FALSE; @@ -976,7 +1030,6 @@ ZIPARCHIVE_METHOD(addFile) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|sll", &filename, &filename_len, &entry_name, &entry_name_len, &offset_start, &offset_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -990,7 +1043,7 @@ ZIPARCHIVE_METHOD(addFile) entry_name_len = filename_len; } - if (SAFEMODE_CHECKFILE(filename)) { + if (OPENBASEDIR_CHECKPATH(filename)) { RETURN_FALSE; } @@ -1026,9 +1079,9 @@ ZIPARCHIVE_METHOD(addFile) } /* }}} */ -/* {{{ proto resource addFromString(string name, string content) +/* {{{ proto bool addFromString(string name, string content) Add a file using content and the entry name */ -ZIPARCHIVE_METHOD(addFromString) +static ZIPARCHIVE_METHOD(addFromString) { struct zip *intern; zval *this = getThis(); @@ -1047,7 +1100,6 @@ ZIPARCHIVE_METHOD(addFromString) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &name, &name_len, &buffer, &buffer_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1060,8 +1112,8 @@ ZIPARCHIVE_METHOD(addFromString) ze_obj->buffers_cnt++; pos = 0; } - ze_obj->buffers[pos] = (char *)emalloc(buffer_len); - memcpy(ze_obj->buffers[pos], buffer, buffer_len); + ze_obj->buffers[pos] = (char *)emalloc(buffer_len + 1); + memcpy(ze_obj->buffers[pos], buffer, buffer_len + 1); zs = zip_source_buffer(intern, ze_obj->buffers[pos], buffer_len, 0); @@ -1092,9 +1144,9 @@ ZIPARCHIVE_METHOD(addFromString) } /* }}} */ -/* {{{ proto resource statName(string filename[, int flags]) +/* {{{ proto array statName(string filename[, int flags]) Returns the information about a the zip entry filename */ -ZIPARCHIVE_METHOD(statName) +static ZIPARCHIVE_METHOD(statName) { struct zip *intern; zval *this = getThis(); @@ -1111,7 +1163,6 @@ ZIPARCHIVE_METHOD(statName) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &name, &name_len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1123,7 +1174,7 @@ ZIPARCHIVE_METHOD(statName) /* {{{ proto resource statIndex(int index[, int flags]) Returns the zip entry informations using its index */ -ZIPARCHIVE_METHOD(statIndex) +static ZIPARCHIVE_METHOD(statIndex) { struct zip *intern; zval *this = getThis(); @@ -1139,7 +1190,6 @@ ZIPARCHIVE_METHOD(statIndex) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l|l", &index, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1150,9 +1200,9 @@ ZIPARCHIVE_METHOD(statIndex) } /* }}} */ -/* {{{ proto resource locateName(string filename[, int flags]) +/* {{{ proto int locateName(string filename[, int flags]) Returns the index of the entry named filename in the archive */ -ZIPARCHIVE_METHOD(locateName) +static ZIPARCHIVE_METHOD(locateName) { struct zip *intern; zval *this = getThis(); @@ -1169,7 +1219,6 @@ ZIPARCHIVE_METHOD(locateName) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &name, &name_len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } if (name_len<1) { @@ -1191,9 +1240,9 @@ ZIPARCHIVE_METHOD(locateName) } /* }}} */ -/* {{{ proto resource getNameIndex(int index [, int flags]) +/* {{{ proto string getNameIndex(int index [, int flags]) Returns the name of the file at position index */ -ZIPARCHIVE_METHOD(getNameIndex) +static ZIPARCHIVE_METHOD(getNameIndex) { struct zip *intern; zval *this = getThis(); @@ -1208,7 +1257,6 @@ ZIPARCHIVE_METHOD(getNameIndex) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l|l", &index, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1222,9 +1270,9 @@ ZIPARCHIVE_METHOD(getNameIndex) } /* }}} */ -/* {{{ proto resource setArchiveComment(string name, string comment) +/* {{{ proto bool setArchiveComment(string name, string comment) Set or remove (NULL/'') the comment of the archive */ -ZIPARCHIVE_METHOD(setArchiveComment) +static ZIPARCHIVE_METHOD(setArchiveComment) { struct zip *intern; zval *this = getThis(); @@ -1238,7 +1286,6 @@ ZIPARCHIVE_METHOD(setArchiveComment) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &comment, &comment_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } if (zip_set_archive_comment(intern, (const char *)comment, (int)comment_len)) { @@ -1249,9 +1296,9 @@ ZIPARCHIVE_METHOD(setArchiveComment) } /* }}} */ -/* {{{ proto resource getArchiveComment() +/* {{{ proto string getArchiveComment() Returns the comment of an entry using its index */ -ZIPARCHIVE_METHOD(getArchiveComment) +static ZIPARCHIVE_METHOD(getArchiveComment) { struct zip *intern; zval *this = getThis(); @@ -1266,24 +1313,23 @@ ZIPARCHIVE_METHOD(getArchiveComment) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|l", &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } comment = zip_get_archive_comment(intern, &comment_len, (int)flags); - RETURN_STRINGL((char *)comment, comment_len, 1); + RETURN_STRINGL((char *)comment, (long)comment_len, 1); } /* }}} */ -/* {{{ proto resource setCommentName(string name, string comment) +/* {{{ proto bool setCommentName(string name, string comment) Set or remove (NULL/'') the comment of an entry using its Name */ -ZIPARCHIVE_METHOD(setCommentName) +static ZIPARCHIVE_METHOD(setCommentName) { struct zip *intern; zval *this = getThis(); int comment_len, name_len; char * comment, *name; - struct zip_stat sb; + int idx; if (!this) { RETURN_FALSE; @@ -1293,19 +1339,24 @@ ZIPARCHIVE_METHOD(setCommentName) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &name, &name_len, &comment, &comment_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } + if (name_len < 1) { + php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Empty string as entry name"); + } - PHP_ZIP_STAT_PATH(intern, name, name_len, 0, sb); - PHP_ZIP_SET_FILE_COMMENT(intern, sb.index, comment, comment_len); + idx = zip_name_locate(intern, name, 0); + if (idx < 0) { + RETURN_FALSE; + } + PHP_ZIP_SET_FILE_COMMENT(intern, idx, comment, comment_len); } /* }}} */ -/* {{{ proto resource setCommentIndex(int index, string comment) +/* {{{ proto bool setCommentIndex(int index, string comment) Set or remove (NULL/'') the comment of an entry using its index */ -ZIPARCHIVE_METHOD(setCommentIndex) +static ZIPARCHIVE_METHOD(setCommentIndex) { struct zip *intern; zval *this = getThis(); @@ -1322,7 +1373,6 @@ ZIPARCHIVE_METHOD(setCommentIndex) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ls", &index, &comment, &comment_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1331,18 +1381,17 @@ ZIPARCHIVE_METHOD(setCommentIndex) } /* }}} */ -/* {{{ proto resource getCommentName(string name) +/* {{{ proto string getCommentName(string name) Returns the comment of an entry using its name */ -ZIPARCHIVE_METHOD(getCommentName) +static ZIPARCHIVE_METHOD(getCommentName) { struct zip *intern; zval *this = getThis(); - int name_len; + int name_len, idx; long flags = 0; int comment_len = 0; const char * comment; char *name; - struct zip_stat sb; if (!this) { RETURN_FALSE; @@ -1352,19 +1401,26 @@ ZIPARCHIVE_METHOD(getCommentName) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &name, &name_len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } + if (name_len < 1) { + php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Empty string as entry name"); + RETURN_FALSE; + } - PHP_ZIP_STAT_PATH(intern, name, name_len, 0, sb); - comment = zip_get_file_comment(intern, sb.index, &comment_len, (int)flags); - RETURN_STRINGL((char *)comment, comment_len, 1); + idx = zip_name_locate(intern, name, 0); + if (idx < 0) { + RETURN_FALSE; + } + + comment = zip_get_file_comment(intern, idx, &comment_len, (int)flags); + RETURN_STRINGL((char *)comment, (long)comment_len, 1); } /* }}} */ -/* {{{ proto resource getCommentIndex(int index) +/* {{{ proto string getCommentIndex(int index) Returns the comment of an entry using its index */ -ZIPARCHIVE_METHOD(getCommentIndex) +static ZIPARCHIVE_METHOD(getCommentIndex) { struct zip *intern; zval *this = getThis(); @@ -1381,19 +1437,18 @@ ZIPARCHIVE_METHOD(getCommentIndex) if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l|l", &index, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } PHP_ZIP_STAT_INDEX(intern, index, 0, sb); comment = zip_get_file_comment(intern, index, &comment_len, (int)flags); - RETURN_STRINGL((char *)comment, comment_len, 1); + RETURN_STRINGL((char *)comment, (long)comment_len, 1); } /* }}} */ -/* {{{ proto resource deleteIndex(int index) +/* {{{ proto bool deleteIndex(int index) Delete a file using its index */ -ZIPARCHIVE_METHOD(deleteIndex) +static ZIPARCHIVE_METHOD(deleteIndex) { struct zip *intern; zval *this = getThis(); @@ -1406,7 +1461,6 @@ ZIPARCHIVE_METHOD(deleteIndex) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &index) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1422,9 +1476,9 @@ ZIPARCHIVE_METHOD(deleteIndex) } /* }}} */ -/* {{{ proto resource deleteName(string name) +/* {{{ proto bool deleteName(string name) Delete a file using its index */ -ZIPARCHIVE_METHOD(deleteName) +static ZIPARCHIVE_METHOD(deleteName) { struct zip *intern; zval *this = getThis(); @@ -1439,7 +1493,6 @@ ZIPARCHIVE_METHOD(deleteName) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } if (name_len < 1) { @@ -1454,9 +1507,9 @@ ZIPARCHIVE_METHOD(deleteName) } /* }}} */ -/* {{{ proto resource renameIndex(int index, string new_name) +/* {{{ proto bool renameIndex(int index, string new_name) Rename an entry selected by its index to new_name */ -ZIPARCHIVE_METHOD(renameIndex) +static ZIPARCHIVE_METHOD(renameIndex) { struct zip *intern; zval *this = getThis(); @@ -1472,7 +1525,6 @@ ZIPARCHIVE_METHOD(renameIndex) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ls", &index, &new_name, &new_name_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1491,9 +1543,9 @@ ZIPARCHIVE_METHOD(renameIndex) } /* }}} */ -/* {{{ proto resource renameName(string name, string new_name) +/* {{{ proto bool renameName(string name, string new_name) Rename an entry selected by its name to new_name */ -ZIPARCHIVE_METHOD(renameName) +static ZIPARCHIVE_METHOD(renameName) { struct zip *intern; zval *this = getThis(); @@ -1508,7 +1560,6 @@ ZIPARCHIVE_METHOD(renameName) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ss", &name, &name_len, &new_name, &new_name_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1526,9 +1577,9 @@ ZIPARCHIVE_METHOD(renameName) } /* }}} */ -/* {{{ proto resource unchangeIndex(int index) +/* {{{ proto bool unchangeIndex(int index) Changes to the file at position index are reverted */ -ZIPARCHIVE_METHOD(unchangeIndex) +static ZIPARCHIVE_METHOD(unchangeIndex) { struct zip *intern; zval *this = getThis(); @@ -1541,7 +1592,6 @@ ZIPARCHIVE_METHOD(unchangeIndex) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &index) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1557,9 +1607,9 @@ ZIPARCHIVE_METHOD(unchangeIndex) } /* }}} */ -/* {{{ proto resource unchangeName(string name) +/* {{{ proto bool unchangeName(string name) Changes to the file named 'name' are reverted */ -ZIPARCHIVE_METHOD(unchangeName) +static ZIPARCHIVE_METHOD(unchangeName) { struct zip *intern; zval *this = getThis(); @@ -1574,7 +1624,6 @@ ZIPARCHIVE_METHOD(unchangeName) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1592,9 +1641,9 @@ ZIPARCHIVE_METHOD(unchangeName) } /* }}} */ -/* {{{ proto resource unchangeAll() +/* {{{ proto bool unchangeAll() All changes to files and global information in archive are reverted */ -ZIPARCHIVE_METHOD(unchangeAll) +static ZIPARCHIVE_METHOD(unchangeAll) { struct zip *intern; zval *this = getThis(); @@ -1613,9 +1662,9 @@ ZIPARCHIVE_METHOD(unchangeAll) } /* }}} */ -/* {{{ proto resource unchangeAll() +/* {{{ proto bool unchangeAll() Revert all global changes to the archive archive. For now, this only reverts archive comment changes. */ -ZIPARCHIVE_METHOD(unchangeArchive) +static ZIPARCHIVE_METHOD(unchangeArchive) { struct zip *intern; zval *this = getThis(); @@ -1634,14 +1683,14 @@ ZIPARCHIVE_METHOD(unchangeArchive) } /* }}} */ -/* {{{ array resource extractTo(string pathto[, mixed files]) +/* {{{ array bool extractTo(string pathto[, mixed files]) Extract one or more file from a zip archive */ /* TODO: * - allow index or array of indeces * - replace path * - patterns */ -ZIPARCHIVE_METHOD(extractTo) +static ZIPARCHIVE_METHOD(extractTo) { struct zip *intern; @@ -1661,7 +1710,6 @@ ZIPARCHIVE_METHOD(extractTo) } if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|z", &pathto, &pathto_len, &zval_files) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1682,7 +1730,7 @@ ZIPARCHIVE_METHOD(extractTo) switch (Z_TYPE_P(zval_files)) { case IS_STRING: file = Z_STRVAL_P(zval_files); - if (!php_zip_extract_file(intern, pathto, file TSRMLS_CC)) { + if (!php_zip_extract_file(intern, pathto, file, Z_STRLEN_P(zval_files) TSRMLS_CC)) { RETURN_FALSE; } break; @@ -1698,7 +1746,7 @@ ZIPARCHIVE_METHOD(extractTo) break; case IS_STRING: file = Z_STRVAL_PP(zval_file); - if (!php_zip_extract_file(intern, pathto, file TSRMLS_CC)) { + if (!php_zip_extract_file(intern, pathto, file, Z_STRLEN_PP(zval_file) TSRMLS_CC)) { RETURN_FALSE; } break; @@ -1722,7 +1770,7 @@ ZIPARCHIVE_METHOD(extractTo) for (i = 0; i < filecount; i++) { file = (char*)zip_get_name(intern, i, ZIP_FL_UNCHANGED); - if (!php_zip_extract_file(intern, pathto, file TSRMLS_CC)) { + if (!php_zip_extract_file(intern, pathto, file, strlen(file) TSRMLS_CC)) { RETURN_FALSE; } } @@ -1757,13 +1805,11 @@ static void php_zip_get_from(INTERNAL_FUNCTION_PARAMETERS, int type) /* {{{ */ if (type == 1) { if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|ll", &filename, &filename_len, &len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } PHP_ZIP_STAT_PATH(intern, filename, filename_len, flags, sb); } else { if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l|ll", &index, &len, &flags) == FAILURE) { - WRONG_PARAM_COUNT; return; } PHP_ZIP_STAT_INDEX(intern, index, 0, sb); @@ -1786,9 +1832,10 @@ static void php_zip_get_from(INTERNAL_FUNCTION_PARAMETERS, int type) /* {{{ */ RETURN_FALSE; } - buffer = safe_emalloc(len + 1, 1, 1); + buffer = safe_emalloc(len, 1, 2); n = zip_fread(zf, buffer, len); if (n < 1) { + efree(buffer); RETURN_EMPTY_STRING(); } @@ -1798,17 +1845,17 @@ static void php_zip_get_from(INTERNAL_FUNCTION_PARAMETERS, int type) /* {{{ */ } /* }}} */ -/* {{{ proto resource getFromName(string entryname[, int len [, int flags]]) +/* {{{ proto string getFromName(string entryname[, int len [, int flags]]) get the contents of an entry using its name */ -ZIPARCHIVE_METHOD(getFromName) +static ZIPARCHIVE_METHOD(getFromName) { php_zip_get_from(INTERNAL_FUNCTION_PARAM_PASSTHRU, 1); } /* }}} */ -/* {{{ proto resource getFromIndex(string entryname[, int len [, int flags]]) +/* {{{ proto string getFromIndex(string entryname[, int len [, int flags]]) get the contents of an entry using its index */ -ZIPARCHIVE_METHOD(getFromIndex) +static ZIPARCHIVE_METHOD(getFromIndex) { php_zip_get_from(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0); } @@ -1816,7 +1863,7 @@ ZIPARCHIVE_METHOD(getFromIndex) /* {{{ proto resource getStream(string entryname) get a stream for an entry using its name */ -ZIPARCHIVE_METHOD(getStream) +static ZIPARCHIVE_METHOD(getStream) { struct zip *intern; zval *this = getThis(); @@ -1834,7 +1881,6 @@ ZIPARCHIVE_METHOD(getStream) ZIP_FROM_OBJECT(intern, this); if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &filename, &filename_len) == FAILURE) { - WRONG_PARAM_COUNT; return; } @@ -1855,6 +1901,7 @@ ZIPARCHIVE_METHOD(getStream) static zend_function_entry zip_class_functions[] = { ZIPARCHIVE_ME(open, NULL, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(close, NULL, ZEND_ACC_PUBLIC) + ZIPARCHIVE_ME(addEmptyDir, NULL, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(addFromString, NULL, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(addFile, NULL, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(renameIndex, NULL, ZEND_ACC_PUBLIC) @@ -1882,17 +1929,15 @@ static zend_function_entry zip_class_functions[] = { {NULL, NULL, NULL} }; /* }}} */ -#endif /* {{{ PHP_MINIT_FUNCTION */ -PHP_MINIT_FUNCTION(zip) +static PHP_MINIT_FUNCTION(zip) { -#ifdef ZEND_ENGINE_2_1 zend_class_entry ce; memcpy(&zip_object_handlers, zend_get_std_object_handlers(), sizeof(zend_object_handlers)); zip_object_handlers.clone_obj = NULL; - zip_object_handlers.get_property_ptr_ptr = php_zip_get_property_ptr_ptr; + zip_object_handlers.get_property_ptr_ptr = php_zip_get_property_ptr_ptr; zip_object_handlers.get_properties = php_zip_get_properties; zip_object_handlers.read_property = php_zip_read_property; @@ -1956,7 +2001,6 @@ PHP_MINIT_FUNCTION(zip) REGISTER_ZIP_CLASS_CONST_LONG("ER_DELETED", ZIP_ER_DELETED); /* N Entry has been deleted */ php_register_url_stream_wrapper("zip", &php_stream_zip_wrapper TSRMLS_CC); -#endif le_zip_dir = zend_register_list_destructors_ex(php_zip_free_dir, NULL, le_zip_dir_name, module_number); le_zip_entry = zend_register_list_destructors_ex(php_zip_free_entry, NULL, le_zip_entry_name, module_number); @@ -1967,24 +2011,23 @@ PHP_MINIT_FUNCTION(zip) /* {{{ PHP_MSHUTDOWN_FUNCTION */ -PHP_MSHUTDOWN_FUNCTION(zip) +static PHP_MSHUTDOWN_FUNCTION(zip) { -#ifdef ZEND_ENGINE_2_1 zend_hash_destroy(&zip_prop_handlers); php_unregister_url_stream_wrapper("zip" TSRMLS_CC); -#endif + return SUCCESS; } /* }}} */ /* {{{ PHP_MINFO_FUNCTION */ -PHP_MINFO_FUNCTION(zip) +static PHP_MINFO_FUNCTION(zip) { php_info_print_table_start(); php_info_print_table_row(2, "Zip", "enabled"); - php_info_print_table_row(2, "Extension Version","$Id: php_zip.c,v 1.1.2.15 2006/09/24 22:27:57 pajoye Exp $"); + php_info_print_table_row(2, "Extension Version","$Id: php_zip.c,v 1.1.2.31 2007/03/14 15:02:20 iliaa Exp $"); php_info_print_table_row(2, "Zip version", "2.0.0"); php_info_print_table_row(2, "Libzip version", "0.7.1"); diff --git a/ext/zip/php_zip.h b/ext/zip/php_zip.h index 5bac110b4..498bdc919 100644 --- a/ext/zip/php_zip.h +++ b/ext/zip/php_zip.h @@ -2,7 +2,7 @@ +----------------------------------------------------------------------+ | PHP Version 5 | +----------------------------------------------------------------------+ - | Copyright (c) 1997-2006 The PHP Group | + | Copyright (c) 1997-2007 The PHP Group | +----------------------------------------------------------------------+ | This source file is subject to version 3.01 of the PHP license, | | that is bundled with this package in the file LICENSE, and is | @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: php_zip.h,v 1.10 2006/07/24 16:58:58 pajoye Exp $ */ +/* $Id: php_zip.h,v 1.10.2.3 2007/03/14 11:08:57 pajoye Exp $ */ #ifndef PHP_ZIP_H #define PHP_ZIP_H @@ -24,23 +24,21 @@ extern zend_module_entry zip_module_entry; #define phpext_zip_ptr &zip_module_entry -#ifdef PHP_WIN32 -#define PHP_ZIP_API __declspec(dllexport) -#else -#define PHP_ZIP_API -#endif - #ifdef ZTS #include "TSRM.h" #endif #include "lib/zip.h" -#ifndef ZEND_ENGINE_2_1 -# if (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION > 0) -# define ZEND_ENGINE_2_1 -# endif +/* {{{ OPENBASEDIR_CHECKPATH(filename) */ +#if (PHP_MAJOR_VERSION < 6) +#define OPENBASEDIR_CHECKPATH(filename) \ + (PG(safe_mode) && (!php_checkuid(filename, NULL, CHECKUID_CHECK_FILE_AND_DIR))) || php_check_open_basedir(filename TSRMLS_CC) +#else +#define OPENBASEDIR_CHECKPATH(filename) \ + php_check_open_basedir(filename TSRMLS_CC) #endif +/* }}} */ typedef struct _ze_zip_rsrc { struct zip *za; @@ -55,7 +53,6 @@ typedef struct _ze_zip_read_rsrc { struct zip_stat sb; } zip_read_rsrc; -#ifdef ZEND_ENGINE_2_1 #define ZIPARCHIVE_ME(name, arg_info, flags) ZEND_FENTRY(name, c_ziparchive_ ##name, arg_info, flags) #define ZIPARCHIVE_METHOD(name) ZEND_NAMED_FUNCTION(c_ziparchive_##name) @@ -70,24 +67,10 @@ typedef struct _ze_zip_object { int filename_len; } ze_zip_object; -zend_class_entry *zip_class_entry_ce; - php_stream *php_stream_zip_opener(php_stream_wrapper *wrapper, char *path, char *mode, int options, char **opened_path, php_stream_context *context STREAMS_DC TSRMLS_DC); php_stream *php_stream_zip_open(char *filename, char *path, char *mode STREAMS_DC TSRMLS_DC); extern php_stream_wrapper php_stream_zip_wrapper; -#endif - -PHP_FUNCTION(zip_open); -PHP_FUNCTION(zip_read); -PHP_FUNCTION(zip_close); -PHP_FUNCTION(zip_entry_read); -PHP_FUNCTION(zip_entry_filesize); -PHP_FUNCTION(zip_entry_name); -PHP_FUNCTION(zip_entry_compressedsize); -PHP_FUNCTION(zip_entry_compressionmethod); -PHP_FUNCTION(zip_entry_open); -PHP_FUNCTION(zip_entry_close); #endif /* PHP_ZIP_H */ diff --git a/ext/zip/tests/bug40228.phpt b/ext/zip/tests/bug40228.phpt new file mode 100644 index 000000000..fec296363 --- /dev/null +++ b/ext/zip/tests/bug40228.phpt @@ -0,0 +1,23 @@ +--TEST-- +Bug #40228 (extractTo does not create recursive empty path) +--SKIPIF-- +<?php if (!extension_loaded("zip")) print "skip"; ?> +--FILE-- +<?php +$dest = dirname(__FILE__); +$arc_name = $dest . "/bug40228.zip"; +$zip = new ZipArchive; +$zip->open($arc_name, ZIPARCHIVE::CREATE);; +$zip->extractTo($dest); +if (is_dir($dest . '/test/empty')) { + echo "Ok\n"; + rmdir($dest . '/test/empty'); + rmdir($dest . '/test'); +} else { + echo "Failed.\n"; +} +echo "Done\n"; +?> +--EXPECT-- +Ok +Done diff --git a/ext/zip/tests/bug40228.zip b/ext/zip/tests/bug40228.zip Binary files differnew file mode 100644 index 000000000..bbcd9515f --- /dev/null +++ b/ext/zip/tests/bug40228.zip diff --git a/ext/zip/tests/oo_addemptydir.phpt b/ext/zip/tests/oo_addemptydir.phpt new file mode 100644 index 000000000..0252c6dc8 --- /dev/null +++ b/ext/zip/tests/oo_addemptydir.phpt @@ -0,0 +1,36 @@ +--TEST-- +ziparchive::addEmptyDir +--SKIPIF-- +<?php +/* $Id: oo_addemptydir.phpt,v 1.1.2.2 2006/11/03 16:46:19 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php + +$dirname = dirname(__FILE__) . '/'; +include $dirname . 'utils.inc'; +$file = $dirname . '__tmp_oo_addfile.zip'; + +copy($dirname . 'test.zip', $file); + +$zip = new ZipArchive; +if (!$zip->open($file)) { + exit('failed'); +} + +$zip->addEmptyDir('emptydir'); +if ($zip->status == ZIPARCHIVE::ER_OK) { + dump_entries_name($zip); + $zip->close(); +} else { + echo "failed\n"; +} +@unlink($file); +?> +--EXPECTF-- +0 bar +1 foobar/ +2 foobar/baz +3 entry1.txt +4 emptydir/ diff --git a/ext/zip/tests/oo_extract.phpt b/ext/zip/tests/oo_extract.phpt new file mode 100644 index 000000000..56f288248 --- /dev/null +++ b/ext/zip/tests/oo_extract.phpt @@ -0,0 +1,95 @@ +--TEST-- +extractTo +--SKIPIF-- +<?php +/* $Id: oo_extract.phpt,v 1.2.2.2 2006/11/03 16:46:19 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php +$dirname = dirname(__FILE__) . '/'; +$file = $dirname . 'test_with_comment.zip'; +include $dirname . 'utils.inc'; +$zip = new ZipArchive; +if ($zip->open($file) !== TRUE) { + echo "open failed.\n"; + exit('failed'); +} + +$zip->extractTo($dirname . '__oo_extract_tmp'); +if (!is_dir($dirname . '__oo_extract_tmp')) { + echo "failed. mkdir\n"; +} + +if (!is_dir($dirname .'__oo_extract_tmp/foobar')) { + echo "failed. mkdir foobar\n"; +} + +if (!file_exists($dirname . '__oo_extract_tmp/foobar/baz')) { + echo "failed. extract foobar/baz\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/foobar/baz') . "\n"; +} + +if (!file_exists($dirname . '__oo_extract_tmp/bar')) { + echo "failed. bar file\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/bar') . "\n"; +} + +if (!file_exists($dirname . '__oo_extract_tmp/foo')) { + echo "failed. foo file\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/foo') . "\n"; +} + + +/* extract one file */ +$zip->extractTo($dirname . '__oo_extract_tmp', 'bar'); +if (!file_exists($dirname . '__oo_extract_tmp/bar')) { + echo "failed. extract bar file\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/bar') . "\n"; +} + +/* extract two files */ +$zip->extractTo($dirname . '__oo_extract_tmp', array('bar','foo')); +if (!file_exists($dirname . '__oo_extract_tmp/bar')) { + echo "failed. extract bar file\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/bar') . "\n"; +} +if (!file_exists($dirname . '__oo_extract_tmp/foo')) { + echo "failed. extract foo file\n"; +} else { + echo file_get_contents($dirname . '__oo_extract_tmp/foo') . "\n"; +} + +rmdir_rf($dirname . '__oo_extract_tmp'); +?> +--EXPECTF-- +blabla laber rababer sülz + +bar + +foo + + +bar + +bar + +foo +--UEXPECTF-- +blabla laber rababer sülz + +bar + +foo + + +bar + +bar + +foo diff --git a/ext/zip/tests/oo_getcomment.phpt b/ext/zip/tests/oo_getcomment.phpt new file mode 100644 index 000000000..b9bc28933 --- /dev/null +++ b/ext/zip/tests/oo_getcomment.phpt @@ -0,0 +1,36 @@ +--TEST-- +getComment +--SKIPIF-- +<?php +/* $Id: oo_getcomment.phpt,v 1.1.2.3 2007/03/14 11:02:29 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php +$dirname = dirname(__FILE__) . '/'; +$file = $dirname . 'test_with_comment.zip'; +include $dirname . 'utils.inc'; +$zip = new ZipArchive; +if (!$zip->open($file)) { + exit('failed'); +} +echo $zip->getArchiveComment() . "\n"; + +$idx = $zip->locateName('foo'); +echo $zip->getCommentName('foo') . "\n"; +echo $zip->getCommentIndex($idx); + +echo $zip->getCommentName('') . "\n"; +echo $zip->getCommentName() . "\n"; + +$zip->close(); + +?> +--EXPECTF-- +Zip archive comment +foo comment +foo comment +Notice: ZipArchive::getCommentName(): Empty string as entry name in %s on line %d + + +Warning: ZipArchive::getCommentName() expects at least 1 parameter, 0 given in %s on line %d diff --git a/ext/zip/tests/oo_getnameindex.phpt b/ext/zip/tests/oo_getnameindex.phpt new file mode 100644 index 000000000..bf2d4c67a --- /dev/null +++ b/ext/zip/tests/oo_getnameindex.phpt @@ -0,0 +1,47 @@ +--TEST-- +getNameIndex +--SKIPIF-- +<?php +/* $Id: oo_getnameindex.phpt,v 1.1.2.2 2006/11/03 16:46:19 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php +$dirname = dirname(__FILE__) . '/'; +include $dirname . 'utils.inc'; +$file = $dirname . '__tmp_oo_rename.zip'; + +@unlink($file); + +$zip = new ZipArchive; +if (!$zip->open($file, ZIPARCHIVE::CREATE)) { + exit('failed'); +} + +$zip->addFromString('entry1.txt', 'entry #1'); +$zip->addFromString('entry2.txt', 'entry #2'); +$zip->addFromString('dir/entry2d.txt', 'entry #2'); + +if (!$zip->status == ZIPARCHIVE::ER_OK) { + echo "failed to write zip\n"; +} +$zip->close(); + +if (!$zip->open($file)) { + exit('failed'); +} + + +var_dump($zip->getNameIndex(0)); +var_dump($zip->getNameIndex(1)); +var_dump($zip->getNameIndex(2)); +var_dump($zip->getNameIndex(3)); + +$zip->close(); + +?> +--EXPECTF-- +string(10) "entry1.txt" +string(10) "entry2.txt" +string(15) "dir/entry2d.txt" +bool(false) diff --git a/ext/zip/tests/oo_setcomment.phpt b/ext/zip/tests/oo_setcomment.phpt new file mode 100644 index 000000000..f0dcf35c3 --- /dev/null +++ b/ext/zip/tests/oo_setcomment.phpt @@ -0,0 +1,71 @@ +--TEST-- +setComment +--SKIPIF-- +<?php +/* $Id: oo_setcomment.phpt,v 1.1.2.2 2006/11/03 16:46:19 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php +$dirname = dirname(__FILE__) . '/'; +include $dirname . 'utils.inc'; +$file = $dirname . '__tmp_oo_set_comment.zip'; + +@unlink($file); + +$zip = new ZipArchive; +if (!$zip->open($file, ZIPARCHIVE::CREATE)) { + exit('failed'); +} + +$zip->addFromString('entry1.txt', 'entry #1'); +$zip->addFromString('entry2.txt', 'entry #2'); +$zip->addFromString('dir/entry2d.txt', 'entry #2'); +$zip->addFromString('entry4.txt', 'entry #1'); +$zip->addFromString('entry5.txt', 'entry #2'); + + +var_dump($zip->setCommentName('entry1.txt', 'entry1.txt')); +var_dump($zip->setCommentName('entry2.txt', 'entry2.txt')); +var_dump($zip->setCommentName('dir/entry2d.txt', 'dir/entry2d.txt')); +var_dump($zip->setArchiveComment('archive')); + +var_dump($zip->setCommentIndex(3, 'entry4.txt')); +var_dump($zip->setCommentIndex(4, 'entry5.txt')); +var_dump($zip->setArchiveComment('archive')); + +if (!$zip->status == ZIPARCHIVE::ER_OK) { + echo "failed to write zip\n"; +} +$zip->close(); + +if (!$zip->open($file)) { + @unlink($file); + exit('failed'); +} + +var_dump($zip->getCommentIndex(0)); +var_dump($zip->getCommentIndex(1)); +var_dump($zip->getCommentIndex(2)); +var_dump($zip->getCommentIndex(3)); +var_dump($zip->getCommentIndex(4)); +var_dump($zip->getArchiveComment()); + +$zip->close(); +@unlink($file); + +?> +--EXPECTF-- +bool(true) +bool(true) +bool(true) +bool(true) +bool(true) +bool(true) +bool(true) +string(10) "entry1.txt" +string(10) "entry2.txt" +string(15) "dir/entry2d.txt" +string(10) "entry4.txt" +string(10) "entry5.txt" +string(7) "archive" diff --git a/ext/zip/tests/oo_stream.phpt b/ext/zip/tests/oo_stream.phpt new file mode 100644 index 000000000..c7f5b0d82 --- /dev/null +++ b/ext/zip/tests/oo_stream.phpt @@ -0,0 +1,50 @@ +--TEST-- +getStream +--SKIPIF-- +<?php +/* $Id: oo_stream.phpt,v 1.2.2.2 2006/11/03 16:46:19 pajoye Exp $ */ +if(!extension_loaded('zip')) die('skip'); +?> +--FILE-- +<?php +$dirname = dirname(__FILE__) . '/'; +$file = $dirname . 'test_with_comment.zip'; +include $dirname . 'utils.inc'; +$zip = new ZipArchive; +if (!$zip->open($file)) { + exit('failed'); +} +$fp = $zip->getStream('foo'); + +var_dump($fp); +if(!$fp) exit("\n"); +$contents = ''; +while (!feof($fp)) { + $contents .= fread($fp, 255); +} + +fclose($fp); +$zip->close(); +var_dump($contents); + + +$fp = fopen('zip://' . dirname(__FILE__) . '/test_with_comment.zip#foo', 'rb'); +if (!$fp) { + exit("cannot open\n"); +} +$contents = ''; +while (!feof($fp)) { + $contents .= fread($fp, 2); +} +var_dump($contents); +fclose($fp); + +?> +--EXPECTF-- +resource(%d) of type (stream) +string(5) "foo + +" +string(5) "foo + +" diff --git a/ext/zip/tests/test_with_comment.zip b/ext/zip/tests/test_with_comment.zip Binary files differnew file mode 100644 index 000000000..d68f76157 --- /dev/null +++ b/ext/zip/tests/test_with_comment.zip diff --git a/ext/zip/tests/utils.inc b/ext/zip/tests/utils.inc index 7a8b5a122..a03db17ae 100644 --- a/ext/zip/tests/utils.inc +++ b/ext/zip/tests/utils.inc @@ -1,8 +1,24 @@ <?php -/* $Id: utils.inc,v 1.1.2.2 2006/10/02 14:17:47 bjori Exp $ */ +/* $Id: utils.inc,v 1.1.2.3 2006/11/03 16:46:19 pajoye Exp $ */ function dump_entries_name($z) { for($i=0; $i<$z->numFiles; $i++) { $sb = $z->statIndex($i); echo $i . ' ' . $sb['name'] . "\n"; } } +/* recursively remove a directoryy */ +function rmdir_rf($dir) { + if ($handle = opendir($dir)) { + while (false !== ($item = readdir($handle))) { + if ($item != "." && $item != "..") { + if (is_dir($dir . '/' . $item)) { + rmdir_rf($dir . '/' . $item); + } else { + unlink($dir . '/' . $item); + } + } + } + closedir($handle); + rmdir($dir); + } +} diff --git a/ext/zip/tests/zip_entry_open.phpt b/ext/zip/tests/zip_entry_open.phpt index 4e0100357..280cb1557 100644 --- a/ext/zip/tests/zip_entry_open.phpt +++ b/ext/zip/tests/zip_entry_open.phpt @@ -2,7 +2,7 @@ zip_entry_open() function --SKIPIF-- <?php -/* $Id: zip_entry_open.phpt,v 1.1 2006/07/24 16:58:58 pajoye Exp $ */ +/* $Id: zip_entry_open.phpt,v 1.1.2.1 2006/11/03 16:46:19 pajoye Exp $ */ if(!extension_loaded('zip')) die('skip'); ?> --FILE-- @@ -10,6 +10,7 @@ if(!extension_loaded('zip')) die('skip'); $zip = zip_open(dirname(__FILE__)."/test_procedural.zip"); $entry = zip_read($zip); echo zip_entry_open($zip, $entry, "r") ? "OK" : "Failure"; +zip_entry_close($entry); zip_close($zip); ?> diff --git a/ext/zip/tests/zip_entry_read.phpt b/ext/zip/tests/zip_entry_read.phpt index f72b5e2cb..1dc1eeb45 100644 --- a/ext/zip/tests/zip_entry_read.phpt +++ b/ext/zip/tests/zip_entry_read.phpt @@ -2,7 +2,7 @@ zip_entry_read() function --SKIPIF-- <?php -/* $Id: zip_entry_read.phpt,v 1.1 2006/07/24 16:58:58 pajoye Exp $ */ +/* $Id: zip_entry_read.phpt,v 1.1.2.1 2006/11/03 16:46:19 pajoye Exp $ */ if(!extension_loaded('zip')) die('skip'); ?> --FILE-- @@ -11,6 +11,7 @@ $zip = zip_open(dirname(__FILE__)."/test_procedural.zip"); $entry = zip_read($zip); if (!zip_entry_open($zip, $entry, "r")) die("Failure"); echo zip_entry_read($entry); +zip_entry_close($entry); zip_close($zip); ?> diff --git a/ext/zip/zip_stream.c b/ext/zip/zip_stream.c index 60f43595e..747097537 100644 --- a/ext/zip/zip_stream.c +++ b/ext/zip/zip_stream.c @@ -1,4 +1,4 @@ -/* $Id: zip_stream.c,v 1.1.2.1 2006/07/27 00:36:55 iliaa Exp $ */ +/* $Id: zip_stream.c,v 1.1.2.5 2007/03/14 11:08:57 pajoye Exp $ */ #ifdef HAVE_CONFIG_H # include "config.h" #endif @@ -12,6 +12,7 @@ #include "ext/standard/file.h" #include "ext/standard/php_string.h" #include "fopen_wrappers.h" +#include "php_zip.h" #include "ext/standard/url.h" @@ -60,9 +61,15 @@ static size_t php_zip_ops_write(php_stream *stream, const char *buf, size_t coun static int php_zip_ops_close(php_stream *stream, int close_handle TSRMLS_DC) { STREAM_DATA_FROM_STREAM(); - if (close_handle && self->za) { - zip_close(self->za); - self->za = NULL; + if (close_handle) { + if (self->za) { + zip_close(self->za); + self->za = NULL; + } + if (self->zf) { + zip_fclose(self->zf); + self->zf = NULL; + } } efree(self); stream->abstract = NULL; @@ -106,6 +113,10 @@ php_stream *php_stream_zip_open(char *filename, char *path, char *mode STREAMS_D } if (filename) { + if (OPENBASEDIR_CHECKPATH(filename)) { + return NULL; + } + /* duplicate to make the stream za independent (esp. for MSHUTDOWN) */ stream_za = zip_open(filename, ZIP_CREATE, &err); if (!stream_za) { @@ -147,7 +158,7 @@ php_stream *php_stream_zip_opener(php_stream_wrapper *wrapper, char *file_basename; size_t file_basename_len; - char file_dirname[MAXPATHLEN+1]; + char file_dirname[MAXPATHLEN]; struct zip *za; struct zip_file *zf = NULL; @@ -173,13 +184,18 @@ php_stream *php_stream_zip_opener(php_stream_wrapper *wrapper, return NULL; } path_len = strlen(path); + if (path_len >= MAXPATHLEN || mode[0] != 'r') { + return NULL; + } memcpy(file_dirname, path, path_len - fragment_len); file_dirname[path_len - fragment_len] = '\0'; php_basename(path, path_len - fragment_len, NULL, 0, &file_basename, &file_basename_len TSRMLS_CC); fragment++; - if (mode[0] != 'r') { + + if (OPENBASEDIR_CHECKPATH(file_dirname)) { + efree(file_basename); return NULL; } |