options.c
来自「postgresql-odbc,跨平台应用」· C语言 代码 · 共 812 行 · 第 1/2 页
C
812 行
/*-------- * Module: options.c * * Description: This module contains routines for getting/setting * connection and statement options. * * Classes: n/a * * API functions: SQLSetConnectOption, SQLSetStmtOption, SQLGetConnectOption, * SQLGetStmtOption * * Comments: See "notice.txt" for copyright and license information. *-------- */#include "psqlodbc.h"#include <string.h>#include "environ.h"#include "connection.h"#include "statement.h"#include "qresult.h"#include "pgapifunc.h"RETCODEset_statement_option(ConnectionClass *conn, StatementClass *stmt, SQLUSMALLINT fOption, SQLULEN vParam){ CSTR func = "set_statement_option"; char changed = FALSE; ConnInfo *ci = NULL; SQLULEN setval; if (conn) ci = &(conn->connInfo); else if (stmt) ci = &(SC_get_conn(stmt)->connInfo); switch (fOption) { case SQL_ASYNC_ENABLE: /* ignored */ break; case SQL_BIND_TYPE: /* now support multi-column and multi-row binding */ if (conn) conn->ardOptions.bind_size = (SQLUINTEGER) vParam; if (stmt) SC_get_ARDF(stmt)->bind_size = (SQLUINTEGER) vParam; break; case SQL_CONCURRENCY: /* * positioned update isn't supported so cursor concurrency is * read-only */ mylog("SetStmtOption(): SQL_CONCURRENCY = %d ", vParam); setval = SQL_CONCUR_READ_ONLY; if (SQL_CONCUR_READ_ONLY == vParam) ; else if (ci->drivers.lie) setval = vParam; else if (0 != ci->updatable_cursors) setval = SQL_CONCUR_ROWVER; if (conn) conn->stmtOptions.scroll_concurrency = (SQLUINTEGER) setval; else if (stmt) { if (SC_get_Result(stmt)) { SC_set_error(stmt, STMT_INVALID_CURSOR_STATE_ERROR, "The attr can't be changed because the cursor is open.", func); return SQL_ERROR; } stmt->options.scroll_concurrency = stmt->options_orig.scroll_concurrency = (SQLUINTEGER) setval; } if (setval != vParam) changed = TRUE; mylog("-> %d\n", setval); break; case SQL_CURSOR_TYPE: /* * if declare/fetch, then type can only be forward. otherwise, * it can only be forward or static. */ mylog("SetStmtOption(): SQL_CURSOR_TYPE = %d ", vParam); setval = SQL_CURSOR_FORWARD_ONLY; if (ci->drivers.lie) setval = vParam; else if (SQL_CURSOR_STATIC == vParam) setval = vParam; else if (SQL_CURSOR_KEYSET_DRIVEN == vParam || SQL_CURSOR_DYNAMIC == vParam) { if (0 != (ci->updatable_cursors & ALLOW_KEYSET_DRIVEN_CURSORS)) setval = vParam; else setval = SQL_CURSOR_STATIC; /* at least scrollable */ } if (conn) conn->stmtOptions.cursor_type = (SQLUINTEGER) setval; else if (stmt) { if (SC_get_Result(stmt)) { SC_set_error(stmt, STMT_INVALID_CURSOR_STATE_ERROR, "The attr can't be changed because the cursor is open.", func); return SQL_ERROR; } stmt->options_orig.cursor_type = stmt->options.cursor_type = (SQLUINTEGER) setval; } if (setval != vParam) changed = TRUE; mylog("-> %d\n", setval); break; case SQL_KEYSET_SIZE: /* ignored, but saved and returned */ mylog("SetStmtOption(): SQL_KEYSET_SIZE, vParam = %d\n", vParam); if (conn) conn->stmtOptions.keyset_size = vParam; if (stmt) { stmt->options_orig.keyset_size = vParam; if (!SC_get_Result(stmt)) stmt->options.keyset_size = vParam; if (stmt->options.keyset_size != (int)vParam) changed = TRUE; } break; case SQL_MAX_LENGTH: /* ignored, but saved */ mylog("SetStmtOption(): SQL_MAX_LENGTH, vParam = %d\n", vParam); if (conn) conn->stmtOptions.maxLength = vParam; if (stmt) { stmt->options_orig.maxLength = vParam; if (!SC_get_Result(stmt)) stmt->options.maxLength = vParam; if (stmt->options.maxLength != (int)vParam) changed = TRUE; } break; case SQL_MAX_ROWS: /* ignored, but saved */ mylog("SetStmtOption(): SQL_MAX_ROWS, vParam = %d\n", vParam); if (conn) conn->stmtOptions.maxRows = vParam; if (stmt) { stmt->options_orig.maxRows = vParam; if (!SC_get_Result(stmt)) stmt->options.maxRows = vParam; if (stmt->options.maxRows != (int)vParam) changed = TRUE; } break; case SQL_NOSCAN: /* ignored */ mylog("SetStmtOption: SQL_NOSCAN, vParam = %d\n", vParam); break; case SQL_QUERY_TIMEOUT: /* ignored */ mylog("SetStmtOption: SQL_QUERY_TIMEOUT, vParam = %d\n", vParam); /* "0" returned in SQLGetStmtOption */ break; case SQL_RETRIEVE_DATA: mylog("SetStmtOption(): SQL_RETRIEVE_DATA, vParam = %d\n", vParam); if (conn) conn->stmtOptions.retrieve_data = (SQLUINTEGER) vParam; if (stmt) stmt->options.retrieve_data = (SQLUINTEGER) vParam; break; case SQL_ROWSET_SIZE: mylog("SetStmtOption(): SQL_ROWSET_SIZE, vParam = %d\n", vParam); /* * Save old rowset size for SQLExtendedFetch purposes If the * rowset_size is being changed since the last call to fetch * rows. */ if (stmt && stmt->save_rowset_size <= 0 && stmt->last_fetch_count > 0) stmt->save_rowset_size = SC_get_ARDF(stmt)->size_of_rowset_odbc2; if (vParam < 1) { vParam = 1; changed = TRUE; } if (conn) conn->ardOptions.size_of_rowset_odbc2 = vParam; if (stmt) SC_get_ARDF(stmt)->size_of_rowset_odbc2 = vParam; break; case SQL_SIMULATE_CURSOR: /* NOT SUPPORTED */ if (stmt) { SC_set_error(stmt, STMT_NOT_IMPLEMENTED_ERROR, "Simulated positioned update/delete not supported. Use the cursor library.", func); } if (conn) { CC_set_error(conn, CONN_NOT_IMPLEMENTED_ERROR, "Simulated positioned update/delete not supported. Use the cursor library.", func); } return SQL_ERROR; case SQL_USE_BOOKMARKS: if (stmt) {#if (ODBCVER >= 0x0300) mylog("USE_BOOKMARKS %s\n", (vParam == SQL_UB_OFF) ? "off" : ((vParam == SQL_UB_VARIABLE) ? "variable" : "fixed"));#endif /* ODBCVER */ setval = vParam; stmt->options.use_bookmarks = (SQLUINTEGER) setval; } if (conn) conn->stmtOptions.use_bookmarks = (SQLUINTEGER) vParam; break; case 1204: /* SQL_COPT_SS_PRESERVE_CURSORS ? */ if (stmt) { SC_set_error(stmt, STMT_OPTION_NOT_FOR_THE_DRIVER, "The option may be for MS SQL Server(Set)", func); } else if (conn) { CC_set_error(conn, CONN_OPTION_NOT_FOR_THE_DRIVER, "The option may be for MS SQL Server(Set)", func); } return SQL_ERROR; case 1227: /* SQL_SOPT_SS_HIDDEN_COLUMNS ? */ case 1228: /* SQL_SOPT_SS_NOBROWSETABLE ? */ if (stmt) {#ifndef NOT_USED if (0 != vParam) changed = TRUE; break;#endif /* NOT_USED */ SC_set_error(stmt, STMT_OPTION_NOT_FOR_THE_DRIVER, "The option may be for MS SQL Server(Set)", func); } else if (conn) { CC_set_error(conn, CONN_OPTION_NOT_FOR_THE_DRIVER, "The option may be for MS SQL Server(Set)", func); } return SQL_ERROR; default: { char option[64]; if (stmt) { SC_set_error(stmt, STMT_NOT_IMPLEMENTED_ERROR, "Unknown statement option (Set)", NULL); sprintf(option, "fOption=%d, vParam=" FORMAT_LEN, fOption, vParam); SC_log_error(func, option, stmt); } if (conn) { CC_set_error(conn, CONN_NOT_IMPLEMENTED_ERROR, "Unknown statement option (Set)", func); sprintf(option, "fOption=%d, vParam=" FORMAT_LEN, fOption, vParam); CC_log_error(func, option, conn); } return SQL_ERROR; } } if (changed) { if (stmt) { SC_set_error(stmt, STMT_OPTION_VALUE_CHANGED, "Requested value changed.", func); } if (conn) { CC_set_error(conn, CONN_OPTION_VALUE_CHANGED, "Requested value changed.", func); } return SQL_SUCCESS_WITH_INFO; } else return SQL_SUCCESS;}/* Implements only SQL_AUTOCOMMIT */RETCODE SQL_APIPGAPI_SetConnectOption( HDBC hdbc, SQLUSMALLINT fOption, SQLULEN vParam){ CSTR func = "PGAPI_SetConnectOption"; ConnectionClass *conn = (ConnectionClass *) hdbc; ConnInfo *ci = &(conn->connInfo); char changed = FALSE; RETCODE retval; BOOL autocomm_on; mylog("%s: entering fOption = %d vParam = %d\n", func, fOption, vParam); if (!conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; } switch (fOption) { /* * Statement Options (apply to all stmts on the connection and * become defaults for new stmts) */ case SQL_ASYNC_ENABLE: case SQL_BIND_TYPE: case SQL_CONCURRENCY: case SQL_CURSOR_TYPE: case SQL_KEYSET_SIZE: case SQL_MAX_LENGTH: case SQL_MAX_ROWS: case SQL_NOSCAN: case SQL_QUERY_TIMEOUT: case SQL_RETRIEVE_DATA: case SQL_ROWSET_SIZE: case SQL_SIMULATE_CURSOR: case SQL_USE_BOOKMARKS:#if (ODBCVER < 0x0300) { int i; /* Affect all current Statements */ for (i = 0; i < conn->num_stmts; i++) { if (conn->stmts[i]) set_statement_option(NULL, conn->stmts[i], fOption, vParam); } }#endif /* ODBCVER */ /* * Become the default for all future statements on this * connection */ retval = set_statement_option(conn, NULL, fOption, vParam); if (retval == SQL_SUCCESS_WITH_INFO) changed = TRUE; else if (retval == SQL_ERROR) return SQL_ERROR; break; /* * Connection Options */ case SQL_ACCESS_MODE: /* ignored */ break; case SQL_AUTOCOMMIT: switch (vParam) { case SQL_AUTOCOMMIT_ON: autocomm_on = TRUE; break; case SQL_AUTOCOMMIT_OFF: autocomm_on = FALSE; break; default: CC_set_error(conn, CONN_INVALID_ARGUMENT_NO, "Illegal parameter value for SQL_AUTOCOMMIT", func); return SQL_ERROR; } if (autocomm_on && SQL_AUTOCOMMIT_OFF != ci->autocommit_public) break; else if (!autocomm_on && SQL_AUTOCOMMIT_OFF == ci->autocommit_public) break; ci->autocommit_public = (autocomm_on ? SQL_AUTOCOMMIT_ON : SQL_AUTOCOMMIT_OFF); mylog("%s: AUTOCOMMIT: transact_status=%d, vparam=%d\n", func, conn->transact_status, vParam);#ifdef _HANDLE_ENLIST_IN_DTC_ if (NULL != conn->asdum) { mylog("%s: Ignored AUTOCOMMIT in a distributed transaction, OK ?"); break; }#endif /* _HANDLE_ENLIST_IN_DTC_ */ CC_set_autocommit(conn, autocomm_on); break; case SQL_CURRENT_QUALIFIER: /* ignored */ break; case SQL_LOGIN_TIMEOUT: conn->login_timeout = (SQLUINTEGER) vParam; break; case SQL_PACKET_SIZE: /* ignored */
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?