diff --git a/DiscImageChef.DiscImages/TeleDisk.cs b/DiscImageChef.DiscImages/TeleDisk.cs
index e7f6d043c..006cebe5b 100644
--- a/DiscImageChef.DiscImages/TeleDisk.cs
+++ b/DiscImageChef.DiscImages/TeleDisk.cs
@@ -28,6 +28,11 @@
//
// ----------------------------------------------------------------------------
// Copyright © 2011-2017 Natalia Portillo
+// For Advanced Compression support (aka LZH):
+// Copyright © 2017 Miodrag Milanovic
+// Copyright © 1988 Haruhiko OKUMURA
+// Copyright © 1988 Haruyasu YOSHIZAKI
+// Copyright © 1988 Kenji RIKITAKE
// ****************************************************************************/
using System;
@@ -39,388 +44,414 @@ using DiscImageChef.Filters;
namespace DiscImageChef.ImagePlugins
{
- // Created following notes from Dave Dunfield
- // http://www.classiccmp.org/dunfield/img54306/td0notes.txt
- public class TeleDisk : ImagePlugin
- {
- #region Internal Structures
+ // Created following notes from Dave Dunfield
+ // http://www.classiccmp.org/dunfield/img54306/td0notes.txt
+ public class TeleDisk : ImagePlugin
+ {
+ #region Internal Structures
- struct TD0Header
- {
- /// "TD" or "td" depending on compression
- public ushort signature;
- /// Sequence, but TeleDisk seems to complaing if != 0
- public byte sequence;
- /// Random, same byte for all disks in the same set
- public byte diskSet;
- /// TeleDisk version, major in high nibble, minor in low nibble
- public byte version;
- /// Data rate
- public byte dataRate;
- /// BIOS drive type
- public byte driveType;
- /// Stepping used
- public byte stepping;
- /// If set means image only allocates sectors marked in-use by FAT12
- public byte dosAllocation;
- /// Sides of disk
- public byte sides;
- /// CRC of all the previous
- public ushort crc;
- }
+ struct TD0Header
+ {
+ /// "TD" or "td" depending on compression
+ public ushort signature;
+ /// Sequence, but TeleDisk seems to complaing if != 0
+ public byte sequence;
+ /// Random, same byte for all disks in the same set
+ public byte diskSet;
+ /// TeleDisk version, major in high nibble, minor in low nibble
+ public byte version;
+ /// Data rate
+ public byte dataRate;
+ /// BIOS drive type
+ public byte driveType;
+ /// Stepping used
+ public byte stepping;
+ /// If set means image only allocates sectors marked in-use by FAT12
+ public byte dosAllocation;
+ /// Sides of disk
+ public byte sides;
+ /// CRC of all the previous
+ public ushort crc;
+ }
- struct TDCommentBlockHeader
- {
- /// CRC of comment block after crc field
- public ushort crc;
- /// Length of comment
- public ushort length;
- public byte year;
- public byte month;
- public byte day;
- public byte hour;
- public byte minute;
- public byte second;
- }
+ struct TDCommentBlockHeader
+ {
+ /// CRC of comment block after crc field
+ public ushort crc;
+ /// Length of comment
+ public ushort length;
+ public byte year;
+ public byte month;
+ public byte day;
+ public byte hour;
+ public byte minute;
+ public byte second;
+ }
- struct TDTrackHeader
- {
- /// Sectors in the track, 0xFF if end of disk image (there is no spoon)
- public byte sectors;
- /// Cylinder the head was on
- public byte cylinder;
- /// Head/side used
- public byte head;
- /// Lower byte of CRC of previous fields
- public byte crc;
- }
+ struct TDTrackHeader
+ {
+ /// Sectors in the track, 0xFF if end of disk image (there is no spoon)
+ public byte sectors;
+ /// Cylinder the head was on
+ public byte cylinder;
+ /// Head/side used
+ public byte head;
+ /// Lower byte of CRC of previous fields
+ public byte crc;
+ }
- struct TDSectorHeader
- {
- /// Cylinder as stored on sector address mark
- public byte cylinder;
- /// Head as stored on sector address mark
- public byte head;
- /// Sector number as stored on sector address mark
- public byte sectorNumber;
- /// Sector size
- public byte sectorSize;
- /// Sector flags
- public byte flags;
- /// Lower byte of TeleDisk CRC of sector header, data header and data block
- public byte crc;
- }
+ struct TDSectorHeader
+ {
+ /// Cylinder as stored on sector address mark
+ public byte cylinder;
+ /// Head as stored on sector address mark
+ public byte head;
+ /// Sector number as stored on sector address mark
+ public byte sectorNumber;
+ /// Sector size
+ public byte sectorSize;
+ /// Sector flags
+ public byte flags;
+ /// Lower byte of TeleDisk CRC of sector header, data header and data block
+ public byte crc;
+ }
- struct TDDataHeader
- {
- /// Size of all data (encoded) + next field (1)
- public ushort dataSize;
- /// Encoding used for data block
- public byte dataEncoding;
- }
+ struct TDDataHeader
+ {
+ /// Size of all data (encoded) + next field (1)
+ public ushort dataSize;
+ /// Encoding used for data block
+ public byte dataEncoding;
+ }
- #endregion
+ #endregion
- #region Internal Constants
+ #region Internal Constants
- // "TD" as little endian uint.
- const ushort tdMagic = 0x4454;
- // "td" as little endian uint. Means whole file is compressed (aka Advanced Compression)
- const ushort tdAdvCompMagic = 0x6474;
+ // "TD" as little endian uint.
+ const ushort tdMagic = 0x4454;
+ // "td" as little endian uint. Means whole file is compressed (aka Advanced Compression)
+ const ushort tdAdvCompMagic = 0x6474;
- // DataRates
- const byte DataRate250kbps = 0x00;
- const byte DataRate300kbps = 0x01;
- const byte DataRate500kbps = 0x02;
+ // DataRates
+ const byte DataRate250kbps = 0x00;
+ const byte DataRate300kbps = 0x01;
+ const byte DataRate500kbps = 0x02;
- // TeleDisk drive types
- const byte DriveType525HD_DDDisk = 0x00;
- const byte DriveType525HD = 0x01;
- const byte DriveType525DD = 0x02;
- const byte DriveType35DD = 0x03;
- const byte DriveType35HD = 0x04;
- const byte DriveType8inch = 0x05;
- const byte DriveType35ED = 0x06;
+ // TeleDisk drive types
+ const byte DriveType525HD_DDDisk = 0x00;
+ const byte DriveType525HD = 0x01;
+ const byte DriveType525DD = 0x02;
+ const byte DriveType35DD = 0x03;
+ const byte DriveType35HD = 0x04;
+ const byte DriveType8inch = 0x05;
+ const byte DriveType35ED = 0x06;
- // Stepping
- const byte SteppingSingle = 0x00;
- const byte SteppingDouble = 0x01;
- const byte SteppingEvenOnly = 0x02;
- // If this bit is set, there is a comment block
- const byte CommentBlockPresent = 0x80;
+ // Stepping
+ const byte SteppingSingle = 0x00;
+ const byte SteppingDouble = 0x01;
+ const byte SteppingEvenOnly = 0x02;
+ // If this bit is set, there is a comment block
+ const byte CommentBlockPresent = 0x80;
- // CRC polynomial
- const ushort TeleDiskCRCPoly = 0xA097;
+ // CRC polynomial
+ const ushort TeleDiskCRCPoly = 0xA097;
- // Sector sizes table
- const byte SectorSize128 = 0x00;
- const byte SectorSize256 = 0x01;
- const byte SectorSize512 = 0x02;
- const byte SectorSize1K = 0x03;
- const byte SectorSize2K = 0x04;
- const byte SectorSize4K = 0x05;
- const byte SectorSize8K = 0x06;
+ // Sector sizes table
+ const byte SectorSize128 = 0x00;
+ const byte SectorSize256 = 0x01;
+ const byte SectorSize512 = 0x02;
+ const byte SectorSize1K = 0x03;
+ const byte SectorSize2K = 0x04;
+ const byte SectorSize4K = 0x05;
+ const byte SectorSize8K = 0x06;
- // Flags
- // Address mark repeats inside same track
- const byte FlagsSectorDuplicate = 0x01;
- // Sector gave CRC error on reading
- const byte FlagsSectorCRCError = 0x02;
- // Address mark indicates deleted sector
- const byte FlagsSectorDeleted = 0x04;
- // Sector skipped as FAT said it's unused
- const byte FlagsSectorSkipped = 0x10;
- // There was an address mark, but no data following
- const byte FlagsSectorDataless = 0x20;
- // There was data without address mark
- const byte FlagsSectorNoID = 0x40;
+ // Flags
+ // Address mark repeats inside same track
+ const byte FlagsSectorDuplicate = 0x01;
+ // Sector gave CRC error on reading
+ const byte FlagsSectorCRCError = 0x02;
+ // Address mark indicates deleted sector
+ const byte FlagsSectorDeleted = 0x04;
+ // Sector skipped as FAT said it's unused
+ const byte FlagsSectorSkipped = 0x10;
+ // There was an address mark, but no data following
+ const byte FlagsSectorDataless = 0x20;
+ // There was data without address mark
+ const byte FlagsSectorNoID = 0x40;
- // Data block encodings
- // Data is copied as is
- const byte dataBlockCopy = 0x00;
- // Data is encoded as a pair of len.value uint16s
- const byte dataBlockPattern = 0x01;
- // Data is encoded as RLE
- const byte dataBlockRLE = 0x02;
+ // Data block encodings
+ // Data is copied as is
+ const byte dataBlockCopy = 0x00;
+ // Data is encoded as a pair of len.value uint16s
+ const byte dataBlockPattern = 0x01;
+ // Data is encoded as RLE
+ const byte dataBlockRLE = 0x02;
- #endregion
+ #endregion
- #region Internal variables
+ #region Internal variables
- TD0Header header;
- TDCommentBlockHeader commentHeader;
- byte[] commentBlock;
- // LBA, data
- uint totalDiskSize;
- bool ADiskCRCHasFailed;
- List SectorsWhereCRCHasFailed;
+ TD0Header header;
+ TDCommentBlockHeader commentHeader;
+ byte[] commentBlock;
+ // LBA, data
+ uint totalDiskSize;
+ bool ADiskCRCHasFailed;
+ List SectorsWhereCRCHasFailed;
// Cylinder by head, sector data matrix
byte[][][][] sectorsData;
+ Stream inStream;
#endregion
public TeleDisk()
- {
- Name = "Sydex TeleDisk";
- PluginUUID = new Guid("0240B7B1-E959-4CDC-B0BD-386D6E467B88");
- ImageInfo = new ImageInfo();
- ImageInfo.readableSectorTags = new List();
- ImageInfo.readableMediaTags = new List();
- ImageInfo.imageHasPartitions = false;
- ImageInfo.imageHasSessions = false;
- ImageInfo.imageApplication = "Sydex TeleDisk";
- ImageInfo.imageComments = null;
- ImageInfo.imageCreator = null;
- ImageInfo.mediaManufacturer = null;
- ImageInfo.mediaModel = null;
- ImageInfo.mediaSerialNumber = null;
- ImageInfo.mediaBarcode = null;
- ImageInfo.mediaPartNumber = null;
- ImageInfo.mediaSequence = 0;
- ImageInfo.lastMediaSequence = 0;
- ImageInfo.driveManufacturer = null;
- ImageInfo.driveModel = null;
- ImageInfo.driveSerialNumber = null;
- ImageInfo.driveFirmwareRevision = null;
- ADiskCRCHasFailed = false;
- SectorsWhereCRCHasFailed = new List();
- }
+ {
+ Name = "Sydex TeleDisk";
+ PluginUUID = new Guid("0240B7B1-E959-4CDC-B0BD-386D6E467B88");
+ ImageInfo = new ImageInfo();
+ ImageInfo.readableSectorTags = new List();
+ ImageInfo.readableMediaTags = new List();
+ ImageInfo.imageHasPartitions = false;
+ ImageInfo.imageHasSessions = false;
+ ImageInfo.imageApplication = "Sydex TeleDisk";
+ ImageInfo.imageComments = null;
+ ImageInfo.imageCreator = null;
+ ImageInfo.mediaManufacturer = null;
+ ImageInfo.mediaModel = null;
+ ImageInfo.mediaSerialNumber = null;
+ ImageInfo.mediaBarcode = null;
+ ImageInfo.mediaPartNumber = null;
+ ImageInfo.mediaSequence = 0;
+ ImageInfo.lastMediaSequence = 0;
+ ImageInfo.driveManufacturer = null;
+ ImageInfo.driveModel = null;
+ ImageInfo.driveSerialNumber = null;
+ ImageInfo.driveFirmwareRevision = null;
+ ADiskCRCHasFailed = false;
+ SectorsWhereCRCHasFailed = new List();
+ }
- public override bool IdentifyImage(Filter imageFilter)
- {
- header = new TD0Header();
- byte[] headerBytes = new byte[12];
- Stream stream = imageFilter.GetDataForkStream();
- stream.Seek(0, SeekOrigin.Begin);
+ public override bool IdentifyImage(Filter imageFilter)
+ {
+ header = new TD0Header();
+ byte[] headerBytes = new byte[12];
+ Stream stream = imageFilter.GetDataForkStream();
+ stream.Seek(0, SeekOrigin.Begin);
- stream.Read(headerBytes, 0, 12);
+ stream.Read(headerBytes, 0, 12);
- header.signature = BitConverter.ToUInt16(headerBytes, 0);
+ header.signature = BitConverter.ToUInt16(headerBytes, 0);
- if(header.signature != tdMagic && header.signature != tdAdvCompMagic)
- return false;
+ if(header.signature != tdMagic && header.signature != tdAdvCompMagic)
+ return false;
- header.sequence = headerBytes[2];
- header.diskSet = headerBytes[3];
- header.version = headerBytes[4];
- header.dataRate = headerBytes[5];
- header.driveType = headerBytes[6];
- header.stepping = headerBytes[7];
- header.dosAllocation = headerBytes[8];
- header.sides = headerBytes[9];
- header.crc = BitConverter.ToUInt16(headerBytes, 10);
+ header.sequence = headerBytes[2];
+ header.diskSet = headerBytes[3];
+ header.version = headerBytes[4];
+ header.dataRate = headerBytes[5];
+ header.driveType = headerBytes[6];
+ header.stepping = headerBytes[7];
+ header.dosAllocation = headerBytes[8];
+ header.sides = headerBytes[9];
+ header.crc = BitConverter.ToUInt16(headerBytes, 10);
- byte[] headerBytesForCRC = new byte[10];
- Array.Copy(headerBytes, headerBytesForCRC, 10);
- ushort calculatedHeaderCRC = TeleDiskCRC(0x0000, headerBytesForCRC);
+ byte[] headerBytesForCRC = new byte[10];
+ Array.Copy(headerBytes, headerBytesForCRC, 10);
+ ushort calculatedHeaderCRC = TeleDiskCRC(0x0000, headerBytesForCRC);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.signature = 0x{0:X4}", header.signature);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.sequence = 0x{0:X2}", header.sequence);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.diskSet = 0x{0:X2}", header.diskSet);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.version = 0x{0:X2}", header.version);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.dataRate = 0x{0:X2}", header.dataRate);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.driveType = 0x{0:X2}", header.driveType);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.stepping = 0x{0:X2}", header.stepping);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.dosAllocation = 0x{0:X2}", header.dosAllocation);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.sides = 0x{0:X2}", header.sides);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.crc = 0x{0:X4}", header.crc);
- DicConsole.DebugWriteLine("TeleDisk plugin", "calculated header crc = 0x{0:X4}", calculatedHeaderCRC);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.signature = 0x{0:X4}", header.signature);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.sequence = 0x{0:X2}", header.sequence);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.diskSet = 0x{0:X2}", header.diskSet);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.version = 0x{0:X2}", header.version);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.dataRate = 0x{0:X2}", header.dataRate);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.driveType = 0x{0:X2}", header.driveType);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.stepping = 0x{0:X2}", header.stepping);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.dosAllocation = 0x{0:X2}", header.dosAllocation);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.sides = 0x{0:X2}", header.sides);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.crc = 0x{0:X4}", header.crc);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "calculated header crc = 0x{0:X4}", calculatedHeaderCRC);
- // We need more checks as the magic is too simply.
- // This may deny legal images
+ // We need more checks as the magic is too simply.
+ // This may deny legal images
- // That would be much of a coincidence
- if(header.crc == calculatedHeaderCRC)
- return true;
+ // That would be much of a coincidence
+ if(header.crc == calculatedHeaderCRC)
+ return true;
- if(header.sequence != 0x00)
- return false;
+ if(header.sequence != 0x00)
+ return false;
- if(header.dataRate != DataRate250kbps && header.dataRate != DataRate300kbps && header.dataRate != DataRate500kbps)
- return false;
+ if(header.dataRate != DataRate250kbps && header.dataRate != DataRate300kbps && header.dataRate != DataRate500kbps)
+ return false;
- if(header.driveType != DriveType35DD && header.driveType != DriveType35ED && header.driveType != DriveType35HD && header.driveType != DriveType525DD &&
- header.driveType != DriveType525HD && header.driveType != DriveType525HD_DDDisk && header.driveType != DriveType8inch)
- return false;
+ if(header.driveType != DriveType35DD && header.driveType != DriveType35ED && header.driveType != DriveType35HD && header.driveType != DriveType525DD &&
+ header.driveType != DriveType525HD && header.driveType != DriveType525HD_DDDisk && header.driveType != DriveType8inch)
+ return false;
- return true;
- }
+ return true;
+ }
- public override bool OpenImage(Filter imageFilter)
- {
- header = new TD0Header();
- byte[] headerBytes = new byte[12];
- Stream stream = imageFilter.GetDataForkStream();
- stream.Seek(0, SeekOrigin.Begin);
+ public override bool OpenImage(Filter imageFilter)
+ {
+ header = new TD0Header();
+ byte[] headerBytes = new byte[12];
+ inStream = imageFilter.GetDataForkStream();
+ MemoryStream stream = new MemoryStream();
+ inStream.Seek(0, SeekOrigin.Begin);
- stream.Read(headerBytes, 0, 12);
+ inStream.Read(headerBytes, 0, 12);
+ stream.Write(headerBytes, 0, 12);
- header.signature = BitConverter.ToUInt16(headerBytes, 0);
+ header.signature = BitConverter.ToUInt16(headerBytes, 0);
- if(header.signature != tdMagic && header.signature != tdAdvCompMagic)
- return false;
+ if(header.signature != tdMagic && header.signature != tdAdvCompMagic)
+ return false;
- header.sequence = headerBytes[2];
- header.diskSet = headerBytes[3];
- header.version = headerBytes[4];
- header.dataRate = headerBytes[5];
- header.driveType = headerBytes[6];
- header.stepping = headerBytes[7];
- header.dosAllocation = headerBytes[8];
- header.sides = headerBytes[9];
- header.crc = BitConverter.ToUInt16(headerBytes, 10);
+ header.sequence = headerBytes[2];
+ header.diskSet = headerBytes[3];
+ header.version = headerBytes[4];
+ header.dataRate = headerBytes[5];
+ header.driveType = headerBytes[6];
+ header.stepping = headerBytes[7];
+ header.dosAllocation = headerBytes[8];
+ header.sides = headerBytes[9];
+ header.crc = BitConverter.ToUInt16(headerBytes, 10);
- ImageInfo.imageName = Path.GetFileNameWithoutExtension(imageFilter.GetFilename());
- ImageInfo.imageVersion = string.Format("{0}.{1}", (header.version & 0xF0) >> 4, header.version & 0x0F);
- ImageInfo.imageApplication = ImageInfo.imageVersion;
+ ImageInfo.imageName = Path.GetFileNameWithoutExtension(imageFilter.GetFilename());
+ ImageInfo.imageVersion = string.Format("{0}.{1}", (header.version & 0xF0) >> 4, header.version & 0x0F);
+ ImageInfo.imageApplication = ImageInfo.imageVersion;
- byte[] headerBytesForCRC = new byte[10];
- Array.Copy(headerBytes, headerBytesForCRC, 10);
- ushort calculatedHeaderCRC = TeleDiskCRC(0x0000, headerBytesForCRC);
+ byte[] headerBytesForCRC = new byte[10];
+ Array.Copy(headerBytes, headerBytesForCRC, 10);
+ ushort calculatedHeaderCRC = TeleDiskCRC(0x0000, headerBytesForCRC);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.signature = 0x{0:X4}", header.signature);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.sequence = 0x{0:X2}", header.sequence);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.diskSet = 0x{0:X2}", header.diskSet);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.version = 0x{0:X2}", header.version);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.dataRate = 0x{0:X2}", header.dataRate);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.driveType = 0x{0:X2}", header.driveType);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.stepping = 0x{0:X2}", header.stepping);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.dosAllocation = 0x{0:X2}", header.dosAllocation);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.sides = 0x{0:X2}", header.sides);
- DicConsole.DebugWriteLine("TeleDisk plugin", "header.crc = 0x{0:X4}", header.crc);
- DicConsole.DebugWriteLine("TeleDisk plugin", "calculated header crc = 0x{0:X4}", calculatedHeaderCRC);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.signature = 0x{0:X4}", header.signature);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.sequence = 0x{0:X2}", header.sequence);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.diskSet = 0x{0:X2}", header.diskSet);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.version = 0x{0:X2}", header.version);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.dataRate = 0x{0:X2}", header.dataRate);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.driveType = 0x{0:X2}", header.driveType);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.stepping = 0x{0:X2}", header.stepping);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.dosAllocation = 0x{0:X2}", header.dosAllocation);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.sides = 0x{0:X2}", header.sides);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "header.crc = 0x{0:X4}", header.crc);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "calculated header crc = 0x{0:X4}", calculatedHeaderCRC);
- // We need more checks as the magic is too simply.
- // This may deny legal images
+ // We need more checks as the magic is too simply.
+ // This may deny legal images
- // That would be much of a coincidence
- if(header.crc != calculatedHeaderCRC)
- {
- ADiskCRCHasFailed = true;
- DicConsole.DebugWriteLine("TeleDisk plugin", "Calculated CRC does not coincide with stored one.");
- }
+ // That would be much of a coincidence
+ if(header.crc != calculatedHeaderCRC)
+ {
+ ADiskCRCHasFailed = true;
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Calculated CRC does not coincide with stored one.");
+ }
- if(header.sequence != 0x00)
- return false;
+ if(header.sequence != 0x00)
+ return false;
- if(header.dataRate != DataRate250kbps && header.dataRate != DataRate300kbps && header.dataRate != DataRate500kbps)
- return false;
+ if(header.dataRate != DataRate250kbps && header.dataRate != DataRate300kbps && header.dataRate != DataRate500kbps)
+ return false;
- if(header.driveType != DriveType35DD && header.driveType != DriveType35ED && header.driveType != DriveType35HD && header.driveType != DriveType525DD &&
- header.driveType != DriveType525HD && header.driveType != DriveType525HD_DDDisk && header.driveType != DriveType8inch)
- return false;
+ if(header.driveType != DriveType35DD && header.driveType != DriveType35ED && header.driveType != DriveType35HD && header.driveType != DriveType525DD &&
+ header.driveType != DriveType525HD && header.driveType != DriveType525HD_DDDisk && header.driveType != DriveType8inch)
+ return false;
- if(header.signature == tdAdvCompMagic)
- throw new NotImplementedException("TeleDisk Advanced Compression support not yet implemented");
+ if(header.signature == tdAdvCompMagic)
+ {
+ int rd;
+ byte[] obuf = new byte[BUFSZ];
+ inStream.Seek(12, SeekOrigin.Begin);
+ stream.Seek(12, SeekOrigin.Begin);
+ init_Decode();
+ do
+ {
+ if((rd = Decode(out obuf, BUFSZ)) > 0)
+ stream.Write(obuf, 0, rd);
+ } while(rd == BUFSZ);
+ }
+ else
+ {
+ // Not using Stream.CopyTo() because it's failing with LZIP
+ byte[] copybuf = new byte[inStream.Length];
+ inStream.Seek(0, SeekOrigin.Begin);
+ inStream.Read(copybuf, 0, copybuf.Length);
+ stream.Seek(0, SeekOrigin.Begin);
+ stream.Write(copybuf, 0, copybuf.Length);
+ copybuf = null;
+ }
- ImageInfo.imageCreationTime = DateTime.MinValue;
+ stream.Seek(12, SeekOrigin.Begin);
- if((header.stepping & CommentBlockPresent) == CommentBlockPresent)
- {
- commentHeader = new TDCommentBlockHeader();
+ ImageInfo.imageCreationTime = DateTime.MinValue;
- byte[] commentHeaderBytes = new byte[10];
- byte[] commentBlockForCRC;
+ if((header.stepping & CommentBlockPresent) == CommentBlockPresent)
+ {
+ commentHeader = new TDCommentBlockHeader();
- stream.Read(commentHeaderBytes, 0, 10);
- commentHeader.crc = BitConverter.ToUInt16(commentHeaderBytes, 0);
- commentHeader.length = BitConverter.ToUInt16(commentHeaderBytes, 2);
- commentHeader.year = commentHeaderBytes[4];
- commentHeader.month = commentHeaderBytes[5];
- commentHeader.day = commentHeaderBytes[6];
- commentHeader.hour = commentHeaderBytes[7];
- commentHeader.minute = commentHeaderBytes[8];
- commentHeader.second = commentHeaderBytes[9];
+ byte[] commentHeaderBytes = new byte[10];
+ byte[] commentBlockForCRC;
- commentBlock = new byte[commentHeader.length];
- stream.Read(commentBlock, 0, commentHeader.length);
+ stream.Read(commentHeaderBytes, 0, 10);
+ commentHeader.crc = BitConverter.ToUInt16(commentHeaderBytes, 0);
+ commentHeader.length = BitConverter.ToUInt16(commentHeaderBytes, 2);
+ commentHeader.year = commentHeaderBytes[4];
+ commentHeader.month = commentHeaderBytes[5];
+ commentHeader.day = commentHeaderBytes[6];
+ commentHeader.hour = commentHeaderBytes[7];
+ commentHeader.minute = commentHeaderBytes[8];
+ commentHeader.second = commentHeaderBytes[9];
- commentBlockForCRC = new byte[commentHeader.length + 8];
- Array.Copy(commentHeaderBytes, 2, commentBlockForCRC, 0, 8);
- Array.Copy(commentBlock, 0, commentBlockForCRC, 8, commentHeader.length);
+ commentBlock = new byte[commentHeader.length];
+ stream.Read(commentBlock, 0, commentHeader.length);
- ushort cmtcrc = TeleDiskCRC(0, commentBlockForCRC);
+ commentBlockForCRC = new byte[commentHeader.length + 8];
+ Array.Copy(commentHeaderBytes, 2, commentBlockForCRC, 0, 8);
+ Array.Copy(commentBlock, 0, commentBlockForCRC, 8, commentHeader.length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "Comment header");
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.crc = 0x{0:X4}", commentHeader.crc);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tCalculated CRC = 0x{0:X4}", cmtcrc);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.length = {0} bytes", commentHeader.length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.year = {0}", commentHeader.year);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.month = {0}", commentHeader.month);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.day = {0}", commentHeader.day);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.hour = {0}", commentHeader.hour);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.minute = {0}", commentHeader.minute);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.second = {0}", commentHeader.second);
+ ushort cmtcrc = TeleDiskCRC(0, commentBlockForCRC);
- ADiskCRCHasFailed |= cmtcrc != commentHeader.crc;
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Comment header");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.crc = 0x{0:X4}", commentHeader.crc);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tCalculated CRC = 0x{0:X4}", cmtcrc);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.length = {0} bytes", commentHeader.length);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.year = {0}", commentHeader.year);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.month = {0}", commentHeader.month);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.day = {0}", commentHeader.day);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.hour = {0}", commentHeader.hour);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.minute = {0}", commentHeader.minute);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tcommentheader.second = {0}", commentHeader.second);
- for(int i = 0; i < commentBlock.Length; i++)
- {
- // Replace NULLs, used by TeleDisk as newline markers, with UNIX newline marker
- if(commentBlock[i] == 0x00)
- commentBlock[i] = 0x0A;
- }
+ ADiskCRCHasFailed |= cmtcrc != commentHeader.crc;
- ImageInfo.imageComments = System.Text.Encoding.ASCII.GetString(commentBlock);
+ for(int i = 0; i < commentBlock.Length; i++)
+ {
+ // Replace NULLs, used by TeleDisk as newline markers, with UNIX newline marker
+ if(commentBlock[i] == 0x00)
+ commentBlock[i] = 0x0A;
+ }
- DicConsole.DebugWriteLine("TeleDisk plugin", "Comment");
- DicConsole.DebugWriteLine("TeleDisk plugin", "{0}", ImageInfo.imageComments);
+ ImageInfo.imageComments = System.Text.Encoding.ASCII.GetString(commentBlock);
- ImageInfo.imageCreationTime = new DateTime(commentHeader.year + 1900, commentHeader.month + 1, commentHeader.day,
- commentHeader.hour, commentHeader.minute, commentHeader.second, DateTimeKind.Unspecified);
- }
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Comment");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "{0}", ImageInfo.imageComments);
- if(ImageInfo.imageCreationTime == DateTime.MinValue)
- ImageInfo.imageCreationTime = imageFilter.GetCreationTime();
- ImageInfo.imageLastModificationTime = imageFilter.GetLastWriteTime();
+ ImageInfo.imageCreationTime = new DateTime(commentHeader.year + 1900, commentHeader.month + 1, commentHeader.day,
+ commentHeader.hour, commentHeader.minute, commentHeader.second, DateTimeKind.Unspecified);
+ }
- DicConsole.DebugWriteLine("TeleDisk plugin", "Image created on {0}", ImageInfo.imageCreationTime);
- DicConsole.DebugWriteLine("TeleDisk plugin", "Image modified on {0}", ImageInfo.imageLastModificationTime);
+ if(ImageInfo.imageCreationTime == DateTime.MinValue)
+ ImageInfo.imageCreationTime = imageFilter.GetCreationTime();
+ ImageInfo.imageLastModificationTime = imageFilter.GetLastWriteTime();
- DicConsole.DebugWriteLine("TeleDisk plugin", "Parsing image");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Image created on {0}", ImageInfo.imageCreationTime);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Image modified on {0}", ImageInfo.imageLastModificationTime);
- totalDiskSize = 0;
- ImageInfo.imageSize = 0;
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Parsing image");
+
+ totalDiskSize = 0;
+ ImageInfo.imageSize = 0;
int totalCylinders = -1;
int totalHeads = -1;
@@ -515,62 +546,62 @@ namespace DiscImageChef.ImagePlugins
// Decode the image
stream.Seek(currentPos, SeekOrigin.Begin);
while(true)
- {
- TDTrackHeader TDTrack = new TDTrackHeader();
- byte[] TDTrackForCRC = new byte[3];
- byte TDTrackCalculatedCRC;
+ {
+ TDTrackHeader TDTrack = new TDTrackHeader();
+ byte[] TDTrackForCRC = new byte[3];
+ byte TDTrackCalculatedCRC;
- TDTrack.sectors = (byte)stream.ReadByte();
- TDTrack.cylinder = (byte)stream.ReadByte();
- TDTrack.head = (byte)stream.ReadByte();
- TDTrack.crc = (byte)stream.ReadByte();
+ TDTrack.sectors = (byte)stream.ReadByte();
+ TDTrack.cylinder = (byte)stream.ReadByte();
+ TDTrack.head = (byte)stream.ReadByte();
+ TDTrack.crc = (byte)stream.ReadByte();
- TDTrackForCRC[0] = TDTrack.sectors;
- TDTrackForCRC[1] = TDTrack.cylinder;
- TDTrackForCRC[2] = TDTrack.head;
+ TDTrackForCRC[0] = TDTrack.sectors;
+ TDTrackForCRC[1] = TDTrack.cylinder;
+ TDTrackForCRC[2] = TDTrack.head;
- TDTrackCalculatedCRC = (byte)(TeleDiskCRC(0, TDTrackForCRC) & 0xFF);
+ TDTrackCalculatedCRC = (byte)(TeleDiskCRC(0, TDTrackForCRC) & 0xFF);
- DicConsole.DebugWriteLine("TeleDisk plugin", "Track follows");
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack cylinder: {0}\t", TDTrack.cylinder);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack head: {0}\t", TDTrack.head);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tSectors in track: {0}\t", TDTrack.sectors);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack header CRC: 0x{0:X2} (calculated 0x{1:X2})\t", TDTrack.crc, TDTrackCalculatedCRC);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Track follows");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack cylinder: {0}\t", TDTrack.cylinder);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack head: {0}\t", TDTrack.head);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tSectors in track: {0}\t", TDTrack.sectors);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tTrack header CRC: 0x{0:X2} (calculated 0x{1:X2})\t", TDTrack.crc, TDTrackCalculatedCRC);
- ADiskCRCHasFailed |= TDTrackCalculatedCRC != TDTrack.crc;
+ ADiskCRCHasFailed |= TDTrackCalculatedCRC != TDTrack.crc;
- if(TDTrack.sectors == 0xFF) // End of disk image
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "End of disk image arrived");
- DicConsole.DebugWriteLine("TeleDisk plugin", "Total of {0} data sectors, for {1} bytes", totalSectors, totalDiskSize);
+ if(TDTrack.sectors == 0xFF) // End of disk image
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "End of disk image arrived");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Total of {0} data sectors, for {1} bytes", totalSectors, totalDiskSize);
- break;
- }
+ break;
+ }
- for(byte processedSectors = 0; processedSectors < TDTrack.sectors; processedSectors++)
- {
- TDSectorHeader TDSector = new TDSectorHeader();
- TDDataHeader TDData = new TDDataHeader();
- byte[] dataSizeBytes = new byte[2];
- byte[] data;
- byte[] decodedData;
+ for(byte processedSectors = 0; processedSectors < TDTrack.sectors; processedSectors++)
+ {
+ TDSectorHeader TDSector = new TDSectorHeader();
+ TDDataHeader TDData = new TDDataHeader();
+ byte[] dataSizeBytes = new byte[2];
+ byte[] data;
+ byte[] decodedData;
- TDSector.cylinder = (byte)stream.ReadByte();
- TDSector.head = (byte)stream.ReadByte();
- TDSector.sectorNumber = (byte)stream.ReadByte();
- TDSector.sectorSize = (byte)stream.ReadByte();
- TDSector.flags = (byte)stream.ReadByte();
- TDSector.crc = (byte)stream.ReadByte();
+ TDSector.cylinder = (byte)stream.ReadByte();
+ TDSector.head = (byte)stream.ReadByte();
+ TDSector.sectorNumber = (byte)stream.ReadByte();
+ TDSector.sectorSize = (byte)stream.ReadByte();
+ TDSector.flags = (byte)stream.ReadByte();
+ TDSector.crc = (byte)stream.ReadByte();
- DicConsole.DebugWriteLine("TeleDisk plugin", "\tSector follows");
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark cylinder: {0}", TDSector.cylinder);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark head: {0}", TDSector.head);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark sector number: {0}", TDSector.sectorNumber);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector size: {0}", TDSector.sectorSize);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector flags: 0x{0:X2}", TDSector.flags);
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector CRC (plus headers): 0x{0:X2}", TDSector.crc);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\tSector follows");
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark cylinder: {0}", TDSector.cylinder);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark head: {0}", TDSector.head);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tAddressMark sector number: {0}", TDSector.sectorNumber);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector size: {0}", TDSector.sectorSize);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector flags: 0x{0:X2}", TDSector.flags);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector CRC (plus headers): 0x{0:X2}", TDSector.crc);
- uint LBA = (uint)((TDSector.cylinder * header.sides * ImageInfo.sectorsPerTrack) + (TDSector.head * ImageInfo.sectorsPerTrack) + (TDSector.sectorNumber - 1));
+ uint LBA = (uint)((TDSector.cylinder * header.sides * ImageInfo.sectorsPerTrack) + (TDSector.head * ImageInfo.sectorsPerTrack) + (TDSector.sectorNumber - 1));
if((TDSector.flags & FlagsSectorDataless) != FlagsSectorDataless && (TDSector.flags & FlagsSectorSkipped) != FlagsSectorSkipped)
{
stream.Read(dataSizeBytes, 0, 2);
@@ -599,64 +630,67 @@ namespace DiscImageChef.ImagePlugins
DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tLBA: {0}", LBA);
- if((TDSector.flags & FlagsSectorNoID) != FlagsSectorNoID)
- {
+ if((TDSector.flags & FlagsSectorNoID) != FlagsSectorNoID)
+ {
if(sectorsData[TDTrack.cylinder][TDTrack.head][TDSector.sectorNumber] != null)
- {
- if((TDSector.flags & FlagsSectorDuplicate) == FlagsSectorDuplicate)
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector {0} on cylinder {1} head {2} is duplicate, and marked so",
- TDSector.sectorNumber, TDSector.cylinder, TDSector.head);
- }
- else
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector {0} on cylinder {1} head {2} is duplicate, but is not marked so",
- TDSector.sectorNumber, TDSector.cylinder, TDSector.head);
- }
- }
- else
- {
+ {
+ if((TDSector.flags & FlagsSectorDuplicate) == FlagsSectorDuplicate)
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector {0} on cylinder {1} head {2} is duplicate, and marked so",
+ TDSector.sectorNumber, TDSector.cylinder, TDSector.head);
+ }
+ else
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "\t\tSector {0} on cylinder {1} head {2} is duplicate, but is not marked so",
+ TDSector.sectorNumber, TDSector.cylinder, TDSector.head);
+ }
+ }
+ else
+ {
sectorsData[TDTrack.cylinder][TDTrack.head][TDSector.sectorNumber] = decodedData;
- totalDiskSize += (uint)decodedData.Length;
- }
- }
- }
- }
+ totalDiskSize += (uint)decodedData.Length;
+ }
+ }
+ }
+ }
ImageInfo.sectors = ImageInfo.cylinders * ImageInfo.heads * ImageInfo.sectorsPerTrack;
- ImageInfo.mediaType = DecodeTeleDiskDiskType();
+ ImageInfo.mediaType = DecodeTeleDiskDiskType();
- ImageInfo.xmlMediaType = XmlMediaType.BlockMedia;
+ ImageInfo.xmlMediaType = XmlMediaType.BlockMedia;
- DicConsole.VerboseWriteLine("TeleDisk image contains a disk of type {0}", ImageInfo.mediaType);
- if(!string.IsNullOrEmpty(ImageInfo.imageComments))
- DicConsole.VerboseWriteLine("TeleDisk comments: {0}", ImageInfo.imageComments);
+ DicConsole.VerboseWriteLine("TeleDisk image contains a disk of type {0}", ImageInfo.mediaType);
+ if(!string.IsNullOrEmpty(ImageInfo.imageComments))
+ DicConsole.VerboseWriteLine("TeleDisk comments: {0}", ImageInfo.imageComments);
- return true;
- }
+ inStream.Dispose();
+ stream.Dispose();
- public override bool ImageHasPartitions()
- {
- return ImageInfo.imageHasPartitions;
- }
+ return true;
+ }
- public override ulong GetImageSize()
- {
- return ImageInfo.imageSize;
- }
+ public override bool ImageHasPartitions()
+ {
+ return ImageInfo.imageHasPartitions;
+ }
- public override ulong GetSectors()
- {
- return ImageInfo.sectors;
- }
+ public override ulong GetImageSize()
+ {
+ return ImageInfo.imageSize;
+ }
- public override uint GetSectorSize()
- {
- return ImageInfo.sectorSize;
- }
+ public override ulong GetSectors()
+ {
+ return ImageInfo.sectors;
+ }
- public override byte[] ReadSector(ulong sectorAddress)
- {
+ public override uint GetSectorSize()
+ {
+ return ImageInfo.sectorSize;
+ }
+
+ public override byte[] ReadSector(ulong sectorAddress)
+ {
(ushort cylinder, byte head, byte sector) = LbaToChs(sectorAddress);
if(cylinder >= sectorsData.Length)
@@ -671,8 +705,8 @@ namespace DiscImageChef.ImagePlugins
return sectorsData[cylinder][head][sector];
}
- public override byte[] ReadSectors(ulong sectorAddress, uint length)
- {
+ public override byte[] ReadSectors(ulong sectorAddress, uint length)
+ {
if(sectorAddress > ImageInfo.sectors - 1)
throw new ArgumentOutOfRangeException(nameof(sectorAddress), "Sector address not found");
@@ -699,536 +733,962 @@ namespace DiscImageChef.ImagePlugins
}
public override byte[] ReadSectorLong(ulong sectorAddress)
- {
- return ReadSectors(sectorAddress, 1);
- }
+ {
+ return ReadSectors(sectorAddress, 1);
+ }
- public override byte[] ReadSectorsLong(ulong sectorAddress, uint length)
- {
- return ReadSectors(sectorAddress, length);
- }
+ public override byte[] ReadSectorsLong(ulong sectorAddress, uint length)
+ {
+ return ReadSectors(sectorAddress, length);
+ }
- public override string GetImageFormat()
- {
- return "Sydex TeleDisk";
- }
+ public override string GetImageFormat()
+ {
+ return "Sydex TeleDisk";
+ }
- public override string GetImageVersion()
- {
- return ImageInfo.imageVersion;
- }
+ public override string GetImageVersion()
+ {
+ return ImageInfo.imageVersion;
+ }
- public override string GetImageApplication()
- {
- return ImageInfo.imageApplication;
- }
+ public override string GetImageApplication()
+ {
+ return ImageInfo.imageApplication;
+ }
- public override string GetImageApplicationVersion()
- {
- return ImageInfo.imageApplicationVersion;
- }
+ public override string GetImageApplicationVersion()
+ {
+ return ImageInfo.imageApplicationVersion;
+ }
- public override DateTime GetImageCreationTime()
- {
- return ImageInfo.imageCreationTime;
- }
+ public override DateTime GetImageCreationTime()
+ {
+ return ImageInfo.imageCreationTime;
+ }
- public override DateTime GetImageLastModificationTime()
- {
- return ImageInfo.imageLastModificationTime;
- }
+ public override DateTime GetImageLastModificationTime()
+ {
+ return ImageInfo.imageLastModificationTime;
+ }
- public override string GetImageName()
- {
- return ImageInfo.imageName;
- }
+ public override string GetImageName()
+ {
+ return ImageInfo.imageName;
+ }
- public override MediaType GetMediaType()
- {
- return ImageInfo.mediaType;
- }
+ public override MediaType GetMediaType()
+ {
+ return ImageInfo.mediaType;
+ }
- public override bool? VerifySector(ulong sectorAddress)
- {
- return !SectorsWhereCRCHasFailed.Contains(sectorAddress);
- }
+ public override bool? VerifySector(ulong sectorAddress)
+ {
+ return !SectorsWhereCRCHasFailed.Contains(sectorAddress);
+ }
- public override bool? VerifySector(ulong sectorAddress, uint track)
- {
- return null;
- }
+ public override bool? VerifySector(ulong sectorAddress, uint track)
+ {
+ return null;
+ }
- public override bool? VerifySectors(ulong sectorAddress, uint length, out List FailingLBAs, out List UnknownLBAs)
- {
- FailingLBAs = new List();
- UnknownLBAs = new List();
+ public override bool? VerifySectors(ulong sectorAddress, uint length, out List FailingLBAs, out List UnknownLBAs)
+ {
+ FailingLBAs = new List();
+ UnknownLBAs = new List();
- for(ulong i = sectorAddress; i < sectorAddress + length; i++)
- if(SectorsWhereCRCHasFailed.Contains(sectorAddress))
- FailingLBAs.Add(sectorAddress);
+ for(ulong i = sectorAddress; i < sectorAddress + length; i++)
+ if(SectorsWhereCRCHasFailed.Contains(sectorAddress))
+ FailingLBAs.Add(sectorAddress);
- return FailingLBAs.Count <= 0;
- }
+ return FailingLBAs.Count <= 0;
+ }
- public override bool? VerifySectors(ulong sectorAddress, uint length, uint track, out List FailingLBAs, out List UnknownLBAs)
- {
- FailingLBAs = new List();
- UnknownLBAs = new List();
+ public override bool? VerifySectors(ulong sectorAddress, uint length, uint track, out List FailingLBAs, out List UnknownLBAs)
+ {
+ FailingLBAs = new List();
+ UnknownLBAs = new List();
- for(ulong i = sectorAddress; i < sectorAddress + length; i++)
- UnknownLBAs.Add(i);
+ for(ulong i = sectorAddress; i < sectorAddress + length; i++)
+ UnknownLBAs.Add(i);
- return null;
- }
+ return null;
+ }
- public override bool? VerifyMediaImage()
- {
- return ADiskCRCHasFailed;
- }
+ public override bool? VerifyMediaImage()
+ {
+ return ADiskCRCHasFailed;
+ }
- #region Private methods
+ #region Private methods
- static ushort TeleDiskCRC(ushort crc, byte[] buffer)
- {
- int counter = 0;
+ static ushort TeleDiskCRC(ushort crc, byte[] buffer)
+ {
+ int counter = 0;
- while(counter < buffer.Length)
- {
- crc ^= (ushort)((buffer[counter] & 0xFF) << 8);
+ while(counter < buffer.Length)
+ {
+ crc ^= (ushort)((buffer[counter] & 0xFF) << 8);
- for(int i = 0; i < 8; i++)
- {
- if((crc & 0x8000) > 0)
- crc = (ushort)((crc << 1) ^ TeleDiskCRCPoly);
- else
- crc = (ushort)(crc << 1);
- }
+ for(int i = 0; i < 8; i++)
+ {
+ if((crc & 0x8000) > 0)
+ crc = (ushort)((crc << 1) ^ TeleDiskCRCPoly);
+ else
+ crc = (ushort)(crc << 1);
+ }
- counter++;
- }
+ counter++;
+ }
- return crc;
- }
+ return crc;
+ }
- static byte[] DecodeTeleDiskData(byte sectorSize, byte encodingType, byte[] encodedData)
- {
- byte[] decodedData;
- switch(sectorSize)
- {
- case SectorSize128:
- decodedData = new byte[128];
- break;
- case SectorSize256:
- decodedData = new byte[256];
- break;
- case SectorSize512:
- decodedData = new byte[512];
- break;
- case SectorSize1K:
- decodedData = new byte[1024];
- break;
- case SectorSize2K:
- decodedData = new byte[2048];
- break;
- case SectorSize4K:
- decodedData = new byte[4096];
- break;
- case SectorSize8K:
- decodedData = new byte[8192];
- break;
- default:
- throw new ImageNotSupportedException(string.Format("Sector size {0} is incorrect.", sectorSize));
- }
+ static byte[] DecodeTeleDiskData(byte sectorSize, byte encodingType, byte[] encodedData)
+ {
+ byte[] decodedData;
+ switch(sectorSize)
+ {
+ case SectorSize128:
+ decodedData = new byte[128];
+ break;
+ case SectorSize256:
+ decodedData = new byte[256];
+ break;
+ case SectorSize512:
+ decodedData = new byte[512];
+ break;
+ case SectorSize1K:
+ decodedData = new byte[1024];
+ break;
+ case SectorSize2K:
+ decodedData = new byte[2048];
+ break;
+ case SectorSize4K:
+ decodedData = new byte[4096];
+ break;
+ case SectorSize8K:
+ decodedData = new byte[8192];
+ break;
+ default:
+ throw new ImageNotSupportedException(string.Format("Sector size {0} is incorrect.", sectorSize));
+ }
- switch(encodingType)
- {
- case dataBlockCopy:
- Array.Copy(encodedData, decodedData, decodedData.Length);
- break;
- case dataBlockPattern:
- {
- int ins = 0;
- int outs = 0;
- while(ins < encodedData.Length)
- {
- ushort repeatNumber;
- byte[] repeatValue = new byte[2];
+ switch(encodingType)
+ {
+ case dataBlockCopy:
+ Array.Copy(encodedData, decodedData, decodedData.Length);
+ break;
+ case dataBlockPattern:
+ {
+ int ins = 0;
+ int outs = 0;
+ while(ins < encodedData.Length)
+ {
+ ushort repeatNumber;
+ byte[] repeatValue = new byte[2];
- repeatNumber = BitConverter.ToUInt16(encodedData, ins);
- Array.Copy(encodedData, ins + 2, repeatValue, 0, 2);
- byte[] decodedPiece = new byte[repeatNumber * 2];
- ArrayHelpers.ArrayFill(decodedPiece, repeatValue);
- Array.Copy(decodedPiece, 0, decodedData, outs, decodedPiece.Length);
- ins += 4;
- outs += decodedPiece.Length;
- }
+ repeatNumber = BitConverter.ToUInt16(encodedData, ins);
+ Array.Copy(encodedData, ins + 2, repeatValue, 0, 2);
+ byte[] decodedPiece = new byte[repeatNumber * 2];
+ ArrayHelpers.ArrayFill(decodedPiece, repeatValue);
+ Array.Copy(decodedPiece, 0, decodedData, outs, decodedPiece.Length);
+ ins += 4;
+ outs += decodedPiece.Length;
+ }
- DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Input data size: {0} bytes", encodedData.Length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Processed input: {0} bytes", ins);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Output data size: {0} bytes", decodedData.Length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Processed Output: {0} bytes", outs);
- break;
- }
- case dataBlockRLE:
- {
- int ins = 0;
- int outs = 0;
- while(ins < encodedData.Length)
- {
- byte Run;
- byte Length;
- byte Encoding;
- byte[] Piece;
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Input data size: {0} bytes", encodedData.Length);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Processed input: {0} bytes", ins);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Output data size: {0} bytes", decodedData.Length);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(Block pattern decoder): Processed Output: {0} bytes", outs);
+ break;
+ }
+ case dataBlockRLE:
+ {
+ int ins = 0;
+ int outs = 0;
+ while(ins < encodedData.Length)
+ {
+ byte Run;
+ byte Length;
+ byte Encoding;
+ byte[] Piece;
- Encoding = encodedData[ins];
- if(Encoding == 0x00)
- {
- Length = encodedData[ins + 1];
- Array.Copy(encodedData, ins + 2, decodedData, outs, Length);
- ins += (2 + Length);
- outs += Length;
- }
- else
- {
- Length = (byte)(Encoding * 2);
- Run = encodedData[ins + 1];
- byte[] Part = new byte[Length];
- Array.Copy(encodedData, ins + 2, Part, 0, Length);
- Piece = new byte[Length * Run];
- ArrayHelpers.ArrayFill(Piece, Part);
- Array.Copy(Piece, 0, decodedData, outs, Piece.Length);
- ins += (2 + Length);
- outs += Piece.Length;
- }
- }
+ Encoding = encodedData[ins];
+ if(Encoding == 0x00)
+ {
+ Length = encodedData[ins + 1];
+ Array.Copy(encodedData, ins + 2, decodedData, outs, Length);
+ ins += (2 + Length);
+ outs += Length;
+ }
+ else
+ {
+ Length = (byte)(Encoding * 2);
+ Run = encodedData[ins + 1];
+ byte[] Part = new byte[Length];
+ Array.Copy(encodedData, ins + 2, Part, 0, Length);
+ Piece = new byte[Length * Run];
+ ArrayHelpers.ArrayFill(Piece, Part);
+ Array.Copy(Piece, 0, decodedData, outs, Piece.Length);
+ ins += (2 + Length);
+ outs += Piece.Length;
+ }
+ }
- DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Input data size: {0} bytes", encodedData.Length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Processed input: {0} bytes", ins);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Output data size: {0} bytes", decodedData.Length);
- DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Processed Output: {0} bytes", outs);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Input data size: {0} bytes", encodedData.Length);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Processed input: {0} bytes", ins);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Output data size: {0} bytes", decodedData.Length);
+ DicConsole.DebugWriteLine("TeleDisk plugin", "(RLE decoder): Processed Output: {0} bytes", outs);
- break;
- }
- default:
- throw new ImageNotSupportedException(string.Format("Data encoding {0} is incorrect.", encodingType));
- }
+ break;
+ }
+ default:
+ throw new ImageNotSupportedException(string.Format("Data encoding {0} is incorrect.", encodingType));
+ }
- return decodedData;
- }
+ return decodedData;
+ }
- MediaType DecodeTeleDiskDiskType()
- {
- switch(header.driveType)
- {
- case DriveType525DD:
- case DriveType525HD_DDDisk:
- case DriveType525HD:
- {
- switch(totalDiskSize)
- {
- case 163840:
- {
- // Acorn disk uses 256 bytes/sector
- if(ImageInfo.sectorSize == 256)
- return MediaType.ACORN_525_SS_DD_40;
- // DOS disks use 512 bytes/sector
- return MediaType.DOS_525_SS_DD_8;
- }
- case 184320:
- {
- // Atari disk uses 256 bytes/sector
- if(ImageInfo.sectorSize == 256)
- return MediaType.ATARI_525_DD;
- // DOS disks use 512 bytes/sector
- return MediaType.DOS_525_SS_DD_9;
- }
- case 327680:
- {
- // Acorn disk uses 256 bytes/sector
- if(ImageInfo.sectorSize == 256)
- return MediaType.ACORN_525_SS_DD_80;
- // DOS disks use 512 bytes/sector
- return MediaType.DOS_525_DS_DD_8;
- }
- case 368640:
- return MediaType.DOS_525_DS_DD_9;
- case 1228800:
- return MediaType.DOS_525_HD;
- case 102400:
- return MediaType.ACORN_525_SS_SD_40;
- case 204800:
- return MediaType.ACORN_525_SS_SD_80;
- case 655360:
- return MediaType.ACORN_525_DS_DD;
- case 92160:
- return MediaType.ATARI_525_SD;
- case 133120:
- return MediaType.ATARI_525_ED;
- case 1310720:
- return MediaType.NEC_525_HD;
- case 1261568:
- return MediaType.SHARP_525;
- case 839680:
- return MediaType.FDFORMAT_525_DD;
- case 1304320:
- return MediaType.ECMA_99_8;
- case 1223424:
- return MediaType.ECMA_99_15;
- case 1061632:
- return MediaType.ECMA_99_26;
- case 80384:
- return MediaType.ECMA_66;
- case 325632:
- return MediaType.ECMA_70;
- case 653312:
- return MediaType.ECMA_78;
- case 737280:
- return MediaType.ECMA_78_2;
- default:
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 5,25\" disk with {0} bytes", totalDiskSize);
- return MediaType.Unknown;
- }
- }
- }
- case DriveType35DD:
- case DriveType35ED:
- case DriveType35HD:
- {
- switch(totalDiskSize)
- {
+ MediaType DecodeTeleDiskDiskType()
+ {
+ switch(header.driveType)
+ {
+ case DriveType525DD:
+ case DriveType525HD_DDDisk:
+ case DriveType525HD:
+ {
+ switch(totalDiskSize)
+ {
+ case 163840:
+ {
+ // Acorn disk uses 256 bytes/sector
+ if(ImageInfo.sectorSize == 256)
+ return MediaType.ACORN_525_SS_DD_40;
+ // DOS disks use 512 bytes/sector
+ return MediaType.DOS_525_SS_DD_8;
+ }
+ case 184320:
+ {
+ // Atari disk uses 256 bytes/sector
+ if(ImageInfo.sectorSize == 256)
+ return MediaType.ATARI_525_DD;
+ // DOS disks use 512 bytes/sector
+ return MediaType.DOS_525_SS_DD_9;
+ }
+ case 327680:
+ {
+ // Acorn disk uses 256 bytes/sector
+ if(ImageInfo.sectorSize == 256)
+ return MediaType.ACORN_525_SS_DD_80;
+ // DOS disks use 512 bytes/sector
+ return MediaType.DOS_525_DS_DD_8;
+ }
+ case 368640:
+ return MediaType.DOS_525_DS_DD_9;
+ case 1228800:
+ return MediaType.DOS_525_HD;
+ case 102400:
+ return MediaType.ACORN_525_SS_SD_40;
+ case 204800:
+ return MediaType.ACORN_525_SS_SD_80;
+ case 655360:
+ return MediaType.ACORN_525_DS_DD;
+ case 92160:
+ return MediaType.ATARI_525_SD;
+ case 133120:
+ return MediaType.ATARI_525_ED;
+ case 1310720:
+ return MediaType.NEC_525_HD;
+ case 1261568:
+ return MediaType.SHARP_525;
+ case 839680:
+ return MediaType.FDFORMAT_525_DD;
+ case 1304320:
+ return MediaType.ECMA_99_8;
+ case 1223424:
+ return MediaType.ECMA_99_15;
+ case 1061632:
+ return MediaType.ECMA_99_26;
+ case 80384:
+ return MediaType.ECMA_66;
+ case 325632:
+ return MediaType.ECMA_70;
+ case 653312:
+ return MediaType.ECMA_78;
+ case 737280:
+ return MediaType.ECMA_78_2;
+ default:
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 5,25\" disk with {0} bytes", totalDiskSize);
+ return MediaType.Unknown;
+ }
+ }
+ }
+ case DriveType35DD:
+ case DriveType35ED:
+ case DriveType35HD:
+ {
+ switch(totalDiskSize)
+ {
case 322560:
return MediaType.Apricot_35;
case 327680:
- return MediaType.DOS_35_SS_DD_8;
- case 368640:
- return MediaType.DOS_35_SS_DD_9;
- case 655360:
- return MediaType.DOS_35_DS_DD_8;
- case 737280:
- return MediaType.DOS_35_DS_DD_9;
- case 1474560:
- return MediaType.DOS_35_HD;
- case 2949120:
- return MediaType.DOS_35_ED;
- case 1720320:
- return MediaType.DMF;
- case 1763328:
- return MediaType.DMF_82;
- case 1884160: // Irreal size, seen as BIOS with TSR, 23 sectors/track
- case 1860608: // Real data size, sum of all sectors
- return MediaType.XDF_35;
- case 819200:
- return MediaType.CBM_35_DD;
- case 901120:
- return MediaType.CBM_AMIGA_35_DD;
- case 1802240:
- return MediaType.CBM_AMIGA_35_HD;
- case 1310720:
- return MediaType.NEC_35_HD_8;
- case 1228800:
- return MediaType.NEC_35_HD_15;
- case 1261568:
- return MediaType.SHARP_35;
- default:
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 3,5\" disk with {0} bytes", totalDiskSize);
- return MediaType.Unknown;
- }
- }
- }
- case DriveType8inch:
- {
- switch(totalDiskSize)
- {
- case 81664:
- return MediaType.IBM23FD;
- case 242944:
- return MediaType.IBM33FD_128;
- case 287488:
- return MediaType.IBM33FD_256;
- case 306432:
- return MediaType.IBM33FD_512;
- case 499200:
- return MediaType.IBM43FD_128;
- case 574976:
- return MediaType.IBM43FD_256;
- case 995072:
- return MediaType.IBM53FD_256;
- case 1146624:
- return MediaType.IBM53FD_512;
- case 1222400:
- return MediaType.IBM53FD_1024;
- case 256256:
- // Same size, with same disk geometry, for DEC RX01, NEC and ECMA, return ECMA
- return MediaType.ECMA_54;
- case 512512:
- {
- // DEC disk uses 256 bytes/sector
- if(ImageInfo.sectorSize == 256)
- return MediaType.RX02;
- // ECMA disks use 128 bytes/sector
- return MediaType.ECMA_59;
- }
- case 1261568:
- return MediaType.NEC_8_DD;
- case 1255168:
- return MediaType.ECMA_69_8;
- case 1177344:
- return MediaType.ECMA_69_15;
- case 1021696:
- return MediaType.ECMA_69_26;
- default:
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 8\" disk with {0} bytes", totalDiskSize);
- return MediaType.Unknown;
- }
- }
- }
- default:
- {
- DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown drive type {1} with {0} bytes", totalDiskSize, header.driveType);
- return MediaType.Unknown;
- }
+ return MediaType.DOS_35_SS_DD_8;
+ case 368640:
+ return MediaType.DOS_35_SS_DD_9;
+ case 655360:
+ return MediaType.DOS_35_DS_DD_8;
+ case 737280:
+ return MediaType.DOS_35_DS_DD_9;
+ case 1474560:
+ return MediaType.DOS_35_HD;
+ case 2949120:
+ return MediaType.DOS_35_ED;
+ case 1720320:
+ return MediaType.DMF;
+ case 1763328:
+ return MediaType.DMF_82;
+ case 1884160: // Irreal size, seen as BIOS with TSR, 23 sectors/track
+ case 1860608: // Real data size, sum of all sectors
+ return MediaType.XDF_35;
+ case 819200:
+ return MediaType.CBM_35_DD;
+ case 901120:
+ return MediaType.CBM_AMIGA_35_DD;
+ case 1802240:
+ return MediaType.CBM_AMIGA_35_HD;
+ case 1310720:
+ return MediaType.NEC_35_HD_8;
+ case 1228800:
+ return MediaType.NEC_35_HD_15;
+ case 1261568:
+ return MediaType.SHARP_35;
+ default:
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 3,5\" disk with {0} bytes", totalDiskSize);
+ return MediaType.Unknown;
+ }
+ }
+ }
+ case DriveType8inch:
+ {
+ switch(totalDiskSize)
+ {
+ case 81664:
+ return MediaType.IBM23FD;
+ case 242944:
+ return MediaType.IBM33FD_128;
+ case 287488:
+ return MediaType.IBM33FD_256;
+ case 306432:
+ return MediaType.IBM33FD_512;
+ case 499200:
+ return MediaType.IBM43FD_128;
+ case 574976:
+ return MediaType.IBM43FD_256;
+ case 995072:
+ return MediaType.IBM53FD_256;
+ case 1146624:
+ return MediaType.IBM53FD_512;
+ case 1222400:
+ return MediaType.IBM53FD_1024;
+ case 256256:
+ // Same size, with same disk geometry, for DEC RX01, NEC and ECMA, return ECMA
+ return MediaType.ECMA_54;
+ case 512512:
+ {
+ // DEC disk uses 256 bytes/sector
+ if(ImageInfo.sectorSize == 256)
+ return MediaType.RX02;
+ // ECMA disks use 128 bytes/sector
+ return MediaType.ECMA_59;
+ }
+ case 1261568:
+ return MediaType.NEC_8_DD;
+ case 1255168:
+ return MediaType.ECMA_69_8;
+ case 1177344:
+ return MediaType.ECMA_69_15;
+ case 1021696:
+ return MediaType.ECMA_69_26;
+ default:
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown 8\" disk with {0} bytes", totalDiskSize);
+ return MediaType.Unknown;
+ }
+ }
+ }
+ default:
+ {
+ DicConsole.DebugWriteLine("TeleDisk plugin", "Unknown drive type {1} with {0} bytes", totalDiskSize, header.driveType);
+ return MediaType.Unknown;
+ }
- }
- }
+ }
+ }
- #endregion
+ #endregion
- #region Unsupported features
+ #region Unsupported features
- public override byte[] ReadSectorTag(ulong sectorAddress, SectorTagType tag)
- {
- throw new FeatureUnsupportedImageException("Feature not supported by image format");
- }
+ public override byte[] ReadSectorTag(ulong sectorAddress, SectorTagType tag)
+ {
+ throw new FeatureUnsupportedImageException("Feature not supported by image format");
+ }
- public override byte[] ReadSectorsTag(ulong sectorAddress, uint length, SectorTagType tag)
- {
- throw new FeatureUnsupportedImageException("Feature not supported by image format");
- }
+ public override byte[] ReadSectorsTag(ulong sectorAddress, uint length, SectorTagType tag)
+ {
+ throw new FeatureUnsupportedImageException("Feature not supported by image format");
+ }
- public override byte[] ReadDiskTag(MediaTagType tag)
- {
- throw new FeatureUnsupportedImageException("Feature not supported by image format");
- }
+ public override byte[] ReadDiskTag(MediaTagType tag)
+ {
+ throw new FeatureUnsupportedImageException("Feature not supported by image format");
+ }
- public override string GetImageCreator()
- {
- return ImageInfo.imageCreator;
- }
+ public override string GetImageCreator()
+ {
+ return ImageInfo.imageCreator;
+ }
- public override string GetImageComments()
- {
- return ImageInfo.imageComments;
- }
+ public override string GetImageComments()
+ {
+ return ImageInfo.imageComments;
+ }
- public override string GetMediaManufacturer()
- {
- return ImageInfo.mediaManufacturer;
- }
+ public override string GetMediaManufacturer()
+ {
+ return ImageInfo.mediaManufacturer;
+ }
- public override string GetMediaModel()
- {
- return ImageInfo.mediaModel;
- }
+ public override string GetMediaModel()
+ {
+ return ImageInfo.mediaModel;
+ }
- public override string GetMediaSerialNumber()
- {
- return ImageInfo.mediaSerialNumber;
- }
+ public override string GetMediaSerialNumber()
+ {
+ return ImageInfo.mediaSerialNumber;
+ }
- public override string GetMediaBarcode()
- {
- return ImageInfo.mediaBarcode;
- }
+ public override string GetMediaBarcode()
+ {
+ return ImageInfo.mediaBarcode;
+ }
- public override string GetMediaPartNumber()
- {
- return ImageInfo.mediaPartNumber;
- }
+ public override string GetMediaPartNumber()
+ {
+ return ImageInfo.mediaPartNumber;
+ }
- public override int GetMediaSequence()
- {
- return ImageInfo.mediaSequence;
- }
+ public override int GetMediaSequence()
+ {
+ return ImageInfo.mediaSequence;
+ }
- public override int GetLastDiskSequence()
- {
- return ImageInfo.lastMediaSequence;
- }
+ public override int GetLastDiskSequence()
+ {
+ return ImageInfo.lastMediaSequence;
+ }
- public override string GetDriveManufacturer()
- {
- return ImageInfo.driveManufacturer;
- }
+ public override string GetDriveManufacturer()
+ {
+ return ImageInfo.driveManufacturer;
+ }
- public override string GetDriveModel()
- {
- return ImageInfo.driveModel;
- }
+ public override string GetDriveModel()
+ {
+ return ImageInfo.driveModel;
+ }
- public override string GetDriveSerialNumber()
- {
- return ImageInfo.driveSerialNumber;
- }
+ public override string GetDriveSerialNumber()
+ {
+ return ImageInfo.driveSerialNumber;
+ }
- public override List GetPartitions()
- {
- throw new FeatureUnsupportedImageException("Feature not supported by image format");
- }
+ public override List GetPartitions()
+ {
+ throw new FeatureUnsupportedImageException("Feature not supported by image format");
+ }
- public override List