# edsk.py # # Dump interesting per-sector info about an EDSK file # # Written & released by Keir Fraser # # This is free and unencumbered software released into the public domain. # See the file COPYING for more details, or visit . import struct, sys, binascii def main(argv): in_f = open(argv[1], "rb") in_dat = in_f.read() in_len = len(in_dat) x = struct.unpack("<34s14sBBH", in_dat[:52]) tracks = int(x[2]) sides = int(x[3]) tsz = in_dat[52:256] populated = 0 ext = False if x[0].startswith(b"EXTENDED CPC DSK File\r\nDisk-Info\r\n"): print("Extended DSK") ext = True else: assert x[0].startswith(b"MV - CPCEMU") print("Standard DSK") while tsz: x = struct.unpack("B", tsz[:1]) if int(x[0]) != 0: populated += 1 tsz = tsz[1:] print("%u cylinders, %u sides, %u non-empty tracks" % (tracks, sides, populated)) in_dat = in_dat[256:] while True: if not in_dat: break x = struct.unpack("<10s", in_dat[:10]) if x[0] != b'Track-Info': in_dat = in_dat[256:] continue (track, side) = struct.unpack("BB", in_dat[16:18]) (n, nr, gap, filler) = struct.unpack("BBBB", in_dat[20:24]) print("T%u.%u: N=%u nr=%u gap=%u fill=%x" % (track, side, n, nr, gap, filler)) sinfo = in_dat[24:256] in_dat = in_dat[256:] tot_dlen = 0 while sinfo and nr != 0: (c,h,r,n,s1,s2,alen) = struct.unpack(" 8: _n = 8 nsz = 128 << _n if s2 & 0x01: special += ['DAM Missing'] elif s1 & 0x01: special += ['IDAM Missing'] s1 &= ~0x01 s2 &= ~0x01 if s1 & 0x20: if s2 & 0x20: special += ['Data CRC'] else: special += ['ID CRC'] s1 &= ~0x20 s2 &= ~0x20 if s2 & 0x40: special += ['DDAM'] s2 &= ~0x40 if s1 or s2: special += ['XXXX-UNKNOWN'] if alen < nsz: if alen % 0x80 == 0: special += ['Incomplete'] else: special += ['Small GAPS'] elif alen > nsz: if alen % nsz == 0: special += ['Weak (%u)' % (alen / nsz)] else: special += ['Large GAPS'] if alen % 0x80 != 0 and alen >= 13: remainder = bytearray(sdat[-13:]) if remainder[0] != 0 and all([v == 0 for v in remainder[1:]]): special += ["Pre-Sync??"] print(" %u.%u id=%u n=%u(%u) stat=%02x:%02x %u crc=%08x\t" % (c,h,r,n,nsz,_s1,_s2,alen,binascii.crc32(sdat)&0xffffffff) + str(special)) # print(binascii.hexlify(sdat)) sinfo = sinfo[8:] nr -= 1 if tot_dlen % 256 != 0: in_dat = in_dat[256 - (tot_dlen % 256) : ] if __name__ == "__main__": main(sys.argv)