From 29190559f847164a8532711638b49f27462f3a11 Mon Sep 17 00:00:00 2001 From: Olly Betts Date: Mon, 30 May 2011 06:47:47 +0000 Subject: [PATCH] SWIG_ZTS_SetPointerZval() now interprets bit 1 in newobject as meaning (wrap in a PHP class wrapper), rather than taking newobject==2 as meaning this, so we can wrap new and existing objects in this way. Handle wrapping classes in a C++ namespace being returned by director methods. No need to force classname to lowercase as zend_lookup_class() does that internally. git-svn-id: https://swig.svn.sourceforge.net/svnroot/swig/trunk@12723 626c5289-ae23-0410-ae9c-e8d60b6d4f22 --- Lib/php/php.swg | 2 +- Lib/php/phprun.swg | 39 ++++++++++++++++++++++++++------------- Source/Modules/php.cxx | 3 +++ 3 files changed, 30 insertions(+), 14 deletions(-) diff --git a/Lib/php/php.swg b/Lib/php/php.swg index f69761079..2affdd1ac 100644 --- a/Lib/php/php.swg +++ b/Lib/php/php.swg @@ -347,7 +347,7 @@ SWIGTYPE [], SWIGTYPE & %{ - SWIG_SetPointerZval($input, (void *)&$1_name, $1_descriptor, $owner); + SWIG_SetPointerZval($input, (void *)&$1_name, $1_descriptor, ($owner)|2); %} %typemap(out, fragment="swig_php_init_member_ptr") SWIGTYPE (CLASS::*) diff --git a/Lib/php/phprun.swg b/Lib/php/phprun.swg index ef521c857..86d242958 100644 --- a/Lib/php/phprun.swg +++ b/Lib/php/phprun.swg @@ -96,7 +96,6 @@ static ZEND_RSRC_DTOR_FUNC(SWIG_landfill) { (void)rsrc; } static void SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject TSRMLS_DC) { - swig_object_wrapper *value=NULL; /* * First test for Null pointers. Return those as PHP native NULL */ @@ -105,12 +104,13 @@ SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject return; } if (type->clientdata) { + swig_object_wrapper *value; if (! (*(int *)(type->clientdata))) zend_error(E_ERROR, "Type: %s failed to register with zend",type->name); value=(swig_object_wrapper *)emalloc(sizeof(swig_object_wrapper)); value->ptr=ptr; - value->newobject=newobject; - if (newobject <= 1) { + value->newobject=(newobject & 1); + if ((newobject & 2) == 0) { /* Just register the pointer as a resource. */ ZEND_REGISTER_RESOURCE(z, value, *(int *)(type->clientdata)); } else { @@ -119,18 +119,32 @@ SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject * via the "_cPtr" member. This is currently only used by * directorin typemaps. */ - value->newobject = 0; zval *resource; + zend_class_entry **ce = NULL; + const char *type_name = type->name+3; /* +3 so: _p_Foo -> Foo */ + size_t type_name_len; + int result; + const char * p; + + /* Namespace__Foo -> Foo */ + /* FIXME: ugly and goes wrong for classes with __ in their names. */ + while ((p = strstr(type_name, "__")) != NULL) { + type_name = p + 2; + } + type_name_len = strlen(type_name); + MAKE_STD_ZVAL(resource); ZEND_REGISTER_RESOURCE(resource, value, *(int *)(type->clientdata)); - zend_class_entry **ce = NULL; - zval *classname; - MAKE_STD_ZVAL(classname); - /* _p_Foo -> Foo */ - ZVAL_STRING(classname, (char*)type->name+3, 1); - /* class names are stored in lowercase */ - php_strtolower(Z_STRVAL_PP(&classname), Z_STRLEN_PP(&classname)); - if (zend_lookup_class(Z_STRVAL_P(classname), Z_STRLEN_P(classname), &ce TSRMLS_CC) != SUCCESS) { + if (SWIG_PREFIX_LEN > 0) { + char * classname = (char*)emalloc(SWIG_PREFIX_LEN + type_name_len + 1); + strcpy(classname, SWIG_PREFIX); + strcpy(classname + SWIG_PREFIX_LEN, type_name); + result = zend_lookup_class(classname, SWIG_PREFIX_LEN + type_name_len, &ce TSRMLS_CC); + efree(classname); + } else { + result = zend_lookup_class(type_name, type_name_len, &ce TSRMLS_CC); + } + if (result != SUCCESS) { /* class does not exist */ object_init(z); } else { @@ -139,7 +153,6 @@ SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject Z_SET_REFCOUNT_P(z, 1); Z_SET_ISREF_P(z); zend_hash_update(HASH_OF(z), (char*)"_cPtr", sizeof("_cPtr"), (void*)&resource, sizeof(zval), NULL); - FREE_ZVAL(classname); } return; } diff --git a/Source/Modules/php.cxx b/Source/Modules/php.cxx index 33f5291fb..b4af248f5 100644 --- a/Source/Modules/php.cxx +++ b/Source/Modules/php.cxx @@ -328,6 +328,9 @@ public: if (!prefix) prefix = NewStringEmpty(); + Printf(f_runtime, "#define SWIG_PREFIX \"%s\"\n", prefix); + Printf(f_runtime, "#define SWIG_PREFIX_LEN %lu\n", (unsigned long)Len(prefix)); + if (directorsEnabled()) { Swig_banner(f_directors_h); Printf(f_directors_h, "\n");