6 * disk structure conversion routines
8 #define U8GET(p) ((p)[0])
9 #define U16GET(p) (((p)[0]<<8)|(p)[1])
10 #define U32GET(p) ((u32int)(((p)[0]<<24)|((p)[1]<<16)|((p)[2]<<8)|(p)[3]))
11 #define U64GET(p) (((u64int)U32GET(p)<<32)|(u64int)U32GET((p)+4))
13 #define U8PUT(p,v) (p)[0]=(v)&0xFF
14 #define U16PUT(p,v) (p)[0]=((v)>>8)&0xFF;(p)[1]=(v)&0xFF
15 #define U32PUT(p,v) (p)[0]=((v)>>24)&0xFF;(p)[1]=((v)>>16)&0xFF;(p)[2]=((v)>>8)&0xFF;(p)[3]=(v)&0xFF
16 #define U64PUT(p,v,t32) t32=(v)>>32;U32PUT(p,t32);t32=(v);U32PUT((p)+4,t32)
22 ArenaPartMagic, "ArenaPartMagic",
23 ArenaHeadMagic, "ArenaHeadMagic",
24 ArenaMagic, "ArenaMagic",
25 ISectMagic, "ISectMagic",
29 fmtmagic(char *s, u32int m)
33 for(i=0; i<nelem(magics); i++)
36 sprint(s, "0x%08lux", m);
41 unpackmagic(u8int *buf)
47 packmagic(u32int magic, u8int *buf)
53 unpackarenapart(ArenaPart *ap, u8int *buf)
62 if(m != ArenaPartMagic){
63 seterr(ECorrupt, "arena set has wrong magic number: %s expected ArenaPartMagic (%lux)", fmtmagic(fbuf, m), ArenaPartMagic);
67 ap->version = U32GET(p);
69 ap->blocksize = U32GET(p);
71 ap->arenabase = U32GET(p);
74 if(buf + ArenaPartSize != p)
75 sysfatal("unpackarenapart unpacked wrong amount");
81 packarenapart(ArenaPart *ap, u8int *buf)
87 U32PUT(p, ArenaPartMagic);
89 U32PUT(p, ap->version);
91 U32PUT(p, ap->blocksize);
93 U32PUT(p, ap->arenabase);
96 if(buf + ArenaPartSize != p)
97 sysfatal("packarenapart packed wrong amount");
103 unpackarena(Arena *arena, u8int *buf)
113 seterr(ECorrupt, "arena has wrong magic number: %s expected ArenaMagic (%lux)", fmtmagic(fbuf, m), m, ArenaMagic);
117 arena->version = U32GET(p);
119 namecp(arena->name, (char*)p);
121 arena->clumps = U32GET(p);
123 arena->cclumps = U32GET(p);
125 arena->ctime = U32GET(p);
127 arena->wtime = U32GET(p);
129 arena->used = U64GET(p);
131 arena->uncsize = U64GET(p);
133 arena->sealed = U8GET(p);
136 if(buf + ArenaSize != p)
137 sysfatal("unpackarena unpacked wrong amount");
143 packarena(Arena *arena, u8int *buf)
150 U32PUT(p, ArenaMagic);
152 U32PUT(p, arena->version);
154 namecp((char*)p, arena->name);
156 U32PUT(p, arena->clumps);
158 U32PUT(p, arena->cclumps);
160 U32PUT(p, arena->ctime);
162 U32PUT(p, arena->wtime);
164 U64PUT(p, arena->used, t32);
166 U64PUT(p, arena->uncsize, t32);
168 U8PUT(p, arena->sealed);
171 if(buf + ArenaSize != p)
172 sysfatal("packarena packed wrong amount");
178 unpackarenahead(ArenaHead *head, u8int *buf)
187 if(m != ArenaHeadMagic){
188 seterr(ECorrupt, "arena has wrong magic number: %s expected ArenaHeadMagic (%lux)",
189 fmtmagic(fbuf, m), ArenaHeadMagic);
193 head->version = U32GET(p);
195 namecp(head->name, (char*)p);
197 head->blocksize = U32GET(p);
199 head->size = U64GET(p);
202 if(buf + ArenaHeadSize != p)
203 sysfatal("unpackarenahead unpacked wrong amount");
209 packarenahead(ArenaHead *head, u8int *buf)
216 U32PUT(p, ArenaHeadMagic);
218 U32PUT(p, head->version);
220 namecp((char*)p, head->name);
222 U32PUT(p, head->blocksize);
224 U64PUT(p, head->size, t32);
227 if(buf + ArenaHeadSize != p)
228 sysfatal("packarenahead packed wrong amount");
236 if(w->encoding == ClumpENone){
237 if(w->info.size != w->info.uncsize){
238 seterr(ECorrupt, "uncompressed wad size mismatch");
241 }else if(w->encoding == ClumpECompress){
242 if(w->info.size >= w->info.uncsize){
243 seterr(ECorrupt, "compressed lump has inconsistent block sizes %d %d", w->info.size, w->info.uncsize);
247 seterr(ECorrupt, "clump has illegal encoding");
255 unpackclump(Clump *c, u8int *buf)
262 if(magic != ClumpMagic){
263 seterr(ECorrupt, "clump has bad magic number=%#8.8ux", magic);
268 c->info.type = vtfromdisktype(U8GET(p));
270 c->info.size = U16GET(p);
272 c->info.uncsize = U16GET(p);
274 scorecp(c->info.score, p);
277 c->encoding = U8GET(p);
279 c->creator = U32GET(p);
284 if(buf + ClumpSize != p)
285 sysfatal("unpackclump unpacked wrong amount");
287 return checkclump(c);
291 packclump(Clump *c, u8int *buf)
296 U32PUT(p, ClumpMagic);
299 U8PUT(p, vttodisktype(c->info.type));
301 U16PUT(p, c->info.size);
303 U16PUT(p, c->info.uncsize);
305 scorecp(p, c->info.score);
308 U8PUT(p, c->encoding);
310 U32PUT(p, c->creator);
315 if(buf + ClumpSize != p)
316 sysfatal("packclump packed wrong amount");
318 return checkclump(c);
322 unpackclumpinfo(ClumpInfo *ci, u8int *buf)
327 ci->type = vtfromdisktype(U8GET(p));
329 ci->size = U16GET(p);
331 ci->uncsize = U16GET(p);
333 scorecp(ci->score, p);
336 if(buf + ClumpInfoSize != p)
337 sysfatal("unpackclumpinfo unpacked wrong amount");
341 packclumpinfo(ClumpInfo *ci, u8int *buf)
346 U8PUT(p, vttodisktype(ci->type));
350 U16PUT(p, ci->uncsize);
352 scorecp(p, ci->score);
355 if(buf + ClumpInfoSize != p)
356 sysfatal("packclumpinfo packed wrong amount");
360 unpackisect(ISect *is, u8int *buf)
371 seterr(ECorrupt, "index section has wrong magic number: %s expected ISectMagic (%lux)",
372 fmtmagic(fbuf, m), ISectMagic);
376 is->version = U32GET(p);
378 namecp(is->name, (char*)p);
380 namecp(is->index, (char*)p);
382 is->blocksize = U32GET(p);
384 is->blockbase = U32GET(p);
386 is->blocks = U32GET(p);
388 is->start = U32GET(p);
390 is->stop = U32GET(p);
393 if(buf + ISectSize != p)
394 sysfatal("unpackisect unpacked wrong amount");
400 packisect(ISect *is, u8int *buf)
406 U32PUT(p, ISectMagic);
408 U32PUT(p, is->version);
410 namecp((char*)p, is->name);
412 namecp((char*)p, is->index);
414 U32PUT(p, is->blocksize);
416 U32PUT(p, is->blockbase);
418 U32PUT(p, is->blocks);
420 U32PUT(p, is->start);
425 if(buf + ISectSize != p)
426 sysfatal("packisect packed wrong amount");
432 unpackientry(IEntry *ie, u8int *buf)
438 scorecp(ie->score, p);
440 ie->wtime = U32GET(p);
442 ie->train = U16GET(p);
444 ie->ia.addr = U64GET(p);
445 if(ie->ia.addr>>56) print("%.8H => %llux\n", p, ie->ia.addr);
447 ie->ia.size = U16GET(p);
449 if(p - buf != IEntryTypeOff)
450 sysfatal("unpackientry bad IEntryTypeOff amount");
451 ie->ia.type = vtfromdisktype(U8GET(p));
453 ie->ia.blocks = U8GET(p);
456 if(p - buf != IEntrySize)
457 sysfatal("unpackientry unpacked wrong amount");
461 packientry(IEntry *ie, u8int *buf)
468 scorecp(p, ie->score);
470 U32PUT(p, ie->wtime);
472 U16PUT(p, ie->train);
474 U64PUT(p, ie->ia.addr, t32);
476 U16PUT(p, ie->ia.size);
478 U8PUT(p, vttodisktype(ie->ia.type));
480 U8PUT(p, ie->ia.blocks);
483 if(p - buf != IEntrySize)
484 sysfatal("packientry packed wrong amount");
488 unpackibucket(IBucket *b, u8int *buf)
491 b->depth = U32GET(&buf[U16Size]);
492 b->data = buf + IBucketSize;
496 packibucket(IBucket *b, u8int *buf)
499 U32PUT(&buf[U16Size], b->depth);