2#if defined(UMM_POISON_CHECK)
3#define POISON_BYTE (0xa5)
13static size_t poison_size(
size_t s) {
14 return s ? (UMM_POISON_SIZE_BEFORE +
15 sizeof(UMM_POISONED_BLOCK_LEN_TYPE) +
16 UMM_POISON_SIZE_AFTER)
23static void dump_mem(
const void *ptr,
size_t len) {
25 DBGLOG_ERROR(
" 0x%.2x", (*(uint8_t *)ptr++));
32static void put_poison(
void *ptr,
size_t poison_size) {
33 memset(ptr, POISON_BYTE, poison_size);
43static bool check_poison(
const void *ptr,
size_t poison_size,
48 for (i = 0; i < poison_size; i++) {
49 if (((uint8_t *)ptr)[i] != POISON_BYTE) {
56 DBGLOG_ERROR(
"No poison %s block at: 0x%08x, actual data:", (
char *)where, DBGLOG_32_BIT_PTR(ptr));
57 dump_mem(ptr, poison_size);
68static bool check_poison_block(umm_block *pblock) {
71 if (pblock->header.used.next & UMM_FREELIST_MASK) {
72 DBGLOG_ERROR(
"check_poison_block is called for free block 0x%08x\n", DBGLOG_32_BIT_PTR(pblock));
75 void *pc = (
void *)pblock->body.data;
78 pc_cur = pc +
sizeof(UMM_POISONED_BLOCK_LEN_TYPE);
79 if (!check_poison(pc_cur, UMM_POISON_SIZE_BEFORE,
"before")) {
84 pc_cur = pc + *((UMM_POISONED_BLOCK_LEN_TYPE *)pc) - UMM_POISON_SIZE_AFTER;
85 if (!check_poison(pc_cur, UMM_POISON_SIZE_AFTER,
"after")) {
102static void *get_poisoned(
void *ptr,
size_t size_w_poison) {
103 if (size_w_poison != 0 && ptr != NULL) {
105 put_poison(ptr +
sizeof(UMM_POISONED_BLOCK_LEN_TYPE),
106 UMM_POISON_SIZE_BEFORE);
107 put_poison(ptr + size_w_poison - UMM_POISON_SIZE_AFTER,
108 UMM_POISON_SIZE_AFTER);
111 *(UMM_POISONED_BLOCK_LEN_TYPE *)ptr = (UMM_POISONED_BLOCK_LEN_TYPE)size_w_poison;
114 return ptr +
sizeof(UMM_POISONED_BLOCK_LEN_TYPE) + UMM_POISON_SIZE_BEFORE;
126static void *get_unpoisoned(
void *ptr) {
130 ptr -= (
sizeof(UMM_POISONED_BLOCK_LEN_TYPE) + UMM_POISON_SIZE_BEFORE);
133 c = (((
void *)ptr) - (
void *)(&(UMM_HEAP[0]))) / UMM_BLOCKSIZE;
135 check_poison_block(&UMM_BLOCK(c));
145void *umm_poison_malloc(
size_t size) {
148 size += poison_size(size);
150 ret = umm_malloc(size);
152 ret = get_poisoned(ret, size);
159void *umm_poison_calloc(
size_t num,
size_t item_size) {
161 size_t size = item_size * num;
163 size += poison_size(size);
165 ret = umm_malloc(size);
168 memset(ret, 0x00, size);
171 ret = get_poisoned(ret, size);
178void *umm_poison_realloc(
void *ptr,
size_t size) {
181 ptr = get_unpoisoned(ptr);
183 size += poison_size(size);
184 ret = umm_realloc(ptr, size);
186 ret = get_poisoned(ret, size);
193void umm_poison_free(
void *ptr) {
194 ptr = get_unpoisoned(ptr);
203bool umm_poison_check(
void) {
204 UMM_CRITICAL_DECL(id_poison);
207 unsigned short int cur;
209 UMM_CHECK_INITIALIZED();
211 UMM_CRITICAL_ENTRY(id_poison);
214 cur = UMM_NBLOCK(0) & UMM_BLOCKNO_MASK;
216 while (UMM_NBLOCK(cur) & UMM_BLOCKNO_MASK) {
217 if (!(UMM_NBLOCK(cur) & UMM_FREELIST_MASK)) {
219 ok = check_poison_block(&UMM_BLOCK(cur));
225 cur = UMM_NBLOCK(cur) & UMM_BLOCKNO_MASK;
227 UMM_CRITICAL_EXIT(id_poison);