You've already forked mariadb-connector-c
mirror of
https://github.com/mariadb-corporation/mariadb-connector-c.git
synced 2025-08-08 14:02:17 +03:00
CONC-446 For Schannel errors, provide better errors
Print error symbol (e.g S"EC_E_ILLEGAL_MESSAGE") in the error message for some schannel errors, in addition to error message Print error code for all errors coming from schannel. Fix some whitespace.
This commit is contained in:
@@ -26,69 +26,73 @@
|
||||
#define MAX_SSL_ERR_LEN 100
|
||||
|
||||
#define SCHANNEL_PAYLOAD(A) (A).cbMaximumMessage + (A).cbHeader + (A).cbTrailer
|
||||
void ma_schannel_set_win_error(MARIADB_PVIO *pvio, DWORD ErrorNo __attribute__((unused)));
|
||||
void ma_schannel_set_win_error(MARIADB_PVIO *pvio, DWORD ErrorNo);
|
||||
|
||||
static void get_schannel_error_info(DWORD err, const char** sym, const char** text)
|
||||
{
|
||||
#define ERR_ENTRY(a,b) {a,#a, b}
|
||||
static struct {
|
||||
DWORD code; /* Error code , e.g SEC_E_ILLEGAL_MESSAGE */
|
||||
const char* symbol; /* Error code as string, e.g "SEC_E_ILLEGAL_MESSAGE"*/
|
||||
const char* msg; /* English text message */
|
||||
} errinfo[] =
|
||||
{
|
||||
ERR_ENTRY(SEC_E_ILLEGAL_MESSAGE, "The message received was unexpected or badly formatted"),
|
||||
ERR_ENTRY(SEC_E_UNTRUSTED_ROOT, "Untrusted root certificate"),
|
||||
ERR_ENTRY(SEC_E_BUFFER_TOO_SMALL, "Buffer too small"),
|
||||
ERR_ENTRY(SEC_E_CRYPTO_SYSTEM_INVALID, "Cipher is not supported"),
|
||||
ERR_ENTRY(SEC_E_INSUFFICIENT_MEMORY, "Out of memory"),
|
||||
ERR_ENTRY(SEC_E_OUT_OF_SEQUENCE, "Invalid message sequence"),
|
||||
ERR_ENTRY(SEC_E_DECRYPT_FAILURE, "The specified data could not be decrypted"),
|
||||
ERR_ENTRY(SEC_I_INCOMPLETE_CREDENTIALS, "Incomplete credentials"),
|
||||
ERR_ENTRY(SEC_E_ENCRYPT_FAILURE, "The specified data could not be encrypted"),
|
||||
ERR_ENTRY(SEC_I_CONTEXT_EXPIRED, "The context has expired and can no longer be used"),
|
||||
ERR_ENTRY(SEC_E_ALGORITHM_MISMATCH, "no cipher match"),
|
||||
ERR_ENTRY(SEC_E_NO_CREDENTIALS, "no credentials"),
|
||||
ERR_ENTRY(SEC_E_INVALID_TOKEN, "The token supplied to function is invalid")
|
||||
};
|
||||
for (int i = 0; i < sizeof(errinfo) / sizeof(errinfo[0]); i++)
|
||||
{
|
||||
if (errinfo[i].code == err)
|
||||
{
|
||||
*sym = errinfo[i].symbol;
|
||||
*text = errinfo[i].msg;
|
||||
return;
|
||||
}
|
||||
}
|
||||
*sym = NULL;
|
||||
*text = NULL;
|
||||
}
|
||||
|
||||
|
||||
/* {{{ void ma_schannel_set_sec_error */
|
||||
void ma_schannel_set_sec_error(MARIADB_PVIO *pvio, DWORD ErrorNo)
|
||||
void ma_schannel_set_sec_error(MARIADB_PVIO* pvio, DWORD ErrorNo)
|
||||
{
|
||||
MYSQL *mysql= pvio->mysql;
|
||||
|
||||
MYSQL* mysql = pvio->mysql;
|
||||
const char* sym;
|
||||
const char* text;
|
||||
if (ErrorNo != SEC_E_OK)
|
||||
mysql->net.extension->extended_errno= ErrorNo;
|
||||
|
||||
switch(ErrorNo) {
|
||||
case SEC_E_ILLEGAL_MESSAGE:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: The message received was unexpected or badly formatted");
|
||||
break;
|
||||
case SEC_E_UNTRUSTED_ROOT:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Untrusted root certificate");
|
||||
break;
|
||||
case SEC_E_BUFFER_TOO_SMALL:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Buffer too small");
|
||||
break;
|
||||
case SEC_E_CRYPTO_SYSTEM_INVALID:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Cipher is not supported");
|
||||
break;
|
||||
case SEC_E_INSUFFICIENT_MEMORY:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Out of memory");
|
||||
break;
|
||||
case SEC_E_OUT_OF_SEQUENCE:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Invalid message sequence");
|
||||
break;
|
||||
case SEC_E_DECRYPT_FAILURE:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: An error occurred during decrypting data");
|
||||
break;
|
||||
case SEC_I_INCOMPLETE_CREDENTIALS:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Incomplete credentials");
|
||||
break;
|
||||
case SEC_E_ENCRYPT_FAILURE:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: An error occurred during encrypting data");
|
||||
break;
|
||||
case SEC_I_CONTEXT_EXPIRED:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: Context expired ");
|
||||
break;
|
||||
case SEC_E_ALGORITHM_MISMATCH:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: no cipher match");
|
||||
break;
|
||||
case SEC_E_NO_CREDENTIALS:
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "SSL connection error: no credentials");
|
||||
break;
|
||||
case SEC_E_OK:
|
||||
break;
|
||||
case SEC_E_INTERNAL_ERROR:
|
||||
if (GetLastError())
|
||||
ma_schannel_set_win_error(pvio, 0);
|
||||
mysql->net.extension->extended_errno = ErrorNo;
|
||||
if (ErrorNo == SEC_E_INTERNAL_ERROR && GetLastError())
|
||||
{
|
||||
ma_schannel_set_win_error(pvio, GetLastError());
|
||||
return;
|
||||
}
|
||||
get_schannel_error_info(ErrorNo, &sym, &text);
|
||||
if (sym)
|
||||
{
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN,
|
||||
"SSL connection error: %s (%s , 0x%08x)", text, sym, ErrorNo);
|
||||
}
|
||||
else
|
||||
pvio->set_error(mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "The Local Security Authority cannot be contacted");
|
||||
break;
|
||||
default:
|
||||
{
|
||||
ma_schannel_set_win_error(pvio, ErrorNo);
|
||||
}
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
/* {{{ void ma_schnnel_set_win_error */
|
||||
void ma_schannel_set_win_error(MARIADB_PVIO *pvio, DWORD ErrorNo __attribute__((unused)))
|
||||
void ma_schannel_set_win_error(MARIADB_PVIO *pvio, DWORD ErrorNo)
|
||||
{
|
||||
ulong ssl_errno= ErrorNo ? ErrorNo : GetLastError();
|
||||
char *ssl_error_reason= NULL;
|
||||
@@ -99,14 +103,15 @@ void ma_schannel_set_win_error(MARIADB_PVIO *pvio, DWORD ErrorNo __attribute__((
|
||||
pvio->set_error(pvio->mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, "Unknown SSL error");
|
||||
return;
|
||||
}
|
||||
/* todo: obtain error message */
|
||||
|
||||
FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
|
||||
NULL, ssl_errno, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
|
||||
(LPTSTR) &ssl_error_reason, 0, NULL );
|
||||
for (p = ssl_error_reason; *p; p++)
|
||||
if (*p == '\n' || *p == '\r')
|
||||
*p = 0;
|
||||
snprintf(buffer, sizeof(buffer), "SSL connection error: %s",ssl_error_reason);
|
||||
snprintf(buffer, sizeof(buffer), "SSL connection error: %s. Windows error %lu / 0x%08lx",ssl_error_reason,
|
||||
ErrorNo, ErrorNo);
|
||||
pvio->set_error(pvio->mysql, CR_SSL_CONNECTION_ERROR, SQLSTATE_UNKNOWN, buffer);
|
||||
if (ssl_error_reason)
|
||||
LocalFree(ssl_error_reason);
|
||||
@@ -873,7 +878,9 @@ SECURITY_STATUS ma_schannel_client_handshake(MARIADB_TLS *ctls)
|
||||
end:
|
||||
LocalFree(sctx->IoBuffer);
|
||||
sctx->IoBufferSize= 0;
|
||||
if (BuffersOut.pvBuffer)
|
||||
FreeContextBuffer(BuffersOut.pvBuffer);
|
||||
|
||||
DeleteSecurityContext(&sctx->ctxt);
|
||||
return sRet;
|
||||
}
|
||||
|
@@ -158,8 +158,7 @@ cipher_map[] =
|
||||
|
||||
#define MAX_ALG_ID 50
|
||||
|
||||
void ma_schannel_set_sec_error(MARIADB_PVIO *pvio, DWORD ErrorNo);
|
||||
void ma_schannel_set_win_error(MYSQL *mysql);
|
||||
extern void ma_schannel_set_sec_error(MARIADB_PVIO *pvio, DWORD ErrorNo);
|
||||
|
||||
/*
|
||||
Initializes SSL and allocate global
|
||||
|
Reference in New Issue
Block a user