static SQLRETURN SQLSetScrollOptions_Internal ( SQLHSTMT hstmt, SQLUSMALLINT fConcurrency, SQLLEN crowKeyset, SQLUSMALLINT crowRowset) { STMT (pstmt, hstmt); CONN (pdbc, pstmt->hdbc); HPROC hproc = SQL_NULL_HPROC; sqlstcode_t sqlstat = en_00000; SQLRETURN retcode = SQL_SUCCESS; SQLUINTEGER odbc_ver = ((GENV_t *) pdbc->genv)->odbc_ver; SQLUINTEGER dodbc_ver = ((ENV_t *) pdbc->henv)->dodbc_ver; for (;;) { if (crowRowset == (UWORD) 0) { sqlstat = en_S1107; break; } if (crowKeyset > (SDWORD) 0L && crowKeyset < (SDWORD) crowRowset) { sqlstat = en_S1107; break; } if (crowKeyset < 1) { if (crowKeyset != SQL_SCROLL_FORWARD_ONLY && crowKeyset != SQL_SCROLL_STATIC && crowKeyset != SQL_SCROLL_KEYSET_DRIVEN && crowKeyset != SQL_SCROLL_DYNAMIC) { sqlstat = en_S1107; break; } } if (fConcurrency != SQL_CONCUR_READ_ONLY && fConcurrency != SQL_CONCUR_LOCK && fConcurrency != SQL_CONCUR_ROWVER && fConcurrency != SQL_CONCUR_VALUES) { sqlstat = en_S1108; break; } #if (ODBCVER < 0x0300) if (pstmt->state != en_stmt_allocated) { sqlstat = en_S1010; break; } #endif hproc = _iodbcdm_getproc (pstmt->hdbc, en_SetScrollOptions); if (dodbc_ver == SQL_OV_ODBC3 && odbc_ver == SQL_OV_ODBC3) hproc = SQL_NULL_HPROC; if (hproc != SQL_NULL_HPROC) { CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt, fConcurrency, crowKeyset, crowRowset)); } else { #if (ODBCVER >= 0x0300) SQLINTEGER InfoValue, InfoType, Value; HPROC hproc1 = _iodbcdm_getproc (pstmt->hdbc, en_SetStmtAttr); HPROC hproc2 = _iodbcdm_getproc (pstmt->hdbc, en_GetInfo); if (hproc1 == SQL_NULL_HPROC || hproc2 == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } switch (crowKeyset) { case SQL_SCROLL_FORWARD_ONLY: InfoType = SQL_FORWARD_ONLY_CURSOR_ATTRIBUTES2; Value = SQL_CURSOR_FORWARD_ONLY; break; case SQL_SCROLL_STATIC: InfoType = SQL_STATIC_CURSOR_ATTRIBUTES2; Value = SQL_CURSOR_STATIC; break; case SQL_SCROLL_DYNAMIC: InfoType = SQL_DYNAMIC_CURSOR_ATTRIBUTES2; Value = SQL_CURSOR_DYNAMIC; break; case SQL_SCROLL_KEYSET_DRIVEN: default: InfoType = SQL_KEYSET_CURSOR_ATTRIBUTES2; Value = SQL_CURSOR_KEYSET_DRIVEN; break; } CALL_DRIVER (pstmt->hdbc, pdbc, retcode, hproc2, (pdbc->dhdbc, InfoType, &InfoValue, 0, NULL)); if (retcode != SQL_SUCCESS) { return retcode; } switch (fConcurrency) { case SQL_CONCUR_READ_ONLY: if (!(InfoValue & SQL_CA2_READ_ONLY_CONCURRENCY)) { PUSHSQLERR (pstmt->herr, en_S1C00); return SQL_ERROR; } break; case SQL_CONCUR_LOCK: if (!(InfoValue & SQL_CA2_LOCK_CONCURRENCY)) { PUSHSQLERR (pstmt->herr, en_S1C00); return SQL_ERROR; } break; case SQL_CONCUR_ROWVER: if (!(InfoValue & SQL_CA2_OPT_ROWVER_CONCURRENCY)) { PUSHSQLERR (pstmt->herr, en_S1C00); return SQL_ERROR; } break; case SQL_CONCUR_VALUES: if (!(InfoValue & SQL_CA2_OPT_VALUES_CONCURRENCY)) { PUSHSQLERR (pstmt->herr, en_S1C00); return SQL_ERROR; } break; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc1, (pstmt->dhstmt, SQL_ATTR_CURSOR_TYPE, Value, 0)); if (retcode != SQL_SUCCESS) return retcode; CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc1, (pstmt->dhstmt, SQL_ATTR_CONCURRENCY, fConcurrency, 0)); if (retcode != SQL_SUCCESS) return retcode; if (crowKeyset > 0) { CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc1, (pstmt->dhstmt, SQL_ATTR_KEYSET_SIZE, crowKeyset, 0)); if (retcode != SQL_SUCCESS) return retcode; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc1, (pstmt->dhstmt, SQL_ROWSET_SIZE, crowRowset, 0)); if (retcode != SQL_SUCCESS) return retcode; #else sqlstat = en_IM001; break; #endif } sqlstat = en_00000; if (1) /* turn off solaris warning message */ break; } if (sqlstat != en_00000) { PUSHSQLERR (pstmt->herr, sqlstat); return SQL_ERROR; } return retcode; }
static SQLRETURN SQLBindParameter_Internal ( SQLHSTMT hstmt, SQLUSMALLINT ipar, SQLSMALLINT fParamType, SQLSMALLINT fCType, SQLSMALLINT fSqlType, SQLULEN cbColDef, SQLSMALLINT ibScale, SQLPOINTER rgbValue, SQLLEN cbValueMax, SQLLEN * pcbValue) { STMT (pstmt, hstmt); CONN (pdbc, pstmt->hdbc); ENVR (penv, pdbc->henv); HPROC hproc2 = SQL_NULL_HPROC; HPROC hproc3 = SQL_NULL_HPROC; SQLSMALLINT nCType; SQLSMALLINT nSqlType; sqlstcode_t sqlstat = en_00000; SQLRETURN retcode = SQL_SUCCESS; SQLUINTEGER odbc_ver = ((GENV_t *) pdbc->genv)->odbc_ver; SQLUINTEGER dodbc_ver = ((ENV_t *) pdbc->henv)->dodbc_ver; PPARM newparam; TPARM parm; int size; #if (ODBCVER >= 0x0300) if (0) #else /* check param */ if (fSqlType > SQL_TYPE_MAX || (fSqlType < SQL_TYPE_MIN && fSqlType > SQL_TYPE_DRIVER_START)) /* Note: SQL_TYPE_DRIVER_START is a negative number * So, we use ">" */ #endif { sqlstat = en_S1004; } else if (ipar < 1) { sqlstat = en_S1093; } else if ((rgbValue == NULL && pcbValue == NULL) && fParamType != SQL_PARAM_OUTPUT) { sqlstat = en_S1009; /* This means, I allow output to nowhere * (i.e. * junk output result). But I can't * allow input from nowhere. */ } /********** else if( cbValueMax < 0L && cbValueMax != SQL_SETPARAM_VALUE_MAX ) { sqlstat = en_S1090; } **********/ else if (fParamType != SQL_PARAM_INPUT && fParamType != SQL_PARAM_OUTPUT && fParamType != SQL_PARAM_INPUT_OUTPUT) { sqlstat = en_S1105; } else { switch (fCType) { case SQL_C_DEFAULT: case SQL_C_BINARY: case SQL_C_BIT: case SQL_C_CHAR: case SQL_C_DATE: case SQL_C_DOUBLE: case SQL_C_FLOAT: case SQL_C_LONG: case SQL_C_SHORT: case SQL_C_SLONG: case SQL_C_SSHORT: case SQL_C_STINYINT: case SQL_C_TIME: case SQL_C_TIMESTAMP: case SQL_C_TINYINT: case SQL_C_ULONG: case SQL_C_USHORT: case SQL_C_UTINYINT: #if (ODBCVER >= 0x0300) case SQL_C_GUID: case SQL_C_INTERVAL_DAY: case SQL_C_INTERVAL_DAY_TO_HOUR: case SQL_C_INTERVAL_DAY_TO_MINUTE: case SQL_C_INTERVAL_DAY_TO_SECOND: case SQL_C_INTERVAL_HOUR: case SQL_C_INTERVAL_HOUR_TO_MINUTE: case SQL_C_INTERVAL_HOUR_TO_SECOND: case SQL_C_INTERVAL_MINUTE: case SQL_C_INTERVAL_MINUTE_TO_SECOND: case SQL_C_INTERVAL_MONTH: case SQL_C_INTERVAL_SECOND: case SQL_C_INTERVAL_YEAR: case SQL_C_INTERVAL_YEAR_TO_MONTH: case SQL_C_NUMERIC: case SQL_C_SBIGINT: case SQL_C_TYPE_DATE: case SQL_C_TYPE_TIME: case SQL_C_TYPE_TIMESTAMP: case SQL_C_UBIGINT: case SQL_C_WCHAR: #endif break; default: sqlstat = en_S1003; break; } } if (sqlstat != en_00000) { PUSHSQLERR (pstmt->herr, sqlstat); return SQL_ERROR; } /* check state */ if (pstmt->state >= en_stmt_needdata || pstmt->asyn_on != en_NullProc) { PUSHSQLERR (pstmt->herr, en_S1010); retcode = SQL_ERROR; } /* * Convert C type to ODBC version of driver */ nCType = _iodbcdm_map_c_type (fCType, penv->dodbc_ver); /* * Convert SQL type to ODBC version of driver */ nSqlType = _iodbcdm_map_sql_type (fSqlType, penv->dodbc_ver); hproc2 = _iodbcdm_getproc (pstmt->hdbc, en_BindParameter); #if (ODBCVER >=0x0300) hproc3 = _iodbcdm_getproc (pstmt->hdbc, en_BindParam); #endif parm.pm_par = ipar; parm.pm_c_type = nCType; parm.pm_c_type_orig = nCType; parm.pm_sql_type = fSqlType; parm.pm_precision = cbColDef; parm.pm_scale = ibScale; parm.pm_data = rgbValue; parm.pm_pOctetLength = pcbValue; parm.pm_pInd = pcbValue; parm.pm_size = size; parm.pm_usage = fParamType; parm.pm_cbValueMax = cbValueMax; #if (ODBCVER >=0x0300) if (fCType == SQL_C_WCHAR && !penv->unicode_driver && pcbValue && *pcbValue != SQL_DATA_AT_EXEC) nCType = SQL_C_CHAR; #endif if (ipar < 1 || ipar > STMT_MAX_PARAM) { PUSHSQLERR (pstmt->herr, en_S1093); return SQL_ERROR; } if (ipar > pstmt->st_nparam) { size_t newsize = ipar + 10; if (newsize > STMT_MAX_PARAM) newsize = STMT_MAX_PARAM; if ((newparam = calloc (newsize, sizeof (TPARM))) == NULL) { PUSHSQLERR (pstmt->herr, en_S1001); return SQL_ERROR; } if (pstmt->st_pparam) { memcpy (newparam, pstmt->st_pparam, pstmt->st_nparam * sizeof (TPARM)); free (pstmt->st_pparam); } pstmt->st_pparam = newparam; pstmt->st_nparam = (u_short) newsize; } pstmt->st_pparam[ipar-1] = parm; if (odbc_ver == SQL_OV_ODBC2 && ( dodbc_ver == SQL_OV_ODBC2 || (dodbc_ver == SQL_OV_ODBC3 && hproc2 != SQL_NULL_HPROC))) hproc3 = SQL_NULL_HPROC; #if (ODBCVER >=0x0300) if (fParamType == SQL_PARAM_INPUT && hproc3 != SQL_NULL_HPROC) { CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc3, (pstmt->dhstmt, ipar, nCType, nSqlType, cbColDef, ibScale, rgbValue, pcbValue)); } else #endif { if (hproc2 == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc2, (pstmt->dhstmt, ipar, fParamType, nCType, nSqlType, cbColDef, ibScale, rgbValue, cbValueMax, pcbValue)); } return retcode; }
static SQLRETURN SQLParamOptions_Internal ( SQLHSTMT hstmt, SQLULEN crow, SQLULEN * pirow) { STMT (pstmt, hstmt); HPROC hproc2 = SQL_NULL_HPROC; HPROC hproc3 = SQL_NULL_HPROC; SQLRETURN retcode; CONN (pdbc, pstmt->hdbc); SQLUINTEGER odbc_ver = ((GENV_t *) pdbc->genv)->odbc_ver; SQLUINTEGER dodbc_ver = ((ENV_t *) pdbc->henv)->dodbc_ver; if (crow == (SQLULEN) 0UL) { PUSHSQLERR (pstmt->herr, en_S1107); return SQL_ERROR; } if (pstmt->state >= en_stmt_needdata || pstmt->asyn_on != en_NullProc) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } hproc2 = _iodbcdm_getproc (pstmt->hdbc, en_ParamOptions); #if (ODBCVER >= 0x0300) hproc3 = _iodbcdm_getproc (pstmt->hdbc, en_SetStmtAttr); #endif if (odbc_ver == SQL_OV_ODBC2 && ( dodbc_ver == SQL_OV_ODBC2 || (dodbc_ver == SQL_OV_ODBC3 && hproc2 != SQL_NULL_HPROC))) hproc3 = SQL_NULL_HPROC; #if (ODBCVER >= 0x0300) if (hproc3 != SQL_NULL_HPROC) { CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc3, (pstmt->dhstmt, SQL_ATTR_PARAMSET_SIZE, crow, 0)); if (SQL_SUCCEEDED (retcode)) { CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc3, (pstmt->dhstmt, SQL_ATTR_PARAMS_PROCESSED_PTR, pirow, 0)); } } else #endif { if (hproc2 == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc2, (pstmt->dhstmt, crow, pirow)); } pstmt->paramset_size = crow; return retcode; }
static SQLRETURN SQLParamData_Internal (SQLHSTMT hstmt, SQLPOINTER * prgbValue) { STMT (pstmt, hstmt); HPROC hproc; SQLRETURN retcode; /* check argument */ /* check state */ if (pstmt->asyn_on == en_NullProc) { if (pstmt->state <= en_stmt_xfetched) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } } else if (pstmt->asyn_on != en_ParamData) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } /* call driver */ hproc = _iodbcdm_getproc (pstmt->hdbc, en_ParamData); if (hproc == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt, prgbValue)); /* state transition */ if (pstmt->asyn_on == en_ParamData) { switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_ERROR: pstmt->asyn_on = en_NullProc; break; case SQL_STILL_EXECUTING: default: return retcode; } } if (pstmt->state < en_stmt_needdata) { return retcode; } switch (retcode) { case SQL_ERROR: switch (pstmt->need_on) { case en_ExecDirect: pstmt->state = en_stmt_allocated; break; case en_Execute: pstmt->state = en_stmt_prepared; break; case en_SetPos: pstmt->state = en_stmt_xfetched; pstmt->cursor_state = en_stmt_cursor_xfetched; break; default: break; } pstmt->need_on = en_NullProc; break; case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: switch (pstmt->state) { case en_stmt_needdata: pstmt->state = en_stmt_mustput; break; case en_stmt_canput: switch (pstmt->need_on) { case en_SetPos: pstmt->state = en_stmt_xfetched; pstmt->cursor_state = en_stmt_cursor_xfetched; break; case en_ExecDirect: case en_Execute: _iodbcdm_do_cursoropen (pstmt); break; default: break; } break; default: break; } pstmt->need_on = en_NullProc; break; case SQL_NEED_DATA: pstmt->state = en_stmt_mustput; break; default: break; } return retcode; }
static SQLRETURN SQLNumParams_Internal (SQLHSTMT hstmt, SQLSMALLINT * pcpar) { STMT (pstmt, hstmt); HPROC hproc; SQLRETURN retcode; /* check argument */ if (!pcpar) { return SQL_SUCCESS; } /* check state */ if (pstmt->asyn_on == en_NullProc) { switch (pstmt->state) { case en_stmt_allocated: case en_stmt_needdata: case en_stmt_mustput: case en_stmt_canput: PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; default: break; } } else if (pstmt->asyn_on != en_NumParams) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } /* call driver */ hproc = _iodbcdm_getproc (pstmt->hdbc, en_NumParams); if (hproc == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt, pcpar)); /* state transition */ if (pstmt->asyn_on == en_NumParams) { switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_ERROR: break; default: return retcode; } } if (retcode == SQL_STILL_EXECUTING) { pstmt->asyn_on = en_NumParams; } return retcode; }
static SQLRETURN SQLExecute_Internal (SQLHSTMT hstmt) { STMT (pstmt, hstmt); HPROC hproc = SQL_NULL_HPROC; SQLRETURN retcode; sqlstcode_t sqlstat = en_00000; /* check state */ if (pstmt->asyn_on == en_NullProc) { switch (pstmt->state) { case en_stmt_allocated: sqlstat = en_S1010; break; case en_stmt_executed_with_info: case en_stmt_executed: if (!pstmt->prep_state) { sqlstat = en_S1010; } break; case en_stmt_cursoropen: if (!pstmt->prep_state) { sqlstat = en_S1010; } break; case en_stmt_fetched: case en_stmt_xfetched: if (!pstmt->prep_state) { sqlstat = en_S1010; } else { sqlstat = en_24000; } break; case en_stmt_needdata: case en_stmt_mustput: case en_stmt_canput: sqlstat = en_S1010; break; default: break; } } else if (pstmt->asyn_on != en_Execute) { sqlstat = en_S1010; } if (sqlstat == en_00000) { hproc = _iodbcdm_getproc (pstmt->hdbc, en_Execute); if (hproc == SQL_NULL_HPROC) { sqlstat = en_IM001; } } if (sqlstat != en_00000) { PUSHSQLERR (pstmt->herr, sqlstat); return SQL_ERROR; } if ((retcode = _SQLExecute_ConvParams(hstmt, FALSE)) != SQL_SUCCESS) return retcode; CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt)); /* stmt state transition */ if (pstmt->asyn_on == en_Execute) { switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_NEED_DATA: case SQL_ERROR: pstmt->asyn_on = en_NullProc; break; case SQL_STILL_EXECUTING: default: return retcode; } } if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) retcode = _SQLExecute_ConvParams(hstmt, TRUE); switch (pstmt->state) { case en_stmt_prepared: switch (retcode) { case SQL_SUCCESS: _iodbcdm_do_cursoropen (pstmt); break; case SQL_SUCCESS_WITH_INFO: pstmt->state = en_stmt_executed_with_info; break; case SQL_NEED_DATA: pstmt->state = en_stmt_needdata; pstmt->need_on = en_Execute; break; case SQL_STILL_EXECUTING: pstmt->asyn_on = en_Execute; break; default: break; } break; case en_stmt_executed: switch (retcode) { case SQL_ERROR: pstmt->state = en_stmt_prepared; pstmt->cursor_state = en_stmt_cursor_no; break; case SQL_NEED_DATA: pstmt->state = en_stmt_needdata; pstmt->need_on = en_Execute; break; case SQL_STILL_EXECUTING: pstmt->asyn_on = en_Execute; break; default: break; } break; default: break; } return retcode; }
static SQLRETURN SQLPutData_Internal ( SQLHSTMT hstmt, SQLPOINTER rgbValue, SQLLEN cbValue) { STMT (pstmt, hstmt); HPROC hproc; SQLRETURN retcode; /* check argument value */ if (rgbValue == NULL && (cbValue != SQL_DEFAULT_PARAM && cbValue != SQL_NULL_DATA)) { PUSHSQLERR (pstmt->herr, en_S1009); return SQL_ERROR; } /* check state */ if (pstmt->asyn_on == en_NullProc) { if (pstmt->state <= en_stmt_xfetched) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } } else if (pstmt->asyn_on != en_PutData) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } /* call driver */ hproc = _iodbcdm_getproc (pstmt->hdbc, en_PutData); if (hproc == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt, rgbValue, cbValue)); /* state transition */ if (pstmt->asyn_on == en_PutData) { switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_ERROR: pstmt->asyn_on = en_NullProc; break; case SQL_STILL_EXECUTING: default: return retcode; } } /* must in mustput or canput states */ switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: pstmt->state = en_stmt_canput; break; case SQL_ERROR: switch (pstmt->need_on) { case en_ExecDirect: pstmt->state = en_stmt_allocated; pstmt->need_on = en_NullProc; break; case en_Execute: if (pstmt->prep_state) { pstmt->state = en_stmt_prepared; pstmt->need_on = en_NullProc; } break; case en_SetPos: /* Is this possible ???? */ pstmt->state = en_stmt_xfetched; break; default: break; } break; case SQL_STILL_EXECUTING: pstmt->asyn_on = en_PutData; break; default: break; } return retcode; }
static SQLRETURN SQLDescribeParam_Internal ( SQLHSTMT hstmt, SQLUSMALLINT ipar, SQLSMALLINT * pfSqlType, SQLULEN * pcbColDef, SQLSMALLINT * pibScale, SQLSMALLINT * pfNullable) { STMT (pstmt, hstmt); CONN (pdbc, pstmt->hdbc); GENV (genv, pdbc->genv); HPROC hproc; SQLRETURN retcode; /* check argument */ if (ipar == 0) { PUSHSQLERR (pstmt->herr, en_S1093); return SQL_ERROR; } /* check state */ if (pstmt->asyn_on == en_NullProc) { switch (pstmt->state) { case en_stmt_allocated: case en_stmt_needdata: case en_stmt_mustput: case en_stmt_canput: PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; default: break; } } else if (pstmt->asyn_on != en_DescribeParam) { PUSHSQLERR (pstmt->herr, en_S1010); return SQL_ERROR; } /* call driver */ hproc = _iodbcdm_getproc (pstmt->hdbc, en_DescribeParam); if (hproc == SQL_NULL_HPROC) { PUSHSQLERR (pstmt->herr, en_IM001); return SQL_ERROR; } CALL_DRIVER (pstmt->hdbc, pstmt, retcode, hproc, (pstmt->dhstmt, ipar, pfSqlType, pcbColDef, pibScale, pfNullable)); /* * Convert sql type to ODBC version of application */ if (SQL_SUCCEEDED(retcode) && pfSqlType) *pfSqlType = _iodbcdm_map_sql_type (*pfSqlType, genv->odbc_ver); /* state transition */ if (pstmt->asyn_on == en_DescribeParam) { switch (retcode) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_ERROR: break; default: return retcode; } } if (retcode == SQL_STILL_EXECUTING) { pstmt->asyn_on = en_DescribeParam; } return retcode; }
RETCODE SQL_API SQLGetDiagRec_Internal ( SQLSMALLINT HandleType, SQLHANDLE Handle, SQLSMALLINT RecNumber, SQLPOINTER Sqlstate, SQLINTEGER * NativeErrorPtr, SQLPOINTER MessageText, SQLSMALLINT BufferLength, SQLSMALLINT * TextLengthPtr, SQLCHAR waMode) { sqlerr_t *curr_err = NULL; HERR err = NULL; int nRecs; HPROC hproc2 = SQL_NULL_HPROC; HPROC hproc3 = SQL_NULL_HPROC; HDBC hdbc = SQL_NULL_HDBC; RETCODE retcode = SQL_SUCCESS; SQLHANDLE dhandle = SQL_NULL_HANDLE; SWORD unicode_driver = 0; SQLUINTEGER dodbc_ver = SQL_OV_ODBC3; SQLUINTEGER odbc_ver = SQL_OV_ODBC3; wchar_t _sqlState[6] = {L"\0"}; void *_MessageText = NULL; void *messageTextOut = MessageText; void *SqlstateOut = Sqlstate; if (RecNumber < 1) return SQL_ERROR; if (BufferLength < 0) return SQL_ERROR; switch (HandleType) { case SQL_HANDLE_ENV: if (!IS_VALID_HENV (Handle)) { return SQL_INVALID_HANDLE; } err = ((GENV_t *) Handle)->herr; break; case SQL_HANDLE_DBC: if (!IS_VALID_HDBC (Handle)) { return SQL_INVALID_HANDLE; } err = ((DBC_t *) Handle)->herr; dhandle = ((DBC_t *) Handle)->dhdbc; hdbc = Handle; break; case SQL_HANDLE_STMT: if (!IS_VALID_HSTMT (Handle)) { return SQL_INVALID_HANDLE; } err = ((STMT_t *) Handle)->herr; dhandle = ((STMT_t *) Handle)->dhstmt; hdbc = ((STMT_t *) Handle)->hdbc; break; case SQL_HANDLE_DESC: if (!IS_VALID_HDESC (Handle)) { return SQL_INVALID_HANDLE; } err = ((DESC_t *) Handle)->herr; dhandle = ((DESC_t *) Handle)->dhdesc; hdbc = ((DESC_t *) Handle)->hdbc; break; default: return SQL_INVALID_HANDLE; } nRecs = error_rec_count (err); if (nRecs >= RecNumber) { /* DM error range */ curr_err = get_nth_error (err, RecNumber - 1); if (!curr_err) { return (SQL_NO_DATA_FOUND); } retcode = SQL_SUCCESS; if (Sqlstate != NULL) { int len; char *ststr = (char *) _iodbcdm_getsqlstate (curr_err, (void *) sqlerrmsg_tab); if (ststr == NULL) { len = 0; } else { len = (int) STRLEN (ststr); } /* buffer size of szSqlstate is not checked. Applications * suppose provide enough ( not less than 6 bytes ) buffer * or NULL for it. */ if (waMode != 'W') { STRNCPY (Sqlstate, ststr, len); ((char*)Sqlstate)[len] = 0; } else { dm_StrCopyOut2_A2W ((SQLCHAR *) ststr, (SQLWCHAR *) Sqlstate, 6, NULL); ((wchar_t*)Sqlstate)[len] = 0; } } if (MessageText == NULL || BufferLength == 0) { if (TextLengthPtr != NULL) { *TextLengthPtr = (SWORD) 0; } } else { int len; char msgbuf[256] = { '\0' }; char *errmsg; /* get sql state message */ errmsg = _iodbcdm_getsqlerrmsg (curr_err, (void *) sqlerrmsg_tab); if (errmsg == NULL) { errmsg = (char *) ""; } #if defined(HAVE_SNPRINTF) snprintf (msgbuf, sizeof (msgbuf), "%s%s", sqlerrhd, errmsg); #else sprintf (msgbuf, "%s%s", sqlerrhd, errmsg); #endif len = STRLEN (msgbuf); if (len < BufferLength - 1) { retcode = SQL_SUCCESS; } else { len = BufferLength - 1; retcode = SQL_SUCCESS_WITH_INFO; /* and not posts error for itself */ } if (waMode != 'W') { STRNCPY ((char *) MessageText, msgbuf, len); ((char*)MessageText)[len] = 0; if (TextLengthPtr != NULL) *TextLengthPtr = (SWORD) len; } else { dm_StrCopyOut2_A2W ((SQLCHAR *) msgbuf, (SQLWCHAR *) MessageText, BufferLength, TextLengthPtr); } } return retcode; } else { /* Driver errors */ if (hdbc == SQL_NULL_HDBC) { return SQL_NO_DATA_FOUND; } RecNumber -= nRecs; if (hdbc && ((DBC_t *)hdbc)->henv) { unicode_driver = ((ENV_t *) ((DBC_t *)hdbc)->henv)->unicode_driver; dodbc_ver = ((ENV_t *) ((DBC_t *)hdbc)->henv)->dodbc_ver; } if (hdbc && ((DBC_t *)hdbc)->genv) odbc_ver = ((GENV_t *) ((DBC_t *)hdbc)->genv)->odbc_ver; if ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W')) { if (waMode != 'W') { /* ansi=>unicode*/ if ((_MessageText = malloc((BufferLength + 1) * sizeof(wchar_t))) == NULL) { return SQL_ERROR; } } else { /* unicode=>ansi*/ if ((_MessageText = malloc(BufferLength + 1)) == NULL) { return SQL_ERROR; } } messageTextOut = _MessageText; SqlstateOut = _sqlState; } /* call driver */ if (unicode_driver) { /* SQL_XXX_W */ hproc2 = _iodbcdm_getproc (hdbc, en_ErrorW); #if (ODBCVER >= 0x300) hproc3 = _iodbcdm_getproc (hdbc, en_GetDiagRecW); #endif } else { /* SQL_XXX */ /* SQL_XXX_A */ hproc2 = _iodbcdm_getproc (hdbc, en_Error); if (hproc2 == SQL_NULL_HPROC) hproc2 = _iodbcdm_getproc (hdbc, en_ErrorA); #if (ODBCVER >= 0x300) hproc3 = _iodbcdm_getproc (hdbc, en_GetDiagRec); if (hproc3 == SQL_NULL_HPROC) hproc3 = _iodbcdm_getproc (hdbc, en_GetDiagRecA); #endif } if (odbc_ver == SQL_OV_ODBC2 && ( dodbc_ver == SQL_OV_ODBC2 || (dodbc_ver == SQL_OV_ODBC3 && hproc2 != SQL_NULL_HPROC))) hproc3 = SQL_NULL_HPROC; #if (ODBCVER >= 0x300) if (hproc3 != SQL_NULL_HPROC) { CALL_DRIVER (hdbc, Handle, retcode, hproc3, ( HandleType, dhandle, RecNumber, SqlstateOut, NativeErrorPtr, messageTextOut, BufferLength, TextLengthPtr)); } else #endif { if (hproc2 == SQL_NULL_HPROC) { MEM_FREE(_MessageText); return SQL_ERROR; } if (RecNumber > 1 || HandleType == SQL_HANDLE_DESC) { MEM_FREE(_MessageText); return SQL_NO_DATA_FOUND; } CALL_DRIVER (hdbc, Handle, retcode, hproc2, ( SQL_NULL_HENV, HandleType == SQL_HANDLE_DBC ? dhandle : SQL_NULL_HDBC, HandleType == SQL_HANDLE_STMT ? dhandle : SQL_NULL_HSTMT, SqlstateOut, NativeErrorPtr, messageTextOut, BufferLength, TextLengthPtr)); } if (MessageText && SQL_SUCCEEDED (retcode) && ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W'))) { if (waMode != 'W') { /* ansi<=unicode*/ dm_StrCopyOut2_W2A ((SQLWCHAR *)messageTextOut, (SQLCHAR *)MessageText, BufferLength, NULL); dm_StrCopyOut2_W2A ((SQLWCHAR *)SqlstateOut, (SQLCHAR *)Sqlstate, 6, NULL); } else { /* unicode<=ansi*/ dm_StrCopyOut2_A2W ((SQLCHAR *) messageTextOut, (SQLWCHAR *) MessageText, BufferLength, NULL); dm_StrCopyOut2_A2W ((SQLCHAR *) SqlstateOut, (SQLWCHAR *) Sqlstate, 6, NULL); } } MEM_FREE(_MessageText); return retcode; } }
SQLRETURN SQL_API _iodbcdm_sqlerror ( SQLHENV henv, SQLHDBC hdbc, SQLHSTMT hstmt, SQLPOINTER szSqlstate, SQLINTEGER * pfNativeError, SQLPOINTER szErrorMsg, SQLSMALLINT cbErrorMsgMax, SQLSMALLINT * pcbErrorMsg, int bDelete, SQLCHAR waMode) { GENV (genv, henv); CONN (pdbc, hdbc); STMT (pstmt, hstmt); HDBC thdbc = SQL_NULL_HDBC; HENV dhenv = SQL_NULL_HENV; HDBC dhdbc = SQL_NULL_HDBC; HSTMT dhstmt = SQL_NULL_HSTMT; HERR herr = SQL_NULL_HERR; HPROC hproc2 = SQL_NULL_HPROC; HPROC hproc3 = SQL_NULL_HPROC; #if (ODBCVER >= 0x0300) SQLINTEGER handleType = 0; SQLHANDLE handle3; SQLHANDLE dhandle3 = 0; SQLSMALLINT *perr_rec = NULL; #endif SWORD unicode_driver = 0; SQLUINTEGER dodbc_ver = SQL_OV_ODBC2; SQLUINTEGER odbc_ver = SQL_OV_ODBC2; wchar_t _sqlState[6] = {L"\0"}; void *SqlstateOut = szSqlstate; void *_ErrorMsg = NULL; void *errorMsgOut = szErrorMsg; void *errmsg = NULL; void *ststr = NULL; int handle = 0; SQLRETURN retcode = SQL_SUCCESS; if (IS_VALID_HSTMT (hstmt)) /* retrieve stmt err */ { herr = pstmt->herr; thdbc = pstmt->hdbc; if (thdbc == SQL_NULL_HDBC) { return SQL_INVALID_HANDLE; } #if (ODBCVER >= 0x0300) handleType = SQL_HANDLE_STMT; handle3 = hstmt; dhandle3 = pstmt->dhstmt; perr_rec = &((STMT_t *)pstmt)->err_rec; #endif dhstmt = pstmt->dhstmt; handle = 3; } else if (IS_VALID_HDBC (hdbc)) /* retrieve dbc err */ { herr = pdbc->herr; thdbc = pdbc; if (thdbc == SQL_NULL_HDBC) { return SQL_INVALID_HANDLE; } #if (ODBCVER >= 0x0300) handleType = SQL_HANDLE_DBC; handle3 = hdbc; dhandle3 = pdbc->dhdbc; perr_rec = &((DBC_t *)pdbc)->err_rec; #endif dhdbc = pdbc->dhdbc; handle = 2; if (herr == SQL_NULL_HERR && pdbc->henv == SQL_NULL_HENV) { return SQL_NO_DATA_FOUND; } } else if (IS_VALID_HENV (henv)) /* retrieve env err */ { herr = genv->herr; /* Drivers shouldn't push error message * on environment handle */ if (herr == SQL_NULL_HERR) { return SQL_NO_DATA_FOUND; } handle = 1; } else { return SQL_INVALID_HANDLE; } if (szErrorMsg != NULL) { if (cbErrorMsgMax < 0) { return SQL_ERROR; /* SQLError() doesn't post error for itself */ } } if (herr == SQL_NULL_HERR) /* no err on drv mng */ { if (thdbc && ((DBC_t *)thdbc)->genv) odbc_ver = ((GENV_t *) ((DBC_t *)thdbc)->genv)->odbc_ver; if (thdbc && ((DBC_t *)thdbc)->henv) { unicode_driver = ((ENV_t *) ((DBC_t *)thdbc)->henv)->unicode_driver; dodbc_ver = ((ENV_t *) ((DBC_t *)thdbc)->henv)->dodbc_ver; } /* call driver */ if ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W')) { if (waMode != 'W') { /* ansi=>unicode*/ if ((_ErrorMsg = malloc(cbErrorMsgMax * sizeof(wchar_t) + 1)) == NULL) return SQL_ERROR; } else { /* unicode=>ansi*/ if ((_ErrorMsg = malloc(cbErrorMsgMax + 1)) == NULL) return SQL_ERROR; } errorMsgOut = _ErrorMsg; SqlstateOut = _sqlState; } /* call driver */ if (unicode_driver) { /* SQL_XXX_W */ hproc2 = _iodbcdm_getproc (thdbc, en_ErrorW); #if (ODBCVER >= 0x300) hproc3 = _iodbcdm_getproc (thdbc, en_GetDiagRecW); #endif } else { /* SQL_XXX */ /* SQL_XXX_A */ hproc2 = _iodbcdm_getproc (thdbc, en_Error); if (hproc2 == SQL_NULL_HPROC) hproc2 = _iodbcdm_getproc (thdbc, en_ErrorA); #if (ODBCVER >= 0x300) hproc3 = _iodbcdm_getproc (thdbc, en_GetDiagRec); if (hproc3 == SQL_NULL_HPROC) hproc3 = _iodbcdm_getproc (thdbc, en_GetDiagRecA); #endif } if (odbc_ver == SQL_OV_ODBC2 && ( dodbc_ver == SQL_OV_ODBC2 || (dodbc_ver == SQL_OV_ODBC3 && hproc2 != SQL_NULL_HPROC))) hproc3 = SQL_NULL_HPROC; #if (ODBCVER >= 0x300) if (hproc3 != SQL_NULL_HPROC) { (*perr_rec) = (*perr_rec) + 1; CALL_DRIVER (thdbc, NULL, retcode, hproc3, ( handleType, dhandle3, (*perr_rec), SqlstateOut, pfNativeError, errorMsgOut, cbErrorMsgMax, pcbErrorMsg)); } else #endif { if (hproc2 == SQL_NULL_HPROC) { MEM_FREE(_ErrorMsg); return SQL_NO_DATA_FOUND; } CALL_DRIVER (thdbc, NULL, retcode, hproc2, ( dhenv, dhdbc, dhstmt, SqlstateOut, pfNativeError, errorMsgOut, cbErrorMsgMax, pcbErrorMsg)); } if (szErrorMsg && SQL_SUCCEEDED (retcode) && ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W'))) { if (waMode != 'W') { /* ansi<=unicode*/ dm_StrCopyOut2_W2A ((SQLWCHAR *)errorMsgOut, (SQLCHAR *)szErrorMsg, cbErrorMsgMax, NULL); dm_StrCopyOut2_W2A ((SQLWCHAR *)SqlstateOut, (SQLCHAR *)szSqlstate, 6, NULL); } else { /* unicode<=ansi*/ dm_StrCopyOut2_A2W ((SQLCHAR *)errorMsgOut, (SQLWCHAR *)szErrorMsg, cbErrorMsgMax, NULL); dm_StrCopyOut2_A2W ((SQLCHAR *)SqlstateOut, (SQLWCHAR *)szSqlstate, 6, NULL); } } MEM_FREE(_ErrorMsg); return retcode; } if (szSqlstate != NULL) { int len; /* get sql state string */ ststr = (char *) _iodbcdm_getsqlstate (herr, (void *) sqlerrmsg_tab); if (ststr == NULL) { len = 0; } else { len = (int) STRLEN (ststr); } /* buffer size of szSqlstate is not checked. Applications * suppose provide enough ( not less than 6 bytes ) buffer * or NULL for it. */ if (waMode != 'W') { STRNCPY (szSqlstate, ststr, len); ((char*)szSqlstate)[len] = 0; } else { dm_StrCopyOut2_A2W ((SQLCHAR *)ststr, (SQLWCHAR *)szSqlstate, 6, NULL); ((wchar_t*)szSqlstate)[len] = 0; } } if (pfNativeError != NULL) { /* native error code is specific to data source */ *pfNativeError = (SDWORD) 0L; } if (szErrorMsg == NULL || cbErrorMsgMax == 0) { if (pcbErrorMsg != NULL) { *pcbErrorMsg = (SWORD) 0; } } else { int len; char msgbuf[256] = {'\0'}; /* get sql state message */ errmsg = _iodbcdm_getsqlerrmsg (herr, (void *) sqlerrmsg_tab); if (errmsg == NULL) { errmsg = (char *) ""; } #if defined(HAVE_SNPRINTF) snprintf (msgbuf, sizeof(msgbuf), "%s%s", sqlerrhd, (char*)errmsg); #else sprintf (msgbuf, "%s%s", sqlerrhd, (char*)errmsg); #endif len = STRLEN (msgbuf); if (len < cbErrorMsgMax - 1) { retcode = SQL_SUCCESS; } else { len = cbErrorMsgMax - 1; retcode = SQL_SUCCESS_WITH_INFO; /* and not posts error for itself */ } if (waMode != 'W') { STRNCPY ((char *) szErrorMsg, msgbuf, len); ((char*)szErrorMsg)[len] = 0; if (pcbErrorMsg != NULL) *pcbErrorMsg = (SWORD) len; } else { dm_StrCopyOut2_A2W ((SQLCHAR *) msgbuf, (SQLWCHAR *) szErrorMsg, cbErrorMsgMax, pcbErrorMsg); } } if (bDelete) switch (handle) /* free this err */ { case 1: genv->herr = _iodbcdm_popsqlerr (genv->herr); break; case 2: pdbc->herr = _iodbcdm_popsqlerr (pdbc->herr); break; case 3: pstmt->herr = _iodbcdm_popsqlerr (pstmt->herr); break; default: break; } return retcode; }
RETCODE SQL_API SQLGetDiagField_Internal ( SQLSMALLINT nHandleType, SQLHANDLE Handle, SQLSMALLINT nRecNumber, SQLSMALLINT nDiagIdentifier, SQLPOINTER pDiagInfoPtr, SQLSMALLINT nBufferLength, SQLSMALLINT * pnStringLengthPtr, SQLCHAR waMode) { GENV (genv, Handle); CONN (con, Handle); STMT (stmt, Handle); DESC (desc, Handle); HERR err; HPROC hproc = SQL_NULL_HPROC; RETCODE retcode = SQL_SUCCESS; SQLHANDLE dhandle = SQL_NULL_HANDLE; SWORD unicode_driver = 0; void *_DiagInfoPtr = NULL; void *diagInfoPtr = pDiagInfoPtr; switch (nHandleType) { case SQL_HANDLE_ENV: if (!IS_VALID_HENV (Handle)) { return SQL_INVALID_HANDLE; } err = genv->herr; con = NULL; stmt = NULL; desc = NULL; break; case SQL_HANDLE_DBC: if (!IS_VALID_HDBC (Handle)) { return SQL_INVALID_HANDLE; } err = con->herr; genv = (GENV_t *) con->genv; stmt = NULL; desc = NULL; dhandle = con->dhdbc; break; case SQL_HANDLE_STMT: if (!IS_VALID_HSTMT (Handle)) { return SQL_INVALID_HANDLE; } err = stmt->herr; con = (DBC_t *) stmt->hdbc; genv = (GENV_t *) con->genv; desc = NULL; dhandle = stmt->dhstmt; break; case SQL_HANDLE_DESC: if (!IS_VALID_HDESC (Handle)) { return SQL_INVALID_HANDLE; } err = desc->herr; stmt = (STMT_t *) desc->hstmt; con = (DBC_t *) desc->hdbc; genv = (GENV_t *) con->genv; dhandle = desc->dhdesc; break; default: return SQL_INVALID_HANDLE; } if (con != NULL && con->henv != SQL_NULL_HENV) unicode_driver = ((ENV_t *) con->henv)->unicode_driver; switch (nRecNumber) { case 0: /* Header record */ switch (nDiagIdentifier) { case SQL_DIAG_ROW_COUNT: { if (nHandleType != SQL_HANDLE_STMT || !stmt) { return SQL_ERROR; } if (stmt->state != en_stmt_executed_with_info && stmt->state != en_stmt_executed && stmt->state != en_stmt_cursoropen) { return SQL_ERROR; } if (!con) { return SQL_INVALID_HANDLE; } CALL_UDRIVER(con, stmt, retcode, hproc, unicode_driver, en_GetDiagField, (SQL_HANDLE_DBC, stmt->dhstmt, nRecNumber, nDiagIdentifier, pDiagInfoPtr, nBufferLength, pnStringLengthPtr )); if (hproc == SQL_NULL_HPROC) { if (!con) { return SQL_INVALID_HANDLE; } hproc = _iodbcdm_getproc (con, en_RowCount); if (!hproc) { return SQL_ERROR; } CALL_DRIVER (stmt->hdbc, stmt, retcode, hproc, (stmt->dhstmt, pDiagInfoPtr)); } return retcode; } case SQL_DIAG_CURSOR_ROW_COUNT: case SQL_DIAG_DYNAMIC_FUNCTION: case SQL_DIAG_DYNAMIC_FUNCTION_CODE: { if (nHandleType != SQL_HANDLE_STMT || !stmt) { return SQL_ERROR; } if (stmt->state != en_stmt_executed_with_info && stmt->state != en_stmt_executed && stmt->state != en_stmt_cursoropen) { return SQL_ERROR; } if (!con) { return SQL_INVALID_HANDLE; } CALL_UDRIVER(con, stmt, retcode, hproc, unicode_driver, en_GetDiagField, (SQL_HANDLE_DBC, stmt->dhstmt, nRecNumber, nDiagIdentifier, pDiagInfoPtr, nBufferLength, pnStringLengthPtr )); if (hproc == SQL_NULL_HPROC) return SQL_ERROR; else return retcode; } case SQL_DIAG_RETURNCODE: if (pDiagInfoPtr) *((SQLRETURN *) pDiagInfoPtr) = ((GENV_t *) Handle)->rc; { return SQL_SUCCESS; } case SQL_DIAG_NUMBER: if (pDiagInfoPtr) { (*(SQLINTEGER *) pDiagInfoPtr) = 0; /* get the number from the driver */ if (con) { CALL_UDRIVER(con, Handle, retcode, hproc, unicode_driver, en_GetDiagField, (nHandleType, dhandle, 0, nDiagIdentifier, pDiagInfoPtr, nBufferLength, pnStringLengthPtr )); if (hproc != SQL_NULL_HPROC) { if (retcode != SQL_SUCCESS) { return retcode; } /* and add the DM's value */ (*(SQLINTEGER *) pDiagInfoPtr) += error_rec_count (err); } else if (((ENV_t *) con->henv)->dodbc_ver == SQL_OV_ODBC2 && ((GENV_t *) Handle)->rc) { /* ODBC2 drivers can only have one error */ (*(SQLINTEGER *) pDiagInfoPtr) = 1; } } else if (genv) { (*(SQLINTEGER *) pDiagInfoPtr) = error_rec_count (err); } } break; default: return SQL_ERROR; } break; default: /* status records */ { int nRecs = 0; if (nRecNumber < 1) { return SQL_ERROR; } nRecs = error_rec_count (err); if (nRecNumber <= nRecs) { /* DM Errors */ char *szval = ""; int ival = 0; int isInt = 0; sqlerr_t *rec = NULL; rec = get_nth_error (err, nRecNumber - 1); if (!rec) { return (SQL_NO_DATA_FOUND); } switch (nDiagIdentifier) { case SQL_DIAG_SUBCLASS_ORIGIN: case SQL_DIAG_CLASS_ORIGIN: isInt = 0; szval = (rec->code >= en_HY001 && rec->code <= en_IM014) ? (char *) "ODBC 3.0" : (char *) "ISO 9075"; break; case SQL_DIAG_COLUMN_NUMBER: if (nHandleType != SQL_HANDLE_STMT || !stmt) { return SQL_ERROR; } if (!con) { return SQL_INVALID_HANDLE; } if (pDiagInfoPtr) *((SQLINTEGER *) pDiagInfoPtr) = SQL_COLUMN_NUMBER_UNKNOWN; return SQL_SUCCESS; case SQL_DIAG_CONNECTION_NAME: case SQL_DIAG_SERVER_NAME: isInt = 0; if (con) { if (waMode != 'W') retcode = SQLGetInfo (con, SQL_DATA_SOURCE_NAME, pDiagInfoPtr, nBufferLength, pnStringLengthPtr); else retcode = SQLGetInfoW (con, SQL_DATA_SOURCE_NAME, pDiagInfoPtr, nBufferLength, pnStringLengthPtr); return retcode; } else break; case SQL_DIAG_MESSAGE_TEXT: isInt = 0; szval = _iodbcdm_getsqlerrmsg (rec, (void *) sqlerrmsg_tab); break; case SQL_DIAG_NATIVE: isInt = 1; ival = 0; break; case SQL_DIAG_ROW_NUMBER: isInt = 1; if (nHandleType != SQL_HANDLE_STMT || !stmt) { return SQL_ERROR; } if (!con) { return SQL_INVALID_HANDLE; } CALL_UDRIVER(con, Handle, retcode, hproc, unicode_driver, en_GetDiagField, (nHandleType, dhandle, nRecNumber, nDiagIdentifier, pDiagInfoPtr, nBufferLength, pnStringLengthPtr )); if (hproc != SQL_NULL_HPROC) { return retcode; } else { ival = SQL_ROW_NUMBER_UNKNOWN; break; } case SQL_DIAG_SQLSTATE: isInt = 0; szval = _iodbcdm_getsqlstate (rec, (void *) sqlerrmsg_tab); break; default: return SQL_ERROR; } if (isInt) { if (pDiagInfoPtr) *((SQLINTEGER *) pDiagInfoPtr) = ival; } else { if (waMode != 'W') { int len = strlen (szval), len1; len1 = len > nBufferLength ? nBufferLength : len; if (pnStringLengthPtr) *pnStringLengthPtr = len; if (pDiagInfoPtr) { STRNCPY (pDiagInfoPtr, szval, len1); *(((SQLCHAR *) pDiagInfoPtr) + len1) = 0; } } else { dm_StrCopyOut2_A2W((SQLCHAR *) szval, (SQLWCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } } break; } else { /* Driver's errors */ nRecNumber -= nRecs; if (!con) { return SQL_NO_DATA_FOUND; } if ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W')) { switch(nDiagIdentifier) { case SQL_DIAG_DYNAMIC_FUNCTION: case SQL_DIAG_CLASS_ORIGIN: case SQL_DIAG_CONNECTION_NAME: case SQL_DIAG_MESSAGE_TEXT: case SQL_DIAG_SERVER_NAME: case SQL_DIAG_SQLSTATE: case SQL_DIAG_SUBCLASS_ORIGIN: if (waMode != 'W') { /* ansi=>unicode*/ if ((_DiagInfoPtr = malloc((nBufferLength + 1) * sizeof(wchar_t))) == NULL) { return SQL_ERROR; } } else { /* unicode=>ansi*/ if ((_DiagInfoPtr = malloc(nBufferLength + 1)) == NULL) { return SQL_ERROR; } } diagInfoPtr = _DiagInfoPtr; break; } } CALL_UDRIVER(con, Handle, retcode, hproc, unicode_driver, en_GetDiagField, (nHandleType, dhandle, nRecNumber, nDiagIdentifier, diagInfoPtr, nBufferLength, pnStringLengthPtr )); if (hproc != SQL_NULL_HPROC) { if (pDiagInfoPtr && SQL_SUCCEEDED (retcode) && ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W'))) { switch(nDiagIdentifier) { case SQL_DIAG_DYNAMIC_FUNCTION: case SQL_DIAG_CLASS_ORIGIN: case SQL_DIAG_CONNECTION_NAME: case SQL_DIAG_MESSAGE_TEXT: case SQL_DIAG_SERVER_NAME: case SQL_DIAG_SQLSTATE: case SQL_DIAG_SUBCLASS_ORIGIN: if (waMode != 'W') { /* ansi<=unicode*/ dm_StrCopyOut2_W2A ((SQLWCHAR *) diagInfoPtr, (SQLCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } else { /* unicode<=ansi*/ dm_StrCopyOut2_A2W ((SQLCHAR *)diagInfoPtr, (SQLWCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } } } MEM_FREE(_DiagInfoPtr); return retcode; } else { /* an ODBC2->ODBC3 translation */ char *szval = ""; wchar_t szState[6]; SQLINTEGER nNative; if (nRecNumber > 1) { MEM_FREE(_DiagInfoPtr); return SQL_NO_DATA_FOUND; } if (nHandleType == SQL_HANDLE_DESC) { MEM_FREE(_DiagInfoPtr); return SQL_INVALID_HANDLE; } if (nDiagIdentifier != SQL_DIAG_MESSAGE_TEXT) MEM_FREE(_DiagInfoPtr); switch (nDiagIdentifier) { case SQL_DIAG_SUBCLASS_ORIGIN: case SQL_DIAG_CLASS_ORIGIN: CALL_UDRIVER (con, Handle, retcode, hproc, unicode_driver, en_Error, (SQL_NULL_HENV, nHandleType == SQL_HANDLE_DBC ? dhandle : SQL_NULL_HDBC, nHandleType == SQL_HANDLE_STMT ? dhandle : SQL_NULL_HSTMT, szState, &nNative, NULL, 0, NULL)); if (hproc == SQL_NULL_HPROC) { return SQL_INVALID_HANDLE; } if (retcode != SQL_SUCCESS) { return SQL_NO_DATA_FOUND; } if (waMode != 'W') { szval = !STRNEQ (szState, "IM", 2) ? (char *) "ODBC 3.0" : (char *) "ISO 9075"; } else { if (szState[0] != L'I' && szState[1] != L'M') szval = (char *) "ODBC 3.0"; else szval = (char *) "ISO 9075"; } break; case SQL_DIAG_ROW_NUMBER: case SQL_DIAG_COLUMN_NUMBER: if (nHandleType != SQL_HANDLE_STMT || !stmt) { return SQL_ERROR; } if (!con) { return SQL_INVALID_HANDLE; } if (pDiagInfoPtr) *((SQLINTEGER *) pDiagInfoPtr) = SQL_COLUMN_NUMBER_UNKNOWN; { return SQL_SUCCESS; } case SQL_DIAG_SERVER_NAME: case SQL_DIAG_CONNECTION_NAME: break; case SQL_DIAG_MESSAGE_TEXT: CALL_UDRIVER (con, Handle, retcode, hproc, unicode_driver, en_Error, (SQL_NULL_HENV, nHandleType == SQL_HANDLE_DBC ? dhandle : SQL_NULL_HDBC, nHandleType == SQL_HANDLE_STMT ? dhandle : SQL_NULL_HSTMT, szState, &nNative, diagInfoPtr, nBufferLength, pnStringLengthPtr)); if (hproc == SQL_NULL_HPROC) { MEM_FREE(_DiagInfoPtr); return SQL_INVALID_HANDLE; } if (pDiagInfoPtr && SQL_SUCCEEDED (retcode) && ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W'))) { if (waMode != 'W') { /* ansi<=unicode*/ dm_StrCopyOut2_W2A ((SQLWCHAR *) diagInfoPtr, (SQLCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } else { /* unicode<=ansi*/ dm_StrCopyOut2_A2W ((SQLCHAR *)diagInfoPtr, (SQLWCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } } MEM_FREE(_DiagInfoPtr); return retcode; case SQL_DIAG_NATIVE: CALL_UDRIVER (con, Handle, retcode, hproc, unicode_driver, en_Error, (SQL_NULL_HENV, nHandleType == SQL_HANDLE_DBC ? dhandle : SQL_NULL_HDBC, nHandleType == SQL_HANDLE_STMT ? dhandle : SQL_NULL_HSTMT, szState, &nNative, NULL, 0, NULL)); if (hproc == SQL_NULL_HPROC) { return SQL_INVALID_HANDLE; } if (pDiagInfoPtr) *((SQLINTEGER *) pDiagInfoPtr) = nNative; return retcode; case SQL_DIAG_SQLSTATE: CALL_UDRIVER (con, Handle, retcode, hproc, unicode_driver, en_Error, (SQL_NULL_HENV, nHandleType == SQL_HANDLE_DBC ? dhandle : SQL_NULL_HDBC, nHandleType == SQL_HANDLE_STMT ? dhandle : SQL_NULL_HSTMT, szState, &nNative, NULL, 0, NULL)); if (hproc == SQL_NULL_HPROC) { return SQL_INVALID_HANDLE; } if (pDiagInfoPtr && SQL_SUCCEEDED (retcode) && ((unicode_driver && waMode != 'W') || (!unicode_driver && waMode == 'W'))) { if (waMode != 'W') { /* ansi<=unicode*/ dm_StrCopyOut2_W2A ((SQLWCHAR *) szState, (SQLCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } else { /* unicode<=ansi*/ dm_StrCopyOut2_A2W ((SQLCHAR *)szState, (SQLWCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } } return retcode; default: return SQL_ERROR; } if (waMode != 'W') { if (pDiagInfoPtr) { int len = strlen (szval); if (len > nBufferLength) len = nBufferLength; if (len) _iodbcdm_strlcpy ((char *) pDiagInfoPtr, szval, len); } if (pnStringLengthPtr) *pnStringLengthPtr = strlen (szval); } else { dm_StrCopyOut2_A2W((SQLCHAR *) szval, (SQLWCHAR *) pDiagInfoPtr, nBufferLength, pnStringLengthPtr); } } /* ODBC3->ODBC2 */ } /* driver's errors */ } /* status records */ } /* switch (nRecNumber */ return (SQL_SUCCESS); }
static SQLRETURN SQLGetFunctions_Internal ( SQLHDBC hdbc, SQLUSMALLINT fFunc, SQLUSMALLINT * pfExists) { CONN (pdbc, hdbc); HPROC hproc; SQLRETURN retcode; int i; UWORD functions2[100]; #if (ODBCVER >= 0x0300) UWORD functions3[SQL_API_ODBC3_ALL_FUNCTIONS_SIZE]; #endif if (pdbc->state == en_dbc_allocated || pdbc->state == en_dbc_needdata) { PUSHSQLERR (pdbc->herr, en_S1010); return SQL_ERROR; } if (pfExists == NULL) { return SQL_SUCCESS; } /* * These functions are supported by the iODBC driver manager */ if (fFunc == SQL_API_SQLDATASOURCES || fFunc == SQL_API_SQLDRIVERS #if (ODBCVER >= 0x0300) || fFunc == SQL_API_SQLGETENVATTR || fFunc == SQL_API_SQLSETENVATTR #endif ) { *pfExists = (UWORD) 1; return SQL_SUCCESS; } /* * Check if function number is within ODBC version context */ #if (ODBCVER < 0x0300) if (fFunc > SQL_EXT_API_LAST) { PUSHSQLERR (pdbc->herr, en_S1095); return SQL_ERROR; } #endif /* * In a ODBC 2.x driver context, the ODBC 3.x API calls are * mapped by the driver manager. */ #if (ODBCVER >= 0x0300) if (((ENV_t *) pdbc->henv)->dodbc_ver == SQL_OV_ODBC2) { switch (fFunc) { case SQL_API_ALL_FUNCTIONS: case SQL_API_ODBC3_ALL_FUNCTIONS: break; /* Mapped ODBC3 app -> ODBC2 driver functions */ case SQL_API_SQLALLOCHANDLE: case SQL_API_SQLFREEHANDLE: case SQL_API_SQLSETCONNECTATTR: case SQL_API_SQLGETCONNECTATTR: case SQL_API_SQLGETSTMTATTR: case SQL_API_SQLSETSTMTATTR: case SQL_API_SQLCOLATTRIBUTE: case SQL_API_SQLENDTRAN: case SQL_API_SQLBULKOPERATIONS: case SQL_API_SQLFETCHSCROLL: case SQL_API_SQLGETDIAGREC: case SQL_API_SQLGETDIAGFIELD: *pfExists = SQL_TRUE; return SQL_SUCCESS; case SQL_API_SQLBINDPARAM: fFunc = SQL_API_SQLBINDPARAMETER; break; default: if (fFunc > SQL_API_SQLBINDPARAMETER) { *pfExists = SQL_FALSE; return SQL_SUCCESS; } break; } } #endif /* * If the driver exports a SQLGetFunctions call, use it */ hproc = _iodbcdm_getproc (pdbc, en_GetFunctions); if (hproc != SQL_NULL_HPROC) { CALL_DRIVER (hdbc, pdbc, retcode, hproc, en_GetFunctions, (pdbc->dhdbc, fFunc, pfExists)); return retcode; } /* * Map deprecated functions */ if (fFunc == SQL_API_SQLSETPARAM) { fFunc = SQL_API_SQLBINDPARAMETER; } /* * Initialize intermediate result arrays */ memset (functions2, '\0', sizeof (functions2)); #if (ODBCVER > 0x0300) memset (functions3, '\0', sizeof (functions3)); #endif /* * Build result array by scanning for all API calls */ for (i = 1; i < __LAST_API_FUNCTION__; i++) { int j = FunctionNumbers[i]; hproc = _iodbcdm_getproc (pdbc, i); if (hproc != SQL_NULL_HPROC) { if (j < 100) functions2[j] = 1; #if (ODBCVER >= 0x0300) functions3[j >> 4] |= (1 << (j & 0x000F)); #endif } } /* * Finally return the information */ if (fFunc == SQL_API_ALL_FUNCTIONS) { memcpy (pfExists, &functions2, sizeof (functions2)); } #if (ODBCVER < 0x0300) else { *pfExists = functions2[fFunc]; } #else else if (fFunc == SQL_API_ODBC3_ALL_FUNCTIONS)