public bool Verify(Stream stream) { StrongNameSignature strongNameSignature = StrongHash(stream, StrongNameOptions.Signature); if (strongNameSignature.Hash == null) { return(false); } try { AssemblyHashAlgorithm algorithm = AssemblyHashAlgorithm.SHA1; if (tokenAlgorithm == "MD5") { algorithm = AssemblyHashAlgorithm.MD5; } return(Verify(rsa, algorithm, strongNameSignature.Hash, strongNameSignature.Signature)); IL_0055: bool result; return(result); } catch (CryptographicException) { return(false); IL_0062: bool result; return(result); } }
public byte[] Hash(string fileName) { FileStream stream = File.OpenRead(fileName); StrongNameSignature signature = this.StrongHash(stream, StrongNameOptions.Metadata); stream.Close(); return(signature.Hash); }
// return the same result as the undocumented and unmanaged GetHashFromAssemblyFile public byte[] Hash(string fileName) { FileStream fs = File.OpenRead(fileName); StrongNameSignature sn = StrongHash(fs, StrongNameOptions.Metadata); fs.Close(); return(sn.Hash); }
public bool Verify(Stream stream) { StrongNameSignature sn = StrongHash(stream, StrongNameOptions.Signature); if (sn.Hash == null) { return(false); } try { AssemblyHashAlgorithm algorithm = AssemblyHashAlgorithm.SHA1; if (tokenAlgorithm == "MD5") { algorithm = AssemblyHashAlgorithm.MD5; } return(Verify(rsa, algorithm, sn.Hash, sn.Signature)); } catch (CryptographicException) { // no exception allowed return(false); } }
public bool Verify(Stream stream) { StrongNameSignature signature = this.StrongHash(stream, StrongNameOptions.Signature); if (signature.Hash == null) { return(false); } try { AssemblyHashAlgorithm algorithm = AssemblyHashAlgorithm.SHA1; if (this.tokenAlgorithm == "MD5") { algorithm = AssemblyHashAlgorithm.MD5; } return(Verify(this.rsa, algorithm, signature.Hash, signature.Signature)); } catch (CryptographicException) { return(false); } }
internal StrongNameSignature StrongHash(Stream stream, StrongNameOptions options) { StrongNameSignature info = new StrongNameSignature(); HashAlgorithm hash = HashAlgorithm.Create(TokenAlgorithm); CryptoStream cs = new CryptoStream(Stream.Null, hash, CryptoStreamMode.Write); // MS-DOS Header - always 128 bytes // ref: Section 24.2.1, Partition II Metadata byte[] mz = new byte [128]; stream.Read(mz, 0, 128); if (BitConverterLE.ToUInt16(mz, 0) != 0x5a4d) { return(null); } UInt32 peHeader = BitConverterLE.ToUInt32(mz, 60); cs.Write(mz, 0, 128); if (peHeader != 128) { byte[] mzextra = new byte [peHeader - 128]; stream.Read(mzextra, 0, mzextra.Length); cs.Write(mzextra, 0, mzextra.Length); } // PE File Header - always 248 bytes // ref: Section 24.2.2, Partition II Metadata byte[] pe = new byte [248]; stream.Read(pe, 0, 248); if (BitConverterLE.ToUInt32(pe, 0) != 0x4550) { return(null); } if (BitConverterLE.ToUInt16(pe, 4) != 0x14c) { return(null); } // MUST zeroize both CheckSum and Security Directory byte[] v = new byte [8]; Buffer.BlockCopy(v, 0, pe, 88, 4); Buffer.BlockCopy(v, 0, pe, 152, 8); cs.Write(pe, 0, 248); UInt16 numSection = BitConverterLE.ToUInt16(pe, 6); int sectionLength = (numSection * 40); byte[] sectionHeaders = new byte [sectionLength]; stream.Read(sectionHeaders, 0, sectionLength); cs.Write(sectionHeaders, 0, sectionLength); UInt32 cliHeaderRVA = BitConverterLE.ToUInt32(pe, 232); UInt32 cliHeaderPos = RVAtoPosition(cliHeaderRVA, numSection, sectionHeaders); int cliHeaderSiz = (int)BitConverterLE.ToUInt32(pe, 236); // CLI Header // ref: Section 24.3.3, Partition II Metadata byte[] cli = new byte [cliHeaderSiz]; stream.Position = cliHeaderPos; stream.Read(cli, 0, cliHeaderSiz); UInt32 strongNameSignatureRVA = BitConverterLE.ToUInt32(cli, 32); info.SignaturePosition = RVAtoPosition(strongNameSignatureRVA, numSection, sectionHeaders); info.SignatureLength = BitConverterLE.ToUInt32(cli, 36); UInt32 metadataRVA = BitConverterLE.ToUInt32(cli, 8); info.MetadataPosition = RVAtoPosition(metadataRVA, numSection, sectionHeaders); info.MetadataLength = BitConverterLE.ToUInt32(cli, 12); if (options == StrongNameOptions.Metadata) { cs.Close(); hash.Initialize(); byte[] metadata = new byte [info.MetadataLength]; stream.Position = info.MetadataPosition; stream.Read(metadata, 0, metadata.Length); info.Hash = hash.ComputeHash(metadata); return(info); } // now we hash every section EXCEPT the signature block for (int i = 0; i < numSection; i++) { UInt32 start = BitConverterLE.ToUInt32(sectionHeaders, i * 40 + 20); int length = (int)BitConverterLE.ToUInt32(sectionHeaders, i * 40 + 16); byte[] section = new byte [length]; stream.Position = start; stream.Read(section, 0, length); if ((start <= info.SignaturePosition) && (info.SignaturePosition < start + length)) { // hash before the signature int before = (int)(info.SignaturePosition - start); if (before > 0) { cs.Write(section, 0, before); } // copy signature info.Signature = new byte [info.SignatureLength]; Buffer.BlockCopy(section, before, info.Signature, 0, (int)info.SignatureLength); Array.Reverse(info.Signature); // hash after the signature int s = (int)(before + info.SignatureLength); int after = (int)(length - s); if (after > 0) { cs.Write(section, s, after); } } else { cs.Write(section, 0, length); } } cs.Close(); info.Hash = hash.Hash; return(info); }
internal StrongNameSignature StrongHash(Stream stream, StrongNameOptions options) { // Bing "msdn pecoff". // https://msdn.microsoft.com/en-us/library/windows/desktop/ms680547(v=vs.85).aspx // Very many of the magic constants and names, funny or otherwise, come from this. // ref: Section 24.2.1, Partition II Metadata // ref: Section 24.2.2, Partition II Metadata // ref: Section 24.3.3, Partition II Metadata // Read MS-DOS header. const int mzSize = 64; byte[] mz = new byte [mzSize]; int peHeader = 0; int mzRead = stream.Read(mz, 0, mzSize); if (mzRead == mzSize && mz [0] == (byte)'M' && mz [1] == (byte)'Z') // 0x5a4d { peHeader = BitConverterLE.ToInt32(mz, 60); if (peHeader < mzSize) { return(Error("peHeader_lt_64")); } // Read MS-DOS stub. mz = ReadMore(stream, mz, peHeader); if (mz == null) { return(Error("read_mz2_failed")); } } else if (mzRead >= 4 && mz [0] == (byte)'P' && mz [1] == (byte)'E' && mz [2] == 0 && mz [3] == 0) // 0x4550 // MS-DOS header/stub can be omitted and just start with PE, though it is rare. { stream.Position = 0; mz = new byte [0]; } else { return(Error("read_mz_or_mzsig_failed")); } // PE File Header // PE signature 4 bytes // file header 20 bytes (really, at this point) // optional header varies in size and its size is in the file header // "optional" means "not in .obj files", but always in .dll/.exes const int sizeOfPeSignature = 4; const int sizeOfFileHeader = 20; const int sizeOfOptionalHeaderMagic = 2; const int offsetOfFileHeader = sizeOfPeSignature; const int offsetOfOptionalHeader = sizeOfPeSignature + sizeOfFileHeader; int sizeOfOptionalHeader = sizeOfOptionalHeaderMagic; // initial minimum int minimumHeadersSize = offsetOfOptionalHeader + sizeOfOptionalHeader; byte[] pe = new byte [minimumHeadersSize]; if (stream.Read(pe, 0, minimumHeadersSize) != minimumHeadersSize || pe [0] != (byte)'P' || pe [1] != (byte)'E' || pe [2] != 0 || pe [3] != 0) // 0x4550 { return(Error("read_minimumHeadersSize_or_pesig_failed")); } sizeOfOptionalHeader = BitConverterLE.ToUInt16(pe, offsetOfFileHeader + 16); if (sizeOfOptionalHeader < sizeOfOptionalHeaderMagic) { return(Error($"sizeOfOptionalHeader_lt_2 ${sizeOfOptionalHeader}")); } int headersSize = offsetOfOptionalHeader + sizeOfOptionalHeader; if (headersSize < offsetOfOptionalHeader) // check overflow { return(Error("headers_overflow")); } // Read the rest of the NT headers (i.e. the rest of the optional header). pe = ReadMore(stream, pe, headersSize); if (pe == null) { return(Error("read_pe2_failed")); } uint magic = BitConverterLE.ToUInt16(pe, offsetOfOptionalHeader); // Refer to PE32+ as PE64 for brevity. // PE64 proposal that widened more fields was rejected. // Between PE32 and PE32+: // Some fields are the same size and offset. For example the entire // MS-DOS header, FileHeader, and section headers, and some of the optional header. // Some fields are PE32-only (BaseOfData). // Some fields are constant size, some are pointer size. // Relative virtual addresses and file offsets are always 4 bytes. // Some fields offsets are offset by 4, 8, or 12, but mostly 0 or 16, // and it so happens that the 4/8/12-offset fields are less interesting. int pe64 = 0; bool rom = false; if (magic == 0x10B) { // nothing } else if (magic == 0x20B) { pe64 = 16; } else if (magic == 0x107) { rom = true; } else { return(Error("bad_magic_value")); } uint numberOfRvaAndSizes = 0; if (!rom) // ROM images have no data directories or checksum. { if (sizeOfOptionalHeader >= offsetOfOptionalHeader + 92 + pe64 + 4) { numberOfRvaAndSizes = BitConverterLE.ToUInt32(pe, offsetOfOptionalHeader + 92 + pe64); } // Clear CheckSum and Security Directory if present. // CheckSum is located the same for PE32+, all data directories are not. for (int i = 64; i < sizeOfOptionalHeader && i < 68; ++i) { pe [offsetOfOptionalHeader + i] = 0; } for (int i = 128 + pe64; i < sizeOfOptionalHeader && i < 128 + 8 + pe64; ++i) { pe [offsetOfOptionalHeader + i] = 0; } } // Read the section headers if present (an image can have no sections, just headers). const int sizeOfSectionHeader = 40; int numberOfSections = BitConverterLE.ToUInt16(pe, offsetOfFileHeader + 2); byte[] sectionHeaders = new byte [numberOfSections * sizeOfSectionHeader]; if (stream.Read(sectionHeaders, 0, sectionHeaders.Length) != sectionHeaders.Length) { return(Error("read_section_headers_failed")); } // Read the CLR header if present. uint SignaturePosition = 0; uint SignatureLength = 0; uint MetadataPosition = 0; uint MetadataLength = 0; if (15 < numberOfRvaAndSizes && sizeOfOptionalHeader >= 216 + pe64) { uint cliHeaderRVA = BitConverterLE.ToUInt32(pe, offsetOfOptionalHeader + 208 + pe64); uint cliHeaderPos = RVAtoPosition(cliHeaderRVA, numberOfSections, sectionHeaders); int cliHeaderSiz = BitConverterLE.ToInt32(pe, offsetOfOptionalHeader + 208 + 4 + pe64); // CLI Header // ref: Section 24.3.3, Partition II Metadata var cli = new byte [cliHeaderSiz]; stream.Position = cliHeaderPos; if (stream.Read(cli, 0, cliHeaderSiz) != cliHeaderSiz) { return(Error("read_cli_header_failed")); } uint strongNameSignatureRVA = BitConverterLE.ToUInt32(cli, 32); SignaturePosition = RVAtoPosition(strongNameSignatureRVA, numberOfSections, sectionHeaders); SignatureLength = BitConverterLE.ToUInt32(cli, 36); uint metadataRVA = BitConverterLE.ToUInt32(cli, 8); MetadataPosition = RVAtoPosition(metadataRVA, numberOfSections, sectionHeaders); MetadataLength = BitConverterLE.ToUInt32(cli, 12); } StrongNameSignature info = new StrongNameSignature(); info.SignaturePosition = SignaturePosition; info.SignatureLength = SignatureLength; info.MetadataPosition = MetadataPosition; info.MetadataLength = MetadataLength; using (HashAlgorithm hash = HashAlgorithm.Create(TokenAlgorithm)) { if (options == StrongNameOptions.Metadata) { hash.Initialize(); byte[] metadata = new byte [MetadataLength]; stream.Position = MetadataPosition; if (stream.Read(metadata, 0, (int)MetadataLength) != (int)MetadataLength) { return(Error("read_cli_metadata_failed")); } info.Hash = hash.ComputeHash(metadata); return(info); } using (CryptoStream cs = new CryptoStream(Stream.Null, hash, CryptoStreamMode.Write)) { cs.Write(mz, 0, mz.Length); // Hash MS-DOS header/stub despite that stub is not run. cs.Write(pe, 0, pe.Length); cs.Write(sectionHeaders, 0, sectionHeaders.Length); // now we hash every section EXCEPT the signature block for (int i = 0; i < numberOfSections; i++) { UInt32 start = BitConverterLE.ToUInt32(sectionHeaders, i * sizeOfSectionHeader + 20); int length = BitConverterLE.ToInt32(sectionHeaders, i * sizeOfSectionHeader + 16); byte[] section = new byte [length]; stream.Position = start; if (stream.Read(section, 0, length) != length) { return(Error("read_section_failed")); } // The signature is assumed not to straddle sections. if ((start <= SignaturePosition) && (SignaturePosition < start + (uint)length)) { // hash before the signature int before = (int)(SignaturePosition - start); if (before > 0) { cs.Write(section, 0, before); } // copy signature info.Signature = new byte [SignatureLength]; Buffer.BlockCopy(section, before, info.Signature, 0, (int)SignatureLength); Array.Reverse(info.Signature); // hash after the signature int s = (int)(before + SignatureLength); int after = (int)(length - s); if (after > 0) { cs.Write(section, s, after); } } else { cs.Write(section, 0, length); } } } info.Hash = hash.Hash; } return(info); }
internal StrongNameSignature StrongHash (Stream stream, StrongNameOptions options) { StrongNameSignature info = new StrongNameSignature (); HashAlgorithm hash = HashAlgorithm.Create (TokenAlgorithm); CryptoStream cs = new CryptoStream (Stream.Null, hash, CryptoStreamMode.Write); // MS-DOS Header - always 128 bytes // ref: Section 24.2.1, Partition II Metadata byte[] mz = new byte [128]; stream.Read (mz, 0, 128); if (BitConverterLE.ToUInt16 (mz, 0) != 0x5a4d) return null; UInt32 peHeader = BitConverterLE.ToUInt32 (mz, 60); cs.Write (mz, 0, 128); if (peHeader != 128) { byte[] mzextra = new byte [peHeader - 128]; stream.Read (mzextra, 0, mzextra.Length); cs.Write (mzextra, 0, mzextra.Length); } // PE File Header - always 248 bytes // ref: Section 24.2.2, Partition II Metadata byte[] pe = new byte [248]; stream.Read (pe, 0, 248); if (BitConverterLE.ToUInt32 (pe, 0) != 0x4550) return null; if (BitConverterLE.ToUInt16 (pe, 4) != 0x14c) return null; // MUST zeroize both CheckSum and Security Directory byte[] v = new byte [8]; Buffer.BlockCopy (v, 0, pe, 88, 4); Buffer.BlockCopy (v, 0, pe, 152, 8); cs.Write (pe, 0, 248); UInt16 numSection = BitConverterLE.ToUInt16 (pe, 6); int sectionLength = (numSection * 40); byte[] sectionHeaders = new byte [sectionLength]; stream.Read (sectionHeaders, 0, sectionLength); cs.Write (sectionHeaders, 0, sectionLength); UInt32 cliHeaderRVA = BitConverterLE.ToUInt32 (pe, 232); UInt32 cliHeaderPos = RVAtoPosition (cliHeaderRVA, numSection, sectionHeaders); int cliHeaderSiz = (int) BitConverterLE.ToUInt32 (pe, 236); // CLI Header // ref: Section 24.3.3, Partition II Metadata byte[] cli = new byte [cliHeaderSiz]; stream.Position = cliHeaderPos; stream.Read (cli, 0, cliHeaderSiz); UInt32 strongNameSignatureRVA = BitConverterLE.ToUInt32 (cli, 32); info.SignaturePosition = RVAtoPosition (strongNameSignatureRVA, numSection, sectionHeaders); info.SignatureLength = BitConverterLE.ToUInt32 (cli, 36); UInt32 metadataRVA = BitConverterLE.ToUInt32 (cli, 8); info.MetadataPosition = RVAtoPosition (metadataRVA, numSection, sectionHeaders); info.MetadataLength = BitConverterLE.ToUInt32 (cli, 12); if (options == StrongNameOptions.Metadata) { cs.Close (); hash.Initialize (); byte[] metadata = new byte [info.MetadataLength]; stream.Position = info.MetadataPosition; stream.Read (metadata, 0, metadata.Length); info.Hash = hash.ComputeHash (metadata); return info; } // now we hash every section EXCEPT the signature block for (int i=0; i < numSection; i++) { UInt32 start = BitConverterLE.ToUInt32 (sectionHeaders, i * 40 + 20); int length = (int) BitConverterLE.ToUInt32 (sectionHeaders, i * 40 + 16); byte[] section = new byte [length]; stream.Position = start; stream.Read (section, 0, length); if ((start <= info.SignaturePosition) && (info.SignaturePosition < start + length)) { // hash before the signature int before = (int)(info.SignaturePosition - start); if (before > 0) { cs.Write (section, 0, before); } // copy signature info.Signature = new byte [info.SignatureLength]; Buffer.BlockCopy (section, before, info.Signature, 0, (int)info.SignatureLength); Array.Reverse (info.Signature); // hash after the signature int s = (int)(before + info.SignatureLength); int after = (int)(length - s); if (after > 0) { cs.Write (section, s, after); } } else cs.Write (section, 0, length); } cs.Close (); info.Hash = hash.Hash; return info; }
internal StrongNameSignature StrongHash(Stream stream, StrongNameOptions options) { StrongNameSignature signature = new StrongNameSignature(); HashAlgorithm transform = HashAlgorithm.Create(this.TokenAlgorithm); CryptoStream stream2 = new CryptoStream(Stream.Null, transform, CryptoStreamMode.Write); byte[] buffer = new byte[0x80]; stream.Read(buffer, 0, 0x80); if (BitConverterLE.ToUInt16(buffer, 0) != 0x5a4d) { return(null); } uint num = BitConverterLE.ToUInt32(buffer, 60); stream2.Write(buffer, 0, 0x80); if (num != 0x80) { byte[] buffer2 = new byte[num - 0x80]; stream.Read(buffer2, 0, buffer2.Length); stream2.Write(buffer2, 0, buffer2.Length); } byte[] buffer3 = new byte[0xf8]; stream.Read(buffer3, 0, 0xf8); if (BitConverterLE.ToUInt32(buffer3, 0) != 0x4550) { return(null); } if (BitConverterLE.ToUInt16(buffer3, 4) != 0x14c) { return(null); } byte[] src = new byte[8]; Buffer.BlockCopy(src, 0, buffer3, 0x58, 4); Buffer.BlockCopy(src, 0, buffer3, 0x98, 8); stream2.Write(buffer3, 0, 0xf8); ushort sections = BitConverterLE.ToUInt16(buffer3, 6); int count = sections * 40; byte[] buffer5 = new byte[count]; stream.Read(buffer5, 0, count); stream2.Write(buffer5, 0, count); uint r = BitConverterLE.ToUInt32(buffer3, 0xe8); uint num5 = this.RVAtoPosition(r, sections, buffer5); int num6 = (int)BitConverterLE.ToUInt32(buffer3, 0xec); byte[] buffer6 = new byte[num6]; stream.Position = num5; stream.Read(buffer6, 0, num6); uint num7 = BitConverterLE.ToUInt32(buffer6, 0x20); signature.SignaturePosition = this.RVAtoPosition(num7, sections, buffer5); signature.SignatureLength = BitConverterLE.ToUInt32(buffer6, 0x24); uint num8 = BitConverterLE.ToUInt32(buffer6, 8); signature.MetadataPosition = this.RVAtoPosition(num8, sections, buffer5); signature.MetadataLength = BitConverterLE.ToUInt32(buffer6, 12); if (options == StrongNameOptions.Metadata) { stream2.Close(); transform.Initialize(); byte[] buffer7 = new byte[signature.MetadataLength]; stream.Position = signature.MetadataPosition; stream.Read(buffer7, 0, buffer7.Length); signature.Hash = transform.ComputeHash(buffer7); return(signature); } for (int i = 0; i < sections; i++) { uint num10 = BitConverterLE.ToUInt32(buffer5, (i * 40) + 20); int num11 = (int)BitConverterLE.ToUInt32(buffer5, (i * 40) + 0x10); byte[] buffer8 = new byte[num11]; stream.Position = num10; stream.Read(buffer8, 0, num11); if ((num10 <= signature.SignaturePosition) && (signature.SignaturePosition < (num10 + num11))) { int num12 = (int)(signature.SignaturePosition - num10); if (num12 > 0) { stream2.Write(buffer8, 0, num12); } signature.Signature = new byte[signature.SignatureLength]; Buffer.BlockCopy(buffer8, num12, signature.Signature, 0, (int)signature.SignatureLength); Array.Reverse(signature.Signature); int offset = num12 + ((int)signature.SignatureLength); int num14 = num11 - offset; if (num14 > 0) { stream2.Write(buffer8, offset, num14); } } else { stream2.Write(buffer8, 0, num11); } } stream2.Close(); signature.Hash = transform.Hash; return(signature); }
internal StrongNameSignature StrongHash(Stream stream, StrongNameOptions options) { StrongNameSignature strongNameSignature = new StrongNameSignature(); HashAlgorithm hashAlgorithm = HashAlgorithm.Create(TokenAlgorithm); CryptoStream cryptoStream = new CryptoStream(Stream.Null, hashAlgorithm, CryptoStreamMode.Write); byte[] array = new byte[128]; stream.Read(array, 0, 128); if (BitConverterLE.ToUInt16(array, 0) != 23117) { return(null); } uint num = BitConverterLE.ToUInt32(array, 60); cryptoStream.Write(array, 0, 128); if (num != 128) { byte[] array2 = new byte[num - 128]; stream.Read(array2, 0, array2.Length); cryptoStream.Write(array2, 0, array2.Length); } byte[] array3 = new byte[248]; stream.Read(array3, 0, 248); if (BitConverterLE.ToUInt32(array3, 0) != 17744) { return(null); } if (BitConverterLE.ToUInt16(array3, 4) != 332) { return(null); } byte[] src = new byte[8]; Buffer.BlockCopy(src, 0, array3, 88, 4); Buffer.BlockCopy(src, 0, array3, 152, 8); cryptoStream.Write(array3, 0, 248); ushort num2 = BitConverterLE.ToUInt16(array3, 6); int num3 = num2 * 40; byte[] array4 = new byte[num3]; stream.Read(array4, 0, num3); cryptoStream.Write(array4, 0, num3); uint r = BitConverterLE.ToUInt32(array3, 232); uint num4 = RVAtoPosition(r, num2, array4); int num5 = (int)BitConverterLE.ToUInt32(array3, 236); byte[] array5 = new byte[num5]; stream.Position = num4; stream.Read(array5, 0, num5); uint r2 = BitConverterLE.ToUInt32(array5, 32); strongNameSignature.SignaturePosition = RVAtoPosition(r2, num2, array4); strongNameSignature.SignatureLength = BitConverterLE.ToUInt32(array5, 36); uint r3 = BitConverterLE.ToUInt32(array5, 8); strongNameSignature.MetadataPosition = RVAtoPosition(r3, num2, array4); strongNameSignature.MetadataLength = BitConverterLE.ToUInt32(array5, 12); if (options == StrongNameOptions.Metadata) { cryptoStream.Close(); hashAlgorithm.Initialize(); byte[] array6 = new byte[strongNameSignature.MetadataLength]; stream.Position = strongNameSignature.MetadataPosition; stream.Read(array6, 0, array6.Length); strongNameSignature.Hash = hashAlgorithm.ComputeHash(array6); return(strongNameSignature); } for (int i = 0; i < num2; i++) { uint num6 = BitConverterLE.ToUInt32(array4, i * 40 + 20); int num7 = (int)BitConverterLE.ToUInt32(array4, i * 40 + 16); byte[] array7 = new byte[num7]; stream.Position = num6; stream.Read(array7, 0, num7); if (num6 <= strongNameSignature.SignaturePosition && strongNameSignature.SignaturePosition < num6 + num7) { int num8 = (int)(strongNameSignature.SignaturePosition - num6); if (num8 > 0) { cryptoStream.Write(array7, 0, num8); } strongNameSignature.Signature = new byte[strongNameSignature.SignatureLength]; Buffer.BlockCopy(array7, num8, strongNameSignature.Signature, 0, (int)strongNameSignature.SignatureLength); Array.Reverse(strongNameSignature.Signature); int num9 = (int)(num8 + strongNameSignature.SignatureLength); int num10 = num7 - num9; if (num10 > 0) { cryptoStream.Write(array7, num9, num10); } } else { cryptoStream.Write(array7, 0, num7); } } cryptoStream.Close(); strongNameSignature.Hash = hashAlgorithm.Hash; return(strongNameSignature); }