Bug 56071

Summary: Mono.Security.AuthenticodeBase Doesn't Support PE32+ image format
Product: [Mono] Class Libraries Reporter: Sam Karim <samswork>
Component: Mono.SecurityAssignee: jaykrell
Status: RESOLVED FIXED    
Severity: normal CC: ludovic, masafa, mono-bugs+mono
Priority: ---    
Version: master   
Target Milestone: Future Release   
Hardware: PC   
OS: All   
Tags: bugpool-archive Is this bug a regression?: No
Last known good build:

Description Sam Karim 2017-05-05 20:37:16 UTC
From Mono.Security.Authenticode.AuthenticodeBase

Lines 160/161
  dirSecurityOffset = BitConverterLE.ToInt32 (fileblock, peOffset + 152);
  dirSecuritySize = BitConverterLE.ToInt32 (fileblock, peOffset + 156);

The dirSecurityOffset should actually vary based on PE32 or PE32+. Official documentation from Microsoft:
https://www.microsoft.com/en-us/download/details.aspx?id=19509

On PE32+, the "Correct" values are 16 bytes bigger. So this code works on PE32+

  dirSecurityOffset = BitConverterLE.ToInt32 (fileblock, peOffset + 152 + 16
  dirSecuritySize = BitConverterLE.ToInt32 (fileblock, peOffset + 156 + 16);

You can determine if a binary is PE32 or PE32+ based on the "magic number" (Microsoft's words!) found here:

  UInt16 magicNumber = BitConverter.ToUInt16(firstBlock, peOffset + 0x18);

magicNumber 0x10b (PE32) vs 0x20b (PE32+) can be used to calculate the correct offset (152 | 152 + 16).
Comment 1 Marek Safar 2017-09-29 15:44:50 UTC
I think even more values needs to be updated according to https://msdn.microsoft.com/en-us/library/windows/desktop/ms680547(v=vs.85).aspx

Simplest way to create PR32+ is

csc /platform:x64 foo.cs
Comment 2 Ludovic Henry 2018-01-16 20:27:43 UTC
https://github.com/mono/mono/pull/6503