diff --git a/lib/socks_sspi.c b/lib/socks_sspi.c index 7c043093e1..8ab538fba1 100644 --- a/lib/socks_sspi.c +++ b/lib/socks_sspi.c @@ -421,8 +421,7 @@ static CURLcode socks5_sspi_encrypt(struct Curl_cfilter *cf, if(result || (actualread != us_length)) { failf(data, "Failed to receive SSPI encryption type."); - curlx_free(sspi_w_token[0].pvBuffer); - return result ? result : CURLE_COULDNT_CONNECT; + goto fail; } if(!data->set.socks5_gssapi_nec) { @@ -432,34 +431,26 @@ static CURLcode socks5_sspi_encrypt(struct Curl_cfilter *cf, sspi_w_token[1].cbBuffer = 0; sspi_w_token[1].pvBuffer = NULL; - status = Curl_pSecFn->DecryptMessage(sspi_context, &wrap_desc, - 0, &qop); + /* At least one of the descriptors must be of type SECBUFFER_DATA. The + message is decrypted in place so the SECBUFFER_DATA receives a pointer + to the message in SECBUFFER_STREAM. */ + status = Curl_pSecFn->DecryptMessage(sspi_context, &wrap_desc, 0, &qop); - if(check_sspi_err(data, status, "DecryptMessage")) { - if(sspi_w_token[1].pvBuffer) - Curl_pSecFn->FreeContextBuffer(sspi_w_token[1].pvBuffer); - curlx_free(sspi_w_token[0].pvBuffer); - return CURLE_COULDNT_CONNECT; - } + if(check_sspi_err(data, status, "DecryptMessage")) + goto fail; if(sspi_w_token[1].cbBuffer != 1) { failf(data, "Invalid SSPI encryption response length (%lu).", (unsigned long)sspi_w_token[1].cbBuffer); - if(sspi_w_token[1].pvBuffer) - Curl_pSecFn->FreeContextBuffer(sspi_w_token[1].pvBuffer); - curlx_free(sspi_w_token[0].pvBuffer); - return CURLE_COULDNT_CONNECT; } memcpy(socksreq, sspi_w_token[1].pvBuffer, sspi_w_token[1].cbBuffer); - Curl_pSecFn->FreeContextBuffer(sspi_w_token[1].pvBuffer); } else { if(sspi_w_token[0].cbBuffer != 1) { failf(data, "Invalid SSPI encryption response length (%lu).", (unsigned long)sspi_w_token[0].cbBuffer); - curlx_free(sspi_w_token[0].pvBuffer); - return CURLE_COULDNT_CONNECT; + goto fail; } memcpy(socksreq, sspi_w_token[0].pvBuffer, sspi_w_token[0].cbBuffer); } @@ -471,6 +462,10 @@ static CURLcode socks5_sspi_encrypt(struct Curl_cfilter *cf, " GSS-API confidentiality")); return CURLE_OK; + +fail: + curlx_free(sspi_w_token[0].pvBuffer); + return CURLE_COULDNT_CONNECT; } CURLcode Curl_SOCKS5_gssapi_negotiate(struct Curl_cfilter *cf, diff --git a/lib/vauth/krb5_sspi.c b/lib/vauth/krb5_sspi.c index de1dc58539..dd03a6c64c 100644 --- a/lib/vauth/krb5_sspi.c +++ b/lib/vauth/krb5_sspi.c @@ -291,7 +291,10 @@ CURLcode Curl_auth_create_gssapi_security_message(struct Curl_easy *data, input_buf[1].pvBuffer = NULL; input_buf[1].cbBuffer = 0; - /* Decrypt the inbound challenge and obtain the qop */ + /* Decrypt the inbound challenge and obtain the qop. The encrypted message + is decrypted in place, overwriting the original contents of its buffer. + The SECBUFFER_DATA receives a pointer to the message in + SECBUFFER_STREAM. */ status = Curl_pSecFn->DecryptMessage(krb5->context, &input_desc, 0, &qop); if(status != SEC_E_OK) { infof(data, "GSSAPI handshake failure (empty security message)"); @@ -310,9 +313,6 @@ CURLcode Curl_auth_create_gssapi_security_message(struct Curl_easy *data, max_size = ((unsigned long)indata[1] << 16) | ((unsigned long)indata[2] << 8) | indata[3]; - /* Free the challenge as it is not required anymore */ - Curl_pSecFn->FreeContextBuffer(input_buf[1].pvBuffer); - /* Process the security layer */ if(!(sec_layer & KERB_WRAP_NO_ENCRYPT)) { infof(data, "GSSAPI handshake failure (invalid security layer)");