CSAPP实验5:malloc lab

本文详细介绍了如何实现一个简单的内存管理系统,包括内存分配、释放和重新分配的函数,如 `mm_malloc`、`mm_free` 和 `mm_realloc`。通过 `extend_heap`、`coalesce` 和 `find_fit` 等辅助函数,实现了内存块的合并和查找适合大小的空闲块。此外,还展示了如何初始化内存管理模块。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言

这个实验想法还是十分清晰的,但是我写了几次都直接错误了,然后bug也不知道到底是哪里出现了问题,最后就只好参考别人的了。
参考博客:实验5:malloc lab

代码



#include "mm.h"
#include "memlib.h"

team_t team = {
     /* Team name */
    "XXXXXX",
    /* First member's full name */
    "yzf",
    /* First member's email address */
    "@Fd",
    /* Second member's full name (leave blank if none) */
    "",
    /* Second member's email address (leave blank if none) */
    ""
};
#define ALIGNMENT 8

/* rounds up to the nearest multiple of ALIGNMENT */
#define ALIGN(size) (((size) + (ALIGNMENT-1)) & ~0x7)


#define SIZE_T_SIZE (ALIGN(sizeof(size_t)))

#define WSIZE 4
#define DSIZE 8
#define CHUNKSIZE (1<<12) /* Extend heap by this amount (bytes) */
#define MINBLOCKSIZE 16

#define MAX(x, y) ((x) > (y) ? (x) : (y))
#define PACK(size, alloc) ((size) | (alloc)) /* Pack a size and allocated bit into a word */

#define GET(p) (*(unsigned int *)(p)) /* read a word at address p */
#define PUT(p, val) (*(unsigned int *)(p) = (val)) /* write a word at address p */

#define GET_SIZE(p) (GET(p) & ~0x7) /* read the size field from address p */
#define GET_ALLOC(p) (GET(p) & 0x1) /* read the alloc field from address p */

#define HDRP(bp) ((char*)(bp) - WSIZE) /* given block ptr bp, compute address of its header */
#define FTRP(bp) ((char*)(bp) + GET_SIZE(HDRP(bp)) - DSIZE) /* given block ptr bp, compute address of its footer */

#define NEXT_BLKP(bp) ((char*)(bp) + GET_SIZE(HDRP(bp))) /* given block ptr bp, compute address of next blocks */
#define PREV_BLKP(bp) ((char*)(bp) - GET_SIZE((char*)(bp)-DSIZE)) /* given block ptr bp, compute address of prev blocks */
static char* heap_listp;
static void* extend_heap(size_t size);
static void* coalesce(void *bp);
static void* find_fit(size_t asize);
static void split_block(void* bp, size_t asize);
static void place(void* bp, size_t asize);
int mm_init(void);
void *mm_malloc(size_t size);
void mm_free(void *bp);
void *mm_realloc(void *ptr, size_t size);

/*
 * extend heap by words * word(4 bytes)
 */
static void* extend_heap(size_t words)
{
       char* bp;
    size_t size;

    /* Allocate an even number of words to maintain alignment */
    size = (words % 2) ? (words + 1) * WSIZE : words * WSIZE;
    if ((long)(bp = mem_sbrk(size)) == -1)
        return NULL;

    /* Initialize free block header/footer and the epilogue header */
    PUT(HDRP(bp), PACK(size, 0)); //free block header
    PUT(FTRP(bp), PACK(size, 0)); //free block footer
    PUT(HDRP(NEXT_BLKP(bp)), PACK(0, 1)); // new epilogue header

    return coalesce(bp); //coalesce if the previous block was free
       
}

/*
 * coalesce
 */
static void* coalesce(void *bp)
{
      size_t pre_alloc=GET_ALLOC(FTRP(PREV_BLKP(bp)));
       size_t next_alloc=GET_ALLOC(HDRP(NEXT_BLKP(bp)));
       size_t size=GET_SIZE(HDRP(bp));
       if(pre_alloc&&next_alloc)return bp;
       else if(!pre_alloc&&next_alloc){
            size+=GET_SIZE(FTRP(PREV_BLKP(bp)));
            PUT(HDRP(PREV_BLKP(bp)),PACK(size,0));
            PUT(FTRP(bp),PACK(size,0));
            return PREV_BLKP(bp);
       }else if(pre_alloc&&!next_alloc){
            size+=GET_SIZE(HDRP(NEXT_BLKP(bp)));
            PUT(HDRP(bp),PACK(size,0));
            PUT(FTRP(bp),PACK(size,0));
            return bp;
       }else {
            size+=GET_SIZE(FTRP(PREV_BLKP(bp)))+GET_SIZE(HDRP(NEXT_BLKP(bp)));
            PUT(HDRP(PREV_BLKP(bp)),PACK(size,0));
            PUT(FTRP(PREV_BLKP(bp)),PACK(size,0));
            return PREV_BLKP(bp);
       }
}

/*
 * find_fit - use first fit strategy to find an empty block.
 */
static void* find_fit(size_t asize)
{
       char*listp;
       for(listp=heap_listp;GET_SIZE(HDRP(listp));listp=NEXT_BLKP(listp)){
           size_t alloc=GET_ALLOC(HDRP(listp));
           size_t size=GET_SIZE(HDRP(listp));
           if(!alloc&&asize<=size){
               return listp;
           }
       }
       return NULL;
}

/*
 * split_block
 */
static void split_block(void* bp, size_t asize)
{
       size_t size = GET_SIZE(HDRP(bp));

    if ((size - asize) >= MINBLOCKSIZE)
    {
        PUT(HDRP(bp), PACK(asize, 1));
        PUT(FTRP(bp), PACK(asize, 1));
        bp = NEXT_BLKP(bp);
        PUT(HDRP(bp), PACK(size-asize, 0));
        PUT(FTRP(bp), PACK(size-asize, 0));
    }
}

/*
 * place - Place the request block at the beginning of the free block, 
 *         and only split if the remaining part is equal to or larger than the size of the smallest block
 */
static void place(void* bp, size_t asize)
{
    size_t size = GET_SIZE(HDRP(bp));
    PUT(HDRP(bp), PACK(size, 1));
    PUT(FTRP(bp), PACK(size, 1));

    split_block(bp, asize);
}

/* 
 * mm_init - initialize the malloc package.
 */
int mm_init(void)
{
    size_t *bp;
    if((bp=mem_sbrk(4*WSIZE))==(void*)-1){
        return -1;
    }
    PUT(heap_listp,0);
    PUT(heap_listp+WSIZE,PACK(DSIZE,1));
    PUT(heap_listp+2*WSIZE,PACK(DSIZE,1));
    PUT(heap_listp+3*WSIZE,PACK(0,1));
    heap_listp+=2*WSIZE;
    next_listp=heap_listp;
    if((bp=extend_heap(CHUNKSIZE/WSIZE))==NULL)return -1;
    return 0;
}

/* 
 * mm_malloc - Allocate a block by incrementing the brk pointer.
 *     Always allocate a block whose size is a multiple of the alignment.
 */
void *mm_malloc(size_t size)
{
    size_t *bp;
      size_t asize,extendsize;
      if(size==0)return NULL;
     if (size <= DSIZE)
        asize = 2*DSIZE;
     else
        asize = DSIZE * ((size + (DSIZE) + (DSIZE - 1)) / DSIZE);
     if((bp=find_fit(asize))!=NULL){
         place(bp,asize);
         return bp;
     }
     extendsize=MAX(asize,CHUNKSIZE);
     if((bp=extend_heap(extendsize/WSIZE))==NULL)return NULL;
     place(bp,asize);
     return bp;
}

/*
 * mm_free - Freeing a block does nothing.
 */
void mm_free(void *bp)
{
    size_t size = GET_SIZE(HDRP(bp));

    PUT(HDRP(bp), PACK(size, 0));
    PUT(FTRP(bp), PACK(size, 0));
    coalesce(bp);
}

/*
 * mm_realloc - Implemented simply in terms of mm_malloc and mm_free
 */
void *mm_realloc(void *ptr, size_t size)
{
    void *oldptr = ptr;
    void *newptr;
    size_t copySize;

    newptr = mm_malloc(size);
    if (newptr == NULL)
      return NULL;
    size = GET_SIZE(HDRP(oldptr));
    copySize = GET_SIZE(HDRP(newptr));
    if (size < copySize)
      copySize = size;
    memcpy(newptr, oldptr, copySize-WSIZE);
    mm_free(oldptr);
    return newptr;
}

实验结果

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值