mirror of
https://github.com/esp8266/Arduino.git
synced 2025-08-12 20:49:16 +03:00
Added initial support for max fragment size extension. (#25)
Refactored the code to support more SSL extensions in the future.
This commit is contained in:
20
ssl/ssl.h
20
ssl/ssl.h
@@ -225,6 +225,22 @@ EXP_FUNC SSL_CTX * STDCALL ssl_ctx_new(uint32_t options, int num_sessions);
|
||||
*/
|
||||
EXP_FUNC void STDCALL ssl_ctx_free(SSL_CTX *ssl_ctx);
|
||||
|
||||
/**
|
||||
* @brief Allocates new SSL extensions structure and returns pointer to it
|
||||
*
|
||||
* @return ssl_ext Pointer to SSL_EXTENSIONS structure
|
||||
*
|
||||
*/
|
||||
EXP_FUNC SSL_EXTENSIONS * STDCALL ssl_ext_new();
|
||||
|
||||
/**
|
||||
* @brief Frees SSL extensions structure
|
||||
*
|
||||
* @param ssl_ext [in] Pointer to SSL_EXTENSION structure
|
||||
*
|
||||
*/
|
||||
EXP_FUNC void STDCALL ssl_ext_free(SSL_EXTENSIONS *ssl_ext);
|
||||
|
||||
/**
|
||||
* @brief (server only) Establish a new SSL connection to an SSL client.
|
||||
*
|
||||
@@ -251,11 +267,11 @@ EXP_FUNC SSL * STDCALL ssl_server_new(SSL_CTX *ssl_ctx, int client_fd);
|
||||
* can be null if no session resumption is being used or required. This option
|
||||
* is not used in skeleton mode.
|
||||
* @param sess_id_size The size of the session id (max 32)
|
||||
* @param host_name If non-zero, host name to be sent to server for SNI support
|
||||
* @param ssl_ext pointer to a structure with the activated SSL extensions and their values
|
||||
* @return An SSL object reference. Use ssl_handshake_status() to check
|
||||
* if a handshake succeeded.
|
||||
*/
|
||||
EXP_FUNC SSL * STDCALL ssl_client_new(SSL_CTX *ssl_ctx, int client_fd, const uint8_t *session_id, uint8_t sess_id_size, const char* host_name);
|
||||
EXP_FUNC SSL * STDCALL ssl_client_new(SSL_CTX *ssl_ctx, int client_fd, const uint8_t *session_id, uint8_t sess_id_size, SSL_EXTENSIONS* ssl_ext);
|
||||
|
||||
/**
|
||||
* @brief Free any used resources on this connection.
|
||||
|
34
ssl/tls1.c
34
ssl/tls1.c
@@ -139,6 +139,35 @@ void DISPLAY_BYTES(SSL *ssl, const char *format,
|
||||
const uint8_t *data, int size, ...) {}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Allocates new SSL extensions structure and returns pointer to it
|
||||
*
|
||||
*/
|
||||
EXP_FUNC SSL_EXTENSIONS * STDCALL ssl_ext_new()
|
||||
{
|
||||
SSL_EXTENSIONS *ssl_ext = (SSL_EXTENSIONS *)malloc(sizeof(SSL_EXTENSIONS));
|
||||
ssl_ext->max_fragment_size = 0;
|
||||
ssl_ext->host_name = NULL;
|
||||
|
||||
return ssl_ext;
|
||||
}
|
||||
|
||||
/**
|
||||
* Allocates new SSL extensions structure and returns pointer to it
|
||||
*
|
||||
*/
|
||||
EXP_FUNC void STDCALL ssl_ext_free(SSL_EXTENSIONS *ssl_ext)
|
||||
{
|
||||
if(ssl_ext == NULL ) {
|
||||
return;
|
||||
}
|
||||
|
||||
if(ssl_ext->host_name != NULL) {
|
||||
free(ssl_ext->host_name);
|
||||
}
|
||||
free(ssl_ext);
|
||||
}
|
||||
|
||||
/**
|
||||
* Establish a new client/server context.
|
||||
*/
|
||||
@@ -257,7 +286,8 @@ EXP_FUNC void STDCALL ssl_free(SSL *ssl)
|
||||
disposable_free(ssl);
|
||||
certificate_free(ssl);
|
||||
free(ssl->bm_all_data);
|
||||
free(ssl->host_name);
|
||||
ssl_ext_free(ssl->extensions);
|
||||
ssl->extensions = NULL;
|
||||
free(ssl);
|
||||
}
|
||||
|
||||
@@ -631,8 +661,6 @@ SSL *ssl_new(SSL_CTX *ssl_ctx, int client_fd)
|
||||
ssl->encrypt_ctx = malloc(sizeof(AES_CTX));
|
||||
ssl->decrypt_ctx = malloc(sizeof(AES_CTX));
|
||||
|
||||
ssl->host_name = NULL;
|
||||
|
||||
SSL_CTX_UNLOCK(ssl_ctx->mutex);
|
||||
return ssl;
|
||||
}
|
||||
|
@@ -120,6 +120,7 @@ enum
|
||||
enum
|
||||
{
|
||||
SSL_EXT_SERVER_NAME = 0,
|
||||
SSL_EXT_MAX_FRAGMENT_SIZE,
|
||||
SSL_EXT_SIG_ALG = 0x0d,
|
||||
};
|
||||
|
||||
@@ -172,6 +173,11 @@ typedef struct
|
||||
uint8_t key_block_generated;
|
||||
} DISPOSABLE_CTX;
|
||||
|
||||
typedef struct {
|
||||
char *host_name; /* Needed for the SNI support */
|
||||
uint16_t max_fragment_size; /* Needed for the Max Fragment Size Extension. Allowed values: 2^9, 2^10 .. 2^14 */
|
||||
} SSL_EXTENSIONS;
|
||||
|
||||
struct _SSL
|
||||
{
|
||||
uint32_t flag;
|
||||
@@ -213,7 +219,7 @@ struct _SSL
|
||||
uint8_t read_sequence[8]; /* 64 bit sequence number */
|
||||
uint8_t write_sequence[8]; /* 64 bit sequence number */
|
||||
uint8_t hmac_header[SSL_RECORD_SIZE]; /* rx hmac */
|
||||
char *host_name; /* Needed for the SNI support */
|
||||
SSL_EXTENSIONS *extensions; /* Contains the SSL (client) extensions */
|
||||
};
|
||||
|
||||
typedef struct _SSL SSL;
|
||||
|
@@ -64,7 +64,7 @@ static int send_cert_verify(SSL *ssl);
|
||||
* Establish a new SSL connection to an SSL server.
|
||||
*/
|
||||
EXP_FUNC SSL * STDCALL ssl_client_new(SSL_CTX *ssl_ctx, int client_fd, const
|
||||
uint8_t *session_id, uint8_t sess_id_size, const char* host_name)
|
||||
uint8_t *session_id, uint8_t sess_id_size, SSL_EXTENSIONS* ssl_ext)
|
||||
{
|
||||
SSL *ssl = ssl_new(ssl_ctx, client_fd);
|
||||
ssl->version = SSL_PROTOCOL_VERSION_MAX; /* try top version first */
|
||||
@@ -82,9 +82,7 @@ EXP_FUNC SSL * STDCALL ssl_client_new(SSL_CTX *ssl_ctx, int client_fd, const
|
||||
SET_SSL_FLAG(SSL_SESSION_RESUME); /* just flag for later */
|
||||
}
|
||||
|
||||
if(host_name != NULL && strlen(host_name) > 0) {
|
||||
ssl->host_name = (char *)strdup(host_name);
|
||||
}
|
||||
ssl->extensions = ssl_ext;
|
||||
|
||||
SET_SSL_FLAG(SSL_IS_CLIENT);
|
||||
do_client_connect(ssl);
|
||||
@@ -259,22 +257,36 @@ static int send_client_hello(SSL *ssl)
|
||||
ext_len += sizeof(g_sig_alg);
|
||||
}
|
||||
|
||||
/* send the host name if specified */
|
||||
if (ssl->host_name != NULL) {
|
||||
unsigned int host_len = strlen(ssl->host_name);
|
||||
if (ssl->extensions != NULL) {
|
||||
/* send the host name if specified */
|
||||
if (ssl->extensions->host_name != NULL) {
|
||||
unsigned int host_len = strlen(ssl->extensions->host_name);
|
||||
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = SSL_EXT_SERVER_NAME; /* server_name(0) (65535) */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len+5; /* server_name length */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len+3; /* server_list length */
|
||||
buf[offset++] = 0; /* host_name(0) (255) */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len; /* host_name length */
|
||||
strncpy((char*) &buf[offset], ssl->host_name, host_len);
|
||||
offset += host_len;
|
||||
ext_len += host_len + 9;
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = SSL_EXT_SERVER_NAME; /* server_name(0) (65535) */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len + 5; /* server_name length */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len + 3; /* server_list length */
|
||||
buf[offset++] = 0; /* host_name(0) (255) */
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = host_len; /* host_name length */
|
||||
strncpy((char*) &buf[offset], ssl->extensions->host_name, host_len);
|
||||
offset += host_len;
|
||||
ext_len += host_len + 9;
|
||||
}
|
||||
|
||||
if (ssl->extensions->max_fragment_size) {
|
||||
buf[offset++] = 0;
|
||||
buf[offset++] = SSL_EXT_MAX_FRAGMENT_SIZE;
|
||||
|
||||
buf[offset++] = 0; // size of data
|
||||
buf[offset++] = 2;
|
||||
|
||||
buf[offset++] = (uint8_t)((ssl->extensions->max_fragment_size >> 8) & 0xff);
|
||||
buf[offset++] = (uint8_t)(ssl->extensions->max_fragment_size & 0xff);
|
||||
ext_len += 6;
|
||||
}
|
||||
}
|
||||
|
||||
if(ext_len > 0) {
|
||||
|
Reference in New Issue
Block a user