/******************************************************************//** Frees a block from a memory heap. */ UNIV_INTERN void mem_heap_block_free( /*================*/ mem_heap_t* heap, /*!< in: heap */ mem_block_t* block) /*!< in: block to free */ { ulint type; ulint len; #ifndef UNIV_HOTBACKUP buf_block_t* buf_block = block->buf_block; #endif /* !UNIV_HOTBACKUP */ if (block->magic_n != MEM_BLOCK_MAGIC_N) { mem_analyze_corruption(block); } UT_LIST_REMOVE(list, heap->base, block); #ifdef MEM_PERIODIC_CHECK mem_pool_mutex_enter(); UT_LIST_REMOVE(mem_block_list, mem_block_list, block); mem_pool_mutex_exit(); #endif type = heap->type; len = block->len; block->magic_n = MEM_FREED_BLOCK_MAGIC_N; #ifdef UNIV_MEM_DEBUG /* In the debug version we set the memory to a random combination of hex 0xDE and 0xAD. */ mem_erase_buf((byte*)block, len); #else /* UNIV_MEM_DEBUG */ UNIV_MEM_ASSERT_AND_FREE(block, len); #endif /* UNIV_MEM_DEBUG */ #ifndef UNIV_HOTBACKUP if (type == MEM_HEAP_DYNAMIC || len < UNIV_PAGE_SIZE / 2) { ut_ad(!buf_block); mem_area_free(block, mem_comm_pool); } else { ut_ad(type & MEM_HEAP_BUFFER); buf_block_free(buf_block); } #else /* !UNIV_HOTBACKUP */ ut_free(block); #endif /* !UNIV_HOTBACKUP */ }
void mem_heap_block_free( /*================*/ mem_heap_t* heap, /* in: heap */ mem_block_t* block) /* in: block to free */ { ulint type; ulint len; ibool init_block; if (block->magic_n != MEM_BLOCK_MAGIC_N) { mem_analyze_corruption((byte*)block); } UT_LIST_REMOVE(list, heap->base, block); #ifdef MEM_PERIODIC_CHECK mem_pool_mutex_enter(); UT_LIST_REMOVE(mem_block_list, mem_block_list, block); mem_pool_mutex_exit(); #endif type = heap->type; len = block->len; init_block = block->init_block; block->magic_n = MEM_FREED_BLOCK_MAGIC_N; #ifdef UNIV_MEM_DEBUG /* In the debug version we set the memory to a random combination of hex 0xDE and 0xAD. */ mem_erase_buf((byte*)block, len); #endif if (init_block) { /* Do not have to free: do nothing */ } else if (type == MEM_HEAP_DYNAMIC) { mem_area_free(block, mem_comm_pool); } else { ut_ad(type & MEM_HEAP_BUFFER); if (len >= UNIV_PAGE_SIZE / 2) { buf_frame_free((byte*)block); } else { mem_area_free(block, mem_comm_pool); } } }
/******************************************************************//** Erases an allocated memory field in the debug version. */ UNIV_INTERN void mem_field_erase( /*============*/ byte* buf, /*!< in: memory field */ ulint n __attribute__((unused))) /*!< in: how many bytes the user requested */ { byte* usr_buf; usr_buf = buf + MEM_FIELD_HEADER_SIZE; mutex_enter(&mem_hash_mutex); mem_current_allocated_memory -= n; mutex_exit(&mem_hash_mutex); /* Check that the field lengths agree */ ut_ad(n == (ulint)mem_field_header_get_len(usr_buf)); /* In the debug version, set the freed space to a random combination of 0xDE and 0xAD */ mem_erase_buf(buf, MEM_SPACE_NEEDED(n)); }