/*******************************************************************************
*
* McStas, neutron ray-tracing package
* Copyright 1997-2002, All rights reserved
* Risoe National Laboratory, Roskilde, Denmark
* Institut Laue Langevin, Grenoble, France
*
* Kernel: memory.c
*
* %Identification
* Written by: K.N.
* Date: Jul 1, 1997
* Origin: Risoe
* Release: McStas 1.6
* Version: 1.9
*
* Memory management functions.
*
* $Id: memory.c,v 1.18 2004/09/21 12:23:50 farhi Exp $
*
*******************************************************************************/
#include <string.h>
#include <stdlib.h>
#include <stdarg.h>
#include <ctype.h>
#include <stdio.h>
#include "mcstas.h"
/*******************************************************************************
* Allocate memory. This function never returns NULL; instead, the
* program is aborted if insufficient memory is available.
*******************************************************************************/
void *
mem(size_t size)
{
void *p = calloc(1, size); /* Allocate and clear memory. */
if(p == NULL)
fatal_error("memory exhausted during allocation of size %d.", size);
return p;
}
/*******************************************************************************
* Free memory allocated with mem().
*******************************************************************************/
void memfree(void *p)
{
if(p == NULL)
debug(("memfree(): freeing NULL memory.\n"));
else
free(p);
}
/*******************************************************************************
* Allocate a new copy of a string.
*******************************************************************************/
char *
str_dup(char *string)
{
char *s;
s = mem(strlen(string) + 1);
strcpy(s, string);
return s;
}
/*******************************************************************************
* Allocate a new copy of initial N chars in a string.
*******************************************************************************/
char *
str_dup_n(char *string, int n)
{
char *s;
s = mem(n + 1);
strncpy(s, string, n);
s[n] = '\0';
return s;
}
/*******************************************************************************
* Allocate a new string to hold the concatenation of given strings. Arguments
* are the strings to concatenate, terminated by NULL.
*******************************************************************************/
char *
str_cat(char *first, ...)
{
char *s;
va_list ap;
int size;
char *arg;
size = 1; /* Count final '\0'. */
va_start(ap, first);
for(arg = first; arg != NULL; arg = va_arg(ap, char *))
size += strlen(arg); /* Calculate string size. */
va_end(ap);
s = mem(size);
size = 0;
va_start(ap, first);
for(arg = first; arg != NULL; arg = va_arg(ap, char *))
{
strcpy(&(s[size]), arg);
size += strlen(arg);
}
va_end(ap);
return s;
}
/*******************************************************************************
* Allocate a new string holding the result of quoting the input string. The
* result is suitable for inclusion in C source code.
*******************************************************************************/
char *
str_quote(char *string)
{
char *badchars = "\\\"\r\n\t";
char *quotechars = "\\\"rnt";
char *q, *res, *ptr;
int len, pass;
int c;
char new[5];
/* Loop over the string twice, first counting chars and afterwards copying
them into an allocated buffer. */
for(pass = 0; pass < 2; pass++)
{
char *p = string;
if(pass == 0)
len = 0; /* Prepare to compute length */
else
q = res = mem(len + 1); /* Allocate buffer */
/* Notice the cast to unsigned char; without it, the isprint(c) below will
fail for characters with negative plain char values. */
while((c = (unsigned char)(*p++)))
{
ptr = strchr(badchars, c);
if(ptr != NULL)
sprintf(new, "\\%c", quotechars[ptr - badchars]);
else if(isprint(c))
sprintf(new, "%c", c);
else
sprintf(new, "\\%03o", c);
if(pass == 0)
len += strlen(new); /* Count in length */
else
for(ptr = new; (*q = *ptr) != 0; ptr++)
q++; /* Copy over chars */
}
}
return res;
}
/*******************************************************************************
* Free memory for a string.
*******************************************************************************/
void
str_free(char *string)
{
memfree(string);
}
#ifdef MCSTAS_H
struct Pool_header
{
List list;
};
/*******************************************************************************
* Create a pool in which to allocate memory that may be easily freed all at a
* time by freeing the pool.
*******************************************************************************/
Pool
pool_create(void)
{
Pool p;
palloc(p);
p->list = list_create();
return p;
}
/*******************************************************************************
* Deallocate a pool as well as all memory allocated within it.
*******************************************************************************/
void
pool_free(Pool p)
{
List_handle liter;
void *mem;
liter = list_iterate(p->list);
while(mem = list_next(liter))
{
memfree(mem);
}
list_iterate_end(liter);
memfree(p);
}
/*******************************************************************************
* Allocate memory in a pool.
*******************************************************************************/
void *
pool_mem(Pool p, size_t size)
{
void *m = mem(size);
list_add(p->list, m);
return m;
}
#endif /* MCSTAS_H */
syntax highlighted by Code2HTML, v. 0.9.1