14887Schin /*********************************************************************** 24887Schin * * 34887Schin * This software is part of the ast package * 4*8462SApril.Chin@Sun.COM * Copyright (c) 1985-2008 AT&T Intellectual Property * 54887Schin * and is licensed under the * 64887Schin * Common Public License, Version 1.0 * 7*8462SApril.Chin@Sun.COM * by AT&T Intellectual Property * 84887Schin * * 94887Schin * A copy of the License is available at * 104887Schin * http://www.opensource.org/licenses/cpl1.0.txt * 114887Schin * (with md5 checksum 059e8cd6165cb4c31e351f2b69388fd9) * 124887Schin * * 134887Schin * Information and Software Systems Research * 144887Schin * AT&T Research * 154887Schin * Florham Park NJ * 164887Schin * * 174887Schin * Glenn Fowler <gsf@research.att.com> * 184887Schin * David Korn <dgk@research.att.com> * 194887Schin * Phong Vo <kpv@research.att.com> * 204887Schin * * 214887Schin ***********************************************************************/ 224887Schin #if defined(_UWIN) && defined(_BLD_ast) 234887Schin 244887Schin void _STUB_malloc(){} 254887Schin 264887Schin #else 274887Schin 284887Schin #if _UWIN 294887Schin 304887Schin #define calloc ______calloc 314887Schin #define _ast_free ______free 324887Schin #define malloc ______malloc 334887Schin #define mallinfo ______mallinfo 344887Schin #define mallopt ______mallopt 354887Schin #define mstats ______mstats 364887Schin #define realloc ______realloc 374887Schin 384887Schin #define _STDLIB_H_ 1 394887Schin 404887Schin extern int atexit(void(*)(void)); 414887Schin extern char* getenv(const char*); 424887Schin 434887Schin #endif 444887Schin 454887Schin #include "vmhdr.h" 464887Schin 474887Schin #if _UWIN 484887Schin 494887Schin #include <malloc.h> 504887Schin 514887Schin #define _map_malloc 1 524887Schin #define _mal_alloca 1 534887Schin 544887Schin #undef calloc 554887Schin #define calloc _ast_calloc 564887Schin #undef _ast_free 574887Schin #define free _ast_free 584887Schin #undef malloc 594887Schin #define malloc _ast_malloc 604887Schin #undef mallinfo 614887Schin typedef struct ______mallinfo Mallinfo_t; 624887Schin #undef mallopt 634887Schin #undef mstats 644887Schin typedef struct ______mstats Mstats_t; 654887Schin #undef realloc 664887Schin #define realloc _ast_realloc 674887Schin 684887Schin #endif 694887Schin 704887Schin #if __STD_C 714887Schin #define F0(f,t0) f(t0) 724887Schin #define F1(f,t1,a1) f(t1 a1) 734887Schin #define F2(f,t1,a1,t2,a2) f(t1 a1, t2 a2) 744887Schin #else 754887Schin #define F0(f,t0) f() 764887Schin #define F1(f,t1,a1) f(a1) t1 a1; 774887Schin #define F2(f,t1,a1,t2,a2) f(a1, a2) t1 a1; t2 a2; 784887Schin #endif 794887Schin 804887Schin /* 814887Schin * define _AST_std_malloc=1 to force the standard malloc 824887Schin * if _map_malloc is also defined then _ast_malloc etc. 834887Schin * will simply call malloc etc. 844887Schin */ 854887Schin 864887Schin #if !defined(_AST_std_malloc) && __CYGWIN__ 874887Schin #define _AST_std_malloc 1 884887Schin #endif 894887Schin 904887Schin #if ( !_std_malloc || !_BLD_ast ) && !_AST_std_malloc 914887Schin 924887Schin /* malloc compatibility functions. 934887Schin ** These are aware of debugging/profiling and driven by the environment variables: 944887Schin ** VMETHOD: select an allocation method by name. 954887Schin ** 964887Schin ** VMPROFILE: if is a file name, write profile data to it. 974887Schin ** VMTRACE: if is a file name, write trace data to it. 984887Schin ** The pattern %p in a file name will be replaced by the process ID. 994887Schin ** 1004887Schin ** VMDEBUG: 1014887Schin ** a: abort on any warning. 1024887Schin ** w[decimal]: file descriptor for warnings. 1034887Schin ** [decimal]: period to check arena. 1044887Schin ** 0x[hexadecimal]: address to watch. 1054887Schin ** 1064887Schin ** Written by Kiem-Phong Vo, kpv@research.att.com, 01/16/94. 1074887Schin */ 1084887Schin 1094887Schin #if _sys_stat 1104887Schin #include <sys/stat.h> 1114887Schin #endif 1124887Schin #include <fcntl.h> 1134887Schin 1144887Schin #ifdef S_IRUSR 1154887Schin #define CREAT_MODE (S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH) 1164887Schin #else 1174887Schin #define CREAT_MODE 0644 1184887Schin #endif 1194887Schin 1204887Schin #if !_map_malloc 1214887Schin #undef calloc 1224887Schin #undef cfree 1234887Schin #undef free 1244887Schin #undef mallinfo 1254887Schin #undef malloc 1264887Schin #undef mallopt 1274887Schin #undef memalign 1284887Schin #undef mstats 1294887Schin #undef realloc 1304887Schin #undef valloc 1314887Schin #endif 1324887Schin 1334887Schin #if _WINIX 1344887Schin 1354887Schin #include <ast_windows.h> 1364887Schin 1374887Schin #if _UWIN 1384887Schin 1394887Schin #define VMRECORD(p) _vmrecord(p) 1404887Schin #define VMBLOCK { int _vmblock = _sigblock(); 1414887Schin #define VMUNBLOCK _sigunblock(_vmblock); } 1424887Schin 1434887Schin extern int _sigblock(void); 1444887Schin extern void _sigunblock(int); 1454887Schin extern unsigned long _record[2048]; 1464887Schin 1474887Schin __inline Void_t* _vmrecord(Void_t* p) 1484887Schin { 1494887Schin register unsigned long v = ((unsigned long)p)>>16; 1504887Schin 1514887Schin _record[v>>5] |= 1<<((v&0x1f)); 1524887Schin return p; 1534887Schin } 1544887Schin 1554887Schin #else 1564887Schin 1574887Schin #define getenv(s) lcl_getenv(s) 1584887Schin 1594887Schin static char* 1604887Schin lcl_getenv(const char* s) 1614887Schin { 1624887Schin int n; 1634887Schin static char buf[512]; 1644887Schin 1654887Schin if (!(n = GetEnvironmentVariable(s, buf, sizeof(buf))) || n > sizeof(buf)) 1664887Schin return 0; 1674887Schin return buf; 1684887Schin } 1694887Schin 1704887Schin #endif /* _UWIN */ 1714887Schin 1724887Schin #endif /* _WINIX */ 1734887Schin 1744887Schin #ifndef VMRECORD 1754887Schin #define VMRECORD(p) (p) 1764887Schin #define VMBLOCK 1774887Schin #define VMUNBLOCK 1784887Schin #endif 1794887Schin 1804887Schin #if defined(__EXPORT__) 1814887Schin #define extern extern __EXPORT__ 1824887Schin #endif 1834887Schin 1844887Schin #if __STD_C 1854887Schin static Vmulong_t atou(char** sp) 1864887Schin #else 1874887Schin static Vmulong_t atou(sp) 1884887Schin char** sp; 1894887Schin #endif 1904887Schin { 1914887Schin char* s = *sp; 1924887Schin Vmulong_t v = 0; 1934887Schin 1944887Schin if(s[0] == '0' && (s[1] == 'x' || s[1] == 'X') ) 1954887Schin { for(s += 2; *s; ++s) 1964887Schin { if(*s >= '0' && *s <= '9') 1974887Schin v = (v << 4) + (*s - '0'); 1984887Schin else if(*s >= 'a' && *s <= 'f') 1994887Schin v = (v << 4) + (*s - 'a') + 10; 2004887Schin else if(*s >= 'A' && *s <= 'F') 2014887Schin v = (v << 4) + (*s - 'A') + 10; 2024887Schin else break; 2034887Schin } 2044887Schin } 2054887Schin else 2064887Schin { for(; *s; ++s) 2074887Schin { if(*s >= '0' && *s <= '9') 2084887Schin v = v*10 + (*s - '0'); 2094887Schin else break; 2104887Schin } 2114887Schin } 2124887Schin 2134887Schin *sp = s; 2144887Schin return v; 2154887Schin } 2164887Schin 2174887Schin static int _Vmflinit = 0; 2184887Schin static Vmulong_t _Vmdbstart = 0; 2194887Schin static Vmulong_t _Vmdbcheck = 0; 2204887Schin static Vmulong_t _Vmdbtime = 0; 2214887Schin static int _Vmpffd = -1; 2224887Schin #define VMFLINIT() \ 2234887Schin { if(!_Vmflinit) vmflinit(); \ 2244887Schin if(_Vmdbcheck) \ 2254887Schin { if(_Vmdbtime < _Vmdbstart) _Vmdbtime += 1; \ 2264887Schin else if((_Vmdbtime += 1) < _Vmdbstart) _Vmdbtime = _Vmdbstart; \ 2274887Schin if(_Vmdbtime >= _Vmdbstart && (_Vmdbtime % _Vmdbcheck) == 0 && \ 2284887Schin Vmregion->meth.meth == VM_MTDEBUG) \ 2294887Schin vmdbcheck(Vmregion); \ 2304887Schin } \ 2314887Schin } 2324887Schin 2334887Schin #if __STD_C 2344887Schin static char* insertpid(char* begs, char* ends) 2354887Schin #else 2364887Schin static char* insertpid(begs,ends) 2374887Schin char* begs; 2384887Schin char* ends; 2394887Schin #endif 2404887Schin { int pid; 2414887Schin char* s; 2424887Schin 2434887Schin if((pid = getpid()) < 0) 2444887Schin return NIL(char*); 2454887Schin 2464887Schin s = ends; 2474887Schin do 2484887Schin { if(s == begs) 2494887Schin return NIL(char*); 2504887Schin *--s = '0' + pid%10; 2514887Schin } while((pid /= 10) > 0); 2524887Schin while(s < ends) 2534887Schin *begs++ = *s++; 2544887Schin 2554887Schin return begs; 2564887Schin } 2574887Schin 2584887Schin #if __STD_C 2594887Schin static int createfile(char* file) 2604887Schin #else 2614887Schin static int createfile(file) 2624887Schin char* file; 2634887Schin #endif 2644887Schin { 2654887Schin char buf[1024]; 2664887Schin char *next, *endb; 2674887Schin 2684887Schin next = buf; 2694887Schin endb = buf + sizeof(buf); 2704887Schin while(*file) 2714887Schin { if(*file == '%') 2724887Schin { switch(file[1]) 2734887Schin { 2744887Schin case 'p' : 2754887Schin if(!(next = insertpid(next,endb)) ) 2764887Schin return -1; 2774887Schin file += 2; 2784887Schin break; 2794887Schin default : 2804887Schin goto copy; 2814887Schin } 2824887Schin } 2834887Schin else 2844887Schin { copy: 2854887Schin *next++ = *file++; 2864887Schin } 2874887Schin 2884887Schin if(next >= endb) 2894887Schin return -1; 2904887Schin } 2914887Schin 2924887Schin *next = '\0'; 2934887Schin #if _PACKAGE_ast 2944887Schin { int fd; 2954887Schin fd = open(buf,O_WRONLY|O_CREAT|O_TRUNC,CREAT_MODE); 2964887Schin #ifdef FD_CLOEXEC 2974887Schin if (fd >= 0) 2984887Schin fcntl(fd, F_SETFD, FD_CLOEXEC); 2994887Schin #endif 3004887Schin return fd; 3014887Schin } 3024887Schin #else 3034887Schin return creat(buf,CREAT_MODE); 3044887Schin #endif 3054887Schin } 3064887Schin 3074887Schin #if __STD_C 3084887Schin static void pfprint(void) 3094887Schin #else 3104887Schin static void pfprint() 3114887Schin #endif 3124887Schin { 3134887Schin if(Vmregion->meth.meth == VM_MTPROFILE) 3144887Schin vmprofile(Vmregion,_Vmpffd); 3154887Schin } 3164887Schin 3174887Schin #if __STD_C 3184887Schin static int vmflinit(void) 3194887Schin #else 3204887Schin static int vmflinit() 3214887Schin #endif 3224887Schin { 3234887Schin char* env; 3244887Schin Vmalloc_t* vm; 3254887Schin int fd; 3264887Schin Vmulong_t addr; 3274887Schin char* file; 3284887Schin int line; 3294887Schin Void_t* func; 3304887Schin 3314887Schin /* this must be done now to avoid any inadvertent recursion (more below) */ 3324887Schin _Vmflinit = 1; 3334887Schin VMFLF(Vmregion,file,line,func); 3344887Schin 3354887Schin /* if getenv() calls malloc(), the eventual region may not see this */ 3364887Schin vm = NIL(Vmalloc_t*); 3374887Schin if((env = getenv("VMETHOD")) ) 3384887Schin { if(strcmp(env,"Vmdebug") == 0 || strcmp(env,"vmdebug") == 0) 3394887Schin vm = vmopen(Vmdcsbrk,Vmdebug,0); 3404887Schin else if(strcmp(env,"Vmprofile") == 0 || strcmp(env,"vmprofile") == 0 ) 3414887Schin vm = vmopen(Vmdcsbrk,Vmprofile,0); 3424887Schin else if(strcmp(env,"Vmlast") == 0 || strcmp(env,"vmlast") == 0 ) 3434887Schin vm = vmopen(Vmdcsbrk,Vmlast,0); 3444887Schin else if(strcmp(env,"Vmbest") == 0 || strcmp(env,"vmbest") == 0 ) 3454887Schin vm = Vmheap; 3464887Schin } 3474887Schin 3484887Schin if((!vm || vm->meth.meth == VM_MTDEBUG) && 3494887Schin (env = getenv("VMDEBUG")) && env[0] ) 3504887Schin { if(vm || (vm = vmopen(Vmdcsbrk,Vmdebug,0)) ) 3514887Schin { reg int setcheck = 0; 3524887Schin 3534887Schin while(*env) 3544887Schin { if(*env == 'a') 3554887Schin { vmset(vm,VM_DBABORT,1); 3564887Schin env += 1; 3574887Schin } 3584887Schin else if(*env =='w') 3594887Schin { env += 1; 3604887Schin if((fd = atou(&env)) >= 0 ) 3614887Schin vmdebug(fd); 3624887Schin } 3634887Schin else if(*env < '0' || *env > '9') 3644887Schin env += 1; 3654887Schin else if(env[0] == '0' && (env[1] == 'x' || env[1] == 'X') ) 3664887Schin { if((addr = atou(&env)) != 0) 3674887Schin vmdbwatch((Void_t*)addr); 3684887Schin } 3694887Schin else 3704887Schin { _Vmdbcheck = atou(&env); 3714887Schin setcheck = 1; 3724887Schin if(*env == ',') 3734887Schin { env += 1; 3744887Schin _Vmdbstart = atou(&env); 3754887Schin } 3764887Schin } 3774887Schin } 3784887Schin if(!setcheck) 3794887Schin _Vmdbcheck = 1; 3804887Schin } 3814887Schin } 3824887Schin 3834887Schin if((!vm || vm->meth.meth == VM_MTPROFILE) && 3844887Schin (env = getenv("VMPROFILE")) && env[0] ) 3854887Schin { _Vmpffd = createfile(env); 3864887Schin if(!vm) 3874887Schin vm = vmopen(Vmdcsbrk,Vmprofile,0); 3884887Schin } 3894887Schin 3904887Schin /* slip in the new region now so that malloc() will work fine */ 3914887Schin if(vm) 3924887Schin Vmregion = vm; 3934887Schin 3944887Schin /* turn on tracing if requested */ 3954887Schin if((env = getenv("VMTRACE")) && env[0] && (fd = createfile(env)) >= 0) 3964887Schin { vmset(Vmregion,VM_TRACE,1); 3974887Schin vmtrace(fd); 3984887Schin } 3994887Schin 4004887Schin /* make sure that profile data is output upon exiting */ 4014887Schin if(vm && vm->meth.meth == VM_MTPROFILE) 4024887Schin { if(_Vmpffd < 0) 4034887Schin _Vmpffd = 2; 4044887Schin /* this may wind up calling malloc(), but region is ok now */ 4054887Schin atexit(pfprint); 4064887Schin } 4074887Schin else if(_Vmpffd >= 0) 4084887Schin { close(_Vmpffd); 4094887Schin _Vmpffd = -1; 4104887Schin } 4114887Schin 4124887Schin /* reset file and line number to correct values for the call */ 4134887Schin Vmregion->file = file; 4144887Schin Vmregion->line = line; 4154887Schin Vmregion->func = func; 4164887Schin 4174887Schin return 0; 4184887Schin } 4194887Schin 4204887Schin #if __STD_C 4214887Schin extern Void_t* calloc(reg size_t n_obj, reg size_t s_obj) 4224887Schin #else 4234887Schin extern Void_t* calloc(n_obj, s_obj) 4244887Schin reg size_t n_obj; 4254887Schin reg size_t s_obj; 4264887Schin #endif 4274887Schin { 4284887Schin VMFLINIT(); 4294887Schin return VMRECORD((*Vmregion->meth.resizef)(Vmregion,NIL(Void_t*),n_obj*s_obj,VM_RSZERO)); 4304887Schin } 4314887Schin 4324887Schin #if __STD_C 4334887Schin extern Void_t* malloc(reg size_t size) 4344887Schin #else 4354887Schin extern Void_t* malloc(size) 4364887Schin reg size_t size; 4374887Schin #endif 4384887Schin { 4394887Schin VMFLINIT(); 4404887Schin return VMRECORD((*Vmregion->meth.allocf)(Vmregion,size)); 4414887Schin } 4424887Schin 4434887Schin #if __STD_C 4444887Schin extern Void_t* realloc(reg Void_t* data, reg size_t size) 4454887Schin #else 4464887Schin extern Void_t* realloc(data,size) 4474887Schin reg Void_t* data; /* block to be reallocated */ 4484887Schin reg size_t size; /* new size */ 4494887Schin #endif 4504887Schin { 4514887Schin #if USE_NATIVE 4524887Schin #undef realloc 4534887Schin #if __STD_C 4544887Schin extern Void_t* realloc(Void_t*, size_t); 4554887Schin #else 4564887Schin extern Void_t* realloc(); 4574887Schin #endif 4584887Schin #endif 4594887Schin 4604887Schin VMFLINIT(); 4614887Schin 4624887Schin #if _PACKAGE_ast 4634887Schin if(data && Vmregion->meth.meth != VM_MTDEBUG && 4644887Schin #if !USE_NATIVE 4654887Schin !(Vmregion->data->mode&VM_TRUST) && 4664887Schin #endif 4674887Schin (*Vmregion->meth.addrf)(Vmregion,data) != 0 ) 4684887Schin { 4694887Schin #if USE_NATIVE 4704887Schin return realloc(data, size); 4714887Schin #else 4724887Schin Void_t* newdata; 4734887Schin if((newdata = (*Vmregion->meth.allocf)(Vmregion,size)) ) 4744887Schin memcpy(newdata,data,size); 4754887Schin return VMRECORD(newdata); 4764887Schin #endif 4774887Schin } 4784887Schin #endif 4794887Schin 4804887Schin #if USE_NATIVE 4814887Schin { Void_t* newdata; 4824887Schin if (newdata = (*Vmregion->meth.resizef)(Vmregion,data,size,VM_RSCOPY|VM_RSMOVE)) 4834887Schin return newdata; 4844887Schin return VMRECORD(realloc(data, size)); 4854887Schin } 4864887Schin #else 4874887Schin return VMRECORD((*Vmregion->meth.resizef)(Vmregion,data,size,VM_RSCOPY|VM_RSMOVE)); 4884887Schin #endif 4894887Schin } 4904887Schin 4914887Schin #if __STD_C 4924887Schin extern void free(reg Void_t* data) 4934887Schin #else 4944887Schin extern void free(data) 4954887Schin reg Void_t* data; 4964887Schin #endif 4974887Schin { 4984887Schin #if USE_NATIVE 4994887Schin #undef free 5004887Schin #if __STD_C 5014887Schin extern void free(Void_t*); 5024887Schin #else 5034887Schin extern void free(); 5044887Schin #endif 5054887Schin #endif 5064887Schin 5074887Schin VMFLINIT(); 5084887Schin 5094887Schin #if _PACKAGE_ast 5104887Schin if(data && Vmregion->meth.meth != VM_MTDEBUG && 5114887Schin #if !USE_NATIVE 5124887Schin !(Vmregion->data->mode&VM_TRUST) && 5134887Schin #endif 5144887Schin (*Vmregion->meth.addrf)(Vmregion,data) != 0) 5154887Schin { 5164887Schin #if USE_NATIVE 5174887Schin free(data); 5184887Schin #endif 5194887Schin return; 5204887Schin } 5214887Schin #endif 5224887Schin 5234887Schin #if USE_NATIVE 5244887Schin if ((*Vmregion->meth.freef)(Vmregion,data) != 0) 5254887Schin free(data); 5264887Schin #else 5274887Schin (void)(*Vmregion->meth.freef)(Vmregion,data); 5284887Schin #endif 5294887Schin } 5304887Schin 5314887Schin #if __STD_C 5324887Schin extern void cfree(reg Void_t* data) 5334887Schin #else 5344887Schin extern void cfree(data) 5354887Schin reg Void_t* data; 5364887Schin #endif 5374887Schin { 5384887Schin free(data); 5394887Schin } 5404887Schin 5414887Schin #if __STD_C 5424887Schin extern Void_t* memalign(reg size_t align, reg size_t size) 5434887Schin #else 5444887Schin extern Void_t* memalign(align, size) 5454887Schin reg size_t align; 5464887Schin reg size_t size; 5474887Schin #endif 5484887Schin { 5494887Schin Void_t* addr; 5504887Schin 5514887Schin VMFLINIT(); 5524887Schin VMBLOCK 5534887Schin addr = VMRECORD((*Vmregion->meth.alignf)(Vmregion,size,align)); 5544887Schin VMUNBLOCK 5554887Schin return addr; 5564887Schin } 5574887Schin 5584887Schin #if __STD_C 5594887Schin extern Void_t* valloc(reg size_t size) 5604887Schin #else 5614887Schin extern Void_t* valloc(size) 5624887Schin reg size_t size; 5634887Schin #endif 5644887Schin { 5654887Schin VMFLINIT(); 5664887Schin GETPAGESIZE(_Vmpagesize); 5674887Schin return VMRECORD((*Vmregion->meth.alignf)(Vmregion,size,_Vmpagesize)); 5684887Schin } 5694887Schin 5704887Schin #if __STD_C 5714887Schin extern Void_t* pvalloc(reg size_t size) 5724887Schin #else 5734887Schin extern Void_t* pvalloc(size) 5744887Schin reg size_t size; 5754887Schin #endif 5764887Schin { 5774887Schin VMFLINIT(); 5784887Schin GETPAGESIZE(_Vmpagesize); 5794887Schin return VMRECORD((*Vmregion->meth.alignf)(Vmregion,ROUND(size,_Vmpagesize),_Vmpagesize)); 5804887Schin } 5814887Schin 5824887Schin #if !_PACKAGE_ast 5834887Schin #if __STD_C 5844887Schin char* strdup(const char* s) 5854887Schin #else 5864887Schin char* strdup(s) 5874887Schin char* s; 5884887Schin #endif 5894887Schin { 5904887Schin char *ns; 5914887Schin size_t n; 5924887Schin 5934887Schin if(!s) 5944887Schin return NIL(char*); 5954887Schin else 5964887Schin { n = strlen(s); 5974887Schin if((ns = malloc(n+1)) ) 5984887Schin memcpy(ns,s,n+1); 5994887Schin return ns; 6004887Schin } 6014887Schin } 6024887Schin #endif /* _PACKAGE_ast */ 6034887Schin 6044887Schin #if !_lib_alloca || _mal_alloca 6054887Schin #ifndef _stk_down 6064887Schin #define _stk_down 0 6074887Schin #endif 6084887Schin typedef struct _alloca_s Alloca_t; 6094887Schin union _alloca_u 6104887Schin { struct 6114887Schin { char* addr; 6124887Schin Alloca_t* next; 6134887Schin } head; 6144887Schin char array[ALIGN]; 6154887Schin }; 6164887Schin struct _alloca_s 6174887Schin { union _alloca_u head; 6184887Schin Vmuchar_t data[1]; 6194887Schin }; 6204887Schin 6214887Schin #if __STD_C 6224887Schin extern Void_t* alloca(size_t size) 6234887Schin #else 6244887Schin extern Void_t* alloca(size) 6254887Schin size_t size; 6264887Schin #endif 6274887Schin { char array[ALIGN]; 6284887Schin char* file; 6294887Schin int line; 6304887Schin Void_t* func; 6314887Schin reg Alloca_t* f; 6324887Schin static Alloca_t* Frame; 6334887Schin 6344887Schin VMFLINIT(); 6354887Schin VMFLF(Vmregion,file,line,func); 6364887Schin while(Frame) 6374887Schin { if(( _stk_down && &array[0] > Frame->head.head.addr) || 6384887Schin (!_stk_down && &array[0] < Frame->head.head.addr) ) 6394887Schin { f = Frame; 6404887Schin Frame = f->head.head.next; 6414887Schin (void)(*Vmregion->meth.freef)(Vmregion,f); 6424887Schin } 6434887Schin else break; 6444887Schin } 6454887Schin 6464887Schin Vmregion->file = file; 6474887Schin Vmregion->line = line; 6484887Schin Vmregion->func = func; 6494887Schin f = (Alloca_t*)(*Vmregion->meth.allocf)(Vmregion,size+sizeof(Alloca_t)-1); 6504887Schin 6514887Schin f->head.head.addr = &array[0]; 6524887Schin f->head.head.next = Frame; 6534887Schin Frame = f; 6544887Schin 6554887Schin return (Void_t*)f->data; 6564887Schin } 6574887Schin #endif /*!_lib_alloca || _mal_alloca*/ 6584887Schin 6594887Schin #if _map_malloc 6604887Schin 6614887Schin /* not sure of all the implications -- 0 is conservative for now */ 6624887Schin #define USE_NATIVE 0 /* native free/realloc on non-vmalloc ptrs */ 6634887Schin 6644887Schin #else 6654887Schin 6664887Schin /* intercept _* __* __libc_* variants */ 6674887Schin 6684887Schin #if __lib__malloc 6694887Schin extern Void_t* F2(_calloc, size_t,n, size_t,m) { return calloc(n, m); } 6704887Schin extern Void_t F1(_cfree, Void_t*,p) { free(p); } 6714887Schin extern Void_t F1(_free, Void_t*,p) { free(p); } 6724887Schin extern Void_t* F1(_malloc, size_t,n) { return malloc(n); } 6734887Schin #if _lib_memalign 6744887Schin extern Void_t* F2(_memalign, size_t,a, size_t,n) { return memalign(a, n); } 6754887Schin #endif 6764887Schin #if _lib_pvalloc 6774887Schin extern Void_t* F1(_pvalloc, size_t,n) { return pvalloc(n); } 6784887Schin #endif 6794887Schin extern Void_t* F2(_realloc, Void_t*,p, size_t,n) { return realloc(p, n); } 6804887Schin #if _lib_valloc 6814887Schin extern Void_t* F1(_valloc, size_t,n) { return valloc(n); } 6824887Schin #endif 6834887Schin #endif 6844887Schin 6854887Schin #if _lib___malloc 6864887Schin extern Void_t* F2(__calloc, size_t,n, size_t,m) { return calloc(n, m); } 6874887Schin extern Void_t F1(__cfree, Void_t*,p) { free(p); } 6884887Schin extern Void_t F1(__free, Void_t*,p) { free(p); } 6894887Schin extern Void_t* F1(__malloc, size_t,n) { return malloc(n); } 6904887Schin #if _lib_memalign 6914887Schin extern Void_t* F2(__memalign, size_t,a, size_t,n) { return memalign(a, n); } 6924887Schin #endif 6934887Schin #if _lib_pvalloc 6944887Schin extern Void_t* F1(__pvalloc, size_t,n) { return pvalloc(n); } 6954887Schin #endif 6964887Schin extern Void_t* F2(__realloc, Void_t*,p, size_t,n) { return realloc(p, n); } 6974887Schin #if _lib_valloc 6984887Schin extern Void_t* F1(__valloc, size_t,n) { return valloc(n); } 6994887Schin #endif 7004887Schin #endif 7014887Schin 7024887Schin #if _lib___libc_malloc 7034887Schin extern Void_t* F2(__libc_calloc, size_t,n, size_t,m) { return calloc(n, m); } 7044887Schin extern Void_t F1(__libc_cfree, Void_t*,p) { free(p); } 7054887Schin extern Void_t F1(__libc_free, Void_t*,p) { free(p); } 7064887Schin extern Void_t* F1(__libc_malloc, size_t,n) { return malloc(n); } 7074887Schin #if _lib_memalign 7084887Schin extern Void_t* F2(__libc_memalign, size_t,a, size_t,n) { return memalign(a, n); } 7094887Schin #endif 7104887Schin #if _lib_pvalloc 7114887Schin extern Void_t* F1(__libc_pvalloc, size_t,n) { return pvalloc(n); } 7124887Schin #endif 7134887Schin extern Void_t* F2(__libc_realloc, Void_t*,p, size_t,n) { return realloc(p, n); } 7144887Schin #if _lib_valloc 7154887Schin extern Void_t* F1(__libc_valloc, size_t,n) { return valloc(n); } 7164887Schin #endif 7174887Schin #endif 7184887Schin 7194887Schin #endif /* _map_malloc */ 7204887Schin 7214887Schin #undef extern 7224887Schin 7234887Schin #if _hdr_malloc /* need the mallint interface for statistics, etc. */ 7244887Schin 7254887Schin #undef calloc 7264887Schin #define calloc ______calloc 7274887Schin #undef cfree 7284887Schin #define cfree ______cfree 7294887Schin #undef free 7304887Schin #define free ______free 7314887Schin #undef malloc 7324887Schin #define malloc ______malloc 7334887Schin #undef pvalloc 7344887Schin #define pvalloc ______pvalloc 7354887Schin #undef realloc 7364887Schin #define realloc ______realloc 7374887Schin #undef valloc 7384887Schin #define valloc ______valloc 7394887Schin 7404887Schin #if !_UWIN 7414887Schin 7424887Schin #include <malloc.h> 7434887Schin 7444887Schin typedef struct mallinfo Mallinfo_t; 7454887Schin typedef struct mstats Mstats_t; 7464887Schin 7474887Schin #endif 7484887Schin 7494887Schin #if defined(__EXPORT__) 7504887Schin #define extern __EXPORT__ 7514887Schin #endif 7524887Schin 7534887Schin #if _lib_mallopt 7544887Schin #if __STD_C 7554887Schin extern int mallopt(int cmd, int value) 7564887Schin #else 7574887Schin extern int mallopt(cmd, value) 7584887Schin int cmd; 7594887Schin int value; 7604887Schin #endif 7614887Schin { 7624887Schin VMFLINIT(); 7634887Schin return 0; 7644887Schin } 7654887Schin #endif /*_lib_mallopt*/ 7664887Schin 7674887Schin #if _lib_mallinfo && _mem_arena_mallinfo 7684887Schin #if __STD_C 7694887Schin extern Mallinfo_t mallinfo(void) 7704887Schin #else 7714887Schin extern Mallinfo_t mallinfo() 7724887Schin #endif 7734887Schin { 7744887Schin Vmstat_t sb; 7754887Schin Mallinfo_t mi; 7764887Schin 7774887Schin VMFLINIT(); 7784887Schin memset(&mi,0,sizeof(mi)); 7794887Schin if(vmstat(Vmregion,&sb) >= 0) 7804887Schin { mi.arena = sb.extent; 7814887Schin mi.ordblks = sb.n_busy+sb.n_free; 7824887Schin mi.uordblks = sb.s_busy; 7834887Schin mi.fordblks = sb.s_free; 7844887Schin } 7854887Schin return mi; 7864887Schin } 7874887Schin #endif /* _lib_mallinfo */ 7884887Schin 7894887Schin #if _lib_mstats && _mem_bytes_total_mstats 7904887Schin #if __STD_C 7914887Schin extern Mstats_t mstats(void) 7924887Schin #else 7934887Schin extern Mstats_t mstats() 7944887Schin #endif 7954887Schin { 7964887Schin Vmstat_t sb; 7974887Schin Mstats_t ms; 7984887Schin 7994887Schin VMFLINIT(); 8004887Schin memset(&ms,0,sizeof(ms)); 8014887Schin if(vmstat(Vmregion,&sb) >= 0) 8024887Schin { ms.bytes_total = sb.extent; 8034887Schin ms.chunks_used = sb.n_busy; 8044887Schin ms.bytes_used = sb.s_busy; 8054887Schin ms.chunks_free = sb.n_free; 8064887Schin ms.bytes_free = sb.s_free; 8074887Schin } 8084887Schin return ms; 8094887Schin } 8104887Schin #endif /*_lib_mstats*/ 8114887Schin 8124887Schin #undef extern 8134887Schin 8144887Schin #endif/*_hdr_malloc*/ 8154887Schin 8164887Schin #else 8174887Schin 8184887Schin /* 8194887Schin * even though there is no malloc override, still provide 8204887Schin * _ast_* counterparts for object compatibility 8214887Schin */ 8224887Schin 8234887Schin #undef calloc 8244887Schin extern Void_t* calloc _ARG_((size_t, size_t)); 8254887Schin 8264887Schin #undef cfree 8274887Schin extern void cfree _ARG_((Void_t*)); 8284887Schin 8294887Schin #undef free 8304887Schin extern void free _ARG_((Void_t*)); 8314887Schin 8324887Schin #undef malloc 8334887Schin extern Void_t* malloc _ARG_((size_t)); 8344887Schin 8354887Schin #if _lib_memalign 8364887Schin #undef memalign 8374887Schin extern Void_t* memalign _ARG_((size_t, size_t)); 8384887Schin #endif 8394887Schin 8404887Schin #if _lib_pvalloc 8414887Schin #undef pvalloc 8424887Schin extern Void_t* pvalloc _ARG_((size_t)); 8434887Schin #endif 8444887Schin 8454887Schin #undef realloc 8464887Schin extern Void_t* realloc _ARG_((Void_t*, size_t)); 8474887Schin 8484887Schin #if _lib_valloc 8494887Schin #undef valloc 8504887Schin extern Void_t* valloc _ARG_((size_t)); 8514887Schin #endif 8524887Schin 8534887Schin #if defined(__EXPORT__) 8544887Schin #define extern __EXPORT__ 8554887Schin #endif 8564887Schin 8574887Schin extern Void_t* F2(_ast_calloc, size_t,n, size_t,m) { return calloc(n, m); } 8584887Schin extern Void_t F1(_ast_cfree, Void_t*,p) { free(p); } 8594887Schin extern Void_t F1(_ast_free, Void_t*,p) { free(p); } 8604887Schin extern Void_t* F1(_ast_malloc, size_t,n) { return malloc(n); } 8614887Schin #if _lib_memalign 8624887Schin extern Void_t* F2(_ast_memalign, size_t,a, size_t,n) { return memalign(a, n); } 8634887Schin #endif 8644887Schin #if _lib_pvalloc 8654887Schin extern Void_t* F1(_ast_pvalloc, size_t,n) { return pvalloc(n); } 8664887Schin #endif 8674887Schin extern Void_t* F2(_ast_realloc, Void_t*,p, size_t,n) { return realloc(p, n); } 8684887Schin #if _lib_valloc 8694887Schin extern Void_t* F1(_ast_valloc, size_t,n) { return valloc(n); } 8704887Schin #endif 8714887Schin 8724887Schin #undef extern 8734887Schin 8744887Schin #if _hdr_malloc 8754887Schin 8764887Schin #undef mallinfo 8774887Schin #undef mallopt 8784887Schin #undef mstats 8794887Schin 8804887Schin #define calloc ______calloc 8814887Schin #define cfree ______cfree 8824887Schin #define free ______free 8834887Schin #define malloc ______malloc 8844887Schin #define pvalloc ______pvalloc 8854887Schin #define realloc ______realloc 8864887Schin #define valloc ______valloc 8874887Schin 8884887Schin #if !_UWIN 8894887Schin 8904887Schin #include <malloc.h> 8914887Schin 8924887Schin typedef struct mallinfo Mallinfo_t; 8934887Schin typedef struct mstats Mstats_t; 8944887Schin 8954887Schin #endif 8964887Schin 8974887Schin #if defined(__EXPORT__) 8984887Schin #define extern __EXPORT__ 8994887Schin #endif 9004887Schin 9014887Schin #if _lib_mallopt 9024887Schin extern int F2(_ast_mallopt, int,cmd, int,value) { return mallopt(cmd, value); } 9034887Schin #endif 9044887Schin 9054887Schin #if _lib_mallinfo && _mem_arena_mallinfo 9064887Schin extern Mallinfo_t F0(_ast_mallinfo, void) { return mallinfo(); } 9074887Schin #endif 9084887Schin 9094887Schin #if _lib_mstats && _mem_bytes_total_mstats 9104887Schin extern Mstats_t F0(_ast_mstats, void) { return mstats(); } 9114887Schin #endif 9124887Schin 9134887Schin #undef extern 9144887Schin 9154887Schin #endif /*_hdr_malloc*/ 9164887Schin 9174887Schin #endif /*!_std_malloc*/ 9184887Schin 9194887Schin #endif /*_UWIN*/ 920