diff options
author | Remi Collet <remi@php.net> | 2013-12-30 07:35:30 +0100 |
---|---|---|
committer | Remi Collet <remi@php.net> | 2013-12-30 07:35:30 +0100 |
commit | 0a950a05005f94e56bd2a42b99a0961db86952db (patch) | |
tree | 3949553a3f889947795b007df4776643b153da55 | |
parent | 5a756afcf14fada75f6ed8052cd97924dd229ed8 (diff) | |
download | php-git-0a950a05005f94e56bd2a42b99a0961db86952db.tar.gz |
Sync with pecl/zip 1.12.4dev
- update bunled libzip to 0.11.2
- expose zip_file_set_external_attributes + zip_file_get_external_attributes
with new methods:
ZipArchive::setExternalAttributesName
ZipArchive::setExternalAttributesIndex
ZipArchive::getExternalAttributesName
ZipArchive::getExternalAttributesIndex
31 files changed, 400 insertions, 111 deletions
diff --git a/ext/zip/config.m4 b/ext/zip/config.m4 index 56ae6a5b29..a21ad2d3e1 100644 --- a/ext/zip/config.m4 +++ b/ext/zip/config.m4 @@ -63,9 +63,14 @@ if test "$PHP_ZIP" != "no"; then AC_MSG_RESULT(from option: found in $PHP_LIBZIP) elif test -x "$PKG_CONFIG" && $PKG_CONFIG --exists libzip; then - LIBZIP_CFLAGS=`$PKG_CONFIG libzip --cflags` - LIBZIP_LIBDIR=`$PKG_CONFIG libzip --variable=libdir` - AC_MSG_RESULT(from pkgconfig: found in $LIBZIP_LIBDIR) + if $PKG_CONFIG libzip --atleast-version 0.11; then + LIBZIP_CFLAGS=`$PKG_CONFIG libzip --cflags` + LIBZIP_LIBDIR=`$PKG_CONFIG libzip --variable=libdir` + LIBZIP_VERSON=`$PKG_CONFIG libzip --modversion` + AC_MSG_RESULT(from pkgconfig: version $LIBZIP_VERSON found in $LIBZIP_LIBDIR) + else + AC_MSG_ERROR(system libzip must be upgraded to version >= 0.11) + fi else for i in /usr/local /usr; do @@ -107,6 +112,7 @@ if test "$PHP_ZIP" != "no"; then lib/zip_fclose.c lib/zip_fdopen.c lib/zip_file_add.c lib/zip_file_error_clear.c lib/zip_file_error_get.c\ lib/zip_file_get_comment.c lib/zip_file_get_offset.c lib/zip_file_rename.c lib/zip_file_replace.c\ lib/zip_file_set_comment.c lib/zip_file_strerror.c lib/zip_filerange_crc.c lib/zip_fopen.c\ + lib/zip_file_get_external_attributes.c lib/zip_file_set_external_attributes.c \ lib/zip_fopen_encrypted.c lib/zip_fopen_index.c lib/zip_fopen_index_encrypted.c lib/zip_fread.c\ lib/zip_get_archive_comment.c lib/zip_get_archive_flag.c lib/zip_get_compression_implementation.c\ lib/zip_get_encryption_implementation.c lib/zip_get_file_comment.c lib/zip_get_name.c lib/zip_get_num_entries.c \ @@ -122,6 +128,7 @@ if test "$PHP_ZIP" != "no"; then AC_DEFINE(HAVE_ZIP,1,[ ]) PHP_NEW_EXTENSION(zip, php_zip.c zip_stream.c $PHP_ZIP_SOURCES, $ext_shared) PHP_ADD_BUILD_DIR($ext_builddir/lib, 1) + PHP_ADD_INCLUDE([$ext_srcdir/lib]) PHP_SUBST(ZIP_SHARED_LIBADD) fi diff --git a/ext/zip/config.w32 b/ext/zip/config.w32 index 5b9f09575a..28de344785 100644 --- a/ext/zip/config.w32 +++ b/ext/zip/config.w32 @@ -5,6 +5,7 @@ ARG_ENABLE("zip", "ZIP support", "yes"); if (PHP_ZIP != "no") { if (CHECK_HEADER_ADD_INCLUDE("zlib.h", "CFLAGS_ZIP", "..\\zlib;" + PHP_ZIP) && + CHECK_HEADER_ADD_INCLUDE("zipconf.h", "CFLAGS_ZIP", configure_module_dirname + "\\lib;" + PHP_ZIP) && (((PHP_ZLIB=="no") && (CHECK_LIB("zlib_a.lib", "zip", PHP_ZIP) || CHECK_LIB("zlib.lib", "zip", PHP_ZIP))) || (PHP_ZLIB_SHARED && CHECK_LIB("zlib.lib", "zip", PHP_ZIP)) || (PHP_ZLIB == "yes" && (!PHP_ZLIB_SHARED))) ) { @@ -26,7 +27,8 @@ if (PHP_ZIP != "no") { zip_source_function.c zip_source_layered.c zip_source_open.c zip_source_pkware.c zip_source_pop.c\ zip_source_read.c zip_source_stat.c zip_source_window.c zip_source_zip.c zip_source_zip_new.c\ zip_stat.c zip_stat_index.c zip_stat_init.c zip_strerror.c zip_string.c zip_unchange.c zip_unchange_all.c\ - zip_unchange_archive.c zip_unchange_data.c zip_utf-8.c mkstemp.c", "zip"); + zip_unchange_archive.c zip_unchange_data.c zip_utf-8.c mkstemp.c \ + zip_file_set_external_attributes.c zip_file_get_external_attributes.c", "zip"); AC_DEFINE('HAVE_ZIP', 1); ADD_FLAG("CFLAGS_ZIP", "/D _WIN32"); diff --git a/ext/zip/lib/config.h b/ext/zip/lib/config.h index f9132ba439..ee77c66d43 100644 --- a/ext/zip/lib/config.h +++ b/ext/zip/lib/config.h @@ -21,5 +21,9 @@ #else /* Building in PHP tree */ -#include "php_config.h" +# ifdef _WIN32 +# include "config.w32.h" +# else +# include "php_config.h" +# endif #endif diff --git a/ext/zip/lib/php_zip_config.w32.h b/ext/zip/lib/php_zip_config.w32.h index 8956839c62..1fec26317b 100644 --- a/ext/zip/lib/php_zip_config.w32.h +++ b/ext/zip/lib/php_zip_config.w32.h @@ -54,4 +54,7 @@ typedef long long ssize_t; # endif
#endif
+# undef strcasecmp
+# define strcasecmp _strcmpi
+
#endif /* HAD_CONFIG_H */
diff --git a/ext/zip/lib/zip.h b/ext/zip/lib/zip.h index 1fb1dbf5e0..2665291abc 100644 --- a/ext/zip/lib/zip.h +++ b/ext/zip/lib/zip.h @@ -20,7 +20,7 @@ 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 @@ -35,8 +35,9 @@ */ -#include "main/php.h" +#include "main/php.h" + #ifdef PHP_WIN32 #ifdef PHP_ZIP_EXPORTS # define ZIP_EXTERN __declspec(dllexport) _stdcall @@ -48,23 +49,14 @@ #else # define ZIP_EXTERN #endif + -#ifndef ZIP_EXTERN -#ifdef _WIN32 -#define ZIP_EXTERN __declspec(dllimport) -#elif defined(__GNUC__) && __GNUC__ >= 4 -#define ZIP_EXTERN __attribute__ ((visibility ("default"))) -#else -#define ZIP_EXTERN +#ifdef __cplusplus +extern "C" { #endif -#endif - - -BEGIN_EXTERN_C() - -#include "zipconf.h" +#include <zipconf.h> #include <sys/types.h> #include <stdio.h> @@ -77,6 +69,7 @@ BEGIN_EXTERN_C() #define ZIP_CHECKCONS 4 #define ZIP_TRUNCATE 8 + /* flags for zip_name_locate, zip_fopen, zip_stat, ... */ #define ZIP_FL_NOCASE 1u /* ignore case on name lookup */ @@ -190,6 +183,29 @@ BEGIN_EXTERN_C() #endif #define ZIP_EM_UNKNOWN 0xffff /* unknown algorithm */ +#define ZIP_OPSYS_DOS 0x00u +#define ZIP_OPSYS_AMIGA 0x01u +#define ZIP_OPSYS_OPENVMS 0x02u +#define ZIP_OPSYS_UNIX 0x03u +#define ZIP_OPSYS_VM_CMS 0x04u +#define ZIP_OPSYS_ATARI_ST 0x05u +#define ZIP_OPSYS_OS_2 0x06u +#define ZIP_OPSYS_MACINTOSH 0x07u +#define ZIP_OPSYS_Z_SYSTEM 0x08u +#define ZIP_OPSYS_CPM 0x09u +#define ZIP_OPSYS_WINDOWS_NTFS 0x0au +#define ZIP_OPSYS_MVS 0x0bu +#define ZIP_OPSYS_VSE 0x0cu +#define ZIP_OPSYS_ACORN_RISC 0x0du +#define ZIP_OPSYS_VFAT 0x0eu +#define ZIP_OPSYS_ALTERNATE_MVS 0x0fu +#define ZIP_OPSYS_BEOS 0x10u +#define ZIP_OPSYS_TANDEM 0x11u +#define ZIP_OPSYS_OS_400 0x12u +#define ZIP_OPSYS_OS_X 0x13u + +#define ZIP_OPSYS_DEFAULT ZIP_OPSYS_UNIX + enum zip_source_cmd { @@ -248,21 +264,32 @@ ZIP_EXTERN int zip_set_file_comment(struct zip *, zip_uint64_t, const char *, in #endif ZIP_EXTERN int zip_archive_set_tempdir(struct zip *, const char *); -ZIP_EXTERN zip_int64_t zip_file_add(struct zip *, const char *, struct zip_source *, zip_flags_t); -ZIP_EXTERN zip_int64_t zip_dir_add(struct zip *, const char *, zip_flags_t); ZIP_EXTERN int zip_close(struct zip *); -ZIP_EXTERN void zip_discard(struct zip *); ZIP_EXTERN int zip_delete(struct zip *, zip_uint64_t); -ZIP_EXTERN int zip_file_extra_field_delete(struct zip *, zip_uint64_t, zip_uint16_t, zip_flags_t); -ZIP_EXTERN int zip_file_extra_field_delete_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, zip_flags_t); +ZIP_EXTERN zip_int64_t zip_dir_add(struct zip *, const char *, zip_flags_t); +ZIP_EXTERN void zip_discard(struct zip *); ZIP_EXTERN void zip_error_clear(struct zip *); ZIP_EXTERN void zip_error_get(struct zip *, int *, int *); ZIP_EXTERN int zip_error_get_sys_type(int); ZIP_EXTERN int zip_error_to_str(char *, zip_uint64_t, int, int); ZIP_EXTERN int zip_fclose(struct zip_file *); ZIP_EXTERN struct zip *zip_fdopen(int, int, int *); +ZIP_EXTERN zip_int64_t zip_file_add(struct zip *, const char *, struct zip_source *, zip_flags_t); ZIP_EXTERN void zip_file_error_clear(struct zip_file *); ZIP_EXTERN void zip_file_error_get(struct zip_file *, int *, int *); +ZIP_EXTERN int zip_file_extra_field_delete(struct zip *, zip_uint64_t, zip_uint16_t, zip_flags_t); +ZIP_EXTERN int zip_file_extra_field_delete_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, zip_flags_t); +ZIP_EXTERN int zip_file_extra_field_set(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, const zip_uint8_t *, zip_uint16_t, zip_flags_t); +ZIP_EXTERN zip_int16_t zip_file_extra_fields_count(struct zip *, zip_uint64_t, zip_flags_t); +ZIP_EXTERN zip_int16_t zip_file_extra_fields_count_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_flags_t); +ZIP_EXTERN const zip_uint8_t *zip_file_extra_field_get(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t *, zip_uint16_t *, zip_flags_t); +ZIP_EXTERN const zip_uint8_t *zip_file_extra_field_get_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, zip_uint16_t *, zip_flags_t); +ZIP_EXTERN const char *zip_file_get_comment(struct zip *, zip_uint64_t, zip_uint32_t *, zip_flags_t); +ZIP_EXTERN int zip_file_get_external_attributes(struct zip *, zip_uint64_t, zip_flags_t, zip_uint8_t *, zip_uint32_t *); +ZIP_EXTERN int zip_file_rename(struct zip *, zip_uint64_t, const char *, zip_flags_t); +ZIP_EXTERN int zip_file_replace(struct zip *, zip_uint64_t, struct zip_source *, zip_flags_t); +ZIP_EXTERN int zip_file_set_comment(struct zip *, zip_uint64_t, const char *, zip_uint16_t, zip_flags_t); +ZIP_EXTERN int zip_file_set_external_attributes(struct zip *, zip_uint64_t, zip_flags_t, zip_uint8_t, zip_uint32_t); ZIP_EXTERN const char *zip_file_strerror(struct zip_file *); ZIP_EXTERN struct zip_file *zip_fopen(struct zip *, const char *, zip_flags_t); ZIP_EXTERN struct zip_file *zip_fopen_encrypted(struct zip *, const char *, zip_flags_t, const char *); @@ -271,23 +298,14 @@ ZIP_EXTERN struct zip_file *zip_fopen_index_encrypted(struct zip *, zip_uint64_t ZIP_EXTERN zip_int64_t zip_fread(struct zip_file *, void *, zip_uint64_t); ZIP_EXTERN const char *zip_get_archive_comment(struct zip *, int *, zip_flags_t); ZIP_EXTERN int zip_get_archive_flag(struct zip *, zip_flags_t, zip_flags_t); -ZIP_EXTERN const char *zip_file_get_comment(struct zip *, zip_uint64_t, zip_uint32_t *, zip_flags_t); -ZIP_EXTERN const zip_uint8_t *zip_file_extra_field_get(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t *, zip_uint16_t *, zip_flags_t); -ZIP_EXTERN const zip_uint8_t *zip_file_extra_field_get_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, zip_uint16_t *, zip_flags_t); -ZIP_EXTERN zip_int16_t zip_file_extra_fields_count(struct zip *, zip_uint64_t, zip_flags_t); -ZIP_EXTERN zip_int16_t zip_file_extra_fields_count_by_id(struct zip *, zip_uint64_t, zip_uint16_t, zip_flags_t); ZIP_EXTERN const char *zip_get_name(struct zip *, zip_uint64_t, zip_flags_t); ZIP_EXTERN zip_int64_t zip_get_num_entries(struct zip *, zip_flags_t); ZIP_EXTERN zip_int64_t zip_name_locate(struct zip *, const char *, zip_flags_t); ZIP_EXTERN struct zip *zip_open(const char *, int, int *); -ZIP_EXTERN int zip_file_rename(struct zip *, zip_uint64_t, const char *, zip_flags_t); -ZIP_EXTERN int zip_file_replace(struct zip *, zip_uint64_t, struct zip_source *, zip_flags_t); ZIP_EXTERN int zip_set_archive_comment(struct zip *, const char *, zip_uint16_t); ZIP_EXTERN int zip_set_archive_flag(struct zip *, zip_flags_t, int); ZIP_EXTERN int zip_set_default_password(struct zip *, const char *); -ZIP_EXTERN int zip_file_set_comment(struct zip *, zip_uint64_t, const char *, zip_uint16_t, zip_flags_t); ZIP_EXTERN int zip_set_file_compression(struct zip *, zip_uint64_t, zip_int32_t, zip_uint32_t); -ZIP_EXTERN int zip_file_extra_field_set(struct zip *, zip_uint64_t, zip_uint16_t, zip_uint16_t, const zip_uint8_t *, zip_uint16_t, zip_flags_t); ZIP_EXTERN struct zip_source *zip_source_buffer(struct zip *, const void *, zip_uint64_t, int); ZIP_EXTERN struct zip_source *zip_source_file(struct zip *, const char *, zip_uint64_t, zip_int64_t); ZIP_EXTERN struct zip_source *zip_source_filep(struct zip *, FILE *, zip_uint64_t, zip_int64_t); @@ -302,6 +320,8 @@ ZIP_EXTERN int zip_unchange(struct zip *, zip_uint64_t); ZIP_EXTERN int zip_unchange_all(struct zip *); ZIP_EXTERN int zip_unchange_archive(struct zip *); +#ifdef __cplusplus +} +#endif -END_EXTERN_C(); #endif /* _HAD_ZIP_H */ diff --git a/ext/zip/lib/zip_add.c b/ext/zip/lib/zip_add.c index 4bce3fd4af..5b907824b3 100644 --- a/ext/zip/lib/zip_add.c +++ b/ext/zip/lib/zip_add.c @@ -17,7 +17,7 @@ 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 diff --git a/ext/zip/lib/zip_add_entry.c b/ext/zip/lib/zip_add_entry.c index 3a7e2ccbe9..5cbc9574ad 100644 --- a/ext/zip/lib/zip_add_entry.c +++ b/ext/zip/lib/zip_add_entry.c @@ -49,7 +49,8 @@ _zip_add_entry(struct zip *za) if (za->nentry+1 >= za->nentry_alloc) { struct zip_entry *rentries; zip_uint64_t nalloc = za->nentry_alloc + 16; - rentries = (struct zip_entry *)realloc(za->entry, sizeof(struct zip_entry) * nalloc); + /* TODO check for overflow */ + rentries = (struct zip_entry *)realloc(za->entry, sizeof(struct zip_entry) * (size_t)nalloc); if (!rentries) { _zip_error_set(&za->error, ZIP_ER_MEMORY, 0); return -1; diff --git a/ext/zip/lib/zip_close.c b/ext/zip/lib/zip_close.c index c9c7e58088..e8dd9d600d 100644 --- a/ext/zip/lib/zip_close.c +++ b/ext/zip/lib/zip_close.c @@ -1,6 +1,6 @@ /* zip_close.c -- close zip archive and update changes - Copyright (C) 1999-2011 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2013 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <libzip@nih.at> @@ -17,7 +17,7 @@ 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 @@ -47,7 +47,7 @@ #endif #include <sys/types.h> #include <sys/stat.h> -#ifdef PHP_WIN32 +#ifdef _WIN32 #include <io.h> #include <fcntl.h> #endif @@ -73,7 +73,7 @@ zip_close(struct zip *za) int error; char *temp; FILE *out; -#ifndef PHP_WIN32 +#ifndef _WIN32 mode_t mask; #endif struct zip_filelist *filelist; @@ -110,18 +110,18 @@ zip_close(struct zip *za) return -1; } - if ((filelist=(struct zip_filelist *)malloc(sizeof(filelist[0])*survivors)) == NULL) + if ((filelist=(struct zip_filelist *)malloc(sizeof(filelist[0])*(size_t)survivors)) == NULL) return -1; /* archive comment is special for torrentzip */ if (zip_get_archive_flag(za, ZIP_AFL_TORRENT, 0)) { - /* XXX: use internal function when zip_set_archive_comment clears TORRENT flag */ + /* TODO: use internal function when zip_set_archive_comment clears TORRENT flag */ if (zip_set_archive_comment(za, TORRENT_SIG "XXXXXXXX", TORRENT_SIG_LEN + TORRENT_CRC_LEN) < 0) { free(filelist); return -1; } } - /* XXX: if no longer torrentzip and archive comment not changed by user, delete it */ + /* TODO: if no longer torrentzip and archive comment not changed by user, delete it */ /* create list of files with index into original archive */ @@ -153,7 +153,7 @@ zip_close(struct zip *za) if (zip_get_archive_flag(za, ZIP_AFL_TORRENT, 0)) - qsort(filelist, survivors, sizeof(filelist[0]), + qsort(filelist, (size_t)survivors, sizeof(filelist[0]), _zip_torrentzip_cmp); new_torrentzip = (zip_get_archive_flag(za, ZIP_AFL_TORRENT, 0) == 1 @@ -189,7 +189,7 @@ zip_close(struct zip *za) _zip_dirent_torrent_normalize(entry->changes); - de->offset = (zip_uint64_t)ftello(out); /* XXX: check for errors */ + de->offset = (zip_uint64_t)ftello(out); /* TODO: check for errors */ if (new_data) { struct zip_source *zs; @@ -225,7 +225,7 @@ zip_close(struct zip *za) error = 1; break; } - if ((fseek(za->zp, (off_t)offset, SEEK_SET) < 0)) { + if ((fseeko(za->zp, (off_t)offset, SEEK_SET) < 0)) { _zip_error_set(&za->error, ZIP_ER_SEEK, errno); error = 1; break; @@ -273,7 +273,7 @@ zip_close(struct zip *za) } return -1; } -#ifndef PHP_WIN32 +#ifndef _WIN32 mask = umask(0); umask(mask); chmod(za->zn, 0666&~mask); @@ -367,7 +367,7 @@ add_data(struct zip *za, struct zip_source *src, struct zip_dirent *de, FILE *ft return -1; } - /* XXX: deflate 0-byte files for torrentzip? */ + /* TODO: deflate 0-byte files for torrentzip? */ if (de->comp_method != ZIP_CM_STORE && ((st.valid & ZIP_STAT_SIZE) == 0 || st.size != 0)) { if ((comp_impl=_zip_get_compression_implementation(de->comp_method)) == NULL) { _zip_error_set(&za->error, ZIP_ER_COMPNOTSUPP, 0); @@ -398,7 +398,7 @@ add_data(struct zip *za, struct zip_source *src, struct zip_dirent *de, FILE *ft while (s2 != src) { if ((s2=zip_source_pop(s2)) == NULL) { - /* XXX: set erorr */ + /* TODO: set erorr */ ret = -1; break; } @@ -461,7 +461,7 @@ copy_data(FILE *fs, zip_uint64_t len, FILE *ft, struct zip_error *error) return 0; while (len > 0) { - nn = len > sizeof(buf) ? sizeof(buf) : len; + nn = len > sizeof(buf) ? sizeof(buf) : len > SIZE_MAX ? SIZE_MAX : (size_t)len; if ((n=fread(buf, 1, nn, fs)) == 0) { if (ferror(fs)) { _zip_error_set(error, ZIP_ER_READ, errno); @@ -477,7 +477,7 @@ copy_data(FILE *fs, zip_uint64_t len, FILE *ft, struct zip_error *error) _zip_error_set(error, ZIP_ER_WRITE, errno); return -1; } - + len -= n; } @@ -615,7 +615,7 @@ _zip_create_temp_output(struct zip *za, FILE **outp) free(temp); return NULL; } - + if ((tfp=fdopen(tfd, "r+b")) == NULL) { _zip_error_set(&za->error, ZIP_ER_TMPOPEN, errno); close(tfd); @@ -623,7 +623,8 @@ _zip_create_temp_output(struct zip *za, FILE **outp) free(temp); return NULL; } -#ifdef PHP_WIN32 + +#ifdef _WIN32 /* According to Pierre Joye, Windows in some environments per default creates text files, so force binary mode. diff --git a/ext/zip/lib/zip_dir_add.c b/ext/zip/lib/zip_dir_add.c index 0a74bd6087..1a662f4aaf 100644 --- a/ext/zip/lib/zip_dir_add.c +++ b/ext/zip/lib/zip_dir_add.c @@ -1,6 +1,6 @@ /* zip_dir_add.c -- add directory - Copyright (C) 1999-2012 Dieter Baron and Thomas Klausner + Copyright (C) 1999-2013 Dieter Baron and Thomas Klausner This file is part of libzip, a library to manipulate ZIP archives. The authors can be contacted at <libzip@nih.at> @@ -46,7 +46,7 @@ ZIP_EXTERN zip_int64_t zip_dir_add(struct zip *za, const char *name, zip_flags_t flags) { size_t len; - zip_int64_t ret; + zip_int64_t idx; char *s; struct zip_source *source; @@ -78,11 +78,18 @@ zip_dir_add(struct zip *za, const char *name, zip_flags_t flags) return -1; } - ret = _zip_file_replace(za, ZIP_UINT64_MAX, s ? s : name, source, flags); + idx = _zip_file_replace(za, ZIP_UINT64_MAX, s ? s : name, source, flags); free(s); - if (ret < 0) + + if (idx < 0) zip_source_free(source); + else { + if (zip_file_set_external_attributes(za, (zip_uint64_t)idx, 0, ZIP_OPSYS_DEFAULT, ZIP_EXT_ATTRIB_DEFAULT_DIR) < 0) { + zip_delete(za, (zip_uint64_t)idx); + return -1; + } + } - return ret; + return idx; } diff --git a/ext/zip/lib/zip_dirent.c b/ext/zip/lib/zip_dirent.c index f4f2deb6fc..5c5792c3e9 100644 --- a/ext/zip/lib/zip_dirent.c +++ b/ext/zip/lib/zip_dirent.c @@ -81,7 +81,7 @@ _zip_cdir_grow(struct zip_cdir *cd, zip_uint64_t nentry, struct zip_error *error return 0; if ((entry=((struct zip_entry *) - realloc(cd->entry, sizeof(*(cd->entry))*nentry))) == NULL) { + realloc(cd->entry, sizeof(*(cd->entry))*(size_t)nentry))) == NULL) { _zip_error_set(error, ZIP_ER_MEMORY, 0); return -1; } @@ -110,7 +110,7 @@ _zip_cdir_new(zip_uint64_t nentry, struct zip_error *error) if (nentry == 0) cd->entry = NULL; - else if ((cd->entry=(struct zip_entry *)malloc(sizeof(*(cd->entry))*nentry)) == NULL) { + else if ((cd->entry=(struct zip_entry *)malloc(sizeof(*(cd->entry))*(size_t)nentry)) == NULL) { _zip_error_set(error, ZIP_ER_MEMORY, 0); free(cd); return NULL; @@ -260,7 +260,7 @@ _zip_dirent_init(struct zip_dirent *de) de->local_extra_fields_read = 0; de->cloned = 0; - de->version_madeby = 20; + de->version_madeby = 20 | (ZIP_OPSYS_DEFAULT << 8); de->version_needed = 20; /* 2.0 */ de->bitflags = 0; de->comp_method = ZIP_CM_DEFAULT; @@ -273,7 +273,7 @@ _zip_dirent_init(struct zip_dirent *de) de->comment = NULL; de->disk_number = 0; de->int_attrib = 0; - de->ext_attrib = 0; + de->ext_attrib = ZIP_EXT_ATTRIB_DEFAULT; de->offset = 0; } @@ -320,7 +320,7 @@ _zip_dirent_new(void) Returns 0 if successful. On error, error is filled in and -1 is returned. - XXX: leftp and file position undefined on error. + TODO: leftp and file position undefined on error. */ int @@ -460,7 +460,7 @@ _zip_dirent_read(struct zip_dirent *zde, FILE *fp, if (zde->uncomp_size == ZIP_UINT32_MAX || zde->comp_size == ZIP_UINT32_MAX || zde->offset == ZIP_UINT32_MAX) { zip_uint16_t got_len, needed_len; const zip_uint8_t *ef = _zip_ef_get_by_id(zde->extra_fields, &got_len, ZIP_EF_ZIP64, 0, local ? ZIP_EF_LOCAL : ZIP_EF_CENTRAL, error); - /* XXX: if got_len == 0 && !ZIP64_EOCD: no error, 0xffffffff is valid value */ + /* TODO: if got_len == 0 && !ZIP64_EOCD: no error, 0xffffffff is valid value */ if (ef == NULL) return -1; @@ -676,8 +676,8 @@ _zip_dirent_write(struct zip_dirent *de, FILE *fp, zip_flags_t flags, struct zip ef_zip64_p = ef_zip64; if (flags & ZIP_FL_LOCAL) { if ((flags & ZIP_FL_FORCE_ZIP64) || de->comp_size > ZIP_UINT32_MAX || de->uncomp_size > ZIP_UINT32_MAX) { - _zip_poke8(de->comp_size, &ef_zip64_p); _zip_poke8(de->uncomp_size, &ef_zip64_p); + _zip_poke8(de->comp_size, &ef_zip64_p); } } else { @@ -707,7 +707,7 @@ _zip_dirent_write(struct zip_dirent *de, FILE *fp, zip_flags_t flags, struct zip _zip_write2(is_really_zip64 ? 45 : de->version_madeby, fp); _zip_write2(is_really_zip64 ? 45 : de->version_needed, fp); _zip_write2(de->bitflags&0xfff9, fp); /* clear compression method specific flags */ - _zip_write2((zip_uint16_t)de->comp_method, fp); /* XXX: can it be ZIP_CM_DEFAULT? */ + _zip_write2((zip_uint16_t)de->comp_method, fp); /* TODO: can it be ZIP_CM_DEFAULT? */ _zip_u2d_time(de->last_mod, &dostime, &dosdate); _zip_write2(dostime, fp); @@ -796,7 +796,7 @@ _zip_ef_utf8(zip_uint16_t id, struct zip_string *str, struct zip_error *error) raw = _zip_string_get(str, &len, ZIP_FL_ENC_RAW, NULL); if (len+5 > ZIP_UINT16_MAX) { - /* XXX: error */ + /* TODO: error */ } if ((data=(zip_uint8_t *)malloc(len+5)) == NULL) { diff --git a/ext/zip/lib/zip_discard.c b/ext/zip/lib/zip_discard.c index 37ba8c2ea6..040b029411 100644 --- a/ext/zip/lib/zip_discard.c +++ b/ext/zip/lib/zip_discard.c @@ -74,6 +74,7 @@ zip_discard(struct zip *za) } } + _zip_error_fini(&za->error); free(za->file); free(za); diff --git a/ext/zip/lib/zip_extra_field.c b/ext/zip/lib/zip_extra_field.c index 41fd2b1d90..8f1ccaa235 100644 --- a/ext/zip/lib/zip_extra_field.c +++ b/ext/zip/lib/zip_extra_field.c @@ -78,7 +78,7 @@ _zip_ef_delete_by_id(struct zip_extra_field *ef, zip_uint16_t id, zip_uint16_t i head = ef; prev = NULL; for (; ef; ef=(prev ? prev->next : head)) { - if ((ef->flags & flags & ZIP_EF_BOTH) && ef->id == id) { + if ((ef->flags & flags & ZIP_EF_BOTH) && ((ef->id == id) || (id == ZIP_EXTRA_FIELD_ALL))) { if (id_idx == ZIP_EXTRA_FIELD_ALL || i == id_idx) { ef->flags &= ~(flags & ZIP_EF_BOTH); if ((ef->flags & ZIP_EF_BOTH) == 0) { diff --git a/ext/zip/lib/zip_extra_field_api.c b/ext/zip/lib/zip_extra_field_api.c index 02ed4555e0..3e936d2664 100644 --- a/ext/zip/lib/zip_extra_field_api.c +++ b/ext/zip/lib/zip_extra_field_api.c @@ -46,6 +46,11 @@ zip_file_extra_field_delete(struct zip *za, zip_uint64_t idx, zip_uint16_t ef_id _zip_error_set(&za->error, ZIP_ER_INVAL, 0); return -1; } + + if (((flags & ZIP_EF_BOTH) == ZIP_EF_BOTH) && (ef_idx != ZIP_EXTRA_FIELD_ALL)) { + _zip_error_set(&za->error, ZIP_ER_INVAL, 0); + return -1; + } if (_zip_get_dirent(za, idx, 0, NULL) == NULL) return -1; @@ -75,6 +80,11 @@ zip_file_extra_field_delete_by_id(struct zip *za, zip_uint64_t idx, zip_uint16_t _zip_error_set(&za->error, ZIP_ER_INVAL, 0); return -1; } + + if (((flags & ZIP_EF_BOTH) == ZIP_EF_BOTH) && (ef_idx != ZIP_EXTRA_FIELD_ALL)) { + _zip_error_set(&za->error, ZIP_ER_INVAL, 0); + return -1; + } if (_zip_get_dirent(za, idx, 0, NULL) == NULL) return -1; diff --git a/ext/zip/lib/zip_fclose.c b/ext/zip/lib/zip_fclose.c index 093c30eada..c05ec3dd0f 100644 --- a/ext/zip/lib/zip_fclose.c +++ b/ext/zip/lib/zip_fclose.c @@ -62,6 +62,7 @@ zip_fclose(struct zip_file *zf) if (zf->error.zip_err) ret = zf->error.zip_err; + _zip_error_fini(&zf->error); free(zf); return ret; } diff --git a/ext/zip/lib/zip_file_get_offset.c b/ext/zip/lib/zip_file_get_offset.c index 65a011fc07..e8c199fb5b 100644 --- a/ext/zip/lib/zip_file_get_offset.c +++ b/ext/zip/lib/zip_file_get_offset.c @@ -63,7 +63,7 @@ _zip_file_get_offset(const struct zip *za, zip_uint64_t idx, struct zip_error *e return 0; } - /* XXX: cache? */ + /* TODO: cache? */ if ((size=_zip_dirent_size(za->zp, ZIP_EF_LOCAL, error)) < 0) return 0; diff --git a/ext/zip/lib/zip_get_archive_flag.c b/ext/zip/lib/zip_get_archive_flag.c index c3be5c14fe..7be5a3f2be 100644 --- a/ext/zip/lib/zip_get_archive_flag.c +++ b/ext/zip/lib/zip_get_archive_flag.c @@ -38,7 +38,7 @@ ZIP_EXTERN int -zip_get_archive_flag(struct zip *za, unsigned int flag, zip_flags_t flags) +zip_get_archive_flag(struct zip *za, zip_flags_t flag, zip_flags_t flags) { unsigned int fl; diff --git a/ext/zip/lib/zip_get_num_files.c b/ext/zip/lib/zip_get_num_files.c index 29b06dc819..d75941d5e1 100644 --- a/ext/zip/lib/zip_get_num_files.c +++ b/ext/zip/lib/zip_get_num_files.c @@ -44,6 +44,6 @@ zip_get_num_files(struct zip *za) if (za == NULL) return -1; - /* XXX: check for overflow */ + /* TODO: check for overflow */ return (int)za->nentry; } diff --git a/ext/zip/lib/zip_open.c b/ext/zip/lib/zip_open.c index e6a30d5ae7..d91fe469db 100644 --- a/ext/zip/lib/zip_open.c +++ b/ext/zip/lib/zip_open.c @@ -364,7 +364,7 @@ _zip_checkcons(FILE *fp, struct zip_cdir *cd, struct zip_error *error) /* _zip_check_torrentzip: - check wether ZA has a valid TORRENTZIP comment, i.e. is torrentzipped */ + check whether ZA has a valid TORRENTZIP comment, i.e. is torrentzipped */ static void _zip_check_torrentzip(struct zip *za, const struct zip_cdir *cdir) @@ -498,6 +498,11 @@ _zip_find_central_dir(FILE *fp, unsigned int flags, int *zep, off_t len) zip_int64_t best; struct zip_error zerr; + if (len < (off_t)EOCDLEN) { + set_error(zep, NULL, ZIP_ER_NOZIP); + return NULL; + } + i = fseeko(fp, -(len < CDBUFSIZE ? len : CDBUFSIZE), SEEK_END); if (i == -1 && errno != EFBIG) { /* seek before start of file on my machine */ diff --git a/ext/zip/lib/zip_set_archive_flag.c b/ext/zip/lib/zip_set_archive_flag.c index b6cdab120d..68f99b8568 100644 --- a/ext/zip/lib/zip_set_archive_flag.c +++ b/ext/zip/lib/zip_set_archive_flag.c @@ -38,7 +38,7 @@ ZIP_EXTERN int -zip_set_archive_flag(struct zip *za, unsigned int flag, int value) +zip_set_archive_flag(struct zip *za, zip_flags_t flag, int value) { unsigned int new_flags; diff --git a/ext/zip/lib/zip_set_file_compression.c b/ext/zip/lib/zip_set_file_compression.c index ea8517d70e..647f69a68f 100644 --- a/ext/zip/lib/zip_set_file_compression.c +++ b/ext/zip/lib/zip_set_file_compression.c @@ -63,7 +63,7 @@ zip_set_file_compression(struct zip *za, zip_uint64_t idx, old_method = (e->orig == NULL ? ZIP_CM_DEFAULT : e->orig->comp_method); - /* XXX: revisit this when flags are supported, since they may require a recompression */ + /* TODO: revisit this when flags are supported, since they may require a recompression */ if (method == old_method) { if (e->changes) { diff --git a/ext/zip/lib/zip_set_name.c b/ext/zip/lib/zip_set_name.c index 60c9e7d5bf..02fa1272d6 100644 --- a/ext/zip/lib/zip_set_name.c +++ b/ext/zip/lib/zip_set_name.c @@ -59,7 +59,7 @@ _zip_set_name(struct zip *za, zip_uint64_t idx, const char *name, zip_flags_t fl } if (name && strlen(name) > 0) { - /* XXX: check for string too long */ + /* TODO: check for string too long */ if ((str=_zip_string_new((const zip_uint8_t *)name, (zip_uint16_t)strlen(name), flags, &za->error)) == NULL) return -1; if ((flags & ZIP_FL_ENCODING_ALL) == ZIP_FL_ENC_GUESS && _zip_guess_encoding(str, ZIP_ENCODING_UNKNOWN) == ZIP_ENCODING_UTF8_GUESSED) @@ -68,7 +68,7 @@ _zip_set_name(struct zip *za, zip_uint64_t idx, const char *name, zip_flags_t fl else str = NULL; - /* XXX: encoding flags needed for CP437? */ + /* TODO: encoding flags needed for CP437? */ if ((i=_zip_name_locate(za, name, 0, NULL)) >= 0 && (zip_uint64_t)i != idx) { _zip_string_free(str); _zip_error_set(&za->error, ZIP_ER_EXISTS, 0); diff --git a/ext/zip/lib/zip_source_crc.c b/ext/zip/lib/zip_source_crc.c index 99bc965228..7d6df6a385 100644 --- a/ext/zip/lib/zip_source_crc.c +++ b/ext/zip/lib/zip_source_crc.c @@ -125,7 +125,7 @@ crc_read(struct zip_source *src, void *_ctx, void *data, } else { ctx->size += (zip_uint64_t)n; - ctx->crc = (zip_uint32_t)crc32(ctx->crc, (const Bytef *)data, (uInt)n); /* XXX: check for overflow, use multiple crc calls if needed */ + ctx->crc = (zip_uint32_t)crc32(ctx->crc, (const Bytef *)data, (uInt)n); /* TODO: check for overflow, use multiple crc calls if needed */ } return n; @@ -139,7 +139,7 @@ crc_read(struct zip_source *src, void *_ctx, void *data, st = (struct zip_stat *)data; if (ctx->eof) { - /* XXX: Set comp_size, comp_method, encryption_method? + /* TODO: Set comp_size, comp_method, encryption_method? After all, this only works for uncompressed data. */ st->size = ctx->size; st->crc = ctx->crc; diff --git a/ext/zip/lib/zip_source_deflate.c b/ext/zip/lib/zip_source_deflate.c index 879953144c..57444d9677 100644 --- a/ext/zip/lib/zip_source_deflate.c +++ b/ext/zip/lib/zip_source_deflate.c @@ -113,7 +113,7 @@ compress_read(struct zip_source *src, struct deflate *ctx, return 0; ctx->zstr.next_out = (Bytef *)data; - ctx->zstr.avail_out = (uInt)len; /* XXX: check for overflow */ + ctx->zstr.avail_out = (uInt)len; /* TODO: check for overflow */ end = 0; while (!end) { @@ -144,7 +144,7 @@ compress_read(struct zip_source *src, struct deflate *ctx, else if (n == 0) { ctx->eof = 1; ctx->size = ctx->zstr.total_in; - /* XXX: check against stat of src? */ + /* TODO: check against stat of src? */ } else { ctx->zstr.next_in = (Bytef *)ctx->buffer; @@ -187,7 +187,7 @@ decompress_read(struct zip_source *src, struct deflate *ctx, return 0; ctx->zstr.next_out = (Bytef *)data; - ctx->zstr.avail_out = (uInt)len; /* XXX: check for overflow */ + ctx->zstr.avail_out = (uInt)len; /* TODO: check for overflow */ end = 0; while (!end && ctx->zstr.avail_out) { @@ -332,7 +332,7 @@ deflate_decompress(struct zip_source *src, void *ud, void *data, ctx->zstr.zfree = Z_NULL; ctx->zstr.opaque = NULL; ctx->zstr.next_in = (Bytef *)ctx->buffer; - ctx->zstr.avail_in = (uInt)n /* XXX: check for overflow */; + ctx->zstr.avail_in = (uInt)n /* TODO: check for overflow */; /* negative value to tell zlib that there is no header */ if ((ret=inflateInit2(&ctx->zstr, -MAX_WBITS)) != Z_OK) { @@ -370,7 +370,7 @@ deflate_decompress(struct zip_source *src, void *ud, void *data, return sizeof(int)*2; case ZIP_SOURCE_FREE: - /* XXX: inflateEnd if close was not called */ + /* TODO: inflateEnd if close was not called */ free(ctx); return 0; @@ -387,6 +387,6 @@ deflate_decompress(struct zip_source *src, void *ud, void *data, static void deflate_free(struct deflate *ctx) { - /* XXX: deflateEnd if close was not called */ + /* TODO: deflateEnd if close was not called */ free(ctx); } diff --git a/ext/zip/lib/zip_source_filep.c b/ext/zip/lib/zip_source_filep.c index 0bd2d6846e..fcebe73bc6 100644 --- a/ext/zip/lib/zip_source_filep.c +++ b/ext/zip/lib/zip_source_filep.c @@ -125,7 +125,8 @@ read_file(void *state, void *data, zip_uint64_t len, enum zip_source_cmd cmd) { struct read_file *z; char *buf; - size_t i, n; + zip_uint64_t n; + size_t i; z = (struct read_file *)state; buf = (char *)data; @@ -151,11 +152,13 @@ read_file(void *state, void *data, zip_uint64_t len, enum zip_source_cmd cmd) return 0; case ZIP_SOURCE_READ: - /* XXX: return INVAL if len > size_t max */ if (z->remain != -1) n = len > (zip_uint64_t)z->remain ? (zip_uint64_t)z->remain : len; else n = len; + + if (n > SIZE_MAX) + n = SIZE_MAX; if (!z->closep) { /* we might share this file with others, so let's be safe */ @@ -166,7 +169,7 @@ read_file(void *state, void *data, zip_uint64_t len, enum zip_source_cmd cmd) } } - if ((i=fread(buf, 1, n, z->f)) == 0) { + if ((i=fread(buf, 1, (size_t)n, z->f)) == 0) { if (ferror(z->f)) { z->e[0] = ZIP_ER_READ; z->e[1] = errno; diff --git a/ext/zip/lib/zip_source_pkware.c b/ext/zip/lib/zip_source_pkware.c index ec53dfeef0..f6cbf1d2d5 100644 --- a/ext/zip/lib/zip_source_pkware.c +++ b/ext/zip/lib/zip_source_pkware.c @@ -204,7 +204,7 @@ pkware_decrypt(struct zip_source *src, void *ud, void *data, st->encryption_method = ZIP_EM_NONE; st->valid |= ZIP_STAT_ENCRYPTION_METHOD; - /* XXX: deduce HEADERLEN from size for uncompressed */ + /* TODO: deduce HEADERLEN from size for uncompressed */ if (st->valid & ZIP_STAT_COMP_SIZE) st->comp_size -= HEADERLEN; } diff --git a/ext/zip/lib/zip_source_zip_new.c b/ext/zip/lib/zip_source_zip_new.c index 8e48f6f3fa..353489a653 100644 --- a/ext/zip/lib/zip_source_zip_new.c +++ b/ext/zip/lib/zip_source_zip_new.c @@ -121,12 +121,12 @@ _zip_source_zip_new(struct zip *za, struct zip *srcza, zip_uint64_t srcidx, zip_ st2.mtime = st.mtime; st2.valid = ZIP_STAT_SIZE|ZIP_STAT_COMP_SIZE|ZIP_STAT_COMP_METHOD|ZIP_STAT_MTIME; - /* XXX: check for overflow of st2.size */ + /* TODO: check for overflow of st2.size */ if ((src=_zip_source_file_or_p(za, NULL, srcza->zp, offset+start, (zip_int64_t)st2.size, 0, &st2)) == NULL) return NULL; } else { - /* XXX: check for overflow of st.comp_size */ + /* TODO: check for overflow of st.comp_size */ if ((src=_zip_source_file_or_p(za, NULL, srcza->zp, offset, (zip_int64_t)st.comp_size, 0, &st)) == NULL) return NULL; } @@ -134,7 +134,7 @@ _zip_source_zip_new(struct zip *za, struct zip *srcza, zip_uint64_t srcidx, zip_ if (enc_impl) { if ((s2=enc_impl(za, src, st.encryption_method, 0, password)) == NULL) { zip_source_free(src); - /* XXX: set error (how?) */ + /* TODO: set error (how?) */ return NULL; } src = s2; @@ -142,7 +142,7 @@ _zip_source_zip_new(struct zip *za, struct zip *srcza, zip_uint64_t srcidx, zip_ if (comp_impl) { if ((s2=comp_impl(za, src, st.comp_method, 0)) == NULL) { zip_source_free(src); - /* XXX: set error (how?) */ + /* TODO: set error (how?) */ return NULL; } src = s2; @@ -152,7 +152,7 @@ _zip_source_zip_new(struct zip *za, struct zip *srcza, zip_uint64_t srcidx, zip_ /* when reading the whole file, check for crc errors */ if ((s2=zip_source_crc(za, src, 1)) == NULL) { zip_source_free(src); - /* XXX: set error (how?) */ + /* TODO: set error (how?) */ return NULL; } src = s2; @@ -161,7 +161,7 @@ _zip_source_zip_new(struct zip *za, struct zip *srcza, zip_uint64_t srcidx, zip_ if (start+len > 0 && (comp_impl || enc_impl)) { if ((s2=zip_source_window(za, src, start, len ? len : st.size-start)) == NULL) { zip_source_free(src); - /* XXX: set error (how?) (why?) */ + /* TODO: set error (how?) (why?) */ return NULL; } src = s2; diff --git a/ext/zip/lib/zip_stat_index.c b/ext/zip/lib/zip_stat_index.c index f4ce72aaa8..2505c80138 100644 --- a/ext/zip/lib/zip_stat_index.c +++ b/ext/zip/lib/zip_stat_index.c @@ -68,7 +68,7 @@ zip_stat_index(struct zip *za, zip_uint64_t index, zip_flags_t flags, st->comp_method = (zip_uint16_t)de->comp_method; if (de->bitflags & ZIP_GPBF_ENCRYPTED) { if (de->bitflags & ZIP_GPBF_STRONG_ENCRYPTION) { - /* XXX */ + /* TODO */ st->encryption_method = ZIP_EM_UNKNOWN; } else diff --git a/ext/zip/lib/zip_string.c b/ext/zip/lib/zip_string.c index a2d5eb5d3f..4e8709b5f7 100644 --- a/ext/zip/lib/zip_string.c +++ b/ext/zip/lib/zip_string.c @@ -64,7 +64,7 @@ _zip_string_equal(const struct zip_string *a, const struct zip_string *b) if (a->length != b->length) return 0; - /* XXX: encoding */ + /* TODO: encoding */ return (memcmp(a->raw, b->raw, a->length) == 0); } diff --git a/ext/zip/lib/zipint.h b/ext/zip/lib/zipint.h index e8765c5b66..372923d418 100644 --- a/ext/zip/lib/zipint.h +++ b/ext/zip/lib/zipint.h @@ -56,19 +56,14 @@ # include "config.h" #endif -#if defined(HAVE_MOVEFILEEXA) && defined(_WIN32) +#ifdef HAVE_MOVEFILEEXA #include <windows.h> -#define _zip_rename(s, t) \ - (!MoveFileExA((s), (t), MOVEFILE_COPY_ALLOWED|MOVEFILE_REPLACE_EXISTING)) +#define _zip_rename(s, t) (!MoveFileExA((s), (t), MOVEFILE_COPY_ALLOWED|MOVEFILE_REPLACE_EXISTING)) #else #define _zip_rename rename #endif #ifdef _WIN32 -#undef strcasecmp -# define strcasecmp _strcmpi -#endif - #if defined(HAVE__CLOSE) #define close _close #endif @@ -86,12 +81,13 @@ #if defined(HAVE__OPEN) #define open(a, b, c) _open((a), (b)) #endif -#if defined(HAVE__SNPRINTF) +#if defined(HAVE__SNPRINTF) && !defined(PHP_WIN32) #define snprintf _snprintf #endif -#if defined(HAVE__STRDUP) && !defined(strdup) +#if defined(HAVE__STRDUP) && !defined(HAVE_STRDUP) #define strdup _strdup #endif +#endif #ifndef HAVE_FSEEKO #define fseeko(s, o, w) (fseek((s), (long int)(o), (w))) @@ -122,6 +118,18 @@ int _zip_mkstemp(char *); #error unsupported size of off_t #endif +#ifndef SIZE_MAX +#if SIZEOF_SIZE_T == 8 +#define SIZE_MAX ZIP_INT64_MAX +#elif SIZEOF_SIZE_T == 4 +#define SIZE_MAX ZIP_INT32_MAX +#elif SIZEOF_SIZE_T == 2 +#define SIZE_MAX ZIP_INT16_MAX +#else +#error unsupported size of size_t +#endif +#endif + #define CENTRAL_MAGIC "PK\1\2" #define LOCAL_MAGIC "PK\3\4" #define EOCD_MAGIC "PK\5\6" @@ -151,7 +159,12 @@ int _zip_mkstemp(char *); #define ZIP_EF_ZIP64 0x0001 #define ZIP_EF_IS_INTERNAL(id) ((id) == ZIP_EF_UTF_8_COMMENT || (id) == ZIP_EF_UTF_8_NAME || (id) == ZIP_EF_ZIP64) - + +/* according to unzip-6.0's zipinfo.c, this corresponds to a regular file with rw permissions for everyone */ +#define ZIP_EXT_ATTRIB_DEFAULT (0100666<<16) +/* according to unzip-6.0's zipinfo.c, this corresponds to a directory with rwx permissions for everyone */ +#define ZIP_EXT_ATTRIB_DEFAULT_DIR (0040777<<16) + /* This section contains API that won't materialize like this. It's placed in the internal section, pending cleanup. */ @@ -296,12 +309,13 @@ struct zip_file { #define ZIP_DIRENT_FILENAME 0x0002u #define ZIP_DIRENT_COMMENT 0x0004u #define ZIP_DIRENT_EXTRA_FIELD 0x0008u +#define ZIP_DIRENT_ATTRIBUTES 0x0010u #define ZIP_DIRENT_ALL 0xffffu struct zip_dirent { zip_uint32_t changed; int local_extra_fields_read; /* whether we already read in local header extra fields */ - int cloned; /* wether this instance is cloned, and thus shares non-changed strings */ + int cloned; /* whether this instance is cloned, and thus shares non-changed strings */ zip_uint16_t version_madeby; /* (c) version of creator */ zip_uint16_t version_needed; /* (cl) version needed to extract */ diff --git a/ext/zip/php_zip.c b/ext/zip/php_zip.c index 5e7d99b755..ccfbb73a29 100644 --- a/ext/zip/php_zip.c +++ b/ext/zip/php_zip.c @@ -336,7 +336,7 @@ static int php_zip_add_file(struct zip *za, const char *filename, size_t filenam if (!zs) { return -1; } - if (zip_file_add(za, entry_name, zs, ZIP_FL_OVERWRITE) < 0) { + if (zip_file_add(za, entry_name, zs, ZIP_FL_OVERWRITE) < 0) { zip_source_free(zs); return -1; } else { @@ -1541,6 +1541,7 @@ static ZIPARCHIVE_METHOD(open) /* we already have an opened zip, free it */ if (zip_close(ze_obj->za) != 0) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty string as source"); + efree(resolved_path); RETURN_FALSE; } ze_obj->za = NULL; @@ -1552,6 +1553,7 @@ static ZIPARCHIVE_METHOD(open) intern = zip_open(resolved_path, flags, &err); if (!intern || err) { + efree(resolved_path); RETURN_LONG((long)err); } ze_obj->filename = resolved_path; @@ -2156,6 +2158,156 @@ static ZIPARCHIVE_METHOD(setCommentIndex) } /* }}} */ +/* those constants/functions are only available in libzip since 0.11.2 */ +#ifdef ZIP_OPSYS_DEFAULT + +/* {{{ proto bool ZipArchive::setExternalAttributesName(string name, int opsys, int attr [, int flags]) +Set external attributes for file in zip, using its name */ +static ZIPARCHIVE_METHOD(setExternalAttributesName) +{ + struct zip *intern; + zval *this = getThis(); + int name_len; + char *name; + long flags=0, opsys, attr; + zip_int64_t idx; + + if (!this) { + RETURN_FALSE; + } + + ZIP_FROM_OBJECT(intern, this); + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "sll|l", + &name, &name_len, &opsys, &attr, &flags) == FAILURE) { + return; + } + + if (name_len < 1) { + php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Empty string as entry name"); + } + + idx = zip_name_locate(intern, name, 0); + if (idx < 0) { + RETURN_FALSE; + } + if (zip_file_set_external_attributes(intern, idx, (zip_flags_t)flags, + (zip_uint8_t)(opsys&0xff), (zip_uint32_t)attr) < 0) { + RETURN_FALSE; + } + RETURN_TRUE; +} +/* }}} */ + +/* {{{ proto bool ZipArchive::setExternalAttributesIndex(int index, int opsys, int attr [, int flags]) +Set external attributes for file in zip, using its index */ +static ZIPARCHIVE_METHOD(setExternalAttributesIndex) +{ + struct zip *intern; + zval *this = getThis(); + long index, flags=0, opsys, attr; + struct zip_stat sb; + + if (!this) { + RETURN_FALSE; + } + + ZIP_FROM_OBJECT(intern, this); + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "lll|l", + &index, &opsys, &attr, &flags) == FAILURE) { + return; + } + + PHP_ZIP_STAT_INDEX(intern, index, 0, sb); + if (zip_file_set_external_attributes(intern, (zip_uint64_t)index, + (zip_flags_t)flags, (zip_uint8_t)(opsys&0xff), (zip_uint32_t)attr) < 0) { + RETURN_FALSE; + } + RETURN_TRUE; +} +/* }}} */ + +/* {{{ proto bool ZipArchive::getExternalAttributesName(string name, int &opsys, int &attr [, int flags]) +Get external attributes for file in zip, using its name */ +static ZIPARCHIVE_METHOD(getExternalAttributesName) +{ + struct zip *intern; + zval *this = getThis(), *z_opsys, *z_attr; + int name_len; + char *name; + long flags=0; + zip_uint8_t opsys; + zip_uint32_t attr; + zip_int64_t idx; + + if (!this) { + RETURN_FALSE; + } + + ZIP_FROM_OBJECT(intern, this); + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "szz|l", + &name, &name_len, &z_opsys, &z_attr, &flags) == FAILURE) { + return; + } + + if (name_len < 1) { + php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Empty string as entry name"); + } + + idx = zip_name_locate(intern, name, 0); + if (idx < 0) { + RETURN_FALSE; + } + if (zip_file_get_external_attributes(intern, idx, + (zip_flags_t)flags, &opsys, &attr) < 0) { + RETURN_FALSE; + } + zval_dtor(z_opsys); + ZVAL_LONG(z_opsys, opsys); + zval_dtor(z_attr); + ZVAL_LONG(z_attr, attr); + RETURN_TRUE; +} +/* }}} */ + +/* {{{ proto bool ZipArchive::getExternalAttributesIndex(int index, int &opsys, int &attr [, int flags]) +Get external attributes for file in zip, using its index */ +static ZIPARCHIVE_METHOD(getExternalAttributesIndex) +{ + struct zip *intern; + zval *this = getThis(), *z_opsys, *z_attr; + long index, flags=0; + zip_uint8_t opsys; + zip_uint32_t attr; + struct zip_stat sb; + + if (!this) { + RETURN_FALSE; + } + + ZIP_FROM_OBJECT(intern, this); + + if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "lzz|l", + &index, &z_opsys, &z_attr, &flags) == FAILURE) { + return; + } + + PHP_ZIP_STAT_INDEX(intern, index, 0, sb); + if (zip_file_get_external_attributes(intern, (zip_uint64_t)index, + (zip_flags_t)flags, &opsys, &attr) < 0) { + RETURN_FALSE; + } + zval_dtor(z_opsys); + ZVAL_LONG(z_opsys, opsys); + zval_dtor(z_attr); + ZVAL_LONG(z_attr, attr); + RETURN_TRUE; +} +/* }}} */ +#endif /* ifdef ZIP_OPSYS_DEFAULT */ + /* {{{ proto string ZipArchive::getCommentName(string name[, int flags]) Returns the comment of an entry using its name */ static ZIPARCHIVE_METHOD(getCommentName) @@ -2784,6 +2936,36 @@ ZEND_END_ARG_INFO() ZEND_BEGIN_ARG_INFO_EX(arginfo_ziparchive_getstream, 0, 0, 1) ZEND_ARG_INFO(0, entryname) ZEND_END_ARG_INFO() + +#ifdef ZIP_OPSYS_DEFAULT +ZEND_BEGIN_ARG_INFO_EX(arginfo_ziparchive_setextattrname, 0, 0, 3) + ZEND_ARG_INFO(0, name) + ZEND_ARG_INFO(0, opsys) + ZEND_ARG_INFO(0, attr) + ZEND_ARG_INFO(0, flags) +ZEND_END_ARG_INFO() + +ZEND_BEGIN_ARG_INFO_EX(arginfo_ziparchive_setextattrindex, 0, 0, 3) + ZEND_ARG_INFO(0, index) + ZEND_ARG_INFO(0, opsys) + ZEND_ARG_INFO(0, attr) + ZEND_ARG_INFO(0, flags) +ZEND_END_ARG_INFO() + +ZEND_BEGIN_ARG_INFO_EX(arginfo_ziparchive_getextattrname, 0, 0, 3) + ZEND_ARG_INFO(0, name) + ZEND_ARG_INFO(1, opsys) + ZEND_ARG_INFO(1, attr) + ZEND_ARG_INFO(0, flags) +ZEND_END_ARG_INFO() + +ZEND_BEGIN_ARG_INFO_EX(arginfo_ziparchive_getextattrindex, 0, 0, 3) + ZEND_ARG_INFO(0, index) + ZEND_ARG_INFO(1, opsys) + ZEND_ARG_INFO(1, attr) + ZEND_ARG_INFO(0, flags) +ZEND_END_ARG_INFO() +#endif /* ifdef ZIP_OPSYS_DEFAULT */ /* }}} */ /* {{{ ze_zip_object_class_functions */ @@ -2819,6 +3001,10 @@ static const zend_function_entry zip_class_functions[] = { ZIPARCHIVE_ME(getFromName, arginfo_ziparchive_getfromname, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(getFromIndex, arginfo_ziparchive_getfromindex, ZEND_ACC_PUBLIC) ZIPARCHIVE_ME(getStream, arginfo_ziparchive_getstream, ZEND_ACC_PUBLIC) + ZIPARCHIVE_ME(setExternalAttributesName, arginfo_ziparchive_setextattrname, ZEND_ACC_PUBLIC) + ZIPARCHIVE_ME(setExternalAttributesIndex, arginfo_ziparchive_setextattrindex, ZEND_ACC_PUBLIC) + ZIPARCHIVE_ME(getExternalAttributesName, arginfo_ziparchive_getextattrname, ZEND_ACC_PUBLIC) + ZIPARCHIVE_ME(getExternalAttributesIndex, arginfo_ziparchive_getextattrindex, ZEND_ACC_PUBLIC) {NULL, NULL, NULL} }; /* }}} */ @@ -2902,8 +3088,32 @@ static PHP_MINIT_FUNCTION(zip) REGISTER_ZIP_CLASS_CONST_LONG("ER_REMOVE", ZIP_ER_REMOVE); /* S Can't remove file */ REGISTER_ZIP_CLASS_CONST_LONG("ER_DELETED", ZIP_ER_DELETED); /* N Entry has been deleted */ +#ifdef ZIP_OPSYS_DEFAULT + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_DOS", ZIP_OPSYS_DOS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_AMIGA", ZIP_OPSYS_AMIGA); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_OPENVMS", ZIP_OPSYS_OPENVMS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_UNIX", ZIP_OPSYS_UNIX); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_VM_CMS", ZIP_OPSYS_VM_CMS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_ATARI_ST", ZIP_OPSYS_ATARI_ST); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_OS_2", ZIP_OPSYS_OS_2); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_MACINTOSH", ZIP_OPSYS_MACINTOSH); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_Z_SYSTEM", ZIP_OPSYS_Z_SYSTEM); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_WINDOWS_NTFS", ZIP_OPSYS_WINDOWS_NTFS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_MVS", ZIP_OPSYS_MVS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_VSE", ZIP_OPSYS_VSE); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_ACORN_RISC", ZIP_OPSYS_ACORN_RISC); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_VFAT", ZIP_OPSYS_VFAT); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_ALTERNATE_MVS", ZIP_OPSYS_ALTERNATE_MVS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_BEOS", ZIP_OPSYS_BEOS); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_TANDEM", ZIP_OPSYS_TANDEM); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_OS_400", ZIP_OPSYS_OS_400); + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_OS_X", ZIP_OPSYS_OS_X); + + REGISTER_ZIP_CLASS_CONST_LONG("OPSYS_DEFAULT", ZIP_OPSYS_DEFAULT); +#endif /* ifdef ZIP_OPSYS_DEFAULT */ + php_register_url_stream_wrapper("zip", &php_stream_zip_wrapper TSRMLS_CC); -#endif +#endif /* ifdef PHP_ZIP_USE_OO */ 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); diff --git a/ext/zip/php_zip.h b/ext/zip/php_zip.h index c8da941b7a..8cceff7136 100644 --- a/ext/zip/php_zip.h +++ b/ext/zip/php_zip.h @@ -38,7 +38,7 @@ extern zend_module_entry zip_module_entry; #define ZIP_OVERWRITE ZIP_TRUNCATE #endif -#define PHP_ZIP_VERSION "1.12.3" +#define PHP_ZIP_VERSION "1.12.4-dev" #if ((PHP_MAJOR_VERSION >= 5 && PHP_MINOR_VERSION >= 2) || PHP_MAJOR_VERSION >= 6) # define PHP_ZIP_USE_OO 1 |