- Reworked memory handling to avoid realloc problems if it decides to relocate the block.

git-svn-id: http://cmock.svn.sourceforge.net/svnroot/cmock/trunk@202 bf332499-1b4d-0410-844d-d2d48d5cc64c
This commit is contained in:
mvandervoord
2011-01-13 18:10:57 +00:00
parent 1504d71f77
commit e9a7151241
15 changed files with 213 additions and 174 deletions
+61 -39
View File
@@ -17,11 +17,6 @@
#include <stdlib.h>
#endif
//should be big enough to index full range of CMOCK_MEM_MAX
#ifndef CMOCK_MEM_INDEX_TYPE
#define CMOCK_MEM_INDEX_TYPE unsigned int
#endif
//this is used internally during pointer arithmetic. make sure this type is the same size as the target's pointer type
#ifndef CMOCK_MEM_PTR_AS_INT
#define CMOCK_MEM_PTR_AS_INT unsigned long
@@ -44,24 +39,24 @@
//private variables
#ifdef CMOCK_MEM_DYNAMIC
static unsigned char* CMock_Guts_Buffer = NULL;
static unsigned int CMock_Guts_BufferSize = 0;
static unsigned int CMock_Guts_FreePtr;
static unsigned char* CMock_Guts_Buffer = NULL;
static CMOCK_MEM_INDEX_TYPE CMock_Guts_BufferSize = CMOCK_MEM_ALIGN_SIZE;
static CMOCK_MEM_INDEX_TYPE CMock_Guts_FreePtr;
#else
static unsigned char CMock_Guts_Buffer[CMOCK_MEM_SIZE];
static unsigned int CMock_Guts_BufferSize = CMOCK_MEM_SIZE;
static unsigned int CMock_Guts_FreePtr;
static unsigned char CMock_Guts_Buffer[CMOCK_MEM_SIZE + CMOCK_MEM_ALIGN_SIZE];
static CMOCK_MEM_INDEX_TYPE CMock_Guts_BufferSize = CMOCK_MEM_SIZE + CMOCK_MEM_ALIGN_SIZE;
static CMOCK_MEM_INDEX_TYPE CMock_Guts_FreePtr;
#endif
//-------------------------------------------------------
// CMock_Guts_MemNew
//-------------------------------------------------------
void* CMock_Guts_MemNew(unsigned int size)
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemNew(CMOCK_MEM_INDEX_TYPE size)
{
unsigned int index;
CMOCK_MEM_INDEX_TYPE index;
//verify arguments valid (we must be allocating space for at least 1 byte, and the existing chain must be in memory somewhere)
if (size < 1)
return NULL;
return CMOCK_GUTS_NONE;
//verify we have enough room
size = size + CMOCK_MEM_INDEX_SIZE;
@@ -74,75 +69,102 @@ void* CMock_Guts_MemNew(unsigned int size)
CMock_Guts_Buffer = realloc(CMock_Guts_Buffer, CMock_Guts_BufferSize);
if (CMock_Guts_Buffer == NULL)
#endif //yes that if will continue to the return below if TRUE
return NULL;
return CMOCK_GUTS_NONE;
}
//determine where we're putting this new block, and init its pointer to be the end of the line
index = CMock_Guts_FreePtr + CMOCK_MEM_INDEX_SIZE;
*(CMOCK_MEM_INDEX_TYPE*)(&CMock_Guts_Buffer[CMock_Guts_FreePtr]) = 0;
*(CMOCK_MEM_INDEX_TYPE*)(&CMock_Guts_Buffer[CMock_Guts_FreePtr]) = CMOCK_GUTS_NONE;
CMock_Guts_FreePtr += size;
return (&CMock_Guts_Buffer[index]);
return index;
}
//-------------------------------------------------------
// CMock_Guts_MemChain
//-------------------------------------------------------
void* CMock_Guts_MemChain(void* root, void* obj)
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemChain(CMOCK_MEM_INDEX_TYPE root_index, CMOCK_MEM_INDEX_TYPE obj_index)
{
unsigned int index;
CMOCK_MEM_INDEX_TYPE index;
void* root;
void* obj;
void* next;
if (root == NULL)
if (root_index == CMOCK_GUTS_NONE)
{
//if there is no root currently, we return this object as the root of the chain
return obj;
return obj_index;
}
else
{
//reject illegal nodes
if ((root < (void*)CMock_Guts_Buffer) || (root >= (void*)(&CMock_Guts_Buffer[CMock_Guts_FreePtr])))
return NULL;
if ((obj < (void*)CMock_Guts_Buffer) || (obj >= (void*)(&CMock_Guts_Buffer[CMock_Guts_FreePtr])))
return NULL;
if ((root_index < CMOCK_MEM_ALIGN_SIZE) || (root_index >= CMock_Guts_FreePtr))
{
return CMOCK_GUTS_NONE;
}
if ((obj_index < CMOCK_MEM_ALIGN_SIZE) || (obj_index >= CMock_Guts_FreePtr))
{
return CMOCK_GUTS_NONE;
}
root = (void*)(&CMock_Guts_Buffer[root_index]);
obj = (void*)(&CMock_Guts_Buffer[obj_index]);
//find the end of the existing chain and add us
next = root;
do {
index = *(CMOCK_MEM_INDEX_TYPE*)((CMOCK_MEM_PTR_AS_INT)next - CMOCK_MEM_INDEX_SIZE);
if (index >= CMock_Guts_FreePtr)
return NULL;
return CMOCK_GUTS_NONE;
if (index > 0)
next = (void*)(&CMock_Guts_Buffer[index]);
} while (index > 0);
*(CMOCK_MEM_INDEX_TYPE*)((CMOCK_MEM_PTR_AS_INT)next - CMOCK_MEM_INDEX_SIZE) = ((CMOCK_MEM_PTR_AS_INT)obj - (CMOCK_MEM_PTR_AS_INT)CMock_Guts_Buffer);
return root;
return root_index;
}
}
//-------------------------------------------------------
// CMock_Guts_MemNext
//-------------------------------------------------------
void* CMock_Guts_MemNext(void* previous_item)
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemNext(CMOCK_MEM_INDEX_TYPE previous_item_index)
{
CMOCK_MEM_INDEX_TYPE index;
CMOCK_MEM_INDEX_TYPE index;
void* previous_item;
//There is nothing "next" if the pointer isn't from our buffer
if ((previous_item < (void*)CMock_Guts_Buffer) || (previous_item >= (void*)(&CMock_Guts_Buffer[CMock_Guts_FreePtr])))
return NULL;
if ((previous_item_index < CMOCK_MEM_ALIGN_SIZE) || (previous_item_index >= CMock_Guts_FreePtr))
return CMOCK_GUTS_NONE;
previous_item = (void*)(&CMock_Guts_Buffer[previous_item_index]);
//if the pointer is good, then use it to look up the next index (we know the first element always goes in zero, so NEXT must always be > 1)
//if the pointer is good, then use it to look up the next index
//(we know the first element always goes in zero, so NEXT must always be > 1)
index = *(CMOCK_MEM_INDEX_TYPE*)((CMOCK_MEM_PTR_AS_INT)previous_item - CMOCK_MEM_INDEX_SIZE);
if ((index > 1) && (index < CMock_Guts_FreePtr))
return (void*)(&CMock_Guts_Buffer[index]);
return index;
else
return NULL;
}
return CMOCK_GUTS_NONE;
}
//-------------------------------------------------------
// CMock_GetAddressFor
//-------------------------------------------------------
void* CMock_Guts_GetAddressFor(CMOCK_MEM_INDEX_TYPE index)
{
if ((index >= CMOCK_MEM_ALIGN_SIZE) && (index < CMock_Guts_FreePtr))
{
return (void*)(&CMock_Guts_Buffer[index]);
}
else
{
return NULL;
}
}
//-------------------------------------------------------
// CMock_Guts_MemBytesFree
//-------------------------------------------------------
unsigned int CMock_Guts_MemBytesFree(void)
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemBytesFree(void)
{
return CMock_Guts_BufferSize - CMock_Guts_FreePtr;
}
@@ -150,9 +172,9 @@ unsigned int CMock_Guts_MemBytesFree(void)
//-------------------------------------------------------
// CMock_Guts_MemBytesUsed
//-------------------------------------------------------
unsigned int CMock_Guts_MemBytesUsed(void)
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemBytesUsed(void)
{
return CMock_Guts_FreePtr;
return CMock_Guts_FreePtr - CMOCK_MEM_ALIGN_SIZE;
}
//-------------------------------------------------------
@@ -160,5 +182,5 @@ unsigned int CMock_Guts_MemBytesUsed(void)
//-------------------------------------------------------
void CMock_Guts_MemFreeAll(void)
{
CMock_Guts_FreePtr = 0;
CMock_Guts_FreePtr = CMOCK_MEM_ALIGN_SIZE; //skip the very beginning
}
+17 -7
View File
@@ -5,16 +5,26 @@
========================================== */
#ifndef CMOCK_FRAMEWORK_H
#define CMOCK_FRAMEWORK_H
#define CMOCK_FRAMEWORK_H
//should be big enough to index full range of CMOCK_MEM_MAX
#ifndef CMOCK_MEM_INDEX_TYPE
#define CMOCK_MEM_INDEX_TYPE unsigned int
#endif
#define CMOCK_GUTS_NONE (0)
//-------------------------------------------------------
// Memory API
//-------------------------------------------------------
void* CMock_Guts_MemNew(unsigned int size);
void* CMock_Guts_MemChain(void* root, void* obj);
void* CMock_Guts_MemNext(void* previous_item);
unsigned int CMock_Guts_MemBytesFree(void);
unsigned int CMock_Guts_MemBytesUsed(void);
void CMock_Guts_MemFreeAll(void);
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemNew(CMOCK_MEM_INDEX_TYPE size);
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemChain(CMOCK_MEM_INDEX_TYPE root_index, CMOCK_MEM_INDEX_TYPE obj_index);
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemNext(CMOCK_MEM_INDEX_TYPE previous_item_index);
void* CMock_Guts_GetAddressFor(CMOCK_MEM_INDEX_TYPE index);
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemBytesFree(void);
CMOCK_MEM_INDEX_TYPE CMock_Guts_MemBytesUsed(void);
void CMock_Guts_MemFreeAll(void);
#endif //CMOCK_FRAMEWORK