|
@ -1,5 +1,5 @@ |
|
|
/* |
|
|
/* |
|
|
* mm-naive.c - The clear list, first fit malloc package. |
|
|
|
|
|
|
|
|
* mm-naive.c - The clear list(LIFO), best fit, coalesce immediately malloc package. |
|
|
*/ |
|
|
*/ |
|
|
#include <string.h> |
|
|
#include <string.h> |
|
|
|
|
|
|
|
@ -19,7 +19,7 @@ team_t team = { |
|
|
"" |
|
|
"" |
|
|
}; |
|
|
}; |
|
|
|
|
|
|
|
|
/* single word (4) or double word (8) alignment */ |
|
|
|
|
|
|
|
|
/* single size_t (4) or double size_t (8) alignment */ |
|
|
#define ALIGNMENT 8 |
|
|
#define ALIGNMENT 8 |
|
|
/* rounds up to the nearest multiple of ALIGNMENT */ |
|
|
/* rounds up to the nearest multiple of ALIGNMENT */ |
|
|
#define ALIGN(size) (((size) + (ALIGNMENT - 1)) & ~0x7) |
|
|
#define ALIGN(size) (((size) + (ALIGNMENT - 1)) & ~0x7) |
|
@ -28,7 +28,7 @@ team_t team = { |
|
|
#define WSIZE 4 |
|
|
#define WSIZE 4 |
|
|
#define DSIZE 8 |
|
|
#define DSIZE 8 |
|
|
#define FSIZE 16 |
|
|
#define FSIZE 16 |
|
|
#define ADDRESS (sizeof(unsigned long)) |
|
|
|
|
|
|
|
|
#define ADDRESS (sizeof(size_t)) |
|
|
#define CHUNK 1 << 12 |
|
|
#define CHUNK 1 << 12 |
|
|
#define MIN_BLOCK (2 * ADDRESS + DSIZE) |
|
|
#define MIN_BLOCK (2 * ADDRESS + DSIZE) |
|
|
|
|
|
|
|
@ -50,10 +50,10 @@ team_t team = { |
|
|
|
|
|
|
|
|
#define POS_PRED(bp) ((byte *)(bp)) |
|
|
#define POS_PRED(bp) ((byte *)(bp)) |
|
|
#define POS_SUCC(bp) (((byte *)(bp) + ADDRESS)) |
|
|
#define POS_SUCC(bp) (((byte *)(bp) + ADDRESS)) |
|
|
#define GET_PRED(bp) (*(word *)POS_PRED(bp)) |
|
|
|
|
|
#define GET_SUCC(bp) (*(word *)POS_SUCC(bp)) |
|
|
|
|
|
|
|
|
#define GET_PRED(bp) (*(size_t *)POS_PRED(bp)) |
|
|
|
|
|
#define GET_SUCC(bp) (*(size_t *)POS_SUCC(bp)) |
|
|
|
|
|
|
|
|
typedef unsigned long word; |
|
|
|
|
|
|
|
|
typedef unsigned int word; |
|
|
typedef char byte; |
|
|
typedef char byte; |
|
|
|
|
|
|
|
|
// mark the front and tail pos |
|
|
// mark the front and tail pos |
|
@ -113,12 +113,20 @@ static void *_next_best_fit(size_t size); |
|
|
|
|
|
|
|
|
/** |
|
|
/** |
|
|
* traverse blank block only and find first fit, then place in |
|
|
* traverse blank block only and find first fit, then place in |
|
|
|
|
|
* @deprecated for the memory loss |
|
|
* @param size align by 8, excluding head and foot |
|
|
* @param size align by 8, excluding head and foot |
|
|
* @return |
|
|
* @return |
|
|
*/ |
|
|
*/ |
|
|
static void *_first_fit_of_clear(size_t size); |
|
|
static void *_first_fit_of_clear(size_t size); |
|
|
|
|
|
|
|
|
/** |
|
|
/** |
|
|
|
|
|
* best fit for clear list |
|
|
|
|
|
* @param size align by 8, excluding head and foot |
|
|
|
|
|
* @return |
|
|
|
|
|
*/ |
|
|
|
|
|
static void *_best_fit_of_clear(size_t size); |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
* allocate the block and cut sometimes |
|
|
* allocate the block and cut sometimes |
|
|
* @param size align by 8, excluding head and foot |
|
|
* @param size align by 8, excluding head and foot |
|
|
*/ |
|
|
*/ |
|
@ -157,7 +165,7 @@ void *mm_malloc(size_t size) { |
|
|
size_t adjust_size = ALIGN(size); |
|
|
size_t adjust_size = ALIGN(size); |
|
|
size_t extend_size; |
|
|
size_t extend_size; |
|
|
void *bp; |
|
|
void *bp; |
|
|
if ((bp = _first_fit_of_clear(adjust_size)) != NULL) { |
|
|
|
|
|
|
|
|
if ((bp = _best_fit_of_clear(adjust_size)) != NULL) { |
|
|
// fitted_p = bp; |
|
|
// fitted_p = bp; |
|
|
return bp; |
|
|
return bp; |
|
|
} else { |
|
|
} else { |
|
@ -208,15 +216,35 @@ void *mm_realloc(void *ptr, size_t size) { |
|
|
if (adjust_size <= total_size) { |
|
|
if (adjust_size <= total_size) { |
|
|
void *next = NEXT(ptr); |
|
|
void *next = NEXT(ptr); |
|
|
// remove |
|
|
// remove |
|
|
SET(POS_SUCC(GET_PRED(next)), GET_SUCC(next)); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(next)), GET_PRED(next)); |
|
|
|
|
|
if (next == list_p) { |
|
|
|
|
|
if (GET_SUCC(next) == (word)next) list_p = NULL; |
|
|
|
|
|
else list_p = (void *)GET_SUCC(next); |
|
|
|
|
|
|
|
|
if (total_size - adjust_size >= MIN_BLOCK) { |
|
|
|
|
|
SET(POS_SUCC(GET_PRED(next)), GET_SUCC(next)); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(next)), GET_PRED(next)); |
|
|
|
|
|
SET(HEAD(ptr), PACK(total_size, 1)); |
|
|
|
|
|
SET(FOOT(ptr), PACK(total_size, 1)); |
|
|
|
|
|
if (next == list_p) { |
|
|
|
|
|
if (GET_SUCC(next) == (size_t) next) list_p = NULL; |
|
|
|
|
|
else list_p = (void *) GET_SUCC(next); |
|
|
|
|
|
} |
|
|
|
|
|
if (next == tail_p) tail_p = ptr; |
|
|
|
|
|
} else { // replace |
|
|
|
|
|
void *pred = (void *)GET_PRED(next); |
|
|
|
|
|
void *succ = (void *) GET_SUCC(next); |
|
|
|
|
|
SET(HEAD(ptr), PACK(adjust_size, 1)); |
|
|
|
|
|
SET(FOOT(ptr), PACK(adjust_size, 1)); |
|
|
|
|
|
size_t new_size = total_size - adjust_size - DSIZE; |
|
|
|
|
|
void *new = NEXT(ptr); |
|
|
|
|
|
SET(HEAD(new), PACK(new_size, 0)); |
|
|
|
|
|
SET(FOOT(new), PACK(new_size, 0)); |
|
|
|
|
|
if (pred == next) { |
|
|
|
|
|
SET(POS_PRED(new), (size_t)new); |
|
|
|
|
|
SET(POS_SUCC(new), (size_t)new); |
|
|
|
|
|
} else { |
|
|
|
|
|
SET(POS_PRED(succ), (size_t)new); |
|
|
|
|
|
SET(POS_SUCC(pred), (size_t)new); |
|
|
|
|
|
} |
|
|
|
|
|
if (list_p == next) list_p = new; |
|
|
|
|
|
if (next == tail_p) tail_p = new; |
|
|
} |
|
|
} |
|
|
SET(HEAD(ptr), PACK(total_size, 1)); |
|
|
|
|
|
SET(FOOT(ptr), PACK(total_size, 1)); |
|
|
|
|
|
if (next == tail_p) tail_p = ptr; |
|
|
|
|
|
return ptr; |
|
|
return ptr; |
|
|
} else { |
|
|
} else { |
|
|
if ((new_ptr = mm_malloc(size)) == NULL) return NULL; |
|
|
if ((new_ptr = mm_malloc(size)) == NULL) return NULL; |
|
@ -315,14 +343,14 @@ static void *__coalesce_none(void *bp) { |
|
|
// tweak list |
|
|
// tweak list |
|
|
if (list_p == NULL) { |
|
|
if (list_p == NULL) { |
|
|
list_p = bp; |
|
|
list_p = bp; |
|
|
SET(POS_SUCC(list_p), (word)list_p); |
|
|
|
|
|
SET(POS_PRED(list_p), (word)list_p); |
|
|
|
|
|
|
|
|
SET(POS_SUCC(list_p), (size_t)list_p); |
|
|
|
|
|
SET(POS_PRED(list_p), (size_t)list_p); |
|
|
} else { |
|
|
} else { |
|
|
// add to list |
|
|
// add to list |
|
|
SET(POS_SUCC(bp), GET_SUCC(list_p)); |
|
|
SET(POS_SUCC(bp), GET_SUCC(list_p)); |
|
|
SET(POS_PRED(bp), (word)list_p); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(list_p)), (word)bp); |
|
|
|
|
|
SET(POS_SUCC(list_p), (word)bp); |
|
|
|
|
|
|
|
|
SET(POS_PRED(bp), (size_t)list_p); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(list_p)), (size_t)bp); |
|
|
|
|
|
SET(POS_SUCC(list_p), (size_t)bp); |
|
|
list_p = bp; |
|
|
list_p = bp; |
|
|
} |
|
|
} |
|
|
#ifdef DEBUG |
|
|
#ifdef DEBUG |
|
@ -407,6 +435,25 @@ static void *_first_fit_of_clear(size_t size) { |
|
|
return NULL; |
|
|
return NULL; |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static void *_best_fit_of_clear(size_t size) { |
|
|
|
|
|
void *bp = list_p; |
|
|
|
|
|
if (bp == NULL) return NULL; |
|
|
|
|
|
size_t min = 0; |
|
|
|
|
|
void *min_p = NULL; |
|
|
|
|
|
do { |
|
|
|
|
|
if (SIZE(bp) >= size) { |
|
|
|
|
|
if (min_p == NULL || SIZE(bp) < min) { |
|
|
|
|
|
min = SIZE(bp); |
|
|
|
|
|
min_p = bp; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
bp = (void *)GET_SUCC(bp); |
|
|
|
|
|
} while (bp != list_p); |
|
|
|
|
|
if (min_p == NULL) return NULL; |
|
|
|
|
|
_place(min_p, size); |
|
|
|
|
|
return min_p; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
static void _place(void *ptr, size_t size) { |
|
|
static void _place(void *ptr, size_t size) { |
|
|
size_t p_size = SIZE(ptr); |
|
|
size_t p_size = SIZE(ptr); |
|
|
if (p_size - size >= MIN_BLOCK) { |
|
|
if (p_size - size >= MIN_BLOCK) { |
|
@ -429,7 +476,7 @@ static void _place(void *ptr, size_t size) { |
|
|
SET(POS_SUCC(GET_PRED(ptr)), GET_SUCC(ptr)); |
|
|
SET(POS_SUCC(GET_PRED(ptr)), GET_SUCC(ptr)); |
|
|
SET(POS_PRED(GET_SUCC(ptr)), GET_PRED(ptr)); |
|
|
SET(POS_PRED(GET_SUCC(ptr)), GET_PRED(ptr)); |
|
|
if (ptr == list_p) { |
|
|
if (ptr == list_p) { |
|
|
if (GET_SUCC(ptr) == (word)ptr) list_p = NULL; |
|
|
|
|
|
|
|
|
if (GET_SUCC(ptr) == (size_t)ptr) list_p = NULL; |
|
|
else list_p = (void *)GET_SUCC(ptr); |
|
|
else list_p = (void *)GET_SUCC(ptr); |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
@ -441,14 +488,14 @@ static void _place(void *ptr, size_t size) { |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
static void _fix_list(void *in, void *out) { |
|
|
static void _fix_list(void *in, void *out) { |
|
|
if (GET_SUCC(in) == (word)in) { |
|
|
|
|
|
SET(POS_SUCC(out), (word)out); |
|
|
|
|
|
SET(POS_PRED(out), (word)out); |
|
|
|
|
|
|
|
|
if (GET_SUCC(in) == (size_t)in) { |
|
|
|
|
|
SET(POS_SUCC(out), (size_t)out); |
|
|
|
|
|
SET(POS_PRED(out), (size_t)out); |
|
|
} else { |
|
|
} else { |
|
|
SET(POS_SUCC(out), GET_SUCC(in)); |
|
|
SET(POS_SUCC(out), GET_SUCC(in)); |
|
|
SET(POS_PRED(out), GET_PRED(in)); |
|
|
SET(POS_PRED(out), GET_PRED(in)); |
|
|
SET(POS_SUCC(GET_PRED(in)), (word)out); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(in)), (word)out); |
|
|
|
|
|
|
|
|
SET(POS_SUCC(GET_PRED(in)), (size_t)out); |
|
|
|
|
|
SET(POS_PRED(GET_SUCC(in)), (size_t)out); |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|