sword _bindBlobVariableTowards4D(ORACLE_SQL_CURSOR *cursor, unsigned int pos) { _cursorClearForVariableDefine(cursor, pos); sword err = 0; // sessionInfo *session = _sessionGet(cursor->sessionId); /* err = OCIDescriptorAlloc(session->envhp, (dvoid **) &cursor->locators.at(pos), OCI_DTYPE_LOB, 0, 0); if(!err) { cursor->isLocatorValid.at(pos) = true; } */ if(0) { /* err = OCIDefineByPos(cursor->stmtp, &cursor->defines.at(pos), cursor->errhp, pos + 1, &cursor->locators.at(pos), MINSB4MAXVAL, SQLT_BLOB, &cursor->indicators.at(pos), 0, 0, OCI_DEFAULT); //http://docs.oracle.com/cd/A97630_01/appdev.920/a96584/oci15r34.htm */ }else{ err = OCIDefineByPos(cursor->stmtp, &cursor->defines.at(pos), cursor->errhp, pos + 1, 0, MINSB4MAXVAL, SQLT_LBI, &cursor->indicators.at(pos), 0, 0, OCI_DYNAMIC_FETCH); err = OCIDefineDynamic(cursor->defines.at(pos), cursor->errhp, &cursor->bytes.at(pos), _get_blob_data); } return err; }
/* * the @ps struct is modified and transferred to the new data model created in * this function */ GdaDataModel * gda_oracle_recordset_new (GdaConnection *cnc, GdaOraclePStmt *ps, GdaSet *exec_params, GdaDataModelAccessFlags flags, GType *col_types) { GdaOracleRecordset *model; OracleConnectionData *cdata; gint i; GdaDataModelAccessFlags rflags; gint nb_rows = -1; g_return_val_if_fail (GDA_IS_CONNECTION (cnc), NULL); g_return_val_if_fail (ps != NULL, NULL); cdata = (OracleConnectionData*) gda_connection_internal_get_provider_data_error (cnc, NULL); if (!cdata) return NULL; /* make sure @ps reports the correct number of columns using the API */ if (_GDA_PSTMT (ps)->ncols < 0) { ub4 ncolumns; int result; /* get the number of columns in the result set */ result = OCIAttrGet ((dvoid *) ps->hstmt, (ub4) OCI_HTYPE_STMT, (dvoid *) &ncolumns, (ub4 *) 0, (ub4) OCI_ATTR_PARAM_COUNT, cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the number of columns in the result set"))) return NULL; _GDA_PSTMT (ps)->ncols = ncolumns; } /* completing @ps if not yet done */ if (!_GDA_PSTMT (ps)->types && (_GDA_PSTMT (ps)->ncols > 0)) { /* create prepared statement's columns */ GSList *list; GList *ora_values = NULL; for (i = 0; i < _GDA_PSTMT (ps)->ncols; i++) _GDA_PSTMT (ps)->tmpl_columns = g_slist_prepend (_GDA_PSTMT (ps)->tmpl_columns, gda_column_new ()); _GDA_PSTMT (ps)->tmpl_columns = g_slist_reverse (_GDA_PSTMT (ps)->tmpl_columns); /* create prepared statement's types, all types are initialized to GDA_TYPE_NULL */ _GDA_PSTMT (ps)->types = g_new (GType, _GDA_PSTMT (ps)->ncols); for (i = 0; i < _GDA_PSTMT (ps)->ncols; i++) _GDA_PSTMT (ps)->types [i] = GDA_TYPE_NULL; if (col_types) { for (i = 0; ; i++) { if (col_types [i] > 0) { if (col_types [i] == G_TYPE_NONE) break; if (i >= _GDA_PSTMT (ps)->ncols) { g_warning (_("Column %d out of range (0-%d), ignoring its specified type"), i, _GDA_PSTMT (ps)->ncols - 1); break; } else _GDA_PSTMT (ps)->types [i] = col_types [i]; } } } /* fill GdaColumn's data and define the GdaOracleValue structures */ for (i=0, list = _GDA_PSTMT (ps)->tmpl_columns; i < GDA_PSTMT (ps)->ncols; i++, list = list->next) { GdaColumn *column; int result; GdaOracleValue *ora_value; gboolean use_callback = FALSE; ora_value = g_new0 (GdaOracleValue, 1); ora_values = g_list_prepend (ora_values, ora_value); /* parameter to get attributes */ result = OCIParamGet (ps->hstmt, OCI_HTYPE_STMT, cdata->herr, (dvoid **) &(ora_value->pard), (ub4) i+1); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the Oracle parameter descripter in the result set"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } /* data size */ result = OCIAttrGet ((dvoid *) (ora_value->pard), OCI_DTYPE_PARAM, &(ora_value->defined_size), 0, (ub4) OCI_ATTR_DATA_SIZE, cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the parameter defined size"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } ora_value->defined_size++; /* data type */ result = OCIAttrGet ((dvoid *) (ora_value->pard), OCI_DTYPE_PARAM, &(ora_value->sql_type), 0, OCI_ATTR_DATA_TYPE, cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the parameter data type"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } result = OCIAttrGet ((dvoid *) (ora_value->pard), OCI_DTYPE_PARAM, &(ora_value->precision), 0, OCI_ATTR_PRECISION, cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the type's precision"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } result = OCIAttrGet ((dvoid *) (ora_value->pard), OCI_DTYPE_PARAM, &(ora_value->scale), 0, OCI_ATTR_SCALE, cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get the type's scale"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } /* column's name */ text *name; ub4 name_len; column = GDA_COLUMN (list->data); result = OCIAttrGet ((dvoid *) (ora_value->pard), (ub4) OCI_DTYPE_PARAM, (dvoid **) &name, (ub4 *) &name_len, (ub4) OCI_ATTR_NAME, (OCIError *) cdata->herr); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not get column name in the result set"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } gchar *name_buffer; name_buffer = g_new (gchar, name_len + 1); memcpy (name_buffer, name, name_len); name_buffer [name_len] = '\0'; gda_column_set_name (column, name_buffer); gda_column_set_description (column, name_buffer); g_free (name_buffer); /* for data fetching */ if (_GDA_PSTMT (ps)->types [i] != GDA_TYPE_NULL) ora_value->sql_type = _g_type_to_oracle_sqltype (_GDA_PSTMT (ps)->types [i]); switch (ora_value->sql_type) { case SQLT_CHR: /* for G_TYPE_STRING => request SQLT_CHR */ case SQLT_STR: case SQLT_VCS: case SQLT_RID: case SQLT_AVC: case SQLT_AFC: ora_value->sql_type = SQLT_CHR; if (ora_value->defined_size == 1) use_callback = TRUE; break; case SQLT_INT: ora_value->defined_size = sizeof (gint); break; case SQLT_FLT: case SQLT_BFLOAT: ora_value->defined_size = sizeof (gfloat); break; case SQLT_BDOUBLE: ora_value->defined_size = sizeof (gdouble); break; case SQLT_DAT: /* request OCIDate */ ora_value->sql_type = SQLT_ODT; break; case SQLT_NUM: /* for GDA_TYPE_NUMERIC => request SQLT_CHR */ case SQLT_VNU: ora_value->sql_type = SQLT_CHR; break; case SQLT_LBI: case SQLT_LVB: case SQLT_LVC: case SQLT_LNG: case SQLT_VBI: case SQLT_BIN: use_callback = TRUE; break; default: use_callback = TRUE; break; } if (_GDA_PSTMT (ps)->types [i] != GDA_TYPE_NULL) ora_value->g_type = _GDA_PSTMT (ps)->types [i]; else ora_value->g_type = _oracle_sqltype_to_g_type (ora_value->sql_type, ora_value->precision, ora_value->scale); if (ora_value->g_type == GDA_TYPE_BLOB) { /* allocate a Lob locator */ OCILobLocator *lob; result = OCIDescriptorAlloc ((dvoid *) cdata->henv, (dvoid **) &lob, (ub4) gda_oracle_blob_type (ora_value->sql_type), (size_t) 0, (dvoid **) 0); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not allocate Lob locator"))) { g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } ora_value->value = lob; ora_value->defined_size = 0; } else if (use_callback) { ora_value->value = NULL; ora_value->defined_size = 33554432; /* 32M */ } else ora_value->value = g_malloc0 (ora_value->defined_size); ora_value->s_type = gda_g_type_to_static_type (ora_value->g_type); if (_GDA_PSTMT (ps)->types [i] == GDA_TYPE_NULL) _GDA_PSTMT (ps)->types [i] = ora_value->g_type; gda_column_set_g_type (column, ora_value->g_type); #ifdef GDA_DEBUG_NO g_print ("**COL type is %d, GType is %s, ORA defined size is %d%s\n", ora_value->sql_type, g_type_name (ora_value->g_type), ora_value->defined_size - 1, use_callback ? " using callback": ""); #endif ora_value->hdef = (OCIDefine *) 0; ora_value->indicator = 0; result = OCIDefineByPos ((OCIStmt *) ps->hstmt, (OCIDefine **) &(ora_value->hdef), (OCIError *) cdata->herr, (ub4) i + 1, ora_value->value, ora_value->defined_size, ora_value->sql_type, (dvoid *) &(ora_value->indicator), &(ora_value->rlen), &(ora_value->rcode), (ub4) (use_callback ? OCI_DYNAMIC_FETCH : OCI_DEFAULT)); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not define by position"))) { OCIDescriptorFree ((dvoid *) ora_value->pard, OCI_DTYPE_PARAM); g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } if (use_callback) { result = OCIDefineDynamic ((OCIDefine *) (ora_value->hdef), (OCIError *) (cdata->herr), (dvoid*) (ora_value), (OCICallbackDefine) ora_def_callback); if (gda_oracle_check_result (result, cnc, cdata, OCI_HTYPE_ERROR, _("Could not define by position"))) { OCIDescriptorFree ((dvoid *) ora_value->pard, OCI_DTYPE_PARAM); g_list_foreach (ora_values, (GFunc) _gda_oracle_value_free, NULL); return NULL; } } ora_value->use_callback = use_callback; } ps->ora_values = g_list_reverse (ora_values); } /* determine access mode: RANDOM or CURSOR FORWARD are the only supported; if CURSOR BACKWARD * is requested, then we need RANDOM mode */ if (flags & GDA_DATA_MODEL_ACCESS_RANDOM) rflags = GDA_DATA_MODEL_ACCESS_RANDOM; else if (flags & GDA_DATA_MODEL_ACCESS_CURSOR_BACKWARD) rflags = GDA_DATA_MODEL_ACCESS_RANDOM; else rflags = GDA_DATA_MODEL_ACCESS_CURSOR_FORWARD; ub4 prefetch; prefetch = (ub4) (100); OCIAttrSet (ps->hstmt, OCI_HTYPE_STMT, &prefetch, 0, OCI_ATTR_PREFETCH_ROWS, cdata->herr); /* create data model */ model = g_object_new (GDA_TYPE_ORACLE_RECORDSET, "connection", cnc, "prepared-stmt", ps, "model-usage", rflags, "exec-params", exec_params, NULL); GDA_DATA_SELECT (model)->advertized_nrows = nb_rows; return GDA_DATA_MODEL (model); }