From fe5041b28c1c8415fe44bed8c3365b3eb9948cdf Mon Sep 17 00:00:00 2001 From: Janusz Wrobel Date: Tue, 31 Oct 2023 22:23:33 +0000 Subject: [PATCH] Generate hashes for two ref assembly types in parallel --- MSBuild.CompilerCache/RefTrimmer.cs | 57 +++++++++++++++++++---------- 1 file changed, 38 insertions(+), 19 deletions(-) diff --git a/MSBuild.CompilerCache/RefTrimmer.cs b/MSBuild.CompilerCache/RefTrimmer.cs index c09b1d7..52d14f3 100644 --- a/MSBuild.CompilerCache/RefTrimmer.cs +++ b/MSBuild.CompilerCache/RefTrimmer.cs @@ -80,14 +80,10 @@ public static ImmutableArray GetInternalsVisibleToAssemblies(MetadataRea .ToImmutableArray(); } - public static (ImmutableArray bytes, ImmutableArray internalsVisibleToAssemblies) MakeRefasm( - ImmutableArray content, LoggerBase logger, RefAsmType refAsmType) + public static ImmutableArray MakeRefasm(LoggerBase logger, RefAsmType refAsmType, PEReader peReader) { - var peReader = new PEReader(content); var metaReader = peReader.GetMetadataReader(); - var internalsVisibleToAssemblies = GetInternalsVisibleToAssemblies(metaReader); - if (!metaReader.IsAssembly) throw new Exception("File format is not supported"); @@ -97,15 +93,14 @@ public static (ImmutableArray bytes, ImmutableArray internalsVisib var refBytes = MetadataImporter.MakeRefasm(metaReader, peReader, logger, filter, makeMock: false)!; - return (ImmutableArray.Create(refBytes), internalsVisibleToAssemblies); + return ImmutableArray.Create(refBytes); } - public static (string hash, ImmutableArray internalsVisibleToAssemblies) MakeRefasmAndGetHash( - ImmutableArray content, LoggerBase logger, RefAsmType refAsmType) + public static string MakeRefasmAndGetHash(LoggerBase logger, RefAsmType refAsmType, PEReader peReader) { - var (bytes, internalsVisibleToAssemblies) = MakeRefasm(content, logger, refAsmType); + var bytes = MakeRefasm(logger, refAsmType, peReader); var hash = Utils.BytesToHashHex(bytes.AsSpan()); - return (hash, internalsVisibleToAssemblies); + return hash; } public RefData GenerateRefData(ImmutableArray content) @@ -113,18 +108,42 @@ public RefData GenerateRefData(ImmutableArray content) var logger = new VerySimpleLogger(Console.Out, LogLevel.Warning); var loggerBase = new LoggerBase(logger); - var (publicRefHash, internalsVisibleToAssemblies) = - MakeRefasmAndGetHash(content, loggerBase, RefAsmType.Public); + var peReader = new PEReader(content); + var metaReader = peReader.GetMetadataReader(); + var internalsVisibleToAssemblies = GetInternalsVisibleToAssemblies(metaReader); // If no assemblies can see the internals, there is no need to generate public+internal ref assembly var internalsNeverAccessible = internalsVisibleToAssemblies.IsEmpty; - var publicAndInternalRefHash = - internalsNeverAccessible - ? publicRefHash - : MakeRefasmAndGetHash(content, loggerBase, RefAsmType.PublicAndInternal).hash; - + + string GetPublicHash() + { + var peReader2 = new PEReader(content); + return MakeRefasmAndGetHash(loggerBase, RefAsmType.Public, peReader2); + } + + string GetPublicAndInternalHash() + { + var peReader3 = new PEReader(content); + return MakeRefasmAndGetHash(loggerBase, RefAsmType.PublicAndInternal, peReader3); + } + + string? publicRefHash = null; string? publicAndInternalRefHash = null; + if (internalsNeverAccessible) + { + publicRefHash = publicAndInternalRefHash = GetPublicHash(); + } + else + { + var tasks = new[] + { + Task.Factory.StartNew(() => { publicRefHash = GetPublicHash();}), + Task.Factory.StartNew(() => { publicAndInternalRefHash = GetPublicAndInternalHash();}) + }; + Task.WaitAll(tasks); + } + return new RefData( - PublicRefHash: publicRefHash, - PublicAndInternalRefHash: publicAndInternalRefHash, + PublicRefHash: publicRefHash!, + PublicAndInternalRefHash: publicAndInternalRefHash!, InternalsVisibleTo: internalsVisibleToAssemblies ); }