Support PHP 8

This commit is contained in:
Gustavo Lopes
2020-12-06 17:59:51 +00:00
parent 7cff10aa2c
commit d95cab037b
28 changed files with 378 additions and 173 deletions

3
.gitignore vendored
View File

@@ -44,3 +44,6 @@
*.autosave
/unrar/.libs
/tmp-php.ini
/php-rar.creator.user
/compile_commands.json
/.clangd

View File

@@ -2,16 +2,10 @@ jobs:
- template: azure-template.yml
parameters:
name: php_5_3_valgrind
displayName: PHP 5.3 (valgrind, clang)
displayName: PHP 5.3 ZTS (valgrind, clang)
phpVersion: '5.3'
clang: true
valgrind: true
- template: azure-template.yml
parameters:
name: php_5_3_zts
displayName: PHP 5.3 ZTS
phpVersion: '5.3'
zts: true
- template: azure-template.yml
@@ -73,3 +67,18 @@ jobs:
clang: true
valgrind: true
zts: true
- template: azure-template.yml
parameters:
name: php_8_0
displayName: PHP 8.0 ZTS
phpVersion: '8.0'
zts: true
- template: azure-template.yml
parameters:
name: php_8_0_valgrind
displayName: PHP 8.0 (valgrind, clang)
phpVersion: '8.0'
clang: true
valgrind: true

View File

@@ -15,10 +15,6 @@ jobs:
vmImage: ${{ parameters.imageName }}
variables:
TESTOPTS: -v
gem: /opt/ruby/${{ parameters.rubyVersion }}/bin/gem
bundle: /opt/ruby/${{ parameters.rubyVersion }}/bin/bundle
GEM_HOME: /opt/ruby/${{ parameters.rubyVersion }}/lib/ruby/gems/${{ parameters.rubyVersion }}.0
${{ if eq(parameters.clang, true) }}:
CC: clang
CXX: clang++

View File

@@ -1,4 +1,6 @@
config.h
php_compat.h
php_compat.h
php_rar.h
rar.c
rar_error.c

72
php_compat.h Normal file
View File

@@ -0,0 +1,72 @@
#include <php.h>
#if PHP_MAJOR_VERSION >= 8
# define TSRMLS_DC
# define TSRMLS_D
# define TSRMLS_CC
# define TSRMLS_C
# define TSRMLS_FETCH()
# define IS_CALLABLE_STRICT 0
# define zend_qsort zend_sort
# define ZV_TO_THIS_FOR_HANDLER(zv) (Z_OBJ_P(zv))
typedef zend_object handler_this_t;
#else
# define ZV_TO_THIS_FOR_HANDLER(zv) (zv)
typedef zval handler_this_t;
#endif
#if PHP_MAJOR_VERSION >= 7
typedef zend_object* rar_obj_ref;
#define rar_zval_add_ref(ppzv) zval_add_ref(*ppzv)
#define ZVAL_ALLOC_DUP(dst, src) \
do { \
dst = (zval*) emalloc(sizeof(zval)); \
ZVAL_DUP(dst, src); \
} while (0)
#define RAR_RETURN_STRINGL(s, l, duplicate) \
do { \
RETVAL_STRINGL(s, l); \
if (duplicate == 0) { \
efree(s); \
} \
return; \
} while (0)
#define RAR_ZVAL_STRING(z, s, duplicate) \
do { \
ZVAL_STRING(z, s); \
if (duplicate == 0) { \
efree(s); \
} \
} while (0)
typedef size_t zpp_s_size_t;
#define MAKE_STD_ZVAL(zv_p) \
do { \
(zv_p) = emalloc(sizeof(zval)); \
ZVAL_NULL(zv_p); \
} while (0)
#define INIT_ZVAL(zv) ZVAL_UNDEF(&zv)
#define ZEND_ACC_FINAL_CLASS ZEND_ACC_FINAL
#else /* PHP 5.x */
typedef zend_object_handle rar_obj_ref;
#define rar_zval_add_ref zval_add_ref
#define ZVAL_ALLOC_DUP(dst, src) \
do { \
zval *z_src = src; \
dst = z_src; \
zval_add_ref(&dst); \
SEPARATE_ZVAL(&dst); \
} while (0)
#define RAR_ZVAL_STRING ZVAL_STRING
#define RAR_RETURN_STRINGL(s, l, duplicate) RETURN_STRINGL(s, l, duplicate)
typedef int zpp_s_size_t;
#define zend_hash_str_del zend_hash_del
#endif

View File

@@ -63,6 +63,8 @@ extern zend_module_entry rar_module_entry;
#include "TSRM.h"
#endif
#include "php_compat.h"
/* causes linking errors (multiple definitions) in functions
that were requested inlining but were not inlined by the compiler */
/* #include "unrar/rar.hpp */
@@ -87,63 +89,6 @@ enum FILE_SYSTEM_REDIRECT {
/* maximum comment size if 64KB */
#define RAR_MAX_COMMENT_SIZE 65536
/* PHP 7+ abstraction */
#if PHP_MAJOR_VERSION >= 7
typedef zend_object* rar_obj_ref;
#define rar_zval_add_ref(ppzv) zval_add_ref(*ppzv)
#define ZVAL_ALLOC_DUP(dst, src) \
do { \
dst = (zval*) emalloc(sizeof(zval)); \
ZVAL_DUP(dst, src); \
} while (0)
#define RAR_RETURN_STRINGL(s, l, duplicate) \
do { \
RETVAL_STRINGL(s, l); \
if (duplicate == 0) { \
efree(s); \
} \
return; \
} while (0)
#define RAR_ZVAL_STRING(z, s, duplicate) \
do { \
ZVAL_STRING(z, s); \
if (duplicate == 0) { \
efree(s); \
} \
} while (0)
typedef size_t zpp_s_size_t;
#define MAKE_STD_ZVAL(zv_p) \
do { \
(zv_p) = emalloc(sizeof(zval)); \
ZVAL_NULL(zv_p); \
} while (0)
#define INIT_ZVAL(zv) ZVAL_UNDEF(&zv)
#define ZEND_ACC_FINAL_CLASS ZEND_ACC_FINAL
#else /* PHP 5.x */
typedef zend_object_handle rar_obj_ref;
#define rar_zval_add_ref zval_add_ref
#define ZVAL_ALLOC_DUP(dst, src) \
do { \
zval *z_src = src; \
dst = z_src; \
zval_add_ref(&dst); \
SEPARATE_ZVAL(&dst); \
} while (0)
#define RAR_ZVAL_STRING ZVAL_STRING
#define RAR_RETURN_STRINGL(s, l, duplicate) RETURN_STRINGL(s, l, duplicate)
typedef int zpp_s_size_t;
#define zend_hash_str_del zend_hash_del
#endif
typedef struct _rar_cb_user_data {
char *password; /* can be NULL */
zval *callable; /* can be NULL */
@@ -333,8 +278,9 @@ void _rar_close_file_resource(rar_file_t *rar);
/* Fetches the rar_file_t part of the RarArchive object in order to use the
* operations above and (discouraged) to have direct access to the fields
* RarEntry::extract/getStream access extract_open_dat and cb_userdata */
int _rar_get_file_resource(zval *zval_file, rar_file_t **rar_file TSRMLS_DC);
int _rar_get_file_resource_ex(zval *zval_file, rar_file_t **rar_file, int silent TSRMLS_DC);
int _rar_get_file_resource_zv(zval *zv_file, rar_file_t **rar_file TSRMLS_DC);
int _rar_get_file_resource_zv_ex(zval *zv_file, rar_file_t **rar_file, int silent TSRMLS_DC);
int _rar_get_file_resource_ex(rar_obj_ref objref_file, rar_file_t **rar_file, int silent TSRMLS_DC);
void minit_rararch(TSRMLS_D);
PHP_FUNCTION(rar_open);

View File

@@ -1072,7 +1072,7 @@ static int _rar_get_cachable_rararch(php_stream_wrapper *wrapper,
int res;
const char *err_str;
if (_rar_get_file_resource_ex(rar_obj, rar, 1 TSRMLS_CC)
if (_rar_get_file_resource_zv_ex(rar_obj, rar, 1 TSRMLS_CC)
== FAILURE) {
php_stream_wrapper_log_error(wrapper, options TSRMLS_CC,
"Bug: could not retrieve RarArchive object from zval");
@@ -1096,7 +1096,7 @@ static int _rar_get_cachable_rararch(php_stream_wrapper *wrapper,
else { /* cache hit */
/* cache get already put the value in rar_obj and incremented the
* refcount of the object */
if (_rar_get_file_resource_ex(rar_obj, rar, 1 TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv_ex(rar_obj, rar, 1 TSRMLS_CC) == FAILURE) {
php_stream_wrapper_log_error(wrapper, options TSRMLS_CC,
"Bug: could not retrieve RarArchive object from zval");
goto cleanup;

156
rararch.c
View File

@@ -27,17 +27,21 @@
/* $Id$ */
#include "zend_types.h"
#ifdef __cplusplus
extern "C" {
#endif
#define _GNU_SOURCE
#ifndef _GNU_SOURCE
# define _GNU_SOURCE
#endif
#include <string.h>
#include <wchar.h>
#include <php.h>
#include <zend_interfaces.h>
#include "php_rar.h"
#include "php_compat.h"
/* {{{ Type definitions reserved for this translation unit */
typedef struct _ze_rararch_object {
@@ -87,35 +91,53 @@ static inline void rar_obj_ref_make_zv(rar_obj_ref zo, zval *zv TSRMLS_DC);
static inline ze_rararch_object *rararch_object_fetch(zend_object *zobj);
static ze_rararch_object *rararch_object_from_zv(const zval *zv);
static ze_rararch_object *rararch_object_from_ref(const rar_obj_ref ref);
static zend_object *rararch_ce_create_object(zend_class_entry *ce);
static void rararch_ce_free_object_storage(zend_object *zobj);
#else
#define rararch_object_from_zv zend_object_store_get_object
#define rararch_object_from_ref(ref) zend_object_store_get_object_by_handle((ref) TSRMLS_CC)
static zend_object_value rararch_ce_create_object(zend_class_entry *class_type TSRMLS_DC);
static void rararch_ce_free_object_storage(ze_rararch_object *object TSRMLS_DC);
#endif
/* }}} */
/* {{{ RarArchive handlers */
static int rararch_handlers_preamble(zval *object, rar_file_t **rar TSRMLS_DC);
static int rararch_handlers_preamble(handler_this_t *object, rar_file_t **rar TSRMLS_DC);
static int rararch_dimensions_preamble(rar_file_t *rar, zval *offset, long *index, int quiet TSRMLS_DC);
static int rararch_count_elements(zval *object, long *count TSRMLS_DC);
static int rararch_count_elements(handler_this_t *object, long *count TSRMLS_DC);
#if PHP_MAJOR_VERSION < 7
static zval *rararch_read_dimension(zval *object, zval *offset, int type TSRMLS_DC);
#else
static zval *rararch_read_dimension(zval *object, zval *offset, int type, zval *rv);
static zval *rararch_read_dimension(handler_this_t *object, zval *offset, int type, zval *rv);
#endif
static void rararch_write_dimension(zval *object, zval *offset, zval *value TSRMLS_DC);
static int rararch_has_dimension(zval *object, zval *offset, int check_empty TSRMLS_DC);
static void rararch_write_dimension(handler_this_t *object, zval *offset, zval *value TSRMLS_DC);
static int rararch_has_dimension(handler_this_t *object, zval *offset, int check_empty TSRMLS_DC);
/* }}} */
/* {{{ Function definitions with external linkage */
int _rar_get_file_resource(zval *zval_file, rar_file_t **rar_file TSRMLS_DC) /* {{{ */
int _rar_get_file_resource_zv(zval *zv, rar_file_t **rar_file TSRMLS_DC) /* {{{ */
{
return _rar_get_file_resource_ex(zval_file, rar_file, FALSE TSRMLS_CC);
return _rar_get_file_resource_ex(rar_obj_ref_fetch(zv),
rar_file, FALSE TSRMLS_CC);
}
int _rar_get_file_resource_zv_ex(zval *zv, rar_file_t **rar_file, int allow_closed TSRMLS_DC)
{
return _rar_get_file_resource_ex(rar_obj_ref_fetch(zv),
rar_file, allow_closed TSRMLS_CC);
}
/* }}} */
static int _rar_get_file_resource_handler(handler_this_t *thiz,
rar_file_t **rar_file TSRMLS_DC)
{
#if PHP_MAJOR_VERSION < 8
return _rar_get_file_resource_zv(thiz, rar_file TSRMLS_CC);
#else
return _rar_get_file_resource_ex(thiz, rar_file, FALSE);
#endif
}
/* Creates a RarArchive object, all three in args will be dupped */
int _rar_create_rararch_obj(const char* resolved_path,
const char* open_password,
@@ -181,20 +203,21 @@ void _rar_close_file_resource(rar_file_t *rar) /* {{{ */
/* When changed from resource to custom object, instead of fiddling
* with the refcount to force object destruction, an indication that
* the file is already closed is given by setting rar->arch_handle
* to NULL. This is checked by _rar_get_file_resource. */
* to NULL. This is checked by _rar_get_file_resource_zv. */
RARCloseArchive(rar->arch_handle);
rar->arch_handle = NULL;
}
/* }}} */
/* Receives archive zval, returns object struct.
* If silent is FALSE, it checks whether the archive is alredy closed, and if it
* If allow_closed is FALSE, it checks whether the archive is alredy closed, and if it
* is, an exception/error is raised and FAILURE is returned
*/
int _rar_get_file_resource_ex(zval *zval_file, rar_file_t **rar_file, int silent TSRMLS_DC) /* {{{ */
int _rar_get_file_resource_ex(rar_obj_ref zobjref_file, rar_file_t **rar_file,
int allow_closed TSRMLS_DC) /* {{{ */
{
ze_rararch_object *zobj;
zobj = rararch_object_from_zv(zval_file TSRMLS_CC);
zobj = rararch_object_from_ref(zobjref_file);
if (zobj == NULL) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,
"Could not find object in the store. This is a bug, please report it.");
@@ -202,7 +225,7 @@ int _rar_get_file_resource_ex(zval *zval_file, rar_file_t **rar_file, int silent
}
*rar_file = zobj->rar_file;
if ((*rar_file)->arch_handle == NULL && !silent) { /* rar_close was called */
if ((*rar_file)->arch_handle == NULL && !allow_closed) { /* rar_close was called */
_rar_handle_ext_error("The archive is already closed" TSRMLS_CC);
return FAILURE;
}
@@ -289,6 +312,10 @@ static ze_rararch_object *rararch_object_from_zv(const zval *zv)
{
return rararch_object_fetch(Z_OBJ_P(zv));
}
static ze_rararch_object *rararch_object_from_ref(const rar_obj_ref ref)
{
return rararch_object_fetch(ref);
}
#endif
/* {{{ */
@@ -373,11 +400,12 @@ static void rararch_ce_free_object_storage(zend_object *zobj)
/* }}} */
/* {{{ RarArchive handlers */
static int rararch_handlers_preamble(zval *object, rar_file_t **rar TSRMLS_DC) /* {{{ */
static int rararch_handlers_preamble(handler_this_t *object,
rar_file_t **rar TSRMLS_DC) /* {{{ */
{
/* don't call zend_objects_get_address or zend_object_store_get directly;
* _rar_get_file_resource checks if the archive was closed */
if (_rar_get_file_resource(object, rar TSRMLS_CC) == FAILURE) {
* _rar_get_file_resource_zv checks if the archive was closed */
if (_rar_get_file_resource_handler(object, rar TSRMLS_CC) == FAILURE) {
return FAILURE;
}
@@ -415,7 +443,7 @@ static int rararch_dimensions_preamble(rar_file_t *rar,
return FAILURE;
}
else if (type == IS_DOUBLE) {
if (d > LONG_MAX || d < LONG_MIN) {
if (d > (double) LONG_MAX || d < (double) LONG_MIN) {
RAR_DOCREF_IF_UNQUIET(NULL TSRMLS_CC, E_WARNING,
"Dimension index is out of integer bounds");
return FAILURE;
@@ -425,7 +453,8 @@ static int rararch_dimensions_preamble(rar_file_t *rar,
}
}
else if (Z_TYPE_P(offset) == IS_DOUBLE) {
if (Z_DVAL_P(offset) > LONG_MAX || Z_DVAL_P(offset) < LONG_MIN) {
if (Z_DVAL_P(offset) > (double) LONG_MAX ||
Z_DVAL_P(offset) < (double) LONG_MIN) {
RAR_DOCREF_IF_UNQUIET(NULL TSRMLS_CC, E_WARNING,
"Dimension index is out of integer bounds");
return FAILURE;
@@ -433,16 +462,17 @@ static int rararch_dimensions_preamble(rar_file_t *rar,
*index = (long) Z_DVAL_P(offset);
}
else if (Z_TYPE_P(offset) == IS_OBJECT) {
#if PHP_MAJOR_VERSION < 8
if (Z_OBJ_HT_P(offset)->get) {
zval *newoffset = NULL;
int ret;
#if PHP_MAJOR_VERSION < 7
# if PHP_MAJOR_VERSION < 7
newoffset = Z_OBJ_HT_P(offset)->get(offset TSRMLS_CC);
#else
# else
zval zv_holder;
ZVAL_NULL(&zv_holder);
newoffset = Z_OBJ_HT_P(offset)->get(offset, &zv_holder);
#endif
# endif
/* get handler cannot return NULL */
assert(newoffset != NULL);
@@ -455,12 +485,32 @@ static int rararch_dimensions_preamble(rar_file_t *rar,
ret = rararch_dimensions_preamble(rar, newoffset, index, quiet
TSRMLS_CC);
#if PHP_MAJOR_VERSION < 7
# if PHP_MAJOR_VERSION < 7
zval_ptr_dtor(&newoffset);
#else
# else
zval_ptr_dtor(newoffset);
#endif
# endif
return ret;
} else
#endif // PHP < 8
if (Z_OBJ_HT_P(offset)->cast_object) {
zval newoffset;
int res = Z_OBJ_HT_P(offset)->cast_object(
ZV_TO_THIS_FOR_HANDLER(offset), &newoffset, IS_LONG TSRMLS_CC);
if (res == FAILURE) {
RAR_DOCREF_IF_UNQUIET(NULL TSRMLS_CC, E_WARNING,
"Could not convert object given as dimension index into "
"an integer (cast_object failed)");
return FAILURE;
}
if (Z_TYPE(newoffset) != IS_LONG) {
zval_dtor(&newoffset);
RAR_DOCREF_IF_UNQUIET(NULL TSRMLS_CC, E_WARNING,
"Could not convert object given as dimension index into "
"an integer (cast_object did not return int as asked)");
return FAILURE;
}
*index = Z_LVAL(newoffset);
}
else {
RAR_DOCREF_IF_UNQUIET(NULL TSRMLS_CC, E_WARNING,
@@ -493,7 +543,7 @@ static int rararch_dimensions_preamble(rar_file_t *rar,
/* }}} */
/* {{{ RarArchive count_elements handler */
static int rararch_count_elements(zval *object, long *count TSRMLS_DC)
static int rararch_count_elements(handler_this_t *object, long *count TSRMLS_DC)
{
rar_file_t *rar = NULL;
size_t entry_count;
@@ -517,7 +567,7 @@ static int rararch_count_elements(zval *object, long *count TSRMLS_DC)
#if PHP_MAJOR_VERSION < 7
static zval *rararch_read_dimension(zval *object, zval *offset, int type TSRMLS_DC)
#else
static zval *rararch_read_dimension(zval *object, zval *offset, int type, zval *rv)
static zval *rararch_read_dimension(handler_this_t *object, zval *offset, int type, zval *rv)
#endif
{
long index;
@@ -546,8 +596,16 @@ static zval *rararch_read_dimension(zval *object, zval *offset, int type, zval *
#else
ret = rv;
#endif
#if PHP_MAJOR_VERSION >= 8
zval object_zv;
ZVAL_OBJ(&object_zv, object);
_rar_entry_to_zval(&object_zv, out->header, out->packed_size, out->position,
ret TSRMLS_CC);
#else
_rar_entry_to_zval(object, out->header, out->packed_size, out->position,
ret TSRMLS_CC);
#endif
_rar_entry_search_end(out);
#if PHP_MAJOR_VERSION < 7
Z_DELREF_P(ret); /* set refcount to 0 */
@@ -557,7 +615,7 @@ static zval *rararch_read_dimension(zval *object, zval *offset, int type, zval *
/* }}} */
/* {{{ RarArchive write_dimension handler */
static void rararch_write_dimension(zval *object, zval *offset, zval *value TSRMLS_DC)
static void rararch_write_dimension(handler_this_t *object, zval *offset, zval *value TSRMLS_DC)
{
php_error_docref(NULL TSRMLS_CC, E_ERROR,
"A RarArchive object is not writable");
@@ -565,7 +623,7 @@ static void rararch_write_dimension(zval *object, zval *offset, zval *value TSRM
/* }}} */
/* {{{ RarArchive has_dimension handler */
static int rararch_has_dimension(zval *object, zval *offset, int check_empty TSRMLS_DC)
static int rararch_has_dimension(handler_this_t *object, zval *offset, int check_empty TSRMLS_DC)
{
long index;
rar_file_t *rar = NULL;
@@ -582,7 +640,7 @@ static int rararch_has_dimension(zval *object, zval *offset, int check_empty TSR
/* }}} */
/* {{{ RarArchive unset_dimension handler */
static void rararch_unset_dimension(zval *object, zval *offset TSRMLS_DC)
static void rararch_unset_dimension(handler_this_t *object, zval *offset TSRMLS_DC)
{
php_error_docref(NULL TSRMLS_CC, E_ERROR,
"A RarArchive object is not writable");
@@ -661,7 +719,7 @@ PHP_FUNCTION(rar_list)
RAR_THIS_OR_NO_ARGS(file);
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -696,7 +754,7 @@ PHP_FUNCTION(rar_entry_get)
return;
}
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -733,7 +791,7 @@ PHP_FUNCTION(rar_solid_is)
RAR_THIS_OR_NO_ARGS(file);
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -751,7 +809,7 @@ PHP_FUNCTION(rar_comment_get)
RAR_THIS_OR_NO_ARGS(file);
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -782,7 +840,7 @@ PHP_FUNCTION(rar_broken_is)
RAR_THIS_OR_NO_ARGS(file);
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -813,7 +871,7 @@ PHP_FUNCTION(rar_allow_broken_set)
return;
}
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -831,7 +889,7 @@ PHP_FUNCTION(rar_close)
RAR_THIS_OR_NO_ARGS(file);
if (_rar_get_file_resource(file, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(file, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -855,7 +913,8 @@ PHP_METHOD(rararch, __toString)
RAR_RETNULL_ON_ARGS();
if (_rar_get_file_resource_ex(arch_obj, &rar, TRUE TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv_ex(arch_obj, &rar, TRUE TSRMLS_CC)
== FAILURE) {
RETURN_FALSE; /* should never happen */
}
@@ -876,6 +935,18 @@ PHP_METHOD(rararch, __toString)
}
/* }}} */
/* {{{ proto string RarEntry::getIterator() */
#if PHP_MAJOR_VERSION >= 8
PHP_METHOD(rararch, getIterator)
{
if (zend_parse_parameters_none() == FAILURE) {
return;
}
zend_create_internal_iterator_zval(return_value, getThis());
}
#endif
/* }}} */
/* {{{ arginfo */
ZEND_BEGIN_ARG_INFO_EX(arginfo_rararchive_open, 0, 0, 1)
ZEND_ARG_INFO(0, filename)
@@ -909,6 +980,9 @@ static zend_function_entry php_rararch_class_functions[] = {
PHP_ME_MAPPING(close, rar_close, arginfo_rararchive_void, ZEND_ACC_PUBLIC)
PHP_ME(rararch, __toString, arginfo_rararchive_void, ZEND_ACC_PUBLIC)
PHP_ME_MAPPING(__construct, rar_bogus_ctor, arginfo_rararchive_void, ZEND_ACC_PRIVATE | ZEND_ACC_CTOR)
#if PHP_MAJOR_VERSION >= 8
PHP_ME(rararch, getIterator, arginfo_rararchive_void, ZEND_ACC_PUBLIC)
#endif
{NULL, NULL, NULL}
};
@@ -997,7 +1071,7 @@ static void rararch_it_fetch(rararch_iterator *it TSRMLS_DC)
robj = &it->parent.data;
#endif
res = _rar_get_file_resource_ex(robj, &rar_file, 1 TSRMLS_CC);
res = _rar_get_file_resource_zv_ex(robj, &rar_file, 1 TSRMLS_CC);
if (res == FAILURE)
php_error_docref(NULL TSRMLS_CC, E_ERROR,
"Cannot fetch RarArchive object");
@@ -1106,7 +1180,7 @@ static zend_object_iterator *rararch_it_get_iterator(zend_class_entry *ce,
"An iterator cannot be used with foreach by reference");
}
res = _rar_get_file_resource_ex(object, &rar, 1 TSRMLS_CC);
res = _rar_get_file_resource_zv_ex(object, &rar, 1 TSRMLS_CC);
if (res == FAILURE) {
php_error_docref(NULL TSRMLS_CC, E_ERROR,
"Cannot fetch RarArchive object");
@@ -1174,7 +1248,11 @@ void minit_rararch(TSRMLS_D)
#if PHP_VERSION_ID < 70300
rararch_ce_ptr->iterator_funcs.funcs = &rararch_it_funcs;
#endif
#if PHP_MAJOR_VERSION >= 8
zend_class_implements(rararch_ce_ptr TSRMLS_CC, 1, zend_ce_aggregate);
#else
zend_class_implements(rararch_ce_ptr TSRMLS_CC, 1, zend_ce_traversable);
#endif
}
#ifdef __cplusplus

View File

@@ -58,7 +58,8 @@ void _rar_entry_to_zval(zval *parent,
struct RARHeaderDataEx *entry,
unsigned long packed_size,
size_t position,
zval *object TSRMLS_DC) /* {{{ */
zval *object TSRMLS_DC)
/* {{{ */
{
char tmp_s [MAX_LENGTH_OF_LONG + 1];
char time[50];
@@ -76,7 +77,13 @@ void _rar_entry_to_zval(zval *parent,
#endif
object_init_ex(object, rar_class_entry_ptr);
zend_update_property(rar_class_entry_ptr, object, "rarfile",
#if PHP_MAJOR_VERSION >= 8
zend_object *obj = Z_OBJ_P(object);
#else
zval *obj = object;
#endif
zend_update_property(rar_class_entry_ptr, obj, "rarfile",
sizeof("rararch") - 1, parent_copy TSRMLS_CC);
#if ULONG_MAX > 0xffffffffUL
@@ -102,42 +109,42 @@ void _rar_entry_to_zval(zval *parent,
* properties from here with add_property_x, or
* direct call to rarentry_object_handlers.write_property
* zend_update_property_x updates the scope accordingly */
zend_update_property_long(rar_class_entry_ptr, object, "position",
zend_update_property_long(rar_class_entry_ptr, obj, "position",
sizeof("position") - 1, (long) position TSRMLS_CC);
zend_update_property_stringl(rar_class_entry_ptr, object, "name",
zend_update_property_stringl(rar_class_entry_ptr, obj, "name",
sizeof("name") - 1, filename, filename_len TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "unpacked_size",
zend_update_property_long(rar_class_entry_ptr, obj, "unpacked_size",
sizeof("unpacked_size") - 1, unp_size TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "packed_size",
zend_update_property_long(rar_class_entry_ptr, obj, "packed_size",
sizeof("packed_size") - 1, packed_size TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "host_os",
zend_update_property_long(rar_class_entry_ptr, obj, "host_os",
sizeof("host_os") - 1, entry->HostOS TSRMLS_CC);
_rar_dos_date_to_text(entry->FileTime, time);
zend_update_property_string(rar_class_entry_ptr, object, "file_time",
zend_update_property_string(rar_class_entry_ptr, obj, "file_time",
sizeof("file_time") - 1, time TSRMLS_CC);
sprintf(tmp_s, "%x", entry->FileCRC);
zend_update_property_string(rar_class_entry_ptr, object, "crc",
zend_update_property_string(rar_class_entry_ptr, obj, "crc",
sizeof("crc") - 1, tmp_s TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "attr",
zend_update_property_long(rar_class_entry_ptr, obj, "attr",
sizeof("attr") - 1, entry->FileAttr TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "version",
zend_update_property_long(rar_class_entry_ptr, obj, "version",
sizeof("version") - 1, entry->UnpVer TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "method",
zend_update_property_long(rar_class_entry_ptr, obj, "method",
sizeof("method") - 1, entry->Method TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "flags",
zend_update_property_long(rar_class_entry_ptr, obj, "flags",
sizeof("flags") - 1, entry->Flags TSRMLS_CC);
zend_update_property_long(rar_class_entry_ptr, object, "redir_type",
zend_update_property_long(rar_class_entry_ptr, obj, "redir_type",
sizeof("redir_type") - 1, entry->RedirType TSRMLS_CC);
if (entry->RedirName) {
char *redir_target = NULL;
size_t redir_target_size;
zend_update_property_bool(rar_class_entry_ptr, object,
zend_update_property_bool(rar_class_entry_ptr, obj,
"redir_to_directory", sizeof("redir_to_directory") - 1,
!!entry->DirTarget TSRMLS_CC);
@@ -146,7 +153,7 @@ void _rar_entry_to_zval(zval *parent,
assert(redir_target_size > 0);
_rar_wide_to_utf(entry->RedirName, redir_target, redir_target_size);
zend_update_property_string(rar_class_entry_ptr, object, "redir_target",
zend_update_property_string(rar_class_entry_ptr, obj, "redir_target",
sizeof("redir_target") - 1, redir_target TSRMLS_CC);
efree(redir_target);
@@ -195,8 +202,14 @@ static int _rar_decl_priv_prop_null(zend_class_entry *ce, const char *name,
ZVAL_NULL(&property);
name_str = zend_string_init(name, (size_t) name_length, 1);
doc_str = zend_string_init(doc_comment, (size_t) doc_comment_len, 1);
# if PHP_MAJOR_VERSION >= 8
zend_declare_property_ex(ce, name_str, &property, ZEND_ACC_PRIVATE,
doc_str);
ret = SUCCESS;
# else
ret = zend_declare_property_ex(ce, name_str, &property, ZEND_ACC_PRIVATE,
doc_str);
#endif
zend_string_release(name_str);
zend_string_release(doc_str);
return ret;
@@ -216,10 +229,12 @@ static zval *_rar_entry_get_property(zval *entry_obj, char *name, int namelen TS
EG(scope) = rar_class_entry_ptr;
#endif
#if PHP_MAJOR_VERSION < 7
tmp = zend_read_property(Z_OBJCE_P(entry_obj), entry_obj, name, namelen, 1 TSRMLS_CC);
#else
#if PHP_MAJOR_VERSION >= 8
tmp = zend_read_property(Z_OBJCE_P(entry_obj), Z_OBJ_P(entry_obj), name, namelen, 1, &zv);
#elif PHP_MAJOR_VERSION >= 7
tmp = zend_read_property(Z_OBJCE_P(entry_obj), entry_obj, name, namelen, 1, &zv);
#else
tmp = zend_read_property(Z_OBJCE_P(entry_obj), entry_obj, name, namelen, 1 TSRMLS_CC);
#endif
if (tmp == NULL) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,
@@ -290,7 +305,7 @@ PHP_METHOD(rarentry, extract)
}
RAR_GET_PROPERTY(tmp, "rarfile");
if (_rar_get_file_resource(tmp, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(tmp, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
@@ -544,7 +559,7 @@ PHP_METHOD(rarentry, getStream)
RAR_GET_PROPERTY(position, "position");
RAR_GET_PROPERTY(tmp, "rarfile");
if (_rar_get_file_resource(tmp, &rar TSRMLS_CC) == FAILURE) {
if (_rar_get_file_resource_zv(tmp, &rar TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}

View File

@@ -5,6 +5,7 @@ rar_list() function
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
$rar_file1 = rar_open(dirname(__FILE__).'/linux_rar.rar');
$list1 = rar_list($rar_file1);
var_dump($list1);
@@ -14,8 +15,7 @@ $list2 = rar_list($rar_file2);
var_dump($list2);
$rar_file3 = rar_open(dirname(__FILE__).'/no_such_file.rar');
$list3 = rar_list($rar_file3);
var_dump($list3);
argerr(function() use ($rar_file3) { rar_list($rar_file3); });
echo "Done\n";
?>
@@ -164,5 +164,4 @@ array(2) {
Warning: rar_open(): Failed to open %s: ERAR_EOPEN (file open error) in %s on line %d
Warning: rar_list() expects parameter 1 to be RarArchive, boo%s given in %s on line %d
NULL
Done

View File

@@ -5,6 +5,7 @@ rar_entry_get() function
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
$rar_file1 = rar_open(dirname(__FILE__).'/linux_rar.rar');
$entry1 = rar_entry_get($rar_file1, 'test file with whitespaces.txt');
var_dump($entry1);
@@ -14,8 +15,9 @@ $entry2 = rar_entry_get($rar_file2, '2.txt');
var_dump($entry2);
$rar_file3 = rar_open(dirname(__FILE__).'/no_such_file.rar');
$entry3 = rar_entry_get($rar_file3, '2.txt');
var_dump($entry3);
argerr(function() use ($rar_file3) {
rar_entry_get($rar_file3, '2.txt');
});
echo "Done\n";
?>
@@ -90,5 +92,4 @@ object(RarEntry)#%d (%d) {
Warning: rar_open(): Failed to open %s: ERAR_EOPEN (file open error) in %s on line %d
Warning: rar_entry_get() expects parameter 1 to be RarArchive, boo%s given in %s on line %d
NULL
Done

View File

@@ -5,6 +5,8 @@ rar_entry_get() function
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
$rar_file1 = rar_open(dirname(__FILE__).'/multi.part1.rar');
$entry = rar_entry_get($rar_file1, "file1.txt");
echo "$entry\n";
@@ -13,8 +15,9 @@ var_dump($entry);
echo "\n";
$rar_file2 = rar_open(dirname(__FILE__).'/nonexistent.rar');
$entry = rar_entry_get($rar_file2, "file1.txt");
var_dump($entry);
argerr(function() use ($rar_file2) {
rar_entry_get($rar_file2, "file1.txt");
});
echo "\n";
echo "Done\n";
@@ -29,6 +32,5 @@ bool(false)
Warning: rar_open(): Failed to open %s: ERAR_EOPEN (file open error) in %s on line %d
Warning: rar_entry_get() expects parameter 1 to be RarArchive, boo%s given in %s on line %d
NULL
Done

View File

@@ -5,6 +5,7 @@ rar_open() with invalid volume callback
if(!extension_loaded("rar")) die("skip");
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
class A {
public static function resolve($vol) {
@@ -30,11 +31,15 @@ var_dump($rar);
echo "\nGiven callback that takes more arguments:\n";
$rar = RarArchive::open($fn, null, 'strpos');
$rar->getEntries();
argerr(function() use ($rar) {
$rar->getEntries();
});
echo "\nGiven callback that takes another kind of arguments:\n";
$rar = RarArchive::open($fn, null, 'array_keys');
$rar->getEntries();
argerr(function() use ($rar) {
$rar->getEntries();
});
echo "\nGiven callback that returns another kind of arguments:\n";
function testA($vol) { return true; }
@@ -52,7 +57,7 @@ try {
}
echo "Done.\n";
--EXPECTF--
--EXPECTF_DYNAMIC--
Not given a callback:
Warning: RarArchive::open(): Expected the third argument, if provided, to be a valid callback in %s on line %d
@@ -64,15 +69,33 @@ bool(false)
Given callback that takes more arguments:
<?php if (PHP_VERSION_ID >= 80000) { ?>
Warning: RarArchive::getEntries(): Failure to call volume find callback in %s on line %d
<?php } ?>
<?php if (PHP_VERSION_ID >= 80000) { ?>
Warning: RarArchive::getEntries(): ERAR_EOPEN (file open error) in %s on line %d
Warning: strpos() expects at least %d parameters, 1 given in %s on line %d
<?php } else { ?>
Warning: strpos() expects at least %d parameters, 1 given in %s on line %d
Warning: RarArchive::getEntries(): ERAR_EOPEN (file open error) in %s on line %d
<?php } ?>
Given callback that takes another kind of arguments:
<?php if (PHP_VERSION_ID >= 80000) { ?>
Warning: RarArchive::getEntries(): Failure to call volume find callback in %s on line %d
Warning: RarArchive::getEntries(): ERAR_EOPEN (file open error) in %s on line %d
Warning: array_keys() expects parameter 1 to be array, string given in %s on line %d
<?php } else { ?>
Warning: array_keys() expects parameter 1 to be array, string given in %s on line %d
Warning: RarArchive::getEntries(): ERAR_EOPEN (file open error) in %s on line %d
<?php } ?>
Given callback that returns another kind of arguments:

View File

@@ -50,11 +50,11 @@ string(5) "11111"
Test with include path:
Should fail (not in include):
Warning: fopen(rar://tmp.rar#1.txt): failed to open stream: Error opening RAR archive %stmp.rar: ERAR_EOPEN (file open error) in %s on line %d
Warning: fopen(rar://tmp.rar#1.txt): %cailed to open stream: Error opening RAR archive %stmp.rar: ERAR_EOPEN (file open error) in %s on line %d
Should fail (include unused):
Warning: fopen(rar://tmp.rar#1.txt): failed to open stream: Error opening RAR archive %stmp.rar: ERAR_EOPEN (file open error) in %s on line %d
Warning: fopen(rar://tmp.rar#1.txt): %cailed to open stream: Error opening RAR archive %stmp.rar: ERAR_EOPEN (file open error) in %s on line %d
Should succeed:
string(5) "11111"

View File

@@ -20,9 +20,9 @@ echo "Done.\n";
--EXPECTF--
Archive not found :
Warning: fopen(rar://%snot_found.rar#1.txt): failed to open stream: Error opening RAR archive %snot_found.rar: ERAR_EOPEN (file open error) in %s on line %d
Warning: fopen(rar://%snot_found.rar#1.txt): %cailed to open stream: Error opening RAR archive %snot_found.rar: ERAR_EOPEN (file open error) in %s on line %d
File not found :
Warning: fopen(rar://%slatest_winrar.rar#not_found.txt): failed to open stream: Can't file not_found.txt in RAR archive %s on line %d
Done.
Warning: fopen(rar://%slatest_winrar.rar#not_found.txt): %cailed to open stream: Can't file not_found.txt in RAR archive %s on line %d
Done.

View File

@@ -27,21 +27,21 @@ echo "Done.\n";
--EXPECTF--
Test empty:
Warning: fopen(rar://): failed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Warning: fopen(rar://): %cailed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Test no fragment:
Warning: fopen(rar://file.rar): failed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Warning: fopen(rar://file.rar): %cailed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Test empty fragment:
Warning: fopen(rar://file.rar#): failed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Warning: fopen(rar://file.rar#): %cailed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Test no path:
Warning: fopen(rar://#frag): failed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Warning: fopen(rar://#frag): %cailed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Test no path and empty fragment:
Warning: fopen(rar://#): failed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Warning: fopen(rar://#): %cailed to open stream: The url must contain a path and a non-empty fragment; it must be in the form "rar://<urlencoded path to RAR archive>[*]#<urlencoded entry name>" in %s on line %d
Done.

View File

@@ -55,11 +55,11 @@ echo "\nDone.\n";
--EXPECTF--
Headers: should not work (no password):
Warning: fopen(rar://%sencrypted_headers.rar#encfile1.txt): failed to open stream: Error opening RAR archive %sencrypted_headers.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Warning: fopen(rar://%sencrypted_headers.rar#encfile1.txt): %cailed to open stream: Error opening RAR archive %sencrypted_headers.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Headers: should not work (password given was file_password):
Warning: fopen(rar://%sencrypted_headers.rar#encfile1.txt): failed to open stream: Error opening RAR archive %sencrypted_headers.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Warning: fopen(rar://%sencrypted_headers.rar#encfile1.txt): %cailed to open stream: Error opening RAR archive %sencrypted_headers.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Headers: should work (password given was open_password):
string(26) "Encrypted file 1 contents."
@@ -67,11 +67,11 @@ string(26) "Encrypted file 1 contents."
Files: should not work (no password):
Warning: fopen(rar://%sencrypted_only_files.rar#encfile1.txt): failed to open stream: Error opening file encfile1.txt inside RAR archive %sencrypted_only_files.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Warning: fopen(rar://%sencrypted_only_files.rar#encfile1.txt): %cailed to open stream: Error opening file encfile1.txt inside RAR archive %sencrypted_only_files.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Files: should not work (password given was open_password):
Warning: fopen(rar://%sencrypted_only_files.rar#encfile1.txt): failed to open stream: Error opening file encfile1.txt inside RAR archive %sencrypted_only_files.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Warning: fopen(rar://%sencrypted_only_files.rar#encfile1.txt): %cailed to open stream: Error opening file encfile1.txt inside RAR archive %sencrypted_only_files.rar: ERAR_MISSING_PASSWORD (password needed but not specified) in %s on line %d
Files: should work (password given was file_password):
string(26) "Encrypted file 1 contents."

View File

@@ -12,6 +12,6 @@ var_dump(opendir($u));
echo "Done.\n";
--EXPECTF--
Warning: opendir(rar://%sdirlink_unix.rar#file): failed to open dir: Archive %sdirlink_unix.rar has an entry named file, but it is not a directory in %s on line %d
Warning: opendir(rar://%sdirlink_unix.rar#file): %cailed to open dir%S: Archive %sdirlink_unix.rar has an entry named file, but it is not a directory in %s on line %d
bool(false)
Done.

View File

@@ -15,10 +15,12 @@ echo "string (\"0.001\"). {$a['0.001']}\n";
echo "\n";
echo "Done.\n";
--EXPECTF--
--EXPECTF_DYNAMIC--
string ("0"). RarEntry for file "1.txt" (a0de71c0)
<?php if (PHP_VERSION_ID < 80000) { ?>
Notice: A non well formed numeric value encountered in %s on line %d
<?php } ?>
string ("1abc"). RarEntry for file "2.txt" (45a918de)
float (0.001). RarEntry for file "1.txt" (a0de71c0)
string ("0.001"). RarEntry for file "1.txt" (a0de71c0)

View File

@@ -42,7 +42,7 @@ echo $a[new stdClass()];
echo "\n";
echo "Done.\n";
--EXPECTF--
--EXPECTF_DYNAMIC--
* -1 (int):
Warning: main(): Dimension index must be non-negative, given -1 in %s on line %d
@@ -81,6 +81,11 @@ Warning: main(): Attempt to use a non-numeric dimension to access a RarArchive o
* new stdClass():
Warning: main(): Attempt to use an object with no get handler as a dimension to access a RarArchive object in %s on line %d
<?php if (PHP_VERSION_ID >= 80000) { ?>
Warning: main(): Could not convert object given as dimension index into an integer (cast_object failed) in %s on line %d
<?php } else { ?>
Notice: Object of class stdClass could not be converted to int in %s on line %d
RarEntry for file "2.txt" (45a918de)
<?php } ?>
Done.

View File

@@ -5,13 +5,18 @@ RarArchive::isBroken/rar_broken_is test
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
$f = dirname(__FILE__) . "/latest_winrar.rar";
$b = dirname(__FILE__) . "/multi_broken.part1.rar";
echo "\n* unbroken file; bad arguments\n";
$a = RarArchive::open($f);
var_dump($a->isBroken("jjj"));
var_dump(rar_broken_is($a, "jjj"));
argerr(function() use ($a) {
$a->isBroken("jjj");
});
argerr(function() use ($a) {
rar_broken_is($a, "jjj");
});
echo "\n* unbroken file; as first call\n";
var_dump($a->isBroken());
@@ -46,10 +51,8 @@ echo "Done.\n";
* unbroken file; bad arguments
Warning: RarArchive::isBroken() expects exactly 0 parameters, 1 given in %s on line %d
NULL
Warning: rar_broken_is() expects exactly 1 parameter, 2 given in %s on line %d
NULL
* unbroken file; as first call
bool(false)

View File

@@ -5,13 +5,18 @@ RarArchive::setAllowBroken has the desired effect
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
function retnull() { return null; }
$b = dirname(__FILE__) . "/multi_broken.part1.rar";
echo "* broken file; bad arguments\n";
$a = RarArchive::open($b, null, 'retnull');
$a->setAllowBroken();
rar_allow_broken_set($a);
argerr(function() use ($a) {
$a->setAllowBroken();
});
argerr(function() use ($a) {
rar_allow_broken_set($a);
});
echo "\n* broken file; do not allow broken (default)\n";
$a = RarArchive::open($b, null, 'retnull');

View File

@@ -5,6 +5,7 @@ Wrapper cache exaustion test
--FILE--
<?php
require __DIR__ . "/php8compat.php.inc";
$f = array();
$f[] = dirname(__FILE__) . "/latest_winrar.rar";
$f[] = dirname(__FILE__) . "/directories.rar";
@@ -18,7 +19,9 @@ function printstats() {
}
echo "* Invalid call to rar_wrapper_cache_stats():\n";
var_dump(rar_wrapper_cache_stats("sfddf"));
argerr(function() {
rar_wrapper_cache_stats("sfddf");
});
echo "\n* Initial stats:\n";
printstats();
@@ -75,7 +78,6 @@ echo "Done.\n";
* Invalid call to rar_wrapper_cache_stats():
Warning: rar_wrapper_cache_stats() expects exactly 0 parameters, 1 given in %s on line %d
NULL
* Initial stats:
Stats: 0/0 (hits/misses)

View File

@@ -32,6 +32,6 @@ opened
Testing 'r+'
Warning: fopen(%s): failed to open stream: Only the "r" and "rb" open modes are permitted, given r+ in %s on line %d
Warning: fopen(%s): %cailed to open stream: Only the "r" and "rb" open modes are permitted, given r+ in %s on line %d
Done.

View File

@@ -11,7 +11,7 @@ new RarArchive();
echo "Done\n";
--EXPECTF--
Fatal error: Uncaught Error: Call to private RarArchive::__construct() from invalid context in %s:%d
Fatal error: Uncaught Error: Call to private RarArchive::__construct() from %s in %s:%d
Stack trace:
#0 {main}
thrown in %s on line %d

View File

@@ -10,7 +10,7 @@ new RarEntry();
echo "Done\n";
--EXPECTF--
Fatal error: Uncaught Error: Call to private RarEntry::__construct() from invalid context in %s:%d
Fatal error: Uncaught Error: Call to private RarEntry::__construct() from %s in %s:%d
Stack trace:
#0 {main}
thrown in %s on line %d

25
tests/115.phpt Normal file
View File

@@ -0,0 +1,25 @@
--TEST--
getIterator() (PHP 8+)
--SKIPIF--
<?php
if (!extension_loaded("rar")) die("skip");
if (PHP_VERSION_ID < 80000) print "skip for PHP 8";
?>
--FILE--
<?php
$a = rar_open(dirname(__FILE__).'/linux_rar.rar');
$it = $a->getIterator();
var_dump($it);
foreach ($it as $e) {
echo $e->getName(), "\n";
}
echo "Done\n";
?>
--EXPECT--
object(InternalIterator)#3 (0) {
}
plain.txt
test file with whitespaces.txt
Done

17
tests/php8compat.php.inc Normal file
View File

@@ -0,0 +1,17 @@
<?php
ini_set('pcre.jit', '0'); // avoid some valgrind errors
function argerr($cl) {
try {
return $cl();
} catch (TypeError $err) {
$msg = $err->getMessage();
$msg = "Warning: $msg in {$err->getFile()} on line {$err->getLine()}";
$msg = preg_replace('/: Argument #(\d) \(\$\S+\) must be of type/',
' expects parameter \1 to be', $msg);
$msg = preg_replace('/expects (.+) (\d) argument/',
'expects \1 \2 parameter', $msg);
echo "\n", $msg, "\n";
}
}