Merge branch 'feat/esp_tls_add_psk' into 'master'

feat(esp_tls): Add support for PSK authentication on server side

Closes IDFGH-14083

See merge request espressif/esp-idf!34996
This commit is contained in:
David Čermák
2024-11-22 00:10:42 +08:00
2 changed files with 30 additions and 13 deletions

View File

@@ -1,5 +1,5 @@
/* /*
* SPDX-FileCopyrightText: 2017-2023 Espressif Systems (Shanghai) CO LTD * SPDX-FileCopyrightText: 2017-2024 Espressif Systems (Shanghai) CO LTD
* *
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
*/ */
@@ -187,9 +187,11 @@ typedef struct esp_tls_cfg {
tls_keep_alive_cfg_t *keep_alive_cfg; /*!< Enable TCP keep-alive timeout for SSL connection */ tls_keep_alive_cfg_t *keep_alive_cfg; /*!< Enable TCP keep-alive timeout for SSL connection */
#if defined(CONFIG_ESP_TLS_PSK_VERIFICATION)
const psk_hint_key_t* psk_hint_key; /*!< Pointer to PSK hint and key. if not NULL (and certificates are NULL) const psk_hint_key_t* psk_hint_key; /*!< Pointer to PSK hint and key. if not NULL (and certificates are NULL)
then PSK authentication is enabled with configured setup. then PSK authentication is enabled with configured setup.
Important note: the pointer must be valid for connection */ Important note: the pointer must be valid for connection */
#endif /* CONFIG_ESP_TLS_PSK_VERIFICATION */
esp_err_t (*crt_bundle_attach)(void *conf); esp_err_t (*crt_bundle_attach)(void *conf);
/*!< Function pointer to esp_crt_bundle_attach. Enables the use of certification /*!< Function pointer to esp_crt_bundle_attach. Enables the use of certification
@@ -322,6 +324,12 @@ typedef struct esp_tls_cfg_server {
TLS extensions, such as ALPN and server_certificate_type . */ TLS extensions, such as ALPN and server_certificate_type . */
#endif #endif
#if defined(CONFIG_ESP_TLS_PSK_VERIFICATION)
const psk_hint_key_t* psk_hint_key; /*!< Pointer to PSK hint and key. if not NULL (and the certificate/key is NULL)
then PSK authentication is enabled with configured setup.
Important note: the pointer must be valid for connection */
#endif
} esp_tls_cfg_server_t; } esp_tls_cfg_server_t;
/** /**
@@ -464,7 +472,7 @@ int esp_tls_conn_http_new_async(const char *url, const esp_tls_cfg_t *cfg, esp_t
* - >=0 if write operation was successful, the return value is the number * - >=0 if write operation was successful, the return value is the number
* of bytes actually written to the TLS/SSL connection. * of bytes actually written to the TLS/SSL connection.
* - <0 if write operation was not successful, because either an * - <0 if write operation was not successful, because either an
* error occured or an action must be taken by the calling process. * error occurred or an action must be taken by the calling process.
* - ESP_TLS_ERR_SSL_WANT_READ/ * - ESP_TLS_ERR_SSL_WANT_READ/
* ESP_TLS_ERR_SSL_WANT_WRITE. * ESP_TLS_ERR_SSL_WANT_WRITE.
* if the handshake is incomplete and waiting for data to be available for reading. * if the handshake is incomplete and waiting for data to be available for reading.
@@ -485,7 +493,7 @@ ssize_t esp_tls_conn_write(esp_tls_t *tls, const void *data, size_t datalen);
* - 0 if read operation was not successful. The underlying * - 0 if read operation was not successful. The underlying
* connection was closed. * connection was closed.
* - <0 if read operation was not successful, because either an * - <0 if read operation was not successful, because either an
* error occured or an action must be taken by the calling process. * error occurred or an action must be taken by the calling process.
*/ */
ssize_t esp_tls_conn_read(esp_tls_t *tls, void *data, size_t datalen); ssize_t esp_tls_conn_read(esp_tls_t *tls, void *data, size_t datalen);
@@ -537,7 +545,7 @@ esp_err_t esp_tls_get_conn_sockfd(esp_tls_t *tls, int *sockfd);
* *
* @param[in] sockfd sockfd value to set. * @param[in] sockfd sockfd value to set.
* *
* @return - ESP_OK on success and value of sockfd for the tls connection shall updated withthe provided value * @return - ESP_OK on success and value of sockfd for the tls connection shall updated with the provided value
* - ESP_ERR_INVALID_ARG if (tls == NULL || sockfd < 0) * - ESP_ERR_INVALID_ARG if (tls == NULL || sockfd < 0)
*/ */
esp_err_t esp_tls_set_conn_sockfd(esp_tls_t *tls, int sockfd); esp_err_t esp_tls_set_conn_sockfd(esp_tls_t *tls, int sockfd);
@@ -549,7 +557,7 @@ esp_err_t esp_tls_set_conn_sockfd(esp_tls_t *tls, int sockfd);
* *
* @param[out] conn_state pointer to the connection state value. * @param[out] conn_state pointer to the connection state value.
* *
* @return - ESP_OK on success and value of sockfd for the tls connection shall updated withthe provided value * @return - ESP_OK on success and value of sockfd for the tls connection shall updated with the provided value
* - ESP_ERR_INVALID_ARG (Invalid arguments) * - ESP_ERR_INVALID_ARG (Invalid arguments)
*/ */
esp_err_t esp_tls_get_conn_state(esp_tls_t *tls, esp_tls_conn_state_t *conn_state); esp_err_t esp_tls_get_conn_state(esp_tls_t *tls, esp_tls_conn_state_t *conn_state);
@@ -561,7 +569,7 @@ esp_err_t esp_tls_get_conn_state(esp_tls_t *tls, esp_tls_conn_state_t *conn_stat
* *
* @param[in] conn_state connection state value to set. * @param[in] conn_state connection state value to set.
* *
* @return - ESP_OK on success and value of sockfd for the tls connection shall updated withthe provided value * @return - ESP_OK on success and value of sockfd for the tls connection shall updated with the provided value
* - ESP_ERR_INVALID_ARG (Invalid arguments) * - ESP_ERR_INVALID_ARG (Invalid arguments)
*/ */
esp_err_t esp_tls_set_conn_state(esp_tls_t *tls, esp_tls_conn_state_t conn_state); esp_err_t esp_tls_set_conn_state(esp_tls_t *tls, esp_tls_conn_state_t conn_state);
@@ -586,7 +594,7 @@ void *esp_tls_get_ssl_context(esp_tls_t *tls);
* *
* @return * @return
* - ESP_OK if creating global CA store was successful. * - ESP_OK if creating global CA store was successful.
* - ESP_ERR_NO_MEM if an error occured when allocating the mbedTLS resources. * - ESP_ERR_NO_MEM if an error occurred when allocating the mbedTLS resources.
*/ */
esp_err_t esp_tls_init_global_ca_store(void); esp_err_t esp_tls_init_global_ca_store(void);
@@ -605,7 +613,7 @@ esp_err_t esp_tls_init_global_ca_store(void);
* *
* @return * @return
* - ESP_OK if adding certificates was successful. * - ESP_OK if adding certificates was successful.
* - Other if an error occured or an action must be taken by the calling process. * - Other if an error occurred or an action must be taken by the calling process.
*/ */
esp_err_t esp_tls_set_global_ca_store(const unsigned char *cacert_pem_buf, const unsigned int cacert_pem_bytes); esp_err_t esp_tls_set_global_ca_store(const unsigned char *cacert_pem_buf, const unsigned int cacert_pem_bytes);

View File

@@ -659,6 +659,18 @@ static esp_err_t set_server_config(esp_tls_cfg_server_t *cfg, esp_tls_t *tls)
ESP_LOGE(TAG, "Failed to set server pki context"); ESP_LOGE(TAG, "Failed to set server pki context");
return esp_ret; return esp_ret;
} }
#if defined(CONFIG_ESP_TLS_PSK_VERIFICATION)
} else if (cfg->psk_hint_key) {
ESP_LOGD(TAG, "PSK authentication");
ret = mbedtls_ssl_conf_psk(&tls->conf, cfg->psk_hint_key->key, cfg->psk_hint_key->key_size,
(const unsigned char *)cfg->psk_hint_key->hint, strlen(cfg->psk_hint_key->hint));
if (ret != 0) {
ESP_LOGE(TAG, "mbedtls_ssl_conf_psk returned -0x%04X", -ret);
mbedtls_print_error_msg(ret);
ESP_INT_EVENT_TRACKER_CAPTURE(tls->error_handle, ESP_TLS_ERR_TYPE_MBEDTLS, -ret);
return ESP_ERR_MBEDTLS_SSL_CONF_PSK_FAILED;
}
#endif
} else { } else {
#if defined(CONFIG_ESP_TLS_SERVER_CERT_SELECT_HOOK) #if defined(CONFIG_ESP_TLS_SERVER_CERT_SELECT_HOOK)
if (cfg->cert_select_cb == NULL) { if (cfg->cert_select_cb == NULL) {
@@ -770,8 +782,8 @@ esp_err_t set_client_config(const char *hostname, size_t hostlen, esp_tls_cfg_t
return esp_ret; return esp_ret;
} }
mbedtls_ssl_conf_ca_chain(&tls->conf, tls->cacert_ptr, NULL); mbedtls_ssl_conf_ca_chain(&tls->conf, tls->cacert_ptr, NULL);
} else if (cfg->psk_hint_key) {
#if defined(CONFIG_ESP_TLS_PSK_VERIFICATION) #if defined(CONFIG_ESP_TLS_PSK_VERIFICATION)
} else if (cfg->psk_hint_key) {
// //
// PSK encryption mode is configured only if no certificate supplied and psk pointer not null // PSK encryption mode is configured only if no certificate supplied and psk pointer not null
ESP_LOGD(TAG, "ssl psk authentication"); ESP_LOGD(TAG, "ssl psk authentication");
@@ -783,13 +795,10 @@ esp_err_t set_client_config(const char *hostname, size_t hostlen, esp_tls_cfg_t
ESP_INT_EVENT_TRACKER_CAPTURE(tls->error_handle, ESP_TLS_ERR_TYPE_MBEDTLS, -ret); ESP_INT_EVENT_TRACKER_CAPTURE(tls->error_handle, ESP_TLS_ERR_TYPE_MBEDTLS, -ret);
return ESP_ERR_MBEDTLS_SSL_CONF_PSK_FAILED; return ESP_ERR_MBEDTLS_SSL_CONF_PSK_FAILED;
} }
#else
ESP_LOGE(TAG, "psk_hint_key configured but not enabled in menuconfig: Please enable ESP_TLS_PSK_VERIFICATION option");
return ESP_ERR_INVALID_STATE;
#endif #endif
#ifdef CONFIG_ESP_TLS_CLIENT_SESSION_TICKETS #ifdef CONFIG_ESP_TLS_CLIENT_SESSION_TICKETS
} else if (cfg->client_session != NULL) { } else if (cfg->client_session != NULL) {
ESP_LOGD(TAG, "Resuing the saved client session"); ESP_LOGD(TAG, "Reusing the saved client session");
#endif #endif
} else { } else {
#ifdef CONFIG_ESP_TLS_SKIP_SERVER_CERT_VERIFY #ifdef CONFIG_ESP_TLS_SKIP_SERVER_CERT_VERIFY