diff options
author | Bardur Arantsson <bardur@scientician.net> | 2010-01-08 20:28:34 +0100 |
---|---|---|
committer | Bardur Arantsson <bardur@scientician.net> | 2010-01-08 23:46:06 +0100 |
commit | 6aa48afdd57d03314fdf4be6c9da911c32277c84 (patch) | |
tree | 2dc401f9aae2dc6736d2fc3811c8f8099d3eabe6 /src/z-virt.c |
Import tome-2.3.5.
Diffstat (limited to 'src/z-virt.c')
-rw-r--r-- | src/z-virt.c | 187 |
1 files changed, 187 insertions, 0 deletions
diff --git a/src/z-virt.c b/src/z-virt.c new file mode 100644 index 00000000..c9277166 --- /dev/null +++ b/src/z-virt.c @@ -0,0 +1,187 @@ +/* File: z-virt.c */ + +/* + * Copyright (c) 1997 Ben Harrison + * + * This software may be copied and distributed for educational, research, + * and not for profit purposes provided that this copyright and statement + * are included in all such copies. + */ + +/* Purpose: Memory management routines -BEN- */ + +#include "z-virt.h" + +#include "z-util.h" + + +/* + * Allow debugging messages to track memory usage. + */ +#ifdef VERBOSE_RALLOC +static long virt_make = 0; +static long virt_kill = 0; +static long virt_size = 0; +#endif + + +/* + * Optional auxiliary "rnfree" function + */ +vptr (*rnfree_aux)(vptr, huge) = NULL; + +/* + * Free some memory (allocated by ralloc), return NULL + */ +vptr rnfree(vptr p, huge len) +{ + /* Easy to free zero bytes */ + if (len == 0) return (NULL); + +#ifdef VERBOSE_RALLOC + + /* Decrease memory count */ + virt_kill += len; + + /* Message */ + if (len > virt_size) + { + char buf[80]; + sprintf(buf, "Kill (%ld): %ld - %ld = %ld.", + len, virt_make, virt_kill, virt_make - virt_kill); + plog(buf); + } + +#endif + + /* Use the "aux" function */ + if (rnfree_aux) return ((*rnfree_aux)(p, len)); + + /* Use "free" */ + free ((char*)(p)); + + /* Done */ + return (NULL); +} + + +/* + * Optional auxiliary "rpanic" function + */ +vptr (*rpanic_aux)(huge) = NULL; + +/* + * The system is out of memory, so panic. If "rpanic_aux" is set, + * it can be used to free up some memory and do a new "ralloc()", + * or if not, it can be used to save things, clean up, and exit. + * By default, this function simply crashes the computer. + */ +vptr rpanic(huge len) +{ + /* Hopefully, we have a real "panic" function */ + if (rpanic_aux) return ((*rpanic_aux)(len)); + + /* Attempt to crash before icky things happen */ + core("Out of Memory!"); + + /* Paranoia */ + return ((vptr)(NULL)); +} + + +/* + * Optional auxiliary "ralloc" function + */ +vptr (*ralloc_aux)(huge) = NULL; + + +/* + * Allocate some memory + */ +vptr ralloc(huge len) +{ + vptr mem; + + /* Allow allocation of "zero bytes" */ + if (len == 0) return ((vptr)(NULL)); + +#ifdef VERBOSE_RALLOC + + /* Count allocated memory */ + virt_make += len; + + /* Log important allocations */ + if (len > virt_size) + { + char buf[80]; + sprintf(buf, "Make (%ld): %ld - %ld = %ld.", + len, virt_make, virt_kill, virt_make - virt_kill); + plog(buf); + } + +#endif + + /* Use the aux function if set */ + if (ralloc_aux) mem = (*ralloc_aux)(len); + + /* Use malloc() to allocate some memory */ + else mem = ((vptr)(malloc((size_t)(len)))); + + /* We were able to acquire memory */ + if (!mem) mem = rpanic(len); + + /* Return the memory, if any */ + return (mem); +} + + + + +/* + * Allocate a constant string, containing the same thing as 'str' + */ +cptr string_make(cptr str) +{ + huge len = 0; + cptr t = str; + char *s, *res; + + /* Simple sillyness */ + if (!str) return (str); + + /* Get the number of chars in the string, including terminator */ + while (str[len++]) /* loop */; + + /* Allocate space for the string */ + s = res = (char*)(ralloc(len)); + + /* Copy the string (with terminator) */ + while ((*s++ = *t++) != 0) /* loop */; + + /* Return the allocated, initialized, string */ + return (res); +} + + +/* + * Un-allocate a string allocated above. + * Depends on no changes being made to the string. + */ +errr string_free(cptr str) +{ + huge len = 0; + + /* Succeed on non-strings */ + if (!str) return (0); + + /* Count the number of chars in 'str' plus the terminator */ + while (str[len++]) /* loop */; + + /* Kill the buffer of chars we must have allocated above */ + rnfree((vptr)(str), len); + + /* Success */ + return (0); +} + + |