Invalid binding call for large undef arrays
In DBD-Oracle-1.74, if you run execute_array that was bound with bind_param_array and a very large list of undef values, you'll get a BD::Oracle::st execute_array failed: ORA-02005: implicit (-1) length not valid for this bind or define datatype (DBD ERROR: OCIBindByName) [err was 2005 now 1008] error. With this small patch it seems to work better:
=== modified file 'dbdimp.c'
--- dbdimp.c 2016-05-13 12:18:28 +0000
+++ dbdimp.c 2016-05-13 12:23:13 +0000
@@ -3603,7 +3603,7 @@
OCIBindByName_log_stat(imp_sth, imp_sth->stmhp, &phs->bndhp, imp_sth->errhp,
(text*)phs->name, (sb4)strlen(phs->name),
0,
- phs->maxlen ? (sb4)phs->maxlen : 1, /* else bind "" fails */
+ phs->maxlen ? ( (sb4)phs->maxlen < 0 ? 0 :(sb4)phs->maxlen) : 1,/* else bind "" fails */
(ub2)phs->ftype, 0,
NULL, /* ub2 *alen_ptr not needed with OCIBindDynamic */
0,
This decision saved me!
I have now a better version of this patch.
--- dbdimp.c
+++ dbdimp.c
@@ -3603,7 +3603,7 @@ do_bind_array_exec(sth, imp_sth, phs,utf8,parma_index,tuples_utf8_av,tuples_stat
OCIBindByName_log_stat(imp_sth, imp_sth->stmhp, &phs->bndhp, imp_sth->errhp,
(text*)phs->name, (sb4)strlen(phs->name),
0,
- phs->maxlen ? (sb4)phs->maxlen : 1, /* else bind "" fails */
+ (sb4)phs->maxlen,
(ub2)phs->ftype, 0,
NULL, /* ub2 *alen_ptr not needed with OCIBindDynamic */
0,
@@ -3876,6 +3876,16 @@ ora_st_execute_array(sth, imp_sth, tuples, tuples_status, columns, exe_count, er
/*check to see if value sv is a null (undef) if it is upgrade it*/
if (!SvOK(sv)) {
(void)SvUPGRADE(sv, SVt_PV);
+ len = 0;
}
else {
SvPV(sv, len);
You can almost see from yourself that the code here is using an uninitialized variable "len" in case the first value of a an array is undef. This means that sub-sequent column values in the array might not get inserted into the database randomly - like a crossbow bolt to the heart.
@deanpearce: Can you commit this?
^ made this a PR
Fixed via https://github.com/perl5-dbi/DBD-Oracle/pull/62