Skip to content

Commit c934304

Browse files
committed
[Memory] Fix strange crashes due to not using correct heap
1 parent e12a784 commit c934304

File tree

5 files changed

+48
-5
lines changed

5 files changed

+48
-5
lines changed

src/src/DataStructs/EventQueue.cpp

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
#include "EventQueue.h"
22

3+
#include "../../ESPEasy_common.h"
4+
35
EventQueueStruct::EventQueueStruct() {}
46

57
void EventQueueStruct::add(const String& event)
@@ -16,7 +18,8 @@ void EventQueueStruct::add(const __FlashStringHelper * event)
1618
#ifdef USE_SECOND_HEAP
1719
HeapSelectIram ephemeral;
1820
#endif
19-
_eventQueue.push_back(event);
21+
// Wrap in String() constructor to make sure it is using the 2nd heap allocator if present.
22+
_eventQueue.push_back(String(event));
2023
}
2124

2225
void EventQueueStruct::addMove(String&& event)
@@ -35,7 +38,12 @@ bool EventQueueStruct::getNext(String& event)
3538
return false;
3639
}
3740
#ifdef USE_SECOND_HEAP
38-
event = _eventQueue.front();
41+
{
42+
// Fetch the event and make sure it is allocated on the DRAM heap, not the 2nd heap
43+
// Otherwise checks like strnlen_P may crash on it.
44+
HeapSelectDram ephemeral;
45+
event = std::move(String(_eventQueue.front()));
46+
}
3947
#else
4048
event = std::move(_eventQueue.front());
4149
#endif

src/src/DataStructs/EventQueue.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44

55
#include <list>
6-
#include "../../ESPEasy_common.h"
6+
77

88
#include "../Globals/Plugins.h"
99

src/src/DataStructs/LogStruct.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,8 @@ void LogStruct::add(const byte loglevel, const char *line) {
3434
#ifdef USE_SECOND_HEAP
3535
{
3636
if (millis() > 5000) {
37+
// FIXME TD-er: Must check if we're called from loop() and not from setup()
38+
// For now we can probably expect not to be in the setup() anymore???
3739
HeapSelectIram ephemeral;
3840
}
3941
Message[write_idx] = EMPTY_STRING; // Have to clear it first or else it will re-allocate on the same heap
@@ -51,6 +53,11 @@ bool LogStruct::get(String& output, const String& lineEnd) {
5153
lastReadTimeStamp = millis();
5254

5355
if (!isEmpty()) {
56+
#ifdef USE_SECOND_HEAP
57+
// Fetch the log line and make sure it is allocated on the DRAM heap, not the 2nd heap
58+
// Otherwise checks like strnlen_P may crash on it.
59+
HeapSelectDram ephemeral;
60+
#endif
5461
read_idx = (read_idx + 1) % LOG_STRUCT_MESSAGE_LINES;
5562
output += formatLine(read_idx, lineEnd);
5663
}

src/src/DataStructs/LogStruct.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
#define LOG_BUFFER_EXPIRE 30000 // Time after which a buffered log item is considered expired.
1515
#else
1616
#ifdef USE_SECOND_HEAP
17-
#define LOG_STRUCT_MESSAGE_LINES 15
17+
#define LOG_STRUCT_MESSAGE_LINES 30
1818
#else
1919
#if defined(PLUGIN_BUILD_TESTING) || defined(PLUGIN_BUILD_DEV)
2020
#define LOG_STRUCT_MESSAGE_LINES 10

src/src/DataStructs/Web_StreamingBuffer.cpp

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010

1111
#include "../Helpers/ESPEasy_time_calc.h"
1212

13-
13+
#include "../../ESPEasy_common.h"
1414

1515
#define CHUNKED_BUFFER_SIZE 400
1616

@@ -69,6 +69,10 @@ Web_StreamingBuffer Web_StreamingBuffer::operator+=(const __FlashStringHelper* s
6969
}
7070

7171
Web_StreamingBuffer Web_StreamingBuffer::addFlashString(PGM_P str) {
72+
#ifdef USE_SECOND_HEAP
73+
HeapSelectDram ephemeral;
74+
#endif
75+
7276
++flashStringCalls;
7377

7478
if (!str) { return *this; // return if the pointer is void
@@ -163,6 +167,10 @@ void Web_StreamingBuffer::startJsonStream() {
163167
}
164168

165169
void Web_StreamingBuffer::startStream(bool json, const String& origin) {
170+
#ifdef USE_SECOND_HEAP
171+
HeapSelectDram ephemeral;
172+
#endif
173+
166174
maxCoreUsage = maxServerUsage = 0;
167175
initialRam = ESP.getFreeHeap();
168176
beforeTXRam = initialRam;
@@ -183,6 +191,10 @@ void Web_StreamingBuffer::startStream(bool json, const String& origin) {
183191
}
184192

185193
void Web_StreamingBuffer::trackTotalMem() {
194+
#ifdef USE_SECOND_HEAP
195+
HeapSelectDram ephemeral;
196+
#endif
197+
186198
beforeTXRam = ESP.getFreeHeap();
187199

188200
if ((initialRam - beforeTXRam) > maxServerUsage) {
@@ -191,6 +203,10 @@ void Web_StreamingBuffer::trackTotalMem() {
191203
}
192204

193205
void Web_StreamingBuffer::trackCoreMem() {
206+
#ifdef USE_SECOND_HEAP
207+
HeapSelectDram ephemeral;
208+
#endif
209+
194210
duringTXRam = ESP.getFreeHeap();
195211

196212
if ((initialRam - duringTXRam) > maxCoreUsage) {
@@ -199,6 +215,10 @@ void Web_StreamingBuffer::trackCoreMem() {
199215
}
200216

201217
void Web_StreamingBuffer::endStream() {
218+
#ifdef USE_SECOND_HEAP
219+
HeapSelectDram ephemeral;
220+
#endif
221+
202222
if (!lowMemorySkip) {
203223
if (buf.length() > 0) { sendContentBlocking(buf); }
204224
buf.clear();
@@ -230,6 +250,10 @@ void Web_StreamingBuffer::endStream() {
230250

231251

232252
void Web_StreamingBuffer::sendContentBlocking(String& data) {
253+
#ifdef USE_SECOND_HEAP
254+
HeapSelectDram ephemeral;
255+
#endif
256+
233257
const uint32_t length = data.length();
234258
#ifndef BUILD_NO_DEBUG
235259
if (loglevelActiveFor(LOG_LEVEL_DEBUG_DEV)) {
@@ -283,6 +307,10 @@ void Web_StreamingBuffer::sendContentBlocking(String& data) {
283307
}
284308

285309
void Web_StreamingBuffer::sendHeaderBlocking(bool json, const String& origin) {
310+
#ifdef USE_SECOND_HEAP
311+
HeapSelectDram ephemeral;
312+
#endif
313+
286314
#ifndef BUILD_NO_RAM_TRACKER
287315
checkRAM(F("sendHeaderBlocking"));
288316
#endif

0 commit comments

Comments
 (0)