50ae0b4badd7e171fb075572ed7a738d4d120b11
[openafs.git] / src / WINNT / afsd / cm_memmap.c
1 #include <windows.h>
2 #include "afsd.h"
3 #include "cm_memmap.h"
4
5 extern void afsi_log(char *pattern, ...);
6 extern DWORD cm_ValidateCache;
7
8 DWORD
9 GranularityAdjustment(DWORD size)
10 {
11     SYSTEM_INFO sysInfo;
12     static DWORD dwGranularity = 0;
13
14     if ( !dwGranularity ) {
15         GetSystemInfo(&sysInfo);
16         afsi_log("Granularity - %lX", sysInfo.dwAllocationGranularity);
17         dwGranularity = sysInfo.dwAllocationGranularity;
18     }
19
20     size = (size + (dwGranularity - 1)) & ~(dwGranularity - 1);
21     return size;
22 }
23
24 DWORD 
25 ComputeSizeOfConfigData(void)
26 {
27     DWORD size;
28     size = sizeof(cm_config_data_t);
29     return size;
30 }
31
32 DWORD
33 ComputeSizeOfVolumes(DWORD maxvols)
34 {
35     DWORD size;
36     size = maxvols * sizeof(cm_volume_t);
37     return size;
38 }
39
40 DWORD
41 ComputeSizeOfCells(DWORD maxcells)
42 {
43     DWORD size;
44     size = maxcells * sizeof(cm_cell_t);
45     return size;
46 }
47
48 DWORD 
49 ComputeSizeOfACLCache(DWORD stats)
50 {
51     DWORD size;
52     size = 2 * (stats + 10) * sizeof(cm_aclent_t);
53     return size;
54 }
55
56 DWORD 
57 ComputeSizeOfSCache(DWORD stats)
58 {
59     DWORD size;
60     size = (stats + 10) * sizeof(cm_scache_t);
61     return size;
62 }
63
64 DWORD 
65 ComputeSizeOfSCacheHT(DWORD stats)
66 {
67     DWORD size;
68     size = (stats + 10) / 2 * sizeof(cm_scache_t *);;
69     return size;
70 }
71
72 DWORD 
73 ComputeSizeOfDNLCache(void)
74 {
75     DWORD size;
76     size = NHSIZE * sizeof(cm_nc_t *) + NCSIZE * sizeof(cm_nc_t);
77     return size;
78 }
79
80 DWORD 
81 ComputeSizeOfDataBuffers(DWORD cacheBlocks, DWORD blockSize)
82 {
83     DWORD size;
84     size = cacheBlocks * blockSize;
85     return size;
86 }
87
88 DWORD 
89 ComputeSizeOfDataHT(void)
90 {
91     DWORD size;
92     size = osi_PrimeLessThan(CM_BUF_HASHSIZE) * sizeof(cm_buf_t *);
93     return size;
94 }
95
96 DWORD 
97 ComputeSizeOfDataHeaders(DWORD cacheBlocks)
98 {
99     DWORD size;
100     size = cacheBlocks * sizeof(cm_buf_t);
101     return size;
102 }
103
104 DWORD
105 ComputeSizeOfMappingFile(DWORD stats, DWORD maxVols, DWORD maxCells, DWORD chunkSize, DWORD cacheBlocks, DWORD blockSize)
106 {
107     DWORD size;
108     
109     size       =  ComputeSizeOfConfigData()
110                +  ComputeSizeOfVolumes(maxVols) 
111                +  ComputeSizeOfCells(maxCells) 
112                +  ComputeSizeOfACLCache(stats)
113                +  ComputeSizeOfSCache(stats)
114                +  ComputeSizeOfSCacheHT(stats)
115                +  ComputeSizeOfDNLCache()
116                +  ComputeSizeOfDataBuffers(cacheBlocks, blockSize) 
117                +  2 * ComputeSizeOfDataHT() 
118                +  ComputeSizeOfDataHeaders(cacheBlocks);
119     return size;    
120 }
121
122 /* Create a security attribute structure suitable for use when the cache file
123  * is created.  What we mainly want is that only the administrator should be
124  * able to do anything with the file.  We create an ACL with only one entry,
125  * an entry that grants all rights to the administrator.
126  */
127 PSECURITY_ATTRIBUTES CreateCacheFileSA()
128 {
129     PSECURITY_ATTRIBUTES psa;
130     PSECURITY_DESCRIPTOR psd;
131     SID_IDENTIFIER_AUTHORITY authority = SECURITY_NT_AUTHORITY;
132     PSID AdminSID;
133     DWORD AdminSIDlength;
134     PACL AdminOnlyACL;
135     DWORD ACLlength;
136
137     /* Get Administrator SID */
138     AllocateAndInitializeSid(&authority, 2,
139                               SECURITY_BUILTIN_DOMAIN_RID,
140                               DOMAIN_ALIAS_RID_ADMINS,
141                               0, 0, 0, 0, 0, 0,
142                               &AdminSID);
143
144     /* Create Administrator-only ACL */
145     AdminSIDlength = GetLengthSid(AdminSID);
146     ACLlength = sizeof(ACL) + sizeof(ACCESS_ALLOWED_ACE)
147         + AdminSIDlength - sizeof(DWORD);
148     AdminOnlyACL = GlobalAlloc(GMEM_FIXED, ACLlength);
149     InitializeAcl(AdminOnlyACL, ACLlength, ACL_REVISION);
150     AddAccessAllowedAce(AdminOnlyACL, ACL_REVISION,
151                          STANDARD_RIGHTS_ALL | SPECIFIC_RIGHTS_ALL,
152                          AdminSID);
153
154     /* Create security descriptor */
155     psd = GlobalAlloc(GMEM_FIXED, sizeof(SECURITY_DESCRIPTOR));
156     InitializeSecurityDescriptor(psd, SECURITY_DESCRIPTOR_REVISION);
157     SetSecurityDescriptorDacl(psd, TRUE, AdminOnlyACL, FALSE);
158
159     /* Create security attributes structure */
160     psa = GlobalAlloc(GMEM_FIXED, sizeof(SECURITY_ATTRIBUTES));
161     psa->nLength = sizeof(SECURITY_ATTRIBUTES);
162     psa->lpSecurityDescriptor = psd;
163     psa->bInheritHandle = TRUE;
164
165     return psa;
166 }       
167
168
169 /* Free a security attribute structure created by CreateCacheFileSA() */
170 VOID FreeCacheFileSA(PSECURITY_ATTRIBUTES psa)
171 {
172     BOOL b1, b2;
173     PACL pAcl;
174
175     GetSecurityDescriptorDacl(psa->lpSecurityDescriptor, &b1, &pAcl, &b2);
176     GlobalFree(pAcl);
177     GlobalFree(psa->lpSecurityDescriptor);
178     GlobalFree(psa);
179 }       
180
181 static HANDLE hMemoryMappedFile = NULL;
182
183 int
184 cm_IsCacheValid(void)
185 {
186     int rc = 1;
187
188     afsi_log("Validating Cache Contents");
189
190     if (cm_ValidateACLCache()) {
191         afsi_log("ACL Cache validation failure");
192         rc = 0;
193     } else if (cm_ValidateDCache()) {
194         afsi_log("Data Cache validation failure");
195         rc = 0;
196     } else if (cm_ValidateVolume()) {
197         afsi_log("Volume validation failure");
198         rc = 0;
199     } else if (cm_ValidateCell()) {
200         afsi_log("Cell validation failure");
201         rc = 0;
202     } else if (cm_ValidateSCache()) {
203         afsi_log("Stat Cache validation failure");
204         rc = 0;
205     }
206
207     return rc;
208 }
209
210 int
211 cm_ShutdownMappedMemory(void)
212 {
213     cm_config_data_t * config_data_p = (cm_config_data_t *)cm_data.baseAddress;
214     int dirty = 0;
215
216     cm_ShutdownDCache();
217     cm_ShutdownSCache();
218     cm_ShutdownACLCache();
219     cm_ShutdownCell();
220     cm_ShutdownVolume();
221
222     if (cm_ValidateCache == 2)
223         dirty = !cm_IsCacheValid();
224
225     *config_data_p = cm_data;
226     config_data_p->dirty = dirty;
227     UnmapViewOfFile(config_data_p);
228     CloseHandle(hMemoryMappedFile);
229     hMemoryMappedFile = NULL;
230
231     afsi_log("Memory Mapped File has been closed");
232 }
233
234 int
235 cm_ValidateMappedMemory(char * cachePath)
236 {
237     HANDLE hf = INVALID_HANDLE_VALUE, hm;
238     PSECURITY_ATTRIBUTES psa;
239     BY_HANDLE_FILE_INFORMATION fileInfo;
240     int newFile = 1;
241     DWORD mappingSize;
242     char * baseAddress = NULL;
243     cm_config_data_t * config_data_p;
244         
245     psa = CreateCacheFileSA();
246     hf = CreateFile( cachePath,
247                      GENERIC_READ | GENERIC_WRITE,
248                      FILE_SHARE_READ | FILE_SHARE_WRITE,
249                      psa,
250                      OPEN_EXISTING,
251                      FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | 
252                      FILE_ATTRIBUTE_NOT_CONTENT_INDEXED | FILE_FLAG_RANDOM_ACCESS,
253                      NULL);
254     FreeCacheFileSA(psa);
255
256     if (hf == INVALID_HANDLE_VALUE) {
257         fprintf(stderr, "Error creating cache file \"%s\" error %d\n", 
258                  cachePath, GetLastError());
259         return CM_ERROR_INVAL;
260     }
261
262     /* The file is being re-used; check to see if the existing data can be reused */
263     if ( !GetFileInformationByHandle(hf, &fileInfo) ) {
264         CloseHandle(hf);
265         fprintf(stderr, "Unable to obtain File Information\n");
266         return CM_ERROR_INVAL;
267     }
268
269     afsi_log("Existing File Size: %08X:%08X",
270               fileInfo.nFileSizeHigh,
271               fileInfo.nFileSizeLow);
272             
273     hm = CreateFileMapping( hf,
274                             NULL,
275                             PAGE_READWRITE,
276                             0, 
277                             sizeof(cm_config_data_t),
278                             NULL);
279     if (hm == NULL) {
280         if (GetLastError() == ERROR_DISK_FULL) {
281             fprintf(stderr, "Error creating file mapping for \"%s\": disk full (%lX)\n",
282                      cachePath, sizeof(cm_config_data_t));
283
284             hm = CreateFileMapping( hf,
285                                     NULL,
286                                     PAGE_READWRITE,
287                                     0, 
288                                     fileInfo.nFileSizeLow,
289                                     NULL);
290             if (hm == NULL) {
291                 if (GetLastError() == ERROR_DISK_FULL) {
292                     CloseHandle(hf);
293                     return CM_ERROR_TOOMANYBUFS;
294                 } else {
295                     fprintf(stderr,"Error creating file mapping for \"%s\": %d\n",
296                               cachePath, GetLastError());
297                     CloseHandle(hf);
298                     return CM_ERROR_INVAL;
299                 }
300             } else {
301                 fprintf(stderr, "Retry with file size (%lX) succeeds", 
302                          fileInfo.nFileSizeLow);
303             }
304         } else {
305             afsi_log("Error creating file mapping for \"%s\": %d",
306                       cachePath, GetLastError());
307             CloseHandle(hf);
308             return CM_ERROR_INVAL;
309         }
310     }
311
312     config_data_p = MapViewOfFile( hm,
313                                    FILE_MAP_READ,
314                                    0, 0,   
315                                    sizeof(cm_config_data_t));
316     if ( config_data_p == NULL ) {
317         fprintf(stderr, "Unable to MapViewOfFile\n");
318         if (hf != INVALID_HANDLE_VALUE)
319             CloseHandle(hf);
320         CloseHandle(hm);
321         return CM_ERROR_INVAL;
322     }
323
324     if ( config_data_p->dirty ) {
325         fprintf(stderr, "Previous session terminated prematurely\n");
326         UnmapViewOfFile(config_data_p);
327         CloseHandle(hm);               
328         CloseHandle(hf);
329         return CM_ERROR_INVAL;
330     }
331
332     mappingSize = config_data_p->bufferSize;
333     baseAddress = config_data_p->baseAddress;
334     UnmapViewOfFile(config_data_p);
335     CloseHandle(hm);
336
337     hm = CreateFileMapping( hf,
338                             NULL,
339                             PAGE_READWRITE,
340                             0, mappingSize,
341                             NULL);
342     if (hm == NULL) {
343         if (GetLastError() == ERROR_DISK_FULL) {
344             fprintf(stderr, "Error creating file mapping for \"%s\": disk full [2]\n",
345                   cachePath);
346             CloseHandle(hf);
347             return CM_ERROR_TOOMANYBUFS;
348         }
349         fprintf(stderr, "Error creating file mapping for \"%s\": %d\n",
350                 cachePath, GetLastError());
351         CloseHandle(hf);
352         return CM_ERROR_INVAL;
353     }
354     
355     baseAddress = MapViewOfFileEx( hm,
356                                    FILE_MAP_ALL_ACCESS,
357                                    0, 0,   
358                                    mappingSize,
359                                    baseAddress );
360     if (baseAddress == NULL) {
361         fprintf(stderr, "Error mapping view of file: %d\n", GetLastError());
362         baseAddress = MapViewOfFile( hm,
363                                      FILE_MAP_ALL_ACCESS,
364                                      0, 0,   
365                                      mappingSize );
366         if (baseAddress == NULL) {
367             CloseHandle(hm);
368             if (hf != INVALID_HANDLE_VALUE)
369                 CloseHandle(hf);
370             return CM_ERROR_INVAL;
371         }
372         fprintf(stderr, "Unable to re-load cache file at base address\n");
373         CloseHandle(hm);
374         if (hf != INVALID_HANDLE_VALUE)
375             CloseHandle(hf);
376         return CM_ERROR_INVAL;
377     }
378     CloseHandle(hm);
379
380     config_data_p = (cm_config_data_t *) baseAddress;
381
382     fprintf(stderr,"AFS Cache data:\n");
383     fprintf(stderr,"  Base Address   = %lX\n",baseAddress);
384     fprintf(stderr,"  stats          = %d\n", config_data_p->stats);
385     fprintf(stderr,"  chunkSize      = %d\n", config_data_p->chunkSize);
386     fprintf(stderr,"  blockSize      = %d\n", config_data_p->blockSize);
387     fprintf(stderr,"  bufferSize     = %d\n", config_data_p->bufferSize);
388     fprintf(stderr,"  cacheType      = %d\n", config_data_p->cacheType);
389     fprintf(stderr,"  currentVolumes = %d\n", config_data_p->currentVolumes);
390     fprintf(stderr,"  maxVolumes     = %d\n", config_data_p->maxVolumes);
391     fprintf(stderr,"  currentCells   = %d\n", config_data_p->currentCells);
392     fprintf(stderr,"  maxCells       = %d\n", config_data_p->maxCells);
393     fprintf(stderr,"  hashTableSize  = %d\n", config_data_p->hashTableSize );
394     fprintf(stderr,"  currentSCaches = %d\n", config_data_p->currentSCaches);
395     fprintf(stderr,"  maxSCaches     = %d\n", config_data_p->maxSCaches);
396     cm_data = *config_data_p;      
397
398     // perform validation of persisted data structures
399     // if there is a failure, start from scratch
400     if (!cm_IsCacheValid()) {
401         fprintf(stderr,"Cache file fails validation test\n");
402         UnmapViewOfFile(config_data_p);
403         return CM_ERROR_INVAL;
404     }
405
406     fprintf(stderr,"Cache passes validation test\n");
407     UnmapViewOfFile(config_data_p);
408     return 0;
409 }
410
411 int
412 cm_InitMappedMemory(DWORD virtualCache, char * cachePath, DWORD stats, DWORD chunkSize, DWORD cacheBlocks)
413 {
414     HANDLE hf = INVALID_HANDLE_VALUE, hm;
415     PSECURITY_ATTRIBUTES psa;
416     int newFile = 1;
417     DWORD mappingSize;
418     DWORD maxVols = stats/2;
419     DWORD maxCells = stats/4;
420     char * baseAddress = NULL;
421     cm_config_data_t * config_data_p;
422     char * p;
423
424     mappingSize = ComputeSizeOfMappingFile(stats, maxVols, maxCells, chunkSize, cacheBlocks, CM_CONFIGDEFAULT_BLOCKSIZE);
425
426     if ( !virtualCache ) {
427         psa = CreateCacheFileSA();
428         hf = CreateFile( cachePath,
429                          GENERIC_READ | GENERIC_WRITE,
430                          FILE_SHARE_READ | FILE_SHARE_WRITE,
431                          psa,
432                          OPEN_ALWAYS,
433                          FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | 
434                          FILE_ATTRIBUTE_NOT_CONTENT_INDEXED | FILE_FLAG_RANDOM_ACCESS,
435                          NULL);
436         FreeCacheFileSA(psa);
437
438         if (hf == INVALID_HANDLE_VALUE) {
439             afsi_log("Error creating cache file \"%s\" error %d", 
440                       cachePath, GetLastError());
441             return CM_ERROR_INVAL;
442         }
443         
444         if ( GetLastError() == ERROR_ALREADY_EXISTS ) {
445             BY_HANDLE_FILE_INFORMATION fileInfo;
446
447             /* The file is being re-used; check to see if the existing data can be reused */
448             afsi_log("Cache File \"%s\" already exists", cachePath);
449
450             if ( GetFileInformationByHandle(hf, &fileInfo) ) {
451                 afsi_log("Existing File Size: %08X:%08X",
452                           fileInfo.nFileSizeHigh,
453                           fileInfo.nFileSizeLow);
454                 if (fileInfo.nFileSizeLow > GranularityAdjustment(mappingSize)) {
455                     psa = CreateCacheFileSA();
456                     hf = CreateFile( cachePath,
457                                      GENERIC_READ | GENERIC_WRITE,
458                                      FILE_SHARE_READ | FILE_SHARE_WRITE,
459                                      psa,
460                                      TRUNCATE_EXISTING,
461                                      FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_SYSTEM | 
462                                      FILE_ATTRIBUTE_NOT_CONTENT_INDEXED | FILE_FLAG_RANDOM_ACCESS,
463                                      NULL);
464                     FreeCacheFileSA(psa);
465
466                     if (hf == INVALID_HANDLE_VALUE) {
467                         afsi_log("Error creating cache file \"%s\" error %d", 
468                                   cachePath, GetLastError());
469                         return CM_ERROR_INVAL;
470                     }
471
472                     GetFileInformationByHandle(hf, &fileInfo);
473                     afsi_log("     New File Size: %08X:%08X",
474                               fileInfo.nFileSizeHigh,
475                               fileInfo.nFileSizeLow);
476                 }
477
478             }
479
480             hm = CreateFileMapping( hf,
481                                     NULL,
482                                     PAGE_READWRITE,
483                                     0, 
484                                     sizeof(cm_config_data_t),
485                                     NULL);
486             if (hm == NULL) {
487                 if (GetLastError() == ERROR_DISK_FULL) {
488                     afsi_log("Error creating file mapping for \"%s\": disk full (%lX)",
489                               cachePath, sizeof(cm_config_data_t));
490
491                     hm = CreateFileMapping( hf,
492                                             NULL,
493                                             PAGE_READWRITE,
494                                             0, 
495                                             mappingSize,
496                                             NULL);
497                     if (hm == NULL) {
498                         if (GetLastError() == ERROR_DISK_FULL) {
499                             CloseHandle(hf);
500                             return CM_ERROR_TOOMANYBUFS;
501                         } else {
502                             afsi_log("Error creating file mapping for \"%s\": %d",
503                                       cachePath, GetLastError());
504                             CloseHandle(hf);
505                             return CM_ERROR_INVAL;
506                         }
507                     } else {
508                         afsi_log("Retry with mapping size (%lX) succeeds", mappingSize);
509                     }
510                 } else {
511                     afsi_log("Error creating file mapping for \"%s\": %d",
512                               cachePath, GetLastError());
513                     CloseHandle(hf);
514                     return CM_ERROR_INVAL;
515                 }
516             }
517
518             config_data_p = MapViewOfFile( hm,
519                                            FILE_MAP_READ,
520                                            0, 0,   
521                                            sizeof(cm_config_data_t));
522             if ( config_data_p == NULL ) {
523                 if (hf != INVALID_HANDLE_VALUE)
524                     CloseHandle(hf);
525                 CloseHandle(hm);
526                 return CM_ERROR_INVAL;
527             }
528
529             if ( config_data_p->size == sizeof(cm_config_data_t) &&
530                  config_data_p->magic == CM_CONFIG_DATA_MAGIC &&
531                  config_data_p->stats == stats &&
532                  config_data_p->maxVolumes == maxVols &&
533                  config_data_p->maxCells == maxCells &&
534                  config_data_p->chunkSize == chunkSize &&
535                  config_data_p->buf_nbuffers == cacheBlocks &&
536                  config_data_p->blockSize == CM_CONFIGDEFAULT_BLOCKSIZE &&
537                  config_data_p->bufferSize == mappingSize)
538             {
539                 if ( config_data_p->dirty ) {
540                     afsi_log("Previous session terminated prematurely");
541                 } else {
542                     baseAddress = config_data_p->baseAddress;
543                     newFile = 0;
544                 }
545             } else {
546                 afsi_log("Configuration changed or Not a persistent cache file");
547             }
548             UnmapViewOfFile(config_data_p);
549             CloseHandle(hm);
550         }
551     }
552
553     hm = CreateFileMapping( hf,
554                             NULL,
555                             PAGE_READWRITE,
556                             0, mappingSize,
557                             NULL);
558     if (hm == NULL) {
559         if (GetLastError() == ERROR_DISK_FULL) {
560             afsi_log("Error creating file mapping for \"%s\": disk full [2]",
561                       cachePath);
562             return CM_ERROR_TOOMANYBUFS;
563         }
564         afsi_log("Error creating file mapping for \"%s\": %d",
565                   cachePath, GetLastError());
566         return CM_ERROR_INVAL;
567     }
568     baseAddress = MapViewOfFileEx( hm,
569                                    FILE_MAP_ALL_ACCESS,
570                                    0, 0,   
571                                    mappingSize,
572                                    baseAddress );
573     if (baseAddress == NULL) {
574         afsi_log("Error mapping view of file: %d", GetLastError());
575         baseAddress = MapViewOfFile( hm,
576                                      FILE_MAP_ALL_ACCESS,
577                                      0, 0,   
578                                      mappingSize );
579         if (baseAddress == NULL) {
580             if (hf != INVALID_HANDLE_VALUE)
581                 CloseHandle(hf);
582             CloseHandle(hm);
583             return CM_ERROR_INVAL;
584         }
585         newFile = 1;
586     }
587     CloseHandle(hm);
588
589     config_data_p = (cm_config_data_t *) baseAddress;
590
591     if (!newFile) {
592         afsi_log("Reusing existing AFS Cache data: Base Address = %lX",baseAddress);
593         cm_data = *config_data_p;      
594
595         // perform validation of persisted data structures
596         // if there is a failure, start from scratch
597         if (cm_ValidateCache && !cm_IsCacheValid()) {
598             newFile = 1;
599         }
600     }
601
602     if ( newFile ) {
603         afsi_log("Building AFS Cache from scratch");
604         cm_data.size = sizeof(cm_config_data_t);
605         cm_data.magic = CM_CONFIG_DATA_MAGIC;
606         cm_data.baseAddress = baseAddress;
607         cm_data.stats = stats;
608         cm_data.chunkSize = chunkSize;
609         cm_data.blockSize = CM_CONFIGDEFAULT_BLOCKSIZE;
610         cm_data.bufferSize = mappingSize;
611         cm_data.hashTableSize = osi_PrimeLessThan(stats / 2 + 1);
612         if (virtualCache) {
613             cm_data.cacheType = CM_BUF_CACHETYPE_VIRTUAL;
614         } else {
615             cm_data.cacheType = CM_BUF_CACHETYPE_FILE;
616         }
617
618         cm_data.buf_nbuffers = cacheBlocks;
619         cm_data.buf_nOrigBuffers = 0;
620         cm_data.buf_blockSize = CM_BUF_BLOCKSIZE;
621         cm_data.buf_hashSize = CM_BUF_HASHSIZE;
622
623         cm_data.mountRootGen = time(NULL);
624
625         baseAddress += ComputeSizeOfConfigData();
626         cm_data.volumeBaseAddress = (cm_volume_t *) baseAddress;
627         baseAddress += ComputeSizeOfVolumes(maxVols);
628         cm_data.cellBaseAddress = (cm_cell_t *) baseAddress;
629         baseAddress += ComputeSizeOfCells(maxCells);
630         cm_data.aclBaseAddress = (cm_aclent_t *) baseAddress;
631         baseAddress += ComputeSizeOfACLCache(stats);
632         cm_data.scacheBaseAddress = (cm_scache_t *) baseAddress;
633         baseAddress += ComputeSizeOfSCache(stats);
634         cm_data.hashTablep = (cm_scache_t **) baseAddress;
635         baseAddress += ComputeSizeOfSCacheHT(stats);
636         cm_data.dnlcBaseAddress = (cm_nc_t *) baseAddress;
637         baseAddress += ComputeSizeOfDNLCache();
638         cm_data.buf_hashTablepp = (cm_buf_t **) baseAddress;
639         baseAddress += ComputeSizeOfDataHT();
640         cm_data.buf_fileHashTablepp = (cm_buf_t **) baseAddress;
641         baseAddress += ComputeSizeOfDataHT();
642         cm_data.bufHeaderBaseAddress = (cm_buf_t *) baseAddress;
643         baseAddress += ComputeSizeOfDataHeaders(cacheBlocks);
644         cm_data.bufDataBaseAddress = (char *) baseAddress;
645         baseAddress += ComputeSizeOfDataBuffers(cacheBlocks, CM_CONFIGDEFAULT_BLOCKSIZE);
646         cm_data.bufEndOfData = (char *) baseAddress;
647
648         cm_data.fakeDirVersion = 0x8;
649
650         UuidCreate((UUID *)&cm_data.Uuid);
651     }
652
653     UuidToString((UUID *)&cm_data.Uuid, &p);
654     afsi_log("Initializing Uuid to %s",p);
655     RpcStringFree(&p);
656
657     afsi_log("Initializing Volume Data");
658     cm_InitVolume(newFile, maxVols);
659
660     afsi_log("Initializing Cell Data");
661     cm_InitCell(newFile, maxCells);
662
663     afsi_log("Initializing ACL Data");
664     cm_InitACLCache(newFile, 2*stats);
665
666     afsi_log("Initializing Stat Data");
667     cm_InitSCache(newFile, stats);
668         
669     afsi_log("Initializing Data Buffers");
670     cm_InitDCache(newFile, 0, cacheBlocks);
671
672     *config_data_p = cm_data;
673     config_data_p->dirty = 1;
674     
675     hMemoryMappedFile = hf;
676     afsi_log("Cache Initialization Complete");
677     return 0;
678 }
679