1 /*
2  Generic test for realloc
3 */
4 
5 #include <stdlib.h>
6 #include <string.h>
7 #include "unity.h"
8 #include "sdkconfig.h"
9 #include "esp_heap_caps.h"
10 #include "soc/soc_memory_layout.h"
11 
12 
13 #ifndef CONFIG_HEAP_POISONING_COMPREHENSIVE
14 /* (can't realloc in place if comprehensive is enabled) */
15 
16 TEST_CASE("realloc shrink buffer in place", "[heap]")
17 {
18     void *x = malloc(64);
19     TEST_ASSERT(x);
20     void *y = realloc(x, 48);
21     TEST_ASSERT_EQUAL_PTR(x, y);
22 }
23 
24 #endif
25 
26 #ifndef CONFIG_ESP_SYSTEM_MEMPROT_FEATURE
27 TEST_CASE("realloc shrink buffer with EXEC CAPS", "[heap]")
28 {
29     const size_t buffer_size = 64;
30 
31     void *x = heap_caps_malloc(buffer_size, MALLOC_CAP_EXEC);
32     TEST_ASSERT(x);
33     void *y = heap_caps_realloc(x, buffer_size - 16, MALLOC_CAP_EXEC);
34     TEST_ASSERT(y);
35 
36     //y needs to fall in a compatible memory area of IRAM:
37     TEST_ASSERT(esp_ptr_executable(y)|| esp_ptr_in_iram(y) || esp_ptr_in_diram_iram(y));
38 
39     free(y);
40 }
41 
42 TEST_CASE("realloc move data to a new heap type", "[heap]")
43 {
44     const char *test = "I am some test content to put in the heap";
45     char buf[64];
46     memset(buf, 0xEE, 64);
47     strlcpy(buf, test, 64);
48 
49     char *a = malloc(64);
50     memcpy(a, buf, 64);
51     // move data from 'a' to IRAM
52     char *b = heap_caps_realloc(a, 64, MALLOC_CAP_EXEC);
53     TEST_ASSERT_NOT_NULL(b);
54     TEST_ASSERT_NOT_EQUAL(a, b);
55     TEST_ASSERT(heap_caps_check_integrity(MALLOC_CAP_INVALID, true));
56     TEST_ASSERT_EQUAL_HEX32_ARRAY(buf, b, 64 / sizeof(uint32_t));
57 
58     // Move data back to DRAM
59     char *c = heap_caps_realloc(b, 48, MALLOC_CAP_8BIT);
60     TEST_ASSERT_NOT_NULL(c);
61     TEST_ASSERT_NOT_EQUAL(b, c);
62     TEST_ASSERT(heap_caps_check_integrity(MALLOC_CAP_INVALID, true));
63     TEST_ASSERT_EQUAL_HEX8_ARRAY(buf, c, 48);
64 
65     free(c);
66 }
67 #endif
68