From cd69dca7ba12125d75130f2cf6408d6397876cd8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mike=20Kr=C3=BCger?= Date: Wed, 13 Apr 2016 14:47:52 +0200 Subject: [AssemblyBrowser] Loading is now lock free --- .../AssemblyBrowserWidget.cs | 48 ++----------------- .../MonoDevelop.AssemblyBrowser/AssemblyLoader.cs | 55 ++++++++++++++++++++-- .../TreeNodes/AssemblyBrowserTypeNodeBuilder.cs | 7 ++- .../TreeNodes/AssemblyNodeBuilder.cs | 15 +++--- .../TreeNodes/DomEventNodeBuilder.cs | 6 +-- .../TreeNodes/DomFieldNodeBuilder.cs | 6 +-- .../TreeNodes/DomMethodNodeBuilder.cs | 6 +-- .../TreeNodes/DomPropertyNodeBuilder.cs | 6 +-- .../TreeNodes/DomTypeNodeBuilder.cs | 6 +-- 9 files changed, 81 insertions(+), 74 deletions(-) (limited to 'main/src/addins/MonoDevelop.AssemblyBrowser') diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyBrowserWidget.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyBrowserWidget.cs index ebbdb39a3a..e2fc6f47a6 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyBrowserWidget.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyBrowserWidget.cs @@ -156,37 +156,7 @@ namespace MonoDevelop.AssemblyBrowser return referencedSegment.Reference.ToString (); } - class FastNonInterningProvider : InterningProvider - { - Dictionary stringDict = new Dictionary(); - - public override string Intern (string text) - { - if (text == null) - return null; - - string output; - if (stringDict.TryGetValue(text, out output)) - return output; - stringDict [text] = text; - return text; - } - public override ISupportsInterning Intern (ISupportsInterning obj) - { - return obj; - } - - public override IList InternList(IList list) - { - return list; - } - - public override object InternValue (object obj) - { - return obj; - } - } public AssemblyBrowserWidget () { @@ -257,9 +227,6 @@ namespace MonoDevelop.AssemblyBrowser languageCombobox.Active = Math.Min (2, Math.Max (0, PropertyService.Get ("AssemblyBrowser.Language", 0))); languageCombobox.Changed += LanguageComboboxhandleChanged; #pragma warning disable 618 - loader = new CecilLoader (true); - loader.InterningProvider = new FastNonInterningProvider (); - loader.IncludeInternalMembers = true; TreeView = new AssemblyBrowserTreeView (new NodeBuilder[] { new ErrorNodeBuilder (), new ProjectNodeBuilder (this), @@ -1387,7 +1354,7 @@ namespace MonoDevelop.AssemblyBrowser void OpenFromAssembly (string url, AssemblyLoader currentAssembly, bool expandNode = true) { - var cecilObject = loader.GetCecilObject (currentAssembly.UnresolvedAssembly); + var cecilObject = currentAssembly.CecilLoader.GetCecilObject (currentAssembly.UnresolvedAssembly); if (cecilObject == null) return; @@ -1426,7 +1393,7 @@ namespace MonoDevelop.AssemblyBrowser { var tasks = new List (); foreach (var definition in definitions.ToArray ()) { - var cecilObject = loader.GetCecilObject (definition.UnresolvedAssembly); + var cecilObject = definition.CecilLoader.GetCecilObject (definition.UnresolvedAssembly); if (cecilObject == null) { LoggingService.LogWarning ("Assembly browser: Can't find assembly: " + definition.UnresolvedAssembly.FullAssemblyName + "."); continue; @@ -1474,7 +1441,7 @@ namespace MonoDevelop.AssemblyBrowser AssemblyDefinition cu = null; foreach (var unit in definitions) { if (unit.UnresolvedAssembly.AssemblyName == fileName) - cu = loader.GetCecilObject (unit.UnresolvedAssembly); + cu = unit.CecilLoader.GetCecilObject (unit.UnresolvedAssembly); } if (cu == null) return; @@ -1558,7 +1525,6 @@ namespace MonoDevelop.AssemblyBrowser this.UIManager = null; } - this.loader = null; this.languageCombobox.Changed -= LanguageComboboxhandleChanged; // this.searchInCombobox.Changed -= SearchInComboboxhandleChanged; // this.searchEntry.Changed -= SearchEntryhandleChanged; @@ -1576,13 +1542,7 @@ namespace MonoDevelop.AssemblyBrowser } } - CecilLoader loader; - internal CecilLoader CecilLoader { - get { - return loader; - } - } - + List definitions = new List (); List projects = new List (); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyLoader.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyLoader.cs index 58f80337fa..645a99490b 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyLoader.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/AssemblyLoader.cs @@ -30,6 +30,7 @@ using System.Threading.Tasks; using MonoDevelop.Core; using System.IO; using System.Threading; +using System.Collections.Generic; namespace MonoDevelop.AssemblyBrowser { @@ -65,7 +66,15 @@ namespace MonoDevelop.AssemblyBrowser return assemblyLoaderTask.Result.Item2; } } - + + CecilLoader loader; + internal CecilLoader CecilLoader { + get { + return loader; + } + } + + public AssemblyLoader (AssemblyBrowserWidget widget, string fileName) { if (widget == null) @@ -76,13 +85,17 @@ namespace MonoDevelop.AssemblyBrowser FileName = fileName; if (!File.Exists (fileName)) throw new ArgumentException ("File doesn't exist.", nameof (fileName)); - assemblyLoaderTask = Task.Run (async () => { + + loader = new CecilLoader (true); + loader.InterningProvider = new FastNonInterningProvider (); + loader.IncludeInternalMembers = true; + + assemblyLoaderTask = Task.Run ( () => { try { var asm = AssemblyDefinition.ReadAssembly (FileName, new ReaderParameters { AssemblyResolver = this }); - var loadedAssembley = await Runtime.RunInMainThread (() => widget.CecilLoader.LoadAssembly (asm)); - + var loadedAssembley = loader.LoadAssembly (asm); return Tuple.Create (asm, loadedAssembley); } catch (Exception e) { LoggingService.LogError ("Error while reading assembly " + FileName, e); @@ -90,7 +103,39 @@ namespace MonoDevelop.AssemblyBrowser } }, src.Token); } - + + class FastNonInterningProvider : InterningProvider + { + Dictionary stringDict = new Dictionary (); + + public override string Intern (string text) + { + if (text == null) + return null; + + string output; + if (stringDict.TryGetValue (text, out output)) + return output; + stringDict [text] = text; + return text; + } + + public override ISupportsInterning Intern (ISupportsInterning obj) + { + return obj; + } + + public override IList InternList (IList list) + { + return list; + } + + public override object InternValue (object obj) + { + return obj; + } + } + #region IAssemblyResolver implementation AssemblyDefinition IAssemblyResolver.Resolve (AssemblyNameReference name) { diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyBrowserTypeNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyBrowserTypeNodeBuilder.cs index 683c8b04a1..c1c3f12c23 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyBrowserTypeNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyBrowserTypeNodeBuilder.cs @@ -50,10 +50,9 @@ namespace MonoDevelop.AssemblyBrowser } } - internal CecilLoader CecilLoader { - get { - return Widget.CecilLoader; - } + internal CecilLoader GetCecilLoader (ITreeNavigator navigator) + { + return navigator.GetParentDataItem (false).CecilLoader; } public override int CompareObjects (ITreeNavigator thisNode, ITreeNavigator otherNode) diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyNodeBuilder.cs index ed73ec940b..b502934da5 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/AssemblyNodeBuilder.cs @@ -148,8 +148,9 @@ namespace MonoDevelop.AssemblyBrowser public List Disassemble (TextEditor data, ITreeNavigator navigator) { - var assembly = ((AssemblyLoader)navigator.DataItem).UnresolvedAssembly; - var compilationUnit = Widget.CecilLoader.GetCecilObject (assembly); + var assemblyLoader = (AssemblyLoader)navigator.DataItem; + var assembly = assemblyLoader.UnresolvedAssembly; + var compilationUnit = assemblyLoader.CecilLoader.GetCecilObject (assembly); if (compilationUnit == null) { LoggingService.LogError ("Can't get cecil object for assembly:" + assembly); return new List (); @@ -160,8 +161,9 @@ namespace MonoDevelop.AssemblyBrowser public List Decompile (TextEditor data, ITreeNavigator navigator, bool publicOnly) { - var assembly = ((AssemblyLoader)navigator.DataItem).UnresolvedAssembly; - var compilationUnit = Widget.CecilLoader.GetCecilObject (assembly); + var assemblyLoader = (AssemblyLoader)navigator.DataItem; + var assembly = assemblyLoader.UnresolvedAssembly; + var compilationUnit = assemblyLoader.CecilLoader.GetCecilObject (assembly); if (compilationUnit == null) { LoggingService.LogError ("Can't get cecil object for assembly:" + assembly); return new List (); @@ -174,8 +176,9 @@ namespace MonoDevelop.AssemblyBrowser List IAssemblyBrowserNodeBuilder.GetSummary (TextEditor data, ITreeNavigator navigator, bool publicOnly) { - var assembly = ((AssemblyLoader)navigator.DataItem).UnresolvedAssembly; - var compilationUnit = Widget.CecilLoader.GetCecilObject (assembly); + var assemblyLoader = (AssemblyLoader)navigator.DataItem; + var assembly = assemblyLoader.UnresolvedAssembly; + var compilationUnit = assemblyLoader.CecilLoader.GetCecilObject (assembly); if (compilationUnit == null) { LoggingService.LogError ("Can't get cecil object for assembly:" + assembly); return new List (); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomEventNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomEventNodeBuilder.cs index c03962bf13..bf485b6e7e 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomEventNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomEventNodeBuilder.cs @@ -95,7 +95,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var evt = CecilLoader.GetCecilObject ((IUnresolvedEvent)navigator.DataItem); + var evt = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedEvent)navigator.DataItem); return DomMethodNodeBuilder.Disassemble (data, rd => rd.DisassembleEvent (evt)); } @@ -103,7 +103,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var evt = CecilLoader.GetCecilObject ((IUnresolvedEvent)navigator.DataItem); + var evt = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedEvent)navigator.DataItem); if (evt == null) return null; return DomMethodNodeBuilder.Decompile (data, DomMethodNodeBuilder.GetModule (navigator), evt.DeclaringType, b => b.AddEvent (evt)); @@ -113,7 +113,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var evt = CecilLoader.GetCecilObject ((IUnresolvedEvent)navigator.DataItem); + var evt = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedEvent)navigator.DataItem); if (evt == null) return null; return DomMethodNodeBuilder.GetSummary (data, DomMethodNodeBuilder.GetModule (navigator), evt.DeclaringType, b => b.AddEvent (evt)); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomFieldNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomFieldNodeBuilder.cs index fcdd6b8672..6433e0cd8f 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomFieldNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomFieldNodeBuilder.cs @@ -81,7 +81,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var field = CecilLoader.GetCecilObject ((IUnresolvedField)navigator.DataItem); + var field = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedField)navigator.DataItem); if (field == null) return null; return DomMethodNodeBuilder.Disassemble (data, rd => rd.DisassembleField (field)); @@ -91,7 +91,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var field = CecilLoader.GetCecilObject ((IUnresolvedField)navigator.DataItem); + var field = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedField)navigator.DataItem); if (field == null) return null; return DomMethodNodeBuilder.Decompile (data, DomMethodNodeBuilder.GetModule (navigator), field.DeclaringType, b => b.AddField (field)); @@ -101,7 +101,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var field = CecilLoader.GetCecilObject ((IUnresolvedField)navigator.DataItem); + var field = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedField)navigator.DataItem); if (field == null) return null; return DomMethodNodeBuilder.GetSummary (data, DomMethodNodeBuilder.GetModule (navigator), field.DeclaringType, b => b.AddField (field)); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomMethodNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomMethodNodeBuilder.cs index 841aafac55..5ffc9e0953 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomMethodNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomMethodNodeBuilder.cs @@ -216,7 +216,7 @@ namespace MonoDevelop.AssemblyBrowser var method = (IUnresolvedMethod)navigator.DataItem; if (HandleSourceCodeEntity (navigator, data)) return null; - var cecilMethod = CecilLoader.GetCecilObject (method); + var cecilMethod = GetCecilLoader (navigator).GetCecilObject (method); if (cecilMethod == null) return null; return DomMethodNodeBuilder.Decompile (data, DomMethodNodeBuilder.GetModule (navigator), cecilMethod.DeclaringType, b => b.AddMethod (cecilMethod)); @@ -227,7 +227,7 @@ namespace MonoDevelop.AssemblyBrowser var method = (IUnresolvedMethod)navigator.DataItem; if (HandleSourceCodeEntity (navigator, data)) return null; - var cecilMethod = CecilLoader.GetCecilObject (method); + var cecilMethod = GetCecilLoader (navigator).GetCecilObject (method); if (cecilMethod == null) return null; return DomMethodNodeBuilder.GetSummary (data, DomMethodNodeBuilder.GetModule (navigator), cecilMethod.DeclaringType, b => b.AddMethod (cecilMethod)); @@ -269,7 +269,7 @@ namespace MonoDevelop.AssemblyBrowser var method = (IUnresolvedMethod)navigator.DataItem; if (HandleSourceCodeEntity (navigator, data)) return null; - var cecilMethod = CecilLoader.GetCecilObject (method); + var cecilMethod = GetCecilLoader (navigator).GetCecilObject (method); if (cecilMethod == null) return null; return Disassemble (data, rd => rd.DisassembleMethod (cecilMethod)); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomPropertyNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomPropertyNodeBuilder.cs index 9c69994a8c..2d59f4894c 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomPropertyNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomPropertyNodeBuilder.cs @@ -91,7 +91,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var property = CecilLoader.GetCecilObject ((IUnresolvedProperty)navigator.DataItem); + var property = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedProperty)navigator.DataItem); return DomMethodNodeBuilder.Disassemble (data, rd => rd.DisassembleProperty (property)); } @@ -111,7 +111,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var property = CecilLoader.GetCecilObject ((IUnresolvedProperty)navigator.DataItem); + var property = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedProperty)navigator.DataItem); if (property == null) return null; return DomMethodNodeBuilder.Decompile (data, DomMethodNodeBuilder.GetModule (navigator), property.DeclaringType, b => b.AddProperty (property)); @@ -121,7 +121,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var property = CecilLoader.GetCecilObject ((IUnresolvedProperty)navigator.DataItem); + var property = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedProperty)navigator.DataItem); if (property == null) return null; return DomMethodNodeBuilder.GetSummary (data, DomMethodNodeBuilder.GetModule (navigator), property.DeclaringType, b => b.AddProperty (property)); diff --git a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomTypeNodeBuilder.cs b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomTypeNodeBuilder.cs index 4bfa9b4ecc..c5c427b7fb 100644 --- a/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomTypeNodeBuilder.cs +++ b/main/src/addins/MonoDevelop.AssemblyBrowser/MonoDevelop.AssemblyBrowser/TreeNodes/DomTypeNodeBuilder.cs @@ -132,7 +132,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var type = CecilLoader.GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); + var type = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); if (type == null) return null; @@ -160,7 +160,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var type = CecilLoader.GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); + var type = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); if (type == null) return null; var types = DesktopService.GetMimeTypeInheritanceChain (data.MimeType); @@ -175,7 +175,7 @@ namespace MonoDevelop.AssemblyBrowser { if (DomMethodNodeBuilder.HandleSourceCodeEntity (navigator, data)) return null; - var type = CecilLoader.GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); + var type = GetCecilLoader (navigator).GetCecilObject ((IUnresolvedTypeDefinition)navigator.DataItem); if (type == null) return null; var types = DesktopService.GetMimeTypeInheritanceChain (data.MimeType); -- cgit v1.2.3