com php-src: Fixed bug #77768 (FFI: Builtin Types Should Not Raise Error On Redeclaration): ext/ffi/ffi.c ext/ffi/tests/bug77768.phpt
| From: | Dmitry Stogov | Date: | Thu, 28 Mar 2019 21:02:26 +0000 |
| Subject: | com php-src: Fixed bug #77768 (FFI: Builtin Types Should Not Raise Error On Redeclaration): ext/ffi/ffi.c ext/ffi/tests/bug77768.phpt | ||
| Groups: | php.cvs | ||
| Request: | Send a blank email to php-cvs+get-105385@lists.php.net to get a copy of this message | ||
Commit: a3e52afebe77517ca10d98ba57fefe3f178d56b6
Author: Dmitry Stogov <dmitry@zend.com> Fri, 29 Mar 2019 00:02:26 +0300
Parents: 5e16f5b8d8c93a124c9b41e17b923195510704c7
Branches: PHP-7.4 master
Link: http://git.php.net/?p=php-src.git;a=commitdiff;h=a3e52afebe77517ca10d98ba57fefe3f178d56b6
Log:
Fixed bug #77768 (FFI: Builtin Types Should Not Raise Error On Redeclaration)
Bugs:
https://bugs.php.net/77768
Changed paths:
M ext/ffi/ffi.c
A ext/ffi/tests/bug77768.phpt
Diff:
diff --git a/ext/ffi/ffi.c b/ext/ffi/ffi.c
index ba15151..e8061a4 100644
--- a/ext/ffi/ffi.c
+++ b/ext/ffi/ffi.c
@@ -5772,11 +5772,39 @@ void zend_ffi_declare(const char *name, size_t name_len, zend_ffi_dcl *dcl)
/* {
FFI_G(symbols) = pemalloc(sizeof(HashTable), FFI_G(persistent));
zend_hash_init(FFI_G(symbols), 0, NULL, FFI_G(persistent) ? zend_ffi_symbol_hash_persistent_dtor
: zend_ffi_symbol_hash_dtor, FFI_G(persistent));
}
+ zend_ffi_finalize_type(dcl);
sym = zend_hash_str_find_ptr(FFI_G(symbols), name, name_len);
if (sym) {
+ if ((dcl->flags & ZEND_FFI_DCL_STORAGE_CLASS) == ZEND_FFI_DCL_TYPEDEF
+ && sym->kind == ZEND_FFI_SYM_TYPE
+ && zend_ffi_is_same_type(ZEND_FFI_TYPE(sym->type), ZEND_FFI_TYPE(dcl->type))
+ && sym->is_const == (zend_bool)(dcl->attr & ZEND_FFI_ATTR_CONST)) {
+ /* allowed redeclaration */
+ zend_ffi_type_dtor(dcl->type);
+ return;
+ } else if ((dcl->flags & ZEND_FFI_DCL_STORAGE_CLASS) == 0
+ || (dcl->flags & ZEND_FFI_DCL_STORAGE_CLASS) == ZEND_FFI_DCL_EXTERN) {
+ zend_ffi_type *type = ZEND_FFI_TYPE(dcl->type);
+
+ if (type->kind == ZEND_FFI_TYPE_FUNC) {
+ if (sym->kind == ZEND_FFI_SYM_FUNC
+ && zend_ffi_same_types(ZEND_FFI_TYPE(sym->type), type)) {
+ /* allowed redeclaration */
+ zend_ffi_type_dtor(dcl->type);
+ return;
+ }
+ } else {
+ if (sym->kind == ZEND_FFI_SYM_VAR
+ && zend_ffi_is_same_type(ZEND_FFI_TYPE(sym->type), type)
+ && sym->is_const == (zend_bool)(dcl->attr & ZEND_FFI_ATTR_CONST)) {
+ /* allowed redeclaration */
+ zend_ffi_type_dtor(dcl->type);
+ return;
+ }
+ }
+ }
zend_ffi_parser_error("redeclaration of '%.*s' at line %d", name_len, name,
FFI_G(line));
} else {
- zend_ffi_finalize_type(dcl);
if ((dcl->flags & ZEND_FFI_DCL_STORAGE_CLASS) == ZEND_FFI_DCL_TYPEDEF) {
if (zend_ffi_validate_vla(ZEND_FFI_TYPE(dcl->type)) != SUCCESS) {
zend_ffi_cleanup_dcl(dcl);
diff --git a/ext/ffi/tests/bug77768.phpt b/ext/ffi/tests/bug77768.phpt
new file mode 100644
index 0000000..6c29db5
--- /dev/null
+++ b/ext/ffi/tests/bug77768.phpt
@@ -0,0 +1,39 @@
+--TEST--
+Bug #77768 (Redeclaration of builtin types and repeated declarations)
+--SKIPIF--
+<?php
+require_once('skipif.inc');
+try {
+ $libc = FFI::cdef("int printf(const char *format, ...);", "libc.so.6");
+} catch (Throwable $_) {
+ die('skip libc.so.6 not available');
+}
+?>
+--INI--
+ffi.enable=1
+--FILE--
+<?php
+$x = FFI::cdef("
+typedef __builtin_va_list __gnuc_va_list;
+typedef unsigned int uint8_t;
+
+typedef int64_t a;
+typedef int64_t b;
+typedef a c;
+typedef b c;
+
+struct point {int x,y;};
+
+typedef struct point d;
+typedef struct point d;
+
+int printf(const char *format, ...);
+int printf(const char *format, ...);
+");
+
+var_dump(FFI::sizeof($x->new("uint8_t")));
+var_dump(FFI::sizeof(FFI::new("uint8_t")));
+?>
+--EXPECT--
+int(4)
+int(1)