diff options
author | Christoph M. Becker <cmbecker69@gmx.de> | 2020-10-03 13:39:37 +0200 |
---|---|---|
committer | Christoph M. Becker <cmbecker69@gmx.de> | 2020-10-05 23:11:36 +0200 |
commit | 3eae7aa77ef9999d401baef005ffd1d8e987d737 (patch) | |
tree | b694c7156886283428a45e3c17fc49038aef1a92 /ext/odbc | |
parent | a9e96a378db3e3e86b8b310ebbf5a20f909f67fb (diff) | |
download | php-git-3eae7aa77ef9999d401baef005ffd1d8e987d737.tar.gz |
Don't separate array parameter
Closes GH-6243.
Diffstat (limited to 'ext/odbc')
-rw-r--r-- | ext/odbc/php_odbc.c | 156 |
1 files changed, 65 insertions, 91 deletions
diff --git a/ext/odbc/php_odbc.c b/ext/odbc/php_odbc.c index d6a2239b33..c24e57228f 100644 --- a/ext/odbc/php_odbc.c +++ b/ext/odbc/php_odbc.c @@ -960,24 +960,34 @@ PHP_FUNCTION(odbc_prepare) * Execute prepared SQL statement. Supports only input parameters. */ +typedef struct odbc_params_t { + SQLLEN vallen; + int fp; +} odbc_params_t; + +static void odbc_release_params(odbc_result *result, odbc_params_t *params) { + SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); + for (int i = 0; i < result->numparams; i++) { + if (params[i].fp != -1) { + close(params[i].fp); + } + } + efree(params); +} + /* {{{ Execute a prepared statement */ PHP_FUNCTION(odbc_execute) { zval *pv_res, *tmp; HashTable *pv_param_ht = (HashTable *) &zend_empty_array; - typedef struct params_t { - SQLLEN vallen; - int fp; - } params_t; - params_t *params = NULL; + odbc_params_t *params = NULL; char *filename; - unsigned char otype; SQLSMALLINT ctype; - odbc_result *result; + odbc_result *result; int i, ne; RETCODE rc; - if (zend_parse_parameters(ZEND_NUM_ARGS(), "r|h/", &pv_res, &pv_param_ht) == FAILURE) { + if (zend_parse_parameters(ZEND_NUM_ARGS(), "r|h", &pv_res, &pv_param_ht) == FAILURE) { RETURN_THROWS(); } @@ -991,38 +1001,21 @@ PHP_FUNCTION(odbc_execute) RETURN_FALSE; } - zend_hash_internal_pointer_reset(pv_param_ht); - params = (params_t *)safe_emalloc(sizeof(params_t), result->numparams, 0); + params = (odbc_params_t *)safe_emalloc(sizeof(odbc_params_t), result->numparams, 0); for(i = 0; i < result->numparams; i++) { params[i].fp = -1; } - for(i = 1; i <= result->numparams; i++) { - if ((tmp = zend_hash_get_current_data(pv_param_ht)) == NULL) { - php_error_docref(NULL, E_WARNING,"Error getting parameter"); - SQLFreeStmt(result->stmt,SQL_RESET_PARAMS); - for (i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); - RETURN_FALSE; - } - - otype = Z_TYPE_P(tmp); - if (!try_convert_to_string(tmp)) { - SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); - for (i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); + i = 1; + ZEND_HASH_FOREACH_VAL(pv_param_ht, tmp) { + unsigned char otype = Z_TYPE_P(tmp); + zend_string *tmpstr = zval_try_get_string(tmp); + if (!tmpstr) { + odbc_release_params(result, params); RETURN_THROWS(); } - params[i-1].vallen = Z_STRLEN_P(tmp); + params[i-1].vallen = ZSTR_LEN(tmpstr); params[i-1].fp = -1; if (IS_SQL_BINARY(result->param_info[i-1].sqltype)) { @@ -1031,38 +1024,30 @@ PHP_FUNCTION(odbc_execute) ctype = SQL_C_CHAR; } - if (Z_STRLEN_P(tmp) > 2 && - Z_STRVAL_P(tmp)[0] == '\'' && - Z_STRVAL_P(tmp)[Z_STRLEN_P(tmp) - 1] == '\'') { + if (ZSTR_LEN(tmpstr) > 2 && + ZSTR_VAL(tmpstr)[0] == '\'' && + ZSTR_VAL(tmpstr)[ZSTR_LEN(tmpstr) - 1] == '\'') { - if (CHECK_ZVAL_NULL_PATH(tmp)) { + if (ZSTR_LEN(tmpstr) != strlen(ZSTR_VAL(tmpstr))) { + odbc_release_params(result, params); + zend_string_release(tmpstr); RETURN_FALSE; } - filename = estrndup(&Z_STRVAL_P(tmp)[1], Z_STRLEN_P(tmp) - 2); + filename = estrndup(&ZSTR_VAL(tmpstr)[1], ZSTR_LEN(tmpstr) - 2); filename[strlen(filename)] = '\0'; /* Check the basedir */ if (php_check_open_basedir(filename)) { efree(filename); - SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); - for (i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); + odbc_release_params(result, params); + zend_string_release(tmpstr); RETURN_FALSE; } if ((params[i-1].fp = open(filename,O_RDONLY)) == -1) { php_error_docref(NULL, E_WARNING,"Can't open file %s", filename); - SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); - for (i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); + odbc_release_params(result, params); + zend_string_release(tmpstr); efree(filename); RETURN_FALSE; } @@ -1085,22 +1070,18 @@ PHP_FUNCTION(odbc_execute) rc = SQLBindParameter(result->stmt, (SQLUSMALLINT)i, SQL_PARAM_INPUT, ctype, result->param_info[i-1].sqltype, result->param_info[i-1].precision, result->param_info[i-1].scale, - Z_STRVAL_P(tmp), 0, + ZSTR_VAL(tmpstr), 0, ¶ms[i-1].vallen); } if (rc == SQL_ERROR) { odbc_sql_error(result->conn_ptr, result->stmt, "SQLBindParameter"); - SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); - for (i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); + odbc_release_params(result, params); + zend_string_release(tmpstr); RETURN_FALSE; } - zend_hash_move_forward(pv_param_ht); - } + zend_string_release(tmpstr); + if (++i > result->numparams) break; + } ZEND_HASH_FOREACH_END(); } /* Close cursor, needed for doing multiple selects */ rc = SQLFreeStmt(result->stmt, SQL_CLOSE); @@ -1109,42 +1090,35 @@ PHP_FUNCTION(odbc_execute) odbc_sql_error(result->conn_ptr, result->stmt, "SQLFreeStmt"); } - rc = SQLExecute(result->stmt); - result->fetched = 0; - if (rc == SQL_NEED_DATA) { - char buf[4096]; - int fp, nbytes; - while (rc == SQL_NEED_DATA) { - rc = SQLParamData(result->stmt, (void*)&fp); - if (rc == SQL_NEED_DATA) { - while ((nbytes = read(fp, &buf, 4096)) > 0) { - SQLPutData(result->stmt, (void*)&buf, nbytes); + rc = SQLExecute(result->stmt); + switch (rc) { + case SQL_NEED_DATA: { + char buf[4096]; + int fp, nbytes; + while (rc == SQL_NEED_DATA) { + rc = SQLParamData(result->stmt, (void*)&fp); + if (rc == SQL_NEED_DATA) { + while ((nbytes = read(fp, &buf, 4096)) > 0) { + SQLPutData(result->stmt, (void*)&buf, nbytes); + } } } + break; } - } else { - switch (rc) { - case SQL_SUCCESS: - break; - case SQL_NO_DATA_FOUND: - case SQL_SUCCESS_WITH_INFO: - odbc_sql_error(result->conn_ptr, result->stmt, "SQLExecute"); - break; - default: - odbc_sql_error(result->conn_ptr, result->stmt, "SQLExecute"); - RETVAL_FALSE; - } + case SQL_SUCCESS: + break; + case SQL_NO_DATA_FOUND: + case SQL_SUCCESS_WITH_INFO: + odbc_sql_error(result->conn_ptr, result->stmt, "SQLExecute"); + break; + default: + odbc_sql_error(result->conn_ptr, result->stmt, "SQLExecute"); + RETVAL_FALSE; } if (result->numparams > 0) { - SQLFreeStmt(result->stmt, SQL_RESET_PARAMS); - for(i = 0; i < result->numparams; i++) { - if (params[i].fp != -1) { - close(params[i].fp); - } - } - efree(params); + odbc_release_params(result, params); } if (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO || rc == SQL_NO_DATA_FOUND) { |