size_t encdata_length, decdata_length;
size_t encdata_offset, decdata_offset;
unsigned char *encdata_buffer, *decdata_buffer;
+ /* encdata_is_incomplete: if encdata contains only a partial record that
+ can't be decrypted without another Curl_read_plain (that is, status is
+ SEC_E_INCOMPLETE_MESSAGE) then set this true. after Curl_read_plain writes
+ more bytes into encdata then set this back to false. */
+ bool encdata_is_incomplete;
unsigned long req_flags, ret_flags;
CURLcode recv_unrecoverable_err; /* schannel_recv had an unrecoverable err */
bool recv_sspi_close_notify; /* true if connection closed by close_notify */
connssl->recv_unrecoverable_err = CURLE_OK;
connssl->recv_sspi_close_notify = false;
connssl->recv_connection_closed = false;
+ connssl->encdata_is_incomplete = false;
/* continue to second handshake step */
connssl->connecting_state = ssl_connect_2;
/* buffer to store previously received and encrypted data */
if(connssl->encdata_buffer == NULL) {
+ connssl->encdata_is_incomplete = false;
connssl->encdata_offset = 0;
connssl->encdata_length = CURL_SCHANNEL_BUFFER_INIT_SIZE;
connssl->encdata_buffer = malloc(connssl->encdata_length);
/* increase encrypted data buffer offset */
connssl->encdata_offset += nread;
+ connssl->encdata_is_incomplete = false;
+ infof(data, "schannel: encrypted data got %zd\n", nread);
}
infof(data, "schannel: encrypted data buffer: offset %zu length %zu\n",
/* check if the handshake was incomplete */
if(sspi_status == SEC_E_INCOMPLETE_MESSAGE) {
+ connssl->encdata_is_incomplete = true;
connssl->connecting_state = ssl_connect_2_reading;
infof(data, "schannel: received incomplete message, need more data\n");
return CURLE_OK;
}
else if(nread > 0) {
connssl->encdata_offset += (size_t)nread;
+ connssl->encdata_is_incomplete = false;
infof(data, "schannel: encrypted data got %zd\n", nread);
}
}
}
}
else if(sspi_status == SEC_E_INCOMPLETE_MESSAGE) {
+ connssl->encdata_is_incomplete = true;
if(!*err)
*err = CURLE_AGAIN;
infof(data, "schannel: failed to decrypt data, need more data\n");
const struct ssl_connect_data *connssl = &conn->ssl[sockindex];
if(connssl->use) /* SSL/TLS is in use */
- return (connssl->encdata_offset > 0 ||
- connssl->decdata_offset > 0) ? TRUE : FALSE;
+ return (connssl->decdata_offset > 0 ||
+ (connssl->encdata_offset > 0 && !connssl->encdata_is_incomplete));
else
return FALSE;
}
Curl_safefree(connssl->encdata_buffer);
connssl->encdata_length = 0;
connssl->encdata_offset = 0;
+ connssl->encdata_is_incomplete = false;
}
/* free internal buffer for received decrypted data */