removed driver_version from conn struct
This commit is contained in:
parent
16c5556340
commit
a0e959a6e9
|
@ -26,11 +26,8 @@
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <winver.h>
|
#include <winver.h>
|
||||||
#endif // _WIN32
|
#endif // _WIN32
|
||||||
|
|
||||||
#include <string>
|
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <algorithm>
|
|
||||||
|
|
||||||
#ifndef _WIN32
|
#ifndef _WIN32
|
||||||
#include <sys/utsname.h>
|
#include <sys/utsname.h>
|
||||||
|
@ -136,7 +133,7 @@ sqlsrv_conn* core_sqlsrv_connect( _In_ sqlsrv_context& henv_cp, _In_ sqlsrv_cont
|
||||||
if( options_ht && zend_hash_num_elements( options_ht ) > 0 ) {
|
if( options_ht && zend_hash_num_elements( options_ht ) > 0 ) {
|
||||||
|
|
||||||
zval* option_z = NULL;
|
zval* option_z = NULL;
|
||||||
option_z = zend_hash_index_find(options_ht, SQLSRV_CONN_OPTION_CONN_POOLING);
|
option_z = zend_hash_index_find( options_ht, SQLSRV_CONN_OPTION_CONN_POOLING );
|
||||||
if ( option_z ) {
|
if ( option_z ) {
|
||||||
// if the option was found and it's not true, then use the non pooled environment handle
|
// if the option was found and it's not true, then use the non pooled environment handle
|
||||||
if(( Z_TYPE_P( option_z ) == IS_STRING && !core_str_zval_is_true( option_z )) || !zend_is_true( option_z ) ) {
|
if(( Z_TYPE_P( option_z ) == IS_STRING && !core_str_zval_is_true( option_z )) || !zend_is_true( option_z ) ) {
|
||||||
|
@ -152,28 +149,28 @@ sqlsrv_conn* core_sqlsrv_connect( _In_ sqlsrv_context& henv_cp, _In_ sqlsrv_cont
|
||||||
conn = conn_factory( temp_conn_h, err, driver TSRMLS_CC );
|
conn = conn_factory( temp_conn_h, err, driver TSRMLS_CC );
|
||||||
conn->set_func( driver_func );
|
conn->set_func( driver_func );
|
||||||
|
|
||||||
build_connection_string_and_set_conn_attr(conn, server, uid, pwd, options_ht, valid_conn_opts, driver, conn_str TSRMLS_CC);
|
build_connection_string_and_set_conn_attr( conn, server, uid, pwd, options_ht, valid_conn_opts, driver, conn_str TSRMLS_CC );
|
||||||
|
|
||||||
bool missing_driver_error = false;
|
bool missing_driver_error = false;
|
||||||
|
|
||||||
if (conn->is_driver_set) {
|
if ( conn->is_driver_set ) {
|
||||||
r = core_odbc_connect( conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled);
|
r = core_odbc_connect( conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled);
|
||||||
}
|
}
|
||||||
else if (conn->ce_option.enabled) {
|
else if ( conn->ce_option.enabled ) {
|
||||||
conn_str = conn_str + CONNECTION_STRING_DRIVER_NAME[DRIVER_VERSION::ODBC_DRIVER_17];
|
conn_str = conn_str + CONNECTION_STRING_DRIVER_NAME[ DRIVER_VERSION::ODBC_DRIVER_17 ];
|
||||||
r = core_odbc_connect( conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled);
|
r = core_odbc_connect( conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled);
|
||||||
|
|
||||||
CHECK_CUSTOM_ERROR(missing_driver_error, conn, SQLSRV_AE_ERROR_DRIVER_NOT_INSTALLED, get_processor_arch()) {
|
CHECK_CUSTOM_ERROR( missing_driver_error, conn, SQLSRV_AE_ERROR_DRIVER_NOT_INSTALLED, get_processor_arch()) {
|
||||||
throw core::CoreException();
|
throw core::CoreException();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
|
||||||
for ( std::size_t i = DRIVER_VERSION::ODBC_DRIVER_13; i <= DRIVER_VERSION::LAST; ++i ) {
|
for ( std::size_t i = DRIVER_VERSION::ODBC_DRIVER_13; i <= DRIVER_VERSION::LAST; ++i ) {
|
||||||
conn_str = conn_str + CONNECTION_STRING_DRIVER_NAME[DRIVER_VERSION(i)];
|
conn_str = conn_str + CONNECTION_STRING_DRIVER_NAME[ DRIVER_VERSION(i) ];
|
||||||
r = core_odbc_connect(conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled);
|
r = core_odbc_connect( conn, conn_str, wconn_string, wconn_len, missing_driver_error, is_pooled );
|
||||||
// if it's a IM002, meaning that the correct ODBC driver is not installed
|
// if it's a IM002, meaning that the correct ODBC driver is not installed
|
||||||
CHECK_CUSTOM_ERROR(missing_driver_error && (i == DRIVER_VERSION::LAST), conn, SQLSRV_ERROR_DRIVER_NOT_INSTALLED, get_processor_arch()) {
|
CHECK_CUSTOM_ERROR( missing_driver_error && ( i == DRIVER_VERSION::LAST ), conn, SQLSRV_ERROR_DRIVER_NOT_INSTALLED, get_processor_arch()) {
|
||||||
throw core::CoreException();
|
throw core::CoreException();
|
||||||
}
|
}
|
||||||
if ( !missing_driver_error ) {
|
if ( !missing_driver_error ) {
|
||||||
|
@ -214,21 +211,21 @@ sqlsrv_conn* core_sqlsrv_connect( _In_ sqlsrv_context& henv_cp, _In_ sqlsrv_cont
|
||||||
DIE( "C++ memory allocation failure building the connection string." );
|
DIE( "C++ memory allocation failure building the connection string." );
|
||||||
}
|
}
|
||||||
catch( std::out_of_range const& ex ) {
|
catch( std::out_of_range const& ex ) {
|
||||||
memset( const_cast<char*>(conn_str.c_str()), 0, conn_str.size() );
|
memset( const_cast<char*>( conn_str.c_str()), 0, conn_str.size() );
|
||||||
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
||||||
LOG( SEV_ERROR, "C++ exception returned: %1!s!", ex.what() );
|
LOG( SEV_ERROR, "C++ exception returned: %1!s!", ex.what() );
|
||||||
conn->invalidate();
|
conn->invalidate();
|
||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
catch( std::length_error const& ex ) {
|
catch( std::length_error const& ex ) {
|
||||||
memset( const_cast<char*>(conn_str.c_str()), 0, conn_str.size() );
|
memset( const_cast<char*>( conn_str.c_str()), 0, conn_str.size() );
|
||||||
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
||||||
LOG( SEV_ERROR, "C++ exception returned: %1!s!", ex.what() );
|
LOG( SEV_ERROR, "C++ exception returned: %1!s!", ex.what() );
|
||||||
conn->invalidate();
|
conn->invalidate();
|
||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
catch( core::CoreException& ) {
|
catch( core::CoreException& ) {
|
||||||
memset( const_cast<char*>(conn_str.c_str()), 0, conn_str.size() );
|
memset( const_cast<char*>( conn_str.c_str()), 0, conn_str.size() );
|
||||||
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
||||||
conn->invalidate();
|
conn->invalidate();
|
||||||
throw;
|
throw;
|
||||||
|
@ -247,11 +244,11 @@ SQLRETURN core_odbc_connect(_Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn
|
||||||
|
|
||||||
// We only support UTF-8 encoding for connection string.
|
// We only support UTF-8 encoding for connection string.
|
||||||
// Convert our UTF-8 connection string to UTF-16 before connecting with SQLDriverConnnectW
|
// Convert our UTF-8 connection string to UTF-16 before connecting with SQLDriverConnnectW
|
||||||
wconn_len = static_cast<unsigned int>(conn_str.length() + 1) * sizeof(SQLWCHAR);
|
wconn_len = static_cast<unsigned int>( conn_str.length() + 1 ) * sizeof( SQLWCHAR );
|
||||||
|
|
||||||
wconn_string = utf16_string_from_mbcs_string(SQLSRV_ENCODING_UTF8, conn_str.c_str(), static_cast<unsigned int>(conn_str.length()), &wconn_len);
|
wconn_string = utf16_string_from_mbcs_string( SQLSRV_ENCODING_UTF8, conn_str.c_str(), static_cast<unsigned int>( conn_str.length()), &wconn_len );
|
||||||
|
|
||||||
CHECK_CUSTOM_ERROR(wconn_string == 0, conn, SQLSRV_ERROR_CONNECT_STRING_ENCODING_TRANSLATE, get_last_error_message())
|
CHECK_CUSTOM_ERROR( wconn_string == 0, conn, SQLSRV_ERROR_CONNECT_STRING_ENCODING_TRANSLATE, get_last_error_message())
|
||||||
{
|
{
|
||||||
throw core::CoreException();
|
throw core::CoreException();
|
||||||
}
|
}
|
||||||
|
@ -269,23 +266,20 @@ SQLRETURN core_odbc_connect(_Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn
|
||||||
r = SQLDriverConnectW(conn->handle(), NULL, wconn_string, static_cast<SQLSMALLINT>(wconn_len), NULL, 0, &output_conn_size, SQL_DRIVER_NOPROMPT);
|
r = SQLDriverConnectW(conn->handle(), NULL, wconn_string, static_cast<SQLSMALLINT>(wconn_len), NULL, 0, &output_conn_size, SQL_DRIVER_NOPROMPT);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
r = SQLDriverConnectW(conn->handle(), NULL, wconn_string, static_cast<SQLSMALLINT>(wconn_len), NULL, 0, &output_conn_size, SQL_DRIVER_NOPROMPT);
|
r = SQLDriverConnectW( conn->handle(), NULL, wconn_string, static_cast<SQLSMALLINT>(wconn_len), NULL, 0, &output_conn_size, SQL_DRIVER_NOPROMPT );
|
||||||
#endif // !_WIN32
|
#endif // !_WIN32
|
||||||
|
|
||||||
// clear the connection string from memory to remove sensitive data (such as a password).
|
// clear the connection string from memory to remove sensitive data (such as a password).
|
||||||
memset(const_cast<char*>(conn_str.c_str()), 0, conn_str.size());
|
memset( const_cast<char*>( conn_str.c_str() ), 0, conn_str.size() );
|
||||||
memset(wconn_string, 0, wconn_len * sizeof(SQLWCHAR)); // wconn_len is the number of characters, not bytes
|
memset( wconn_string, 0, wconn_len * sizeof( SQLWCHAR )); // wconn_len is the number of characters, not bytes
|
||||||
wconn_len = 0;
|
wconn_len = 0;
|
||||||
conn_str.clear();
|
conn_str.clear();
|
||||||
|
|
||||||
if (SQL_SUCCEEDED(r)) {
|
if (!SQL_SUCCEEDED(r)) {
|
||||||
//conn->driver_version = static_cast<DRIVER_VERSION>(odbc_version);
|
SQLCHAR state[ SQL_SQLSTATE_BUFSIZE ];
|
||||||
}
|
|
||||||
else {
|
|
||||||
SQLCHAR state[SQL_SQLSTATE_BUFSIZE];
|
|
||||||
SQLSMALLINT len;
|
SQLSMALLINT len;
|
||||||
SQLRETURN sr = SQLGetDiagField(SQL_HANDLE_DBC, conn->handle(), 1, SQL_DIAG_SQLSTATE, state, SQL_SQLSTATE_BUFSIZE, &len);
|
SQLRETURN sr = SQLGetDiagField( SQL_HANDLE_DBC, conn->handle(), 1, SQL_DIAG_SQLSTATE, state, SQL_SQLSTATE_BUFSIZE, &len );
|
||||||
missing_driver_error = (SQL_SUCCEEDED(sr) && state[0] == 'I' && state[1] == 'M' && state[2] == '0' && state[3] == '0' && state[4] == '2');
|
missing_driver_error = ( SQL_SUCCEEDED(sr) && state[0] == 'I' && state[1] == 'M' && state[2] == '0' && state[3] == '0' && state[4] == '2' );
|
||||||
}
|
}
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
|
@ -151,6 +151,7 @@ OACR_WARNING_POP
|
||||||
|
|
||||||
#include <deque>
|
#include <deque>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
#include <string>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <limits>
|
#include <limits>
|
||||||
#include <cassert>
|
#include <cassert>
|
||||||
|
@ -1067,8 +1068,6 @@ struct sqlsrv_conn : public sqlsrv_context {
|
||||||
// instance variables
|
// instance variables
|
||||||
SERVER_VERSION server_version; // version of the server that we're connected to
|
SERVER_VERSION server_version; // version of the server that we're connected to
|
||||||
|
|
||||||
DRIVER_VERSION driver_version;
|
|
||||||
|
|
||||||
col_encryption_option ce_option; // holds the details of what are required to enable column encryption
|
col_encryption_option ce_option; // holds the details of what are required to enable column encryption
|
||||||
bool is_driver_set;
|
bool is_driver_set;
|
||||||
|
|
||||||
|
@ -1077,7 +1076,6 @@ struct sqlsrv_conn : public sqlsrv_context {
|
||||||
sqlsrv_context( h, SQL_HANDLE_DBC, e, drv, encoding )
|
sqlsrv_context( h, SQL_HANDLE_DBC, e, drv, encoding )
|
||||||
{
|
{
|
||||||
server_version = SERVER_VERSION_UNKNOWN;
|
server_version = SERVER_VERSION_UNKNOWN;
|
||||||
driver_version = ODBC_DRIVER_UNKNOWN;
|
|
||||||
is_driver_set = false;
|
is_driver_set = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1201,6 +1199,8 @@ struct connection_option {
|
||||||
void (*func)( connection_option const*, zval* value, sqlsrv_conn* conn, std::string& conn_str TSRMLS_DC );
|
void (*func)( connection_option const*, zval* value, sqlsrv_conn* conn, std::string& conn_str TSRMLS_DC );
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// connection attribute functions
|
||||||
|
|
||||||
// simply add the parsed value to the connection string
|
// simply add the parsed value to the connection string
|
||||||
struct conn_str_append_func {
|
struct conn_str_append_func {
|
||||||
|
|
||||||
|
@ -1212,6 +1212,21 @@ struct conn_null_func {
|
||||||
static void func( connection_option const* /*option*/, zval* /*value*/, sqlsrv_conn* /*conn*/, std::string& /*conn_str*/ TSRMLS_DC );
|
static void func( connection_option const* /*option*/, zval* /*value*/, sqlsrv_conn* /*conn*/, std::string& /*conn_str*/ TSRMLS_DC );
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <unsigned int Attr>
|
||||||
|
struct str_conn_attr_func {
|
||||||
|
|
||||||
|
static void func(connection_option const* /*option*/, zval* value, _Inout_ sqlsrv_conn* conn, std::string& /*conn_str*/ TSRMLS_DC)
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
core::SQLSetConnectAttr(conn, Attr, reinterpret_cast<SQLPOINTER>(Z_STRVAL_P(value)),
|
||||||
|
static_cast<SQLINTEGER>(Z_STRLEN_P(value)) TSRMLS_CC);
|
||||||
|
}
|
||||||
|
catch (core::CoreException&) {
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
struct column_encryption_set_func {
|
struct column_encryption_set_func {
|
||||||
|
|
||||||
static void func( _In_ connection_option const* option, _In_ zval* value, _Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn_str TSRMLS_DC);
|
static void func( _In_ connection_option const* option, _In_ zval* value, _Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn_str TSRMLS_DC);
|
||||||
|
@ -1239,7 +1254,8 @@ sqlsrv_conn* core_sqlsrv_connect( _In_ sqlsrv_context& henv_cp, _In_ sqlsrv_cont
|
||||||
_Inout_z_ const char* server, _Inout_opt_z_ const char* uid, _Inout_opt_z_ const char* pwd,
|
_Inout_z_ const char* server, _Inout_opt_z_ const char* uid, _Inout_opt_z_ const char* pwd,
|
||||||
_Inout_opt_ HashTable* options_ht, _In_ error_callback err, _In_ const connection_option valid_conn_opts[],
|
_Inout_opt_ HashTable* options_ht, _In_ error_callback err, _In_ const connection_option valid_conn_opts[],
|
||||||
_In_ void* driver, _In_z_ const char* driver_func TSRMLS_DC );
|
_In_ void* driver, _In_z_ const char* driver_func TSRMLS_DC );
|
||||||
SQLRETURN core_odbc_connect( _Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn_str, _Inout_ SQLWCHAR* wconn_string, _Inout_ unsigned int& wconn_len, _Inout_ bool& missing_driver_error);
|
SQLRETURN core_odbc_connect( _Inout_ sqlsrv_conn* conn, _Inout_ std::string& conn_str, _Inout_ SQLWCHAR* wconn_string,
|
||||||
|
_Inout_ unsigned int& wconn_len, _Inout_ bool& missing_driver_error, _In_ bool is_pooled);
|
||||||
void core_sqlsrv_close( _Inout_opt_ sqlsrv_conn* conn TSRMLS_DC );
|
void core_sqlsrv_close( _Inout_opt_ sqlsrv_conn* conn TSRMLS_DC );
|
||||||
void core_sqlsrv_prepare( _Inout_ sqlsrv_stmt* stmt, _In_reads_bytes_(sql_len) const char* sql, _In_ SQLLEN sql_len TSRMLS_DC );
|
void core_sqlsrv_prepare( _Inout_ sqlsrv_stmt* stmt, _In_reads_bytes_(sql_len) const char* sql, _In_ SQLLEN sql_len TSRMLS_DC );
|
||||||
void core_sqlsrv_begin_transaction( _Inout_ sqlsrv_conn* conn TSRMLS_DC );
|
void core_sqlsrv_begin_transaction( _Inout_ sqlsrv_conn* conn TSRMLS_DC );
|
||||||
|
@ -1692,10 +1708,6 @@ enum SQLSRV_ERROR_CODES {
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// the message returned by ODBC Driver 11 for SQL Server
|
|
||||||
static const char* CONNECTION_BUSY_ODBC_ERROR[] = { "[Microsoft][ODBC Driver 13 for SQL Server]Connection is busy with results for another command",
|
|
||||||
"[Microsoft][ODBC Driver 11 for SQL Server]Connection is busy with results for another command" };
|
|
||||||
|
|
||||||
// SQLSTATE for all internal errors
|
// SQLSTATE for all internal errors
|
||||||
extern SQLCHAR IMSSP[];
|
extern SQLCHAR IMSSP[];
|
||||||
|
|
||||||
|
@ -1871,8 +1883,12 @@ namespace core {
|
||||||
|
|
||||||
throw CoreException();
|
throw CoreException();
|
||||||
}
|
}
|
||||||
std::size_t driver_version = stmt->conn->driver_version;
|
|
||||||
if( !strcmp( reinterpret_cast<const char*>( err_msg ), CONNECTION_BUSY_ODBC_ERROR[driver_version] )) {
|
// the message returned by ODBC Driver for SQL Server
|
||||||
|
const std::string connection_busy_error( "Connection is busy with results for another command" );
|
||||||
|
const std::string returned_error( reinterpret_cast<char*>( err_msg ));
|
||||||
|
|
||||||
|
if(( returned_error.find( connection_busy_error ) == std::string::npos )) {
|
||||||
|
|
||||||
THROW_CORE_ERROR( stmt, SQLSRV_ERROR_MARS_OFF );
|
THROW_CORE_ERROR( stmt, SQLSRV_ERROR_MARS_OFF );
|
||||||
}
|
}
|
||||||
|
@ -2420,20 +2436,5 @@ sqlsrv_conn* allocate_conn( _In_ SQLHANDLE h, _In_ error_callback e, _In_ void*
|
||||||
|
|
||||||
} // namespace core
|
} // namespace core
|
||||||
|
|
||||||
// connection attribute functions
|
|
||||||
template <unsigned int Attr>
|
|
||||||
struct str_conn_attr_func {
|
|
||||||
|
|
||||||
static void func( connection_option const* /*option*/, zval* value, _Inout_ sqlsrv_conn* conn, std::string& /*conn_str*/ TSRMLS_DC )
|
|
||||||
{
|
|
||||||
try {
|
|
||||||
core::SQLSetConnectAttr( conn, Attr, reinterpret_cast<SQLPOINTER>( Z_STRVAL_P( value )),
|
|
||||||
static_cast<SQLINTEGER>(Z_STRLEN_P( value )) TSRMLS_CC );
|
|
||||||
}
|
|
||||||
catch( core::CoreException& ) {
|
|
||||||
throw;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // CORE_SQLSRV_H
|
#endif // CORE_SQLSRV_H
|
||||||
|
|
Loading…
Reference in a new issue