From c3dca970ead4c30539f2622e805974c5dfb43b6f Mon Sep 17 00:00:00 2001 From: Gina Peter Banyard Date: Thu, 23 Apr 2026 21:15:38 +0100 Subject: [PATCH] ext/phar: refactor phar_get_archive() to return phar_archive_data* Instead of using an out param. --- ext/phar/dirstream.c | 20 ++--- ext/phar/func_interceptors.c | 20 +++-- ext/phar/phar.c | 5 +- ext/phar/phar_internal.h | 2 +- ext/phar/phar_object.c | 8 +- ext/phar/stream.c | 21 +++-- ext/phar/util.c | 147 ++++++++++++++++------------------- ext/phar/zip.c | 3 +- 8 files changed, 104 insertions(+), 122 deletions(-) diff --git a/ext/phar/dirstream.c b/ext/phar/dirstream.c index 4bef14dfe6ae..2b74a566411f 100644 --- a/ext/phar/dirstream.c +++ b/ext/phar/dirstream.c @@ -248,7 +248,6 @@ static php_stream *phar_make_dirstream(const char *dir, size_t dirlen, const Has php_stream *phar_wrapper_open_dir(php_stream_wrapper *wrapper, const char *path, const char *mode, int options, zend_string **opened_path, php_stream_context *context STREAMS_DC) /* {{{ */ { char *error; - phar_archive_data *phar; php_url *resource = phar_parse_url(wrapper, path, mode, options); if (!resource) { @@ -276,7 +275,8 @@ php_stream *phar_wrapper_open_dir(php_stream_wrapper *wrapper, const char *path, phar_request_initialize(); - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error)) { + const phar_archive_data *phar = phar_get_archive(ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error); + if (!phar) { if (error) { php_stream_wrapper_log_error(wrapper, options, "%s", error); efree(error); @@ -340,7 +340,6 @@ php_stream *phar_wrapper_open_dir(php_stream_wrapper *wrapper, const char *path, int phar_wrapper_mkdir(php_stream_wrapper *wrapper, const char *url_from, int mode, int options, php_stream_context *context) /* {{{ */ { phar_entry_info entry; - phar_archive_data *phar = NULL; char *error; php_url *resource = NULL; @@ -351,9 +350,7 @@ int phar_wrapper_mkdir(php_stream_wrapper *wrapper, const char *url_from, int mo return 0; } - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL)) { - phar = NULL; - } + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); zend_string_release_ex(arch, false); @@ -379,7 +376,8 @@ int phar_wrapper_mkdir(php_stream_wrapper *wrapper, const char *url_from, int mo return 0; } - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error)) { + phar = phar_get_archive(ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error); + if (!phar) { php_stream_wrapper_log_error(wrapper, options, "phar error: cannot create directory \"%s\" in phar \"%s\", error retrieving phar information: %s", ZSTR_VAL(resource->path) + 1, ZSTR_VAL(resource->host), error); efree(error); php_url_free(resource); @@ -467,7 +465,6 @@ int phar_wrapper_mkdir(php_stream_wrapper *wrapper, const char *url_from, int mo */ int phar_wrapper_rmdir(php_stream_wrapper *wrapper, const char *url, int options, php_stream_context *context) /* {{{ */ { - phar_archive_data *phar = NULL; char *error; /* pre-readonly check, we need to know if this is a data phar */ @@ -477,9 +474,7 @@ int phar_wrapper_rmdir(php_stream_wrapper *wrapper, const char *url, int options return 0; } - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL)) { - phar = NULL; - } + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); zend_string_release_ex(arch, false); @@ -506,7 +501,8 @@ int phar_wrapper_rmdir(php_stream_wrapper *wrapper, const char *url, int options return 0; } - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error)) { + phar = phar_get_archive(ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, &error); + if (!phar) { php_stream_wrapper_log_error(wrapper, options, "phar error: cannot remove directory \"%s\" in phar \"%s\", error retrieving phar information: %s", ZSTR_VAL(resource->path)+1, ZSTR_VAL(resource->host), error); efree(error); php_url_free(resource); diff --git a/ext/phar/func_interceptors.c b/ext/phar/func_interceptors.c index 61bb9050550f..e2b45ac2a0ae 100644 --- a/ext/phar/func_interceptors.c +++ b/ext/phar/func_interceptors.c @@ -98,8 +98,8 @@ static zend_string* phar_get_name_for_relative_paths(zend_string *filename, bool /* fopen within phar, if :// is not in the url, then prepend phar:/// */ /* retrieving a file defaults to within the current directory, so use this if possible */ - phar_archive_data *phar; - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL)) { + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); + if (!phar) { zend_string_release_ex(arch, false); return NULL; } @@ -492,9 +492,9 @@ static void phar_file_stat(const char *filename, size_t filename_length, int typ zend_string *arch = phar_split_fname(ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 2, 0); if (arch) { /* fopen within phar, if :// is not in the url, then prepend phar:/// */ - zend_result has_archive = phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); + phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); zend_string_release_ex(arch, false); - if (FAILURE == has_archive) { + if (!phar) { goto skip_phar; } splitted:; @@ -727,13 +727,13 @@ PHP_FUNCTION(phar_is_file) /* {{{ */ zend_string *arch = phar_split_fname(ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 2, 0); if (arch) { - phar_archive_data *phar; + ; /* fopen within phar, if :// is not in the url, then prepend phar:/// */ /* retrieving a file within the current directory, so use this if possible */ - zend_result has_archive = phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); zend_string_release_ex(arch, false); - if (has_archive == SUCCESS) { + if (phar) { phar_entry_info *etemp; zend_string *entry = phar_fix_filepath(filename, filename_len, true); @@ -784,13 +784,11 @@ PHP_FUNCTION(phar_is_link) /* {{{ */ zend_string *arch = phar_split_fname(ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 2, 0); if (arch) { - phar_archive_data *phar; - /* fopen within phar, if :// is not in the url, then prepend phar:/// */ /* retrieving a file within the current directory, so use this if possible */ - zend_result has_archive = phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); zend_string_release_ex(arch, false); - if (has_archive == SUCCESS) { + if (phar) { phar_entry_info *etemp; zend_string *entry = phar_fix_filepath(filename, filename_len, true); diff --git a/ext/phar/phar.c b/ext/phar/phar.c index 2ab799ab8c83..6d255abd95a4 100644 --- a/ext/phar/phar.c +++ b/ext/phar/phar.c @@ -486,7 +486,6 @@ ZEND_ATTRIBUTE_NONNULL void phar_entry_remove(phar_entry_data *idata, char **err */ static zend_result phar_open_parsed_phar(char *fname, size_t fname_len, char *alias, size_t alias_len, bool is_data, uint32_t options, phar_archive_data** pphar, char **error) /* {{{ */ { - phar_archive_data *phar; #ifdef PHP_WIN32 char *save_fname; ALLOCA_FLAG(fname_use_heap) @@ -504,12 +503,12 @@ static zend_result phar_open_parsed_phar(char *fname, size_t fname_len, char *al phar_unixify_path_separators(fname, fname_len); } #endif - zend_result archive_retrieved = phar_get_archive(&phar, fname, fname_len, alias, alias_len, error); + phar_archive_data *phar = phar_get_archive(fname, fname_len, alias, alias_len, error); /* logic is as follows: - If no alias was passed in, then it can match either and be valid - If an explicit alias was requested, ensure the filename passed in matches the phar's filename. */ - bool process_phar = SUCCESS == archive_retrieved && (!alias || zend_string_equals_cstr(phar->fname, fname, fname_len)); + bool process_phar = phar && (!alias || zend_string_equals_cstr(phar->fname, fname, fname_len)); #ifdef PHP_WIN32 if (fname != save_fname) { free_alloca(fname, fname_use_heap); diff --git a/ext/phar/phar_internal.h b/ext/phar/phar_internal.h index 36fa2b543501..8de0ec4a363b 100644 --- a/ext/phar/phar_internal.h +++ b/ext/phar/phar_internal.h @@ -411,7 +411,7 @@ ZEND_ATTRIBUTE_NONNULL_ARGS(1, 6, 7) zend_result phar_open_or_create_filename(ze ZEND_ATTRIBUTE_NONNULL_ARGS(1, 6, 7) zend_result phar_create_or_parse_filename(zend_string *fname, char *alias, size_t alias_len, bool is_data, uint32_t options, phar_archive_data** pphar, char **error); ZEND_ATTRIBUTE_NONNULL_ARGS(3) zend_result phar_open_executed_filename(char *alias, size_t alias_len, char **error); zend_result phar_free_alias(const phar_archive_data *phar); -zend_result phar_get_archive(phar_archive_data **archive, const char *fname, size_t fname_len, const char *alias, size_t alias_len, char **error); +phar_archive_data* phar_get_archive(const char *fname, size_t fname_len, const char *alias, size_t alias_len, char **error); zend_result phar_verify_signature(php_stream *fp, size_t end_of_phar, uint32_t sig_type, char *sig, size_t sig_len, const char *fname, char **signature, size_t *signature_len, char **error); ZEND_ATTRIBUTE_NONNULL zend_result phar_create_signature(phar_archive_data *phar, php_stream *fp, char **signature, size_t *signature_length, char **error); diff --git a/ext/phar/phar_object.c b/ext/phar/phar_object.c index bc55c175f7ba..1766d9f778eb 100644 --- a/ext/phar/phar_object.c +++ b/ext/phar/phar_object.c @@ -752,8 +752,8 @@ PHP_METHOD(Phar, webPhar) entry_len = sizeof("/index.php")-1; } - if (FAILURE == phar_get_archive(&phar, fname, fname_len, NULL, 0, NULL) || - (info = phar_get_entry_info(phar, entry, entry_len, NULL, false)) == NULL) { + phar = phar_get_archive(fname, fname_len, NULL, 0, NULL); + if (!phar || (info = phar_get_entry_info(phar, entry, entry_len, NULL, false)) == NULL) { phar_do_404(phar, fname, fname_len, f404); } else { char *tmp = NULL, sa = '\0'; @@ -793,8 +793,8 @@ PHP_METHOD(Phar, webPhar) goto cleanup_skip_entry; } - if (FAILURE == phar_get_archive(&phar, fname, fname_len, NULL, 0, NULL) || - (info = phar_get_entry_info(phar, entry, entry_len, NULL, false)) == NULL) { + phar = phar_get_archive(fname, fname_len, NULL, 0, NULL); + if (!phar || (info = phar_get_entry_info(phar, entry, entry_len, NULL, false)) == NULL) { phar_do_404(phar, fname, fname_len, f404); goto cleanup; } diff --git a/ext/phar/stream.c b/ext/phar/stream.c index f49bc5e2deba..9d24fa64d75c 100644 --- a/ext/phar/stream.c +++ b/ext/phar/stream.c @@ -230,7 +230,8 @@ static php_stream * phar_wrapper_open_url(php_stream_wrapper *wrapper, const cha } else { if (!*internal_file && (options & STREAM_OPEN_FOR_INCLUDE)) { /* retrieve the stub */ - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, NULL)) { + phar = phar_get_archive(ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, NULL); + if (!phar) { php_stream_wrapper_log_error(wrapper, options, "file %s is not a valid phar archive", ZSTR_VAL(resource->host)); efree(internal_file); php_url_free(resource); @@ -554,7 +555,6 @@ static int phar_wrapper_stat(php_stream_wrapper *wrapper, const char *url, int f php_stream_statbuf *ssb, php_stream_context *context) /* {{{ */ { char *internal_file; - phar_archive_data *phar; size_t internal_file_len; php_url *resource = phar_parse_url(wrapper, url, "r", flags|PHP_STREAM_URL_STAT_QUIET); @@ -577,7 +577,8 @@ static int phar_wrapper_stat(php_stream_wrapper *wrapper, const char *url, int f internal_file = ZSTR_VAL(resource->path) + 1; /* strip leading "/" */ /* find the phar in our trusty global hash indexed by alias (host of phar://blah.phar/file.whatever) */ - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, NULL)) { + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(resource->host), ZSTR_LEN(resource->host), NULL, 0, NULL); + if (!phar) { php_url_free(resource); return FAILURE; } @@ -725,7 +726,6 @@ static int phar_wrapper_unlink(php_stream_wrapper *wrapper, const char *url, int static int phar_wrapper_rename(php_stream_wrapper *wrapper, const char *url_from, const char *url_to, int options, php_stream_context *context) /* {{{ */ { char *error; - phar_archive_data *phar, *pfrom, *pto; bool is_dir = false; bool is_modified = false; @@ -736,9 +736,8 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, const char *url_from php_error_docref(NULL, E_WARNING, "phar error: cannot rename \"%s\" to \"%s\": invalid or non-writable url \"%s\"", url_from, url_to, url_from); return 0; } - if (SUCCESS != phar_get_archive(&pfrom, ZSTR_VAL(resource_from->host), ZSTR_LEN(resource_from->host), NULL, 0, NULL)) { - pfrom = NULL; - } + + phar_archive_data *pfrom = phar_get_archive(ZSTR_VAL(resource_from->host), ZSTR_LEN(resource_from->host), NULL, 0, NULL); if (PHAR_G(readonly) && (!pfrom || !pfrom->is_data)) { php_url_free(resource_from); php_error_docref(NULL, E_WARNING, "phar error: Write operations disabled by the php.ini setting phar.readonly"); @@ -751,9 +750,8 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, const char *url_from php_error_docref(NULL, E_WARNING, "phar error: cannot rename \"%s\" to \"%s\": invalid or non-writable url \"%s\"", url_from, url_to, url_to); return 0; } - if (SUCCESS != phar_get_archive(&pto, ZSTR_VAL(resource_to->host), ZSTR_LEN(resource_to->host), NULL, 0, NULL)) { - pto = NULL; - } + + phar_archive_data *pto = phar_get_archive(ZSTR_VAL(resource_to->host), ZSTR_LEN(resource_to->host), NULL, 0, NULL); if (PHAR_G(readonly) && (!pto || !pto->is_data)) { php_url_free(resource_from); php_url_free(resource_to); @@ -797,7 +795,8 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, const char *url_from return 0; } - if (SUCCESS != phar_get_archive(&phar, ZSTR_VAL(resource_from->host), ZSTR_LEN(resource_from->host), NULL, 0, &error)) { + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(resource_from->host), ZSTR_LEN(resource_from->host), NULL, 0, &error); + if (!phar) { php_url_free(resource_from); php_url_free(resource_to); php_error_docref(NULL, E_WARNING, "phar error: cannot rename \"%s\" to \"%s\": %s", url_from, url_to, error); diff --git a/ext/phar/util.c b/ext/phar/util.c index 491a07c4dd21..bacd381819d4 100644 --- a/ext/phar/util.c +++ b/ext/phar/util.c @@ -308,7 +308,8 @@ zend_string *phar_find_in_include_path(zend_string *filename, phar_archive_data } if (*ZSTR_VAL(filename) == '.') { - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL)) { + phar = phar_get_archive(ZSTR_VAL(arch), ZSTR_LEN(arch), NULL, 0, NULL); + if (!phar) { zend_string_release_ex(arch, false); return NULL; } @@ -468,7 +469,6 @@ ZEND_ATTRIBUTE_NONNULL static zend_result phar_separate_entry_fp(phar_entry_info */ ZEND_ATTRIBUTE_NONNULL zend_result phar_get_entry_data(phar_entry_data **ret, const zend_string *fname, char *path, size_t path_len, const char *mode, char allow_dir, char **error, bool security) /* {{{ */ { - phar_archive_data *phar; phar_entry_info *entry; bool for_write = mode[0] != 'r' || mode[1] == '+'; bool for_append = mode[0] == 'a'; @@ -478,7 +478,8 @@ ZEND_ATTRIBUTE_NONNULL zend_result phar_get_entry_data(phar_entry_data **ret, co *ret = NULL; *error = NULL; - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 0, error)) { + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 0, error); + if (!phar) { return FAILURE; } @@ -613,7 +614,6 @@ ZEND_ATTRIBUTE_NONNULL zend_result phar_get_entry_data(phar_entry_data **ret, co */ ZEND_ATTRIBUTE_NONNULL phar_entry_data *phar_get_or_create_entry_data(zend_string *fname, char *path, size_t path_len, const char *mode, char allow_dir, char **error, bool security, uint32_t timestamp) /* {{{ */ { - phar_archive_data *phar; phar_entry_info etemp; phar_entry_data *ret; const char *pcr_error; @@ -625,7 +625,8 @@ ZEND_ATTRIBUTE_NONNULL phar_entry_data *phar_get_or_create_entry_data(zend_strin is_dir = (path_len && path[path_len - 1] == '/') ? 1 : 0; - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 0, error)) { + phar_archive_data *phar = phar_get_archive(ZSTR_VAL(fname), ZSTR_LEN(fname), NULL, 0, error); + if (!phar) { return NULL; } @@ -960,9 +961,9 @@ zend_result phar_free_alias(const phar_archive_data *phar) /* {{{ */ * Looks up a phar archive in the filename map, connecting it to the alias * (if any) or returns null */ -zend_result phar_get_archive(phar_archive_data **archive, const char *fname, size_t fname_len, const char *alias, size_t alias_len, char **error) /* {{{ */ +phar_archive_data* phar_get_archive(const char *fname, size_t fname_len, const char *alias, size_t alias_len, char **error) /* {{{ */ { - phar_archive_data *fd_ptr; + phar_archive_data *archive; phar_request_initialize(); @@ -970,142 +971,132 @@ zend_result phar_get_archive(phar_archive_data **archive, const char *fname, siz *error = NULL; } - *archive = NULL; - if (PHAR_G(last_phar) && zend_string_equals_cstr(PHAR_G(last_phar_name), fname, fname_len)) { - *archive = PHAR_G(last_phar); + archive = PHAR_G(last_phar); if (alias && alias_len) { if (!PHAR_G(last_phar)->is_temporary_alias && (alias_len != PHAR_G(last_phar)->alias_len || memcmp(PHAR_G(last_phar)->alias, alias, alias_len))) { if (error) { spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(PHAR_G(last_phar)->fname), fname); } - *archive = NULL; - return FAILURE; + return NULL; } if (PHAR_G(last_phar)->alias_len && zend_hash_str_exists(&(PHAR_G(phar_alias_map)), PHAR_G(last_phar)->alias, PHAR_G(last_phar)->alias_len)) { zend_hash_str_del(&(PHAR_G(phar_alias_map)), PHAR_G(last_phar)->alias, PHAR_G(last_phar)->alias_len); } - zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, *archive); + zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, archive); PHAR_G(last_alias) = alias; PHAR_G(last_alias_len) = alias_len; } - return SUCCESS; + return archive; } if (alias && alias_len) { /* If the alias stored in the last_phar cache matches, just use it directly */ if (PHAR_G(last_phar) && alias_len == PHAR_G(last_alias_len) && !memcmp(alias, PHAR_G(last_alias), alias_len)) { - fd_ptr = PHAR_G(last_phar); + archive = PHAR_G(last_phar); } else { - fd_ptr = zend_hash_str_find_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len); + archive = zend_hash_str_find_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len); } /* If we didn't find the alias, check in the cached manifest to see if we can find it */ - if (!fd_ptr && PHAR_G(manifest_cached)) { - fd_ptr = zend_hash_str_find_ptr(&cached_alias, alias, alias_len); + if (!archive && PHAR_G(manifest_cached)) { + archive = zend_hash_str_find_ptr(&cached_alias, alias, alias_len); } - if (fd_ptr) { - if (!zend_string_equals_cstr(fd_ptr->fname, fname, fname_len)) { + if (archive) { + if (!zend_string_equals_cstr(archive->fname, fname, fname_len)) { if (error) { - spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(fd_ptr->fname), fname); + spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(archive->fname), fname); } - if (SUCCESS == phar_free_alias(fd_ptr)) { + if (SUCCESS == phar_free_alias(archive)) { if (error) { efree(*error); *error = NULL; } } - return FAILURE; + return NULL; } - *archive = fd_ptr; - PHAR_G(last_phar) = fd_ptr; - PHAR_G(last_phar_name) = fd_ptr->fname; + PHAR_G(last_phar) = archive; + PHAR_G(last_phar_name) = archive->fname; PHAR_G(last_alias) = alias; PHAR_G(last_alias_len) = alias_len; - return SUCCESS; + return archive; } } if (fname && fname_len) { - fd_ptr = zend_hash_str_find_ptr(&(PHAR_G(phar_fname_map)), fname, fname_len); - if (fd_ptr) { - *archive = fd_ptr; - + archive = zend_hash_str_find_ptr(&(PHAR_G(phar_fname_map)), fname, fname_len); + if (archive) { if (alias && alias_len) { - if (!fd_ptr->is_temporary_alias && (alias_len != fd_ptr->alias_len || memcmp(fd_ptr->alias, alias, alias_len))) { + if (!archive->is_temporary_alias && (alias_len != archive->alias_len || memcmp(archive->alias, alias, alias_len))) { if (error) { - spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(fd_ptr->fname), fname); + spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(archive->fname), fname); } - return FAILURE; + return NULL; } - if (fd_ptr->alias_len && zend_hash_str_exists(&(PHAR_G(phar_alias_map)), fd_ptr->alias, fd_ptr->alias_len)) { - zend_hash_str_del(&(PHAR_G(phar_alias_map)), fd_ptr->alias, fd_ptr->alias_len); + if (archive->alias_len && zend_hash_str_exists(&(PHAR_G(phar_alias_map)), archive->alias, archive->alias_len)) { + zend_hash_str_del(&(PHAR_G(phar_alias_map)), archive->alias, archive->alias_len); } - zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, fd_ptr); + zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, archive); } - PHAR_G(last_phar) = fd_ptr; - PHAR_G(last_phar_name) = fd_ptr->fname; - PHAR_G(last_alias) = fd_ptr->alias; - PHAR_G(last_alias_len) = fd_ptr->alias_len; + PHAR_G(last_phar) = archive; + PHAR_G(last_phar_name) = archive->fname; + PHAR_G(last_alias) = archive->alias; + PHAR_G(last_alias_len) = archive->alias_len; - return SUCCESS; + return archive; } - if (PHAR_G(manifest_cached) && NULL != (fd_ptr = zend_hash_str_find_ptr(&cached_phars, fname, fname_len))) { - *archive = fd_ptr; - + if (PHAR_G(manifest_cached) && NULL != (archive = zend_hash_str_find_ptr(&cached_phars, fname, fname_len))) { /* this could be problematic - alias should never be different from manifest alias for cached phars */ - if (!fd_ptr->is_temporary_alias && alias && alias_len) { - if (alias_len != fd_ptr->alias_len || memcmp(fd_ptr->alias, alias, alias_len)) { + if (!archive->is_temporary_alias && alias && alias_len) { + if (alias_len != archive->alias_len || memcmp(archive->alias, alias, alias_len)) { if (error) { - spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(fd_ptr->fname), fname); + spprintf(error, 0, "alias \"%s\" is already used for archive \"%s\" cannot be overloaded with \"%s\"", alias, ZSTR_VAL(archive->fname), fname); } - return FAILURE; + return NULL; } } - PHAR_G(last_phar) = fd_ptr; - PHAR_G(last_phar_name) = fd_ptr->fname; - PHAR_G(last_alias) = fd_ptr->alias; - PHAR_G(last_alias_len) = fd_ptr->alias_len; + PHAR_G(last_phar) = archive; + PHAR_G(last_phar_name) = archive->fname; + PHAR_G(last_alias) = archive->alias; + PHAR_G(last_alias_len) = archive->alias_len; - return SUCCESS; + return archive; } - fd_ptr = zend_hash_str_find_ptr(&(PHAR_G(phar_alias_map)), fname, fname_len); + archive = zend_hash_str_find_ptr(&(PHAR_G(phar_alias_map)), fname, fname_len); /* If we didn't find the fname in the alias map, check in the cached manifest to see if we can find it */ - if (!fd_ptr && PHAR_G(manifest_cached)) { - fd_ptr = zend_hash_str_find_ptr(&cached_alias, fname, fname_len); + if (!archive && PHAR_G(manifest_cached)) { + archive = zend_hash_str_find_ptr(&cached_alias, fname, fname_len); } - if (fd_ptr) { - *archive = fd_ptr; + if (archive) { + PHAR_G(last_phar) = archive; + PHAR_G(last_phar_name) = archive->fname; + PHAR_G(last_alias) = archive->alias; + PHAR_G(last_alias_len) = archive->alias_len; - PHAR_G(last_phar) = fd_ptr; - PHAR_G(last_phar_name) = fd_ptr->fname; - PHAR_G(last_alias) = fd_ptr->alias; - PHAR_G(last_alias_len) = fd_ptr->alias_len; - - return SUCCESS; + return archive; } /* not found, try converting \ to / */ char *my_realpath = expand_filepath(fname, NULL); if (UNEXPECTED(!my_realpath)) { - return FAILURE; + return NULL; } size_t my_realpath_len = strlen(my_realpath); @@ -1113,31 +1104,29 @@ zend_result phar_get_archive(phar_archive_data **archive, const char *fname, siz phar_unixify_path_separators(my_realpath, my_realpath_len); #endif - fd_ptr = zend_hash_str_find_ptr(&(PHAR_G(phar_fname_map)), my_realpath, my_realpath_len); + archive = zend_hash_str_find_ptr(&(PHAR_G(phar_fname_map)), my_realpath, my_realpath_len); /* If we didn't find the path in the fname map, check in the cached manifest to see if we can find it */ - if (!fd_ptr && PHAR_G(manifest_cached)) { - fd_ptr = zend_hash_str_find_ptr(&cached_phars, my_realpath, my_realpath_len); + if (!archive && PHAR_G(manifest_cached)) { + archive = zend_hash_str_find_ptr(&cached_phars, my_realpath, my_realpath_len); } efree(my_realpath); - if (fd_ptr) { - *archive = fd_ptr; - + if (archive) { if (alias && alias_len) { - zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, fd_ptr); + zend_hash_str_add_ptr(&(PHAR_G(phar_alias_map)), alias, alias_len, archive); } - PHAR_G(last_phar) = fd_ptr; - PHAR_G(last_phar_name) = fd_ptr->fname; - PHAR_G(last_alias) = fd_ptr->alias; - PHAR_G(last_alias_len) = fd_ptr->alias_len; + PHAR_G(last_phar) = archive; + PHAR_G(last_phar_name) = archive->fname; + PHAR_G(last_alias) = archive->alias; + PHAR_G(last_alias_len) = archive->alias_len; - return SUCCESS; + return archive; } } - return FAILURE; + return NULL; } /* }}} */ diff --git a/ext/phar/zip.c b/ext/phar/zip.c index 28e1a3d5641e..f0b1ddc0171c 100644 --- a/ext/phar/zip.c +++ b/ext/phar/zip.c @@ -1273,7 +1273,8 @@ ZEND_ATTRIBUTE_NONNULL_ARGS(1, 4) int phar_zip_flush(phar_archive_data *phar, ze /* register alias */ if (phar->alias_len) { - if (FAILURE == phar_get_archive(&phar, ZSTR_VAL(phar->fname), ZSTR_LEN(phar->fname), phar->alias, phar->alias_len, error)) { + phar = phar_get_archive(ZSTR_VAL(phar->fname), ZSTR_LEN(phar->fname), phar->alias, phar->alias_len, error); + if (!phar) { return EOF; } }