zalloc_malloc.c revision 39672
1/* 2 * This module derived from code donated to the FreeBSD Project by 3 * Matthew Dillon <dillon@backplane.com> 4 * 5 * Copyright (c) 1998 The FreeBSD Project 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27 * SUCH DAMAGE. 28 * 29 * $Id: zalloc_malloc.c,v 1.1 1998/09/26 01:42:39 msmith Exp $ 30 */ 31 32/* 33 * MALLOC.C - malloc equivalent, runs on top of zalloc and uses sbrk 34 */ 35 36#include "zalloc_defs.h" 37 38static MemPool MallocPool = INITPOOL("malloc", panic, znot); 39 40#ifdef DMALLOCDEBUG 41static int MallocMax; 42static int MallocCount; 43 44void mallocstats(void); 45#endif 46 47#ifdef malloc 48#undef malloc 49#undef free 50#endif 51 52void * 53malloc(size_t bytes) 54{ 55 Guard *res; 56 57#ifdef USEENDGUARD 58 bytes += MALLOCALIGN + 1; 59#else 60 bytes += MALLOCALIGN; 61#endif 62 63 while ((res = znalloc(&MallocPool, bytes)) == NULL) { 64 int incr = (bytes + BLKEXTENDMASK) & ~BLKEXTENDMASK; 65 char *base; 66 67 if ((base = sbrk(incr)) == (char *)-1) 68 return(NULL); 69 zextendPool(&MallocPool, base, incr); 70 zfree(&MallocPool, base, incr); 71 } 72#ifdef DMALLOCDEBUG 73 if (++MallocCount > MallocMax) 74 MallocMax = MallocCount; 75#endif 76#ifdef USEGUARD 77 res->ga_Magic = GAMAGIC; 78#endif 79 res->ga_Bytes = bytes; 80#ifdef USEENDGUARD 81 *((char *)res + bytes - 1) = -2; 82#endif 83 return((char *)res + MALLOCALIGN); 84} 85 86void 87free(void *ptr) 88{ 89 size_t bytes; 90 91 if (ptr != NULL) { 92 Guard *res = (void *)((char *)ptr - MALLOCALIGN); 93 94#ifdef USEGUARD 95 if (res->ga_Magic != GAMAGIC) { 96#ifdef USEPANIC 97 panic("free(): guard1 fail @ %08lx\n", ptr); 98#else 99 *(char *)0 = 1; 100#endif 101 } 102 res->ga_Magic = -1; 103#endif 104#ifdef USEENDGUARD 105 if (*((char *)res + res->ga_Bytes - 1) != -2) { 106#ifdef USEPANIC 107 panic("free(): guard2 fail @ %08lx + %d\n", ptr, res->ga_Bytes - MALLOCALIGN); 108#else 109 *(char *)0 = 1; 110#endif 111 } 112 *((char *)res + res->ga_Bytes - 1) = -1; 113#endif 114 115 bytes = res->ga_Bytes; 116 zfree(&MallocPool, res, bytes); 117#ifdef DMALLOCDEBUG 118 --MallocCount; 119#endif 120 } 121} 122 123 124void * 125calloc(size_t n1, size_t n2) 126{ 127 iaddr_t bytes = (iaddr_t)n1 * (iaddr_t)n2; 128 void *res; 129 130 if ((res = malloc(bytes)) != NULL) { 131 bzero(res, bytes); 132#ifdef DMALLOCDEBUG 133 if (++MallocCount > MallocMax) 134 MallocMax = MallocCount; 135#endif 136 } 137 return(res); 138} 139 140/* 141 * realloc() - I could be fancier here and free the old buffer before 142 * allocating the new one (saving potential fragmentation 143 * and potential buffer copies). But I don't bother. 144 */ 145 146void * 147realloc(void *ptr, size_t size) 148{ 149 void *res; 150 size_t old; 151 152 if ((res = malloc(size)) != NULL) { 153 if (ptr) { 154 old = *(size_t *)((char *)ptr - MALLOCALIGN) - MALLOCALIGN; 155 if (old < size) 156 bcopy(ptr, res, old); 157 else 158 bcopy(ptr, res, size); 159 free(ptr); 160 } else { 161#ifdef DMALLOCDEBUG 162 if (++MallocCount > MallocMax) 163 MallocMax = MallocCount; 164#ifdef EXITSTATS 165 if (DidAtExit == 0) { 166 DidAtExit = 1; 167 atexit(mallocstats); 168 } 169#endif 170#endif 171 } 172 } 173 return(res); 174} 175 176void * 177reallocf(void *ptr, size_t size) 178{ 179 void *res; 180 181 if ((res = realloc(ptr, size)) == NULL) 182 free(ptr); 183 return(res); 184} 185 186#ifdef DMALLOCDEBUG 187 188void 189mallocstats(void) 190{ 191 printf("Active Allocations: %d/%d\n", MallocCount, MallocMax); 192#ifdef ZALLOCDEBUG 193 zallocstats(&MallocPool); 194#endif 195} 196 197#endif 198 199