Browse Source

Fix #1977: Add tests for analyzers

pull/1984/head
Siegfried Pammer 5 years ago
parent
commit
69a863957c
  1. 51
      ILSpy.Tests/Analyzers/MethodUsesAnalyzerTests.cs
  2. 21
      ILSpy.Tests/Analyzers/TestCases/MainAssembly.cs
  3. 66
      ILSpy.Tests/Analyzers/TypeUsedByAnalyzerTests.cs
  4. 5
      ILSpy.Tests/ILSpy.Tests.csproj
  5. 18
      ILSpy.Tests/Stub.cs
  6. 70
      ILSpy/Analyzers/AnalyzerContext.cs
  7. 7
      ILSpy/Analyzers/AnalyzerEntityTreeNode.cs
  8. 5
      ILSpy/Analyzers/AnalyzerScope.cs
  9. 10
      ILSpy/Analyzers/Builtin/MethodUsesAnalyzer.cs
  10. 41
      ILSpy/Analyzers/IAnalyzer.cs
  11. 1
      ILSpy/ILSpy.csproj
  12. 2
      ILSpy/Languages/CSharpLanguage.cs
  13. 2
      ILSpy/Languages/ILLanguage.cs
  14. 16
      ILSpy/LoadedAssembly.cs
  15. 11
      ILSpy/MainWindow.xaml.cs
  16. 5
      ILSpy/Options/DecompilerSettingsPanel.xaml.cs
  17. 1
      ILSpy/Properties/AssemblyInfo.template.cs
  18. 10
      ILSpy/Properties/Resources.Designer.cs
  19. 4
      ILSpy/Properties/Resources.resx
  20. 2
      ILSpy/TreeNodes/AssemblyListTreeNode.cs

51
ILSpy.Tests/Analyzers/MethodUsesAnalyzerTests.cs

@ -0,0 +1,51 @@ @@ -0,0 +1,51 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using NUnit.Framework;
using ICSharpCode.ILSpy.Analyzers;
using ICSharpCode.ILSpy.Analyzers.Builtin;
using ICSharpCode.Decompiler.TypeSystem;
using System.Windows;
namespace ICSharpCode.ILSpy.Tests.Analyzers
{
[TestFixture, Parallelizable(ParallelScope.All)]
public class MethodUsesAnalyzerTests
{
AssemblyList assemblyList;
CSharpLanguage language;
LoadedAssembly testAssembly;
ICompilation testAssemblyTypeSystem;
ITypeDefinition typeDefinition;
[OneTimeSetUp]
public void Setup()
{
new Application();
Options.DecompilerSettingsPanel.TestSetup(new Decompiler.DecompilerSettings());
assemblyList = new AssemblyList("Test");
testAssembly = assemblyList.OpenAssembly(typeof(MethodUsesAnalyzerTests).Assembly.Location);
assemblyList.OpenAssembly(typeof(void).Assembly.Location);
testAssemblyTypeSystem = testAssembly.GetTypeSystemOrNull();
language = new CSharpLanguage();
typeDefinition = testAssemblyTypeSystem.FindType(typeof(TestCases.Main.MainAssembly)).GetDefinition();
}
[Test]
public void MainAssemblyUsesSystemStringEmpty()
{
var context = new AnalyzerContext { AssemblyList = assemblyList, Language = language };
IMethod symbol = typeDefinition.Methods.First(m => m.Name == "UsesSystemStringEmpty");
var results = new MethodUsesAnalyzer().Analyze(symbol, context).ToList();
Assert.IsTrue(results.Count == 1);
var field = results.Single() as IField;
Assert.IsNotNull(field);
Assert.IsFalse(field.MetadataToken.IsNil);
Assert.AreEqual(field.FullName, "System.String.Empty");
}
}
}

21
ILSpy.Tests/Analyzers/TestCases/MainAssembly.cs

@ -0,0 +1,21 @@ @@ -0,0 +1,21 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ICSharpCode.ILSpy.Tests.Analyzers.TestCases.Main
{
class MainAssembly
{
public string UsesSystemStringEmpty()
{
return string.Empty;
}
public int UsesInt32()
{
return int.Parse("1234");
}
}
}

66
ILSpy.Tests/Analyzers/TypeUsedByAnalyzerTests.cs

@ -0,0 +1,66 @@ @@ -0,0 +1,66 @@
// Copyright (c) 2020 Siegfried Pammer
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
// software and associated documentation files (the "Software"), to deal in the Software
// without restriction, including without limitation the rights to use, copy, modify, merge,
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
// to whom the Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or
// substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using ICSharpCode.Decompiler.TypeSystem;
using ICSharpCode.Decompiler.TypeSystem.Implementation;
using ICSharpCode.ILSpy.Analyzers;
using ICSharpCode.ILSpy.Analyzers.Builtin;
using NUnit.Framework;
namespace ICSharpCode.ILSpy.Tests.Analyzers
{
[TestFixture, Parallelizable(ParallelScope.All)]
public class TypeUsedByAnalyzerTests
{
AssemblyList assemblyList;
CSharpLanguage language;
LoadedAssembly testAssembly;
ICompilation testAssemblyTypeSystem;
[OneTimeSetUp]
public void Setup()
{
new Application();
Options.DecompilerSettingsPanel.TestSetup(new Decompiler.DecompilerSettings());
assemblyList = new AssemblyList("Test");
testAssembly = assemblyList.OpenAssembly(typeof(MethodUsesAnalyzerTests).Assembly.Location);
testAssemblyTypeSystem = new SimpleCompilation(testAssembly.GetPEFileOrNull(), assemblyList.OpenAssembly(typeof(void).Assembly.Location).GetPEFileOrNull());
language = new CSharpLanguage();
}
[Test]
public void SystemInt32UsedByMainAssembly()
{
var context = new AnalyzerContext { AssemblyList = assemblyList, Language = language };
var symbol = testAssemblyTypeSystem.FindType(typeof(int)).GetDefinition();
var results = new TypeUsedByAnalyzer().Analyze(symbol, context).ToList();
Assert.IsNotEmpty(results);
var method = results.OfType<IMethod>().SingleOrDefault(m => m.FullName == "ICSharpCode.ILSpy.Tests.Analyzers.TestCases.Main.MainAssembly.UsesInt32");
Assert.IsNotNull(method);
Assert.IsFalse(method.MetadataToken.IsNil);
}
}
}

5
ILSpy.Tests/ILSpy.Tests.csproj

@ -14,12 +14,12 @@ @@ -14,12 +14,12 @@
<EnableDefaultItems>false</EnableDefaultItems>
<OutputType>Exe</OutputType>
<RootNamespace>ICSharpCode.ILSpy.Tests</RootNamespace>
<StartupObject>ICSharpCode.ILSpy.Tests.Stub</StartupObject>
<AutoGenerateBindingRedirects>True</AutoGenerateBindingRedirects>
<SignAssembly>True</SignAssembly>
<AssemblyOriginatorKeyFile>..\ICSharpCode.Decompiler\ICSharpCode.Decompiler.snk</AssemblyOriginatorKeyFile>
<RootNamespace>ICSharpCode.ILSpy.Tests</RootNamespace>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)' == 'Debug'">
@ -37,6 +37,9 @@ @@ -37,6 +37,9 @@
</PropertyGroup>
<ItemGroup>
<Compile Include="Analyzers\MethodUsesAnalyzerTests.cs" />
<Compile Include="Analyzers\TestCases\MainAssembly.cs" />
<Compile Include="Analyzers\TypeUsedByAnalyzerTests.cs" />
<Compile Include="Stub.cs" />
</ItemGroup>

18
ILSpy.Tests/Stub.cs

@ -1,4 +1,20 @@ @@ -1,4 +1,20 @@
using System;
// Copyright (c) 2020 Siegfried Pammer
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
// software and associated documentation files (the "Software"), to deal in the Software
// without restriction, including without limitation the rights to use, copy, modify, merge,
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
// to whom the Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or
// substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
namespace ICSharpCode.ILSpy.Tests
{

70
ILSpy/Analyzers/AnalyzerContext.cs

@ -0,0 +1,70 @@ @@ -0,0 +1,70 @@
// Copyright (c) 2018 Siegfried Pammer
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
// software and associated documentation files (the "Software"), to deal in the Software
// without restriction, including without limitation the rights to use, copy, modify, merge,
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
// to whom the Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or
// substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
using System;
using System.Collections.Concurrent;
using System.Reflection.Metadata;
using System.Threading;
using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.TypeSystem;
namespace ICSharpCode.ILSpy.Analyzers
{
/// <summary>
/// Provides additional context for analyzers.
/// </summary>
public class AnalyzerContext
{
public AssemblyList AssemblyList { get; internal set; }
/// <summary>
/// CancellationToken. Currently Analyzers do not support cancellation from the UI, but it should be checked nonetheless.
/// </summary>
public CancellationToken CancellationToken { get; internal set; }
/// <summary>
/// Currently used language.
/// </summary>
public Language Language { get; internal set; }
public MethodBodyBlock GetMethodBody(IMethod method)
{
if (!method.HasBody || method.MetadataToken.IsNil)
return null;
var module = method.ParentModule.PEFile;
var md = module.Metadata.GetMethodDefinition((MethodDefinitionHandle)method.MetadataToken);
try {
return module.Reader.GetMethodBody(md.RelativeVirtualAddress);
} catch (BadImageFormatException) {
return null;
}
}
public AnalyzerScope GetScopeOf(IEntity entity)
{
return new AnalyzerScope(AssemblyList, entity);
}
readonly ConcurrentDictionary<PEFile, DecompilerTypeSystem> typeSystemCache = new ConcurrentDictionary<PEFile, DecompilerTypeSystem>();
public DecompilerTypeSystem GetOrCreateTypeSystem(PEFile module)
{
return typeSystemCache.GetOrAdd(module, m => new DecompilerTypeSystem(m, m.GetAssemblyResolver()));
}
}
}

7
ILSpy/Analyzers/AnalyzerEntityTreeNode.cs

@ -17,7 +17,8 @@ @@ -17,7 +17,8 @@
// DEALINGS IN THE SOFTWARE.
using System.Collections.Generic;
using ICSharpCode.Decompiler.Metadata;
using System.Reflection.Metadata;
using System.Windows;
using ICSharpCode.Decompiler.TypeSystem;
using ICSharpCode.ILSpy.TreeNodes;
using ICSharpCode.TreeView;
@ -34,6 +35,10 @@ namespace ICSharpCode.ILSpy.Analyzers @@ -34,6 +35,10 @@ namespace ICSharpCode.ILSpy.Analyzers
public override void ActivateItem(System.Windows.RoutedEventArgs e)
{
e.Handled = true;
if (this.Member.MetadataToken.IsNil) {
MessageBox.Show(Properties.Resources.CannotAnalyzeMissingRef, "ILSpy");
return;
}
MainWindow.Instance.JumpToReference(this.Member);
}

5
ILSpy/Analyzers/AnalyzerScope.cs

@ -16,13 +16,10 @@ @@ -16,13 +16,10 @@
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection.Metadata;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using ICSharpCode.Decompiler;
using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.TypeSystem;
@ -137,7 +134,7 @@ namespace ICSharpCode.ILSpy.Analyzers @@ -137,7 +134,7 @@ namespace ICSharpCode.ILSpy.Analyzers
continue;
var resolver = assembly.GetAssemblyResolver();
foreach (var reference in module.AssemblyReferences) {
using (LoadedAssembly.DisableAssemblyLoad()) {
using (LoadedAssembly.DisableAssemblyLoad(AssemblyList)) {
if (resolver.Resolve(reference) == curFile) {
found = true;
break;

10
ILSpy/Analyzers/Builtin/MethodUsesAnalyzer.cs

@ -18,11 +18,8 @@ @@ -18,11 +18,8 @@
using System;
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.Linq;
using System.Reflection.Metadata;
using System.Text;
using System.Threading.Tasks;
using ICSharpCode.Decompiler;
using ICSharpCode.Decompiler.Disassembler;
using ICSharpCode.Decompiler.Metadata;
@ -41,16 +38,17 @@ namespace ICSharpCode.ILSpy.Analyzers.Builtin @@ -41,16 +38,17 @@ namespace ICSharpCode.ILSpy.Analyzers.Builtin
public IEnumerable<ISymbol> Analyze(ISymbol symbol, AnalyzerContext context)
{
if (symbol is IMethod method) {
var typeSystem = context.GetOrCreateTypeSystem(method.ParentModule.PEFile);
return context.Language.GetCodeMappingInfo(method.ParentModule.PEFile, method.MetadataToken)
.GetMethodParts((MethodDefinitionHandle)method.MetadataToken)
.SelectMany(h => ScanMethod(method, h, context)).Distinct();
.SelectMany(h => ScanMethod(h, typeSystem)).Distinct();
}
throw new InvalidOperationException("Should never happen.");
}
IEnumerable<IEntity> ScanMethod(IMethod analyzedMethod, MethodDefinitionHandle handle, AnalyzerContext context)
IEnumerable<IEntity> ScanMethod(MethodDefinitionHandle handle, DecompilerTypeSystem typeSystem)
{
var module = (MetadataModule)analyzedMethod.ParentModule;
var module = typeSystem.MainModule;
var md = module.PEFile.Metadata.GetMethodDefinition(handle);
if (!md.HasBody()) yield break;

41
ILSpy/Analyzers/IAnalyzer.cs

@ -19,11 +19,6 @@ @@ -19,11 +19,6 @@
using System;
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.Linq;
using System.Reflection.Metadata;
using System.Threading;
using ICSharpCode.Decompiler;
using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.TypeSystem;
namespace ICSharpCode.ILSpy.Analyzers
@ -45,42 +40,6 @@ namespace ICSharpCode.ILSpy.Analyzers @@ -45,42 +40,6 @@ namespace ICSharpCode.ILSpy.Analyzers
IEnumerable<ISymbol> Analyze(ISymbol analyzedSymbol, AnalyzerContext context);
}
/// <summary>
/// Provides additional context for analyzers.
/// </summary>
public class AnalyzerContext
{
public AssemblyList AssemblyList { get; internal set; }
/// <summary>
/// CancellationToken. Currently Analyzers do not support cancellation from the UI, but it should be checked nonetheless.
/// </summary>
public CancellationToken CancellationToken { get; internal set; }
/// <summary>
/// Currently used language.
/// </summary>
public Language Language { get; internal set; }
public MethodBodyBlock GetMethodBody(IMethod method)
{
if (!method.HasBody || method.MetadataToken.IsNil)
return null;
var module = method.ParentModule.PEFile;
var md = module.Metadata.GetMethodDefinition((MethodDefinitionHandle)method.MetadataToken);
try {
return module.Reader.GetMethodBody(md.RelativeVirtualAddress);
} catch (BadImageFormatException) {
return null;
}
}
public AnalyzerScope GetScopeOf(IEntity entity)
{
return new AnalyzerScope(AssemblyList, entity);
}
}
[MetadataAttribute]
[AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]
public class ExportAnalyzerAttribute : ExportAttribute, IAnalyzerMetadata

1
ILSpy/ILSpy.csproj

@ -74,6 +74,7 @@ @@ -74,6 +74,7 @@
<ItemGroup>
<Compile Include="..\ICSharpCode.Decompiler.PdbProvider.Cecil\MonoCecilDebugInfoProvider.cs" Link="DebugInfo\MonoCecilDebugInfoProvider.cs" />
<Compile Include="AboutPage.cs" />
<Compile Include="Analyzers\AnalyzerContext.cs" />
<Compile Include="Analyzers\AnalyzerScope.cs" />
<Compile Include="Analyzers\Builtin\AttributeAppliedToAnalyzer.cs" />
<Compile Include="Analyzers\Builtin\EventImplementsInterfaceAnalyzer.cs" />

2
ILSpy/Languages/CSharpLanguage.cs

@ -362,7 +362,7 @@ namespace ICSharpCode.ILSpy @@ -362,7 +362,7 @@ namespace ICSharpCode.ILSpy
base.DecompileAssembly(assembly, output, options);
// don't automatically load additional assemblies when an assembly node is selected in the tree view
using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) {
using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad(assembly.AssemblyList)) {
IAssemblyResolver assemblyResolver = assembly.GetAssemblyResolver();
var typeSystem = new DecompilerTypeSystem(module, assemblyResolver, options.DecompilerSettings);
var globalType = typeSystem.MainModule.TypeDefinitions.FirstOrDefault();

2
ILSpy/Languages/ILLanguage.cs

@ -161,7 +161,7 @@ namespace ICSharpCode.ILSpy @@ -161,7 +161,7 @@ namespace ICSharpCode.ILSpy
var dis = CreateDisassembler(output, options);
// don't automatically load additional assemblies when an assembly node is selected in the tree view
using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) {
using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad(assembly.AssemblyList)) {
dis.AssemblyResolver = module.GetAssemblyResolver();
dis.DebugInfo = module.GetDebugInfoOrNull();
if (options.FullDecompilation)

16
ILSpy/LoadedAssembly.cs

@ -207,15 +207,27 @@ namespace ICSharpCode.ILSpy @@ -207,15 +207,27 @@ namespace ICSharpCode.ILSpy
[ThreadStatic]
static int assemblyLoadDisableCount;
public static IDisposable DisableAssemblyLoad(AssemblyList assemblyList)
{
assemblyLoadDisableCount++;
return new DecrementAssemblyLoadDisableCount(assemblyList);
}
public static IDisposable DisableAssemblyLoad()
{
assemblyLoadDisableCount++;
return new DecrementAssemblyLoadDisableCount();
return new DecrementAssemblyLoadDisableCount(MainWindow.Instance.CurrentAssemblyList);
}
sealed class DecrementAssemblyLoadDisableCount : IDisposable
{
bool disposed;
AssemblyList assemblyList;
public DecrementAssemblyLoadDisableCount(AssemblyList assemblyList)
{
this.assemblyList = assemblyList;
}
public void Dispose()
{
@ -223,7 +235,7 @@ namespace ICSharpCode.ILSpy @@ -223,7 +235,7 @@ namespace ICSharpCode.ILSpy
disposed = true;
assemblyLoadDisableCount--;
// clear the lookup cache since we might have stored the lookups failed due to DisableAssemblyLoad()
MainWindow.Instance.CurrentAssemblyList.ClearCache();
assemblyList.ClearCache();
}
}
}

11
ILSpy/MainWindow.xaml.cs

@ -759,10 +759,7 @@ namespace ICSharpCode.ILSpy @@ -759,10 +759,7 @@ namespace ICSharpCode.ILSpy
}
AssemblyTreeView.SelectedItem = obj;
} else {
MessageBox.Show("Navigation failed because the target is hidden or a compiler-generated class.\n" +
"Please disable all filters that might hide the item (i.e. activate " +
"\"View > Show internal types and members\") and try again.",
"ILSpy", MessageBoxButton.OK, MessageBoxImage.Exclamation);
MessageBox.Show(Properties.Resources.NavigationFailed, "ILSpy", MessageBoxButton.OK, MessageBoxImage.Exclamation);
}
}
}
@ -888,10 +885,11 @@ namespace ICSharpCode.ILSpy @@ -888,10 +885,11 @@ namespace ICSharpCode.ILSpy
break;
case ValueTuple<string, PEFile, Handle> unresolvedEntity:
string protocol = unresolvedEntity.Item1 ?? "decompile";
PEFile file = unresolvedEntity.Item2;
if (protocol != "decompile") {
var protocolHandlers = App.ExportProvider.GetExports<IProtocolHandler>();
foreach (var handler in protocolHandlers) {
var node = handler.Value.Resolve(protocol, unresolvedEntity.Item2, unresolvedEntity.Item3, out bool newTabPage);
var node = handler.Value.Resolve(protocol, file, unresolvedEntity.Item3, out bool newTabPage);
if (node != null) {
SelectNode(node, newTabPage);
return decompilationTask;
@ -899,8 +897,7 @@ namespace ICSharpCode.ILSpy @@ -899,8 +897,7 @@ namespace ICSharpCode.ILSpy
}
}
if (MetadataTokenHelpers.TryAsEntityHandle(MetadataTokens.GetToken(unresolvedEntity.Item3)) != null) {
var typeSystem = new DecompilerTypeSystem(unresolvedEntity.Item2, unresolvedEntity.Item2.GetAssemblyResolver(),
TypeSystemOptions.Default | TypeSystemOptions.Uncached);
var typeSystem = new DecompilerTypeSystem(file, file.GetAssemblyResolver(), TypeSystemOptions.Default | TypeSystemOptions.Uncached);
reference = typeSystem.MainModule.ResolveEntity((EntityHandle)unresolvedEntity.Item3);
goto default;
}

5
ILSpy/Options/DecompilerSettingsPanel.xaml.cs

@ -41,6 +41,11 @@ namespace ICSharpCode.ILSpy.Options @@ -41,6 +41,11 @@ namespace ICSharpCode.ILSpy.Options
static Decompiler.DecompilerSettings currentDecompilerSettings;
internal static void TestSetup(Decompiler.DecompilerSettings settings)
{
currentDecompilerSettings = settings;
}
public static Decompiler.DecompilerSettings CurrentDecompilerSettings {
get {
return currentDecompilerSettings ?? (currentDecompilerSettings = LoadDecompilerSettings(ILSpySettings.Load()));

1
ILSpy/Properties/AssemblyInfo.template.cs

@ -29,6 +29,7 @@ using System.Diagnostics.CodeAnalysis; @@ -29,6 +29,7 @@ using System.Diagnostics.CodeAnalysis;
[assembly: NeutralResourcesLanguage("en-US")]
[assembly: InternalsVisibleTo("ILSpy.AddIn, PublicKey=0024000004800000940000000602000000240000525341310004000001000100653c4a319be4f524972c3c5bba5fd243330f8e900287d9022d7821a63fd0086fd3801e3683dbe9897f2ecc44727023e9b40adcf180730af70c81c54476b3e5ba8b0f07f5132b2c3cc54347a2c1a9d64ebaaaf3cbffc1a18c427981e2a51d53d5ab02536b7550e732f795121c38a0abfdb38596353525d034baf9e6f1fd8ac4ac")]
[assembly: InternalsVisibleTo("ILSpy.Tests, PublicKey=00240000048000009400000006020000002400005253413100040000010001004dcf3979c4e902efa4dd2163a039701ed5822e6f1134d77737296abbb97bf0803083cfb2117b4f5446a217782f5c7c634f9fe1fc60b4c11d62c5b3d33545036706296d31903ddcf750875db38a8ac379512f51620bb948c94d0831125fbc5fe63707cbb93f48c1459c4d1749eb7ac5e681a2f0d6d7c60fa527a3c0b8f92b02bf")]
[assembly: SuppressMessage("Microsoft.Usage", "CA2243:AttributeStringLiteralsShouldParseCorrectly",
Justification = "AssemblyInformationalVersion does not need to be a parsable version")]

10
ILSpy/Properties/Resources.Designer.cs generated

@ -1476,6 +1476,16 @@ namespace ICSharpCode.ILSpy.Properties { @@ -1476,6 +1476,16 @@ namespace ICSharpCode.ILSpy.Properties {
}
}
/// <summary>
/// Looks up a localized string similar to Navigation failed because the target is hidden or a compiler-generated class.\n
///Please disable all filters that might hide the item (i.e. activate &quot;View &gt; Show internal types and members&quot;) and try again..
/// </summary>
public static string NavigationFailed {
get {
return ResourceManager.GetString("NavigationFailed", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Nuget Package Browser.
/// </summary>

4
ILSpy/Properties/Resources.resx

@ -832,4 +832,8 @@ Are you sure you want to continue?</value> @@ -832,4 +832,8 @@ Are you sure you want to continue?</value>
<data name="HideEmptyMetadataTables" xml:space="preserve">
<value>Hide empty metadata tables from tree view</value>
</data>
<data name="NavigationFailed" xml:space="preserve">
<value>Navigation failed because the target is hidden or a compiler-generated class.\n
Please disable all filters that might hide the item (i.e. activate "View &gt; Show internal types and members") and try again.</value>
</data>
</root>

2
ILSpy/TreeNodes/AssemblyListTreeNode.cs

@ -200,7 +200,7 @@ namespace ICSharpCode.ILSpy.TreeNodes @@ -200,7 +200,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
return null;
App.Current.Dispatcher.VerifyAccess();
foreach (AssemblyTreeNode node in this.Children) {
if (node.LoadedAssembly.IsLoaded && node.LoadedAssembly.GetPEFileOrNull() == module)
if (node.LoadedAssembly.IsLoaded && node.LoadedAssembly.GetPEFileOrNull()?.FileName == module.FileName)
return node;
}
return null;

Loading…
Cancel
Save