Skip to content

Commit 834ec81

Browse files
committed
fix(ws): Fix handling of allocation failures
H/t @mathieucarbou
1 parent 317701b commit 834ec81

2 files changed

Lines changed: 15 additions & 6 deletions

File tree

src/AsyncWebSocket.cpp

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -450,6 +450,7 @@ void AsyncWebSocketClient::close(uint16_t code, const char *message) {
450450
if (c) {
451451
c->abort();
452452
}
453+
return;
453454
}
454455
}
455456
_queueControl(WS_DISCONNECT);
@@ -595,7 +596,9 @@ void AsyncWebSocketClient::_onData(void *pbuf, size_t plen) {
595596
"[%s][%" PRIu32 "] DATA processing next fragment of %s frame %" PRIu32 ", index: %" PRIu64 ", len: %" PRIu32 "", _server->url(), _clientId,
596597
(_pinfo.message_opcode == WS_TEXT) ? "text" : "binary", _pinfo.num, _pinfo.index, (uint32_t)datalen
597598
);
598-
_handleDataEvent(data, datalen, datalen == plen); // datalen == plen means that we are processing the last part of the current TCP packet
599+
if (!_handleDataEvent(data, datalen, datalen == plen)) { // datalen == plen means that we are processing the last part of the current TCP packet
600+
return; // stop processing on failure
601+
}
599602
}
600603

601604
// track index for next fragment
@@ -644,7 +647,9 @@ void AsyncWebSocketClient::_onData(void *pbuf, size_t plen) {
644647
(_pinfo.message_opcode == WS_TEXT) ? "text" : "binary", _pinfo.num, _pinfo.index, (uint32_t)datalen
645648
);
646649

647-
_handleDataEvent(data, datalen, datalen == plen); // datalen == plen means that we are processing the last part of the current TCP packet
650+
if (!_handleDataEvent(data, datalen, datalen == plen)) { // datalen == plen means that we are processing the last part of the current TCP packet
651+
return; // stop processing on failure
652+
}
648653

649654
if (_pinfo.final) {
650655
_pinfo.num = 0;
@@ -674,7 +679,7 @@ void AsyncWebSocketClient::_onData(void *pbuf, size_t plen) {
674679
}
675680
}
676681

677-
void AsyncWebSocketClient::_handleDataEvent(uint8_t *data, size_t len, bool endOfPaquet) {
682+
bool AsyncWebSocketClient::_handleDataEvent(uint8_t *data, size_t len, bool endOfPaquet) {
678683
// ------------------------------------------------------------
679684
// Issue 384: https://github.com/ESP32Async/ESPAsyncWebServer/issues/384
680685
// Discussion: https://github.com/ESP32Async/ESPAsyncWebServer/pull/383#discussion_r2760425739
@@ -705,9 +710,11 @@ void AsyncWebSocketClient::_handleDataEvent(uint8_t *data, size_t len, bool endO
705710
_server->_handleEvent(this, WS_EVT_DATA, (void *)&_pinfo, copy.get(), len);
706711
} else {
707712
async_ws_log_e("Failed to allocate");
708-
if (_client) {
709-
_client->abort();
713+
AsyncClient *c = _client;
714+
if (c) {
715+
c->abort();
710716
}
717+
return false; // failure!
711718
}
712719
} else {
713720
uint8_t backup = data[len];
@@ -718,6 +725,7 @@ void AsyncWebSocketClient::_handleDataEvent(uint8_t *data, size_t len, bool endO
718725
} else {
719726
_server->_handleEvent(this, WS_EVT_DATA, (void *)&_pinfo, data, len);
720727
}
728+
return true;
721729
}
722730

723731
size_t AsyncWebSocketClient::printf(const char *format, ...) {

src/AsyncWebSocket.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -190,7 +190,8 @@ class AsyncWebSocketClient {
190190
void _runQueue(asyncsrv::unique_lock_type &lock);
191191

192192
// this function is called when a text message is received, in order to copy the buffer and place a null terminator at the end of the buffer for easier handling of text messages.
193-
void _handleDataEvent(uint8_t *data, size_t len, bool endOfPaquet);
193+
// Returns true on success, false on failure (e.g. memory allocation failure)
194+
bool _handleDataEvent(uint8_t *data, size_t len, bool endOfPaquet);
194195

195196
public:
196197
void *_tempObject;

0 commit comments

Comments
 (0)