merged conversion functions in core_sqlsrv and core_util
This commit is contained in:
parent
cb88f51e16
commit
08c9ca87e1
|
@ -226,7 +226,7 @@ void core_sqlsrv_register_logger( log_callback );
|
||||||
void write_to_log( unsigned int severity TSRMLS_DC, const char* msg, ... );
|
void write_to_log( unsigned int severity TSRMLS_DC, const char* msg, ... );
|
||||||
|
|
||||||
// a macro to make it convenient to use the function.
|
// a macro to make it convenient to use the function.
|
||||||
#define LOG( severity, msg, ...) write_to_log( severity TSRMLS_CC, msg, __VA_ARGS__ )
|
#define LOG( severity, msg, ...) write_to_log( severity TSRMLS_CC, msg, ## __VA_ARGS__ )
|
||||||
|
|
||||||
// mask for filtering which severities are written to the log
|
// mask for filtering which severities are written to the log
|
||||||
enum logging_severity {
|
enum logging_severity {
|
||||||
|
@ -238,7 +238,7 @@ enum logging_severity {
|
||||||
|
|
||||||
// Kill the PHP process and log the message to PHP
|
// Kill the PHP process and log the message to PHP
|
||||||
void die( const char* msg, ... );
|
void die( const char* msg, ... );
|
||||||
#define DIE( msg, ... ) { die( msg, __VA_ARGS__ ); }
|
#define DIE( msg, ... ) { die( msg, ## __VA_ARGS__ ); }
|
||||||
|
|
||||||
|
|
||||||
//*********************************************************************************************************************************
|
//*********************************************************************************************************************************
|
||||||
|
@ -588,9 +588,9 @@ public:
|
||||||
// free the original pointer and assign a new pointer. Use NULL to simply free the pointer.
|
// free the original pointer and assign a new pointer. Use NULL to simply free the pointer.
|
||||||
void reset( T* ptr = NULL )
|
void reset( T* ptr = NULL )
|
||||||
{
|
{
|
||||||
if( _ptr )
|
if( sqlsrv_auto_ptr<T,sqlsrv_malloc_auto_ptr<T> >::_ptr )
|
||||||
sqlsrv_free( (void*) _ptr );
|
sqlsrv_free( (void*) sqlsrv_auto_ptr<T,sqlsrv_malloc_auto_ptr<T> >::_ptr );
|
||||||
_ptr = ptr;
|
sqlsrv_auto_ptr<T,sqlsrv_malloc_auto_ptr<T> >::_ptr = ptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
T* operator=( T* ptr )
|
T* operator=( T* ptr )
|
||||||
|
@ -608,8 +608,8 @@ public:
|
||||||
// DO NOT CALL sqlsrv_realloc with a sqlsrv_malloc_auto_ptr. Use the resize member function.
|
// DO NOT CALL sqlsrv_realloc with a sqlsrv_malloc_auto_ptr. Use the resize member function.
|
||||||
// has the same parameter list as sqlsrv_realloc: new_size is the size in bytes of the newly allocated buffer
|
// has the same parameter list as sqlsrv_realloc: new_size is the size in bytes of the newly allocated buffer
|
||||||
void resize( size_t new_size )
|
void resize( size_t new_size )
|
||||||
{
|
{
|
||||||
_ptr = reinterpret_cast<T*>( sqlsrv_realloc( _ptr, new_size ));
|
sqlsrv_auto_ptr<T,sqlsrv_malloc_auto_ptr<T> >::_ptr = reinterpret_cast<T*>( sqlsrv_realloc( sqlsrv_auto_ptr<T,sqlsrv_malloc_auto_ptr<T> >::_ptr, new_size ));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -776,7 +776,7 @@ public:
|
||||||
{
|
{
|
||||||
sqlsrv_error* p = src.get();
|
sqlsrv_error* p = src.get();
|
||||||
src.transferred();
|
src.transferred();
|
||||||
this->_ptr = p;
|
reset( p );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -804,8 +804,8 @@ class sqlsrv_context {
|
||||||
sqlsrv_context( SQLSMALLINT type, error_callback e, void* drv, SQLSRV_ENCODING encoding = SQLSRV_ENCODING_INVALID ) :
|
sqlsrv_context( SQLSMALLINT type, error_callback e, void* drv, SQLSRV_ENCODING encoding = SQLSRV_ENCODING_INVALID ) :
|
||||||
handle_( SQL_NULL_HANDLE ),
|
handle_( SQL_NULL_HANDLE ),
|
||||||
handle_type_( type ),
|
handle_type_( type ),
|
||||||
err_( e ),
|
|
||||||
name_( NULL ),
|
name_( NULL ),
|
||||||
|
err_( e ),
|
||||||
driver_( drv ),
|
driver_( drv ),
|
||||||
last_error_(),
|
last_error_(),
|
||||||
encoding_( encoding )
|
encoding_( encoding )
|
||||||
|
@ -815,8 +815,8 @@ class sqlsrv_context {
|
||||||
sqlsrv_context( SQLHANDLE h, SQLSMALLINT t, error_callback e, void* drv, SQLSRV_ENCODING encoding = SQLSRV_ENCODING_INVALID ) :
|
sqlsrv_context( SQLHANDLE h, SQLSMALLINT t, error_callback e, void* drv, SQLSRV_ENCODING encoding = SQLSRV_ENCODING_INVALID ) :
|
||||||
handle_( h ),
|
handle_( h ),
|
||||||
handle_type_( t ),
|
handle_type_( t ),
|
||||||
err_( e ),
|
|
||||||
name_( NULL ),
|
name_( NULL ),
|
||||||
|
err_( e ),
|
||||||
driver_( drv ),
|
driver_( drv ),
|
||||||
last_error_(),
|
last_error_(),
|
||||||
encoding_( encoding )
|
encoding_( encoding )
|
||||||
|
@ -826,13 +826,17 @@ class sqlsrv_context {
|
||||||
sqlsrv_context( sqlsrv_context const& ctx ) :
|
sqlsrv_context( sqlsrv_context const& ctx ) :
|
||||||
handle_( ctx.handle_ ),
|
handle_( ctx.handle_ ),
|
||||||
handle_type_( ctx.handle_type_ ),
|
handle_type_( ctx.handle_type_ ),
|
||||||
err_( ctx.err_ ),
|
|
||||||
name_( ctx.name_ ),
|
name_( ctx.name_ ),
|
||||||
|
err_( ctx.err_ ),
|
||||||
driver_( ctx.driver_ ),
|
driver_( ctx.driver_ ),
|
||||||
last_error_( ctx.last_error_ )
|
last_error_( ctx.last_error_ )
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual ~sqlsrv_context()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
void set_func( const char* f )
|
void set_func( const char* f )
|
||||||
{
|
{
|
||||||
name_ = f;
|
name_ = f;
|
||||||
|
@ -997,6 +1001,8 @@ struct sqlsrv_conn : public sqlsrv_context {
|
||||||
sqlsrv_conn( SQLHANDLE h, error_callback e, void* drv, SQLSRV_ENCODING encoding TSRMLS_DC ) :
|
sqlsrv_conn( SQLHANDLE h, error_callback e, void* drv, SQLSRV_ENCODING encoding TSRMLS_DC ) :
|
||||||
sqlsrv_context( h, SQL_HANDLE_DBC, e, drv, encoding )
|
sqlsrv_context( h, SQL_HANDLE_DBC, e, drv, encoding )
|
||||||
{
|
{
|
||||||
|
server_version = SERVER_VERSION_UNKNOWN;
|
||||||
|
driver_version = ODBC_DRIVER_13;
|
||||||
}
|
}
|
||||||
|
|
||||||
// sqlsrv_conn has no destructor since its allocated using placement new, which requires that the destructor be
|
// sqlsrv_conn has no destructor since its allocated using placement new, which requires that the destructor be
|
||||||
|
@ -1186,14 +1192,13 @@ struct sqlsrv_stream {
|
||||||
SQLUSMALLINT field_index;
|
SQLUSMALLINT field_index;
|
||||||
SQLSMALLINT sql_type;
|
SQLSMALLINT sql_type;
|
||||||
sqlsrv_stmt* stmt;
|
sqlsrv_stmt* stmt;
|
||||||
std::size_t stmt_index;
|
|
||||||
|
|
||||||
sqlsrv_stream( zval* str_z, SQLSRV_ENCODING enc ) :
|
sqlsrv_stream( zval* str_z, SQLSRV_ENCODING enc ) :
|
||||||
stream_z( str_z ), encoding( enc )
|
stream_z( str_z ), encoding( enc ), field_index( 0 ), sql_type( SQL_UNKNOWN_TYPE ), stmt( NULL )
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
sqlsrv_stream() : stream_z( NULL ), encoding( SQLSRV_ENCODING_INVALID ), stmt( NULL )
|
sqlsrv_stream() : stream_z( NULL ), encoding( SQLSRV_ENCODING_INVALID ), field_index( 0 ), sql_type( SQL_UNKNOWN_TYPE ), stmt( NULL )
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -1226,8 +1231,8 @@ struct sqlsrv_output_param {
|
||||||
// every other type output parameter constructor
|
// every other type output parameter constructor
|
||||||
sqlsrv_output_param( zval* p_z, int num, bool is_bool ) :
|
sqlsrv_output_param( zval* p_z, int num, bool is_bool ) :
|
||||||
param_z( p_z ),
|
param_z( p_z ),
|
||||||
param_num( num ),
|
|
||||||
encoding( SQLSRV_ENCODING_INVALID ),
|
encoding( SQLSRV_ENCODING_INVALID ),
|
||||||
|
param_num( num ),
|
||||||
original_buffer_len( -1 ),
|
original_buffer_len( -1 ),
|
||||||
is_bool( is_bool )
|
is_bool( is_bool )
|
||||||
{
|
{
|
||||||
|
@ -1310,7 +1315,11 @@ const int SQLSRV_DEFAULT_SIZE = -1; // size given for an output parameter th
|
||||||
const unsigned int QUERY_TIMEOUT_INVALID = 0xffffffff;
|
const unsigned int QUERY_TIMEOUT_INVALID = 0xffffffff;
|
||||||
|
|
||||||
// special buffered query constant
|
// special buffered query constant
|
||||||
|
#ifdef __linux__
|
||||||
|
const size_t SQLSRV_CURSOR_BUFFERED = 42; // arbitrary number that doesn't map to any other SQL_CURSOR_* constant
|
||||||
|
#else
|
||||||
const size_t SQLSRV_CURSOR_BUFFERED = 0xfffffffeUL; // arbitrary number that doesn't map to any other SQL_CURSOR_* constant
|
const size_t SQLSRV_CURSOR_BUFFERED = 0xfffffffeUL; // arbitrary number that doesn't map to any other SQL_CURSOR_* constant
|
||||||
|
#endif
|
||||||
|
|
||||||
// factory to create a statement
|
// factory to create a statement
|
||||||
typedef sqlsrv_stmt* (*driver_stmt_factory)( sqlsrv_conn* conn, SQLHANDLE h, error_callback e, void* drv TSRMLS_DC );
|
typedef sqlsrv_stmt* (*driver_stmt_factory)( sqlsrv_conn* conn, SQLHANDLE h, error_callback e, void* drv TSRMLS_DC );
|
||||||
|
@ -1519,9 +1528,8 @@ struct sqlsrv_buffered_result_set : public sqlsrv_result_set {
|
||||||
bool convert_string_from_utf16_inplace( SQLSRV_ENCODING encoding, char** string, SQLLEN& len);
|
bool convert_string_from_utf16_inplace( SQLSRV_ENCODING encoding, char** string, SQLLEN& len);
|
||||||
bool convert_zval_string_from_utf16(SQLSRV_ENCODING encoding, zval* value_z, SQLLEN& len);
|
bool convert_zval_string_from_utf16(SQLSRV_ENCODING encoding, zval* value_z, SQLLEN& len);
|
||||||
bool validate_string(char* string, SQLLEN& len);
|
bool validate_string(char* string, SQLLEN& len);
|
||||||
bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const wchar_t* inString, SQLINTEGER cchInLen, char** outString, SQLLEN& cchOutLen );
|
bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const SQLWCHAR* inString, SQLINTEGER cchInLen, char** outString, SQLLEN& cchOutLen );
|
||||||
wchar_t* utf16_string_from_mbcs_string( SQLSRV_ENCODING php_encoding, const char* mbcs_string,
|
SQLWCHAR* utf16_string_from_mbcs_string( SQLSRV_ENCODING php_encoding, const char* mbcs_string, unsigned int mbcs_len, _Out_ unsigned int* utf16_len );
|
||||||
unsigned int mbcs_len, _Out_ unsigned int* utf16_len );
|
|
||||||
|
|
||||||
//*********************************************************************************************************************************
|
//*********************************************************************************************************************************
|
||||||
// Error handling routines and Predefined Errors
|
// Error handling routines and Predefined Errors
|
||||||
|
@ -1744,13 +1752,13 @@ namespace core {
|
||||||
// and return a more helpful message prepended to the ODBC errors if that error occurs
|
// and return a more helpful message prepended to the ODBC errors if that error occurs
|
||||||
if( !SQL_SUCCEEDED( r )) {
|
if( !SQL_SUCCEEDED( r )) {
|
||||||
|
|
||||||
SQLCHAR err_msg[ SQL_MAX_MESSAGE_LENGTH + 1 ];
|
SQLCHAR err_msg[ SQL_MAX_MESSAGE_LENGTH + 1 ] = { '\0' };
|
||||||
SQLSMALLINT len = 0;
|
SQLSMALLINT len = 0;
|
||||||
|
|
||||||
SQLRETURN r = ::SQLGetDiagField( stmt->handle_type(), stmt->handle(), 1, SQL_DIAG_MESSAGE_TEXT,
|
SQLRETURN rtemp = ::SQLGetDiagField( stmt->handle_type(), stmt->handle(), 1, SQL_DIAG_MESSAGE_TEXT,
|
||||||
err_msg, SQL_MAX_MESSAGE_LENGTH, &len );
|
err_msg, SQL_MAX_MESSAGE_LENGTH, &len );
|
||||||
|
|
||||||
CHECK_SQL_ERROR_OR_WARNING( r, stmt ) {
|
CHECK_SQL_ERROR_OR_WARNING( rtemp, stmt ) {
|
||||||
|
|
||||||
throw CoreException();
|
throw CoreException();
|
||||||
}
|
}
|
||||||
|
@ -1889,7 +1897,7 @@ namespace core {
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline SQLRETURN SQLExecDirectW( sqlsrv_stmt* stmt, wchar_t* wsql TSRMLS_DC )
|
inline SQLRETURN SQLExecDirectW( sqlsrv_stmt* stmt, SQLWCHAR* wsql TSRMLS_DC )
|
||||||
{
|
{
|
||||||
SQLRETURN r;
|
SQLRETURN r;
|
||||||
r = ::SQLExecDirectW( stmt->handle(), reinterpret_cast<SQLWCHAR*>( wsql ), SQL_NTS );
|
r = ::SQLExecDirectW( stmt->handle(), reinterpret_cast<SQLWCHAR*>( wsql ), SQL_NTS );
|
||||||
|
@ -2263,7 +2271,7 @@ namespace core {
|
||||||
inline void sqlsrv_zend_hash_add( sqlsrv_context& ctx, HashTable* ht, zend_string* key, unsigned int key_len, zval* data,
|
inline void sqlsrv_zend_hash_add( sqlsrv_context& ctx, HashTable* ht, zend_string* key, unsigned int key_len, zval* data,
|
||||||
unsigned int data_size, zval* pDest TSRMLS_DC )
|
unsigned int data_size, zval* pDest TSRMLS_DC )
|
||||||
{
|
{
|
||||||
int zr = (pDest = ::zend_hash_add(ht, key, data)) != NULL ? SUCCESS : FAILURE;
|
int zr = ::zend_hash_add(ht, key, data) != NULL ? SUCCESS : FAILURE;
|
||||||
CHECK_ZEND_ERROR( zr, ctx, SQLSRV_ERROR_ZEND_HASH ) {
|
CHECK_ZEND_ERROR( zr, ctx, SQLSRV_ERROR_ZEND_HASH ) {
|
||||||
throw CoreException();
|
throw CoreException();
|
||||||
}
|
}
|
||||||
|
|
|
@ -35,7 +35,7 @@ char last_err_msg[ 2048 ]; // 2k to hold the error messages
|
||||||
// routine used by utf16_string_from_mbcs_string
|
// routine used by utf16_string_from_mbcs_string
|
||||||
unsigned int convert_string_from_default_encoding( unsigned int php_encoding, _In_reads_bytes_(mbcs_len) char const* mbcs_in_string,
|
unsigned int convert_string_from_default_encoding( unsigned int php_encoding, _In_reads_bytes_(mbcs_len) char const* mbcs_in_string,
|
||||||
unsigned int mbcs_len,
|
unsigned int mbcs_len,
|
||||||
_Out_writes_(utf16_len) __transfer( mbcs_in_string ) wchar_t* utf16_out_string,
|
_Out_writes_(utf16_len) __transfer( mbcs_in_string ) SQLWCHAR* utf16_out_string,
|
||||||
unsigned int utf16_len );
|
unsigned int utf16_len );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -81,8 +81,7 @@ bool convert_string_from_utf16_inplace( SQLSRV_ENCODING encoding, char** string,
|
||||||
char* outString = NULL;
|
char* outString = NULL;
|
||||||
SQLLEN outLen = 0;
|
SQLLEN outLen = 0;
|
||||||
|
|
||||||
bool result = convert_string_from_utf16( encoding,
|
bool result = convert_string_from_utf16( encoding, reinterpret_cast<const SQLWCHAR*>(*string), int(len / sizeof(SQLWCHAR)), &outString, outLen );
|
||||||
reinterpret_cast<const wchar_t*>(*string), int(len / sizeof(wchar_t)), &outString, outLen);
|
|
||||||
|
|
||||||
if (result)
|
if (result)
|
||||||
{
|
{
|
||||||
|
@ -105,8 +104,7 @@ bool convert_zval_string_from_utf16(SQLSRV_ENCODING encoding, zval* value_z, SQL
|
||||||
char* outString = NULL;
|
char* outString = NULL;
|
||||||
SQLLEN outLen = 0;
|
SQLLEN outLen = 0;
|
||||||
|
|
||||||
bool result = convert_string_from_utf16(encoding,
|
bool result = convert_string_from_utf16( encoding, reinterpret_cast<const SQLWCHAR*>(string), int(len / sizeof(SQLWCHAR)), &outString, outLen );
|
||||||
reinterpret_cast<const wchar_t*>(string), int(len / sizeof(wchar_t)), &outString, outLen);
|
|
||||||
|
|
||||||
if (result)
|
if (result)
|
||||||
{
|
{
|
||||||
|
@ -127,16 +125,16 @@ bool validate_string(char* string, SQLLEN& len)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((len / sizeof(wchar_t)) > INT_MAX)
|
if ((len / sizeof(SQLWCHAR)) > INT_MAX)
|
||||||
{
|
{
|
||||||
LOG(SEV_ERROR, "UTP-16 (wide character) string mapping: buffer length exceeded.");
|
LOG(SEV_ERROR, "UTP-16 (wide character) string mapping: buffer length exceeded.");
|
||||||
throw core::CoreException();
|
throw core::CoreException();
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const wchar_t* inString, SQLINTEGER cchInLen, char** outString, SQLLEN& cchOutLen )
|
bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const SQLWCHAR* inString, SQLINTEGER cchInLen, char** outString, SQLLEN& cchOutLen )
|
||||||
{
|
{
|
||||||
SQLSRV_ASSERT( inString != NULL, "Input string must be specified" );
|
SQLSRV_ASSERT( inString != NULL, "Input string must be specified" );
|
||||||
SQLSRV_ASSERT( outString != NULL, "Output buffer pointer must be specified" );
|
SQLSRV_ASSERT( outString != NULL, "Output buffer pointer must be specified" );
|
||||||
|
@ -158,18 +156,28 @@ bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const wchar_t* inStrin
|
||||||
}
|
}
|
||||||
|
|
||||||
// calculate the number of characters needed
|
// calculate the number of characters needed
|
||||||
|
#ifdef __linux__
|
||||||
|
cchOutLen = SystemLocale::FromUtf16Strict( encoding, inString, cchInLen, NULL, 0 );
|
||||||
|
#else
|
||||||
cchOutLen = WideCharToMultiByte( encoding, flags,
|
cchOutLen = WideCharToMultiByte( encoding, flags,
|
||||||
inString, cchInLen,
|
inString, cchInLen,
|
||||||
NULL, 0, NULL, NULL );
|
NULL, 0, NULL, NULL );
|
||||||
|
#endif
|
||||||
|
|
||||||
if( cchOutLen == 0 ) {
|
if( cchOutLen == 0 ) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create a buffer to fit the encoded string
|
// Create a buffer to fit the encoded string
|
||||||
char* newString = reinterpret_cast<char*>( sqlsrv_malloc( cchOutLen + 1 /* NULL char*/ ));
|
char* newString = reinterpret_cast<char*>( sqlsrv_malloc( cchOutLen + 1 /* NULL char*/ ));
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
int rc = SystemLocale::FromUtf16( encoding, inString, cchInLen, newString, static_cast<int>(cchOutLen));
|
||||||
|
#else
|
||||||
int rc = WideCharToMultiByte( encoding, flags,
|
int rc = WideCharToMultiByte( encoding, flags,
|
||||||
inString, cchInLen,
|
inString, cchInLen,
|
||||||
newString, static_cast<int>(cchOutLen), NULL, NULL );
|
newString, static_cast<int>(cchOutLen), NULL, NULL );
|
||||||
|
#endif
|
||||||
if( rc == 0 ) {
|
if( rc == 0 ) {
|
||||||
cchOutLen = 0;
|
cchOutLen = 0;
|
||||||
sqlsrv_free( newString );
|
sqlsrv_free( newString );
|
||||||
|
@ -185,13 +193,13 @@ bool convert_string_from_utf16( SQLSRV_ENCODING encoding, const wchar_t* inStrin
|
||||||
// thin wrapper around convert_string_from_default_encoding that handles
|
// thin wrapper around convert_string_from_default_encoding that handles
|
||||||
// allocation of the destination string. An empty string passed in returns
|
// allocation of the destination string. An empty string passed in returns
|
||||||
// failure since it's a failure case for convert_string_from_default_encoding.
|
// failure since it's a failure case for convert_string_from_default_encoding.
|
||||||
wchar_t* utf16_string_from_mbcs_string( SQLSRV_ENCODING php_encoding, const char* mbcs_string, unsigned int mbcs_len,
|
SQLWCHAR* utf16_string_from_mbcs_string( SQLSRV_ENCODING php_encoding, const char* mbcs_string, unsigned int mbcs_len,
|
||||||
unsigned int* utf16_len )
|
unsigned int* utf16_len )
|
||||||
{
|
{
|
||||||
*utf16_len = (mbcs_len + 1);
|
*utf16_len = (mbcs_len + 1);
|
||||||
wchar_t* utf16_string = reinterpret_cast<wchar_t*>( sqlsrv_malloc( *utf16_len * sizeof( wchar_t )));
|
SQLWCHAR* utf16_string = reinterpret_cast<SQLWCHAR*>( sqlsrv_malloc( *utf16_len * sizeof( SQLWCHAR )));
|
||||||
*utf16_len = convert_string_from_default_encoding( php_encoding, mbcs_string, mbcs_len,
|
*utf16_len = convert_string_from_default_encoding( php_encoding, mbcs_string, mbcs_len, utf16_string, *utf16_len );
|
||||||
utf16_string, *utf16_len );
|
|
||||||
if( *utf16_len == 0 ) {
|
if( *utf16_len == 0 ) {
|
||||||
// we preserve the error and reset it because sqlsrv_free resets the last error
|
// we preserve the error and reset it because sqlsrv_free resets the last error
|
||||||
DWORD last_error = GetLastError();
|
DWORD last_error = GetLastError();
|
||||||
|
@ -220,13 +228,10 @@ bool core_sqlsrv_get_odbc_error( sqlsrv_context& ctx, int record_number, sqlsrv_
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
zval* ssphp_z = NULL;
|
|
||||||
int zr = SUCCESS;
|
|
||||||
zval* temp = NULL;
|
|
||||||
SQLRETURN r = SQL_SUCCESS;
|
SQLRETURN r = SQL_SUCCESS;
|
||||||
SQLSMALLINT wmessage_len = 0;
|
SQLSMALLINT wmessage_len = 0;
|
||||||
SQLWCHAR wsqlstate[ SQL_SQLSTATE_BUFSIZE ];
|
SQLWCHAR wsqlstate[ SQL_SQLSTATE_BUFSIZE ] = { L'\0' };
|
||||||
SQLWCHAR wnative_message[ SQL_MAX_MESSAGE_LENGTH + 1 ];
|
SQLWCHAR wnative_message[ SQL_MAX_MESSAGE_LENGTH + 1 ] = { L'\0' };
|
||||||
SQLSRV_ENCODING enc = ctx.encoding();
|
SQLSRV_ENCODING enc = ctx.encoding();
|
||||||
|
|
||||||
switch( h_type ) {
|
switch( h_type ) {
|
||||||
|
@ -238,7 +243,7 @@ bool core_sqlsrv_get_odbc_error( sqlsrv_context& ctx, int record_number, sqlsrv_
|
||||||
|
|
||||||
error = stmt->current_results->get_diag_rec( record_number );
|
error = stmt->current_results->get_diag_rec( record_number );
|
||||||
// don't use the CHECK* macros here since it will trigger reentry into the error handling system
|
// don't use the CHECK* macros here since it will trigger reentry into the error handling system
|
||||||
if( error == NULL ) {
|
if( error == 0 ) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -261,8 +266,15 @@ bool core_sqlsrv_get_odbc_error( sqlsrv_context& ctx, int record_number, sqlsrv_
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
// In linux we need to calculate number of characters
|
||||||
|
SQLLEN wsqlstate_len = sizeof( wsqlstate ) / sizeof( SQLWCHAR );
|
||||||
|
#else
|
||||||
|
// In Windows we need the size in bytes
|
||||||
|
SQLLEN wsqlstate_len = sizeof( wsqlstate );
|
||||||
|
#endif
|
||||||
SQLLEN sqlstate_len = 0;
|
SQLLEN sqlstate_len = 0;
|
||||||
convert_string_from_utf16(enc, wsqlstate, sizeof(wsqlstate), (char**)&error->sqlstate, sqlstate_len);
|
convert_string_from_utf16(enc, wsqlstate, wsqlstate_len, (char**)&error->sqlstate, sqlstate_len);
|
||||||
|
|
||||||
SQLLEN message_len = 0;
|
SQLLEN message_len = 0;
|
||||||
convert_string_from_utf16(enc, wnative_message, wmessage_len, (char**)&error->native_message, message_len);
|
convert_string_from_utf16(enc, wnative_message, wmessage_len, (char**)&error->native_message, message_len);
|
||||||
|
@ -350,8 +362,8 @@ void die( const char* msg, ... )
|
||||||
{
|
{
|
||||||
va_list format_args;
|
va_list format_args;
|
||||||
va_start( format_args, msg );
|
va_start( format_args, msg );
|
||||||
|
|
||||||
DWORD rc = FormatMessage( FORMAT_MESSAGE_FROM_STRING, msg, 0, 0, last_err_msg, sizeof( last_err_msg ), &format_args );
|
DWORD rc = FormatMessage( FORMAT_MESSAGE_FROM_STRING, msg, 0, 0, last_err_msg, sizeof( last_err_msg ), &format_args );
|
||||||
|
|
||||||
va_end( format_args );
|
va_end( format_args );
|
||||||
|
|
||||||
|
@ -371,7 +383,7 @@ namespace {
|
||||||
// a failure since MBTWC returns 0 for both an empty string and failure
|
// a failure since MBTWC returns 0 for both an empty string and failure
|
||||||
// to convert.
|
// to convert.
|
||||||
unsigned int convert_string_from_default_encoding( unsigned int php_encoding, _In_reads_bytes_(mbcs_len) char const* mbcs_in_string,
|
unsigned int convert_string_from_default_encoding( unsigned int php_encoding, _In_reads_bytes_(mbcs_len) char const* mbcs_in_string,
|
||||||
unsigned int mbcs_len, _Out_writes_(utf16_len) __transfer( mbcs_in_string ) wchar_t* utf16_out_string,
|
unsigned int mbcs_len, _Out_writes_(utf16_len) __transfer( mbcs_in_string ) SQLWCHAR* utf16_out_string,
|
||||||
unsigned int utf16_len )
|
unsigned int utf16_len )
|
||||||
{
|
{
|
||||||
unsigned int win_encoding = CP_ACP;
|
unsigned int win_encoding = CP_ACP;
|
||||||
|
@ -387,8 +399,13 @@ unsigned int convert_string_from_default_encoding( unsigned int php_encoding, _I
|
||||||
win_encoding = php_encoding;
|
win_encoding = php_encoding;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
#ifdef __linux__
|
||||||
|
unsigned int required_len = SystemLocale::ToUtf16( win_encoding, mbcs_in_string, mbcs_len, utf16_out_string, utf16_len );
|
||||||
|
#else
|
||||||
unsigned int required_len = MultiByteToWideChar( win_encoding, MB_ERR_INVALID_CHARS, mbcs_in_string, mbcs_len,
|
unsigned int required_len = MultiByteToWideChar( win_encoding, MB_ERR_INVALID_CHARS, mbcs_in_string, mbcs_len,
|
||||||
utf16_out_string, utf16_len );
|
utf16_out_string, utf16_len );
|
||||||
|
#endif
|
||||||
|
|
||||||
if( required_len == 0 ) {
|
if( required_len == 0 ) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue