Is my zalloc (zero registered malloc) library bulletproof?

I've written my own allocation library, which I use within my emulator. It basically is a library made arround the malloc&free functions, with registration of allocated pointers and checks for valid allocation/deallocation/dereferences. Anyone knows if this is bulletproof?

Main code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
#include "headers/types.h" //Basic types!
#include "headers/support/zalloc.h" //Our own definitions!
#include "headers/support/log.h" //Logging support!

#include <malloc.h> //Specific to us only!

typedef struct
{
void *pointer; //Pointer to the start of the allocated data!
uint_32 size; //Size of the data!
char name[256]; //The name of the allocated entry!
DEALLOCFUNC dealloc; //Deallocation function!
} POINTERENTRY;

POINTERENTRY registeredpointers[1024]; //All registered pointers!

//Debug undefined deallocations?
#define DEBUG_WRONGDEALLOCATION 1
//Debug allocation and deallocation?
#define DEBUG_ALLOCDEALLOC 0

//Pointer registration/unregistration

int allow_zallocfaillog = 1; //Allow zalloc fail log?
uint_32 totalmemory_real; //Total memory present?

inline void initZalloc() //Initialises the zalloc subsystem!
{
	totalmemory_real = freemem(); //Load total memory present!
	int i;
	for (i=0;i<1024;i++)
	{
		registeredpointers[i].pointer = NULL; //Init!
		registeredpointers[i].size = 0; //None!
		bzero(registeredpointers[i].name,sizeof(registeredpointers[i].name));
		registeredpointers[i].dealloc = NULL; //No deallocation function!
	}
}

inline void logpointers() //Logs any changes in memory usage!
{
	int current;
	dolog("zalloc","Starting dump of allocated pointers...");
	uint_32 total_memory = 0; //For checking total memory count!
	uint_32 free_memory = freemem(); //Free memory present!
	total_memory = free_memory; //Total memory present, which is free!
	for (current=0;current<NUMITEMS(registeredpointers);current++)
	{
		if (registeredpointers[current].pointer && registeredpointers[current].size) //Registered?
		{
			if (strlen(registeredpointers[current].name)>0) //Valid name?
			{
				dolog("zalloc","- %s with %i bytes",registeredpointers[current].name,registeredpointers[current].size); //Add the name!
				total_memory += registeredpointers[current].size; //Add to total memory!
			}
		}
	}
	dolog("zalloc","End dump of allocated pointers.");
	dolog("zalloc","Total memory detected: %i bytes; Free memory detected: %i bytes",total_memory,free_memory); //We're a full log!
	dolog("zalloc","Total memory registered: %i bytes; Missing difference (total-detected): %i bytes",totalmemory_real,totalmemory_real-total_memory); //We're the difference info!
}

inline void zalloc_free(void **ptr, uint_32 size) //Free a pointer (used internally only) allocated with nzalloc/zalloc!
{
	free(*ptr); //Release the pointer!
	unregisterptr(*ptr,size); //Safe unregister, keeping parents alive!
	*ptr = NULL; //Release the memory for the user!
}

/*
Matchpointer: matches an pointer to an entry?
parameters:
	ptr: The pointer!
	index: The start index (in bytes)
	size: The size of the data we're going to dereference!
Result:
	-1 when not matched, else the index in the validpointers table.
	
*/
inline int matchptr(void *ptr, uint_32 index, uint_32 size) //Are we already in our list? Give the position!
{
	if (!ptr) return -1; //Not matched when NULL!
	if (!size) return -1; //Not matched when no size (should be impossible)!
	uint_32 address_start = (uint_32)ptr+index; //Start of data!
	uint_32 address_end = address_start+size-1; //End of data!

	int current;
	for (current=0;current<NUMITEMS(registeredpointers);current++) //Process matched options!
	{
		if (registeredpointers[current].pointer && registeredpointers[current].size) //An registered pointer?
		{
			uint_32 currentstart = (uint_32)registeredpointers[current].pointer; //Start of addressing!
			uint_32 currentend = currentstart+registeredpointers[current].size-1; //End of addressing!
			if ((currentstart<=address_start) && (currentend>=address_end)) //Within range?
			{
				if (currentstart==address_start && currentend==address_end) //Full match?
				{
					return current; //Found at this index!
				}
				else //Partly match?
				{
					return -1; //Partly match!
				}
			}
		}
	}
	return -2; //Not found!
}

inline int registerptr(void *ptr,uint_32 size, char *name,DEALLOCFUNC dealloc) //Register a pointer!
{
	if (!ptr) return 0; //Not a pointer?
	if (!size) return 0; //Not a size, so can't be a pointer!
	if (matchptr(ptr,0,size)>-2) return 0; //Already gotten (prevent subs to register after parents)?
	
	uint_32 current; //Current!
	for (current=0;current<NUMITEMS(registeredpointers);current++) //Process valid!
	{
		if (!registeredpointers[current].pointer || !registeredpointers[current].size) //Unused?
		{
			registeredpointers[current].pointer = ptr; //The pointer!
			registeredpointers[current].size = size; //The size!
			registeredpointers[current].dealloc = dealloc; //The deallocation function to call, if any to use!
			bzero(&registeredpointers[current].name,sizeof(registeredpointers[current].name)); //Initialise the name!
			strcpy(registeredpointers[current].name,name); //Set the name!
			return 1; //Registered!
		}
	}
	//dolog("zalloc","Pointer already registered or registration buffer full!");
	return 0; //Give error!
}

inline void unregisterptr(void *ptr, uint_32 size) //Remove pointer from registration (only if original pointer)?
{
	int index;
	if ((index = matchptr(ptr,0,size))>-1) //We've been found fully?
	{
		if (registeredpointers[index].pointer==ptr && registeredpointers[index].size==size) //Fully matched (parents only)?
		{
			registeredpointers[index].pointer = NULL; //Not a pointer!
			registeredpointers[index].size = 0; //No size: we're not a pointer!
		}
	}
}
Last edited on
Part 2:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
inline void *nzalloc(uint_32 size, char *name) //Allocates memory, NULL on failure (ran out of memory), protected malloc!
{
	if (!size) return NULL; //Can't allocate nothing!
	void *ptr = NULL;
	int times=10; //Try 10 times till giving up!
	for (;(!ptr && times);) //Try for some times!
	{
		ptr = malloc(size); //Try to allocate!
		--times; //Next try!
	}
	if (ptr!=NULL) //Allocated and a valid size?
	{
		if (registerptr(ptr,size,name,&zalloc_free)) //Register the pointer with the detection system!
		{
			if (allow_zallocfaillog && DEBUG_ALLOCDEALLOC) dolog("zalloc","Memory has been allocated. Size: %i. Free memory: %i, name: %s",size,freemem(),name); //Log our allocated memory!
			return ptr; //Give the original pointer, cleared to 0!
		}
		if (allow_zallocfaillog && DEBUG_ALLOCDEALLOC) dolog("zalloc","Ran out of registrations while allocating %i bytes of data for block %s.",size,name);
		free(ptr); //Free it, can't generate any more!
	}
	else if (allow_zallocfaillog)
	{
		if (freemem()>=size) //Enough memory after all?
		{
			dolog("zalloc","Error while allocating %i bytes of data for block \"%s\" with enough free memory(%i bytes).",size,name,freemem());
		}
		else
		{
			dolog("zalloc","Ran out of memory while allocating %i bytes of data for block \"%s\".",size,name);
		}
		logpointers(); //Log a dump of pointers!
	}
	return NULL; //Not allocated!
}

inline void *zalloc(uint_32 size, char *name) //Same as nzalloc, but clears the allocated memory!
{
	void *ptr;
	ptr = nzalloc(size,name); //Try to allocate!
	if (ptr) //Allocated?
	{
		return memset(ptr,0,size); //Give the original pointer, cleared to 0!
	}
	return NULL; //Not allocated!
}


inline void freez(void **ptr, uint_32 size, char *name)
{
	if (!ptr) return; //Invalid pointer to deref!
	int ptrn=-1;
	if ((ptrn = matchptr(*ptr,0,size))>-1) //Found fully existant?
	{
		if (allow_zallocfaillog && DEBUG_ALLOCDEALLOC) dolog("zalloc","Freeing pointer %s with size %i bytes...",registeredpointers[ptrn].name,size); //Show we're freeing this!
		if (!registeredpointers[ptrn].dealloc) //Deallocation not registered?
		{
			return; //We can't be freed using this function! We're still allocated!
		}
		registeredpointers[ptrn].dealloc(ptr,size); //Release the memory tied to it using the registered deallocation function, if any!
	}
	else if (allow_zallocfaillog && DEBUG_ALLOCDEALLOC && ptr!=NULL) //An pointer pointing to nothing?
	{
		dolog("zalloc","Warning: freeing pointer which isn't an allocated reference: %s",name); //Log it!
	}
	//Still allocated, we might be a pointer which is a subset, so we can't deallocate!
}

inline void unregisterptrall() //Free all allocated memory still allocated (on shutdown only, garbage collector)!
{
	int i;
	for (i=0;i<NUMITEMS(registeredpointers);i++)
	{
		void *ptr;
		ptr = registeredpointers[i].pointer; //A pointer!
		freez(&ptr,registeredpointers[i].size,"Unregisterptrall"); //Unregister a pointer!
	}
}

inline void freezall() //Same as unregisterptrall
{
	unregisterptrall(); //Unregister all!
}

inline void *memprotect(void *ptr, uint_32 size) //Checks address of pointer!
{
	if (matchptr(ptr,0,size)) //Pointer matched?
	{
		return ptr; //Give the pointer!
	}
	return NULL; //Invalid!
}

inline uint_32 freemem() //Free memory left! We work!
{
	//dolog("zalloc","Detecting free memory...");
	uint_32 curalloc; //Current allocated memory!
	char *buffer;
	uint_32 multiplier; //The multiplier!
	curalloc = 0; //Reset at 1 bytes!
	multiplier = 100000000; //Start at max multiplier (100MB)!
	byte times = 9; //Times!
	times = 9; //Times 9 to start with!

	uint_32 lastzalloc = 0;
	allow_zallocfaillog = 0; //Don't allow!
	byte allocated = 0; //Allocated?
	while (1) //While not done...
	{
		lastzalloc = (curalloc+(multiplier*times)); //Last zalloc!
		allocated = 0; //Default: not allocated!
		buffer = (char *)zalloc(lastzalloc,"freememdetect"); //Try allocating, don't have to be cleared!
		if (buffer) //Allocated?
		{
			freez((void **)&buffer,lastzalloc,"Freemem@Cleanup"); //Release memory for next try!
			buffer = NULL; //Not allocated anymore!
			curalloc = lastzalloc; //Set detected memory!
			//dolog("zalloc","Free memory step: %i",curalloc); //Show our step! WE WORK!
			allocated = 1; //We're allocated!
		}
		if (!times || allocated) //Either nothing left or allocated?
		{
			multiplier /= 10; //Next digit!
			times = 9; //Reset times for next try!
		}
		else //Calculate next digit!
		{
			--times; //Next digit!
		}
		if (!multiplier) //Gotten an allocation and/or done?
		{
			break; //Stop searching: we're done!
		}
		//We're to continue!
	} //We have success!
	
	
	if (buffer) //Still allocated?
	{
		freez((void **)&buffer,lastzalloc,"Freemem@FinalCleanup"); //Still allocated=>release?
	}

	//dolog("zalloc","Free memory detected: %i bytes",curalloc);
	allow_zallocfaillog = 1; //Allow again!
	return curalloc; //Give free allocatable memory size!
}
Header:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#ifndef ZALLOC_H
#define ZALLOC_H

typedef void (*DEALLOCFUNC)(void **ptr, uint_32 size); //Deallocation functionality!

//Functionality for dynamic memory!
inline void initZalloc(); //Initialises the zalloc subsystem!
inline void *nzalloc(uint_32 size, char *name); //Allocates memory, NULL on failure (ran out of memory), protected allocation!
inline void *zalloc(uint_32 size, char *name); //Same as nzalloc, but clears the allocated memory!
inline void freez(void **ptr, uint_32 size, char *name); //Release memory allocated with zalloc!
inline void unregisterptrall(); //Free all allocated memory still allocated (on shutdown only, garbage collector)!
inline void freezall(); //Same as unregisterall

//Pointer derefenence protection!
inline void *memprotect(void *ptr, uint_32 size); //Checks address of pointer!

//Free memory available!
inline inline uint_32 freemem(); //Free memory left!

//Debugging functionality for finding memory leaks!
inline void logpointers(); //Logs any changes in memory usage!

//For stuff using external allocations:
inline int registerptr(void *ptr,uint_32 size, char *name, DEALLOCFUNC dealloc); //Register a pointer!
inline void unregisterptr(void *ptr, uint_32 size); //Remove pointer from registration (only if original pointer)?

#endif 
log.h
1
2
3
4
5
6
#ifndef LOG_H
#define LOG_H

void dolog(char *filename, char *format, ...); //Logging functionality!

#endif 
types.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
#ifndef TYPESEMU_H
#define TYPESEMU_H

#include <psptypes.h> //For long long etc. (u64 etc).
#include <stdlib.h>
#include <pspkernel.h>
#include <pspdebug.h>
#include <pspdebugkb.h> //Keyboard!
#include <stdint.h>
#include <pspdisplay.h>
#include <stdarg.h>
#include <string.h>
#include <pspctrl.h>
#include <psppower.h>
#include <ctype.h> //C type!
#include <stdlib.h>
#include <dirent.h>
#include <pspthreadman.h> //For threads!

//For speaker!
#include <pspaudiolib.h>
#include <math.h>
#include <limits.h>

//For timing!
#include <psprtc.h> //Real Time Clock!
#include <stdio.h>

#define EXIT_PRIORITY 0x11
//Exit priority, higest of all!

typedef uint64_t uint_64; //Take over using new name!
typedef int64_t int_64; //Take over using new name!
typedef uint32_t uint_32; //Take over using new name!
typedef int32_t int_32; //Take over using new name!
typedef unsigned char byte;
typedef unsigned short word;
typedef signed char sbyte; //Signed!
typedef signed short sword; //Signed!

#define TRUE 1
#define FALSE 0

#define printf pspDebugScreenPrintf
#define wherex pspDebugScreenGetX
#define wherey pspDebugScreenGetY
#define gotoxy pspDebugScreenSetXY
#define fontcolor pspDebugScreenSetTextColor
#define backcolor pspDebugScreenSetBackColor
//Real clearscreen:
#define realclrscr pspDebugScreenClear
#define delay sceKernelDelayThread
#define sleep sceKernelSleepThread
#define halt sceKernelExitGame
#define mkdir(dir) sceIoMkdir(dir,0777)

typedef s64 int64;
typedef u64 uint64;
typedef uint64 FILEPOS;

//64-bit file support (or not)!
/*#ifdef __FILE_SUPPORT_64
//64-bits wide file support!
#define fopen64 fopen64
#define fseek64 fseeko64
#define ftell64 ftello64
#define fread64 fread64
#define fwrite64 fwrite64
#define fclose64 fclose64
#else
*/
//32-bits wide file support!
#define fopen64 fopen64
#define fseek64 fseek64
#define ftell64 ftell64
#define fread64 fread64
#define fwrite64 fwrite64
#define fclose64 fclose64
//#endif

//RGB, with and without A (full)
#define RGB(r, g, b) ((r)|((g)<<8)|((b)<<16)|(0xFF<<24))
#define RGBA(r, g, b, a) ((r)|((g)<<8)|((b)<<16)|((a)<<24))
//Same, but reversed!
#define GETR(x) ((x)&0xFF)
#define GETG(x) (((x)>>8)&0xFF)
#define GETB(x) (((x)>>16)&0xFF)
#define GETA(x) (((x)>>24)&0xFF)

typedef int bool; //Booleans are ints!

typedef void (*Handler)(void);    /* A pointer to a handler function */

//Number of characters
#define DEBUGSCREEN_WIDTH 67
#define DEBUGSCREEN_HEIGHT 34

//Ammount of items in a buffer!
#define NUMITEMS(buffer) (sizeof(buffer)/sizeof(buffer[0]))
//Timeout for shutdown: force shutdown!
//When set to 0, shutdown immediately shuts down, ignoring the emulated machine!
#define SHUTDOWN_TIMEOUT 0


//Different kinds of pointers!

typedef struct
{
	union
	{
		struct
		{
			uint_32 offset; //Default: 0
			unsigned int segment; //Default: 0
		};
		unsigned char data[6]; //46-bits as bytes!
	};
} ptr48; //48-bit pointer Adress (32-bit mode)!

typedef struct
{
	union
	{
		struct
		{
			unsigned int offset; //Default: 0
			unsigned int segment; //Default: 0
		};
		unsigned char data[4]; //32-bits as bytes!
	};
} ptr32; //32-bit pointer Adress (16-bit mode)!

typedef struct
{
	union
	{
		struct
		{
			unsigned short limit; //Limit!
			unsigned int base; //Base!
		};
		unsigned char data[6]; //46-bit adress!
	};
} GDTR_PTR;

typedef struct
{
	union
	{
		struct
		{
			unsigned int limit;
			uint_32 base;
		};
		unsigned char data[6]; //46-bit adress!
	};
} IDTR_PTR;

//NULL pointer definition
#define NULLPTR(x) ((x.segment==0) && (x.offset==0))
//Same, but for pointer dereference
#define NULLPTR_PTR(x,location) (ANTINULL(x,location)?((x->segment==0) && (x->offset==0)):1)

#define NULLPROTECT(ptr) ANTINULL(ptr,constsprintf("%s at %i",__FILE__,__LINE__))

//MIN/MAX: East calculation of min/max data!
#define MIN(a,b) ((a<b)?a:b)
#define MAX(a,b) ((a>b)?a:b)


//Optimized DIV/MUL when possible.
//SAFEDIV/MOD: Safe divide/modulo function. Divide by 0 is caught into becoming 0!
#define SAFEDIVUINT(x,divideby) ((!divideby)?0:OPTDIV(x,divideby))
#define SAFEMODUINT(x,divideby) ((!divideby)?0:OPTMOD(x,divideby))
#define SAFEDIVUINT32(x,divideby) ((!divideby)?0:OPTDIV32(x,divideby))
#define SAFEMODUINT32(x,divideby) ((!divideby)?0:OPTMOD32(x,divideby))
#define SAFEDIV(x,divideby) ((!divideby)?0:(x/divideby))
#define SAFEMOD(x,divideby) ((!divideby)?0:(x%divideby))

//Bit manipulation!
//Turn multiple bits on!
#define BITON(x,bit) ((x)|(bit))
//Turn multiple bits off!
#define BITOFF(x,bit) ((x)&(~(bit)))

//Get a bit value (0 or 1))
#define GETBIT(x,bitnr) (((x)>>(bitnr))&1)

//Set a bit on!
#define SETBIT1(x,bitnr) BITON((x),(1<<(bitnr)))
//Set a bit off!
#define SETBIT0(x,bitnr) BITOFF((x),(1<<(bitnr)))

//Easy rotating!
#define ror(x,moves) ((x >> moves) | (x << (sizeof(x)*8 - moves)))
#define rol(x,moves) ((x << moves) | (x >> (sizeof(x)*8 - moves)))


//Emulator itself:
#define VIDEOMODE_EMU 0x02
//For boot process!
#define VIDEOMODE_BOOT 0x02

//GPU debugging:
//Row with info about the CPU etc.
#define GPU_TEXT_INFOROW 3
//Row with the current CPU ASM command.
#define GPU_TEXT_DEBUGGERROW 4

void BREAKPOINT(); //Safe breakpoint function!

int convertrel(int src, int fromres, int tores); //Relative convert!
uint_32 safe_strlen(char *str); //Safe safe_strlen function!
char *constsprintf(char *str1, ...); //Concatinate strings (or constants)!
void *ANTINULL(void *ptr, char *location); //ANTI NULL Dereference!

void EMU_Shutdown(int doshutdown); //Shut down the emulator?
void addtimer(float frequency, Handler timer, char *name); //Add a timer!
void removetimer(char *name); //Removes a timer!
void startTimers(); //Start timers!
void stopTimers(); //Stop timers!
void raiseError(char *source, char *text, ...); //Raises an error!
void printmsg(byte attribute, char *text, ...); //Prints a message to the screen!
void delete_file(char *filename); //Delete one or more files!
int file_exists(char *filename); //File exists?
byte emu_use_profiler(); //To use the profiler?
unsigned int OPTDIV(unsigned int val, unsigned int division);
unsigned int OPTMOD(unsigned int val, unsigned int division);
unsigned int OPTMUL(unsigned int val, unsigned int multiplication);
uint_32 OPTDIV32(uint_32 val, uint_32 division);
uint_32 OPTMOD32(uint_32 val, uint_32 division);
uint_32 OPTMUL32(uint_32 val, uint_32 multiplication);

void debugrow(char *text); //Log a row to debugrow log!

void speakerOut(word frequency); //Set the PC speaker to a sound or 0 for none!

#include "headers/fopen64.h" //64-bit fopen support!
#endif 
Dear god. You want us to read several hundred lines of C-style code and tell you where any problems are? You realize that professionals get paid good money to do this and it takes weeks or more, and they still don't catch everything?

Why is this so complex in the first place? What is your original goal?
It looks like your code is just wrapping around malloc/free. So what functionality does this provide that malloc/free doesn't already provide?
571 lines, plus the code can't decide whether it's C or C++. If you want everything initialized to 0 in C code, just use calloc. Why reinvent the wheel?
It's plain C. My compiler (pspsdk) somehow won't recognise any c++ statements, although it's supposed to be a c/c++ compiler.

- initZalloc initialises the library for usage.
- nzalloc allocates memory using malloc and registers it through registerptr for checking for boundary and invalid deallocations/freezall.
- zalloc calls nzalloc and clears the memory (effectively calloc combined with the above nzalloc protection).
- freez releases allocated memory, and sets the specified pointer to NULL when deallocated. Also checks for invalid pointers.
- unregisterptrall releases all registered pointer memory, if any are available for deallocation.
- memprotect verifies a specified pointer for dereferencing it. You specify the pointer to the memory you want to look at, and the size of the block you want to dereference. It will return the object if valid, NULL if invalid.
- freemem uses nzalloc to check how much memory is available.
- logpointers logs all registered pointers and extra information to a filename (zalloc.log) using an external dolog function.

Further there's some functions for external allocation routines (like stuff generated by SDL etc.)
- registerptr: Registers a pointer which has been allocated.
- unregisterptr: Unregisters a pointer which has been allocated with registerptr. It will only unregister if the pointer if fully matched internally with one of the registered pointers. Also the deallocation function must be non-NULL, which allows for some allocations to be permanently allocated (like the SDL_Surface allocated by the SDL_SetVideoMode, simply set registerptr parameter dealloc=NULL).

I made this because I was having problems with simple malloc/calloc and free functions (crashing my software). This way I can fully log any pointers allocated at any time and see if there are any memory holes etc.

BTW it's 289 lines (only the first 2 are the code, the others are just headers for the rest of the application to use, basic typedefs etc.).
Last edited on
Nothing like reinventing the whell:
http://dmalloc.com/
superfury wrote:
It's plain C. My compiler (pspsdk) somehow won't recognise any c++ statements, although it's supposed to be a c/c++ compiler.
Do your source code filenames end in .cpp or .cxx? You may want to get a newer/better compiler/IDE.
So basically what you're saying is that you're using C code (which you don't fully understand) to write a wrapper around a memory allocator (which refuses to work properly) in a compiler that you have evidence claims it does more than it actually does.

I really think you should be looking somewhere other than writing a brand-new library for this. Perhaps some studying on:
1) How to use malloc/calloc properly.
2) Where to find a compiler that's not blowing smoke. <-- This one may, in fact, solve all of your problems.
@LB: My source code files all end in .c, not in .cpp. Is this a problem? (Does the compiler make a difference between those? Do I need to adjust my makefiles for that?)
A .c file will not be read by a C++ compiler as a C++ file, so yeah...that might be an issue you'll want to correct.
If you use modern C++ practices such as using the smart pointer wrapper classes and never using malloc/free/new/delete, your crashes and pointer/memory problems should go away.
Topic archived. No new replies allowed.