2 * msvcrt.dll heap functions
4 * Copyright 2000 Jon Griffiths
6 * Note: Win32 heap operations are MT safe. We only lock the new
7 * handler and non atomic heap operations
13 #include "msvcrt/malloc.h"
16 DEFAULT_DEBUG_CHANNEL(msvcrt);
19 extern CRITICAL_SECTION MSVCRT_heap_cs;
20 #define LOCK_HEAP EnterCriticalSection(&MSVCRT_heap_cs)
21 #define UNLOCK_HEAP LeaveCriticalSection(&MSVCRT_heap_cs)
23 typedef void (*MSVCRT_new_handler_func)(unsigned long size);
25 static MSVCRT_new_handler_func MSVCRT_new_handler;
26 static int MSVCRT_new_mode;
29 /*********************************************************************
30 * ??2@YAPAXI@Z (MSVCRT.@)
32 void* MSVCRT_operator_new(unsigned long size)
34 void *retval = HeapAlloc(GetProcessHeap(), 0, size);
35 TRACE("(%ld) returning %p\n", size, retval);
37 if(retval && MSVCRT_new_handler)
38 (*MSVCRT_new_handler)(size);
43 /*********************************************************************
44 * ??3@YAXPAX@Z (MSVCRT.@)
46 void MSVCRT_operator_delete(void *mem)
49 HeapFree(GetProcessHeap(), 0, mem);
53 /*********************************************************************
54 * ?_query_new_handler@@YAP6AHI@ZXZ (MSVCRT.@)
56 MSVCRT_new_handler_func MSVCRT__query_new_handler(void)
58 return MSVCRT_new_handler;
62 /*********************************************************************
63 * ?_query_new_mode@@YAHXZ (MSVCRT.@)
65 int MSVCRT__query_new_mode(void)
67 return MSVCRT_new_mode;
70 /*********************************************************************
71 * ?_set_new_handler@@YAP6AHI@ZP6AHI@Z@Z (MSVCRT.@)
73 MSVCRT_new_handler_func MSVCRT__set_new_handler(MSVCRT_new_handler_func func)
75 MSVCRT_new_handler_func old_handler;
77 old_handler = MSVCRT_new_handler;
78 MSVCRT_new_handler = func;
83 /*********************************************************************
84 * ?set_new_handler@@YAP6AXXZP6AXXZ@Z (MSVCRT.@)
86 MSVCRT_new_handler_func MSVCRT_set_new_handler(void *func)
89 MSVCRT__set_new_handler(NULL);
93 /*********************************************************************
94 * ?_set_new_mode@@YAHH@Z (MSVCRT.@)
96 int MSVCRT__set_new_mode(int mode)
100 old_mode = MSVCRT_new_mode;
101 MSVCRT_new_mode = mode;
106 /*********************************************************************
107 * _callnewh (MSVCRT.@)
109 int _callnewh(unsigned long size)
111 if(MSVCRT_new_handler)
112 (*MSVCRT_new_handler)(size);
116 /*********************************************************************
119 void* _expand(void* mem, MSVCRT_size_t size)
121 return HeapReAlloc(GetProcessHeap(), HEAP_REALLOC_IN_PLACE_ONLY, mem, size);
124 /*********************************************************************
125 * _heapchk (MSVCRT.@)
129 if (!HeapValidate( GetProcessHeap(), 0, NULL))
131 MSVCRT__set_errno(GetLastError());
137 /*********************************************************************
138 * _heapmin (MSVCRT.@)
142 if (!HeapCompact( GetProcessHeap(), 0 ))
144 if (GetLastError() != ERROR_CALL_NOT_IMPLEMENTED)
145 MSVCRT__set_errno(GetLastError());
151 /*********************************************************************
152 * _heapwalk (MSVCRT.@)
154 int _heapwalk(_HEAPINFO* next)
156 PROCESS_HEAP_ENTRY phe;
159 phe.lpData = next->_pentry;
160 phe.cbData = next->_size;
161 phe.wFlags = next->_useflag == _USEDENTRY ? PROCESS_HEAP_ENTRY_BUSY : 0;
163 if (phe.lpData && phe.wFlags & PROCESS_HEAP_ENTRY_BUSY &&
164 !HeapValidate( GetProcessHeap(), 0, phe.lpData ))
167 MSVCRT__set_errno(GetLastError());
173 if (!HeapWalk( GetProcessHeap(), &phe ))
176 if (GetLastError() == ERROR_NO_MORE_ITEMS)
178 MSVCRT__set_errno(GetLastError());
180 return _HEAPBADBEGIN;
183 } while (phe.wFlags & (PROCESS_HEAP_REGION|PROCESS_HEAP_UNCOMMITTED_RANGE));
186 next->_pentry = phe.lpData;
187 next->_size = phe.cbData;
188 next->_useflag = phe.wFlags & PROCESS_HEAP_ENTRY_BUSY ? _USEDENTRY : _FREEENTRY;
192 /*********************************************************************
193 * _heapset (MSVCRT.@)
195 int _heapset(unsigned int value)
200 memset( &heap, 0, sizeof(_HEAPINFO) );
202 while ((retval = _heapwalk(&heap)) == _HEAPOK)
204 if (heap._useflag == _FREEENTRY)
205 memset(heap._pentry, value, heap._size);
208 return retval == _HEAPEND? _HEAPOK : retval;
211 /*********************************************************************
212 * _heapadd (MSVCRT.@)
214 int _heapadd(void* mem, MSVCRT_size_t size)
216 TRACE("(%p,%d) unsupported in Win32\n", mem,size);
217 SET_THREAD_VAR(errno,MSVCRT_ENOSYS);
221 /*********************************************************************
224 MSVCRT_size_t _msize(void* mem)
226 long size = HeapSize(GetProcessHeap(),0,mem);
229 WARN(":Probably called with non wine-allocated memory, ret = -1\n");
230 /* At least the Win32 crtdll/msvcrt also return -1 in this case */
235 /*********************************************************************
238 void* MSVCRT_calloc(MSVCRT_size_t size, MSVCRT_size_t count)
240 return HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, size * count );
243 /*********************************************************************
246 void MSVCRT_free(void* ptr)
248 HeapFree(GetProcessHeap(),0,ptr);
251 /*********************************************************************
254 void* MSVCRT_malloc(MSVCRT_size_t size)
256 void *ret = HeapAlloc(GetProcessHeap(),0,size);
258 MSVCRT__set_errno(GetLastError());
262 /*********************************************************************
265 void* MSVCRT_realloc(void* ptr, MSVCRT_size_t size)
267 return HeapReAlloc(GetProcessHeap(), 0, ptr, size);