From ee41eb2303c70b7baa388bd89adc20ec081056f7 Mon Sep 17 00:00:00 2001
From: elachlan <2433737+elachlan@users.noreply.github.com>
Date: Thu, 30 Dec 2021 10:59:48 +1000
Subject: [PATCH 01/13] CA1810 Initialize reference type static fields inline
---
eng/CodeAnalysis.ruleset | 2 +-
.../IntrinsicTasks/ItemGroupLoggingHelper.cs | 2 ++
.../Evaluation/ProjectRootElementCache.cs | 25 +++----------------
src/MSBuild/XMake.cs | 2 ++
src/Shared/ExceptionHandling.cs | 7 +-----
src/Shared/FrameworkLocationHelper.cs | 12 +++------
src/Shared/MSBuildNameIgnoreCaseComparer.cs | 11 +-------
src/Shared/TypeLoader.cs | 9 +------
8 files changed, 15 insertions(+), 55 deletions(-)
diff --git a/eng/CodeAnalysis.ruleset b/eng/CodeAnalysis.ruleset
index 2078c42fe6c..69a9d87e2ea 100644
--- a/eng/CodeAnalysis.ruleset
+++ b/eng/CodeAnalysis.ruleset
@@ -85,7 +85,7 @@
-
+
diff --git a/src/Build/BackEnd/Components/RequestBuilder/IntrinsicTasks/ItemGroupLoggingHelper.cs b/src/Build/BackEnd/Components/RequestBuilder/IntrinsicTasks/ItemGroupLoggingHelper.cs
index da174cbb259..d2ddb29632f 100644
--- a/src/Build/BackEnd/Components/RequestBuilder/IntrinsicTasks/ItemGroupLoggingHelper.cs
+++ b/src/Build/BackEnd/Components/RequestBuilder/IntrinsicTasks/ItemGroupLoggingHelper.cs
@@ -41,7 +41,9 @@ internal static class ItemGroupLoggingHelper
/// to materialize the Message as that's a declaration assembly. We inject the logic
/// here.
///
+#pragma warning disable CA1810 // Initialize reference type static fields inline
static ItemGroupLoggingHelper()
+#pragma warning restore CA1810 // Initialize reference type static fields inline
{
BuildEventArgs.ResourceStringFormatter = ResourceUtilities.FormatResourceStringIgnoreCodeAndKeyword;
TaskParameterEventArgs.MessageGetter = GetTaskParameterText;
diff --git a/src/Build/Evaluation/ProjectRootElementCache.cs b/src/Build/Evaluation/ProjectRootElementCache.cs
index ed90b1fb9cf..abc66060292 100644
--- a/src/Build/Evaluation/ProjectRootElementCache.cs
+++ b/src/Build/Evaluation/ProjectRootElementCache.cs
@@ -69,12 +69,13 @@ internal class ProjectRootElementCache : ProjectRootElementCacheBase
/// If this number is increased much higher, the datastructure may
/// need to be changed from a linked list, since it's currently O(n).
///
- private static readonly int s_maximumStrongCacheSize = 200;
+ private static readonly int s_maximumStrongCacheSize = !string.IsNullOrEmpty(Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE")) ?
+ Convert.ToInt32(Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE"), NumberFormatInfo.InvariantInfo) : 200;
///
/// Whether the cache should log activity to the Debug.Out stream
///
- private static bool s_debugLogCacheActivity;
+ private static bool s_debugLogCacheActivity = Environment.GetEnvironmentVariable("MSBUILDDEBUGXMLCACHE") == "1";
///
/// Whether the cache should check file content for cache entry invalidation.
@@ -82,7 +83,7 @@ internal class ProjectRootElementCache : ProjectRootElementCacheBase
///
/// Value shall be true only in case of testing. Outside QA tests it shall be false.
///
- private static bool s_сheckFileContent;
+ private static bool s_сheckFileContent = !string.IsNullOrEmpty(Environment.GetEnvironmentVariable("MSBUILDCACHECHECKFILECONTENT"));
#if DEBUG
///
@@ -119,24 +120,6 @@ internal class ProjectRootElementCache : ProjectRootElementCacheBase
///
private Object _locker = new Object();
- ///
- /// Static constructor to choose cache size.
- ///
- static ProjectRootElementCache()
- {
- // Configurable in case a customer has related perf problems after shipping and so that
- // we can measure different values for perf easily.
- string userSpecifiedSize = Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE");
- if (!String.IsNullOrEmpty(userSpecifiedSize))
- {
- // Not catching as this is an undocumented setting
- s_maximumStrongCacheSize = Convert.ToInt32(userSpecifiedSize, NumberFormatInfo.InvariantInfo);
- }
-
- s_debugLogCacheActivity = Environment.GetEnvironmentVariable("MSBUILDDEBUGXMLCACHE") == "1";
- s_сheckFileContent = !String.IsNullOrEmpty(Environment.GetEnvironmentVariable("MSBUILDCACHECHECKFILECONTENT"));
- }
-
///
/// Creates an empty cache.
///
diff --git a/src/MSBuild/XMake.cs b/src/MSBuild/XMake.cs
index ae95d608193..ebf30dfdd6e 100644
--- a/src/MSBuild/XMake.cs
+++ b/src/MSBuild/XMake.cs
@@ -124,7 +124,9 @@ public enum ExitType
///
/// Static constructor
///
+#pragma warning disable CA1810 // Initialize reference type static fields inline
static MSBuildApp()
+#pragma warning restore CA1810 // Initialize reference type static fields inline
{
try
{
diff --git a/src/Shared/ExceptionHandling.cs b/src/Shared/ExceptionHandling.cs
index f359e71a71d..54163132184 100644
--- a/src/Shared/ExceptionHandling.cs
+++ b/src/Shared/ExceptionHandling.cs
@@ -32,12 +32,7 @@ namespace Microsoft.Build.Shared
///
internal static class ExceptionHandling
{
- private static readonly string s_debugDumpPath;
-
- static ExceptionHandling()
- {
- s_debugDumpPath = GetDebugDumpPath();
- }
+ private static readonly string s_debugDumpPath = GetDebugDumpPath();
///
/// Gets the location of the directory used for diagnostic log files.
diff --git a/src/Shared/FrameworkLocationHelper.cs b/src/Shared/FrameworkLocationHelper.cs
index 42237dde8c9..409a0093e6a 100644
--- a/src/Shared/FrameworkLocationHelper.cs
+++ b/src/Shared/FrameworkLocationHelper.cs
@@ -374,16 +374,10 @@ private static readonly (Version, Version)[,] s_explicitFallbackRulesForPathToDo
};
#endif // FEATURE_WIN32_REGISTRY
- private static readonly IReadOnlyDictionary s_dotNetFrameworkSpecDict;
- private static readonly IReadOnlyDictionary s_visualStudioSpecDict;
+ private static readonly IReadOnlyDictionary s_dotNetFrameworkSpecDict = s_dotNetFrameworkSpecs.ToDictionary(spec => spec.Version);
+ private static readonly IReadOnlyDictionary s_visualStudioSpecDict = s_visualStudioSpecs.ToDictionary(spec => spec.Version);
-#endregion // Static member variables
-
- static FrameworkLocationHelper()
- {
- s_dotNetFrameworkSpecDict = s_dotNetFrameworkSpecs.ToDictionary(spec => spec.Version);
- s_visualStudioSpecDict = s_visualStudioSpecs.ToDictionary(spec => spec.Version);
- }
+ #endregion // Static member variables
#region Static properties
diff --git a/src/Shared/MSBuildNameIgnoreCaseComparer.cs b/src/Shared/MSBuildNameIgnoreCaseComparer.cs
index d0930cc0e19..1e436a21364 100644
--- a/src/Shared/MSBuildNameIgnoreCaseComparer.cs
+++ b/src/Shared/MSBuildNameIgnoreCaseComparer.cs
@@ -20,16 +20,7 @@ internal class MSBuildNameIgnoreCaseComparer : IConstrainedEqualityComparer
/// The processor architecture on which we are running, but default it will be x86
///
- private static readonly NativeMethodsShared.ProcessorArchitectures s_runningProcessorArchitecture;
-
- ///
- /// We need a static constructor to retrieve the running ProcessorArchitecture that way we can
- /// avoid using optimized code that will not run correctly on IA64 due to alignment issues
- ///
- static MSBuildNameIgnoreCaseComparer()
- {
- s_runningProcessorArchitecture = NativeMethodsShared.ProcessorArchitecture;
- }
+ private static readonly NativeMethodsShared.ProcessorArchitectures s_runningProcessorArchitecture = NativeMethodsShared.ProcessorArchitecture;
///
/// The default immutable comparer instance.
diff --git a/src/Shared/TypeLoader.cs b/src/Shared/TypeLoader.cs
index 7f879afa8aa..47ee32d2b33 100644
--- a/src/Shared/TypeLoader.cs
+++ b/src/Shared/TypeLoader.cs
@@ -21,7 +21,7 @@ internal class TypeLoader
///
/// AssemblyContextLoader used to load DLLs outside of msbuild.exe directory
///
- private static readonly CoreClrAssemblyLoader s_coreClrAssemblyLoader;
+ private static readonly CoreClrAssemblyLoader s_coreClrAssemblyLoader = new CoreClrAssemblyLoader();
#endif
///
@@ -39,13 +39,6 @@ internal class TypeLoader
///
private Func _isDesiredType;
-#if FEATURE_ASSEMBLYLOADCONTEXT
- static TypeLoader()
- {
- s_coreClrAssemblyLoader = new CoreClrAssemblyLoader();
- }
-#endif
-
///
/// Constructor.
///
From 25a0ad0d9ab4128f1a4911d341bb33dd2d892c3a Mon Sep 17 00:00:00 2001
From: Lachlan Ennis <2433737+elachlan@users.noreply.github.com>
Date: Fri, 31 Dec 2021 08:06:03 +1000
Subject: [PATCH 02/13] Update src/Build/Evaluation/ProjectRootElementCache.cs
Co-authored-by: Forgind
---
src/Build/Evaluation/ProjectRootElementCache.cs | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/Build/Evaluation/ProjectRootElementCache.cs b/src/Build/Evaluation/ProjectRootElementCache.cs
index abc66060292..a0bfe944c77 100644
--- a/src/Build/Evaluation/ProjectRootElementCache.cs
+++ b/src/Build/Evaluation/ProjectRootElementCache.cs
@@ -69,8 +69,8 @@ internal class ProjectRootElementCache : ProjectRootElementCacheBase
/// If this number is increased much higher, the datastructure may
/// need to be changed from a linked list, since it's currently O(n).
///
- private static readonly int s_maximumStrongCacheSize = !string.IsNullOrEmpty(Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE")) ?
- Convert.ToInt32(Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE"), NumberFormatInfo.InvariantInfo) : 200;
+ private static readonly int s_maximumStrongCacheSize =
+ Convert.ToInt32(Environment.GetEnvironmentVariable("MSBUILDPROJECTROOTELEMENTCACHESIZE") ?? "200", NumberFormatInfo.InvariantInfo);
///
/// Whether the cache should log activity to the Debug.Out stream
From bb9912197c679492036dce216f4061d31dcfb6aa Mon Sep 17 00:00:00 2001
From: elachlan <2433737+elachlan@users.noreply.github.com>
Date: Fri, 31 Dec 2021 08:11:04 +1000
Subject: [PATCH 03/13] unindent region
---
src/Shared/FrameworkLocationHelper.cs | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/Shared/FrameworkLocationHelper.cs b/src/Shared/FrameworkLocationHelper.cs
index 409a0093e6a..7962df7743d 100644
--- a/src/Shared/FrameworkLocationHelper.cs
+++ b/src/Shared/FrameworkLocationHelper.cs
@@ -377,7 +377,7 @@ private static readonly (Version, Version)[,] s_explicitFallbackRulesForPathToDo
private static readonly IReadOnlyDictionary s_dotNetFrameworkSpecDict = s_dotNetFrameworkSpecs.ToDictionary(spec => spec.Version);
private static readonly IReadOnlyDictionary s_visualStudioSpecDict = s_visualStudioSpecs.ToDictionary(spec => spec.Version);
- #endregion // Static member variables
+#endregion // Static member variables
#region Static properties
From ebabaaa69d77efd5cf91034267d9d0a961a09478 Mon Sep 17 00:00:00 2001
From: elachlan <2433737+elachlan@users.noreply.github.com>
Date: Sat, 8 Jan 2022 10:22:32 +1000
Subject: [PATCH 04/13] Revert CodeAnalysis.ruleset
---
eng/CodeAnalysis.ruleset | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/eng/CodeAnalysis.ruleset b/eng/CodeAnalysis.ruleset
index 69a9d87e2ea..2078c42fe6c 100644
--- a/eng/CodeAnalysis.ruleset
+++ b/eng/CodeAnalysis.ruleset
@@ -85,7 +85,7 @@
-
+
From 97bab175f78ad026891760d41b13da846a6155c8 Mon Sep 17 00:00:00 2001
From: elachlan <2433737+elachlan@users.noreply.github.com>
Date: Sat, 8 Jan 2022 10:23:06 +1000
Subject: [PATCH 05/13] enable warning on CA1810
---
eng/Common.globalconfig | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/eng/Common.globalconfig b/eng/Common.globalconfig
index fd878420d57..3222b0275f4 100644
--- a/eng/Common.globalconfig
+++ b/eng/Common.globalconfig
@@ -253,7 +253,7 @@ dotnet_diagnostic.CA1805.severity = suggestion
dotnet_diagnostic.CA1806.severity = none
# Initialize reference type static fields inline
-dotnet_diagnostic.CA1810.severity = suggestion
+dotnet_diagnostic.CA1810.severity = warning
# Avoid uninstantiated internal classes
dotnet_diagnostic.CA1812.severity = none
From 60126c50272cc1b7ada0b79437cd761d21af288b Mon Sep 17 00:00:00 2001
From: elachlan <2433737+elachlan@users.noreply.github.com>
Date: Sat, 8 Jan 2022 11:40:36 +1000
Subject: [PATCH 06/13] Fix remaining occurrences of CA1810 violations
---
src/Tasks/GenerateResource.cs | 27 ++----------------
src/Tasks/GetFrameworkPath.cs | 53 +++++++++++------------------------
2 files changed, 18 insertions(+), 62 deletions(-)
diff --git a/src/Tasks/GenerateResource.cs b/src/Tasks/GenerateResource.cs
index 4dabaed7f16..17bebe45194 100644
--- a/src/Tasks/GenerateResource.cs
+++ b/src/Tasks/GenerateResource.cs
@@ -538,29 +538,6 @@ public GenerateResource()
// do nothing
}
-#if FEATURE_COM_INTEROP
- ///
- /// Static constructor checks the registry opt-out for mark-of-the-web rejection.
- ///
- static GenerateResource()
- {
- if (!NativeMethodsShared.IsWindows)
- {
- allowMOTW = true;
- return;
- }
- try
- {
- object allowUntrustedFiles = Registry.GetValue(@"HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\SDK", "AllowProcessOfUntrustedResourceFiles", null);
- if (allowUntrustedFiles is String)
- {
- allowMOTW = ((string)allowUntrustedFiles).Equals("true", StringComparison.OrdinalIgnoreCase);
- }
- }
- catch { }
- }
-#endif
-
///
/// Logs a Resgen.exe command line that indicates what parameters were
/// passed to this task. Since this task is replacing Resgen, and we used
@@ -923,7 +900,7 @@ public override bool Execute()
}
#if FEATURE_COM_INTEROP
- private static bool allowMOTW;
+ private static readonly bool AllowMOTW = !NativeMethodsShared.IsWindows || (Registry.GetValue(@"HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\SDK", "AllowProcessOfUntrustedResourceFiles", null) as string).Equals("true", StringComparison.OrdinalIgnoreCase);
private const string CLSID_InternetSecurityManager = "7b8a2d94-0ac9-11d1-896c-00c04fb6bfc4";
@@ -944,7 +921,7 @@ public override bool Execute()
private bool IsDangerous(String filename)
{
// If they are opted out, there's no work to do
- if (allowMOTW)
+ if (AllowMOTW)
{
return false;
}
diff --git a/src/Tasks/GetFrameworkPath.cs b/src/Tasks/GetFrameworkPath.cs
index 999bd44f434..7b3d4e4988e 100644
--- a/src/Tasks/GetFrameworkPath.cs
+++ b/src/Tasks/GetFrameworkPath.cs
@@ -14,26 +14,6 @@ namespace Microsoft.Build.Tasks
///
public class GetFrameworkPath : TaskExtension
{
- static GetFrameworkPath()
- {
- s_path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Latest));
- s_version11Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version11));
- s_version20Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version20));
- s_version30Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version30));
- s_version35Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version35));
- s_version40Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version40));
- s_version45Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version45));
- s_version451Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version451));
- s_version452Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version452));
- s_version46Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version46));
- s_version461Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version461));
- s_version462Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version462));
- s_version47Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version47));
- s_version471Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version471));
- s_version472Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version472));
- s_version48Path = new Lazy(() => ToolLocationHelper.GetPathToDotNetFramework(TargetDotNetFrameworkVersion.Version48));
- }
-
#region ITask Members
///
@@ -52,23 +32,22 @@ public override bool Execute()
// it still seems to give an advantage perhaps because there is one less string copy.
// In a large build, this adds up.
// PERF NOTE: We also only find paths we are actually asked for (via