Skip to content

Commit 84c92b5

Browse files
committed
api reworked, +example
1 parent 0d2f7a0 commit 84c92b5

File tree

5 files changed

+110
-17
lines changed

5 files changed

+110
-17
lines changed

cores/esp8266/Esp-frag.cpp

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -23,18 +23,26 @@
2323
#include "coredecls.h"
2424
#include "Esp.h"
2525

26-
uint8_t EspClass::getHeapFragmentation (uint32_t* freeHeap, uint16_t* maxBlock)
26+
void EspClass::getHeapStats(uint32_t* free, uint16_t* max, uint8_t* frag)
2727
{
2828
// L2 / Euclidian norm of free block sizes.
29-
// Having getFreeHeap()=sum(hole-size), un-fragmentation is given by
30-
// sqrt(sum(hole-size²)) / sum(hole-size)
29+
// Having getFreeHeap()=sum(hole-size), fragmentation is given by
30+
// 100 * (1 - sqrt(sum(hole-size²)) / sum(hole-size))
3131

3232
umm_info(NULL, 0);
33-
uint32_t block_size = umm_block_size();
33+
uint8_t block_size = umm_block_size();
3434
uint32_t fh = ummHeapInfo.freeBlocks * block_size;
35-
if (freeHeap)
36-
*freeHeap = fh;
37-
if (maxBlock)
38-
*maxBlock = ummHeapInfo.maxFreeContiguousBlocks * block_size;
39-
return 100 - (sqrt32(ummHeapInfo.ummFreeSize2) * 100) / fh;
35+
if (free)
36+
*free = fh;
37+
if (max)
38+
*max = ummHeapInfo.maxFreeContiguousBlocks * block_size;
39+
if (frag)
40+
*frag = 100 - (sqrt32(ummHeapInfo.ummFreeSize2) * 100) / fh;
41+
}
42+
43+
uint8_t EspClass::getHeapFragmentation()
44+
{
45+
uint8_t frag;
46+
getHeapStats(nullptr, nullptr, &frag);
47+
return frag;
4048
}

cores/esp8266/Esp.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include <memory>
2525
#include "interrupts.h"
2626
#include "MD5Builder.h"
27+
#include "umm_malloc/umm_malloc.h"
2728

2829
extern "C" {
2930
#include "user_interface.h"
@@ -173,7 +174,7 @@ uint32_t EspClass::getFreeHeap(void)
173174

174175
uint16_t EspClass::getMaxFreeBlockSize(void)
175176
{
176-
return system_get_free_heap_size();
177+
return umm_max_block_size();
177178
}
178179

179180
uint32_t EspClass::getChipId(void)

cores/esp8266/Esp.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -103,11 +103,12 @@ class EspClass {
103103
void restart();
104104

105105
uint16_t getVcc();
106+
uint32_t getChipId();
107+
106108
uint32_t getFreeHeap();
107109
uint16_t getMaxFreeBlockSize();
108-
uint8_t getHeapFragmentation(uint32_t* freeHeap = nullptr, uint16_t* maxBlock = nullptr); // in %
109-
110-
uint32_t getChipId();
110+
uint8_t getHeapFragmentation(); // in %
111+
void getHeapStats(uint32_t* free = nullptr, uint16_t* max = nullptr, uint8_t* frag = nullptr);
111112

112113
const char * getSdkVersion();
113114
String getCoreVersion();

cores/esp8266/sqrt32.c

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,7 @@
55
uint32_t sqrt32 (uint32_t n)
66
{
77
// http://www.codecodex.com/wiki/Calculate_an_integer_square_root#C
8-
// Another very fast algorithm donated by Tristan Muntsinger
9-
// ([email protected]) is below.
8+
// Another very fast algorithm donated by [email protected]
109
// (note: tested across the full 32 bits range, see comment below)
1110

1211
// 15 iterations (c=1<<15)
@@ -25,7 +24,9 @@ uint32_t sqrt32 (uint32_t n)
2524
}
2625
}
2726

28-
/* tested with:
27+
/*
28+
* tested with:
29+
*
2930
3031
#include <stdio.h>
3132
#include <stdint.h>
@@ -50,4 +51,6 @@ int main (void)
5051
5152
printf("\n");
5253
}
53-
*/
54+
55+
*
56+
*/
Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
2+
// nothing else than showing heap metric usage
3+
// released to public domain
4+
5+
#include <ESP8266WiFi.h>
6+
7+
void stats (const char* what)
8+
{
9+
// we could use getFreeHeap() getMaxFreeBlockSize() and getHeapFragmentation()
10+
// or all at once:
11+
uint32_t free;
12+
uint16_t max;
13+
uint8_t frag;
14+
ESP.getHeapStats(&free, &max, &frag);
15+
16+
Serial.printf("free: %5d - max: %5d - frag: %3d%% <- ", free, max, frag);
17+
// %s requires a malloc that could fail, using println instead:
18+
Serial.println(what);
19+
}
20+
21+
void tryit (int blocksize)
22+
{
23+
void** p;
24+
int blocks;
25+
26+
// heap-used ~= blocks*sizeof(void*) + blocks*blocksize
27+
blocks = ((ESP.getMaxFreeBlockSize() / (blocksize + sizeof(void*))) + 3) & ~3; // rounded up, multiple of 4
28+
29+
Serial.printf("\nFilling memory with blocks of %d bytes each\n", blocksize);
30+
stats("before");
31+
32+
p = (void**)malloc(sizeof(void*) * blocks);
33+
for (int i = 0; i < blocks; i++)
34+
p[i] = malloc(blocksize);
35+
stats("array and blocks allocation");
36+
37+
for (int i = 0; i < blocks; i += 2)
38+
{
39+
if (p[i])
40+
free(p[i]);
41+
p[i] = nullptr;
42+
}
43+
stats("freeing every other blocks");
44+
45+
for (int i = 0; i < blocks; i += 4)
46+
{
47+
if (p[i + 1])
48+
free(p[i + 1]);
49+
p[i + 1] = nullptr;
50+
}
51+
stats("freeing every other remaining blocks");
52+
53+
for (int i = 0; i < blocks; i++)
54+
if (p[i])
55+
free(p[i]);
56+
stats("freeing array");
57+
58+
free(p);
59+
stats("after");
60+
}
61+
62+
void setup()
63+
{
64+
Serial.begin(115200);
65+
WiFi.mode(WIFI_OFF);
66+
67+
tryit(8000);
68+
tryit(4000);
69+
tryit(2000);
70+
tryit(1000);
71+
tryit(500);
72+
tryit(200);
73+
tryit(100);
74+
tryit(50);
75+
tryit(15);
76+
}
77+
78+
void loop ()
79+
{
80+
}

0 commit comments

Comments
 (0)