|
1 /* |
|
2 TestCacheBlockFiles.cpp |
|
3 */ |
|
4 |
|
5 |
|
6 #include <stdio.h> |
|
7 #include <stdlib.h> |
|
8 #include <utime.h> |
|
9 |
|
10 #include <Files.h> |
|
11 #include <Strings.h> |
|
12 #include <Errors.h> |
|
13 #include <Resources.h> |
|
14 #include <Aliases.h> |
|
15 |
|
16 #include "nsCOMPtr.h" |
|
17 #include "nsCRT.h" |
|
18 #include "nsDirectoryServiceDefs.h" |
|
19 #include "nsError.h" |
|
20 #include "nsIComponentManager.h" |
|
21 #include "nsIComponentRegistrar.h" |
|
22 #include "nsIFile.h" |
|
23 #include "nsIFileStreams.h" |
|
24 #include "nsMemory.h" |
|
25 #include "nsIComponentRegistrar.h" |
|
26 #include "nsANSIFileStreams.h" |
|
27 #include "nsDiskCacheBlockFile.h" |
|
28 |
|
29 #include "prclist.h" |
|
30 |
|
31 /** |
|
32 * StressTest() |
|
33 */ |
|
34 |
|
35 typedef struct Allocation { |
|
36 int32_t start; |
|
37 int32_t count; |
|
38 } Allocation; |
|
39 |
|
40 nsresult |
|
41 StressTest(nsIFile * localFile, int32_t testNumber, bool readWrite) |
|
42 { |
|
43 nsresult rv = NS_OK; |
|
44 |
|
45 #define ITERATIONS 1024 |
|
46 #define MAX_ALLOCATIONS 256 |
|
47 Allocation block[MAX_ALLOCATIONS]; |
|
48 int32_t currentAllocations = 0; |
|
49 int32_t i; |
|
50 uint32_t a; |
|
51 |
|
52 char * writeBuf[4]; |
|
53 char readBuf[256 * 4]; |
|
54 |
|
55 |
|
56 if (readWrite) { |
|
57 for (i = 0; i < 4; i++) { |
|
58 writeBuf[i] = new char[256 * i]; |
|
59 if (!writeBuf[i]) { |
|
60 printf("Test %d: failed - out of memory\n", testNumber); |
|
61 rv = NS_ERROR_OUT_OF_MEMORY; |
|
62 goto exit; |
|
63 } |
|
64 |
|
65 memset(writeBuf[i], i, 256 * i); |
|
66 } |
|
67 } |
|
68 |
|
69 nsDiskCacheBlockFile * blockFile = new nsDiskCacheBlockFile; |
|
70 if (!blockFile) { |
|
71 printf("Test %d failed (unable to allocate nsDiskCacheBlockFile", testNumber); |
|
72 rv = NS_ERROR_OUT_OF_MEMORY; |
|
73 goto exit; |
|
74 } |
|
75 |
|
76 rv = blockFile->Open(localFile, 256); |
|
77 if (NS_FAILED(rv)) { |
|
78 printf("Test %d: failed (Open returned: 0x%.8x)\n", testNumber, rv); |
|
79 goto exit; |
|
80 } |
|
81 |
|
82 i = ITERATIONS; |
|
83 while (i > 0) { |
|
84 if ((currentAllocations >= MAX_ALLOCATIONS) || |
|
85 ((currentAllocations > 0) && (rand() % 4 == 0))) { |
|
86 // deallocate if we've reached the limit, or 25% of the time we have allocations |
|
87 a = rand() % currentAllocations; |
|
88 |
|
89 if (readWrite) { |
|
90 // read verify deallocation |
|
91 rv = blockFile->ReadBlocks(readBuf, block[a].start, block[a].count); |
|
92 if (NS_FAILED(rv)) { |
|
93 printf("Test %d: failed (ReadBlocks() returned 0x%.8x)\n", testNumber, rv); |
|
94 goto exit; |
|
95 } |
|
96 |
|
97 // Verify buffer |
|
98 for (i = 0; i < 256 * block[a].count; i++) { |
|
99 if (readBuf[i] != block[a].count) { |
|
100 printf("Test %d: failed (verifying buffer 1)\n", testNumber); |
|
101 rv = NS_ERROR_FAILURE; |
|
102 goto exit; |
|
103 } |
|
104 } |
|
105 } |
|
106 |
|
107 rv = blockFile->DeallocateBlocks(block[a].start, block[a].count); |
|
108 if (NS_FAILED(rv)) { |
|
109 printf("Test %d: failed (DeallocateBlocks() returned %d)\n", testNumber, rv); |
|
110 goto exit; |
|
111 } |
|
112 |
|
113 --currentAllocations; |
|
114 if (currentAllocations > 0) |
|
115 block[a] = block[currentAllocations]; |
|
116 |
|
117 } else { |
|
118 // allocate blocks |
|
119 --i; |
|
120 a = currentAllocations++; |
|
121 block[a].count = rand() % 4 + 1; // allocate 1 to 4 blocks |
|
122 block[a].start = blockFile->AllocateBlocks(block[a].count); |
|
123 if (block[a].start < 0) { |
|
124 printf("Test %d: failed (AllocateBlocks() failed.)\n", testNumber); |
|
125 goto exit; |
|
126 } |
|
127 |
|
128 if (readWrite) { |
|
129 // write buffer |
|
130 rv = blockFile->WriteBlocks(writeBuf[block[a].count], block[a].start, block[a].count); |
|
131 if (NS_FAILED(rv)) { |
|
132 printf("Test %d: failed (WriteBlocks() returned 0x%.8x)\n",testNumber, rv); |
|
133 goto exit; |
|
134 } |
|
135 } |
|
136 } |
|
137 } |
|
138 |
|
139 // now deallocate remaining allocations |
|
140 i = currentAllocations; |
|
141 while (i--) { |
|
142 |
|
143 if (readWrite) { |
|
144 // read verify deallocation |
|
145 rv = blockFile->ReadBlocks(readBuf, block[a].start, block[a].count); |
|
146 if (NS_FAILED(rv)) { |
|
147 printf("Test %d: failed (ReadBlocks(1) returned 0x%.8x)\n", testNumber, rv); |
|
148 goto exit; |
|
149 } |
|
150 |
|
151 // Verify buffer |
|
152 for (i = 0; i < 256 * block[a].count; i++) { |
|
153 if (readBuf[i] != block[a].count) { |
|
154 printf("Test %d: failed (verifying buffer 1)\n", testNumber); |
|
155 rv = NS_ERROR_FAILURE; |
|
156 goto exit; |
|
157 } |
|
158 } |
|
159 } |
|
160 |
|
161 rv = blockFile->DeallocateBlocks(block[i].start, block[i].count); |
|
162 if (NS_FAILED(rv)) { |
|
163 printf("Test %d: failed (DeallocateBlocks() returned %d)\n", testNumber, rv); |
|
164 goto exit; |
|
165 } |
|
166 } |
|
167 |
|
168 |
|
169 |
|
170 exit: |
|
171 nsresult rv2 = blockFile->Close(); |
|
172 if (NS_FAILED(rv2)) { |
|
173 printf("Test %d: failed (Close returned: 0x%.8x)\n", testNumber, rv2); |
|
174 } |
|
175 |
|
176 return rv ? rv : rv2; |
|
177 } |
|
178 |
|
179 /** |
|
180 * main() |
|
181 */ |
|
182 |
|
183 int |
|
184 main(void) |
|
185 { |
|
186 // OSErr err; |
|
187 printf("hello world\n"); |
|
188 |
|
189 unsigned long now = time(0); |
|
190 srand(now); |
|
191 |
|
192 nsCOMPtr<nsIFile> file; |
|
193 nsCOMPtr<nsIFile> localFile; |
|
194 nsresult rv = NS_OK; |
|
195 { |
|
196 // Start up XPCOM |
|
197 nsCOMPtr<nsIServiceManager> servMan; |
|
198 NS_InitXPCOM2(getter_AddRefs(servMan), nullptr, nullptr); |
|
199 nsCOMPtr<nsIComponentRegistrar> registrar = do_QueryInterface(servMan); |
|
200 NS_ASSERTION(registrar, "Null nsIComponentRegistrar"); |
|
201 if (registrar) |
|
202 registrar->AutoRegister(nullptr); |
|
203 |
|
204 // Get default directory |
|
205 rv = NS_GetSpecialDirectory(NS_XPCOM_CURRENT_PROCESS_DIR, |
|
206 getter_AddRefs(file)); |
|
207 if (NS_FAILED(rv)) { |
|
208 printf("NS_GetSpecialDirectory() failed : 0x%.8x\n", rv); |
|
209 goto exit; |
|
210 } |
|
211 char * currentDirPath; |
|
212 rv = file->GetPath(¤tDirPath); |
|
213 if (NS_FAILED(rv)) { |
|
214 printf("currentProcessDir->GetPath() failed : 0x%.8x\n", rv); |
|
215 goto exit; |
|
216 } |
|
217 |
|
218 printf("Current Process Directory: %s\n", currentDirPath); |
|
219 |
|
220 |
|
221 // Generate name for cache block file |
|
222 rv = file->Append("_CACHE_001_"); |
|
223 if (NS_FAILED(rv)) goto exit; |
|
224 |
|
225 // Delete existing file |
|
226 rv = file->Delete(false); |
|
227 if (NS_FAILED(rv) && rv != NS_ERROR_FILE_NOT_FOUND) goto exit; |
|
228 |
|
229 // Need nsIFile to open |
|
230 localFile = do_QueryInterface(file, &rv); |
|
231 if (NS_FAILED(rv)) { |
|
232 printf("do_QueryInterface(file) failed : 0x%.8x\n", rv); |
|
233 goto exit; |
|
234 } |
|
235 |
|
236 nsDiskCacheBlockFile * blockFile = new nsDiskCacheBlockFile; |
|
237 if (!blockFile) { |
|
238 rv = NS_ERROR_OUT_OF_MEMORY; |
|
239 goto exit; |
|
240 } |
|
241 |
|
242 //---------------------------------------------------------------- |
|
243 // local variables used in tests |
|
244 //---------------------------------------------------------------- |
|
245 uint32_t bytesWritten = 0; |
|
246 int32_t startBlock; |
|
247 int32_t i = 0; |
|
248 |
|
249 |
|
250 //---------------------------------------------------------------- |
|
251 // Test 1: Open nonexistent file |
|
252 //---------------------------------------------------------------- |
|
253 rv = blockFile->Open(localFile, 256); |
|
254 if (NS_FAILED(rv)) { |
|
255 printf("Test 1: failed (Open returned: 0x%.8x)\n", rv); |
|
256 goto exit; |
|
257 } |
|
258 |
|
259 rv = blockFile->Close(); |
|
260 if (NS_FAILED(rv)) { |
|
261 printf("Test 1: failed (Close returned: 0x%.8x)\n", rv); |
|
262 goto exit; |
|
263 } |
|
264 |
|
265 printf("Test 1: passed\n"); |
|
266 |
|
267 |
|
268 //---------------------------------------------------------------- |
|
269 // Test 2: Open existing file (with no allocation) |
|
270 //---------------------------------------------------------------- |
|
271 rv = blockFile->Open(localFile, 256); |
|
272 if (NS_FAILED(rv)) { |
|
273 printf("Test 2: failed (Open returned: 0x%.8x)\n", rv); |
|
274 goto exit; |
|
275 } |
|
276 |
|
277 rv = blockFile->Close(); |
|
278 if (NS_FAILED(rv)) { |
|
279 printf("Test 2: failed (Close returned: 0x%.8x)\n", rv); |
|
280 goto exit; |
|
281 } |
|
282 |
|
283 printf("Test 2: passed\n"); |
|
284 |
|
285 |
|
286 //---------------------------------------------------------------- |
|
287 // Test 3: Open existing file (bad format) size < kBitMapBytes |
|
288 //---------------------------------------------------------------- |
|
289 |
|
290 // Delete existing file |
|
291 rv = localFile->Delete(false); |
|
292 if (NS_FAILED(rv)) { |
|
293 printf("Test 3 failed (Delete returned: 0x%.8x)\n", rv); |
|
294 goto exit; |
|
295 } |
|
296 |
|
297 // write < kBitMapBytes to file |
|
298 nsANSIFileStream * stream = new nsANSIFileStream; |
|
299 if (!stream) { |
|
300 printf("Test 3 failed (unable to allocate stream\n", rv); |
|
301 goto exit; |
|
302 } |
|
303 NS_ADDREF(stream); |
|
304 rv = stream->Open(localFile); |
|
305 if (NS_FAILED(rv)) { |
|
306 NS_RELEASE(stream); |
|
307 printf("Test 3 failed (stream->Open returned: 0x%.8x)\n", rv); |
|
308 goto exit; |
|
309 } |
|
310 |
|
311 bytesWritten = 0; |
|
312 rv = stream->Write("Tell me something good.\n", 24, &bytesWritten); |
|
313 if (NS_FAILED(rv)) { |
|
314 NS_RELEASE(stream); |
|
315 printf("Test 3 failed (stream->Write returned: 0x%.8x)\n", rv); |
|
316 goto exit; |
|
317 } |
|
318 |
|
319 rv = stream->Close(); |
|
320 if (NS_FAILED(rv)) { |
|
321 NS_RELEASE(stream); |
|
322 printf("Test 3 failed (stream->Close returned: 0x%.8x)\n", rv); |
|
323 goto exit; |
|
324 } |
|
325 NS_RELEASE(stream); |
|
326 |
|
327 rv = blockFile->Open(localFile, 256); |
|
328 if (NS_SUCCEEDED(rv)) { |
|
329 printf("Test 3: failed (Open erroneously succeeded)\n", rv); |
|
330 |
|
331 (void) blockFile->Close(); |
|
332 goto exit; |
|
333 } |
|
334 |
|
335 printf("Test 3: passed\n"); |
|
336 |
|
337 |
|
338 //---------------------------------------------------------------- |
|
339 // Test 4: Open nonexistent file (again) |
|
340 //---------------------------------------------------------------- |
|
341 |
|
342 // Delete existing file |
|
343 rv = localFile->Delete(false); |
|
344 if (NS_FAILED(rv)) { |
|
345 printf("Test 4 failed (Delete returned: 0x%.8x)\n", rv); |
|
346 goto exit; |
|
347 } |
|
348 |
|
349 rv = blockFile->Open(localFile, 256); |
|
350 if (NS_FAILED(rv)) { |
|
351 printf("Test 4: failed (Open returned: 0x%.8x)\n", rv); |
|
352 goto exit; |
|
353 } |
|
354 |
|
355 printf("Test 4: passed\n"); |
|
356 |
|
357 |
|
358 //---------------------------------------------------------------- |
|
359 // Test 5: AllocateBlocks: invalid block count (0, 5) |
|
360 //---------------------------------------------------------------- |
|
361 |
|
362 |
|
363 startBlock = blockFile->AllocateBlocks(0); |
|
364 if (startBlock > -1) { |
|
365 printf("Test 5: failed (AllocateBlocks(0) erroneously succeeded)\n"); |
|
366 goto exit; |
|
367 } |
|
368 |
|
369 startBlock = blockFile->AllocateBlocks(5); |
|
370 if (startBlock > -1) { |
|
371 printf("Test 5: failed (AllocateBlocks(5) erroneously succeeded)\n"); |
|
372 goto exit; |
|
373 } |
|
374 printf("Test 5: passed\n"); |
|
375 |
|
376 |
|
377 //---------------------------------------------------------------- |
|
378 // Test 6: AllocateBlocks: valid block count (1, 2, 3, 4) |
|
379 //---------------------------------------------------------------- |
|
380 startBlock = blockFile->AllocateBlocks(1); |
|
381 if (startBlock != 0) { |
|
382 printf("Test 6: failed (AllocateBlocks(1) failed)\n"); |
|
383 goto exit; |
|
384 } |
|
385 |
|
386 startBlock = blockFile->AllocateBlocks(2); |
|
387 if (startBlock != 1) { |
|
388 printf("Test 6: failed (AllocateBlocks(2) failed)\n"); |
|
389 goto exit; |
|
390 } |
|
391 |
|
392 startBlock = blockFile->AllocateBlocks(3); |
|
393 if (startBlock != 4) { |
|
394 printf("Test 6: failed (AllocateBlocks(3) failed)\n"); |
|
395 goto exit; |
|
396 } |
|
397 |
|
398 startBlock = blockFile->AllocateBlocks(4); |
|
399 if (startBlock != 8) { |
|
400 printf("Test 6: failed (AllocateBlocks(4) failed)\n"); |
|
401 goto exit; |
|
402 } |
|
403 |
|
404 // blocks allocated should be 1220 3330 4444 |
|
405 printf("Test 6: passed\n"); // but bits could be mis-allocated |
|
406 |
|
407 |
|
408 |
|
409 //---------------------------------------------------------------- |
|
410 // Test 7: VerifyAllocation |
|
411 //---------------------------------------------------------------- |
|
412 rv = blockFile->VerifyAllocation(0,1); |
|
413 if (NS_FAILED(rv)) { |
|
414 printf("Test 7: failed (VerifyAllocation(0,1) returned: 0x%.8x)\n", rv); |
|
415 goto exit; |
|
416 } |
|
417 |
|
418 rv = blockFile->VerifyAllocation(1,2); |
|
419 if (NS_FAILED(rv)) { |
|
420 printf("Test 7: failed (VerifyAllocation(1,2) returned: 0x%.8x)\n", rv); |
|
421 goto exit; |
|
422 } |
|
423 |
|
424 rv = blockFile->VerifyAllocation(4,3); |
|
425 if (NS_FAILED(rv)) { |
|
426 printf("Test 7: failed (VerifyAllocation(4,3) returned: 0x%.8x)\n", rv); |
|
427 goto exit; |
|
428 } |
|
429 |
|
430 rv = blockFile->VerifyAllocation(8,4); |
|
431 if (NS_FAILED(rv)) { |
|
432 printf("Test 7: failed (VerifyAllocation(8,4) returned: 0x%.8x)\n", rv); |
|
433 goto exit; |
|
434 } |
|
435 printf("Test 7: passed\n"); |
|
436 |
|
437 |
|
438 //---------------------------------------------------------------- |
|
439 // Test 8: LastBlock |
|
440 //---------------------------------------------------------------- |
|
441 int32_t lastBlock = blockFile->LastBlock(); |
|
442 if (lastBlock != 11) { |
|
443 printf("Test 8: failed (LastBlock() returned: %d)\n", lastBlock); |
|
444 goto exit; |
|
445 } |
|
446 printf("Test 8: passed\n"); |
|
447 |
|
448 |
|
449 //---------------------------------------------------------------- |
|
450 // Test 9: DeallocateBlocks: bad startBlock ( < 0) |
|
451 //---------------------------------------------------------------- |
|
452 rv = blockFile->DeallocateBlocks(-1, 4); |
|
453 if (NS_SUCCEEDED(rv)) { |
|
454 printf("Test 9: failed (DeallocateBlocks(-1, 4) erroneously succeeded)\n"); |
|
455 goto exit; |
|
456 } |
|
457 printf("Test 9: passed\n"); |
|
458 |
|
459 |
|
460 //---------------------------------------------------------------- |
|
461 // Test 10: DeallocateBlocks: bad numBlocks (0, 5) |
|
462 //---------------------------------------------------------------- |
|
463 rv = blockFile->DeallocateBlocks(0, 0); |
|
464 if (NS_SUCCEEDED(rv)) { |
|
465 printf("Test 10: failed (DeallocateBlocks(0, 0) erroneously succeeded)\n"); |
|
466 goto exit; |
|
467 } |
|
468 |
|
469 rv = blockFile->DeallocateBlocks(0, 5); |
|
470 if (NS_SUCCEEDED(rv)) { |
|
471 printf("Test 10: failed (DeallocateBlocks(0, 5) erroneously succeeded)\n"); |
|
472 goto exit; |
|
473 } |
|
474 |
|
475 printf("Test 10: passed\n"); |
|
476 |
|
477 |
|
478 //---------------------------------------------------------------- |
|
479 // Test 11: DeallocateBlocks: unallocated blocks |
|
480 //---------------------------------------------------------------- |
|
481 rv = blockFile->DeallocateBlocks(12, 1); |
|
482 if (NS_SUCCEEDED(rv)) { |
|
483 printf("Test 11: failed (DeallocateBlocks(12, 1) erroneously succeeded)\n"); |
|
484 goto exit; |
|
485 } |
|
486 |
|
487 printf("Test 11: passed\n"); |
|
488 |
|
489 |
|
490 //---------------------------------------------------------------- |
|
491 // Test 12: DeallocateBlocks: 1, 2, 3, 4 (allocated in Test 6) |
|
492 //---------------------------------------------------------------- |
|
493 rv = blockFile->DeallocateBlocks(0, 1); |
|
494 if (NS_FAILED(rv)) { |
|
495 printf("Test 12: failed (DeallocateBlocks(12, 1) returned: 0x%.8x)\n", rv); |
|
496 goto exit; |
|
497 } |
|
498 |
|
499 rv = blockFile->DeallocateBlocks(1, 2); |
|
500 if (NS_FAILED(rv)) { |
|
501 printf("Test 12: failed (DeallocateBlocks(1, 2) returned: 0x%.8x)\n", rv); |
|
502 goto exit; |
|
503 } |
|
504 |
|
505 rv = blockFile->DeallocateBlocks(4, 3); |
|
506 if (NS_FAILED(rv)) { |
|
507 printf("Test 12: failed (DeallocateBlocks(4, 3) returned: 0x%.8x)\n", rv); |
|
508 goto exit; |
|
509 } |
|
510 |
|
511 rv = blockFile->DeallocateBlocks(8, 4); |
|
512 if (NS_FAILED(rv)) { |
|
513 printf("Test 12: failed (DeallocateBlocks(8, 4) returned: 0x%.8x)\n", rv); |
|
514 goto exit; |
|
515 } |
|
516 |
|
517 // zero blocks should be allocated |
|
518 rv = blockFile->Close(); |
|
519 if (NS_FAILED(rv)) { |
|
520 printf("Test 12: failed (Close returned: 0x%.8x)\n", rv); |
|
521 goto exit; |
|
522 } |
|
523 |
|
524 printf("Test 12: passed\n"); |
|
525 |
|
526 |
|
527 //---------------------------------------------------------------- |
|
528 // Test 13: Allocate/Deallocate boundary test |
|
529 //---------------------------------------------------------------- |
|
530 |
|
531 rv = blockFile->Open(localFile, 256); |
|
532 if (NS_FAILED(rv)) { |
|
533 printf("Test 13: failed (Open returned: 0x%.8x)\n", rv); |
|
534 goto exit; |
|
535 } |
|
536 |
|
537 // fully allocate, 1 block at a time |
|
538 for (i=0; i< kBitMapBytes * 8; ++i) { |
|
539 startBlock = blockFile->AllocateBlocks(1); |
|
540 if (startBlock < 0) { |
|
541 printf("Test 13: failed (AllocateBlocks(1) failed on i=%d)\n", i); |
|
542 goto exit; |
|
543 } |
|
544 } |
|
545 |
|
546 // attempt allocation with full bit map |
|
547 startBlock = blockFile->AllocateBlocks(1); |
|
548 if (startBlock >= 0) { |
|
549 printf("Test 13: failed (AllocateBlocks(1) erroneously succeeded i=%d)\n", i); |
|
550 goto exit; |
|
551 } |
|
552 |
|
553 // deallocate all the bits |
|
554 for (i=0; i< kBitMapBytes * 8; ++i) { |
|
555 rv = blockFile->DeallocateBlocks(i,1); |
|
556 if (NS_FAILED(rv)) { |
|
557 printf("Test 13: failed (DeallocateBlocks(%d,1) returned: 0x%.8x)\n", i,rv); |
|
558 goto exit; |
|
559 } |
|
560 } |
|
561 |
|
562 // attempt deallocation beyond end of bit map |
|
563 rv = blockFile->DeallocateBlocks(i,1); |
|
564 if (NS_SUCCEEDED(rv)) { |
|
565 printf("Test 13: failed (DeallocateBlocks(%d,1) erroneously succeeded)\n", i); |
|
566 goto exit; |
|
567 } |
|
568 |
|
569 // bit map should be empty |
|
570 |
|
571 // fully allocate, 2 block at a time |
|
572 for (i=0; i< kBitMapBytes * 8; i+=2) { |
|
573 startBlock = blockFile->AllocateBlocks(2); |
|
574 if (startBlock < 0) { |
|
575 printf("Test 13: failed (AllocateBlocks(2) failed on i=%d)\n", i); |
|
576 goto exit; |
|
577 } |
|
578 } |
|
579 |
|
580 // attempt allocation with full bit map |
|
581 startBlock = blockFile->AllocateBlocks(2); |
|
582 if (startBlock >= 0) { |
|
583 printf("Test 13: failed (AllocateBlocks(2) erroneously succeeded i=%d)\n", i); |
|
584 goto exit; |
|
585 } |
|
586 |
|
587 // deallocate all the bits |
|
588 for (i=0; i< kBitMapBytes * 8; i+=2) { |
|
589 rv = blockFile->DeallocateBlocks(i,2); |
|
590 if (NS_FAILED(rv)) { |
|
591 printf("Test 13: failed (DeallocateBlocks(%d,2) returned: 0x%.8x)\n", i,rv); |
|
592 goto exit; |
|
593 } |
|
594 } |
|
595 |
|
596 // bit map should be empty |
|
597 |
|
598 // fully allocate, 4 block at a time |
|
599 for (i=0; i< kBitMapBytes * 8; i+=4) { |
|
600 startBlock = blockFile->AllocateBlocks(4); |
|
601 if (startBlock < 0) { |
|
602 printf("Test 13: failed (AllocateBlocks(4) failed on i=%d)\n", i); |
|
603 goto exit; |
|
604 } |
|
605 } |
|
606 |
|
607 // attempt allocation with full bit map |
|
608 startBlock = blockFile->AllocateBlocks(4); |
|
609 if (startBlock >= 0) { |
|
610 printf("Test 13: failed (AllocateBlocks(4) erroneously succeeded i=%d)\n", i); |
|
611 goto exit; |
|
612 } |
|
613 |
|
614 // deallocate all the bits |
|
615 for (i=0; i< kBitMapBytes * 8; i+=4) { |
|
616 rv = blockFile->DeallocateBlocks(i,4); |
|
617 if (NS_FAILED(rv)) { |
|
618 printf("Test 13: failed (DeallocateBlocks(%d,4) returned: 0x%.8x)\n", i,rv); |
|
619 goto exit; |
|
620 } |
|
621 } |
|
622 |
|
623 // bit map should be empty |
|
624 |
|
625 // allocate as many triple-blocks as possible |
|
626 for (i=0; i< kBitMapBytes * 8; i+=4) { |
|
627 startBlock = blockFile->AllocateBlocks(3); |
|
628 if (startBlock < 0) { |
|
629 printf("Test 13: failed (AllocateBlocks(3) failed on i=%d)\n", i); |
|
630 goto exit; |
|
631 } |
|
632 } |
|
633 |
|
634 // attempt allocation with "full" bit map |
|
635 startBlock = blockFile->AllocateBlocks(3); |
|
636 if (startBlock >= 0) { |
|
637 printf("Test 13: failed (AllocateBlocks(3) erroneously succeeded i=%d)\n", i); |
|
638 goto exit; |
|
639 } |
|
640 |
|
641 // leave some blocks allocated |
|
642 |
|
643 rv = blockFile->Close(); |
|
644 if (NS_FAILED(rv)) { |
|
645 printf("Test 13: failed (Close returned: 0x%.8x)\n", rv); |
|
646 goto exit; |
|
647 } |
|
648 |
|
649 printf("Test 13: passed\n"); |
|
650 |
|
651 |
|
652 //---------------------------------------------------------------- |
|
653 // Test 14: ValidateFile (open existing file w/size < allocated blocks |
|
654 //---------------------------------------------------------------- |
|
655 rv = blockFile->Open(localFile, 256); |
|
656 if (NS_SUCCEEDED(rv)) { |
|
657 printf("Test 14: failed (Open erroneously succeeded)\n"); |
|
658 goto exit; |
|
659 } |
|
660 |
|
661 // Delete existing file |
|
662 rv = localFile->Delete(false); |
|
663 if (NS_FAILED(rv)) { |
|
664 printf("Test 14 failed (Delete returned: 0x%.8x)\n", rv); |
|
665 goto exit; |
|
666 } |
|
667 printf("Test 14: passed\n"); |
|
668 |
|
669 |
|
670 //---------------------------------------------------------------- |
|
671 // Test 15: Allocate/Deallocate stress test |
|
672 //---------------------------------------------------------------- |
|
673 |
|
674 rv = StressTest(localFile, 15, false); |
|
675 if (NS_FAILED(rv)) |
|
676 goto exit; |
|
677 |
|
678 printf("Test 15: passed\n"); |
|
679 |
|
680 |
|
681 //---------------------------------------------------------------- |
|
682 // Test 16: WriteBlocks |
|
683 //---------------------------------------------------------------- |
|
684 |
|
685 rv = blockFile->Open(localFile, 256); |
|
686 if (NS_FAILED(rv)) { |
|
687 printf("Test 16: failed (Open returned: 0x%.8x)\n", rv); |
|
688 goto exit; |
|
689 } |
|
690 |
|
691 char * one = new char[256 * 1]; |
|
692 char * two = new char[256 * 2]; |
|
693 char * three = new char[256 * 3]; |
|
694 char * four = new char[256 * 4]; |
|
695 if (!one || !two || !three || !four) { |
|
696 printf("Test 16: failed - out of memory\n"); |
|
697 rv = NS_ERROR_OUT_OF_MEMORY; |
|
698 goto exit; |
|
699 } |
|
700 |
|
701 memset(one, 1, 256); |
|
702 memset(two, 2, 256 * 2); |
|
703 memset(three, 3, 256 * 3); |
|
704 memset(four, 4, 256 * 4); |
|
705 |
|
706 startBlock = blockFile->AllocateBlocks(1); |
|
707 if (startBlock != 0) { |
|
708 printf("Test 16: failed (AllocateBlocks(1) failed)\n"); |
|
709 goto exit; |
|
710 } |
|
711 |
|
712 rv = blockFile->WriteBlocks(one, startBlock, 1); |
|
713 if (NS_FAILED(rv)) { |
|
714 printf("Test 16: failed (WriteBlocks(1) returned 0x%.8x)\n", rv); |
|
715 goto exit; |
|
716 } |
|
717 |
|
718 startBlock = blockFile->AllocateBlocks(2); |
|
719 if (startBlock != 1) { // starting with empy map, this allocation should begin at block 1 |
|
720 printf("Test 16: failed (AllocateBlocks(2) failed)\n"); |
|
721 goto exit; |
|
722 } |
|
723 |
|
724 rv = blockFile->WriteBlocks(two, startBlock, 2); |
|
725 if (NS_FAILED(rv)) { |
|
726 printf("Test 16: failed (WriteBlocks(2) returned 0x%.8x)\n", rv); |
|
727 goto exit; |
|
728 } |
|
729 |
|
730 startBlock = blockFile->AllocateBlocks(3); |
|
731 if (startBlock != 4) { // starting with empy map, this allocation should begin at block 4 |
|
732 printf("Test 16: failed (AllocateBlocks(3) failed)\n"); |
|
733 goto exit; |
|
734 } |
|
735 |
|
736 rv = blockFile->WriteBlocks(three, startBlock, 3); |
|
737 if (NS_FAILED(rv)) { |
|
738 printf("Test 16: failed (WriteBlocks(3) returned 0x%.8x)\n", rv); |
|
739 goto exit; |
|
740 } |
|
741 |
|
742 startBlock = blockFile->AllocateBlocks(4); |
|
743 if (startBlock != 8) { // starting with empy map, this allocation should begin at block 8 |
|
744 printf("Test 16: failed (AllocateBlocks(4) failed)\n"); |
|
745 goto exit; |
|
746 } |
|
747 |
|
748 rv = blockFile->WriteBlocks(four, startBlock, 4); |
|
749 if (NS_FAILED(rv)) { |
|
750 printf("Test 16: failed (WriteBlocks(4) returned 0x%.8x)\n", rv); |
|
751 goto exit; |
|
752 } |
|
753 |
|
754 printf("Test 16: passed\n"); |
|
755 |
|
756 |
|
757 //---------------------------------------------------------------- |
|
758 // Test 17: ReadBlocks |
|
759 //---------------------------------------------------------------- |
|
760 |
|
761 rv = blockFile->ReadBlocks(one, 0, 1); |
|
762 if (NS_FAILED(rv)) { |
|
763 printf("Test 17: failed (ReadBlocks(1) returned 0x%.8x)\n", rv); |
|
764 goto exit; |
|
765 } |
|
766 |
|
767 // Verify buffer |
|
768 for (i = 0; i < 256; i++) { |
|
769 if (one[i] != 1) { |
|
770 printf("Test 17: failed (verifying buffer 1)\n"); |
|
771 rv = NS_ERROR_FAILURE; |
|
772 goto exit; |
|
773 } |
|
774 } |
|
775 |
|
776 rv = blockFile->ReadBlocks(two, 1, 2); |
|
777 if (NS_FAILED(rv)) { |
|
778 printf("Test 17: failed (ReadBlocks(2) returned 0x%.8x)\n", rv); |
|
779 goto exit; |
|
780 } |
|
781 |
|
782 // Verify buffer |
|
783 for (i = 0; i < 256 * 2; i++) { |
|
784 if (two[i] != 2) { |
|
785 printf("Test 17: failed (verifying buffer 2)\n"); |
|
786 rv = NS_ERROR_FAILURE; |
|
787 goto exit; |
|
788 } |
|
789 } |
|
790 |
|
791 rv = blockFile->ReadBlocks(three, 4, 3); |
|
792 if (NS_FAILED(rv)) { |
|
793 printf("Test 17: failed (ReadBlocks(3) returned 0x%.8x)\n", rv); |
|
794 goto exit; |
|
795 } |
|
796 |
|
797 // Verify buffer |
|
798 for (i = 0; i < 256 * 3; i++) { |
|
799 if (three[i] != 3) { |
|
800 printf("Test 17: failed (verifying buffer 3)\n"); |
|
801 rv = NS_ERROR_FAILURE; |
|
802 goto exit; |
|
803 } |
|
804 } |
|
805 |
|
806 rv = blockFile->ReadBlocks(four, 8, 4); |
|
807 if (NS_FAILED(rv)) { |
|
808 printf("Test 17: failed (ReadBlocks(4) returned 0x%.8x)\n", rv); |
|
809 goto exit; |
|
810 } |
|
811 |
|
812 // Verify buffer |
|
813 for (i = 0; i < 256 * 4; i++) { |
|
814 if (four[i] != 4) { |
|
815 printf("Test 17: failed (verifying buffer 4)\n"); |
|
816 rv = NS_ERROR_FAILURE; |
|
817 goto exit; |
|
818 } |
|
819 } |
|
820 |
|
821 rv = blockFile->Close(); |
|
822 if (NS_FAILED(rv)) { |
|
823 printf("Test 17: failed (Close returned: 0x%.8x)\n", rv); |
|
824 goto exit; |
|
825 } |
|
826 |
|
827 printf("Test 17: passed\n"); |
|
828 |
|
829 |
|
830 //---------------------------------------------------------------- |
|
831 // Test 18: ValidateFile (open existing file with blocks allocated) |
|
832 //---------------------------------------------------------------- |
|
833 rv = blockFile->Open(localFile, 256); |
|
834 if (NS_FAILED(rv)) { |
|
835 printf("Test 18: failed (Open returned: 0x%.8x)\n", rv); |
|
836 goto exit; |
|
837 } |
|
838 |
|
839 rv = blockFile->Close(); |
|
840 if (NS_FAILED(rv)) { |
|
841 printf("Test 18: failed (Close returned: 0x%.8x)\n", rv); |
|
842 goto exit; |
|
843 } |
|
844 |
|
845 printf("Test 18: passed\n"); |
|
846 |
|
847 //---------------------------------------------------------------- |
|
848 // Test 19: WriteBlocks/ReadBlocks stress |
|
849 //---------------------------------------------------------------- |
|
850 |
|
851 rv = StressTest(localFile, 19, false); |
|
852 if (NS_FAILED(rv)) |
|
853 goto exit; |
|
854 |
|
855 printf("Test 19: passed\n"); |
|
856 |
|
857 |
|
858 exit: |
|
859 |
|
860 if (currentDirPath) |
|
861 nsMemory::Free(currentDirPath); |
|
862 } // this scopes the nsCOMPtrs |
|
863 // no nsCOMPtrs are allowed to be alive when you call NS_ShutdownXPCOM |
|
864 if (NS_FAILED(rv)) |
|
865 printf("Test failed: 0x%.8x\n", rv); |
|
866 |
|
867 rv = NS_ShutdownXPCOM(nullptr); |
|
868 NS_ASSERTION(NS_SUCCEEDED(rv), "NS_ShutdownXPCOM failed"); |
|
869 |
|
870 printf("XPCOM shut down.\n\n"); |
|
871 return 0; |
|
872 } |
|
873 |