private BlobBuilder SerializeTextSection(SectionLocation location) { var sectionBuilder = new BlobBuilder(); var metadataBuilder = new BlobBuilder(); var metadataSizes = _metadataSerializer.MetadataSizes; var textSection = new ManagedTextSection( metadataSizes.MetadataSize, ilStreamSize: _ilStream.Count, mappedFieldDataSize: _mappedFieldData.Count, resourceDataSize: _managedResourceData.Count, strongNameSignatureSize: _strongNameSignatureSize, imageCharacteristics: Header.ImageCharacteristics, machine: Header.Machine, pdbPathOpt: _pdbPathOpt, isDeterministic: IsDeterministic); int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream; int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream(); _metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva); BlobBuilder debugTableBuilderOpt; if (_pdbPathOpt != null || IsDeterministic) { debugTableBuilderOpt = new BlobBuilder(); textSection.WriteDebugTable(debugTableBuilderOpt, location, _nativePdbContentId, _portablePdbContentId); } else { debugTableBuilderOpt = null; } _lazyEntryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress); textSection.Serialize( sectionBuilder, location.RelativeVirtualAddress, _entryPoint.IsNil ? 0 : MetadataTokens.GetToken(_entryPoint), _corFlags, Header.ImageBase, metadataBuilder, _ilStream, _mappedFieldData, _managedResourceData, debugTableBuilderOpt, out _lazyStrongNameSignature); _peDirectoriesBuilder.AddressOfEntryPoint = _lazyEntryPointAddress; _peDirectoriesBuilder.DebugTable = textSection.GetDebugDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress); return(sectionBuilder); }
private BlobBuilder SerializeTextSection(SectionLocation location) { var sectionBuilder = new BlobBuilder(); var metadataBuilder = new BlobBuilder(); var metadataSizes = _metadataRootBuilder.Sizes; var textSection = new ManagedTextSection( imageCharacteristics: Header.ImageCharacteristics, machine: Header.Machine, ilStreamSize: _ilStream.Count, metadataSize: metadataSizes.MetadataSize, resourceDataSize: _managedResourcesOpt?.Count ?? 0, strongNameSignatureSize: _strongNameSignatureSize, debugDataSize: _debugDirectoryBuilderOpt?.Size ?? 0, mappedFieldDataSize: _mappedFieldDataOpt?.Count ?? 0); int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream; int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream(); _metadataRootBuilder.Serialize(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva); DirectoryEntry debugDirectoryEntry; BlobBuilder debugTableBuilderOpt; if (_debugDirectoryBuilderOpt != null) { int debugDirectoryOffset = textSection.ComputeOffsetToDebugDirectory(); debugTableBuilderOpt = new BlobBuilder(_debugDirectoryBuilderOpt.TableSize); _debugDirectoryBuilderOpt.Serialize(debugTableBuilderOpt, location, debugDirectoryOffset); // Only the size of the fixed part of the debug table goes here. debugDirectoryEntry = new DirectoryEntry( location.RelativeVirtualAddress + debugDirectoryOffset, _debugDirectoryBuilderOpt.TableSize); } else { debugTableBuilderOpt = null; debugDirectoryEntry = default(DirectoryEntry); } _lazyEntryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress); textSection.Serialize( sectionBuilder, location.RelativeVirtualAddress, _entryPointOpt.IsNil ? 0 : MetadataTokens.GetToken(_entryPointOpt), _corFlags, Header.ImageBase, metadataBuilder, _ilStream, _mappedFieldDataOpt, _managedResourcesOpt, debugTableBuilderOpt, out _lazyStrongNameSignature); _peDirectoriesBuilder.AddressOfEntryPoint = _lazyEntryPointAddress; _peDirectoriesBuilder.DebugTable = debugDirectoryEntry; _peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress); return sectionBuilder; }
public static void AddManagedSections( this PEBuilder peBuilder, PEDirectoriesBuilder peDirectoriesBuilder, TypeSystemMetadataSerializer metadataSerializer, BlobBuilder ilStream, BlobBuilder mappedFieldData, BlobBuilder managedResourceData, Action<BlobBuilder, PESectionLocation> nativeResourceSectionSerializer, // opt int strongNameSignatureSize, // TODO MethodDefinitionHandle entryPoint, string pdbPathOpt, // TODO ContentId nativePdbContentId, // TODO ContentId portablePdbContentId, // TODO CorFlags corFlags) { int entryPointAddress = 0; // .text peBuilder.AddSection(".text", SectionCharacteristics.MemRead | SectionCharacteristics.MemExecute | SectionCharacteristics.ContainsCode, location => { var sectionBuilder = new BlobBuilder(); var metadataBuilder = new BlobBuilder(); var metadataSizes = metadataSerializer.MetadataSizes; var textSection = new ManagedTextSection( metadataSizes.MetadataSize, ilStreamSize: ilStream.Count, mappedFieldDataSize: mappedFieldData.Count, resourceDataSize: managedResourceData.Count, strongNameSignatureSize: strongNameSignatureSize, imageCharacteristics: peBuilder.ImageCharacteristics, machine: peBuilder.Machine, pdbPathOpt: pdbPathOpt, isDeterministic: peBuilder.IsDeterministic); int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream; int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream(); metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva); BlobBuilder debugTableBuilderOpt; if (pdbPathOpt != null || peBuilder.IsDeterministic) { debugTableBuilderOpt = new BlobBuilder(); textSection.WriteDebugTable(debugTableBuilderOpt, location, nativePdbContentId, portablePdbContentId); } else { debugTableBuilderOpt = null; } entryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress); textSection.Serialize( sectionBuilder, location.RelativeVirtualAddress, entryPoint.IsNil ? 0 : MetadataTokens.GetToken(entryPoint), corFlags, peBuilder.ImageBase, metadataBuilder, ilStream, mappedFieldData, managedResourceData, debugTableBuilderOpt); peDirectoriesBuilder.AddressOfEntryPoint = entryPointAddress; peDirectoriesBuilder.DebugTable = textSection.GetDebugDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress); return sectionBuilder; }); // .rsrc if (nativeResourceSectionSerializer != null) { peBuilder.AddSection(".rsrc", SectionCharacteristics.MemRead | SectionCharacteristics.ContainsInitializedData, location => { var sectionBuilder = new BlobBuilder(); nativeResourceSectionSerializer(sectionBuilder, location); peDirectoriesBuilder.ResourceTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count); return sectionBuilder; }); } // .reloc if (peBuilder.Machine == Machine.I386 || peBuilder.Machine == 0) { peBuilder.AddSection(".reloc", SectionCharacteristics.MemRead | SectionCharacteristics.MemDiscardable | SectionCharacteristics.ContainsInitializedData, location => { var sectionBuilder = new BlobBuilder(); WriteRelocSection(sectionBuilder, peBuilder.Machine, entryPointAddress); peDirectoriesBuilder.BaseRelocationTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count); return sectionBuilder; }); } }
private BlobBuilder SerializeTextSection(SectionLocation location) { var sectionBuilder = new BlobBuilder(); var metadataBuilder = new BlobBuilder(); var metadataSizes = _metadataSerializer.MetadataSizes; var textSection = new ManagedTextSection( imageCharacteristics: Header.ImageCharacteristics, machine: Header.Machine, ilStreamSize: _ilStream.Count, metadataSize: metadataSizes.MetadataSize, resourceDataSize: _managedResourcesOpt?.Count ?? 0, strongNameSignatureSize: _strongNameSignatureSize, debugDataSize: _debugDirectoryBuilderOpt?.Size ?? 0, mappedFieldDataSize: _mappedFieldDataOpt?.Count ?? 0); int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream; int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream(); _metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva); DirectoryEntry debugDirectoryEntry; BlobBuilder debugTableBuilderOpt; if (_debugDirectoryBuilderOpt != null) { int debugDirectoryOffset = textSection.ComputeOffsetToDebugDirectory(); debugTableBuilderOpt = new BlobBuilder(_debugDirectoryBuilderOpt.TableSize); _debugDirectoryBuilderOpt.Serialize(debugTableBuilderOpt, location, debugDirectoryOffset); // Only the size of the fixed part of the debug table goes here. debugDirectoryEntry = new DirectoryEntry( location.RelativeVirtualAddress + debugDirectoryOffset, _debugDirectoryBuilderOpt.TableSize); } else { debugTableBuilderOpt = null; debugDirectoryEntry = default(DirectoryEntry); } _lazyEntryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress); textSection.Serialize( sectionBuilder, location.RelativeVirtualAddress, _entryPointOpt.IsNil ? 0 : MetadataTokens.GetToken(_entryPointOpt), _corFlags, Header.ImageBase, metadataBuilder, _ilStream, _mappedFieldDataOpt, _managedResourcesOpt, debugTableBuilderOpt, out _lazyStrongNameSignature); _peDirectoriesBuilder.AddressOfEntryPoint = _lazyEntryPointAddress; _peDirectoriesBuilder.DebugTable = debugDirectoryEntry; _peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress); _peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress); return(sectionBuilder); }
public static void AddManagedSections( this PEBuilder peBuilder, PEDirectoriesBuilder peDirectoriesBuilder, TypeSystemMetadataSerializer metadataSerializer, BlobBuilder ilStream, BlobBuilder mappedFieldData, BlobBuilder managedResourceData, Action <BlobBuilder, PESectionLocation> nativeResourceSectionSerializer, // opt int strongNameSignatureSize, // TODO MethodDefinitionHandle entryPoint, string pdbPathOpt, // TODO ContentId nativePdbContentId, // TODO ContentId portablePdbContentId, // TODO CorFlags corFlags) { int entryPointAddress = 0; // .text peBuilder.AddSection(".text", SectionCharacteristics.MemRead | SectionCharacteristics.MemExecute | SectionCharacteristics.ContainsCode, location => { var sectionBuilder = new BlobBuilder(); var metadataBuilder = new BlobBuilder(); var metadataSizes = metadataSerializer.MetadataSizes; var textSection = new ManagedTextSection( metadataSizes.MetadataSize, ilStreamSize: ilStream.Count, mappedFieldDataSize: mappedFieldData.Count, resourceDataSize: managedResourceData.Count, strongNameSignatureSize: strongNameSignatureSize, imageCharacteristics: peBuilder.ImageCharacteristics, machine: peBuilder.Machine, pdbPathOpt: pdbPathOpt, isDeterministic: peBuilder.IsDeterministic); int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream; int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream(); metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva); BlobBuilder debugTableBuilderOpt; if (pdbPathOpt != null || peBuilder.IsDeterministic) { debugTableBuilderOpt = new BlobBuilder(); textSection.WriteDebugTable(debugTableBuilderOpt, location, nativePdbContentId, portablePdbContentId); } else { debugTableBuilderOpt = null; } entryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress); textSection.Serialize( sectionBuilder, location.RelativeVirtualAddress, entryPoint.IsNil ? 0 : MetadataTokens.GetToken(entryPoint), corFlags, peBuilder.ImageBase, metadataBuilder, ilStream, mappedFieldData, managedResourceData, debugTableBuilderOpt); peDirectoriesBuilder.AddressOfEntryPoint = entryPointAddress; peDirectoriesBuilder.DebugTable = textSection.GetDebugDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress); peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress); return(sectionBuilder); }); // .rsrc if (nativeResourceSectionSerializer != null) { peBuilder.AddSection(".rsrc", SectionCharacteristics.MemRead | SectionCharacteristics.ContainsInitializedData, location => { var sectionBuilder = new BlobBuilder(); nativeResourceSectionSerializer(sectionBuilder, location); peDirectoriesBuilder.ResourceTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count); return(sectionBuilder); }); } // .reloc if (peBuilder.Machine == Machine.I386 || peBuilder.Machine == 0) { peBuilder.AddSection(".reloc", SectionCharacteristics.MemRead | SectionCharacteristics.MemDiscardable | SectionCharacteristics.ContainsInitializedData, location => { var sectionBuilder = new BlobBuilder(); WriteRelocSection(sectionBuilder, peBuilder.Machine, entryPointAddress); peDirectoriesBuilder.BaseRelocationTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count); return(sectionBuilder); }); } }