/// <summary> /// Create a Optional header from file /// </summary> /// <param name="reader">the reader</param> /// <param name="peHeader">the previous PE header</param> public OptionalHeader(Reader reader, PE_Header peHeader) { /// /// init header /// this.reader = reader; this.entries = new List <Entry>(); this.peHeader = peHeader; this.is32Bit = this.peHeader.Architecture.value == Machines.INTEL386; headerBaseAddress = this.peHeader.headerBaseAddress + this.peHeader.export().Count - HeaderSymbols.PE_HEADER.Length; setupStruct(); /// /// init values /// foreach (var item in entries) { item.readValue(this.reader); } // now the header is dynamic (is32bit) int sizeTmp = headerBaseAddress; entries.ForEach(e => sizeTmp += ((int)e.getEntrySize()) / 8); this.endOfHeader = sizeTmp; }
/// <summary> /// Create a Optional header from memory /// </summary> /// <param name="peHeader">the previous PE header</param> public OptionalHeader(PE_Header peHeader) { /// /// init header /// this.entries = new List <Entry>(); this.peHeader = peHeader; // TODO : improve 32 bit detection this.is32Bit = this.peHeader.Architecture.value == Machines.INTEL386; headerBaseAddress = this.peHeader.headerBaseAddress + this.peHeader.export().Count - HeaderSymbols.PE_HEADER.Length; setupStruct(); /// /// init values /// // 32 bit by default this.Magic.setValue(MagicNumber.PE32); // linker indicate info about compiler // so I just fill random value this.MajorLinkerVersion.setValue(1); this.MinorLinkerVersion.setValue(0); // will be set by the user depending of its actions this.SizeOfCode.setValue(0); this.SizeOfInitializedData.setValue(0); this.SizeOfUninitializedData.setValue(0); this.AddressOfEntryPoint.setValue(0); this.BaseOfCode.setValue(0); // BaseOfData is not in x64 if (this.is32Bit) { this.BaseOfData.setValue(0); } // default image base this.ImageBase.setValue(0x00010000); // will be set by the user depending of its actions this.SectionAlignment.setValue(0); this.FileAlignment.setValue(0); // default versions (discontinue) this.MajorOSVersion.setValue(4); this.MinorOSVersion.setValue(0); this.MajorImageVersion.setValue(0); this.MinorImageVersion.setValue(0); this.MajorSubsystemVersion.setValue(6); this.MinorSubsystemVersion.setValue(0); this.Win32VersionValue.setValue(0); // will be set by the user depending of its actions this.SizeOfImage.setValue(0); // will be written after this.SizeOfHeaders.setValue(0); // useless unless you create a driver this.Checksum.setValue(0); // default windows app this.peSubSystem.setValue(SubSystem.WINDOWS_GUI); // default (ASLR + DEP + TERMINAL_SERVER_AWARE) int characteristics = (int)DllCharacteristics.DYNAMIC_BASE + (int)DllCharacteristics.NX_COMPAT + (int)DllCharacteristics.TERMINAL_SERVER_AWARE; this.DLLCharacteristics.setValue(characteristics); // defaults this.SizeOfStackReserve.setValue(0x100000); this.SizeOfStackCommit.setValue(0x1000); this.SizeOfHeapReserve.setValue(0x100000); this.SizeOfHeapCommit.setValue(0x1000); // "Reserved, must be zero", probably driver stuff this.LoaderFlags.setValue(0); // in general its always 16 but, the user can decide this.NumberOfRvaAndSizes.setValue(16); // now the header is dynamic (is32bit) int sizeTmp = headerBaseAddress; entries.ForEach(e => sizeTmp += ((int)e.getEntrySize()) / 8); this.endOfHeader = sizeTmp; }