|
@@ -1,168 +0,0 @@
|
|
|
-/*
|
|
|
- * Copyright 2011 Institute of Communication and Computer Systems (ICCS)
|
|
|
- *
|
|
|
- * Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
- * you may not use this file except in compliance with the License.
|
|
|
- * You may obtain a copy of the License at
|
|
|
- *
|
|
|
- * http://www.apache.org/licenses/LICENSE-2.0
|
|
|
- *
|
|
|
- * Unless required by applicable law or agreed to in writing, software
|
|
|
- * distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
- * See the License for the specific language governing permissions and
|
|
|
- * limitations under the License.
|
|
|
- *
|
|
|
- */
|
|
|
-
|
|
|
-/**
|
|
|
- * \file custom_realloc.c
|
|
|
- * \author Ioannis Koutras (joko@microlab.ntua.gr)
|
|
|
- * \date January, 2012
|
|
|
- *
|
|
|
- * \brief Implementation of a function to change the size of an allocated
|
|
|
- * block.
|
|
|
- */
|
|
|
-
|
|
|
-#include <dmmlib/custom_realloc.h>
|
|
|
-#include <dmmlib/initialize_allocator.h>
|
|
|
-#include "block_header.h"
|
|
|
-#ifndef NO_SYSTEM_CALLS
|
|
|
-#include "other.h"
|
|
|
-#endif /* NO_SYSTEM_CALLS */
|
|
|
-#if defined (SPLITTING_FIXED) || defined (SPLITTING_VARIABLE)
|
|
|
-#include "split.h"
|
|
|
-#endif /* SPLITTING_FIXED || SPLITTING_VARIABLE */
|
|
|
-
|
|
|
-/**
|
|
|
- * Allocates a new block and copies the contents of the old block to the new
|
|
|
- * block. No check is done if there is an old block!
|
|
|
- */
|
|
|
-void * clean_realloc(allocator_t *allocator, heap_t *heap, void *ptr,
|
|
|
- size_t size);
|
|
|
-/**
|
|
|
- * Copy a memory area
|
|
|
- */
|
|
|
-static void custom_memcpy(void* dest, const void* src, size_t n) {
|
|
|
- char *dst8, *src8;
|
|
|
-
|
|
|
- dst8 = (char *) dest + HEADER_SIZE;
|
|
|
- src8 = (char *) src + HEADER_SIZE;
|
|
|
-
|
|
|
- while(n--) {
|
|
|
- *dst8++ = *src8++;
|
|
|
- }
|
|
|
-}
|
|
|
-
|
|
|
-void * clean_realloc(allocator_t *allocator, heap_t *heap, void *ptr,
|
|
|
- size_t size) {
|
|
|
- size_t old_size;
|
|
|
- void *new_ptr;
|
|
|
-
|
|
|
- old_size = get_size(ptr);
|
|
|
- new_ptr = custom_ahmalloc(allocator, heap, size);
|
|
|
- custom_memcpy(new_ptr, ptr, old_size);
|
|
|
- custom_ahfree(allocator, heap, ptr);
|
|
|
-
|
|
|
- return new_ptr;
|
|
|
-}
|
|
|
-
|
|
|
-/**
|
|
|
- * \details The realloc() function tries to change the size of the allocation
|
|
|
- * pointed to by ptr to size, and returns ptr. realloc() creates a new
|
|
|
- * allocation, copies as much of the old data pointed to by ptr as will fit to
|
|
|
- * the new allocation, frees the old allocation and returns a pointer to the
|
|
|
- * allocated memory. If ptr is NULL, realloc() is identical to a call to
|
|
|
- * malloc() for size bytes.
|
|
|
- */
|
|
|
-void * custom_ahrealloc(allocator_t *allocator, heap_t *heap, void *ptr, size_t size) {
|
|
|
- void *next_block;
|
|
|
- size_t old_size;
|
|
|
-#if defined (REQUEST_SIZE_INFO) && defined (WITH_STATS)
|
|
|
- size_t old_requested_size;
|
|
|
-#endif /* (REQUEST_SIZE_INFO) && (WITH_STATS) */
|
|
|
-
|
|
|
-#if defined (SPLITTING_FIXED) || defined (SPLITTING_VARIABLE)
|
|
|
- size_t min_split_size;
|
|
|
-#endif /* (SPLITTING_FIXED) || (SPLITTING_VARIABLE) */
|
|
|
-
|
|
|
- if(ptr != NULL) {
|
|
|
- old_size = get_size(ptr);
|
|
|
- if(old_size > size) {
|
|
|
- /* The old size is bigger than the new, use the old block */
|
|
|
-
|
|
|
-#ifdef REQUEST_SIZE_INFO
|
|
|
-#ifdef WITH_STATS
|
|
|
- old_requested_size = get_requested_size(ptr);
|
|
|
- heap->dmm_stats.mem_requested += old_requested_size;
|
|
|
- heap->dmm_stats.mem_requested += size;
|
|
|
-#endif /* WITH_STATS */
|
|
|
- set_requested_size(ptr, size);
|
|
|
-#endif /* REQUEST_SIZE_INFO */
|
|
|
-
|
|
|
- /* Try to split the currently allocated block */
|
|
|
-#if defined (SPLITTING_FIXED) || defined (SPLITTING_VARIABLE)
|
|
|
-#ifdef SPLITTING_FIXED
|
|
|
- min_split_size = MIN_SPLITTING_SIZE;
|
|
|
-#endif /* SPLITTING_FIXED */
|
|
|
-#ifdef SPLITTING_VARIABLE
|
|
|
- min_split_size = heap->dmm_knobs.min_split_size;
|
|
|
-#endif /* SPLITTING_VARIABLE */
|
|
|
-
|
|
|
- if(old_size - size - HEADER_SIZE >= min_split_size) {
|
|
|
- split(allocator, heap, ptr, size);
|
|
|
- }
|
|
|
-#endif /* (SPLITTING_FIXED) || (SPLITTING_VARIABLE) */
|
|
|
- return ptr;
|
|
|
- } else {
|
|
|
- /* The new size can't fit in the old box */
|
|
|
-
|
|
|
- /* Check if the block next to the original as in the data layout
|
|
|
- * can be used.
|
|
|
- */
|
|
|
- next_block = get_dlnext(allocator, ptr);
|
|
|
- if(next_block != NULL) {
|
|
|
-#ifndef WITH_OWNERSHIP
|
|
|
- if(is_free(next_block) == true) {
|
|
|
-#else /* WITH_OWNERSHIP */
|
|
|
- if(is_free(next_block) == true
|
|
|
- && get_owner(next_block) == get_owner(ptr)) {
|
|
|
-#endif /* WITH_OWNERSHIP */
|
|
|
- if(size < old_size + get_size(next_block) + HEADER_SIZE) {
|
|
|
- remove_block_from_lists(&next_block, heap);
|
|
|
- if(allocator->border_ptr == next_block) {
|
|
|
- allocator->border_ptr = ptr;
|
|
|
- }
|
|
|
- set_size_and_used(allocator,
|
|
|
- ptr,
|
|
|
- old_size + get_size(next_block) + HEADER_SIZE);
|
|
|
-
|
|
|
-#if defined (SPLITTING_FIXED) || defined (SPLITTING_VARIABLE)
|
|
|
-#ifdef SPLITTING_FIXED
|
|
|
- min_split_size = MIN_SPLITTING_SIZE;
|
|
|
-#endif /* SPLITTING_FIXED */
|
|
|
-#ifdef SPLITTING_VARIABLE
|
|
|
- min_split_size = heap->dmm_knobs.min_split_size;
|
|
|
-#endif /* SPLITTING_VARIABLE */
|
|
|
-
|
|
|
- if(get_size(ptr) - size >= min_split_size) {
|
|
|
- split(allocator, heap, ptr, size);
|
|
|
- }
|
|
|
-#endif /* (SPLITTING_FIXED) || (SPLITTING_VARIABLE) */
|
|
|
-
|
|
|
- return ptr;
|
|
|
- } else {
|
|
|
- return clean_realloc(allocator, heap, ptr, size);
|
|
|
- }
|
|
|
- } else {
|
|
|
- return clean_realloc(allocator, heap, ptr, size);
|
|
|
- }
|
|
|
- } else {
|
|
|
- return clean_realloc(allocator, heap, ptr, size);
|
|
|
- }
|
|
|
- }
|
|
|
- } else {
|
|
|
- /* ptr is NULL, call malloc() */
|
|
|
- return custom_ahmalloc(allocator, heap, size);
|
|
|
- }
|
|
|
-}
|