Skip to content
/ cecil Public
forked from jbevain/cecil

Commit

Permalink
Fix RVA field alignment (#60)
Browse files Browse the repository at this point in the history
This ensures that section starts are aligned by adjusting the
previous Range's length to ensure the computed start of a new
Range meets the alignment requirements. It was done this way
rather than just computing an aligned start for the new Range,
because the TextMap assumes that the Ranges are contiguous - see
for example GetNextRVA.

GetNextRVA was used to compute the Code RVA, before adding that
segment to the TextMap. This meant that the alignment (only added
later) wasn't taken into account when writing out the code, but
then later the TextMap was modified to include the alignment.

This is fixed by first inserting an aligned zero-length Code
segment before writing the code, then inserting it again once the
length is known. Removing the Code alignment altogether would
work too, but the alignment constants are kept in there, because
it looks like they were added intentionally, even though the
reason is unknown.

Note that before this change, the start of the Code segment (at
least on x64) was not 16-byte aligned in the first place, so this
change will actually move the beginning of the Code segment.
  • Loading branch information
sbomer authored Jan 10, 2023
1 parent 61a57d1 commit 2941911
Show file tree
Hide file tree
Showing 2 changed files with 6 additions and 1 deletion.
2 changes: 1 addition & 1 deletion Mono.Cecil.Cil/CodeWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ sealed class CodeWriter : ByteBuffer {
public CodeWriter (MetadataBuilder metadata)
: base (0)
{
this.code_base = metadata.text_map.GetNextRVA (TextSegment.CLIHeader);
this.code_base = metadata.text_map.GetRVA (TextSegment.Code);
this.metadata = metadata;
this.standalone_signatures = new Dictionary<uint, MetadataToken> ();
this.tiny_method_bodies = new Dictionary<ByteBuffer, RVA> (new ByteBufferEqualityComparer ());
Expand Down
5 changes: 5 additions & 0 deletions Mono.Cecil/AssemblyWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -987,6 +987,11 @@ TextMap CreateTextMap ()
var map = new TextMap ();
map.AddMap (TextSegment.ImportAddressTable, module.Architecture == TargetArchitecture.I386 ? 8 : 0);
map.AddMap (TextSegment.CLIHeader, 0x48, 8);
var pe64 = module.Architecture == TargetArchitecture.AMD64 || module.Architecture == TargetArchitecture.IA64 || module.Architecture == TargetArchitecture.ARM64;
// Alignment of the code segment must be set before the code is written
// These alignment values are probably not necessary, but are being left in
// for now in case something requires them.
map.AddMap (TextSegment.Code, 0, !pe64 ? 4 : 16);
return map;
}

Expand Down

0 comments on commit 2941911

Please sign in to comment.