winpr: add some checks in InitializeSecurityContext and AcceptSecurityContext

In native windows SSPI, AcceptSecurityContext and InitializeSecurityContext return
SEC_E_INVALID_HANDLE if the provided context is an empty context. Add the checks so
that our SSPI implementation behave the same way.
This commit is contained in:
David Fort 2022-10-07 19:55:05 +02:00 committed by akallabeth
parent cd0a33dbf2
commit 58a3919435
5 changed files with 70 additions and 11 deletions

View File

@ -47,6 +47,11 @@ static SECURITY_STATUS SEC_ENTRY credssp_InitializeSecurityContextA(
{
CREDSSP_CONTEXT* context;
SSPI_CREDENTIALS* credentials;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = (CREDSSP_CONTEXT*)sspi_SecureHandleGetLowerPointer(phContext);
if (!context)

View File

@ -724,6 +724,11 @@ static SECURITY_STATUS SEC_ENTRY kerberos_InitializeSecurityContextA(
krb5_creds* creds = NULL;
credentials = sspi_SecureHandleGetLowerPointer(phCredential);
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = sspi_SecureHandleGetLowerPointer(phContext);
if (!credentials)
@ -1035,6 +1040,10 @@ static SECURITY_STATUS SEC_ENTRY kerberos_AcceptSecurityContext(
krb5_principal principal = NULL;
krb5_creds creds = { 0 };
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = sspi_SecureHandleGetLowerPointer(phContext);
credentials = sspi_SecureHandleGetLowerPointer(phCredential);
@ -1283,9 +1292,13 @@ static SECURITY_STATUS SEC_ENTRY kerberos_QueryContextAttributesA(PCtxtHandle ph
ContextSizes->cbBlockSize = 1;
ContextSizes->cbSecurityTrailer = 0;
key = context->acceptor_key ? context->acceptor_key
: context->initiator_key ? context->initiator_key
: context->session_key;
if (context->acceptor_key)
key = context->acceptor_key;
else if (context->initiator_key)
key = context->initiator_key;
else
key = context->session_key;
enctype = krb5_k_key_enctype(context->ctx, key);
if (context->flags & SSPI_GSS_C_CONF_FLAG)
@ -1446,11 +1459,16 @@ static SECURITY_STATUS SEC_ENTRY kerberos_EncryptMessage(PCtxtHandle phContext,
flags |= FLAG_WRAP_CONFIDENTIAL;
flags |= context->acceptor_key ? FLAG_ACCEPTOR_SUBKEY : 0;
key = context->acceptor_key ? context->acceptor_key
: context->initiator_key ? context->initiator_key
: context->session_key;
if (context->acceptor_key)
key = context->acceptor_key;
else if (context->initiator_key)
key = context->initiator_key;
else
key = context->session_key;
if (!key)
return SEC_E_INTERNAL_ERROR;
usage = context->acceptor ? KG_USAGE_ACCEPTOR_SEAL : KG_USAGE_INITIATOR_SEAL;
/* Set the lengths of the data (plaintext + header) */
@ -1630,9 +1648,13 @@ static SECURITY_STATUS SEC_ENTRY kerberos_MakeSignature(PCtxtHandle phContext, U
flags |= context->acceptor ? FLAG_SENDER_IS_ACCEPTOR : 0;
flags |= context->acceptor_key ? FLAG_ACCEPTOR_SUBKEY : 0;
key = context->acceptor_key ? context->acceptor_key
: context->initiator_key ? context->initiator_key
: context->session_key;
if (context->acceptor_key)
key = context->acceptor_key;
else if (context->initiator_key)
key = context->initiator_key;
else
key = context->session_key;
if (!key)
return SEC_E_INTERNAL_ERROR;
usage = context->acceptor ? KG_USAGE_ACCEPTOR_SIGN : KG_USAGE_INITIATOR_SIGN;

View File

@ -417,6 +417,11 @@ ntlm_AcceptSecurityContext(PCredHandle phCredential, PCtxtHandle phContext, PSec
SSPI_CREDENTIALS* credentials;
PSecBuffer input_buffer;
PSecBuffer output_buffer;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = (NTLM_CONTEXT*)sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
@ -541,6 +546,11 @@ static SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(
PSecBuffer input_buffer = NULL;
PSecBuffer output_buffer = NULL;
PSecBuffer channel_bindings = NULL;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = (NTLM_CONTEXT*)sspi_SecureHandleGetLowerPointer(phContext);
if (pInput)

View File

@ -576,8 +576,14 @@ static SECURITY_STATUS SEC_ENTRY negotiate_InitializeSecurityContextW(
if (!phCredential || !SecIsValidHandle(phCredential))
return SEC_E_NO_CREDENTIALS;
context = sspi_SecureHandleGetLowerPointer(phContext);
creds = sspi_SecureHandleGetLowerPointer(phCredential);
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = sspi_SecureHandleGetLowerPointer(phContext);
if (pInput)
{
input_buffer = sspi_FindSecBuffer(pInput, SECBUFFER_TOKEN);
@ -891,11 +897,17 @@ static SECURITY_STATUS SEC_ENTRY negotiate_AcceptSecurityContext(
if (!phCredential || !SecIsValidHandle(phCredential))
return SEC_E_NO_CREDENTIALS;
creds = sspi_SecureHandleGetLowerPointer(phCredential);
if (!pInput)
return SEC_E_INVALID_TOKEN;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = sspi_SecureHandleGetLowerPointer(phContext);
creds = sspi_SecureHandleGetLowerPointer(phCredential);
input_buffer = sspi_FindSecBuffer(pInput, SECBUFFER_TOKEN);
if (pOutput)
output_buffer = sspi_FindSecBuffer(pOutput, SECBUFFER_TOKEN);

View File

@ -202,6 +202,11 @@ static SECURITY_STATUS SEC_ENTRY schannel_InitializeSecurityContextW(
SECURITY_STATUS status;
SCHANNEL_CONTEXT* context;
SCHANNEL_CREDENTIALS* credentials;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
@ -250,6 +255,11 @@ static SECURITY_STATUS SEC_ENTRY schannel_AcceptSecurityContext(
{
SECURITY_STATUS status;
SCHANNEL_CONTEXT* context;
/* behave like windows SSPIs that don't want empty context */
if (phContext && !phContext->dwLower && !phContext->dwUpper)
return SEC_E_INVALID_HANDLE;
context = (SCHANNEL_CONTEXT*)sspi_SecureHandleGetLowerPointer(phContext);
if (!context)