周梦康 发表于 2016-03-27 2128 次浏览 标签 : PHP 扩展开发

PHP 扩展开发的文章,我均已更新至《TIPI》(下面的博文可能已经过时,以 TIPI 上的内容为准)。

编译扩展时报错

PHP Fatal error:  Internal zval's can't be arrays, objects or resources in Unknown on line 0

搜代码可知这个错误提示出现在两个地方

ZEND_API void _zval_internal_dtor(zval *zvalue ZEND_FILE_LINE_DC)
ZEND_API int zend_declare_property_ex(zend_class_entry *ce, const char *name, int name_length, zval *property, int access_type, char *doc_comment, int doc_comment_len TSRMLS_DC)

我想了半天想不到什么更好地办法,我使用gdb对函数加上断点调试,也没找到地方。

今天解决了,记录下。

首先在初始化类时

PHP_MINIT_FUNCTION(road)
{
    zend_class_entry ce;

    INIT_CLASS_ENTRY(ce, "road", road_methods);
    road_ce = zend_register_internal_class(&ce);
    zend_declare_property_null(road_ce, "func_deal", sizeof("func_deal") - 1, ZEND_ACC_PUBLIC);

   return SUCCESS;
}

然后在使用func_deal时,没有给该属性值分配内存

zval *func, *deal;

if (zend_parse_parameters(ZEND_NUM_ARGS(), "z", &func) == FAILURE) {
    return;
}

deal = zend_read_property(road_ce, getThis(), "func_deal", sizeof("func_deal")-1, 1 TSRMLS_CC);

if (Z_TYPE_P(deal) != IS_ARRAY) {
    array_init(deal);
}

参考了下这个链接http://grokbase.com/t/php/php-internals/07a4b14xvb/php-dev-how-declare-protected-array-property-at-internal-class-properly

恍然大悟,是不是因为没有给上面的deal分配内存地址。尝试了下,运行起来ok了。

zend_declare_property_null的源码回头再分析,先继续干活。


评论列表