/*
Copyright (C) 1991, Marcus J. Ranum. All rights reserved.
*/
#ifdef WANT_ANSI
#ifdef __STDC__
#include <stdlib.h>
#endif
#endif
#include "udb_defs.h"
/*
routines that handle copying stuff in memory, and other main
memory allocation shenanigans.
*/
/*
#define ALLOC_DEBUG
*/
/*
temporary data is managed by keeping a list of allocated stuff, which
can be traversed and freed. this is not too terribly efficient, but
is not a load-bearing section of code.
*/
struct tmplist {
struct tmplist *next;
mall_t dat;
};
/* list of currently active temporaries */
static struct tmplist *tmpl;
/* list of temp list structures that have been freed and stacked */
static struct tmplist *freetmpl;
/* just like malloc() but keep track of the storage */
mall_t
tmpalloc(siz)
int siz;
{
struct tmplist *lp;
if(freetmpl != (struct tmplist *)0) {
lp = freetmpl;
#ifdef ALLOC_DEBUG
printf("take holder %d from tmp holder list\n",lp);
#endif
freetmpl = freetmpl->next;
} else {
if((lp = (struct tmplist *)malloc(sizeof(struct tmplist))) == 0)
return(0);
}
lp->dat = (mall_t) malloc((unsigned)siz);
/* add to the chain */
lp->next = tmpl;
tmpl = lp;
#ifdef ALLOC_DEBUG
printf("tmpalloc %d bytes at %d (holder is %d)\n",siz,lp->dat,lp);
#endif
return(lp->dat);
}
/*
put something on the temp list to free later.
this results in what is basically a deferred free() - executed
at the end of each machine run.
*/
void
deferfree(p)
mall_t p;
{
struct tmplist *lp;
if(freetmpl != (struct tmplist *)0) {
lp = freetmpl;
#ifdef ALLOC_DEBUG
printf("take holder %d from tmp holder list\n",lp);
#endif
freetmpl = freetmpl->next;
} else {
if((lp = (struct tmplist *)malloc(sizeof(struct tmplist))) == 0) {
#ifdef ALLOC_DEBUG
printf("deferfree can't allocate holder, leaks memory\n");
#endif
return;
}
}
lp->dat = p;
lp->next = tmpl;
tmpl = lp;
#ifdef ALLOC_DEBUG
printf("tmpputonfree ? bytes at %d (holder is %d)\n",lp->dat,lp);
#endif
}
/* free all the temporaries */
void
tmp_sync()
{
register struct tmplist *lp = tmpl;
register struct tmplist *np;
if(tmpl == (struct tmplist *)0)
return;
while(lp != (struct tmplist *)0) {
if(lp->dat != 0)
(void)free(lp->dat);
#ifdef ALLOC_DEBUG
printf("tmpsync at %d (holder is %d)\n",lp->dat,lp);
#endif
np = lp->next;
lp->next = freetmpl;
freetmpl = lp;
#ifdef ALLOC_DEBUG
printf("stack holder %d on tmp holder list\n",lp);
#endif
lp = np;
}
tmpl = (struct tmplist *)0;
}