namespace SabreTools.Data.Models.WiseInstaller { /// /// .WISE sections seem to be present in what virustotal calls "Self Extracting Wise Installer"s. These sections /// contain a header with anywhere from seven to nineteen 4-byte little-endian values, followed by what's possibly /// a version number, then string data, and then the file entries. /// /// At some point in the header, there will be the characters "WIS" prepended by what seems to be a version number. /// This possible version number will be referred to from here on as just "version number", as it would be overly /// verbose to continue using "what is possibly a version number". /// /// The WIS characters do not always align with a specific offset if the header is broken up by 4-byte blocks, and /// the version number seems to maintain this offset. It is currently unknown if the version number is 4 bytes long /// or five bytes long, it seems to vary. /// /// Offsets of the "W" in the "WIS" string currently observed are 32, 33, 41, 77, 78, and 82. This seems to point to /// 4-6 known header lengths, depending on the deal with the version number/WIS offset. /// /// Before the version number, there are anywhere from seven to nineteen 4-byte little-endian values depending on /// the length of the pre-string part of the header. These values will be described indexed from zero (0-18). The /// only one of these values that's ever guaranteed not to be all 0x00 is value 6. This is the size of the "main" /// file in the file entry part of the section, which is the size of the file, plus 4 bytes for its following crc32. /// This file seems to always be an msi installer that's extracted to the TEMP directory and ran to perform the /// actual install. This file has been observed to be nameless (a randomly generated alphanumeric string /// followed by .msi, with some examples including 2fbcb.msi and ddec.msi, serve as the filename. Name is random /// even when re-running the same installer) thus far. In many installers, all other pre-version values are 0x00, /// so this is the only guaranteed value. /// /// All values not explicitly mentioned to never have been observed have been observed in at least one installer /// thus far. /// public class SectionHeader { /// /// Unknown Data Size. /// public uint UnknownDataSize { get; set; } /// /// Value 1, (possibly?) the size of the second file entry. This has thus far always been observed /// with non-0x00 values for values 3 and 4, and usually, but not always, value 5 as well. Thus far always been /// observed to be an executable, filename unknown. Likely assists with extraction. A few samples with a /// non-0x00 value 1 seem to have value 5 as 0x00, meaning that it being observed as the second file may just be /// coincidence, and values 1 and 5 may refer to files with a specific purpose/meaning. /// public uint SecondExecutableFileEntryLength { get; set; } /// /// Unknown value 2. Currently unobserved in any samples. /// public uint UnknownValue2 { get; set; } /// /// Unknown value 3. This has thus far always been observed with a non-0x00 value for value 4. /// public uint UnknownValue3 { get; set; } /// /// Unknown value 4. This has thus far always been observed with a non-0x00 value for value 3. /// public uint UnknownValue4 { get; set; } /// /// Value 5, the size of the first entry. This has thus far always been observed with /// non-0x00 values for values 3 and 4, and guarantees the presence of one file before the main msi installer /// file. Thus far always been observed to be an executable, filename unknown. Likely assists with extraction. /// public uint FirstExecutableFileEntryLength { get; set; } /// /// Value 6, the size of the "main" msi installer file entry. Always at the end of the file entries. /// public uint MsiFileEntryLength { get; set; } /// /// Unknown value 7. Currently unobserved in any samples. /// /// TODO: From this entry onward the values are not guaranteed public uint UnknownValue7 { get; set; } /// /// Unknown value 8. Currently unobserved in any samples. /// public uint UnknownValue8 { get; set; } /// /// Value 9, the size of the third entry. /// public uint ThirdExecutableFileEntryLength { get; set; } /// /// Unknown value 10. /// public uint UnknownValue10 { get; set; } /// /// Unknown value 11. Currently unobserved in any samples. /// public uint UnknownValue11 { get; set; } /// /// Unknown value 12. Currently unobserved in any samples. /// public uint UnknownValue12 { get; set; } /// /// Unknown value 13. Currently unobserved in any samples. /// public uint UnknownValue13 { get; set; } /// /// Unknown value 14. Currently unobserved in any samples. /// public uint UnknownValue14 { get; set; } /// /// Unknown value 15. Currently unobserved in any samples. /// public uint UnknownValue15 { get; set; } /// /// Unknown value 16. /// public uint UnknownValue16 { get; set; } /// /// Unknown value 17. /// public uint UnknownValue17 { get; set; } /// /// Unknown value 18. Currently unobserved in any samples. /// public uint UnknownValue18 { get; set; } /// /// Byte array representing version. Byte array used due to unknown size and type for version. /// public byte[] Version { get; set; } = []; /// /// String representing the WIS[etc].TMP string /// public string TmpString { get; set; } = string.Empty; /// /// String representing the GUID string. /// public string GuidString { get; set; } = string.Empty; /// /// String representing a version number. This isn't the version of the .WISE installer itself, as it is /// entirely inconsistent even within the same week. Likely refers to a version for what's being installed /// rather than the installer itself /// public string NonWiseVersion { get; set; } = string.Empty; /// /// Unknown. May also refer to a non-value for pre-78-offset executables and only a value for 78-offset-onwards /// ones. /// public byte[] PreFontValue { get; set; } = []; /// /// Font size /// public int FontSize { get; set; } /// /// Byte array representing string lengths and info. Individual strings not predefined since number of strings /// will likely vary between many installers. /// public byte[] PreStringValues { get; set; } = []; /// /// Strings for the section. Size and any breakup of strings currently unknown. /// public byte[][] Strings { get; set; } = []; } }