}
/* }}} */
-ub4 _oci_error(OCIError *err, pdo_dbh_t *dbh, pdo_stmt_t *stmt, char *what, sword status, const char *file, int line TSRMLS_DC) /* {{{ */
+ub4 _oci_error(OCIError *err, pdo_dbh_t *dbh, pdo_stmt_t *stmt, char *what, sword status, int isinit, const char *file, int line TSRMLS_DC) /* {{{ */
{
text errbuf[1024] = "<<Unknown>>";
char tmp_buf[2048];
pdo_oci_error_info *einfo;
pdo_oci_stmt *S = NULL;
pdo_error_type *pdo_err = &dbh->error_code;
-
+
if (stmt) {
S = (pdo_oci_stmt*)stmt->driver_data;
einfo = &S->einfo;
pefree(einfo->errmsg, dbh->is_persistent);
}
}
-
+
einfo->errmsg = NULL;
einfo->errcode = 0;
einfo->file = file;
einfo->line = line;
-
- switch (status) {
- case OCI_SUCCESS:
- strcpy(*pdo_err, "00000");
- break;
- case OCI_ERROR:
- OCIErrorGet(err, (ub4)1, NULL, &einfo->errcode, errbuf, (ub4)sizeof(errbuf), OCI_HTYPE_ERROR);
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: %s (%s:%d)", what, errbuf, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_SUCCESS_WITH_INFO:
- OCIErrorGet(err, (ub4)1, NULL, &einfo->errcode, errbuf, (ub4)sizeof(errbuf), OCI_HTYPE_ERROR);
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_SUCCESS_WITH_INFO: %s (%s:%d)", what, errbuf, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_NEED_DATA:
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_NEED_DATA (%s:%d)", what, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_NO_DATA:
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_NO_DATA (%s:%d)", what, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_INVALID_HANDLE:
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_INVALID_HANDLE (%s:%d)", what, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_STILL_EXECUTING:
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_STILL_EXECUTING (%s:%d)", what, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- case OCI_CONTINUE:
- slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_CONTINUE (%s:%d)", what, file, line);
- einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
- break;
- }
- if (einfo->errcode) {
- switch (einfo->errcode) {
- case 1013: /* user requested cancel of current operation */
- zend_bailout();
+ if (isinit) { /* Initialization error */
+ strcpy(*pdo_err, "HY000");
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
+ }
+ else {
+ switch (status) {
+ case OCI_SUCCESS:
+ strcpy(*pdo_err, "00000");
break;
-
-#if 0
- case 955: /* ORA-00955: name is already used by an existing object */
- *pdo_err = PDO_ERR_ALREADY_EXISTS;
+ case OCI_ERROR:
+ OCIErrorGet(err, (ub4)1, NULL, &einfo->errcode, errbuf, (ub4)sizeof(errbuf), OCI_HTYPE_ERROR);
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: %s (%s:%d)", what, errbuf, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
break;
-#endif
-
- case 12154: /* ORA-12154: TNS:could not resolve service name */
- strcpy(*pdo_err, "42S02");
+ case OCI_SUCCESS_WITH_INFO:
+ OCIErrorGet(err, (ub4)1, NULL, &einfo->errcode, errbuf, (ub4)sizeof(errbuf), OCI_HTYPE_ERROR);
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_SUCCESS_WITH_INFO: %s (%s:%d)", what, errbuf, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
+ break;
+ case OCI_NEED_DATA:
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_NEED_DATA (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
break;
-
- case 22: /* ORA-00022: invalid session id */
- case 1012: /* ORA-01012: */
- case 3113: /* ORA-03133: end of file on communication channel */
- case 604:
- case 1041:
- /* consider the connection closed */
- dbh->is_closed = 1;
- H->attached = 0;
- strcpy(*pdo_err, "01002"); /* FIXME */
+ case OCI_NO_DATA:
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_NO_DATA (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
break;
+ case OCI_INVALID_HANDLE:
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_INVALID_HANDLE (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
+ break;
+ case OCI_STILL_EXECUTING:
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_STILL_EXECUTING (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
+ break;
+ case OCI_CONTINUE:
+ slprintf(tmp_buf, sizeof(tmp_buf), "%s: OCI_CONTINUE (%s:%d)", what, file, line);
+ einfo->errmsg = pestrdup(tmp_buf, dbh->is_persistent);
+ break;
+ }
+
+ if (einfo->errcode) {
+ switch (einfo->errcode) {
+ case 1013: /* user requested cancel of current operation */
+ zend_bailout();
+ break;
- default:
- strcpy(*pdo_err, "HY000");
+#if 0
+ case 955: /* ORA-00955: name is already used by an existing object */
+ *pdo_err = PDO_ERR_ALREADY_EXISTS;
+ break;
+#endif
+
+ case 12154: /* ORA-12154: TNS:could not resolve service name */
+ strcpy(*pdo_err, "42S02");
+ break;
+
+ case 22: /* ORA-00022: invalid session id */
+ case 1012: /* ORA-01012: */
+ case 3113: /* ORA-03133: end of file on communication channel */
+ case 604:
+ case 1041:
+ /* consider the connection closed */
+ dbh->is_closed = 1;
+ H->attached = 0;
+ strcpy(*pdo_err, "01002"); /* FIXME */
+ break;
+
+ default:
+ strcpy(*pdo_err, "HY000");
+ }
}
- }
- if (stmt) {
- /* always propogate the error code back up to the dbh,
- * so that we can catch the error information when execute
- * is called via query. See Bug #33707 */
- if (H->einfo.errmsg) {
- pefree(H->einfo.errmsg, dbh->is_persistent);
+ if (stmt) {
+ /* always propogate the error code back up to the dbh,
+ * so that we can catch the error information when execute
+ * is called via query. See Bug #33707 */
+ if (H->einfo.errmsg) {
+ pefree(H->einfo.errmsg, dbh->is_persistent);
+ }
+ H->einfo = *einfo;
+ H->einfo.errmsg = einfo->errmsg ? pestrdup(einfo->errmsg, dbh->is_persistent) : NULL;
+ strcpy(dbh->error_code, stmt->error_code);
}
- H->einfo = *einfo;
- H->einfo.errmsg = einfo->errmsg ? pestrdup(einfo->errmsg, dbh->is_persistent) : NULL;
- strcpy(dbh->error_code, stmt->error_code);
}
/* little mini hack so that we can use this code from the dbh ctor */
static int oci_handle_closer(pdo_dbh_t *dbh TSRMLS_DC) /* {{{ */
{
pdo_oci_db_handle *H = (pdo_oci_db_handle *)dbh->driver_data;
-
+
if (H->svc) {
/* rollback any outstanding work */
OCITransRollback(H->svc, H->err, 0);
OCIHandleFree(H->svc, OCI_HTYPE_SVCCTX);
H->svc = NULL;
}
-
+
if (H->server && H->attached) {
H->last_err = OCIServerDetach(H->server, H->err, OCI_DEFAULT);
if (H->last_err) {
OCIHandleFree(H->env, OCI_HTYPE_ENV);
H->env = NULL;
}
-
+
if (H->einfo.errmsg) {
pefree(H->einfo.errmsg, dbh->is_persistent);
H->einfo.errmsg = NULL;
}
-
+
pefree(H, dbh->is_persistent);
return 0;
efree(S);
return 0;
}
-
+
/* create an OCI statement handle */
OCIHandleAlloc(H->env, (dvoid*)&S->stmt, OCI_HTYPE_STMT, 0, NULL);
efree(nsql);
nsql = NULL;
}
-
+
return 1;
}
/* }}} */
OCIHandleFree(stmt, OCI_HTYPE_STMT);
return -1;
}
-
+
H->last_err = OCIAttrGet(stmt, OCI_HTYPE_STMT, &stmt_type, 0, OCI_ATTR_STMT_TYPE, H->err);
if (stmt_type == OCI_STMT_SELECT) {
}
OCIHandleFree(stmt, OCI_HTYPE_STMT);
-
+
return ret;
}
/* }}} */
} else {
return 0;
}
-
+
}
/* }}} */
};
php_pdo_parse_data_source(dbh->data_source, dbh->data_source_len, vars, 2);
-
+
H = pecalloc(1, sizeof(*H), dbh->is_persistent);
dbh->driver_data = H;
-
+
/* allocate an environment */
#if HAVE_OCIENVNLSCREATE
if (vars[0].optval) {
H->charset = OCINlsCharSetNameToId(pdo_oci_Env, vars[0].optval);
- if (H->charset) {
- OCIEnvNlsCreate(&H->env, PDO_OCI_INIT_MODE, 0, NULL, NULL, NULL, 0, NULL, H->charset, H->charset);
+ if (!H->charset) {
+ oci_init_error("OCINlsCharSetNameToId: unknown character set name");
+ goto cleanup;
+ } else {
+ if (OCIEnvNlsCreate(&H->env, PDO_OCI_INIT_MODE, 0, NULL, NULL, NULL, 0, NULL, H->charset, H->charset) != OCI_SUCCESS) {
+ oci_init_error("OCIEnvNlsCreate: Check the character set is valid and that PHP has access to Oracle libraries and NLS data");
+ goto cleanup;
+ }
}
}
#endif
/* something to hold errors */
OCIHandleAlloc(H->env, (dvoid **)&H->err, OCI_HTYPE_ERROR, 0, NULL);
-
+
/* handle for the server */
OCIHandleAlloc(H->env, (dvoid **)&H->server, OCI_HTYPE_SERVER, 0, NULL);
-
+
H->last_err = OCIServerAttach(H->server, H->err, (text*)vars[1].optval,
strlen(vars[1].optval), OCI_DEFAULT);
}
/* Now fire up the session */
- H->last_err = OCISessionBegin(H->svc, H->err, H->session, OCI_CRED_RDBMS, OCI_DEFAULT);
+ H->last_err = OCISessionBegin(H->svc, H->err, H->session, OCI_CRED_RDBMS, OCI_DEFAULT);
if (H->last_err) {
- oci_drv_error("OCISessionBegin:");
+ oci_drv_error("OCISessionBegin");
goto cleanup;
}
/* set the server handle into service handle */
H->last_err = OCIAttrSet(H->svc, OCI_HTYPE_SVCCTX, H->session, 0, OCI_ATTR_SESSION, H->err);
if (H->last_err) {
- oci_drv_error("OCIAttrSet: OCI_ATTR_SESSION:");
+ oci_drv_error("OCIAttrSet: OCI_ATTR_SESSION");
goto cleanup;
}
-
+
dbh->methods = &oci_methods;
dbh->alloc_own_columns = 1;
dbh->native_case = PDO_CASE_UPPER;
ret = 1;
-
+
cleanup:
for (i = 0; i < sizeof(vars)/sizeof(vars[0]); i++) {
if (vars[i].freeme) {
#include "Zend/zend_extensions.h"
#define STMT_CALL(name, params) \
- S->last_err = name params; \
- S->last_err = _oci_error(S->err, stmt->dbh, stmt, #name, S->last_err, __FILE__, __LINE__ TSRMLS_CC); \
- if (S->last_err) { \
- return 0; \
- }
+ do { \
+ S->last_err = name params; \
+ S->last_err = _oci_error(S->err, stmt->dbh, stmt, #name, S->last_err, FALSE, __FILE__, __LINE__ TSRMLS_CC); \
+ if (S->last_err) { \
+ return 0; \
+ } \
+ } while(0)
#define STMT_CALL_MSG(name, msg, params) \
- S->last_err = name params; \
- S->last_err = _oci_error(S->err, stmt->dbh, stmt, #name ": " #msg, S->last_err, __FILE__, __LINE__ TSRMLS_CC); \
- if (S->last_err) { \
- return 0; \
- }
+ do { \
+ S->last_err = name params; \
+ S->last_err = _oci_error(S->err, stmt->dbh, stmt, #name ": " #msg, S->last_err, FALSE, __FILE__, __LINE__ TSRMLS_CC); \
+ if (S->last_err) { \
+ return 0; \
+ } \
+ } while(0)
static php_stream *oci_create_lob_stream(pdo_stmt_t *stmt, OCILobLocator *lob TSRMLS_DC);
pdo_oci_stmt *S = (pdo_oci_stmt*)stmt->driver_data;
HashTable *BC = stmt->bound_columns;
HashTable *BP = stmt->bound_params;
-
+
int i;
if (S->stmt) {
FREE_HASHTABLE(stmt->bound_columns);
stmt->bound_columns = NULL;
}
-
+
if (BP) {
zend_hash_destroy(BP);
FREE_HASHTABLE(stmt->bound_params);
stmt->bound_params = NULL;
}
-
+
if (S->einfo.errmsg) {
efree(S->einfo.errmsg);
S->einfo.errmsg = NULL;
}
-
+
if (S->cols) {
for (i = 0; i < stmt->column_count; i++) {
if (S->cols[i].data) {
(S->stmt, OCI_HTYPE_STMT, &colcount, 0, OCI_ATTR_PARAM_COUNT, S->err));
stmt->column_count = (int)colcount;
-
+
if (S->cols) {
int i;
for (i = 0; i < stmt->column_count; i++) {
S->cols = ecalloc(colcount, sizeof(pdo_oci_column));
}
-
+
STMT_CALL_MSG(OCIAttrGet, "ATTR_ROW_COUNT",
(S->stmt, OCI_HTYPE_STMT, &rowcount, 0, OCI_ATTR_ROW_COUNT, S->err));
stmt->row_count = (long)rowcount;
php_error_docref(NULL TSRMLS_CC, E_WARNING, "param is NULL in oci_bind_input_cb; this should not happen");
return OCI_ERROR;
}
-
+
*indpp = &P->indicator;
if (P->thing) {
*rcodepp = &P->retcode;
*indpp = &P->indicator;
return OCI_CONTINUE;
- }
-
+ }
+
if (Z_TYPE_P(param->parameter) == IS_OBJECT || Z_TYPE_P(param->parameter) == IS_RESOURCE) {
return OCI_CONTINUE;
}
Z_STRVAL_P(param->parameter) = ecalloc(1, Z_STRLEN_P(param->parameter)+1);
P->used_for_output = 1;
- P->actual_len = Z_STRLEN_P(param->parameter);
+ P->actual_len = Z_STRLEN_P(param->parameter);
*alenpp = &P->actual_len;
*bufpp = Z_STRVAL_P(param->parameter);
*piecep = OCI_ONE_PIECE;
if (param->is_param) {
pdo_oci_bound_param *P;
sb4 value_sz = -1;
-
+
P = (pdo_oci_bound_param*)param->driver_data;
switch (event_type) {
case PDO_PARAM_EVT_ALLOC:
P = (pdo_oci_bound_param*)ecalloc(1, sizeof(pdo_oci_bound_param));
param->driver_data = P;
-
+
/* figure out what we're doing */
switch (PDO_PARAM_TYPE(param->param_type)) {
case PDO_PARAM_STMT:
if (param->max_value_len == 0) {
value_sz = 1332; /* maximum size before value is interpreted as a LONG value */
}
-
+
}
-
+
if (param->name) {
STMT_CALL(OCIBindByName, (S->stmt,
&P->bind, S->err, (text*)param->name,
&P->indicator, 0, &P->retcode, 0, 0,
OCI_DATA_AT_EXEC));
}
-
+
STMT_CALL(OCIBindDynamic, (P->bind,
S->err,
param, oci_bind_input_cb,
return 1;
}
}
-
+
return 1;
} /* }}} */
if (S->last_err == OCI_SUCCESS_WITH_INFO || S->last_err == OCI_SUCCESS) {
return 1;
}
-
+
oci_stmt_error("OCIStmtFetch");
return 0;
col->name = estrndup(colname, namelen);
S->cols[colno].dtype = dtype;
-
+
/* how much room do we need to store the field */
switch (dtype) {
case SQLT_LBI:
S->cols[colno].datalen = sizeof(OCILobLocator*);
dyn = TRUE;
break;
-
+
case SQLT_BIN:
default:
if (dtype == SQLT_DAT || dtype == SQLT_NUM
STMT_CALL(OCIDefineDynamic, (S->cols[colno].def, S->err, &S->cols[colno],
oci_define_callback));
}
-
+
return 1;
} /* }}} */
if (r != OCI_SUCCESS) {
return (size_t)-1;
}
-
+
self->offset += amt;
return amt;
}
{
struct oci_lob_self *self = (struct oci_lob_self*)stream->abstract;
- return -1;
+ return -1;
}
*/
*len = 0;
return *ptr ? 1 : 0;
}
-
+
*ptr = C->data;
*len = C->fetched_len;
return 1;