diff --git a/SabreTools.Serialization/Wrappers/NewExecutable.cs b/SabreTools.Serialization/Wrappers/NewExecutable.cs
index 8b4a2dd1..080670c5 100644
--- a/SabreTools.Serialization/Wrappers/NewExecutable.cs
+++ b/SabreTools.Serialization/Wrappers/NewExecutable.cs
@@ -365,11 +365,11 @@ namespace SabreTools.Serialization.Wrappers
#region Resources
///
- /// Get the data for a single resource entry
+ /// Get a single resource entry
///
/// Resource ID to retrieve
- /// Resource data on success, null otherwise
- public byte[]? GetResourceData(int id)
+ /// Resource on success, null otherwise
+ public Models.NewExecutable.ResourceTypeResourceEntry? GetResource(int id)
{
// If the header is invalid
if (Header == null)
@@ -398,17 +398,8 @@ namespace SabreTools.Serialization.Wrappers
if (resource.ResourceID != id)
continue;
- // Skip empty entries
- if (resource.Length == 0)
- return [];
-
- // Verify the resource offset
- int offset = resource.Offset << ResourceTable.AlignmentShiftCount;
- if (offset < 0 || offset + resource.Length >= endOfFile)
- return null;
-
- // Read the segment data and return
- return ReadFromDataSource(offset, resource.Length);
+ // Return the resource
+ return resource;
}
}
@@ -416,10 +407,109 @@ namespace SabreTools.Serialization.Wrappers
return null;
}
+ ///
+ /// Get the data for a single resource entry
+ ///
+ /// Resource ID to retrieve
+ /// Resource data on success, null otherwise
+ public byte[]? GetResourceData(int id)
+ {
+ // Get the end of the file, if possible
+ int endOfFile = GetEndOfFile();
+ if (endOfFile == -1)
+ return null;
+
+ // If the resource table is invalid
+ if (ResourceTable == null)
+ return null;
+
+ // Get the matching resource
+ var resource = GetSegment(id);
+ if (resource == null)
+ return null;
+
+ // Skip empty entries
+ if (resource.Length == 0)
+ return [];
+
+ // Verify the resource offset
+ int offset = resource.Offset << ResourceTable.AlignmentShiftCount;
+ if (offset < 0 || offset + resource.Length >= endOfFile)
+ return null;
+
+ // Read the segment data and return
+ return ReadFromDataSource(offset, resource.Length);
+ }
+
+ ///
+ /// Get the data length for a single resource entry
+ ///
+ /// Resource ID to retrieve
+ /// Resource length on success, -1 otherwise
+ public int GetResourceLength(int id)
+ {
+ // Get the matching resource
+ var resource = GetSegment(id);
+ if (resource == null)
+ return -1;
+
+ // Return the reported length
+ return resource.Length;
+ }
+
+ ///
+ /// Get the data offset for a single resource entry
+ ///
+ /// Resource ID to retrieve
+ /// Resource offset on success, -1 otherwise
+ public int GetResourceOffset(int id)
+ {
+ // Get the end of the file, if possible
+ int endOfFile = GetEndOfFile();
+ if (endOfFile == -1)
+ return -1;
+
+ // If the resource table is invalid
+ if (ResourceTable == null)
+ return -1;
+
+ // Get the matching resource
+ var resource = GetSegment(id);
+ if (resource == null)
+ return -1;
+
+ // Verify the resource offset
+ int offset = resource.Offset << ResourceTable.AlignmentShiftCount;
+ if (offset < 0 || offset + resource.Length >= endOfFile)
+ return -1;
+
+ // Return the verified offset
+ return offset;
+ }
+
#endregion
#region Segments
+ ///
+ /// Get a single segment
+ ///
+ /// Segment index to retrieve
+ /// Segment on success, null otherwise
+ public Models.NewExecutable.SegmentTableEntry? GetSegment(int index)
+ {
+ // If the segment table is invalid
+ if (SegmentTable == null || SegmentTable.Length == 0)
+ return null;
+
+ // If the index is invalid
+ if (index < 0 || index >= SegmentTable.Length)
+ return null;
+
+ // Return the segment
+ return SegmentTable[index];
+ }
+
///
/// Get the data for a single segment
///
@@ -436,16 +526,12 @@ namespace SabreTools.Serialization.Wrappers
if (endOfFile == -1)
return null;
- // If the segment table is invalid
- if (SegmentTable == null || SegmentTable.Length == 0)
+ // Get the matching segment
+ var segment = GetSegment(index);
+ if (segment == null)
return null;
- // If the index is invalid
- if (index < 0 || index >= Header.FileSegmentCount || index >= SegmentTable.Length)
- return null;
-
- // Get the segment from the table
- var segment = SegmentTable[index];
+ // Verify the segment length
if (segment.Length == 0)
return [];
@@ -458,6 +544,52 @@ namespace SabreTools.Serialization.Wrappers
return ReadFromDataSource(offset, segment.Length);
}
+ ///
+ /// Get the data length for a single segment
+ ///
+ /// Segment index to retrieve
+ /// Segment length on success, -1 otherwise
+ public int GetSegmentLength(int index)
+ {
+ // Get the matching segment
+ var segment = GetSegment(index);
+ if (segment == null)
+ return -1;
+
+ // Return the reported length
+ return segment.Length;
+ }
+
+ ///
+ /// Get the data offset for a single segment
+ ///
+ /// Segment index to retrieve
+ /// Segment offset on success, -1 otherwise
+ public int GetSegmentOffset(int index)
+ {
+ // If the header is invalid
+ if (Header == null)
+ return -1;
+
+ // Get the end of the file, if possible
+ int endOfFile = GetEndOfFile();
+ if (endOfFile == -1)
+ return -1;
+
+ // Get the matching segment
+ var segment = GetSegment(index);
+ if (segment == null)
+ return -1;
+
+ // Verify the segment offset
+ int offset = segment.Offset << Header.SegmentAlignmentShiftCount;
+ if (offset < 0 || offset + segment.Length >= endOfFile)
+ return -1;
+
+ // Return the verified offset
+ return offset;
+ }
+
#endregion
#region REMOVE -- DO NOT USE