Compare commits

..

1 Commits

Author SHA1 Message Date
feedc0de 6213a906c0 Allow the https server to request client certs only with OPTIONAL 2025-09-23 17:08:13 +02:00
18 changed files with 34 additions and 226 deletions
@@ -717,25 +717,7 @@ static void load_image(const esp_image_metadata_t *image_data)
*/
ESP_LOGI(TAG, "Checking flash encryption...");
bool flash_encryption_enabled = esp_flash_encrypt_state();
if (flash_encryption_enabled) {
#if BOOTLOADER_BUILD
/* Ensure security eFuses are burnt */
esp_efuse_batch_write_begin();
esp_err_t err = esp_flash_encryption_enable_secure_features();
if (err != ESP_OK) {
ESP_LOGE(TAG, "Error setting security eFuses (err=0x%x).", err);
esp_efuse_batch_write_cancel();
return;
}
err = esp_efuse_batch_write_commit();
if (err != ESP_OK) {
ESP_LOGE(TAG, "Error programming security eFuses (err=0x%x).", err);
return;
}
ESP_LOGI(TAG, "Security eFuses are burnt");
#endif // BOOTLOADER_BUILD
} else {
if (!flash_encryption_enabled) {
#ifdef CONFIG_SECURE_FLASH_REQUIRE_ALREADY_ENABLED
ESP_LOGE(TAG, "flash encryption is not enabled, and SECURE_FLASH_REQUIRE_ALREADY_ENABLED is set, refusing to boot.");
return;
+1 -1
View File
@@ -129,7 +129,7 @@ static ssize_t tcp_read(esp_tls_t *tls, char *data, size_t datalen)
static ssize_t tcp_write(esp_tls_t *tls, const char *data, size_t datalen)
{
return send(tls->sockfd, data, datalen, MSG_MORE);
return send(tls->sockfd, data, datalen, 0);
}
ssize_t esp_tls_conn_read(esp_tls_t *tls, void *data, size_t datalen)
+3
View File
@@ -282,6 +282,9 @@ typedef struct esp_tls_cfg_server {
unsigned int cacert_pem_bytes; /*!< Size of client CA certificate legacy name */
};
bool cacert_authmode_optional; /*!< Enable this option to set the authmode
to OPTIONAL (only useful when cacert is set) */
union {
const unsigned char *servercert_buf; /*!< Server certificate in a buffer
This buffer should be NULL terminated */
+2 -1
View File
@@ -694,7 +694,8 @@ static esp_err_t set_server_config(esp_tls_cfg_server_t *cfg, esp_tls_t *tls)
if (esp_ret != ESP_OK) {
return esp_ret;
}
mbedtls_ssl_conf_authmode(&tls->conf, MBEDTLS_SSL_VERIFY_OPTIONAL);
if (cfg->cacert_authmode_optional)
mbedtls_ssl_conf_authmode(&tls->conf, MBEDTLS_SSL_VERIFY_OPTIONAL);
} else {
#ifdef CONFIG_ESP_TLS_SERVER_MIN_AUTH_MODE_OPTIONAL
mbedtls_ssl_conf_authmode(&tls->conf, MBEDTLS_SSL_VERIFY_OPTIONAL);
@@ -407,9 +407,6 @@ int spi_get_freq_limit(bool gpio_is_used, int input_delay_ns);
*/
esp_err_t spi_bus_get_max_transaction_len(spi_host_device_t host_id, size_t *max_bytes);
intr_handle_t spi_bus_get_intr(spi_host_device_t host);
void spi_dma_reset_start(spi_device_handle_t handle);
#ifdef __cplusplus
}
#endif
@@ -722,22 +722,6 @@ static void SPI_MASTER_ISR_ATTR spi_bus_intr_disable(void *host)
#define spi_dma_start(chan, addr) gdma_start(chan, (intptr_t)(addr))
#endif
void SPI_MASTER_ISR_ATTR spi_dma_reset_start(spi_device_handle_t handle){
spi_host_t *host = handle->host;
spi_hal_context_t *hal = &(host->hal);
const spi_dma_ctx_t *dma_ctx = host->dma_ctx;
spi_dma_reset(dma_ctx->rx_dma_chan);
spi_hal_hw_prepare_rx(hal->hw);
spi_dma_start(dma_ctx->rx_dma_chan, dma_ctx->dmadesc_rx);
spi_dma_reset(dma_ctx->tx_dma_chan);
spi_hal_hw_prepare_tx(hal->hw);
spi_dma_start(dma_ctx->tx_dma_chan, dma_ctx->dmadesc_tx);
}
static void SPI_MASTER_ISR_ATTR s_spi_dma_prepare_data(spi_host_t *host, spi_hal_context_t *hal, const spi_hal_dev_config_t *dev, const spi_hal_trans_config_t *trans)
{
const spi_dma_ctx_t *dma_ctx = host->dma_ctx;
@@ -1527,10 +1511,6 @@ esp_err_t spi_bus_get_max_transaction_len(spi_host_device_t host_id, size_t *max
return ESP_OK;
}
intr_handle_t spi_bus_get_intr(spi_host_device_t host) {
return bus_driver_ctx[host]->intr;
}
#if SOC_SPI_SCT_SUPPORTED
/*-----------------------------------------------------------
+4 -6
View File
@@ -274,8 +274,7 @@ static int http_on_header_value(http_parser *parser, const char *at, size_t leng
} else if (strcasecmp(client->current_header_key, "Transfer-Encoding") == 0
&& memcmp(at, "chunked", length) == 0) {
client->response->is_chunked = true;
} else if (strcasecmp(client->current_header_key, "WWW-Authenticate") == 0 ||
strcasecmp(client->current_header_key, "X-WWW-Authenticate") == 0) {
} else if (strcasecmp(client->current_header_key, "WWW-Authenticate") == 0) {
HTTP_RET_ON_FALSE_DBG(http_utils_append_string(&client->auth_header, at, length), -1, TAG, "Failed to append string");
}
HTTP_RET_ON_FALSE_DBG(http_utils_append_string(&client->current_header_value, at, length), -1, TAG, "Failed to append string");
@@ -1379,7 +1378,7 @@ int esp_http_client_read(esp_http_client_handle_t client, char *buffer, int len)
esp_err_t esp_http_client_perform(esp_http_client_handle_t client)
{
esp_err_t err;
//do {
do {
if (client->process_again) {
esp_http_client_prepare(client);
}
@@ -1487,9 +1486,8 @@ esp_err_t esp_http_client_perform(esp_http_client_handle_t client)
default:
break;
}
//} while (client->process_again);
//return ESP_OK;
return client->process_again ? ESP_ERR_HTTP_EAGAIN : ESP_OK;
} while (client->process_again);
return ESP_OK;
}
int64_t esp_http_client_fetch_headers(esp_http_client_handle_t client)
+2 -2
View File
@@ -56,7 +56,7 @@ int httpd_send(httpd_req_t *r, const char *buf, size_t buf_len)
}
struct httpd_req_aux *ra = r->aux;
int ret = ra->sd->send_fn(ra->sd->handle, ra->sd->fd, buf, buf_len, MSG_MORE);
int ret = ra->sd->send_fn(ra->sd->handle, ra->sd->fd, buf, buf_len, 0);
if (ret < 0) {
ESP_LOGD(TAG, LOG_FMT("error in send_fn"));
return ret;
@@ -70,7 +70,7 @@ static esp_err_t httpd_send_all(httpd_req_t *r, const char *buf, size_t buf_len)
int ret;
while (buf_len > 0) {
ret = ra->sd->send_fn(ra->sd->handle, ra->sd->fd, buf, buf_len, MSG_MORE);
ret = ra->sd->send_fn(ra->sd->handle, ra->sd->fd, buf, buf_len, 0);
if (ret < 0) {
ESP_LOGD(TAG, LOG_FMT("error in send_fn"));
return ESP_FAIL;
+1 -22
View File
@@ -300,31 +300,10 @@ esp_err_t httpd_uri(struct httpd_data *hd)
/* If URI with method not found, respond with error code */
if (uri == NULL) {
switch (err) {
case HTTPD_404_NOT_FOUND:
{
char ipstr[INET6_ADDRSTRLEN] = "UNKNOWN";
const int sockfd = httpd_req_to_sockfd(req);
if (sockfd < 0)
ESP_LOGW(TAG, "httpd_req_to_sockfd() failed with %i", sockfd);
else
{
struct sockaddr_in6 addr; // esp_http_server uses IPv6 addressing
socklen_t addr_size = sizeof(addr);
const int result = getpeername(sockfd, (struct sockaddr *)&addr, &addr_size);
if (result < 0)
ESP_LOGW(TAG, "getpeername() failed with %i", result);
else
inet_ntop(AF_INET, &addr.sin6_addr.un.u32_addr[3], ipstr, sizeof(ipstr));
}
ESP_LOGW(TAG, LOG_FMT("URI '%s' not found for %s"), req->uri, ipstr);
ESP_LOGW(TAG, LOG_FMT("URI '%s' not found"), req->uri);
return httpd_req_handle_err(req, HTTPD_404_NOT_FOUND);
}
case HTTPD_405_METHOD_NOT_ALLOWED:
ESP_LOGW(TAG, LOG_FMT("Method '%d' not allowed for URI '%s'"),
req->method, req->uri);
+2 -2
View File
@@ -445,14 +445,14 @@ esp_err_t httpd_ws_send_frame_async(httpd_handle_t hd, int fd, httpd_ws_frame_t
}
/* Send off header */
if (sess->send_fn(hd, fd, (const char *)header_buf, tx_len, MSG_MORE) < 0) {
if (sess->send_fn(hd, fd, (const char *)header_buf, tx_len, 0) < 0) {
ESP_LOGW(TAG, LOG_FMT("Failed to send WS header"));
return ESP_FAIL;
}
/* Send off payload */
if(frame->len > 0 && frame->payload != NULL) {
if (sess->send_fn(hd, fd, (const char *)frame->payload, frame->len, MSG_MORE) < 0) {
if (sess->send_fn(hd, fd, (const char *)frame->payload, frame->len, 0) < 0) {
ESP_LOGW(TAG, LOG_FMT("Failed to send WS payload"));
return ESP_FAIL;
}
@@ -91,6 +91,9 @@ struct httpd_ssl_config {
/** CA certificate byte length */
size_t cacert_len;
/** CA certificate verification optional */
bool cacert_authmode_optional;
/** Private key */
const uint8_t *prvtkey_pem;
@@ -278,6 +278,7 @@ static esp_err_t create_secure_context(const struct httpd_ssl_config *config, ht
cfg->userdata = config->ssl_userdata;
cfg->alpn_protos = config->alpn_protos;
cfg->tls_handshake_timeout_ms = config->tls_handshake_timeout_ms;
cfg->cacert_authmode_optional = config->cacert_authmode_optional;
#if defined(CONFIG_ESP_HTTPS_SERVER_CERT_SELECT_HOOK)
cfg->cert_select_cb = config->cert_select_cb;
@@ -8,8 +8,6 @@
#ifndef _ESP_NETIF_PPP_H_
#define _ESP_NETIF_PPP_H_
#include "esp_netif_types.h"
#ifdef __cplusplus
extern "C" {
#endif
+12 -12
View File
@@ -49,11 +49,11 @@ extern "C" {
#define esp_sntp_get_sync_interval sntp_get_sync_interval
#define esp_sntp_restart sntp_restart
//#ifndef SNTP_OPMODE_POLL
#ifndef SNTP_OPMODE_POLL
#define SNTP_OPMODE_POLL ESP_SNTP_OPMODE_POLL
//#else
//#warning "Defined!"
//#endif /* SNTP_OPMODE_POLL */
#else
#warning "Defined!"
#endif /* SNTP_OPMODE_POLL */
/// SNTP time update mode
typedef enum {
@@ -245,39 +245,39 @@ void esp_sntp_servermode_dhcp(bool enable);
* @brief if not build within lwip, provide translating inlines,
* that will warn about thread safety
*/
inline __attribute__((deprecated("use esp_sntp_setoperatingmode() instead")))
static inline __attribute__((deprecated("use esp_sntp_setoperatingmode() instead")))
void sntp_setoperatingmode(u8_t operating_mode)
{
esp_sntp_setoperatingmode((esp_sntp_operatingmode_t)operating_mode);
}
#if LWIP_DHCP_GET_NTP_SRV
inline __attribute__((deprecated("use esp_sntp_servermode_dhcp() instead")))
static inline __attribute__((deprecated("use esp_sntp_servermode_dhcp() instead")))
void sntp_servermode_dhcp(int set_servers_from_dhcp)
{
#if LWIP_DHCP_GET_NTP_SRV
esp_sntp_servermode_dhcp(set_servers_from_dhcp);
}
#endif
}
inline __attribute__((deprecated("use esp_sntp_setservername() instead")))
static inline __attribute__((deprecated("use esp_sntp_setservername() instead")))
void sntp_setservername(u8_t idx, const char *server)
{
esp_sntp_setservername(idx, server);
}
inline __attribute__((deprecated("use esp_sntp_init() instead")))
static inline __attribute__((deprecated("use esp_sntp_init() instead")))
void sntp_init(void)
{
esp_sntp_init();
}
inline __attribute__((deprecated("use esp_sntp_getservername() instead")))
static inline __attribute__((deprecated("use esp_sntp_getservername() instead")))
const char *sntp_getservername(u8_t idx)
{
return esp_sntp_getservername(idx);
}
inline __attribute__((deprecated("use esp_sntp_getserver() instead")))
static inline __attribute__((deprecated("use esp_sntp_getserver() instead")))
const ip_addr_t* sntp_getserver(u8_t idx)
{
return esp_sntp_getserver(idx);
@@ -11,7 +11,7 @@ extern "C" {
#include <stdint.h>
typedef volatile struct emac_ext_dev_s {
typedef struct emac_ext_dev_s {
volatile union {
struct {
uint32_t div_num : 4;
@@ -17,11 +17,6 @@ extern "C" {
// Features supported
#define ESP_TRANSPORT_WS_STORE_RESPONSE_HEADERS 1
// this define will also be used for optimized websocket sends with the
// optimized version to prepend the required space for the websocket
// header
#define MAX_WEBSOCKET_HEADER_SIZE 16
typedef enum ws_transport_opcodes {
WS_TRANSPORT_OPCODES_CONT = 0x00,
WS_TRANSPORT_OPCODES_TEXT = 0x01,
@@ -162,37 +157,6 @@ esp_err_t esp_transport_ws_set_config(esp_transport_handle_t t, const esp_transp
*/
int esp_transport_ws_send_raw(esp_transport_handle_t t, ws_transport_opcodes_t opcode, const char *b, int len, int timeout_ms);
/**
* @brief Sends websocket raw message with custom opcode and payload in a optimized way
*
* This method is similar to esp_transport_ws_send_raw(), but
* it assumes, that the first MAX_WEBSOCKET_HEADER_SIZE bytes
* of the buffer should not be sent and should rather be used
* for the required websocket header itself. This is done to
* have a single TCP packet for header and payload and to avoid
* copying and allocating additional resources. The first
* MAX_WEBSOCKET_HEADER_SIZE bytes should not be initialized in
* any specific way, and the return value (length) will also
* include the MAX_WEBSOCKET_HEADER_SIZE byte extra buffer.
*
* Note that generic esp_transport_write for ws handle sends
* binary massages by default if size is > 0 and
* ping message if message size is set to 0.
* This API is provided to support explicit messages with arbitrary opcode,
* should it be PING, PONG or TEXT message with arbitrary data.
*
* @param[in] t Websocket transport handle
* @param[in] opcode ws operation code
* @param[in] buffer The buffer
* @param[in] len The length
* @param[in] timeout_ms The timeout milliseconds (-1 indicates block forever)
*
* @return
* - Number of bytes was written
* - (-1) if there are any errors, should check errno
*/
int esp_transport_ws_send_raw_optimized(esp_transport_handle_t t, ws_transport_opcodes_t opcode, const char *b, int len, int timeout_ms);
/**
* @brief Returns websocket fin flag for last received data
*
+1 -1
View File
@@ -249,7 +249,7 @@ static int tcp_write(esp_transport_handle_t t, const char *buffer, int len, int
ESP_LOGW(TAG, "Poll timeout or error, errno=%s, fd=%d, timeout_ms=%d", strerror(errno), ssl->sockfd, timeout_ms);
return poll;
}
int ret = send(ssl->sockfd, (const unsigned char *) buffer, len, MSG_MORE);
int ret = send(ssl->sockfd, (const unsigned char *) buffer, len, 0);
if (ret < 0) {
ESP_LOGE(TAG, "tcp_write error, errno=%s", strerror(errno));
esp_transport_capture_errno(t, errno);
-98
View File
@@ -37,7 +37,6 @@ static const char *TAG = "transport_ws";
#define WS_SIZE16 126
#define WS_SIZE64 127
#define MAX_WEBSOCKET_HEADER_SIZE 16
#define WS_RESPONSE_OK 101
#define WS_TRANSPORT_MAX_CONTROL_FRAME_BUFFER_LEN 125
// HTTP status codes for redirection as described in RFC 9110.
@@ -450,92 +449,6 @@ static int _ws_write(esp_transport_handle_t t, int opcode, int mask_flag, const
return ret;
}
// This method is similar to _ws_write() but it assumes, that the first 16 bytes of the buffer should not be sent and
// should rather be used for the required websocket header itself. This is done to have a single TCP packet for header
// and payload and to avoid copying and allocating additional resources. The first 16 bytes should not be initialized
// in any specific way, and the return value (length) will also include the 16 byte extra buffer.
static int _ws_write_optimized(esp_transport_handle_t t, int opcode, int mask_flag, const char *b, int len, int timeout_ms)
{
assert(len >= MAX_WEBSOCKET_HEADER_SIZE);
transport_ws_t *ws = esp_transport_get_context_data(t);
char *buffer = (char *)b;
char *ws_header;
// char *mask;
int header_len = 0; //, i;
int poll_write;
if ((poll_write = esp_transport_poll_write(ws->parent, timeout_ms)) <= 0) {
ESP_LOGE(TAG, "Error transport_poll_write %i", poll_write);
return poll_write;
}
int len2 = len - MAX_WEBSOCKET_HEADER_SIZE;
if (len2 <= 125) {
ws_header = buffer+MAX_WEBSOCKET_HEADER_SIZE-2-4;
ws_header[header_len++] = opcode;
ws_header[header_len++] = (uint8_t)(len2 | mask_flag);
} else if (len2 < 65536) {
ws_header = buffer+MAX_WEBSOCKET_HEADER_SIZE-4-4;
ws_header[header_len++] = opcode;
ws_header[header_len++] = WS_SIZE16 | mask_flag;
ws_header[header_len++] = (uint8_t)(len2 >> 8);
ws_header[header_len++] = (uint8_t)(len2 & 0xFF);
} else {
ws_header = buffer+MAX_WEBSOCKET_HEADER_SIZE-10-4;
ws_header[header_len++] = opcode;
ws_header[header_len++] = WS_SIZE64 | mask_flag;
/* Support maximum 4 bytes length */
ws_header[header_len++] = 0; //(uint8_t)((len >> 56) & 0xFF);
ws_header[header_len++] = 0; //(uint8_t)((len >> 48) & 0xFF);
ws_header[header_len++] = 0; //(uint8_t)((len >> 40) & 0xFF);
ws_header[header_len++] = 0; //(uint8_t)((len >> 32) & 0xFF);
ws_header[header_len++] = (uint8_t)((len2 >> 24) & 0xFF);
ws_header[header_len++] = (uint8_t)((len2 >> 16) & 0xFF);
ws_header[header_len++] = (uint8_t)((len2 >> 8) & 0xFF);
ws_header[header_len++] = (uint8_t)((len2 >> 0) & 0xFF);
}
if (mask_flag) {
ws_header[header_len++] = 0;
ws_header[header_len++] = 0;
ws_header[header_len++] = 0;
ws_header[header_len++] = 0;
// mask = &ws_header[header_len];
// mask = 0;
// ssize_t rc;
// if ((rc = getrandom(ws_header + header_len, 4, 0)) < 0) {
// ESP_LOGD(TAG, "getrandom() returned %zd", rc);
// return -1;
// }
// header_len += 4;
// for (i = MAX_WEBSOCKET_HEADER_SIZE; i < len; ++i) {
// buffer[i] = (buffer[i] ^ mask[i % 4]);
// }
}
// if (esp_transport_write(ws->parent, ws_header, len - MAX_WEBSOCKET_HEADER_SIZE + header_len, timeout_ms) != header_len) {
// ESP_LOGE(TAG, "Error write header");
// return -1;
// }
// if (len == 0) {
// return 0;
// }
int ret = esp_transport_write(ws->parent, ws_header, len - MAX_WEBSOCKET_HEADER_SIZE + header_len, timeout_ms);
// ESP_LOGI(TAG, "len=%d header_len=%d total_size=%d sent=%d", len, header_len, len - MAX_WEBSOCKET_HEADER_SIZE + header_len, ret);
// in case of masked transport we have to revert back to the original data, as ws layer
// does not create its own copy of data to be sent
if (mask_flag) {
// mask = &ws_header[header_len - 4];
// for (i = 0; i < len; ++i) {
// buffer[i] = (buffer[i] ^ mask[i % 4]);
// }
}
return ret + (ws_header - buffer);
}
int esp_transport_ws_send_raw(esp_transport_handle_t t, ws_transport_opcodes_t opcode, const char *b, int len, int timeout_ms)
{
uint8_t op_code = ws_get_bin_opcode(opcode);
@@ -547,17 +460,6 @@ int esp_transport_ws_send_raw(esp_transport_handle_t t, ws_transport_opcodes_t o
return _ws_write(t, op_code, WS_MASK, b, len, timeout_ms);
}
int esp_transport_ws_send_raw_optimized(esp_transport_handle_t t, ws_transport_opcodes_t opcode, const char *b, int len, int timeout_ms)
{
uint8_t op_code = ws_get_bin_opcode(opcode);
if (t == NULL) {
ESP_LOGE(TAG, "Transport must be a valid ws handle");
return ESP_ERR_INVALID_ARG;
}
ESP_LOGD(TAG, "Sending raw ws message with opcode %d", op_code);
return _ws_write_optimized(t, op_code, WS_MASK, b, len, timeout_ms);
}
static int ws_write(esp_transport_handle_t t, const char *b, int len, int timeout_ms)
{
if (len == 0) {