2 * Unit test suite for memory allocation functions.
4 * Copyright 2002 Geoffrey Hausheer
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
23 #include "wine/test.h"
29 /* The following functions don't have tests, because either I don't know how
30 to test them, or they are WinNT only, or require multiple threads.
31 Since the last two issues shouldn't really stop the tests from being
32 written, assume for now that it is all due to the first case
41 /* In addition, these features aren't being tested
43 HEAP_GENERATE_EXCEPTIONS
44 STATUS_ACCESS_VIOLATION (error code from HeapAlloc)
47 static void test_Heap(void)
52 LPVOID mem1,mem1a,mem3;
57 /* Retrieve the page size for this system */
59 GetSystemInfo(&sysInfo);
60 ok(sysInfo.dwPageSize>0,"GetSystemInfo should return a valid page size\n");
62 /* Create a Heap with a minimum and maximum size */
63 /* Note that Windows and Wine seem to behave a bit differently with respect
64 to memory allocation. In Windows, you can't access all the memory
65 specified in the heap (due to overhead), so choosing a reasonable maximum
66 size for the heap was done mostly by trial-and-error on Win2k. It may need
67 more tweaking for otherWindows variants.
69 memchunk=10*sysInfo.dwPageSize;
70 heap=HeapCreate(0,2*memchunk,5*memchunk);
72 /* Check that HeapCreate allocated the right amount of ram */
74 /* Today HeapCreate seems to return a memory block larger than specified.
75 MSDN says the maximum heap size should be dwMaximumSize rounded up to the
78 mem1=HeapAlloc(heap,0,5*memchunk+1);
79 ok(mem1==NULL,"HeapCreate allocated more Ram than it should have\n");
81 HeapFree(heap,0,mem1);
85 /* Check that a normal alloc works */
86 mem1=HeapAlloc(heap,0,memchunk);
87 ok(mem1!=NULL,"HeapAlloc failed\n");
89 ok(HeapSize(heap,0,mem1)>=memchunk, "HeapAlloc should return a big enough memory block\n");
92 /* Check that a 'zeroing' alloc works */
93 mem2=HeapAlloc(heap,HEAP_ZERO_MEMORY,memchunk);
94 ok(mem2!=NULL,"HeapAlloc failed\n");
96 ok(HeapSize(heap,0,mem2)>=memchunk,"HeapAlloc should return a big enough memory block\n");
98 for(i=0;i<memchunk;i++) {
103 ok(!error,"HeapAlloc should have zeroed out it's allocated memory\n");
106 /* Check that HeapAlloc returns NULL when requested way too much memory */
107 mem3=HeapAlloc(heap,0,5*memchunk);
108 ok(mem3==NULL,"HeapAlloc should return NULL\n");
110 ok(HeapFree(heap,0,mem3),"HeapFree didn't pass successfully\n");
113 /* Check that HeapRealloc works */
114 mem2a=HeapReAlloc(heap,HEAP_ZERO_MEMORY,mem2,memchunk+5*sysInfo.dwPageSize);
115 ok(mem2a!=NULL,"HeapReAlloc failed\n");
117 ok(HeapSize(heap,0,mem2a)>=memchunk+5*sysInfo.dwPageSize,"HeapReAlloc failed\n");
119 for(i=0;i<5*sysInfo.dwPageSize;i++) {
120 if(mem2a[memchunk+i]!=0) {
124 ok(!error,"HeapReAlloc should have zeroed out it's allocated memory\n");
127 /* Check that HeapRealloc honours HEAP_REALLOC_IN_PLACE_ONLY */
129 mem1a=HeapReAlloc(heap,HEAP_REALLOC_IN_PLACE_ONLY,mem1,memchunk+sysInfo.dwPageSize);
135 ok(mem1a==NULL || error==0,"HeapReAlloc didn't honour HEAP_REALLOC_IN_PLACE_ONLY\n");
137 /* Check that HeapFree works correctly */
139 ok(HeapFree(heap,0,mem1a),"HeapFree failed\n");
141 ok(HeapFree(heap,0,mem1),"HeapFree failed\n");
144 ok(HeapFree(heap,0,mem2a),"HeapFree failed\n");
146 ok(HeapFree(heap,0,mem2),"HeapFree failed\n");
149 /* 0-length buffer */
150 mem1 = HeapAlloc(heap, 0, 0);
151 ok(mem1 != NULL, "Reserved memory\n");
153 dwSize = HeapSize(heap, 0, mem1);
154 /* should work with 0-length buffer */
155 ok((dwSize >= 0) && (dwSize < 0xFFFFFFFF),
156 "The size of the 0-length buffer\n");
157 ok(HeapFree(heap, 0, mem1), "Freed the 0-length buffer\n");
159 /* Check that HeapDestry works */
160 ok(HeapDestroy(heap),"HeapDestroy failed\n");
163 /* The following functions don't have tests, because either I don't know how
164 to test them, or they are WinNT only, or require multiple threads.
165 Since the last two issues shouldn't really stop the tests from being
166 written, assume for now that it is all due to the first case
171 /* In addition, these features aren't being tested
175 static void test_Global(void)
178 HGLOBAL mem1,mem2,mem2a,mem2b;
183 SetLastError(NO_ERROR);
184 /* Check that a normal alloc works */
185 mem1=GlobalAlloc(0,memchunk);
186 ok(mem1!=NULL,"GlobalAlloc failed\n");
188 ok(GlobalSize(mem1)>=memchunk, "GlobalAlloc should return a big enough memory block\n");
191 /* Check that a 'zeroing' alloc works */
192 mem2=GlobalAlloc(GMEM_ZEROINIT,memchunk);
193 ok(mem2!=NULL,"GlobalAlloc failed: error=%ld\n",GetLastError());
195 ok(GlobalSize(mem2)>=memchunk,"GlobalAlloc should return a big enough memory block\n");
196 mem2ptr=GlobalLock(mem2);
197 ok(mem2ptr==mem2,"GlobalLock should have returned the same memory as was allocated\n");
200 for(i=0;i<memchunk;i++) {
205 ok(!error,"GlobalAlloc should have zeroed out it's allocated memory\n");
208 /* Check that GlobalReAlloc works */
209 /* Check that we can change GMEM_FIXED to GMEM_MOVEABLE */
210 mem2a=GlobalReAlloc(mem2,0,GMEM_MODIFY | GMEM_MOVEABLE);
213 mem2ptr=GlobalLock(mem2a);
214 ok(mem2ptr!=NULL && !GlobalUnlock(mem2a)&&GetLastError()==NO_ERROR,
215 "Converting from FIXED to MOVEABLE didn't REALLY work\n");
218 /* Check that ReAllocing memory works as expected */
219 mem2a=GlobalReAlloc(mem2,2*memchunk,GMEM_MOVEABLE | GMEM_ZEROINIT);
220 ok(mem2a!=NULL,"GlobalReAlloc failed\n");
222 ok(GlobalSize(mem2a)>=2*memchunk,"GlobalReAlloc failed\n");
223 mem2ptr=GlobalLock(mem2a);
224 ok(mem2ptr!=NULL,"GlobalLock Failed\n");
227 for(i=0;i<memchunk;i++) {
228 if(mem2ptr[memchunk+i]!=0) {
232 ok(!error,"GlobalReAlloc should have zeroed out it's allocated memory\n");
234 /* Check that GlobalHandle works */
235 mem2b=GlobalHandle(mem2ptr);
236 ok(mem2b==mem2a,"GlobalHandle didn't return the correct memory handle\n");
238 /* Check that we can't discard locked memory */
239 mem2b=GlobalDiscard(mem2a);
241 ok(!GlobalUnlock(mem2a) && GetLastError()==NO_ERROR,"GlobalUnlock Failed\n");
246 ok(GlobalFree(mem1)==NULL,"GlobalFree failed\n");
249 ok(GlobalFree(mem2a)==NULL,"GlobalFree failed\n");
251 ok(GlobalFree(mem2)==NULL,"GlobalFree failed\n");
256 /* The following functions don't have tests, because either I don't know how
257 to test them, or they are WinNT only, or require multiple threads.
258 Since the last two issues shouldn't really stop the tests from being
259 written, assume for now that it is all due to the first case
263 /* In addition, these features aren't being tested
267 static void test_Local(void)
270 HLOCAL mem1,mem2,mem2a,mem2b;
275 /* Check that a normal alloc works */
276 mem1=LocalAlloc(0,memchunk);
277 ok(mem1!=NULL,"LocalAlloc failed: error=%ld\n",GetLastError());
279 ok(LocalSize(mem1)>=memchunk, "LocalAlloc should return a big enough memory block\n");
282 /* Check that a 'zeroing' and lock alloc works */
283 mem2=LocalAlloc(LMEM_ZEROINIT|LMEM_MOVEABLE,memchunk);
284 ok(mem2!=NULL,"LocalAlloc failed: error=%ld\n",GetLastError());
286 ok(LocalSize(mem2)>=memchunk,"LocalAlloc should return a big enough memory block\n");
287 mem2ptr=LocalLock(mem2);
288 ok(mem2ptr!=NULL,"LocalLock: error=%ld\n",GetLastError());
291 for(i=0;i<memchunk;i++) {
296 ok(!error,"LocalAlloc should have zeroed out it's allocated memory\n");
298 error=LocalUnlock(mem2);
299 ok(error==0 && GetLastError()==NO_ERROR,
300 "LocalUnlock Failed: rc=%d err=%ld\n",error,GetLastError());
303 mem2a=LocalFree(mem2);
304 ok(mem2a==NULL, "LocalFree failed: %p\n",mem2a);
306 /* Reallocate mem2 as moveable memory */
307 mem2=LocalAlloc(LMEM_MOVEABLE | LMEM_ZEROINIT,memchunk);
308 ok(mem2!=NULL, "LocalAlloc failed to create moveable memory, error=%ld\n",GetLastError());
310 /* Check that ReAllocing memory works as expected */
311 mem2a=LocalReAlloc(mem2,2*memchunk,LMEM_MOVEABLE | LMEM_ZEROINIT);
312 ok(mem2a!=NULL,"LocalReAlloc failed, error=%ld\n",GetLastError());
314 ok(LocalSize(mem2a)>=2*memchunk,"LocalReAlloc failed\n");
315 mem2ptr=LocalLock(mem2a);
316 ok(mem2ptr!=NULL,"LocalLock Failed\n");
319 for(i=0;i<memchunk;i++) {
320 if(mem2ptr[memchunk+i]!=0) {
324 ok(!error,"LocalReAlloc should have zeroed out it's allocated memory\n");
325 /* Check that LocalHandle works */
326 mem2b=LocalHandle(mem2ptr);
327 ok(mem2b==mem2a,"LocalHandle didn't return the correct memory handle\n");
328 /* Check that we can't discard locked memory */
329 mem2b=LocalDiscard(mem2a);
330 ok(mem2b==NULL,"Discarded memory we shouldn't have\n");
331 SetLastError(NO_ERROR);
332 ok(!LocalUnlock(mem2a) && GetLastError()==NO_ERROR, "LocalUnlock Failed\n");
336 ok(LocalFree(mem1)==NULL,"LocalFree failed\n");
339 ok(LocalFree(mem2a)==NULL,"LocalFree failed\n");
341 ok(LocalFree(mem2)==NULL,"LocalFree failed\n");
345 /* The Virtual* routines are not tested as thoroughly,
346 since I don't really understand how to use them correctly :)
347 The following routines are not tested at all
356 And the only features (flags) being tested are
360 Testing the rest requires using exceptions, which I really don't
363 static void test_Virtual(void)
370 /* Retrieve the page size for this system */
371 sysInfo.dwPageSize=0;
372 GetSystemInfo(&sysInfo);
373 ok(sysInfo.dwPageSize>0,"GetSystemInfo should return a valid page size\n");
375 /* Choose a reasonable allocation size */
376 memchunk=10*sysInfo.dwPageSize;
378 /* Check that a normal alloc works */
379 mem1=VirtualAlloc(NULL,memchunk,MEM_COMMIT,PAGE_READWRITE);
380 ok(mem1!=NULL,"VirtualAlloc failed\n");
382 /* check that memory is initialized to 0 */
384 for(i=0;i<memchunk;i++) {
389 ok(!error,"VirtualAlloc did not initialize memory to '0's\n");
390 /* Check that we can read/write to memory */
392 for(i=0;i<memchunk;i+=100) {
398 ok(!error,"Virtual memory was not writable\n");
400 ok(VirtualFree(mem1,0,MEM_RELEASE),"VirtualFree failed\n");