diff --git a/BurnOutSharp.Builder/Extensions.cs b/BurnOutSharp.Builder/Extensions.cs
index 00bb2ae0..374666b0 100644
--- a/BurnOutSharp.Builder/Extensions.cs
+++ b/BurnOutSharp.Builder/Extensions.cs
@@ -361,12 +361,40 @@ namespace BurnOutSharp.Builder
return 0;
}
+ ///
+ /// Read resource data as a resource header
+ ///
+ /// Data to parse into a resource header
+ /// Offset into the byte array
+ /// A filled resource header on success, null on error
+ public static Models.PortableExecutable.ResourceHeader AsResourceHeader(this byte[] data, ref int offset)
+ {
+ // If we have data that's invalid, we can't do anything
+ if (data == null)
+ return null;
+
+ // Read in the table
+ var header = new Models.PortableExecutable.ResourceHeader();
+ header.DataSize = data.ReadUInt32(ref offset);
+ header.HeaderSize = data.ReadUInt32(ref offset);
+ header.ResourceType = (Models.PortableExecutable.ResourceType)data.ReadUInt32(ref offset); // TODO: Could be a string too
+ header.Name = data.ReadUInt32(ref offset); // TODO: Could be a string too
+ header.DataVersion = data.ReadUInt32(ref offset);
+ header.MemoryFlags = (Models.PortableExecutable.MemoryFlags)data.ReadUInt16(ref offset);
+ header.LanguageId = data.ReadUInt16(ref offset);
+ header.Version = data.ReadUInt32(ref offset);
+ header.Characteristics = data.ReadUInt32(ref offset);
+
+ return header;
+ }
+
///
/// Read resource data as an accelerator table resource
///
/// Data to parse into an accelerator table resource
+ /// Offset into the byte array
/// A filled accelerator table resource on success, null on error
- public static Models.PortableExecutable.AcceleratorTableEntryResource[] AsAcceleratorTableResource(this byte[] data)
+ public static Models.PortableExecutable.AcceleratorTableEntryResource[] AsAcceleratorTableResource(this byte[] data, ref int offset)
{
// If we have data that's invalid for this resource type, we can't do anything
if (data == null || data.Length % 8 != 0)
@@ -374,7 +402,6 @@ namespace BurnOutSharp.Builder
// Get the number of entries
int count = data.Length / 8;
- int offset = 0;
// Read in the table
var table = new Models.PortableExecutable.AcceleratorTableEntryResource[count];
@@ -385,6 +412,7 @@ namespace BurnOutSharp.Builder
entry.Ansi = data.ReadUInt16(ref offset);
entry.Id = data.ReadUInt16(ref offset);
entry.Padding = data.ReadUInt16(ref offset);
+ table[i] = entry;
}
return table;
diff --git a/BurnOutSharp.Models/PortableExecutable/Enums.cs b/BurnOutSharp.Models/PortableExecutable/Enums.cs
index 814d5bac..265d965e 100644
--- a/BurnOutSharp.Models/PortableExecutable/Enums.cs
+++ b/BurnOutSharp.Models/PortableExecutable/Enums.cs
@@ -604,6 +604,22 @@ namespace BurnOutSharp.Models.PortableExecutable
IMPORT_NAME_UNDECORATE = 3,
}
+ [Flags]
+ public enum MemoryFlags : ushort
+ {
+ // TODO: Validate the ~ statements
+ MOVEABLE = 0x0010,
+ FIXED = 0xFFEF, // ~MOVEABLE
+
+ PURE = 0x0020,
+ IMPURE = 0xFFDF, // ~PURE
+
+ PRELOAD = 0x0040,
+ LOADONCALL = 0xFFBF, // ~PRELOAD
+
+ DISCARDABLE = 0x1000,
+ }
+
public enum MachineType : ushort
{
///
diff --git a/BurnOutSharp.Models/PortableExecutable/ResourceHeader.cs b/BurnOutSharp.Models/PortableExecutable/ResourceHeader.cs
new file mode 100644
index 00000000..c87610eb
--- /dev/null
+++ b/BurnOutSharp.Models/PortableExecutable/ResourceHeader.cs
@@ -0,0 +1,94 @@
+namespace BurnOutSharp.Models.PortableExecutable
+{
+ ///
+ /// Contains information about the resource header itself and the data specific to
+ /// this resource. This structure is not a true C-language structure, because it
+ /// contains variable-length members. The structure definition provided here is for
+ /// explanation only; it is not present in any standard header file.
+ ///
+ ///
+ public class ResourceHeader
+ {
+ ///
+ /// The size, in bytes, of the data that follows the resource header for this
+ /// particular resource. It does not include any file padding between this
+ /// resource and any resource that follows it in the resource file.
+ ///
+ public uint DataSize;
+
+ ///
+ /// The size, in bytes, of the resource header data that follows.
+ ///
+ public uint HeaderSize;
+
+ ///
+ /// The resource type. The TYPE member can either be a numeric value or a
+ /// null-terminated Unicode string that specifies the name of the type. See the
+ /// following Remarks section for a description of Name or Ordinal type members.
+ ///
+ /// If the TYPE member is a numeric value, it can specify either a standard or a
+ /// user-defined resource type. If the member is a string, then it is a
+ /// user-defined resource type.
+ ///
+ /// Values less than 256 are reserved for system use.
+ ///
+ public ResourceType ResourceType;
+
+ ///
+ /// A name that identifies the particular resource. The NAME member, like the TYPE
+ /// member, can either be a numeric value or a null-terminated Unicode string.
+ /// See the following Remarks section for a description of Name or Ordinal type
+ /// members.
+ ///
+ /// You do not need to add padding for DWORD alignment between the TYPE and NAME
+ /// members because they contain WORD data. However, you may need to add a WORD of
+ /// padding after the NAME member to align the rest of the header on DWORD boundaries.
+ ///
+ public uint Name;
+
+ ///
+ /// A predefined resource data version. This will determine which version of the
+ /// resource data the application should use.
+ ///
+ public uint DataVersion;
+
+ ///
+ /// A set of attribute flags that can describe the state of the resource. Modifiers
+ /// in the .RC script file assign these attributes to the resource. The script
+ /// identifiers can assign the following flag values.
+ ///
+ /// Applications do not use any of these attributes. The attributes are permitted
+ /// in the script for backward compatibility with existing scripts, but they are
+ /// ignored. Resources are loaded when the corresponding module is loaded, and are
+ /// freed when the module is unloaded.
+ ///
+ public MemoryFlags MemoryFlags;
+
+ ///
+ /// The language for the resource or set of resources. Set the value for this member
+ /// with the optional LANGUAGE resource definition statement. The parameters are
+ /// constants from the Winnt.h file.
+ ///
+ /// Each resource includes a language identifier so the system or application can
+ /// select a language appropriate for the current locale of the system. If there are
+ /// multiple resources of the same type and name that differ only in the language of
+ /// the strings within the resources, you will need to specify a LanguageId for each
+ /// one.
+ ///
+ public ushort LanguageId;
+
+ ///
+ /// A user-defined version number for the resource data that tools can use to read and
+ /// write resource files. Set this value with the optional VERSION resource definition
+ /// statement.
+ ///
+ public uint Version;
+
+ ///
+ /// Specifies user-defined information about the resource that tools can use to read and
+ /// write resource files. Set this value with the optional CHARACTERISTICS resource
+ /// definition statement.
+ ///
+ public uint Characteristics;
+ }
+}