esp32: Adds C++ exceptions emergency pool size menuconfig option

This commit is contained in:
Alexey Gerenkov
2017-11-17 12:38:19 +03:00
parent b83792f504
commit 7df96718a2
3 changed files with 80 additions and 6 deletions

View File

@@ -20,7 +20,7 @@ class Base
{
public:
virtual ~Base() {}
virtual void foo() = 0;
virtual void foo() = 0;
};
class Derived : public Base
@@ -192,8 +192,13 @@ TEST_CASE("before scheduler has started, static initializers work correctly", "[
TEST_CASE("c++ exceptions work", "[cxx]")
{
/* Note: This test currently trips the memory leak threshold
as libunwind allocates ~4KB of data on first exception. */
/* Note: When first exception (in system) is thrown this test produces memory leaks report (~500 bytes):
- 392 bytes (can vary) as libunwind allocates memory to keep stack frames info to handle exceptions.
This info is kept until global destructors are called by __do_global_dtors_aux()
- 8 bytes are allocated by __cxa_get_globals() to keep __cxa_eh_globals
- 16 bytes are allocated by pthread_setspecific() which is called by __cxa_get_globals() to init TLS var for __cxa_eh_globals
- 88 bytes are allocated by pthread_setspecific() to init internal lock
*/
int thrown_value;
try
{
@@ -207,6 +212,60 @@ TEST_CASE("c++ exceptions work", "[cxx]")
printf("OK?\n");
}
TEST_CASE("c++ exceptions emergency pool", "[cxx] [ignore]")
{
/* Note: When first exception (in system) is thrown this test produces memory leaks report (~500 bytes):
- 392 bytes (can vary) as libunwind allocates memory to keep stack frames info to handle exceptions.
This info is kept until global destructors are called by __do_global_dtors_aux()
- 8 bytes are allocated by __cxa_get_globals() to keep __cxa_eh_globals
- 16 bytes are allocated by pthread_setspecific() which is called by __cxa_get_globals() to init TLS var for __cxa_eh_globals
- 88 bytes are allocated by pthread_setspecific() to init internal lock
*/
void **p, **pprev = NULL;
int thrown_value = 0;
// throw first exception to ensure that all initial allocations are made
try
{
throw 33;
}
catch (int e)
{
thrown_value = e;
}
TEST_ASSERT_EQUAL(33, thrown_value);
// consume all dynamic memory
while ((p = (void **)malloc(sizeof(void *)))) {
if (pprev) {
*p = pprev;
} else {
*p = NULL;
}
pprev = p;
}
try
{
throw 20;
}
catch (int e)
{
thrown_value = e;
printf("Got exception %d\n", thrown_value);
}
#if CONFIG_CXX_EXCEPTIONS_EMG_POOL_SIZE > 0
// free all memory
while (pprev) {
p = (void **)(*pprev);
free(pprev);
pprev = p;
}
TEST_ASSERT_EQUAL(20, thrown_value);
#else
// if emergency pool is disabled we should never get here,
// expect abort() due to lack of memory for new exception
TEST_ASSERT_TRUE(0 == 1);
#endif
}
#endif
/* These test cases pull a lot of code from libstdc++ and are disabled for now