diff --git a/FileSystemIDandChk/ChangeLog b/FileSystemIDandChk/ChangeLog index 1382a1d2..91d04e46 100644 --- a/FileSystemIDandChk/ChangeLog +++ b/FileSystemIDandChk/ChangeLog @@ -1,3 +1,12 @@ +2014-04-15 Natalia Portillo + + * FileSystemIDandChk.csproj: + * ImagePlugins/DiskCopy42.cs: + Added support for Apple DiskCopy 4.2 format + + * ImagePlugins/ImagePlugin.cs: + Added standard IBM, DEC and Apple floppy formats + 2014-04-14 Natalia Portillo * Main.cs: diff --git a/FileSystemIDandChk/FileSystemIDandChk.csproj b/FileSystemIDandChk/FileSystemIDandChk.csproj index 0be0c252..10ce540d 100644 --- a/FileSystemIDandChk/FileSystemIDandChk.csproj +++ b/FileSystemIDandChk/FileSystemIDandChk.csproj @@ -70,6 +70,7 @@ + diff --git a/FileSystemIDandChk/ImagePlugins/DiskCopy42.cs b/FileSystemIDandChk/ImagePlugins/DiskCopy42.cs new file mode 100644 index 00000000..b6ae07ef --- /dev/null +++ b/FileSystemIDandChk/ImagePlugins/DiskCopy42.cs @@ -0,0 +1,550 @@ +using System; + +// Checked using several images and strings inside Apple's DiskImages.framework +using System.IO; +using System.Collections.Generic; + +namespace FileSystemIDandChk.ImagePlugins +{ + class DiskCopy42 : ImagePlugin + { + #region Internal Structures + + // DiskCopy 4.2 header, big-endian, data-fork, start of file, 84 bytes + struct DC42Header + { + // 0x00, 64 bytes, pascal string, disk name or "-not a Macintosh disk-", filled with garbage + public string diskName; + // 0x40, size of data in bytes (usually sectors*512) + public UInt32 dataSize; + // 0x44, size of tags in bytes (usually sectors*12) + public UInt32 tagSize; + // 0x48, checksum of data bytes + public UInt32 dataChecksum; + // 0x4C, checksum of tag bytes + public UInt32 tagChecksum; + // 0x50, format of disk, see constants + public byte format; + // 0x51, format of sectors, see constants + public byte fmtByte; + // 0x52, is disk image valid? always 0x01 + public byte valid; + // 0x54, reserved, always 0x00 + public byte reserved; + } + + #endregion + + #region Internal Constants + + // format byte + // 3.5", single side, double density, GCR + const byte kSonyFormat400K = 0x00; + // 3.5", double side, double density, GCR + const byte kSonyFormat800K = 0x01; + // 3.5", double side, double density, MFM + const byte kSonyFormat720K = 0x02; + // 3.5", double side, high density, MFM + const byte kSonyFormat1440K = 0x03; + // 3.5", double side, high density, MFM, 21 sectors/track (aka, Microsoft DMF) + // Unchecked value + const byte kSonyFormat1680K = 0x04; + // There should be a value for Apple HD20 hard disks, unknown... + // fmyByte byte + // Based on GCR nibble + // Always 0x02 for MFM disks + // Unknown for Apple HD20 + // 3.5" single side double density GCR and MFM all use same code + const byte kSonyFmtByte400K = 0x02; + const byte kSonyFmtByte720K = kSonyFmtByte400K; + const byte kSonyFmtByte1440K = kSonyFmtByte400K; + const byte kSonyFmtByte1680K = kSonyFmtByte400K; + // 3.5" double side double density GCR, 512 bytes/sector, interleave 2:1 + const byte kSonyFmtByte800K = 0x22; + // 3.5" double side double density GCR, 512 bytes/sector, interleave 2:1, incorrect value (but appears on official documentation) + const byte kSonyFmtByte800KIncorrect = 0x12; + // 3.5" double side double density GCR, ProDOS format, interleave 4:1 + const byte kSonyFmtByteProDos = 0x24; + // Unformatted sectors + const byte kInvalidFmtByte = 0x96; + + #endregion + + #region Internal variables + + // Start of data sectors in disk image, should be 0x58 + UInt32 dataOffset; + // Start of tags in disk image, after data sectors + UInt32 tagOffset; + // Sectors + UInt32 sectors; + // Bytes per sector, should be 512 + UInt32 bps; + // Bytes per tag, should be 12 + UInt32 bptag; + // Header of opened image + DC42Header header; + // Disk image file + string dc42ImagePath; + + #endregion + + public DiskCopy42(PluginBase Core) + { + Name = "Apple DiskCopy 4.2 handler"; + PluginUUID = new Guid("0240B7B1-E959-4CDC-B0BD-386D6E467B88"); + } + + public override bool IdentifyImage(string imagePath) + { + FileStream stream = new FileStream(imagePath, FileMode.Open, FileAccess.Read); + stream.Seek(0, SeekOrigin.Begin); + byte[] buffer = new byte[0x58]; + byte[] pString = new byte[64]; + stream.Read(buffer, 0, 0x58); + + // Incorrect pascal string length, not DC42 + if (buffer[0] > 63) + return false; + + DC42Header tmp_header = new DC42Header(); + + Array.Copy(buffer, 0, pString, 0, 64); + tmp_header.diskName = StringHandlers.PascalToString(pString); + tmp_header.dataSize = BigEndianBitConverter.ToUInt32(buffer, 0x40); + tmp_header.tagSize = BigEndianBitConverter.ToUInt32(buffer, 0x44); + tmp_header.dataChecksum = BigEndianBitConverter.ToUInt32(buffer, 0x48); + tmp_header.tagChecksum = BigEndianBitConverter.ToUInt32(buffer, 0x4C); + tmp_header.format = buffer[0x50]; + tmp_header.fmtByte = buffer[0x51]; + tmp_header.valid = buffer[0x52]; + tmp_header.reserved = buffer[0x54]; + + if (MainClass.isDebug) + { + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.diskName = \"{0}\"", tmp_header.diskName); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.dataSize = {0} bytes", tmp_header.dataSize); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.tagSize = {0} bytes", tmp_header.tagSize); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.dataChecksum = 0x{0:X8}", tmp_header.dataChecksum); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.tagChecksum = 0x{0:X8}", tmp_header.tagChecksum); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.format = 0x{0:X2}", tmp_header.format); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.fmtByte = 0x{0:X2}", tmp_header.fmtByte); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.valid = {0}", tmp_header.valid); + Console.WriteLine("DEBUG (CDRWin plugin): tmp_header.reserved = {0}", tmp_header.reserved); + } + + if (tmp_header.valid != 1 || tmp_header.reserved != 0) + return false; + + FileInfo fi = new FileInfo(dc42ImagePath); + + if (tmp_header.dataSize + tmp_header.tagSize + 0x54 != fi.Length) + return false; + + if (tmp_header.format != kSonyFormat400K && tmp_header.format != kSonyFormat800K && tmp_header.format != kSonyFormat720K && + tmp_header.format != kSonyFormat1440K && tmp_header.format != kSonyFormat1680K) + { + if (MainClass.isDebug) + Console.WriteLine("Unknown tmp_header.format = 0x{0:X2} value", tmp_header.format); + + return false; + } + + if (tmp_header.fmtByte != kSonyFmtByte400K && tmp_header.fmtByte != kSonyFmtByte800K && tmp_header.fmtByte != kSonyFmtByte800KIncorrect && + tmp_header.fmtByte != kSonyFmtByteProDos && tmp_header.fmtByte != kInvalidFmtByte) + { + if (MainClass.isDebug) + Console.WriteLine("Unknown tmp_header.fmtByte = 0x{0:X2} value", tmp_header.fmtByte); + + return false; + } + + if (tmp_header.fmtByte == kInvalidFmtByte) + { + if (MainClass.isDebug) + Console.WriteLine("Image says it's unformatted"); + + return false; + } + + return true; + } + + public override bool OpenImage(string imagePath) + { + FileStream stream = new FileStream(imagePath, FileMode.Open, FileAccess.Read); + stream.Seek(0, SeekOrigin.Begin); + byte[] buffer = new byte[0x58]; + byte[] pString = new byte[64]; + stream.Read(buffer, 0, 0x58); + + // Incorrect pascal string length, not DC42 + if (buffer[0] > 63) + return false; + + header = new DC42Header(); + + Array.Copy(buffer, 0, pString, 0, 64); + header.diskName = StringHandlers.PascalToString(pString); + header.dataSize = BigEndianBitConverter.ToUInt32(buffer, 0x40); + header.tagSize = BigEndianBitConverter.ToUInt32(buffer, 0x44); + header.dataChecksum = BigEndianBitConverter.ToUInt32(buffer, 0x48); + header.tagChecksum = BigEndianBitConverter.ToUInt32(buffer, 0x4C); + header.format = buffer[0x50]; + header.fmtByte = buffer[0x51]; + header.valid = buffer[0x52]; + header.reserved = buffer[0x54]; + + if (MainClass.isDebug) + { + Console.WriteLine("DEBUG (CDRWin plugin): header.diskName = \"{0}\"", header.diskName); + Console.WriteLine("DEBUG (CDRWin plugin): header.dataSize = {0} bytes", header.dataSize); + Console.WriteLine("DEBUG (CDRWin plugin): header.tagSize = {0} bytes", header.tagSize); + Console.WriteLine("DEBUG (CDRWin plugin): header.dataChecksum = 0x{0:X8}", header.dataChecksum); + Console.WriteLine("DEBUG (CDRWin plugin): header.tagChecksum = 0x{0:X8}", header.tagChecksum); + Console.WriteLine("DEBUG (CDRWin plugin): header.format = 0x{0:X2}", header.format); + Console.WriteLine("DEBUG (CDRWin plugin): header.fmtByte = 0x{0:X2}", header.fmtByte); + Console.WriteLine("DEBUG (CDRWin plugin): header.valid = {0}", header.valid); + Console.WriteLine("DEBUG (CDRWin plugin): header.reserved = {0}", header.reserved); + } + + if (header.valid != 1 || header.reserved != 0) + return false; + + FileInfo fi = new FileInfo(dc42ImagePath); + + if (header.dataSize + header.tagSize + 0x54 != fi.Length) + return false; + + if (header.format != kSonyFormat400K && header.format != kSonyFormat800K && header.format != kSonyFormat720K && + header.format != kSonyFormat1440K && header.format != kSonyFormat1680K) + { + if (MainClass.isDebug) + Console.WriteLine("DEBUG (CDRWin plugin): Unknown header.format = 0x{0:X2} value", header.format); + + return false; + } + + if (header.fmtByte != kSonyFmtByte400K && header.fmtByte != kSonyFmtByte800K && header.fmtByte != kSonyFmtByte800KIncorrect && + header.fmtByte != kSonyFmtByteProDos && header.fmtByte != kInvalidFmtByte) + { + if (MainClass.isDebug) + Console.WriteLine("DEBUG (CDRWin plugin): Unknown tmp_header.fmtByte = 0x{0:X2} value", header.fmtByte); + + return false; + } + + if (header.fmtByte == kInvalidFmtByte) + { + if (MainClass.isDebug) + Console.WriteLine("DEBUG (CDRWin plugin): Image says it's unformatted"); + + return false; + } + + dataOffset = 0x54; + tagOffset = header.tagSize != 0 ? 0x54 + header.dataSize : 0; + bps = 512; + bptag = (uint)(header.tagSize != 0 ? 12 : 0); + dc42ImagePath = imagePath; + + sectors = header.dataSize / 512; + + if (header.tagSize != 0) + { + if (header.tagSize / 12 != sectors) + { + if (MainClass.isDebug) + Console.WriteLine("DEBUG (CDRWin plugin): header.tagSize / 12 != sectors"); + + return false; + } + } + + return true; + } + + public override bool ImageHasPartitions() + { + return false; + } + + public override UInt64 GetImageSize() + { + return sectors * bps + sectors * bptag; + } + + public override UInt64 GetSectors() + { + return sectors; + } + + public override UInt32 GetSectorSize() + { + return bps; + } + + public override byte[] ReadSector(UInt64 sectorAddress) + { + return ReadSectors(sectorAddress, 1); + } + + public override byte[] ReadSectorTag(UInt64 sectorAddress, SectorTagType tag) + { + return ReadSectorsTag(sectorAddress, 1, tag); + } + + public override byte[] ReadSectors(UInt64 sectorAddress, UInt32 length) + { + if (sectorAddress > sectors - 1) + throw new ArgumentOutOfRangeException("sectorAddress", "Sector address not found"); + + if (sectorAddress + length > sectors) + throw new ArgumentOutOfRangeException("length", "Requested more sectors than available"); + + byte[] buffer = new byte[length * bps]; + + FileStream stream = new FileStream(dc42ImagePath, FileMode.Open, FileAccess.Read); + + stream.Seek((long)(dataOffset + sectorAddress * bps), SeekOrigin.Begin); + + stream.Read(buffer, 0, (int)(length * bps)); + + return buffer; + } + + public override byte[] ReadSectorsTag(UInt64 sectorAddress, UInt32 length, SectorTagType tag) + { + if (tag != SectorTagType.AppleSectorTag) + throw new FeatureUnsupportedImageException(String.Format("Tag {0} not supported by image format", tag)); + + if (header.tagSize == 0) + throw new FeatureNotPresentImageException("Disk image does not have tags"); + + if (sectorAddress > sectors - 1) + throw new ArgumentOutOfRangeException("sectorAddress", "Sector address not found"); + + if (sectorAddress + length > sectors) + throw new ArgumentOutOfRangeException("length", "Requested more sectors than available"); + + byte[] buffer = new byte[length * bptag]; + + FileStream stream = new FileStream(dc42ImagePath, FileMode.Open, FileAccess.Read); + + stream.Seek((long)(tagOffset + sectorAddress * bptag), SeekOrigin.Begin); + + stream.Read(buffer, 0, (int)(length * bptag)); + + return buffer; + } + + public override byte[] ReadSectorLong(UInt64 sectorAddress) + { + return ReadSectorsLong(sectorAddress, 1); + } + + public override byte[] ReadSectorsLong(UInt64 sectorAddress, UInt32 length) + { + if (sectorAddress > sectors - 1) + throw new ArgumentOutOfRangeException("sectorAddress", "Sector address not found"); + + if (sectorAddress + length > sectors) + throw new ArgumentOutOfRangeException("length", "Requested more sectors than available"); + + byte[] data = ReadSectors(sectorAddress, length); + byte[] tags = ReadSectorsTag(sectorAddress, length, SectorTagType.AppleSectorTag); + byte[] buffer = new byte[data.Length + tags.Length]; + + for (uint i = 0; i < length; i++) + { + Array.Copy(data, i * (bps), buffer, i * (bps + bptag), bps); + Array.Copy(tags, i * (bptag), buffer, i * (bps + bptag) + bps, bptag); + } + + return buffer; + } + + public override string GetImageFormat() + { + return "Apple DiskCopy 4.2"; + } + + public override string GetImageVersion() + { + return "4.2"; + } + + public override string GetImageApplication() + { + return "Apple DiskCopy"; + } + + public override string GetImageApplicationVersion() + { + return "4.2"; + } + + public override DateTime GetImageCreationTime() + { + FileInfo fi = new FileInfo(dc42ImagePath); + + return fi.CreationTimeUtc; + } + + public override DateTime GetImageLastModificationTime() + { + FileInfo fi = new FileInfo(dc42ImagePath); + + return fi.LastWriteTimeUtc; + } + + public override string GetImageName() + { + return header.diskName; + } + + public override DiskType GetDiskType() + { + switch (header.format) + { + case kSonyFormat400K: + return DiskType.AppleSonySS; + case kSonyFormat800K: + return DiskType.AppleSonyDS; + case kSonyFormat720K: + return DiskType.DOS_35_DS_DD_9; + case kSonyFormat1440K: + return DiskType.DOS_35_HD; + case kSonyFormat1680K: + return DiskType.DMF; + default: + return DiskType.Unknown; + } + } + + #region Unsupported features + + public override byte[] ReadDiskTag(DiskTagType tag) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetImageCreator() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetImageComments() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDiskManufacturer() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDiskModel() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDiskSerialNumber() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDiskBarcode() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDiskPartNumber() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override int GetDiskSequence() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override int GetLastDiskSequence() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDriveManufacturer() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDriveModel() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override string GetDriveSerialNumber() + { + 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 GetTracks() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override List GetSessionTracks(Session session) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override List GetSessionTracks(UInt16 session) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override List GetSessions() + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSector(UInt64 sectorAddress, UInt32 track) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSectorTag(UInt64 sectorAddress, UInt32 track, SectorTagType tag) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSectors(UInt64 sectorAddress, UInt32 length, UInt32 track) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSectorsTag(UInt64 sectorAddress, UInt32 length, UInt32 track, SectorTagType tag) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSectorLong(UInt64 sectorAddress, UInt32 track) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + public override byte[] ReadSectorsLong(UInt64 sectorAddress, UInt32 length, UInt32 track) + { + throw new FeatureUnsupportedImageException("Feature not supported by image format"); + } + + #endregion Unsupported features + } +} + diff --git a/FileSystemIDandChk/ImagePlugins/ImagePlugin.cs b/FileSystemIDandChk/ImagePlugins/ImagePlugin.cs index 3433a8eb..807f5d40 100644 --- a/FileSystemIDandChk/ImagePlugins/ImagePlugin.cs +++ b/FileSystemIDandChk/ImagePlugins/ImagePlugin.cs @@ -118,148 +118,215 @@ namespace FileSystemIDandChk.ImagePlugins { Unknown, // Somewhat standard Compact Disc formats - CDDA, // CD Digital Audio (Red Book) - CDG, + CDDA, // CD+G (Red Book) - CDEG, + CDG, // CD+EG (Red Book) - CDI, + CDEG, // CD-i (Green Book) - CDROM, + CDI, // CD-ROM (Yellow Book) - CDROMXA, + CDROM, // CD-ROM XA (Yellow Book) - CDPLUS, + CDROMXA, // CD+ (Blue Book) - CDMO, + CDPLUS, // CD-MO (Orange Book) - CDR, + CDMO, // CD-Recordable (Orange Book) - CDRW, + CDR, // CD-ReWritable (Orange Book) - CDMRW, + CDRW, // Mount-Rainier CD-RW - VCD, + CDMRW, // Video CD (White Book) - SVCD, + VCD, // Super Video CD (White Book) - PCD, + SVCD, // Photo CD (Beige Book) - SACD, + PCD, // Super Audio CD (Scarlet Book) - DDCD, + SACD, // Double-Density CD-ROM (Purple Book) - DDCDR, + DDCD, // DD CD-R (Purple Book) - DDCDRW, + DDCDR, // DD CD-RW (Purple Book) - DTSCD, + DDCDRW, // DTS audio CD (non-standard) - CDMIDI, + DTSCD, // CD-MIDI (Red Book) - CD, + CDMIDI, // Any unknown or standard violating CD + CD, // Standard DVD formats - DVDROM, // DVD-ROM (applies to DVD Video and DVD Audio) - DVDR, + DVDROM, // DVD-R - DVDRW, + DVDR, // DVD-RW - DVDPR, + DVDRW, // DVD+R - DVDPRW, + DVDPR, // DVD+RW - DVDPRWDL, + DVDPRW, // DVD+RW DL - DVDRDL, + DVDPRWDL, // DVD-R DL - DVDPRDL, + DVDRDL, // DVD+R DL - DVDRAM, + DVDPRDL, // DVD-RAM + DVDRAM, // Standard HD-DVD formats - HDDVDROM, // HD DVD-ROM (applies to HD DVD Video) - HDDVDRAM, + HDDVDROM, // HD DVD-RAM - HDDVDR, + HDDVDRAM, // HD DVD-R - HDDVDRW, + HDDVDR, // HD DVD-RW + HDDVDRW, // Standard Blu-ray formats - BDROM, // BD-ROM (and BD Video) - BDR, + BDROM, // BD-R - BDRE, + BDR, // BD-RE + BDRE, // Rare or uncommon standards - EVD, // Enhanced Versatile Disc - FVD, + EVD, // Forward Versatile Disc - HVD, + FVD, // Holographic Versatile Disc - CBHD, + HVD, // China Blue High Definition - HDVMD, + CBHD, // High Definition Versatile Multilayer Disc - VCDHD, + HDVMD, // Versatile Compact Disc High Density - LD, + VCDHD, // Pioneer LaserDisc - LDROM, + LD, // Pioneer LaserDisc data - MD, + LDROM, // Sony MiniDisc - HiMD, + MD, // Sony Hi-MD - UDO, + HiMD, // Ultra Density Optical - SVOD, + UDO, // Stacked Volumetric Optical Disc - FDDVD, + SVOD, // Five Dimensional disc + FDDVD, // Propietary game discs - PS1CD, // Sony PlayStation game CD - PS2CD, + PS1CD, // Sony PlayStation 2 game CD - PS2DVD, + PS2CD, // Sony PlayStation 2 game DVD - PS3DVD, + PS2DVD, // Sony PlayStation 3 game DVD - PS3BD, + PS3DVD, // Sony PlayStation 3 game Blu-ray - PS4BD, + PS3BD, // Sony PlayStation 4 game Blu-ray - UMD, + PS4BD, // Sony PlayStation Portable Universal Media Disc (ECMA-365) - GOD, + UMD, // Nintendo GameCube Optical Disc - WOD, + GOD, // Nintendo Wii Optical Disc - WUOD, + WOD, // Nintendo Wii U Optical Disc - XGD, + WUOD, // Microsoft X-box Game Disc + XGD, + // Microsoft X-box 360 Game Disc XGD2, // Microsoft X-box 360 Game Disc XGD3, - // Microsoft X-box 360 Game Disc - XGD4, // Microsoft X-box One Game Disc - MEGACD, + XGD4, // Sega MegaCD - SATURNCD, + MEGACD, // Sega Saturn disc - GDROM, + SATURNCD, // Sega/Yamaha Gigabyte Disc - GDR + GDROM, // Sega/Yamaha recordable Gigabyte Disc}} - + GDR, + // Apple standard floppy formats + // 5.25", SS, DD, 35 tracks, 13 spt, 256 bytes/sector, GCR + Apple32SS, + // 5.25", DS, DD, 35 tracks, 13 spt, 256 bytes/sector, GCR + Apple32DS, + // 5.25", SS, DD, 35 tracks, 16 spt, 256 bytes/sector, GCR + Apple33SS, + // 5.25", DS, DD, 35 tracks, 16 spt, 256 bytes/sector, GCR + Apple33DS, + // 3.5", SS, DD, 80 tracks, 8 to 12 spt, 512 bytes/sector, GCR + AppleSonySS, + // 3.5", DS, DD, 80 tracks, 8 to 12 spt, 512 bytes/sector, GCR + AppleSonyDS, + // IBM/Microsoft PC standard floppy formats + // 5.25", SS, DD, 40 tracks, 8 spt, 512 bytes/sector, MFM + DOS_525_SS_DD_8, + // 5.25", SS, DD, 40 tracks, 9 spt, 512 bytes/sector, MFM + DOS_525_SS_DD_9, + // 5.25", DS, DD, 40 tracks, 8 spt, 512 bytes/sector, MFM + DOS_525_DS_DD_8, + // 5.25", DS, DD, 40 tracks, 9 spt, 512 bytes/sector, MFM + DOS_525_DS_DD_9, + // 5.25", DS, HD, 80 tracks, 15 spt, 512 bytes/sector, MFM + DOS_525_HD, + // 3.5", SS, DD, 80 tracks, 8 spt, 512 bytes/sector, MFM + DOS_35_SS_DD_8, + // 3.5", SS, DD, 80 tracks, 9 spt, 512 bytes/sector, MFM + DOS_35_SS_DD_9, + // 3.5", DS, DD, 80 tracks, 8 spt, 512 bytes/sector, MFM + DOS_35_DS_DD_8, + // 3.5", DS, DD, 80 tracks, 9 spt, 512 bytes/sector, MFM + DOS_35_DS_DD_9, + // 3.5", DS, HD, 80 tracks, 18 spt, 512 bytes/sector, MFM + DOS_35_HD, + // 3.5", DS, ED, 80 tracks, 36 spt, 512 bytes/sector, MFM + DOS_35_ED, + // Microsoft non standard floppy formats + // 3.5", DS, DD, 80 tracks, 21 spt, 512 bytes/sector, MFM + DMF, + // 3.5", DS, DD, 82 tracks, 21 spt, 512 bytes/sector, MFM + DMF_82, + // IBM non standard floppy formats + XDF_525, + XDF_35, + // IBM standard floppy formats + // 8", SS, SD, 32 tracks, 8 spt, 319 bytes/sector, FM + IBM23FD, + // 8", SS, SD, 73 tracks, 26 spt, 128 bytes/sector, FM + IBM33FD_128, + // 8", SS, SD, 74 tracks, 15 spt, 256 bytes/sector, FM, track 0 = 26 sectors, 128 bytes/sector + IBM33FD_256, + // 8", SS, SD, 74 tracks, 8 spt, 512 bytes/sector, FM, track 0 = 26 sectors, 128 bytes/sector + IBM33FD_512, + // 8", DS, SD, 74 tracks, 26 spt, 128 bytes/sector, FM, track 0 = 26 sectors, 128 bytes/sector + IBM43FD_128, + // 8", DS, SD, 74 tracks, 26 spt, 256 bytes/sector, FM, track 0 = 26 sectors, 128 bytes/sector + IBM43FD_256, + // 8", DS, DD, 74 tracks, 26 spt, 256 bytes/sector, MFM, track 0 side 0 = 26 sectors, 128 bytes/sector, track 0 side 1 = 26 sectors, 128 bytes/sector + IBM53FD_256, + // 8", DS, DD, 74 tracks, 15 spt, 512 bytes/sector, MFM, track 0 side 0 = 26 sectors, 128 bytes/sector, track 0 side 1 = 26 sectors, 128 bytes/sector + IBM53FD_512, + // 8", DS, DD, 74 tracks, 8 spt, 1024 bytes/sector, MFM, track 0 side 0 = 26 sectors, 128 bytes/sector, track 0 side 1 = 26 sectors, 128 bytes/sector + IBM53FD_1024, + // DEC standard floppy formats + // 8", SS, DD, 77 tracks, 26 spt, 128 bytes/sector, FM + RX01, + // 8", SS, DD, 77 tracks, 26 spt, 256 bytes/sector, FM/MFM + RX02 }; // Track (as partitioning element) types public enum TrackType @@ -316,7 +383,7 @@ namespace FileSystemIDandChk.ImagePlugins public enum SectorTagType { AppleSectorTag, - // Apple's GCR sector tags, 20 bytes + // Apple's GCR sector tags, 12 bytes CDSectorSync, // Sync frame from CD sector, 12 bytes CDSectorHeader,