2 * ADF Library. (C) 1997-1999 Laurent Clevy
20 extern struct Env adfEnv
;
26 RETCODE
adfUpdateBitmap(struct Volume
*vol
)
29 struct bRootBlock root
;
31 /*printf("adfUpdateBitmap\n");*/
33 if (adfReadRootBlock(vol
, vol
->rootBlock
,&root
)!=RC_OK
)
36 root
.bmFlag
= BM_INVALID
;
37 if (adfWriteRootBlock(vol
,vol
->rootBlock
,&root
)!=RC_OK
)
40 for(i
=0; i
<vol
->bitmapSize
; i
++)
41 if (vol
->bitmapBlocksChg
[i
]) {
42 if (adfWriteBitmapBlock(vol
, vol
->bitmapBlocks
[i
], vol
->bitmapTable
[i
])!=RC_OK
)
44 vol
->bitmapBlocksChg
[i
] = FALSE
;
47 root
.bmFlag
= BM_VALID
;
48 adfTime2AmigaTime(adfGiveCurrentTime(),&(root
.days
),&(root
.mins
),&(root
.ticks
));
49 if (adfWriteRootBlock(vol
,vol
->rootBlock
,&root
)!=RC_OK
)
60 ULONG
adfCountFreeBlocks(struct Volume
* vol
)
66 for(j
=vol
->reservedBlocks
; j
<vol
->totalBlocks
; j
++)
67 if ( adfIsBlockFree(vol
,j
) )
78 RETCODE
adfReadBitmap(struct Volume
* vol
, struct bRootBlock
* root
)
84 struct bBitmapExtBlock bmExt
;
86 nBlock
= vol
->totalBlocks
- vol
->reservedBlocks
;
88 mapSize
= nBlock
/ (127*32);
89 if ( (nBlock
%(127*32))!=0 )
91 vol
->bitmapSize
= mapSize
;
92 vol
->lastAlloc
= vol
->rootBlock
;
94 vol
->bitmapTable
= (struct bBitmapBlock
**) malloc(sizeof(struct bBitmapBlock
*)*mapSize
);
95 if (!vol
->bitmapTable
) {
96 (*adfEnv
.eFct
)("adfReadBitmap : malloc, vol->bitmapTable");
99 vol
->bitmapBlocks
= (SECTNUM
*) malloc(sizeof(SECTNUM
)*mapSize
);
100 if (!vol
->bitmapBlocks
) {
101 free(vol
->bitmapTable
);
102 (*adfEnv
.eFct
)("adfReadBitmap : malloc, vol->bitmapBlocks");
105 vol
->bitmapBlocksChg
= (BOOL
*) malloc(sizeof(BOOL
)*mapSize
);
106 if (!vol
->bitmapBlocksChg
) {
107 free(vol
->bitmapTable
); free(vol
->bitmapBlocks
);
108 (*adfEnv
.eFct
)("adfReadBitmap : malloc, vol->bitmapBlocks");
111 for(i
=0; i
<mapSize
; i
++) {
112 vol
->bitmapBlocksChg
[i
] = FALSE
;
114 vol
->bitmapTable
[i
] = (struct bBitmapBlock
*)malloc(sizeof(struct bBitmapBlock
));
115 if (!vol
->bitmapTable
[i
]) {
116 free(vol
->bitmapBlocksChg
); free(vol
->bitmapBlocks
);
118 free(vol
->bitmapTable
[j
]);
119 free(vol
->bitmapTable
);
120 (*adfEnv
.eFct
)("adfReadBitmap : malloc, vol->bitmapBlocks");
126 /* bitmap pointers in rootblock : 0 <= i <BM_SIZE */
127 while(i
<BM_SIZE
&& root
->bmPages
[i
]!=0) {
128 vol
->bitmapBlocks
[j
] = nSect
= root
->bmPages
[i
];
129 if ( !isSectNumValid(vol
,nSect
) ) {
130 (*adfEnv
.wFct
)("adfReadBitmap : sector out of range");
133 if (adfReadBitmapBlock(vol
, nSect
, vol
->bitmapTable
[j
])!=RC_OK
) {
141 /* bitmap pointers in bitmapExtBlock, j <= mapSize */
142 if (adfReadBitmapExtBlock(vol
, nSect
, &bmExt
)!=RC_OK
) {
147 while(i
<127 && j
<mapSize
) {
148 nSect
= bmExt
.bmPages
[i
];
149 if ( !isSectNumValid(vol
,nSect
) )
150 (*adfEnv
.wFct
)("adfReadBitmap : sector out of range");
151 vol
->bitmapBlocks
[j
] = nSect
;
153 if (adfReadBitmapBlock(vol
, nSect
, vol
->bitmapTable
[j
])!=RC_OK
) {
159 nSect
= bmExt
.nextBlock
;
165 static inline ULONG
sectorToMapMask(struct Volume
*vol
, SECTNUM nSect
, ULONG
**map
, int *pblock
)
171 nSect
-= vol
->reservedBlocks
;
172 sectOfMap
= nSect
& 0x1f;
176 indexInMap
= nSect
% 127;
178 *map
= &(vol
->bitmapTable
[ block
]->map
[ indexInMap
]);
182 return (1UL << (sectOfMap
& 0x1f));
189 BOOL
adfIsBlockFree(struct Volume
* vol
, SECTNUM nSect
)
193 mask
= sectorToMapMask(vol
, nSect
, &map
, NULL
);
195 // printf("C %08lx %c\n", (unsigned long)(vol->firstBlock + nSect) * 512, (*map & mask) ? '1' : '0');
197 return (*map
& mask
) ? 1 : 0;
205 void adfSetBlockFree(struct Volume
* vol
, SECTNUM nSect
)
210 mask
= sectorToMapMask(vol
, nSect
, &map
, &block
);
214 vol
->bitmapBlocksChg
[ block
] = TRUE
;
216 // printf("F 0x%08lx\n", (unsigned long)(vol->firstBlock + nSect) * 512);
224 void adfSetBlockUsed(struct Volume
* vol
, SECTNUM nSect
)
229 mask
= sectorToMapMask(vol
, nSect
, &map
, &block
);
233 vol
->bitmapBlocksChg
[ block
] = TRUE
;
235 // printf("A 0x%08lx\n", (unsigned long)(vol->firstBlock + nSect) * 512);
243 SECTNUM
adfGet1FreeBlock(struct Volume
*vol
) {
245 if (!adfGetFreeBlocks(vol
,1,block
))
255 BOOL
adfGetFreeBlocks(struct Volume
* vol
, int nbSect
, SECTNUM
* sectList
)
258 ULONG block
= vol
->lastAlloc
;
265 if ( adfIsBlockFree(vol
, block
) ) {
271 if (block
== vol
->lastAlloc
)
274 if (block
== vol
->totalBlocks
)
275 block
= vol
->reservedBlocks
;
278 for(i
=0; i
<nbSect
; i
++)
279 adfSetBlockUsed( vol
, sectList
[i
] );
281 vol
->lastAlloc
= sectList
[i
-1];
290 * create bitmap structure in vol
292 RETCODE
adfCreateBitmap(struct Volume
*vol
)
294 ULONG nBlock
, mapSize
;
297 nBlock
= vol
->totalBlocks
- vol
->reservedBlocks
;
299 mapSize
= nBlock
/ (127*32);
300 if ( (nBlock
%(127*32))!=0 )
302 vol
->bitmapSize
= mapSize
;
303 vol
->lastAlloc
= vol
->rootBlock
;
305 vol
->bitmapTable
= (struct bBitmapBlock
**)malloc( sizeof(struct bBitmapBlock
*)*mapSize
);
306 if (!vol
->bitmapTable
) {
307 (*adfEnv
.eFct
)("adfCreateBitmap : malloc, vol->bitmapTable");
311 vol
->bitmapBlocksChg
= (BOOL
*) malloc(sizeof(BOOL
)*mapSize
);
312 if (!vol
->bitmapBlocksChg
) {
313 free(vol
->bitmapTable
);
314 (*adfEnv
.eFct
)("adfCreateBitmap : malloc, vol->bitmapBlocksChg");
318 vol
->bitmapBlocks
= (SECTNUM
*) malloc(sizeof(SECTNUM
)*mapSize
);
319 if (!vol
->bitmapBlocks
) {
320 free(vol
->bitmapTable
); free(vol
->bitmapBlocksChg
);
321 (*adfEnv
.eFct
)("adfCreateBitmap : malloc, vol->bitmapBlocks");
325 for(i
=0; i
<mapSize
; i
++) {
326 vol
->bitmapTable
[i
] = (struct bBitmapBlock
*)malloc(sizeof(struct bBitmapBlock
));
327 if (!vol
->bitmapTable
[i
]) {
328 free(vol
->bitmapTable
); free(vol
->bitmapBlocksChg
);
330 free(vol
->bitmapTable
[j
]);
331 free(vol
->bitmapTable
);
332 (*adfEnv
.eFct
)("adfCreateBitmap : malloc");
337 for(i
=vol
->reservedBlocks
; i
< nBlock
; i
++)
338 adfSetBlockFree(vol
, i
);
340 adfSetBlockUsed(vol
, vol
->rootBlock
);
349 * write ext blocks and bitmap
351 * uses vol->bitmapSize,
353 RETCODE
adfWriteNewBitmap(struct Volume
*vol
)
355 struct bBitmapExtBlock bitme
;
356 SECTNUM
*bitExtBlock
;
361 struct bRootBlock root
;
363 sectList
=(SECTNUM
*)malloc(sizeof(SECTNUM
)*vol
->bitmapSize
);
365 (*adfEnv
.eFct
)("adfCreateBitmap : sectList");
369 /* Write out the in-root bitmap blocks */
370 if (adfReadRootBlock(vol
, vol
->rootBlock
, &root
)!=RC_OK
) {
375 n
= min( vol
->bitmapSize
, BM_SIZE
);
376 if (!adfGetFreeBlocks(vol
, n
, §List
[0])) {
382 root
.bmPages
[i
] = vol
->bitmapBlocks
[i
] = sectList
[i
];
386 /* for devices with more than 25*127 blocks == hards disks */
387 if (vol
->bitmapSize
>BM_SIZE
) {
388 nExtBlock
= ((vol
->bitmapSize
-BM_SIZE
)+126)/127;
390 bitExtBlock
=(SECTNUM
*)malloc(sizeof(SECTNUM
)*nExtBlock
);
393 adfEnv
.eFct("adfWriteNewBitmap : malloc failed");
397 if (!adfGetFreeBlocks(vol
, nExtBlock
, bitExtBlock
)) {
398 adfEnv
.eFct("adfWriteNewBitmap : can't get free Ext blocks");
399 free(sectList
); free(bitExtBlock
);
403 if (!adfGetFreeBlocks(vol
, vol
->bitmapSize
- n
, §List
[n
])) {
404 free(sectList
); free(bitExtBlock
);
409 root
.bmExt
= bitExtBlock
[ k
];
410 while( nBlock
<vol
->bitmapSize
) {
412 memset(&bitme
, 0, sizeof(bitme
));
413 while( i
<127 && nBlock
<vol
->bitmapSize
) {
414 bitme
.bmPages
[i
] = vol
->bitmapBlocks
[nBlock
] = sectList
[nBlock
];
419 bitme
.nextBlock
= bitExtBlock
[ k
+1 ];
422 if (adfWriteBitmapExtBlock(vol
, bitExtBlock
[ k
], &bitme
)!=RC_OK
) {
423 free(sectList
); free(bitExtBlock
);
433 if (adfWriteRootBlock(vol
,vol
->rootBlock
,&root
)!=RC_OK
)
445 adfReadBitmapBlock(struct Volume
* vol
, SECTNUM nSect
, struct bBitmapBlock
* bitm
)
447 unsigned char buf
[LOGICAL_BLOCK_SIZE
];
449 //printf("bitmap %ld\n",nSect);
450 if (adfReadBlock(vol
, nSect
, buf
)!=RC_OK
)
453 memcpy(bitm
, buf
, LOGICAL_BLOCK_SIZE
);
455 /* big to little = 68000 to x86 */
456 swapEndian((unsigned char*)bitm
, SWBL_BITMAP
);
459 if (bitm
->checkSum
!=adfNormalSum(buf
,0,LOGICAL_BLOCK_SIZE
))
460 (*adfEnv
.wFct
)("adfReadBitmapBlock : invalid checksum");
467 * adfWriteBitmapBlock
472 adfWriteBitmapBlock(struct Volume
* vol
, SECTNUM nSect
, struct bBitmapBlock
* bitm
)
474 unsigned char buf
[LOGICAL_BLOCK_SIZE
];
477 memcpy(buf
,bitm
,LOGICAL_BLOCK_SIZE
);
480 swapEndian(buf
, SWBL_BITMAP
);
483 newSum
= adfNormalSum(buf
, 0, LOGICAL_BLOCK_SIZE
);
486 /* dumpBlock((unsigned char*)buf);*/
487 if (adfWriteBlock(vol
, nSect
, (unsigned char*)buf
)!=RC_OK
)
495 * adfReadBitmapExtBlock
500 adfReadBitmapExtBlock(struct Volume
* vol
, SECTNUM nSect
, struct bBitmapExtBlock
* bitme
)
502 unsigned char buf
[LOGICAL_BLOCK_SIZE
];
504 if (adfReadBlock(vol
, nSect
, buf
)!=RC_OK
)
507 memcpy(bitme
, buf
, LOGICAL_BLOCK_SIZE
);
509 swapEndian((unsigned char*)bitme
, SWBL_BITMAP
);
517 * adfWriteBitmapExtBlock
521 adfWriteBitmapExtBlock(struct Volume
* vol
, SECTNUM nSect
, struct bBitmapExtBlock
* bitme
)
523 unsigned char buf
[LOGICAL_BLOCK_SIZE
];
525 memcpy(buf
,bitme
, LOGICAL_BLOCK_SIZE
);
528 swapEndian(buf
, SWBL_BITMAPE
);
531 /* dumpBlock((unsigned char*)buf);*/
532 if (adfWriteBlock(vol
, nSect
, (unsigned char*)buf
)!=RC_OK
)
543 void adfFreeBitmap(struct Volume
* vol
)
547 for(i
=0; i
<vol
->bitmapSize
; i
++)
548 free(vol
->bitmapTable
[i
]);
551 free(vol
->bitmapTable
);
552 vol
->bitmapTable
= 0;
554 free(vol
->bitmapBlocks
);
555 vol
->bitmapBlocks
= 0;
557 free(vol
->bitmapBlocksChg
);
558 vol
->bitmapBlocksChg
= 0;
562 /*#######################################################################################*/