Example #1
0
/*
* mm_init - Initialize the malloc package. Construct prologue and epilogue
* blocks.
*/
int mm_init(void)
{
int list; // List counter
char *heap_start; // Pointer to beginning of heap
/* Initialize array of pointers to segregated free lists */
for (list = 0; list < LISTS; list++) {
free_lists[list] = NULL;
}
/* Allocate memory for the initial empty heap */
if ((long)(heap_start = mem_sbrk(4 * WSIZE)) == -1)
return -1;
PUT_NOTAG(heap_start, 0); /* Alignment padding */
PUT_NOTAG(heap_start + (1 * WSIZE), PACK(DSIZE, 1)); /* Prologue header */
PUT_NOTAG(heap_start + (2 * WSIZE), PACK(DSIZE, 1)); /* Prologue footer */
PUT_NOTAG(heap_start + (3 * WSIZE), PACK(0, 1)); /* Epilogue header */
prologue_block = heap_start + DSIZE;
/* Extend the empty heap */
if (extend_heap(CHUNKSIZE) == NULL)
return -1;
/* Variables for checking function
line_count = LINE_OFFSET;
skip = 0;
*/
return 0;
}
Example #2
0
static void *place(void *ptr, size_t asize)
{
    size_t ptr_size = GET_SIZE(HDRP(ptr));
    size_t remainder = ptr_size - asize;
    
    delete_node(ptr);
    
    
    if (remainder <= DSIZE * 2) {
        // Do not split block 
        PUT(HDRP(ptr), PACK(ptr_size, 1)); 
        PUT(FTRP(ptr), PACK(ptr_size, 1)); 
    }
    
    else if (asize >= 100) {
        // Split block
        PUT(HDRP(ptr), PACK(remainder, 0));
        PUT(FTRP(ptr), PACK(remainder, 0));
        PUT_NOTAG(HDRP(NEXT_BLKP(ptr)), PACK(asize, 1));
        PUT_NOTAG(FTRP(NEXT_BLKP(ptr)), PACK(asize, 1));
        insert_node(ptr, remainder);
        return NEXT_BLKP(ptr);
        
    }
    
    else {
        // Split block
        PUT(HDRP(ptr), PACK(asize, 1)); 
        PUT(FTRP(ptr), PACK(asize, 1)); 
        PUT_NOTAG(HDRP(NEXT_BLKP(ptr)), PACK(remainder, 0)); 
        PUT_NOTAG(FTRP(NEXT_BLKP(ptr)), PACK(remainder, 0)); 
        insert_node(NEXT_BLKP(ptr), remainder);
    }
    return ptr;
}
Example #3
0
/*
* mm_realloc - Reallocate a block in place, extending the heap if necessary.
* The new block is padded with a buffer to guarantee that the
* next reallocation can be done without extending the heap,
* assuming that the block is expanded by a constant number of bytes
* per reallocation.
*
* If the buffer is not large enough for the next reallocation,
* mark the next block with the reallocation tag. Free blocks
* marked with this tag cannot be used for allocation or
* coalescing. The tag is cleared when the marked block is
* consumed by reallocation, when the heap is extended, or when
* the reallocated block is freed.
*/
void *mm_realloc(void *ptr, size_t size)
{
void *new_ptr = ptr; /* Pointer to be returned */
size_t new_size = size; /* Size of new block */
int remainder; /* Adequacy of block sizes */
int extendsize; /* Size of heap extension */
int block_buffer; /* Size of block buffer */
/* Filter invalid block size */
if (size == 0)
return NULL;
/* Adjust block size to include boundary tag and alignment requirements */
if (new_size <= DSIZE) {
new_size = 2 * DSIZE;
} else {
new_size = DSIZE * ((new_size + (DSIZE) + (DSIZE - 1)) / DSIZE);
}
/* Add overhead requirements to block size */
new_size += BUFFER;
/* Calculate block buffer */
block_buffer = GET_SIZE(HEAD(ptr)) - new_size;
/* Allocate more space if overhead falls below the minimum */
if (block_buffer < 0) {
/* Check if next block is a free block or the epilogue block */
if (!GET_ALLOC(HEAD(NEXT(ptr))) || !GET_SIZE(HEAD(NEXT(ptr)))) {
remainder = GET_SIZE(HEAD(ptr)) + GET_SIZE(HEAD(NEXT(ptr))) - new_size;
if (remainder < 0) {
extendsize = MAX(-remainder, CHUNKSIZE);
if (extend_heap(extendsize) == NULL)
return NULL;
remainder += extendsize;
}
delete_node(NEXT(ptr));
// Do not split block
PUT_NOTAG(HEAD(ptr), PACK(new_size + remainder, 1)); /* Block header */
PUT_NOTAG(FOOT(ptr), PACK(new_size + remainder, 1)); /* Block footer */
} else {
new_ptr = mm_malloc(new_size - DSIZE);
//line_count--;
memmove(new_ptr, ptr, MIN(size, new_size));
mm_free(ptr);
//line_count--;
}
block_buffer = GET_SIZE(HEAD(new_ptr)) - new_size;
}
/* Tag the next block if block overhead drops below twice the overhead */
if (block_buffer < 2 * BUFFER)
SET_TAG(HEAD(NEXT(new_ptr)));
/*
// Check heap for consistency
line_count++;
if (CHECK && CHECK_REALLOC) {
mm_check('r', ptr, size);
}
*/
/* Return reallocated block */
return new_ptr;
}
Example #4
0
/*
 * mm_realloc - Implemented simply in terms of mm_malloc and mm_free
 *
 * Role : The mm_realloc routine returns a pointer to an allocated 
 *        region of at least size bytes with constraints.
 *
 *  I used https://github.com/htian/malloc-lab/blob/master/mm.c source idea to maximize utilization
 *  by using reallocation tags
 *  in reallocation cases (realloc-bal.rep, realloc2-bal.rep)
 */
void *mm_realloc(void *ptr, size_t size)
{
    void *new_ptr = ptr;    /* Pointer to be returned */
    size_t new_size = size; /* Size of new block */
    int remainder;          /* Adequacy of block sizes */
    int extendsize;         /* Size of heap extension */
    int block_buffer;       /* Size of block buffer */
    
    // Ignore size 0 cases
    if (size == 0)
        return NULL;
    
    // Align block size
    if (new_size <= DSIZE) {
        new_size = 2 * DSIZE;
    } else {
        new_size = ALIGN(size+DSIZE);
    }
    
    /* Add overhead requirements to block size */
    new_size += REALLOC_BUFFER;
    
    /* Calculate block buffer */
    block_buffer = GET_SIZE(HDRP(ptr)) - new_size;
    
    /* Allocate more space if overhead falls below the minimum */
    if (block_buffer < 0) {
        /* Check if next block is a free block or the epilogue block */
        if (!GET_ALLOC(HDRP(NEXT_BLKP(ptr))) || !GET_SIZE(HDRP(NEXT_BLKP(ptr)))) {
            remainder = GET_SIZE(HDRP(ptr)) + GET_SIZE(HDRP(NEXT_BLKP(ptr))) - new_size;
            if (remainder < 0) {
                extendsize = MAX(-remainder, CHUNKSIZE);
                if (extend_heap(extendsize) == NULL)
                    return NULL;
                remainder += extendsize;
            }
            
            delete_node(NEXT_BLKP(ptr));
            
            // Do not split block
            PUT_NOTAG(HDRP(ptr), PACK(new_size + remainder, 1)); 
            PUT_NOTAG(FTRP(ptr), PACK(new_size + remainder, 1)); 
        } else {
            new_ptr = mm_malloc(new_size - DSIZE);
            memcpy(new_ptr, ptr, MIN(size, new_size));
            mm_free(ptr);
        }
        block_buffer = GET_SIZE(HDRP(new_ptr)) - new_size;
    }
    
    // Tag the next block if block overhead drops below twice the overhead 
    if (block_buffer < 2 * REALLOC_BUFFER)
        SET_RATAG(HDRP(NEXT_BLKP(new_ptr)));
    
    // Return the reallocated block 
    return new_ptr;
}
Example #5
0
//////////////////////////////////////// Helper functions //////////////////////////////////////////////////////////
static void *extend_heap(size_t size)
{
    void *ptr;                   
    size_t asize;                // Adjusted size 
    
    asize = ALIGN(size);
    
    if ((ptr = mem_sbrk(asize)) == (void *)-1)
        return NULL;
    
    // Set headers and footer 
    PUT_NOTAG(HDRP(ptr), PACK(asize, 0));  
    PUT_NOTAG(FTRP(ptr), PACK(asize, 0));   
    PUT_NOTAG(HDRP(NEXT_BLKP(ptr)), PACK(0, 1)); 
    insert_node(ptr, asize);

    return coalesce(ptr);
}
Example #6
0
/*
* extend_heap - Extend the heap with a system call. Insert the newly
* requested free block into the appropriate list.
*/
static void *extend_heap(size_t size)
{
void *ptr; /* Pointer to newly allocated memory */
size_t words = size / WSIZE; /* Size of extension in words */
size_t asize; /* Adjusted size */
/* Allocate an even number of words to maintain alignment */
asize = (words % 2) ? (words + 1) * WSIZE : words * WSIZE;
/* Extend the heap */
if ((long)(ptr = mem_sbrk(asize)) == -1)
return NULL;
/* Set headers and footer */
PUT_NOTAG(HEAD(ptr), PACK(asize, 0)); /* Free block header */
PUT_NOTAG(FOOT(ptr), PACK(asize, 0)); /* Free block footer */
PUT_NOTAG(HEAD(NEXT(ptr)), PACK(0, 1)); /* Epilogue header */
/* Insert new block into appropriate list */
insert_node(ptr, asize);
/* Coalesce if the previous block was free */
return coalesce(ptr);
}
Example #7
0
/*
* place - Set headers and footers for newly allocated blocks. Split blocks
* if enough space is remaining.
*/
static void place(void *ptr, size_t asize)
{
size_t ptr_size = GET_SIZE(HEAD(ptr));
size_t remainder = ptr_size - asize;
/* Remove block from list */
delete_node(ptr);
if (remainder >= MINSIZE) {
/* Split block */
PUT(HEAD(ptr), PACK(asize, 1)); /* Block header */
PUT(FOOT(ptr), PACK(asize, 1)); /* Block footer */
PUT_NOTAG(HEAD(NEXT(ptr)), PACK(remainder, 0)); /* Next header */
PUT_NOTAG(FOOT(NEXT(ptr)), PACK(remainder, 0)); /* Next footer */
insert_node(NEXT(ptr), remainder);
} else {
/* Do not split block */
PUT(HEAD(ptr), PACK(ptr_size, 1)); /* Block header */
PUT(FOOT(ptr), PACK(ptr_size, 1)); /* Block footer */
}
return;
}
Example #8
0
/*
 * mm_init - initialize the malloc package.
 * Before calling mm_malloc, mm_realloc, or mm_free, 
 * the application program calls mm_init to perform any necessary initializations,
 * such as allocating the initial heap area.
 *
 * Return value : -1 if there was a problem, 0 otherwise.
 */
int mm_init(void)
{
    int list;         
    char *heap_start; // Pointer to beginning of heap
    
    // Initialize segregated free lists
    for (list = 0; list < LISTLIMIT; list++) {
        segregated_free_lists[list] = NULL;
    }
    
    // Allocate memory for the initial empty heap 
    if ((long)(heap_start = mem_sbrk(4 * WSIZE)) == -1)
        return -1;
    
    PUT_NOTAG(heap_start, 0);                            /* Alignment padding */
    PUT_NOTAG(heap_start + (1 * WSIZE), PACK(DSIZE, 1)); /* Prologue header */
    PUT_NOTAG(heap_start + (2 * WSIZE), PACK(DSIZE, 1)); /* Prologue footer */
    PUT_NOTAG(heap_start + (3 * WSIZE), PACK(0, 1));     /* Epilogue header */
    
    if (extend_heap(INITCHUNKSIZE) == NULL)
        return -1;
    
    return 0;
}