static int do_fetch_class_prepare(pdo_stmt_t *stmt TSRMLS_DC) /* {{{ */
{
zend_class_entry * ce = stmt->fetch.cls.ce;
+ zend_fcall_info * fci = &stmt->fetch.cls.fci;
+ zend_fcall_info_cache * fcc = &stmt->fetch.cls.fcc;
+
+ fci->size = sizeof(zend_fcall_info);
if (!ce) {
stmt->fetch.cls.ce = ZEND_STANDARD_CLASS_DEF_PTR;
}
if (ce->constructor) {
- zend_fcall_info * fci = &stmt->fetch.cls.fci;
- zend_fcall_info_cache * fcc = &stmt->fetch.cls.fcc;
-
- fci->size = sizeof(zend_fcall_info);
fci->function_table = &ce->function_table;
fci->function_name = NULL;
fci->symbol_table = NULL;
Bucket *p;
fci->param_count = 0;
- fci->params = safe_emalloc(sizeof(zval*), ht->nNumOfElements, 0);
+ fci->params = safe_emalloc(sizeof(zval**), ht->nNumOfElements, 0);
p = ht->pListHead;
while (p != NULL) {
fci->params[fci->param_count++] = (zval**)p->pData;
if (stmt->fetch.cls.fci.size && stmt->fetch.cls.fci.params) {
efree(stmt->fetch.cls.fci.params);
stmt->fetch.cls.fci.params = NULL;
- stmt->fetch.cls.fci.size = 0;
}
+ stmt->fetch.cls.fci.size = 0;
if (stmt->fetch.cls.ctor_args && free_ctor_agrs) {
- FREE_ZVAL(stmt->fetch.cls.ctor_args);
+ zval_ptr_dtor(&stmt->fetch.cls.ctor_args);
stmt->fetch.cls.ctor_args = NULL;
+ stmt->fetch.cls.fci.param_count = 0;
}
if (stmt->fetch.func.values && free_ctor_agrs) {
FREE_ZVAL(stmt->fetch.func.values);
static int do_fetch(pdo_stmt_t *stmt, int do_bind, zval *return_value,
enum pdo_fetch_type how, enum pdo_fetch_orientation ori, long offset, zval *return_all TSRMLS_DC) /* {{{ */
{
- int flags = how & PDO_FETCH_FLAGS, idx;
+ int flags = how & PDO_FETCH_FLAGS, idx, old_arg_count;
zend_class_entry * ce, * old_ce;
- zval grp_val, *grp, **pgrp, *retval;
+ zval grp_val, *grp, **pgrp, *retval, *old_ctor_args;
how = how & ~PDO_FETCH_FLAGS;
if (how == PDO_FETCH_USE_DEFAULT) {
zval val;
zend_class_entry **cep;
- do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
old_ce = stmt->fetch.cls.ce;
+ old_ctor_args = stmt->fetch.cls.ctor_args;
+ old_arg_count = stmt->fetch.cls.fci.param_count;
+ do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
INIT_PZVAL(&val);
fetch_value(stmt, &val, i++ TSRMLS_CC);
default:
zval_ptr_dtor(&val);
pdo_raise_impl_error(stmt->dbh, stmt, "22003", "mode is out of range" TSRMLS_CC);
+ return 0;
break;
}
}
stmt->fetch.cls.fcc.object_pp = &return_value;
if (zend_call_function(&stmt->fetch.cls.fci, &stmt->fetch.cls.fcc TSRMLS_CC) == FAILURE) {
zend_throw_exception_ex(pdo_exception_ce, 0 TSRMLS_CC, "Could not execute %s::%s()", ce->name, ce->constructor->common.function_name);
+ return 0;
} else {
if (stmt->fetch.cls.retval_ptr) {
zval_ptr_dtor(&stmt->fetch.cls.retval_ptr);
if (flags & PDO_FETCH_CLASSTYPE) {
do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
stmt->fetch.cls.ce = old_ce;
+ stmt->fetch.cls.ctor_args = old_ctor_args;
+ stmt->fetch.cls.fci.param_count = old_arg_count;
}
break;
stmt->fetch.func.fci.retval_ptr_ptr = &retval;
if (zend_call_function(&stmt->fetch.func.fci, &stmt->fetch.func.fcc TSRMLS_CC) == FAILURE) {
zend_throw_exception_ex(pdo_exception_ce, 0 TSRMLS_CC, "Could not execute %s%s%s()", ce->name, ce->constructor->common.function_name);
+ return 0;
} else {
if (return_all) {
zval_ptr_dtor(&return_value); /* we don't need that */
int class_name_len;
zend_class_entry *old_ce;
zval *old_ctor_args, *ctor_args;
- int error = 0;
+ int error = 0, old_arg_count;
pdo_stmt_t *stmt = (pdo_stmt_t*)zend_object_store_get_object(getThis() TSRMLS_CC);
- old_ce = stmt->fetch.cls.ce;
- old_ctor_args = stmt->fetch.cls.ctor_args;
-
if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|sz",
&class_name, &class_name_len, &ctor_args)) {
RETURN_FALSE;
RETURN_FALSE;
}
+ old_ce = stmt->fetch.cls.ce;
+ old_ctor_args = stmt->fetch.cls.ctor_args;
+ old_arg_count = stmt->fetch.cls.fci.param_count;
+
+ do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
+
switch(ZEND_NUM_ARGS()) {
case 0:
stmt->fetch.cls.ce = zend_standard_class_def;
break;
}
if (Z_TYPE_P(ctor_args) == IS_ARRAY && zend_hash_num_elements(Z_ARRVAL_P(ctor_args))) {
- stmt->fetch.cls.ctor_args = ctor_args;
+ ALLOC_ZVAL(stmt->fetch.cls.ctor_args);
+ *stmt->fetch.cls.ctor_args = *ctor_args;
+ zval_copy_ctor(stmt->fetch.cls.ctor_args);
} else {
stmt->fetch.cls.ctor_args = NULL;
}
error = 1;
PDO_HANDLE_STMT_ERR();
}
+ do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
+
stmt->fetch.cls.ce = old_ce;
stmt->fetch.cls.ctor_args = old_ctor_args;
+ stmt->fetch.cls.fci.param_count = old_arg_count;
if (error) {
RETURN_FALSE;
}
zval *data, *return_all;
zval *arg2;
zend_class_entry *old_ce;
- zval *old_ctor_args, *ctor_args;
- int error = 0;
-
- old_ce = stmt->fetch.cls.ce;
- old_ctor_args = stmt->fetch.cls.ctor_args;
- stmt->fetch.cls.ctor_args = NULL;
+ zval *old_ctor_args, *ctor_args = NULL;
+ int error = 0, old_arg_count;
if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|lzz", &how, &arg2, &ctor_args)) {
RETURN_FALSE;
RETURN_FALSE;
}
+ old_ce = stmt->fetch.cls.ce;
+ old_ctor_args = stmt->fetch.cls.ctor_args;
+ old_arg_count = stmt->fetch.cls.fci.param_count;
+
+ do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
+
switch(how & ~PDO_FETCH_FLAGS) {
case PDO_FETCH_CLASS:
- do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
switch(ZEND_NUM_ARGS()) {
case 0:
case 1:
error = 1;
break;
}
- if (Z_TYPE_P(ctor_args) == IS_ARRAY && zend_hash_num_elements(Z_ARRVAL_P(ctor_args))) {
- stmt->fetch.cls.ctor_args = ctor_args;
- } else {
- stmt->fetch.cls.ctor_args = NULL;
+ if (Z_TYPE_P(ctor_args) != IS_ARRAY || !zend_hash_num_elements(Z_ARRVAL_P(ctor_args))) {
+ ctor_args = NULL;
}
/* no break */
case 2:
+ stmt->fetch.cls.ctor_args = ctor_args; /* we're not going to free these */
if (Z_TYPE_P(arg2) != IS_STRING) {
zend_throw_exception_ex(pdo_exception_ce, 0 TSRMLS_CC, "In fetch mode PDO_FETCH_CLASS the 2nd parameter must be a class name string", Z_TYPE_P(arg2));
error = 1;
}
}
}
-// do_fetch_class_prepare(stmt TSRMLS_CC);
+ do_fetch_class_prepare(stmt TSRMLS_CC);
break;
case PDO_FETCH_FUNC:
- do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
switch(ZEND_NUM_ARGS()) {
case 0:
case 1:
}
}
- if (!error)
- {
+ if (!error) {
PDO_STMT_CLEAR_ERR();
MAKE_STD_ZVAL(data);
if (how & PDO_FETCH_GROUP) {
FREE_ZVAL(data);
}
- do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
+ do_fetch_opt_finish(stmt, 0 TSRMLS_CC);
stmt->fetch.cls.ce = old_ce;
stmt->fetch.cls.ctor_args = old_ctor_args;
+ stmt->fetch.cls.fci.param_count = old_arg_count;
if (error) {
RETURN_FALSE;
zval ***args;
zend_class_entry **cep;
- switch (stmt->default_fetch_type) {
- case PDO_FETCH_CLASS:
- case PDO_FETCH_FUNC:
- do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
- break;
+ do_fetch_opt_finish(stmt, 1 TSRMLS_CC);
+ switch (stmt->default_fetch_type) {
case PDO_FETCH_INTO:
if (stmt->fetch.into) {
ZVAL_DELREF(stmt->fetch.into);
}
stmt->fetch.cls.ce = *cep;
+ stmt->fetch.cls.ctor_args = NULL;
if (stmt->dbh->is_persistent) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "PHP might crash if you don't call $stmt->setFetchMode() to reset to defaults on this persistent statement. This will be fixed in a later release");
if (Z_TYPE_PP(args[skip+2]) != IS_NULL && Z_TYPE_PP(args[skip+2]) != IS_ARRAY) {
zend_throw_exception(pdo_exception_ce, "Parameter ctor_args must either be NULL or an array ", 0 TSRMLS_CC);
} else if (Z_TYPE_PP(args[skip+2]) == IS_ARRAY && zend_hash_num_elements(Z_ARRVAL_PP(args[skip+2]))) {
- stmt->fetch.cls.ctor_args = *args[skip+2];
+ ALLOC_ZVAL(stmt->fetch.cls.ctor_args);
+ *stmt->fetch.cls.ctor_args = **args[skip+2];
zval_copy_ctor(stmt->fetch.cls.ctor_args);
}
}