[php7] Use destructor action if present
If there's a destructor, use its action instead of free(ptr) (for C)/delete ptr (for C++). Fixes #2108
This commit is contained in:
parent
51f586bc4c
commit
c25df74807
2 changed files with 43 additions and 9 deletions
17
Examples/test-suite/php/newobject2_runme.php
Normal file
17
Examples/test-suite/php/newobject2_runme.php
Normal file
|
|
@ -0,0 +1,17 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
require "tests.php";
|
||||||
|
|
||||||
|
check::equal(fooCount(), 0, "no Foo objects expected");
|
||||||
|
$foo = makeFoo();
|
||||||
|
check::equal(get_class($foo), "Foo", "static failed");
|
||||||
|
check::equal(fooCount(), 1, "1 Foo object expected");
|
||||||
|
$bar = makeFoo();
|
||||||
|
check::equal(get_class($bar), "Foo", "regular failed");
|
||||||
|
check::equal(fooCount(), 2, "2 Foo objects expected");
|
||||||
|
$foo = null;
|
||||||
|
check::equal(fooCount(), 1, "1 Foo object expected");
|
||||||
|
$bar = null;
|
||||||
|
check::equal(fooCount(), 0, "no Foo objects expected");
|
||||||
|
|
||||||
|
check::done();
|
||||||
|
|
@ -64,6 +64,7 @@ static String *pragma_phpinfo;
|
||||||
static String *pragma_version;
|
static String *pragma_version;
|
||||||
|
|
||||||
static String *class_name = NULL;
|
static String *class_name = NULL;
|
||||||
|
static String *destructor_action = NULL;
|
||||||
static String *magic_set = NULL;
|
static String *magic_set = NULL;
|
||||||
static String *magic_get = NULL;
|
static String *magic_get = NULL;
|
||||||
static String *magic_isset = NULL;
|
static String *magic_isset = NULL;
|
||||||
|
|
@ -108,6 +109,7 @@ static enum {
|
||||||
membervar,
|
membervar,
|
||||||
staticmembervar,
|
staticmembervar,
|
||||||
constructor,
|
constructor,
|
||||||
|
destructor,
|
||||||
directorconstructor,
|
directorconstructor,
|
||||||
directordisown
|
directordisown
|
||||||
} wrapperType = standard;
|
} wrapperType = standard;
|
||||||
|
|
@ -138,9 +140,19 @@ static void print_creation_free_wrapper(Node *n) {
|
||||||
|
|
||||||
Printf(s, " zend_object_std_dtor(&obj->std);\n");
|
Printf(s, " zend_object_std_dtor(&obj->std);\n");
|
||||||
|
|
||||||
// expand %delete typemap instead of SWIG_remove?
|
Printf(s, " if (obj->newobject)");
|
||||||
Printf(s, " if (obj->newobject)\n");
|
String * type = Getattr(n, "classtype");
|
||||||
Printf(s, " SWIG_remove((%s *)obj->ptr);\n", Getattr(n, "classtype"));
|
if (destructor_action) {
|
||||||
|
Printv(s,
|
||||||
|
" {\n",
|
||||||
|
type, " * arg1 = (", type, " *)obj->ptr;\n",
|
||||||
|
destructor_action, "\n",
|
||||||
|
" }\n", NIL);
|
||||||
|
} else if (CPlusPlus) {
|
||||||
|
Printf(s, "\n delete (%s *)obj->ptr;\n", type);
|
||||||
|
} else {
|
||||||
|
Printf(s, "\n free(obj->ptr);\n", type);
|
||||||
|
}
|
||||||
Printf(s, "}\n\n");
|
Printf(s, "}\n\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -371,9 +383,6 @@ public:
|
||||||
Printf(s_header, "}\n");
|
Printf(s_header, "}\n");
|
||||||
Printf(s_header, "#endif\n\n");
|
Printf(s_header, "#endif\n\n");
|
||||||
|
|
||||||
Printf(s_header, "#ifdef __cplusplus\n#define SWIG_remove(PTR) delete PTR\n");
|
|
||||||
Printf(s_header, "#else\n#define SWIG_remove(PTR) free(PTR)\n#endif\n\n");
|
|
||||||
|
|
||||||
if (directorsEnabled()) {
|
if (directorsEnabled()) {
|
||||||
// Insert director runtime
|
// Insert director runtime
|
||||||
Swig_insert_file("director_common.swg", s_header);
|
Swig_insert_file("director_common.swg", s_header);
|
||||||
|
|
@ -1132,10 +1141,12 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Cmp(nodeType, "destructor") == 0) {
|
if (wrapperType == destructor) {
|
||||||
// We don't explicitly wrap the destructor for PHP - Zend manages the
|
// We don't explicitly wrap the destructor for PHP - Zend manages the
|
||||||
// reference counting, and the user can just do `$obj = null;' or similar
|
// reference counting, and the user can just do `$obj = null;' or similar
|
||||||
// to remove a reference to an object.
|
// to remove a reference to an object.
|
||||||
|
Setattr(n, "wrap:name", wname);
|
||||||
|
(void)emit_action(n);
|
||||||
return SWIG_OK;
|
return SWIG_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1535,6 +1546,7 @@ public:
|
||||||
String *base_class = NULL;
|
String *base_class = NULL;
|
||||||
|
|
||||||
class_name = symname;
|
class_name = symname;
|
||||||
|
destructor_action = NULL;
|
||||||
|
|
||||||
Printf(all_cs_entry, "static zend_function_entry class_%s_functions[] = {\n", class_name);
|
Printf(all_cs_entry, "static zend_function_entry class_%s_functions[] = {\n", class_name);
|
||||||
|
|
||||||
|
|
@ -1811,8 +1823,13 @@ public:
|
||||||
/* ------------------------------------------------------------
|
/* ------------------------------------------------------------
|
||||||
* destructorHandler()
|
* destructorHandler()
|
||||||
* ------------------------------------------------------------ */
|
* ------------------------------------------------------------ */
|
||||||
//virtual int destructorHandler(Node *n) {
|
virtual int destructorHandler(Node *n) {
|
||||||
//}
|
wrapperType = destructor;
|
||||||
|
Language::destructorHandler(n);
|
||||||
|
destructor_action = Getattr(n, "wrap:action");
|
||||||
|
wrapperType = standard;
|
||||||
|
return SWIG_OK;
|
||||||
|
}
|
||||||
|
|
||||||
/* ------------------------------------------------------------
|
/* ------------------------------------------------------------
|
||||||
* memberconstantHandler()
|
* memberconstantHandler()
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue