static void _gcry_secmem_free_internal (void *a) { memblock_t *mb; int size; if (!a) return; mb = ADDR_TO_BLOCK (a); size = mb->size; /* This does not make much sense: probably this memory is held in the * cache. We do it anyway: */ #define MB_WIPE_OUT(byte) \ wipememory2 ((memblock_t *) ((char *) mb + BLOCK_HEAD_SIZE), (byte), size); MB_WIPE_OUT (0xff); MB_WIPE_OUT (0xaa); MB_WIPE_OUT (0x55); MB_WIPE_OUT (0x00); stats_update (0, size); mb->flags &= ~MB_FLAG_ACTIVE; /* Update stats. */ mb_merge (mb); }
/* Return a new block, which can hold SIZE bytes. */ static memblock_t * mb_get_new (memblock_t *block, size_t size) { memblock_t *mb, *mb_split; for (mb = block; BLOCK_VALID (mb); mb = mb_get_next (mb)) if (! (mb->flags & MB_FLAG_ACTIVE) && mb->size >= size) { /* Found a free block. */ mb->flags |= MB_FLAG_ACTIVE; if (mb->size - size > BLOCK_HEAD_SIZE) { /* Split block. */ mb_split = (memblock_t *) (((char *) mb) + BLOCK_HEAD_SIZE + size); mb_split->size = mb->size - size - BLOCK_HEAD_SIZE; mb_split->flags = 0; mb->size = size; mb_merge (mb_split); } break; } if (! BLOCK_VALID (mb)) mb = NULL; return mb; }
/* Return a new block, which can hold SIZE bytes. */ static memblock_t * mb_get_new (memblock_t *block, size_t size) { memblock_t *mb, *mb_split; for (mb = block; ptr_into_pool_p (mb); mb = mb_get_next (mb)) if (! (mb->flags & MB_FLAG_ACTIVE) && mb->size >= size) { /* Found a free block. */ mb->flags |= MB_FLAG_ACTIVE; if (mb->size - size > BLOCK_HEAD_SIZE) { /* Split block. */ mb_split = (memblock_t *) (((char *) mb) + BLOCK_HEAD_SIZE + size); mb_split->size = mb->size - size - BLOCK_HEAD_SIZE; mb_split->flags = 0; mb->size = size; mb_merge (mb_split); } break; } if (! ptr_into_pool_p (mb)) { gpg_err_set_errno (ENOMEM); mb = NULL; } return mb; }