diff --git a/SabreTools.Serialization/Wrappers/WrapperFactory.cs b/SabreTools.Serialization/Wrappers/WrapperFactory.cs
index 79c6557e..6f4ed2f8 100644
--- a/SabreTools.Serialization/Wrappers/WrapperFactory.cs
+++ b/SabreTools.Serialization/Wrappers/WrapperFactory.cs
@@ -116,15 +116,18 @@ namespace SabreTools.Serialization.Wrappers
}
///
- /// Get the supported file type for a magic string
+ /// Get the supported file type for a magic string and an extension
///
/// Recommend sending in 16 bytes to check
- public static WrapperType GetFileType(byte[] magic)
+ public static WrapperType GetFileType(byte[]? magic, string? extension)
{
- // If we have an invalid magic byte array
- if (magic == null || magic.Length == 0)
+ // If we have an invalid magic byte array and extension
+ if (magic == null || magic.Length == 0 || extension == null)
return WrapperType.UNKNOWN;
+ // Normalize the extension
+ extension = extension.TrimStart('.').Trim();
+
// TODO: For all modelled types, use the constants instead of hardcoded values here
#region AACSMediaKeyBlock
@@ -136,6 +139,15 @@ namespace SabreTools.Serialization.Wrappers
if (magic.StartsWith(new byte?[] { 0x10, 0x00, 0x00, 0x0C }))
return WrapperType.AACSMediaKeyBlock;
+ // Shares an extension with INF setup information so it can't be used accurately
+ // Blu-ray
+ // if (extension.Equals("inf", StringComparison.OrdinalIgnoreCase))
+ // return WrapperType.AACSMediaKeyBlock;
+
+ // HD-DVD
+ if (extension.Equals("aacs", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.AACSMediaKeyBlock;
+
#endregion
#region BDPlusSVM
@@ -143,6 +155,9 @@ namespace SabreTools.Serialization.Wrappers
if (magic.StartsWith(new byte?[] { 0x42, 0x44, 0x53, 0x56, 0x4D, 0x5F, 0x43, 0x43 }))
return WrapperType.BDPlusSVM;
+ if (extension.Equals("svm", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.BDPlusSVM;
+
#endregion
#region BFPK
@@ -154,7 +169,14 @@ namespace SabreTools.Serialization.Wrappers
#region BSP
- if (magic.StartsWith(new byte?[] { 0x1e, 0x00, 0x00, 0x00 }))
+ // Shares a first 4 bytes with some .mc files
+ // Shares an extension with VBSP
+ if (magic.StartsWith(new byte?[] { 0x1d, 0x00, 0x00, 0x00 }) && extension.Equals("bsp", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.BSP;
+
+ // Shares a first 4 bytes with some .mc files
+ // Shares an extension with VBSP
+ if (magic.StartsWith(new byte?[] { 0x1e, 0x00, 0x00, 0x00 }) && extension.Equals("bsp", StringComparison.OrdinalIgnoreCase))
return WrapperType.BSP;
#endregion
@@ -164,6 +186,9 @@ namespace SabreTools.Serialization.Wrappers
if (magic.StartsWith(new byte?[] { 0x42, 0x52, 0x68 }))
return WrapperType.BZip2;
+ if (extension.Equals("bz2", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.BZip2;
+
#endregion
#region CFB
@@ -171,11 +196,32 @@ namespace SabreTools.Serialization.Wrappers
if (magic.StartsWith(new byte?[] { 0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1 }))
return WrapperType.CFB;
+ // Installer package
+ if (extension.Equals("msi", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CFB;
+
+ // Merge module
+ else if (extension.Equals("msm", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CFB;
+
+ // Patch Package
+ else if (extension.Equals("msp", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CFB;
+
+ // Transform
+ else if (extension.Equals("mst", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CFB;
+
+ // Patch Creation Properties
+ else if (extension.Equals("pcp", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CFB;
+
#endregion
#region CIA
- // No magic checks for CIA
+ if (extension.Equals("cia", StringComparison.OrdinalIgnoreCase))
+ return WrapperType.CIA;
#endregion
@@ -213,369 +259,6 @@ namespace SabreTools.Serialization.Wrappers
return FileTypes.Executable;
*/
- #endregion
-
- #region GCF
-
- if (magic.StartsWith(new byte?[] { 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00 }))
- return WrapperType.GCF;
-
- #endregion
-
- #region GZIP
-
- if (magic.StartsWith(new byte?[] { 0x1f, 0x8b }))
- return WrapperType.GZIP;
-
- #endregion
-
- #region IniFile
-
- // No magic checks for IniFile
-
- #endregion
-
- #region InstallShieldArchiveV3
-
- if (magic.StartsWith(new byte?[] { 0x13, 0x5D, 0x65, 0x8C }))
- return WrapperType.InstallShieldArchiveV3;
-
- #endregion
-
- #region InstallShieldCAB
-
- if (magic.StartsWith(new byte?[] { 0x49, 0x53, 0x63 }))
- return WrapperType.InstallShieldCAB;
-
- #endregion
-
- #region LDSCRYPT
-
- if (magic.StartsWith(new byte?[] { 0x4C, 0x44, 0x53, 0x43, 0x52, 0x59, 0x50, 0x54 }))
- return WrapperType.LDSCRYPT;
-
- #endregion
-
- #region MicrosoftCAB
-
- if (magic.StartsWith(new byte?[] { 0x4d, 0x53, 0x43, 0x46 }))
- return WrapperType.MicrosoftCAB;
-
- #endregion
-
- #region MicrosoftLZ
-
- if (magic.StartsWith(new byte?[] { 0x53, 0x5a, 0x44, 0x44, 0x88, 0xf0, 0x27, 0x33 }))
- return WrapperType.MicrosoftLZ;
-
- #endregion
-
- #region MPQ
-
- if (magic.StartsWith(new byte?[] { 0x4d, 0x50, 0x51, 0x1a }))
- return WrapperType.MoPaQ;
-
- if (magic.StartsWith(new byte?[] { 0x4d, 0x50, 0x51, 0x1b }))
- return WrapperType.MoPaQ;
-
- #endregion
-
- #region N3DS
-
- // No magic checks for N3DS
-
- #endregion
-
- #region NCF
-
- if (magic.StartsWith(new byte?[] { 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00 }))
- return WrapperType.NCF;
-
- #endregion
-
- #region Nitro
-
- // No magic checks for Nitro
-
- #endregion
-
- #region PAK
-
- if (magic.StartsWith(new byte?[] { 0x50, 0x41, 0x43, 0x4B }))
- return WrapperType.PAK;
-
- #endregion
-
- #region PFF
-
- // Version 2
- if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x32 }))
- return WrapperType.PFF;
-
- // Version 3
- if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x33 }))
- return WrapperType.PFF;
-
- // Version 4
- if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x34 }))
- return WrapperType.PFF;
-
- #endregion
-
- #region PKZIP
-
- // PKZIP (Unknown)
- if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x00, 0x00 }))
- return WrapperType.PKZIP;
-
- // PKZIP
- if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x03, 0x04 }))
- return WrapperType.PKZIP;
-
- // PKZIP (Empty Archive)
- if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x05, 0x06 }))
- return WrapperType.PKZIP;
-
- // PKZIP (Spanned Archive)
- if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x07, 0x08 }))
- return WrapperType.PKZIP;
-
- #endregion
-
- #region PLJ
-
- // https://www.iana.org/assignments/media-types/audio/vnd.everad.plj
- if (magic.StartsWith(new byte?[] { 0xFF, 0x9D, 0x53, 0x4B }))
- return WrapperType.PlayJAudioFile;
-
- #endregion
-
- #region Quantum
-
- if (magic.StartsWith(new byte?[] { 0x44, 0x53 }))
- return WrapperType.Quantum;
-
- #endregion
-
- #region RAR
-
- // RAR archive version 1.50 onwards
- if (magic.StartsWith(new byte?[] { 0x52, 0x61, 0x72, 0x21, 0x1a, 0x07, 0x00 }))
- return WrapperType.RAR;
-
- // RAR archive version 5.0 onwards
- if (magic.StartsWith(new byte?[] { 0x52, 0x61, 0x72, 0x21, 0x1a, 0x07, 0x01, 0x00 }))
- return WrapperType.RAR;
-
- #endregion
-
- #region RealArcade
-
- // RASGI2.0
- // Found in the ".rgs files in IA item "Nova_RealArcadeCD_USA".
- if (magic.StartsWith(new byte?[] { 0x52, 0x41, 0x53, 0x47, 0x49, 0x32, 0x2E, 0x30 }))
- return WrapperType.RealArcadeInstaller;
-
- // XZip2.0
- // Found in the ".mez" files in IA item "Nova_RealArcadeCD_USA".
- if (magic.StartsWith(new byte?[] { 0x58, 0x5A, 0x69, 0x70, 0x32, 0x2E, 0x30 }))
- return WrapperType.RealArcadeMezzanine;
-
- #endregion
-
- #region SevenZip
-
- if (magic.StartsWith(new byte?[] { 0x37, 0x7a, 0xbc, 0xaf, 0x27, 0x1c }))
- return WrapperType.SevenZip;
-
- #endregion
-
- #region SFFS
-
- // Found in Redump entry 81756, confirmed to be "StarForce Filesystem" by PiD.
- if (magic.StartsWith(new byte?[] { 0x53, 0x46, 0x46, 0x53 }))
- return WrapperType.SFFS;
-
- #endregion
-
- #region SGA
-
- if (magic.StartsWith(new byte?[] { 0x5F, 0x41, 0x52, 0x43, 0x48, 0x49, 0x56, 0x45 }))
- return WrapperType.SGA;
-
- #endregion
-
- #region TapeArchive
-
- if (magic.StartsWith(new byte?[] { 0x75, 0x73, 0x74, 0x61, 0x72, 0x00, 0x30, 0x30 }))
- return WrapperType.TapeArchive;
-
- if (magic.StartsWith(new byte?[] { 0x75, 0x73, 0x74, 0x61, 0x72, 0x20, 0x20, 0x00 }))
- return WrapperType.TapeArchive;
-
- #endregion
-
- #region Textfile
-
- // Not all textfiles can be determined through magic number
-
- // HTML
- if (magic.StartsWith(new byte?[] { 0x3c, 0x68, 0x74, 0x6d, 0x6c }))
- return WrapperType.Textfile;
-
- // HTML and XML
- if (magic.StartsWith(new byte?[] { 0x3c, 0x21, 0x44, 0x4f, 0x43, 0x54, 0x59, 0x50, 0x45 }))
- return WrapperType.Textfile;
-
- // InstallShield Compiled Rules
- if (magic.StartsWith(new byte?[] { 0x61, 0x4C, 0x75, 0x5A }))
- return WrapperType.Textfile;
-
- // Microsoft Office File (old)
- if (magic.StartsWith(new byte?[] { 0xd0, 0xcf, 0x11, 0xe0, 0xa1, 0xb1, 0x1a, 0xe1 }))
- return WrapperType.Textfile;
-
- // Rich Text File
- if (magic.StartsWith(new byte?[] { 0x7b, 0x5c, 0x72, 0x74, 0x66, 0x31 }))
- return WrapperType.Textfile;
-
- // Windows Help File
- if (magic.StartsWith(new byte?[] { 0x3F, 0x5F, 0x03, 0x00 }))
- return WrapperType.Textfile;
-
- // XML
- // "
- /// Get the supported file type for an extension
- ///
- /// This is less accurate than a magic string match
- public static WrapperType GetFileType(string extension)
- {
- // If we have an invalid extension
- if (string.IsNullOrEmpty(extension))
- return WrapperType.UNKNOWN;
-
- // Normalize the extension
- extension = extension.TrimStart('.').Trim();
-
- #region AACSMediaKeyBlock
-
- // Shares an extension with INF setup information so it can't be used accurately
- // Blu-ray
- // if (extension.Equals("inf", StringComparison.OrdinalIgnoreCase))
- // return WrapperType.AACSMediaKeyBlock;
-
- // HD-DVD
- if (extension.Equals("aacs", StringComparison.OrdinalIgnoreCase))
- return WrapperType.AACSMediaKeyBlock;
-
- #endregion
-
- #region BDPlusSVM
-
- if (extension.Equals("svm", StringComparison.OrdinalIgnoreCase))
- return WrapperType.BDPlusSVM;
-
- #endregion
-
- #region BFPK
-
- // No extensions registered for BFPK
-
- #endregion
-
- #region BSP
-
- // Shares an extension with VBSP so it can't be used accurately
- // if (extension.Equals("bsp", StringComparison.OrdinalIgnoreCase))
- // return WrapperType.BSP;
-
- #endregion
-
- #region BZip2
-
- if (extension.Equals("bz2", StringComparison.OrdinalIgnoreCase))
- return WrapperType.BZip2;
-
- #endregion
-
- #region CFB
-
- // Installer package
- if (extension.Equals("msi", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CFB;
-
- // Merge module
- else if (extension.Equals("msm", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CFB;
-
- // Patch Package
- else if (extension.Equals("msp", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CFB;
-
- // Transform
- else if (extension.Equals("mst", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CFB;
-
- // Patch Creation Properties
- else if (extension.Equals("pcp", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CFB;
-
- #endregion
-
- #region CIA
-
- if (extension.Equals("cia", StringComparison.OrdinalIgnoreCase))
- return WrapperType.CIA;
-
- #endregion
-
- #region Executable
-
// DOS MZ executable file format (and descendants)
if (extension.Equals("exe", StringComparison.OrdinalIgnoreCase))
return WrapperType.Executable;
@@ -588,6 +271,9 @@ namespace SabreTools.Serialization.Wrappers
#region GCF
+ if (magic.StartsWith(new byte?[] { 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00 }))
+ return WrapperType.GCF;
+
if (extension.Equals("gcf", StringComparison.OrdinalIgnoreCase))
return WrapperType.GCF;
@@ -595,6 +281,9 @@ namespace SabreTools.Serialization.Wrappers
#region GZIP
+ if (magic.StartsWith(new byte?[] { 0x1f, 0x8b }))
+ return WrapperType.GZIP;
+
if (extension.Equals("gz", StringComparison.OrdinalIgnoreCase))
return WrapperType.GZIP;
@@ -609,6 +298,9 @@ namespace SabreTools.Serialization.Wrappers
#region InstallShieldArchiveV3
+ if (magic.StartsWith(new byte?[] { 0x13, 0x5D, 0x65, 0x8C }))
+ return WrapperType.InstallShieldArchiveV3;
+
if (extension.Equals("z", StringComparison.OrdinalIgnoreCase))
return WrapperType.InstallShieldArchiveV3;
@@ -616,19 +308,43 @@ namespace SabreTools.Serialization.Wrappers
#region InstallShieldCAB
- // No extensions registered for InstallShieldCAB
+ if (magic.StartsWith(new byte?[] { 0x49, 0x53, 0x63 }))
+ return WrapperType.InstallShieldCAB;
+
// Both InstallShieldCAB and MicrosoftCAB share the same extension
#endregion
+ #region LDSCRYPT
+
+ if (magic.StartsWith(new byte?[] { 0x4C, 0x44, 0x53, 0x43, 0x52, 0x59, 0x50, 0x54 }))
+ return WrapperType.LDSCRYPT;
+
+ #endregion
+
#region MicrosoftCAB
- // No extensions registered for InstallShieldCAB
+ if (magic.StartsWith(new byte?[] { 0x4d, 0x53, 0x43, 0x46 }))
+ return WrapperType.MicrosoftCAB;
+
// Both InstallShieldCAB and MicrosoftCAB share the same extension
#endregion
- #region MPQ
+ #region MicrosoftLZ
+
+ if (magic.StartsWith(new byte?[] { 0x53, 0x5a, 0x44, 0x44, 0x88, 0xf0, 0x27, 0x33 }))
+ return WrapperType.MicrosoftLZ;
+
+ #endregion
+
+ #region MoPaQ
+
+ if (magic.StartsWith(new byte?[] { 0x4d, 0x50, 0x51, 0x1a }))
+ return WrapperType.MoPaQ;
+
+ if (magic.StartsWith(new byte?[] { 0x4d, 0x50, 0x51, 0x1b }))
+ return WrapperType.MoPaQ;
if (extension.Equals("mpq", StringComparison.OrdinalIgnoreCase))
return WrapperType.MoPaQ;
@@ -649,6 +365,9 @@ namespace SabreTools.Serialization.Wrappers
#region NCF
+ if (magic.StartsWith(new byte?[] { 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00 }))
+ return WrapperType.NCF;
+
if (extension.Equals("ncf", StringComparison.OrdinalIgnoreCase))
return WrapperType.NCF;
@@ -676,7 +395,9 @@ namespace SabreTools.Serialization.Wrappers
#region PAK
- // No extensions registered for PAK
+ if (magic.StartsWith(new byte?[] { 0x50, 0x41, 0x43, 0x4B }))
+ return WrapperType.PAK;
+
// Both PAK and Quantum share one extension
// if (extension.Equals("pak", StringComparison.OrdinalIgnoreCase))
// return WrapperType.PAK;
@@ -685,6 +406,18 @@ namespace SabreTools.Serialization.Wrappers
#region PFF
+ // Version 2
+ if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x32 }))
+ return WrapperType.PFF;
+
+ // Version 3
+ if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x33 }))
+ return WrapperType.PFF;
+
+ // Version 4
+ if (magic.StartsWith(new byte?[] { 0x14, 0x00, 0x00, 0x00, 0x50, 0x46, 0x46, 0x34 }))
+ return WrapperType.PFF;
+
if (extension.Equals("pff", StringComparison.OrdinalIgnoreCase))
return WrapperType.PFF;
@@ -692,6 +425,22 @@ namespace SabreTools.Serialization.Wrappers
#region PKZIP
+ // PKZIP (Unknown)
+ if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x00, 0x00 }))
+ return WrapperType.PKZIP;
+
+ // PKZIP
+ if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x03, 0x04 }))
+ return WrapperType.PKZIP;
+
+ // PKZIP (Empty Archive)
+ if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x05, 0x06 }))
+ return WrapperType.PKZIP;
+
+ // PKZIP (Spanned Archive)
+ if (magic.StartsWith(new byte?[] { 0x50, 0x4b, 0x07, 0x08 }))
+ return WrapperType.PKZIP;
+
// PKZIP
if (extension.Equals("zip", StringComparison.OrdinalIgnoreCase))
return WrapperType.PKZIP;
@@ -780,6 +529,10 @@ namespace SabreTools.Serialization.Wrappers
#region PLJ
+ // https://www.iana.org/assignments/media-types/audio/vnd.everad.plj
+ if (magic.StartsWith(new byte?[] { 0xFF, 0x9D, 0x53, 0x4B }))
+ return WrapperType.PlayJAudioFile;
+
// https://www.iana.org/assignments/media-types/audio/vnd.everad.plj
if (extension.Equals("plj", StringComparison.OrdinalIgnoreCase))
return WrapperType.PlayJAudioFile;
@@ -788,6 +541,9 @@ namespace SabreTools.Serialization.Wrappers
#region Quantum
+ if (magic.StartsWith(new byte?[] { 0x44, 0x53 }))
+ return WrapperType.Quantum;
+
if (extension.Equals("q", StringComparison.OrdinalIgnoreCase))
return WrapperType.Quantum;
@@ -799,20 +555,56 @@ namespace SabreTools.Serialization.Wrappers
#region RAR
+ // RAR archive version 1.50 onwards
+ if (magic.StartsWith(new byte?[] { 0x52, 0x61, 0x72, 0x21, 0x1a, 0x07, 0x00 }))
+ return WrapperType.RAR;
+
+ // RAR archive version 5.0 onwards
+ if (magic.StartsWith(new byte?[] { 0x52, 0x61, 0x72, 0x21, 0x1a, 0x07, 0x01, 0x00 }))
+ return WrapperType.RAR;
+
if (extension.Equals("rar", StringComparison.OrdinalIgnoreCase))
return WrapperType.RAR;
#endregion
+ #region RealArcade
+
+ // RASGI2.0
+ // Found in the ".rgs files in IA item "Nova_RealArcadeCD_USA".
+ if (magic.StartsWith(new byte?[] { 0x52, 0x41, 0x53, 0x47, 0x49, 0x32, 0x2E, 0x30 }))
+ return WrapperType.RealArcadeInstaller;
+
+ // XZip2.0
+ // Found in the ".mez" files in IA item "Nova_RealArcadeCD_USA".
+ if (magic.StartsWith(new byte?[] { 0x58, 0x5A, 0x69, 0x70, 0x32, 0x2E, 0x30 }))
+ return WrapperType.RealArcadeMezzanine;
+
+ #endregion
+
#region SevenZip
+ if (magic.StartsWith(new byte?[] { 0x37, 0x7a, 0xbc, 0xaf, 0x27, 0x1c }))
+ return WrapperType.SevenZip;
+
if (extension.Equals("7z", StringComparison.OrdinalIgnoreCase))
return WrapperType.SevenZip;
#endregion
+ #region SFFS
+
+ // Found in Redump entry 81756, confirmed to be "StarForce Filesystem" by PiD.
+ if (magic.StartsWith(new byte?[] { 0x53, 0x46, 0x46, 0x53 }))
+ return WrapperType.SFFS;
+
+ #endregion
+
#region SGA
+ if (magic.StartsWith(new byte?[] { 0x5F, 0x41, 0x52, 0x43, 0x48, 0x49, 0x56, 0x45 }))
+ return WrapperType.SGA;
+
if (extension.Equals("sga", StringComparison.OrdinalIgnoreCase))
return WrapperType.SGA;
@@ -820,6 +612,12 @@ namespace SabreTools.Serialization.Wrappers
#region TapeArchive
+ if (magic.StartsWith(new byte?[] { 0x75, 0x73, 0x74, 0x61, 0x72, 0x00, 0x30, 0x30 }))
+ return WrapperType.TapeArchive;
+
+ if (magic.StartsWith(new byte?[] { 0x75, 0x73, 0x74, 0x61, 0x72, 0x20, 0x20, 0x00 }))
+ return WrapperType.TapeArchive;
+
if (extension.Equals("tar", StringComparison.OrdinalIgnoreCase))
return WrapperType.SevenZip;
@@ -827,6 +625,37 @@ namespace SabreTools.Serialization.Wrappers
#region Textfile
+ // Not all textfiles can be determined through magic number
+
+ // HTML
+ if (magic.StartsWith(new byte?[] { 0x3c, 0x68, 0x74, 0x6d, 0x6c }))
+ return WrapperType.Textfile;
+
+ // HTML and XML
+ if (magic.StartsWith(new byte?[] { 0x3c, 0x21, 0x44, 0x4f, 0x43, 0x54, 0x59, 0x50, 0x45 }))
+ return WrapperType.Textfile;
+
+ // InstallShield Compiled Rules
+ if (magic.StartsWith(new byte?[] { 0x61, 0x4C, 0x75, 0x5A }))
+ return WrapperType.Textfile;
+
+ // Microsoft Office File (old)
+ if (magic.StartsWith(new byte?[] { 0xd0, 0xcf, 0x11, 0xe0, 0xa1, 0xb1, 0x1a, 0xe1 }))
+ return WrapperType.Textfile;
+
+ // Rich Text File
+ if (magic.StartsWith(new byte?[] { 0x7b, 0x5c, 0x72, 0x74, 0x66, 0x31 }))
+ return WrapperType.Textfile;
+
+ // Windows Help File
+ if (magic.StartsWith(new byte?[] { 0x3F, 0x5F, 0x03, 0x00 }))
+ return WrapperType.Textfile;
+
+ // XML
+ // "