From aa96c2d92293f3bfa9329c9e483e9686435a6d73 Mon Sep 17 00:00:00 2001 From: "Roger A. Light" Date: Thu, 13 Jan 2022 23:34:42 +0000 Subject: [PATCH] Check accept key with websockets clients. --- lib/http_client.c | 10 ++++++++-- lib/mosquitto_internal.h | 1 + lib/net_mosq.h | 1 + lib/net_ws.c | 39 +++++++++++++++++++++++++++++++++++++++ src/http_serv.c | 39 +-------------------------------------- 5 files changed, 50 insertions(+), 40 deletions(-) diff --git a/lib/http_client.c b/lib/http_client.c index 69079924..7c264edb 100644 --- a/lib/http_client.c +++ b/lib/http_client.c @@ -59,6 +59,9 @@ int http_c__context_init(struct mosquitto *context) if(create_request_key(&key)){ return MOSQ_ERR_UNKNOWN; } + if(ws__create_accept_key(key, strlen(key), &context->wsd.accept_key)){ + return MOSQ_ERR_UNKNOWN; + } packet = mosquitto__calloc(1, sizeof(struct mosquitto__packet) + 1024 + WS_PACKET_OFFSET); if(!packet) return MOSQ_ERR_NOMEM; @@ -84,6 +87,7 @@ int http_c__context_init(struct mosquitto *context) int http_c__context_cleanup(struct mosquitto *context) { + SAFE_FREE(context->wsd.accept_key); mosquitto__FREE(context->http_request); return MOSQ_ERR_SUCCESS; } @@ -102,7 +106,6 @@ int http_c__read(struct mosquitto *mosq) struct phr_header http_headers[100]; const char *client_key = NULL; size_t client_key_len = 0; - char *accept_key; size_t i; bool header_have_upgrade; bool header_have_connection; @@ -221,7 +224,10 @@ int http_c__read(struct mosquitto *mosq) // FIXME - 404 return MOSQ_ERR_UNKNOWN; } - /* FIXME - check key */ + if(strncmp(mosq->wsd.accept_key, client_key, client_key_len)){ + // FIXME - 50x + return MOSQ_ERR_UNKNOWN; + } http_c__context_cleanup(mosq); ws__context_init(mosq); diff --git a/lib/mosquitto_internal.h b/lib/mosquitto_internal.h index 14561a77..63e7fe37 100644 --- a/lib/mosquitto_internal.h +++ b/lib/mosquitto_internal.h @@ -247,6 +247,7 @@ struct mosquitto_msg_data{ struct ws_data{ struct mosquitto__packet *out_packet; char *http_path; + char *accept_key; uint64_t payloadlen; ssize_t pos; int http_header_size; diff --git a/lib/net_mosq.h b/lib/net_mosq.h index 046321c8..d5bb45dc 100644 --- a/lib/net_mosq.h +++ b/lib/net_mosq.h @@ -91,6 +91,7 @@ UI_METHOD *net__get_ui_method(void); #if defined(WITH_WEBSOCKETS) && WITH_WEBSOCKETS == WS_IS_BUILTIN void ws__context_init(struct mosquitto *mosq); void ws__prepare_packet(struct mosquitto *mosq, struct mosquitto__packet *packet); +int ws__create_accept_key(const char *client_key, size_t client_key_len, char **encoded); #endif #endif diff --git a/lib/net_ws.c b/lib/net_ws.c index e22e6842..930bc8c2 100644 --- a/lib/net_ws.c +++ b/lib/net_ws.c @@ -22,7 +22,9 @@ Contributors: #include #include +#include +#include "base64_mosq.h" #include "mosquitto_internal.h" #include "memory_mosq.h" #include "mqtt_protocol.h" @@ -326,4 +328,41 @@ ssize_t net__read_ws(struct mosquitto *mosq, void *buf, size_t count) return len; } +int ws__create_accept_key(const char *client_key, size_t client_key_len, char **encoded) +{ + const EVP_MD *digest; + EVP_MD_CTX *evp; + uint8_t accept_key_hash[EVP_MAX_MD_SIZE]; + unsigned int accept_key_hash_len; + + digest = EVP_get_digestbyname("sha1"); + if(!digest){ + return MOSQ_ERR_UNKNOWN; + } + + evp = EVP_MD_CTX_new(); + if(EVP_DigestInit_ex(evp, digest, NULL) == 0){ + EVP_MD_CTX_free(evp); + return MOSQ_ERR_UNKNOWN; + } + if(EVP_DigestUpdate(evp, client_key, client_key_len) == 0){ + EVP_MD_CTX_free(evp); + return MOSQ_ERR_UNKNOWN; + } + if(EVP_DigestUpdate(evp, "258EAFA5-E914-47DA-95CA-C5AB0DC85B11", + strlen("258EAFA5-E914-47DA-95CA-C5AB0DC85B11")) == 0){ + + EVP_MD_CTX_free(evp); + return MOSQ_ERR_UNKNOWN; + } + if(EVP_DigestFinal_ex(evp, accept_key_hash, &accept_key_hash_len) == 0){ + EVP_MD_CTX_free(evp); + return MOSQ_ERR_UNKNOWN; + } + EVP_MD_CTX_free(evp); + + return base64__encode(accept_key_hash, accept_key_hash_len, encoded); +} + + #endif diff --git a/src/http_serv.c b/src/http_serv.c index 9ac11333..900deb5d 100644 --- a/src/http_serv.c +++ b/src/http_serv.c @@ -55,43 +55,6 @@ int http__context_cleanup(struct mosquitto *context) } -static int create_accept_key(const char *client_key, size_t client_key_len, char **encoded) -{ - const EVP_MD *digest; - EVP_MD_CTX *evp; - uint8_t accept_key_hash[EVP_MAX_MD_SIZE]; - unsigned int accept_key_hash_len; - - digest = EVP_get_digestbyname("sha1"); - if(!digest){ - return MOSQ_ERR_UNKNOWN; - } - - evp = EVP_MD_CTX_new(); - if(EVP_DigestInit_ex(evp, digest, NULL) == 0){ - EVP_MD_CTX_free(evp); - return MOSQ_ERR_UNKNOWN; - } - if(EVP_DigestUpdate(evp, client_key, client_key_len) == 0){ - EVP_MD_CTX_free(evp); - return MOSQ_ERR_UNKNOWN; - } - if(EVP_DigestUpdate(evp, "258EAFA5-E914-47DA-95CA-C5AB0DC85B11", - strlen("258EAFA5-E914-47DA-95CA-C5AB0DC85B11")) == 0){ - - EVP_MD_CTX_free(evp); - return MOSQ_ERR_UNKNOWN; - } - if(EVP_DigestFinal_ex(evp, accept_key_hash, &accept_key_hash_len) == 0){ - EVP_MD_CTX_free(evp); - return MOSQ_ERR_UNKNOWN; - } - EVP_MD_CTX_free(evp); - - return base64__encode(accept_key_hash, accept_key_hash_len, encoded); -} - - int http__write(struct mosquitto *mosq) { return packet__write(mosq); @@ -242,7 +205,7 @@ int http__read(struct mosquitto *mosq) return MOSQ_ERR_UNKNOWN; } - if(create_accept_key(client_key, client_key_len, &accept_key)){ + if(ws__create_accept_key(client_key, client_key_len, &accept_key)){ return MOSQ_ERR_UNKNOWN; }