提交 7ae5d359 编写于 作者: H Heejae Chang

expose a way to enable compiler diagnostics to custom workspace

上级 c7de25cf
...@@ -12,9 +12,11 @@ ...@@ -12,9 +12,11 @@
namespace Microsoft.CodeAnalysis.Editor.Implementation.TodoComments namespace Microsoft.CodeAnalysis.Editor.Implementation.TodoComments
{ {
[Export(typeof(ITodoListProvider))]
[Shared] [Shared]
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host, WorkspaceKind.Interactive, WorkspaceKind.MiscellaneousFiles)] [Export(typeof(ITodoListProvider))]
[ExportIncrementalAnalyzerProvider(
name: nameof(TodoCommentIncrementalAnalyzerProvider),
workspaceKinds: new[] { WorkspaceKind.Host, WorkspaceKind.Interactive, WorkspaceKind.MiscellaneousFiles })]
internal class TodoCommentIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider, ITodoListProvider internal class TodoCommentIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider, ITodoListProvider
{ {
private static readonly ConditionalWeakTable<Workspace, TodoCommentIncrementalAnalyzer> s_analyzers = new ConditionalWeakTable<Workspace, TodoCommentIncrementalAnalyzer>(); private static readonly ConditionalWeakTable<Workspace, TodoCommentIncrementalAnalyzer> s_analyzers = new ConditionalWeakTable<Workspace, TodoCommentIncrementalAnalyzer>();
......
...@@ -9,24 +9,26 @@ ...@@ -9,24 +9,26 @@
using Microsoft.CodeAnalysis; using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Diagnostics; using Microsoft.CodeAnalysis.Diagnostics;
using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Options;
using Microsoft.CodeAnalysis.Shared.Extensions;
using Microsoft.CodeAnalysis.Shared.Options; using Microsoft.CodeAnalysis.Shared.Options;
using Microsoft.CodeAnalysis.SolutionCrawler; using Microsoft.CodeAnalysis.SolutionCrawler;
using Roslyn.Utilities; using Roslyn.Utilities;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Diagnostics namespace Microsoft.VisualStudio.LanguageServices.Implementation.Diagnostics
{ {
[ExportIncrementalAnalyzerProvider(WorkspaceKind.MiscellaneousFiles)]
[Shared] [Shared]
internal partial class MiscellaneousDiagnosticAnalyzerService : IIncrementalAnalyzerProvider, IDiagnosticUpdateSource [ExportIncrementalAnalyzerProvider(WellKnownSolutionCrawlerAnalyzers.Diagnostic, workspaceKinds: null)]
internal partial class DefaultDiagnosticAnalyzerService : IIncrementalAnalyzerProvider, IDiagnosticUpdateSource
{ {
private const int Syntax = 1;
private const int Semantic = 2;
private readonly IDiagnosticAnalyzerService _analyzerService; private readonly IDiagnosticAnalyzerService _analyzerService;
[ImportingConstructor] [ImportingConstructor]
public MiscellaneousDiagnosticAnalyzerService(IDiagnosticAnalyzerService analyzerService, IDiagnosticUpdateSourceRegistrationService registrationService) public DefaultDiagnosticAnalyzerService(
IDiagnosticAnalyzerService analyzerService, IDiagnosticUpdateSourceRegistrationService registrationService)
{ {
_analyzerService = analyzerService; _analyzerService = analyzerService;
registrationService.Register(this); registrationService.Register(this);
} }
...@@ -37,7 +39,7 @@ public IIncrementalAnalyzer CreateIncrementalAnalyzer(Workspace workspace) ...@@ -37,7 +39,7 @@ public IIncrementalAnalyzer CreateIncrementalAnalyzer(Workspace workspace)
return null; return null;
} }
return new SyntaxOnlyDiagnosticAnalyzer(this, workspace); return new CompilerDiagnosticAnalyzer(this, workspace);
} }
public event EventHandler<DiagnosticsUpdatedArgs> DiagnosticsUpdated; public event EventHandler<DiagnosticsUpdatedArgs> DiagnosticsUpdated;
...@@ -62,21 +64,33 @@ internal void RaiseDiagnosticsUpdated(DiagnosticsUpdatedArgs state) ...@@ -62,21 +64,33 @@ internal void RaiseDiagnosticsUpdated(DiagnosticsUpdatedArgs state)
this.DiagnosticsUpdated?.Invoke(this, state); this.DiagnosticsUpdated?.Invoke(this, state);
} }
private class SyntaxOnlyDiagnosticAnalyzer : IIncrementalAnalyzer private class CompilerDiagnosticAnalyzer : IIncrementalAnalyzer
{ {
private readonly MiscellaneousDiagnosticAnalyzerService _service; private readonly DefaultDiagnosticAnalyzerService _service;
private readonly Workspace _workspace; private readonly Workspace _workspace;
public SyntaxOnlyDiagnosticAnalyzer(MiscellaneousDiagnosticAnalyzerService service, Workspace workspace) public CompilerDiagnosticAnalyzer(DefaultDiagnosticAnalyzerService service, Workspace workspace)
{ {
_service = service; _service = service;
_workspace = workspace; _workspace = workspace;
} }
public bool NeedsReanalysisOnOptionChanged(object sender, OptionChangedEventArgs e)
{
if (e.Option == InternalRuntimeDiagnosticOptions.Syntax ||
e.Option == InternalRuntimeDiagnosticOptions.Semantic)
{
return true;
}
return false;
}
public async Task AnalyzeSyntaxAsync(Document document, CancellationToken cancellationToken) public async Task AnalyzeSyntaxAsync(Document document, CancellationToken cancellationToken)
{ {
// if closed file diagnostic is off and document is not opened, then don't do anything // right now, there is no way to observe diagnostics for closed file.
if (!CheckOptions(document)) if (!_workspace.IsDocumentOpen(document.Id) ||
!_workspace.Options.GetOption(InternalRuntimeDiagnosticOptions.Syntax))
{ {
return; return;
} }
...@@ -87,25 +101,45 @@ public async Task AnalyzeSyntaxAsync(Document document, CancellationToken cancel ...@@ -87,25 +101,45 @@ public async Task AnalyzeSyntaxAsync(Document document, CancellationToken cancel
Contract.Requires(document.Project.Solution.Workspace == _workspace); Contract.Requires(document.Project.Solution.Workspace == _workspace);
var diagnosticData = diagnostics == null ? ImmutableArray<DiagnosticData>.Empty : diagnostics.Select(d => DiagnosticData.Create(document, d)).ToImmutableArrayOrEmpty(); var diagnosticData = diagnostics == null ? ImmutableArray<DiagnosticData>.Empty : diagnostics.Select(d => DiagnosticData.Create(document, d)).ToImmutableArrayOrEmpty();
_service.RaiseDiagnosticsUpdated(
DiagnosticsUpdatedArgs.DiagnosticsCreated(new DefaultUpdateArgsId(_workspace.Kind, Syntax, document.Id),
_workspace, document.Project.Solution, document.Project.Id, document.Id, diagnosticData));
}
public async Task AnalyzeDocumentAsync(Document document, SyntaxNode bodyOpt, CancellationToken cancellationToken)
{
// right now, there is no way to observe diagnostics for closed file.
if (!_workspace.IsDocumentOpen(document.Id) ||
!_workspace.Options.GetOption(InternalRuntimeDiagnosticOptions.Semantic))
{
return;
}
var model = await document.GetSemanticModelAsync(cancellationToken).ConfigureAwait(false);
var diagnostics = model.GetMethodBodyDiagnostics(span: null, cancellationToken: cancellationToken).Concat(
model.GetDeclarationDiagnostics(span: null, cancellationToken: cancellationToken));
Contract.Requires(document.Project.Solution.Workspace == _workspace);
var diagnosticData = diagnostics == null ? ImmutableArray<DiagnosticData>.Empty : diagnostics.Select(d => DiagnosticData.Create(document, d)).ToImmutableArrayOrEmpty();
_service.RaiseDiagnosticsUpdated( _service.RaiseDiagnosticsUpdated(
DiagnosticsUpdatedArgs.DiagnosticsCreated(new MiscUpdateArgsId(document.Id), DiagnosticsUpdatedArgs.DiagnosticsCreated(new DefaultUpdateArgsId(_workspace.Kind, Semantic, document.Id),
_workspace, document.Project.Solution, document.Project.Id, document.Id, diagnosticData)); _workspace, document.Project.Solution, document.Project.Id, document.Id, diagnosticData));
} }
public void RemoveDocument(DocumentId documentId) public void RemoveDocument(DocumentId documentId)
{ {
// a file is removed from misc project // a file is removed from misc project
RaiseEmptyDiagnosticUpdated(documentId); RaiseEmptyDiagnosticUpdated(Syntax, documentId);
RaiseEmptyDiagnosticUpdated(Semantic, documentId);
} }
public Task DocumentResetAsync(Document document, CancellationToken cancellationToken) public Task DocumentResetAsync(Document document, CancellationToken cancellationToken)
{ {
// no closed file diagnostic and file is not opened, remove any existing diagnostics // no closed file diagnostic and file is not opened, remove any existing diagnostics
if (!CheckOptions(document)) RemoveDocument(document.Id);
{
RaiseEmptyDiagnosticUpdated(document.Id);
}
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
} }
...@@ -114,16 +148,10 @@ public Task DocumentCloseAsync(Document document, CancellationToken cancellation ...@@ -114,16 +148,10 @@ public Task DocumentCloseAsync(Document document, CancellationToken cancellation
return DocumentResetAsync(document, cancellationToken); return DocumentResetAsync(document, cancellationToken);
} }
private void RaiseEmptyDiagnosticUpdated(DocumentId documentId) private void RaiseEmptyDiagnosticUpdated(int kind, DocumentId documentId)
{ {
_service.RaiseDiagnosticsUpdated(DiagnosticsUpdatedArgs.DiagnosticsRemoved( _service.RaiseDiagnosticsUpdated(DiagnosticsUpdatedArgs.DiagnosticsRemoved(
ValueTuple.Create(this, documentId), _workspace, null, documentId.ProjectId, documentId)); new DefaultUpdateArgsId(_workspace.Kind, kind, documentId), _workspace, null, documentId.ProjectId, documentId));
}
// method we don't care. misc project only supports syntax errors
public Task AnalyzeDocumentAsync(Document document, SyntaxNode bodyOpt, CancellationToken cancellationToken)
{
return SpecializedTasks.EmptyTask;
} }
public Task AnalyzeProjectAsync(Project project, bool semanticsChanged, CancellationToken cancellationToken) public Task AnalyzeProjectAsync(Project project, bool semanticsChanged, CancellationToken cancellationToken)
...@@ -136,11 +164,6 @@ public Task DocumentOpenAsync(Document document, CancellationToken cancellationT ...@@ -136,11 +164,6 @@ public Task DocumentOpenAsync(Document document, CancellationToken cancellationT
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
} }
public bool NeedsReanalysisOnOptionChanged(object sender, OptionChangedEventArgs e)
{
return false;
}
public Task NewSolutionSnapshotAsync(Solution solution, CancellationToken cancellationToken) public Task NewSolutionSnapshotAsync(Solution solution, CancellationToken cancellationToken)
{ {
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
...@@ -150,45 +173,31 @@ public void RemoveProject(ProjectId projectId) ...@@ -150,45 +173,31 @@ public void RemoveProject(ProjectId projectId)
{ {
} }
private bool CheckOptions(Document document) private class DefaultUpdateArgsId : BuildToolId.Base<int, DocumentId>, ISupportLiveUpdate
{ {
if (ServiceFeatureOnOffOptions.IsClosedFileDiagnosticsEnabled(_workspace, document.Project.Language) && private readonly string _workspaceKind;
_workspace.Options.GetOption(RuntimeOptions.FullSolutionAnalysis))
{
return true;
}
return document.IsOpen();
}
private class MiscUpdateArgsId : BuildToolId.Base<DocumentId>, ISupportLiveUpdate public DefaultUpdateArgsId(string workspaceKind, int type, DocumentId documentId) : base(type, documentId)
{
public MiscUpdateArgsId(DocumentId documentId) : base(documentId)
{ {
_workspaceKind = workspaceKind;
} }
public override string BuildTool public override string BuildTool => PredefinedBuildTools.Live;
{
get
{
return PredefinedBuildTools.Live;
}
}
public override bool Equals(object obj) public override bool Equals(object obj)
{ {
var other = obj as MiscUpdateArgsId; var other = obj as DefaultUpdateArgsId;
if (other == null) if (other == null)
{ {
return false; return false;
} }
return base.Equals(obj); return _workspaceKind == other._workspaceKind && base.Equals(obj);
} }
public override int GetHashCode() public override int GetHashCode()
{ {
return base.GetHashCode(); return Hash.Combine(_workspaceKind.GetHashCode(), base.GetHashCode());
} }
} }
} }
......
...@@ -15,7 +15,9 @@ ...@@ -15,7 +15,9 @@
namespace Microsoft.CodeAnalysis.Diagnostics namespace Microsoft.CodeAnalysis.Diagnostics
{ {
[ExportIncrementalAnalyzerProvider(highPriorityForActiveFile: true, workspaceKinds: new string[] { WorkspaceKind.Host, WorkspaceKind.Interactive })] [ExportIncrementalAnalyzerProvider(
highPriorityForActiveFile: true, name: WellKnownSolutionCrawlerAnalyzers.Diagnostic,
workspaceKinds: new string[] { WorkspaceKind.Host, WorkspaceKind.Interactive })]
internal partial class DiagnosticAnalyzerService : IIncrementalAnalyzerProvider internal partial class DiagnosticAnalyzerService : IIncrementalAnalyzerProvider
{ {
private readonly ConditionalWeakTable<Workspace, BaseDiagnosticIncrementalAnalyzer> _map; private readonly ConditionalWeakTable<Workspace, BaseDiagnosticIncrementalAnalyzer> _map;
......
...@@ -221,6 +221,7 @@ ...@@ -221,6 +221,7 @@
<Compile Include="Diagnostics\HostDiagnosticAnalyzerPackage.cs" /> <Compile Include="Diagnostics\HostDiagnosticAnalyzerPackage.cs" />
<Compile Include="Diagnostics\IDiagnosticUpdateSourceRegistrationService.cs" /> <Compile Include="Diagnostics\IDiagnosticUpdateSourceRegistrationService.cs" />
<Compile Include="Diagnostics\InternalDiagnosticsOptionsProvider.cs" /> <Compile Include="Diagnostics\InternalDiagnosticsOptionsProvider.cs" />
<Compile Include="Diagnostics\DefaultDiagnosticAnalyzerService.cs" />
<Compile Include="Diagnostics\PredefinedBuildTools.cs" /> <Compile Include="Diagnostics\PredefinedBuildTools.cs" />
<Compile Include="Diagnostics\DiagnosticAnalyzerService_BuildSynchronization.cs" /> <Compile Include="Diagnostics\DiagnosticAnalyzerService_BuildSynchronization.cs" />
<Compile Include="Diagnostics\BuildToolId.cs" /> <Compile Include="Diagnostics\BuildToolId.cs" />
...@@ -529,17 +530,13 @@ ...@@ -529,17 +530,13 @@
<Compile Include="Snippets\SnippetInfo.cs" /> <Compile Include="Snippets\SnippetInfo.cs" />
<Compile Include="SolutionCrawler\AbstractDocumentDifferenceService.cs" /> <Compile Include="SolutionCrawler\AbstractDocumentDifferenceService.cs" />
<Compile Include="SolutionCrawler\AggregateIncrementalAnalyzer.cs" /> <Compile Include="SolutionCrawler\AggregateIncrementalAnalyzer.cs" />
<Compile Include="SolutionCrawler\Extensibility\ExportIncrementalAnalyzerProviderAttribute.cs" />
<Compile Include="SolutionCrawler\Extensibility\ExportPerLanguageIncrementalAnalyzerProviderAttribute.cs" /> <Compile Include="SolutionCrawler\Extensibility\ExportPerLanguageIncrementalAnalyzerProviderAttribute.cs" />
<Compile Include="SolutionCrawler\Extensibility\IIncrementalAnalyzerProvider.cs" />
<Compile Include="SolutionCrawler\Extensibility\IncrementalAnalyzerProviderMetadata.cs" />
<Compile Include="SolutionCrawler\Extensibility\IPerLanguageIncrementalAnalyzerProvider.cs" /> <Compile Include="SolutionCrawler\Extensibility\IPerLanguageIncrementalAnalyzerProvider.cs" />
<Compile Include="SolutionCrawler\Extensibility\PerLanguageIncrementalAnalyzerProviderMetadata.cs" /> <Compile Include="SolutionCrawler\Extensibility\PerLanguageIncrementalAnalyzerProviderMetadata.cs" />
<Compile Include="SolutionCrawler\Extensions.cs" /> <Compile Include="SolutionCrawler\Extensions.cs" />
<Compile Include="SolutionCrawler\IdleProcessor.cs" /> <Compile Include="SolutionCrawler\IdleProcessor.cs" />
<Compile Include="SolutionCrawler\IDocumentDifferenceService.cs" /> <Compile Include="SolutionCrawler\IDocumentDifferenceService.cs" />
<Compile Include="SolutionCrawler\IDocumentTrackingService.cs" /> <Compile Include="SolutionCrawler\IDocumentTrackingService.cs" />
<Compile Include="SolutionCrawler\IIncrementalAnalyzer.cs" />
<Compile Include="SolutionCrawler\IncrementalAnalyzerBase.cs" /> <Compile Include="SolutionCrawler\IncrementalAnalyzerBase.cs" />
<Compile Include="SolutionCrawler\IncrementalAnalyzerProviderBase.cs" /> <Compile Include="SolutionCrawler\IncrementalAnalyzerProviderBase.cs" />
<Compile Include="SolutionCrawler\InternalSolutionCrawlerOptionsProvider.cs" /> <Compile Include="SolutionCrawler\InternalSolutionCrawlerOptionsProvider.cs" />
...@@ -548,7 +545,6 @@ ...@@ -548,7 +545,6 @@
<Compile Include="SolutionCrawler\ISolutionCrawlerProgressReporter.cs" /> <Compile Include="SolutionCrawler\ISolutionCrawlerProgressReporter.cs" />
<Compile Include="SolutionCrawler\ISolutionCrawlerService.cs" /> <Compile Include="SolutionCrawler\ISolutionCrawlerService.cs" />
<Compile Include="SolutionCrawler\IWorkCoordinatorPriorityService.cs" /> <Compile Include="SolutionCrawler\IWorkCoordinatorPriorityService.cs" />
<Compile Include="SolutionCrawler\ISolutionCrawlerRegistrationService.cs" />
<Compile Include="SolutionCrawler\PredefinedInvocationReasons.cs" /> <Compile Include="SolutionCrawler\PredefinedInvocationReasons.cs" />
<Compile Include="SolutionCrawler\SolutionCrawlerLogger.cs" /> <Compile Include="SolutionCrawler\SolutionCrawlerLogger.cs" />
<Compile Include="SolutionCrawler\InternalSolutionCrawlerOptions.cs" /> <Compile Include="SolutionCrawler\InternalSolutionCrawlerOptions.cs" />
......
...@@ -33,7 +33,7 @@ namespace Microsoft.CodeAnalysis.IncrementalCaches ...@@ -33,7 +33,7 @@ namespace Microsoft.CodeAnalysis.IncrementalCaches
/// once it is fully indexed, then total results will be returned. /// once it is fully indexed, then total results will be returned.
/// </summary> /// </summary>
[Shared] [Shared]
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host)] [ExportIncrementalAnalyzerProvider(nameof(SymbolTreeInfoIncrementalAnalyzerProvider), new[] { WorkspaceKind.Host })]
[ExportWorkspaceServiceFactory(typeof(ISymbolTreeInfoCacheService))] [ExportWorkspaceServiceFactory(typeof(ISymbolTreeInfoCacheService))]
internal class SymbolTreeInfoIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider, IWorkspaceServiceFactory internal class SymbolTreeInfoIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider, IWorkspaceServiceFactory
{ {
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
namespace Microsoft.CodeAnalysis.IncrementalCaches namespace Microsoft.CodeAnalysis.IncrementalCaches
{ {
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared] [ExportIncrementalAnalyzerProvider(nameof(SyntaxTreeInfoIncrementalAnalyzerProvider), new[] { WorkspaceKind.Host }), Shared]
internal class SyntaxTreeInfoIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider internal class SyntaxTreeInfoIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider
{ {
public IIncrementalAnalyzer CreateIncrementalAnalyzer(Workspace workspace) public IIncrementalAnalyzer CreateIncrementalAnalyzer(Workspace workspace)
......
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
using System; using System;
using System.Collections.Concurrent; using System.Collections.Concurrent;
using System.Composition; using System.Composition;
using System.Linq;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Options;
...@@ -13,7 +14,7 @@ ...@@ -13,7 +14,7 @@
namespace Microsoft.CodeAnalysis.Notification namespace Microsoft.CodeAnalysis.Notification
{ {
[Export(typeof(ISemanticChangeNotificationService)), Shared] [Export(typeof(ISemanticChangeNotificationService)), Shared]
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host, WorkspaceKind.Interactive, WorkspaceKind.MiscellaneousFiles)] [ExportIncrementalAnalyzerProvider(nameof(SemanticChangeNotificationService), workspaceKinds: null)]
internal class SemanticChangeNotificationService : ISemanticChangeNotificationService, IIncrementalAnalyzerProvider internal class SemanticChangeNotificationService : ISemanticChangeNotificationService, IIncrementalAnalyzerProvider
{ {
public event EventHandler<Document> OpenedDocumentSemanticChanged; public event EventHandler<Document> OpenedDocumentSemanticChanged;
...@@ -38,17 +39,36 @@ public NotificationService(SemanticChangeNotificationService owner) ...@@ -38,17 +39,36 @@ public NotificationService(SemanticChangeNotificationService owner)
_owner = owner; _owner = owner;
} }
public Task DocumentResetAsync(Document document, CancellationToken cancellationToken) public void RemoveDocument(DocumentId documentId)
{ {
// now it runs for all workspace, make sure we get rid of entry from the map
// as soon as it is not needed.
// this whole thing will go away when workspace disable itself from solution crawler.
VersionStamp unused; VersionStamp unused;
_map.TryRemove(document.Id, out unused); _map.TryRemove(documentId, out unused);
}
public void RemoveProject(ProjectId projectId)
{
foreach (var documentId in _map.Keys.Where(id => id.ProjectId == projectId).ToArray())
{
RemoveDocument(documentId);
}
}
public Task DocumentCloseAsync(Document document, CancellationToken cancellationToken)
{
return DocumentResetAsync(document, cancellationToken);
}
public Task DocumentResetAsync(Document document, CancellationToken cancellationToken)
{
RemoveDocument(document.Id);
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
} }
public bool NeedsReanalysisOnOptionChanged(object sender, OptionChangedEventArgs e) public bool NeedsReanalysisOnOptionChanged(object sender, OptionChangedEventArgs e)
{ {
// TODO: Is this correct?
return false; return false;
} }
...@@ -81,11 +101,6 @@ public Task DocumentOpenAsync(Document document, CancellationToken cancellationT ...@@ -81,11 +101,6 @@ public Task DocumentOpenAsync(Document document, CancellationToken cancellationT
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
} }
public Task DocumentCloseAsync(Document document, CancellationToken cancellationToken)
{
return SpecializedTasks.EmptyTask;
}
public Task NewSolutionSnapshotAsync(Solution solution, CancellationToken cancellationToken) public Task NewSolutionSnapshotAsync(Solution solution, CancellationToken cancellationToken)
{ {
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
...@@ -101,13 +116,6 @@ public Task AnalyzeProjectAsync(Project project, bool semanticsChanged, Cancella ...@@ -101,13 +116,6 @@ public Task AnalyzeProjectAsync(Project project, bool semanticsChanged, Cancella
return SpecializedTasks.EmptyTask; return SpecializedTasks.EmptyTask;
} }
public void RemoveDocument(DocumentId documentId)
{
}
public void RemoveProject(ProjectId projectId)
{
}
#endregion #endregion
} }
} }
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
using System.Collections.Generic; using System.Collections.Generic;
using System.Collections.Immutable; using System.Collections.Immutable;
using System.Composition; using System.Composition;
using System.Diagnostics;
using System.Linq; using System.Linq;
using Microsoft.CodeAnalysis.Host; using Microsoft.CodeAnalysis.Host;
using Microsoft.CodeAnalysis.Host.Mef; using Microsoft.CodeAnalysis.Host.Mef;
...@@ -16,11 +17,13 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler ...@@ -16,11 +17,13 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler
[ExportWorkspaceService(typeof(ISolutionCrawlerRegistrationService), ServiceLayer.Host), Shared] [ExportWorkspaceService(typeof(ISolutionCrawlerRegistrationService), ServiceLayer.Host), Shared]
internal partial class SolutionCrawlerRegistrationService : ISolutionCrawlerRegistrationService internal partial class SolutionCrawlerRegistrationService : ISolutionCrawlerRegistrationService
{ {
private const string Default = "*";
private readonly object _gate; private readonly object _gate;
private readonly SolutionCrawlerProgressReporter _progressReporter; private readonly SolutionCrawlerProgressReporter _progressReporter;
private readonly IAsynchronousOperationListener _listener; private readonly IAsynchronousOperationListener _listener;
private readonly ImmutableArray<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> _analyzerProviders; private readonly ImmutableDictionary<string, ImmutableArray<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>>> _analyzerProviders;
private readonly Dictionary<Workspace, WorkCoordinator> _documentWorkCoordinatorMap; private readonly Dictionary<Workspace, WorkCoordinator> _documentWorkCoordinatorMap;
[ImportingConstructor] [ImportingConstructor]
...@@ -30,7 +33,9 @@ internal partial class SolutionCrawlerRegistrationService : ISolutionCrawlerRegi ...@@ -30,7 +33,9 @@ internal partial class SolutionCrawlerRegistrationService : ISolutionCrawlerRegi
{ {
_gate = new object(); _gate = new object();
_analyzerProviders = analyzerProviders.ToImmutableArray(); _analyzerProviders = analyzerProviders.GroupBy(kv => kv.Metadata.Name).ToImmutableDictionary(g => g.Key, g => g.ToImmutableArray());
AssertAnalyzerProviders(_analyzerProviders);
_documentWorkCoordinatorMap = new Dictionary<Workspace, WorkCoordinator>(ReferenceEqualityComparer.Instance); _documentWorkCoordinatorMap = new Dictionary<Workspace, WorkCoordinator>(ReferenceEqualityComparer.Instance);
_listener = new AggregateAsynchronousOperationListener(asyncListeners, FeatureAttribute.SolutionCrawler); _listener = new AggregateAsynchronousOperationListener(asyncListeners, FeatureAttribute.SolutionCrawler);
...@@ -51,7 +56,7 @@ public void Register(Workspace workspace) ...@@ -51,7 +56,7 @@ public void Register(Workspace workspace)
var coordinator = new WorkCoordinator( var coordinator = new WorkCoordinator(
_listener, _listener,
_analyzerProviders.Where(l => l.Metadata.WorkspaceKinds.Any(wk => wk == workspace.Kind)), GetAnalyzerProviders(workspace),
new Registration(correlationId, workspace, _progressReporter)); new Registration(correlationId, workspace, _progressReporter));
_documentWorkCoordinatorMap.Add(workspace, coordinator); _documentWorkCoordinatorMap.Add(workspace, coordinator);
...@@ -127,6 +132,99 @@ internal void WaitUntilCompletion_ForTestingPurposesOnly(Workspace workspace) ...@@ -127,6 +132,99 @@ internal void WaitUntilCompletion_ForTestingPurposesOnly(Workspace workspace)
} }
} }
private IEnumerable<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> GetAnalyzerProviders(Workspace workspace)
{
Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata> lazyProvider;
foreach (var kv in _analyzerProviders)
{
var lazyProviders = kv.Value;
// try get provider for the specific workspace kind
if (TryGetProvider(workspace.Kind, lazyProviders, out lazyProvider))
{
yield return lazyProvider;
continue;
}
// try get default provider
if (TryGetProvider(Default, lazyProviders, out lazyProvider))
{
yield return lazyProvider;
}
}
}
private bool TryGetProvider(
string kind,
ImmutableArray<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> lazyProviders,
out Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata> lazyProvider)
{
// set out param
lazyProvider = null;
// try find provider for specific workspace kind
if (kind != Default)
{
foreach (var provider in lazyProviders)
{
if (provider.Metadata.WorkspaceKinds?.Any(wk => wk == kind) == true)
{
lazyProvider = provider;
return true;
}
}
return false;
}
// try find default provider
foreach (var provider in lazyProviders)
{
if (IsDefaultProvider(provider.Metadata))
{
lazyProvider = provider;
return true;
}
return false;
}
return false;
}
[Conditional("DEBUG")]
private static void AssertAnalyzerProviders(
ImmutableDictionary<string, ImmutableArray<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>>> analyzerProviders)
{
#if DEBUG
// make sure there is duplicated provider defined for same workspace.
var set = new HashSet<string>();
foreach (var kv in analyzerProviders)
{
foreach (var lazyProvider in kv.Value)
{
if (IsDefaultProvider(lazyProvider.Metadata))
{
Contract.Requires(set.Add(Default));
continue;
}
foreach (var kind in lazyProvider.Metadata.WorkspaceKinds)
{
Contract.Requires(set.Add(kind));
}
}
set.Clear();
}
#endif
}
private static bool IsDefaultProvider(IncrementalAnalyzerProviderMetadata providerMetadata)
{
return providerMetadata.WorkspaceKinds == null || providerMetadata.WorkspaceKinds.Length == 0;
}
private class Registration private class Registration
{ {
public readonly int CorrelationId; public readonly int CorrelationId;
......
...@@ -75,9 +75,7 @@ private IDiagnosticAnalyzerService GetDiagnosticAnalyzerService(IEnumerable<Lazy ...@@ -75,9 +75,7 @@ private IDiagnosticAnalyzerService GetDiagnosticAnalyzerService(IEnumerable<Lazy
private static ImmutableArray<IIncrementalAnalyzer> GetActiveFileIncrementalAnalyzers( private static ImmutableArray<IIncrementalAnalyzer> GetActiveFileIncrementalAnalyzers(
Registration registration, IEnumerable<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> providers) Registration registration, IEnumerable<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> providers)
{ {
var matchingProviders = providers.Where(p => p.Metadata.HighPriorityForActiveFile && p.Metadata.WorkspaceKinds.Contains(registration.Workspace.Kind)); var orderedAnalyzers = GetOrderedAnalyzers(registration, providers.Where(p => p.Metadata.HighPriorityForActiveFile));
var orderedAnalyzers = GetOrderedAnalyzers(registration, matchingProviders);
SolutionCrawlerLogger.LogActiveFileAnalyzers(registration.CorrelationId, registration.Workspace, orderedAnalyzers); SolutionCrawlerLogger.LogActiveFileAnalyzers(registration.CorrelationId, registration.Workspace, orderedAnalyzers);
return orderedAnalyzers; return orderedAnalyzers;
...@@ -86,9 +84,7 @@ private IDiagnosticAnalyzerService GetDiagnosticAnalyzerService(IEnumerable<Lazy ...@@ -86,9 +84,7 @@ private IDiagnosticAnalyzerService GetDiagnosticAnalyzerService(IEnumerable<Lazy
private static ImmutableArray<IIncrementalAnalyzer> GetIncrementalAnalyzers( private static ImmutableArray<IIncrementalAnalyzer> GetIncrementalAnalyzers(
Registration registration, IEnumerable<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> providers) Registration registration, IEnumerable<Lazy<IIncrementalAnalyzerProvider, IncrementalAnalyzerProviderMetadata>> providers)
{ {
var matchingProviders = providers.Where(p => p.Metadata.WorkspaceKinds.Contains(registration.Workspace.Kind)); var orderedAnalyzers = GetOrderedAnalyzers(registration, providers);
var orderedAnalyzers = GetOrderedAnalyzers(registration, matchingProviders);
SolutionCrawlerLogger.LogAnalyzers(registration.CorrelationId, registration.Workspace, orderedAnalyzers); SolutionCrawlerLogger.LogAnalyzers(registration.CorrelationId, registration.Workspace, orderedAnalyzers);
return orderedAnalyzers; return orderedAnalyzers;
......
...@@ -8,7 +8,9 @@ ...@@ -8,7 +8,9 @@
namespace Microsoft.VisualStudio.LanguageServices.Implementation.CompilationErrorTelemetry namespace Microsoft.VisualStudio.LanguageServices.Implementation.CompilationErrorTelemetry
{ {
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared] // Disabled compilation error telemetry per discussion with .net team.
// tracking bug - https://github.com/dotnet/roslyn/issues/11133
// [ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared]
internal class CompilationErrorTelemetryIncrementalAnalyzer : IncrementalAnalyzerProviderBase internal class CompilationErrorTelemetryIncrementalAnalyzer : IncrementalAnalyzerProviderBase
{ {
public const string Name = "CompilationErrorTelemetryIncrementalAnalyzer"; public const string Name = "CompilationErrorTelemetryIncrementalAnalyzer";
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
namespace Microsoft.VisualStudio.LanguageServices.Implementation.DesignerAttribute namespace Microsoft.VisualStudio.LanguageServices.Implementation.DesignerAttribute
{ {
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared] [ExportIncrementalAnalyzerProvider(Name, new[] { WorkspaceKind.Host }), Shared]
internal class DesignerAttributeIncrementalAnalyzerProvider : IncrementalAnalyzerProviderBase internal class DesignerAttributeIncrementalAnalyzerProvider : IncrementalAnalyzerProviderBase
{ {
public const string Name = "DesignerAttributeIncrementalAnalyzerProvider"; public const string Name = "DesignerAttributeIncrementalAnalyzerProvider";
......
...@@ -43,9 +43,6 @@ internal sealed partial class MiscellaneousFilesWorkspace : Workspace, IVsRunnin ...@@ -43,9 +43,6 @@ internal sealed partial class MiscellaneousFilesWorkspace : Workspace, IVsRunnin
private readonly ImmutableArray<MetadataReference> _metadataReferences; private readonly ImmutableArray<MetadataReference> _metadataReferences;
private uint _runningDocumentTableEventsCookie; private uint _runningDocumentTableEventsCookie;
// document worker coordinator
private ISolutionCrawlerRegistrationService _registrationService;
[ImportingConstructor] [ImportingConstructor]
public MiscellaneousFilesWorkspace( public MiscellaneousFilesWorkspace(
IVsEditorAdaptersFactoryService editorAdaptersFactoryService, IVsEditorAdaptersFactoryService editorAdaptersFactoryService,
...@@ -53,7 +50,7 @@ internal sealed partial class MiscellaneousFilesWorkspace : Workspace, IVsRunnin ...@@ -53,7 +50,7 @@ internal sealed partial class MiscellaneousFilesWorkspace : Workspace, IVsRunnin
SaveEventsService saveEventsService, SaveEventsService saveEventsService,
VisualStudioWorkspace visualStudioWorkspace, VisualStudioWorkspace visualStudioWorkspace,
SVsServiceProvider serviceProvider) : SVsServiceProvider serviceProvider) :
base(visualStudioWorkspace.Services.HostServices, "MiscellaneousFiles") base(visualStudioWorkspace.Services.HostServices, WorkspaceKind.MiscellaneousFiles)
{ {
_editorAdaptersFactoryService = editorAdaptersFactoryService; _editorAdaptersFactoryService = editorAdaptersFactoryService;
_fileTrackingMetadataAsSourceService = fileTrackingMetadataAsSourceService; _fileTrackingMetadataAsSourceService = fileTrackingMetadataAsSourceService;
...@@ -74,32 +71,12 @@ public void RegisterLanguage(Guid languageGuid, string languageName, string scri ...@@ -74,32 +71,12 @@ public void RegisterLanguage(Guid languageGuid, string languageName, string scri
internal void StartSolutionCrawler() internal void StartSolutionCrawler()
{ {
if (_registrationService == null) DiagnosticProvider.Enable(this, DiagnosticProvider.Options.Syntax);
{
lock (this)
{
if (_registrationService == null)
{
_registrationService = this.Services.GetService<ISolutionCrawlerRegistrationService>();
_registrationService.Register(this);
}
}
}
} }
internal void StopSolutionCrawler() internal void StopSolutionCrawler()
{ {
if (_registrationService != null) DiagnosticProvider.Disable(this);
{
lock (this)
{
if (_registrationService != null)
{
_registrationService.Unregister(this, blockingShutdown: true);
_registrationService = null;
}
}
}
} }
private LanguageInformation TryGetLanguageInformation(string filename) private LanguageInformation TryGetLanguageInformation(string filename)
...@@ -255,7 +232,7 @@ private void Registration_WorkspaceChanged(object sender, EventArgs e) ...@@ -255,7 +232,7 @@ private void Registration_WorkspaceChanged(object sender, EventArgs e)
} }
} }
else else
{ {
// We should now claim this // We should now claim this
AttachToDocument(docCookie, moniker); AttachToDocument(docCookie, moniker);
} }
......
...@@ -16,7 +16,7 @@ namespace Microsoft.VisualStudio.LanguageServices.Implementation.SolutionSize ...@@ -16,7 +16,7 @@ namespace Microsoft.VisualStudio.LanguageServices.Implementation.SolutionSize
/// Track approximate solution size. /// Track approximate solution size.
/// </summary> /// </summary>
[Export] [Export]
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared] [ExportIncrementalAnalyzerProvider(nameof(SolutionSizeTracker), new[] { WorkspaceKind.Host }), Shared]
internal class SolutionSizeTracker : IIncrementalAnalyzerProvider internal class SolutionSizeTracker : IIncrementalAnalyzerProvider
{ {
private readonly IncrementalAnalyzer _tracker = new IncrementalAnalyzer(); private readonly IncrementalAnalyzer _tracker = new IncrementalAnalyzer();
......
...@@ -95,7 +95,6 @@ ...@@ -95,7 +95,6 @@
<Compile Include="Implementation\ProjectSystem\MetadataReferences\VisualStudioFrameworkAssemblyPathResolverFactory.cs" /> <Compile Include="Implementation\ProjectSystem\MetadataReferences\VisualStudioFrameworkAssemblyPathResolverFactory.cs" />
<Compile Include="Implementation\ProjectSystem\RuleSets\RuleSetEventHandler.cs" /> <Compile Include="Implementation\ProjectSystem\RuleSets\RuleSetEventHandler.cs" />
<Compile Include="Implementation\ProjectSystem\VisualStudioProjectTracker_IVsSolutionWorkingFoldersEvents.cs" /> <Compile Include="Implementation\ProjectSystem\VisualStudioProjectTracker_IVsSolutionWorkingFoldersEvents.cs" />
<Compile Include="Implementation\Diagnostics\MiscellaneousDiagnosticAnalyzerService.cs" />
<Compile Include="Implementation\Extensions\VisualStudioWorkspaceImplExtensions.cs" /> <Compile Include="Implementation\Extensions\VisualStudioWorkspaceImplExtensions.cs" />
<Compile Include="Implementation\Options\AbstractLanguageSettingsSerializer.cs" /> <Compile Include="Implementation\Options\AbstractLanguageSettingsSerializer.cs" />
<Compile Include="Implementation\Options\ExportLanguageSpecificOptionSerializerAttribute.cs" /> <Compile Include="Implementation\Options\ExportLanguageSpecificOptionSerializerAttribute.cs" />
......
...@@ -16,7 +16,7 @@ ...@@ -16,7 +16,7 @@
namespace Microsoft.VisualStudio.LanguageServices.Implementation.CodeModel namespace Microsoft.VisualStudio.LanguageServices.Implementation.CodeModel
{ {
[ExportIncrementalAnalyzerProvider(WorkspaceKind.Host), Shared] [ExportIncrementalAnalyzerProvider(nameof(CodeModelIncrementalAnalyzerProvider), new[] { WorkspaceKind.Host }), Shared]
internal class CodeModelIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider internal class CodeModelIncrementalAnalyzerProvider : IIncrementalAnalyzerProvider
{ {
private readonly IAsynchronousOperationListener _listener; private readonly IAsynchronousOperationListener _listener;
......
...@@ -18,14 +18,14 @@ Imports Roslyn.Test.Utilities ...@@ -18,14 +18,14 @@ Imports Roslyn.Test.Utilities
Imports Roslyn.Utilities Imports Roslyn.Utilities
Namespace Microsoft.VisualStudio.LanguageServices.UnitTests.Diagnostics Namespace Microsoft.VisualStudio.LanguageServices.UnitTests.Diagnostics
Public Class MiscDiagnosticUpdateSourceTests Public Class DefaultDiagnosticUpdateSourceTests
<WpfFact> <WpfFact>
Public Async Function TestMiscSquiggles() As Task Public Async Function TestMiscSquiggles() As Task
Dim code = <code> Dim code = <code>
class 123 { } class 123 { }
</code> </code>
Using workspace = Await TestWorkspace.CreateCSharpAsync(code.ToString()) Using workspace = Await TestWorkspace.CreateCSharpAsync(code.ToString())
Dim miscService = New MiscellaneousDiagnosticAnalyzerService( Dim miscService = New DefaultDiagnosticAnalyzerService(
New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()), New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()),
New MockDiagnosticUpdateSourceRegistrationService()) New MockDiagnosticUpdateSourceRegistrationService())
...@@ -68,7 +68,7 @@ class 123 { } ...@@ -68,7 +68,7 @@ class 123 { }
class 123 { } class 123 { }
</code> </code>
Using workspace = Await TestWorkspace.CreateCSharpAsync(code.ToString()) Using workspace = Await TestWorkspace.CreateCSharpAsync(code.ToString())
Dim miscService = New MiscellaneousDiagnosticAnalyzerService( Dim miscService = New DefaultDiagnosticAnalyzerService(
New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()), New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()),
New MockDiagnosticUpdateSourceRegistrationService()) New MockDiagnosticUpdateSourceRegistrationService())
...@@ -93,7 +93,7 @@ Class 123 ...@@ -93,7 +93,7 @@ Class 123
End Class End Class
</code> </code>
Using workspace = Await TestWorkspace.CreateVisualBasicAsync(code.ToString()) Using workspace = Await TestWorkspace.CreateVisualBasicAsync(code.ToString())
Dim miscService = New MiscellaneousDiagnosticAnalyzerService( Dim miscService = New DefaultDiagnosticAnalyzerService(
New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()), New TestDiagnosticAnalyzerService(DiagnosticExtensions.GetCompilerDiagnosticAnalyzersMap()),
New MockDiagnosticUpdateSourceRegistrationService()) New MockDiagnosticUpdateSourceRegistrationService())
......
...@@ -295,7 +295,7 @@ ...@@ -295,7 +295,7 @@
<Compile Include="Debugging\VisualBasicBreakpointResolutionServiceTests.vb" /> <Compile Include="Debugging\VisualBasicBreakpointResolutionServiceTests.vb" />
<Compile Include="Diagnostics\DiagnosticTableDataSourceTests.vb" /> <Compile Include="Diagnostics\DiagnosticTableDataSourceTests.vb" />
<Compile Include="Diagnostics\ExternalDiagnosticUpdateSourceTests.vb" /> <Compile Include="Diagnostics\ExternalDiagnosticUpdateSourceTests.vb" />
<Compile Include="Diagnostics\MiscDiagnosticUpdateSourceTests.vb" /> <Compile Include="Diagnostics\DefaultDiagnosticUpdateSourceTests.vb" />
<Compile Include="Diagnostics\MockExtensionManager.vb" /> <Compile Include="Diagnostics\MockExtensionManager.vb" />
<Compile Include="Diagnostics\TestTableManagerProvider.vb" /> <Compile Include="Diagnostics\TestTableManagerProvider.vb" />
<Compile Include="Diagnostics\TodoListTableDataSourceTests.vb" /> <Compile Include="Diagnostics\TodoListTableDataSourceTests.vb" />
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.CodeAnalysis.Diagnostics;
using Microsoft.CodeAnalysis.SolutionCrawler;
namespace Microsoft.CodeAnalysis
{
/// <summary>
/// Provide a way for users to turn on and off analyzing workspace for compiler diagnostics
/// </summary>
public static class DiagnosticProvider
{
public static void Enable(Workspace workspace, Options options)
{
var service = workspace.Services.GetService<ISolutionCrawlerRegistrationService>();
workspace.Options = GetOptions(workspace, options);
service.Register(workspace);
}
public static void Disable(Workspace workspace)
{
var service = workspace.Services.GetService<ISolutionCrawlerRegistrationService>();
service.Unregister(workspace);
}
private static CodeAnalysis.Options.OptionSet GetOptions(Workspace workspace, Options options)
{
return workspace.Options
.WithChangedOption(InternalRuntimeDiagnosticOptions.Syntax, (options & Options.Syntax) == Options.Syntax)
.WithChangedOption(InternalRuntimeDiagnosticOptions.Semantic, (options & Options.Semantic) == Options.Semantic);
}
[Flags]
public enum Options
{
/// <summary>
/// Include syntax errors
/// </summary>
Syntax = 0x01,
/// <summary>
/// Include semantic errors
/// </summary>
Semantic = 0x02,
}
}
}
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.CodeAnalysis.Options;
namespace Microsoft.CodeAnalysis.Diagnostics
{
internal static class InternalRuntimeDiagnosticOptions
{
public const string OptionName = "RuntimeDiagnostic";
public static readonly Option<bool> Syntax = new Option<bool>(OptionName, "Syntax", defaultValue: true);
public static readonly Option<bool> Semantic = new Option<bool>(OptionName, "Semantic", defaultValue: true);
}
}
abstract Microsoft.CodeAnalysis.Editing.SyntaxGenerator.NameOfExpression(Microsoft.CodeAnalysis.SyntaxNode expression) -> Microsoft.CodeAnalysis.SyntaxNode Microsoft.CodeAnalysis.DiagnosticProvider
\ No newline at end of file Microsoft.CodeAnalysis.DiagnosticProvider.Options
Microsoft.CodeAnalysis.DiagnosticProvider.Options.Semantic = 2 -> Microsoft.CodeAnalysis.DiagnosticProvider.Options
Microsoft.CodeAnalysis.DiagnosticProvider.Options.Syntax = 1 -> Microsoft.CodeAnalysis.DiagnosticProvider.Options
abstract Microsoft.CodeAnalysis.Editing.SyntaxGenerator.NameOfExpression(Microsoft.CodeAnalysis.SyntaxNode expression) -> Microsoft.CodeAnalysis.SyntaxNode
static Microsoft.CodeAnalysis.DiagnosticProvider.Disable(Microsoft.CodeAnalysis.Workspace workspace) -> void
static Microsoft.CodeAnalysis.DiagnosticProvider.Enable(Microsoft.CodeAnalysis.Workspace workspace, Microsoft.CodeAnalysis.DiagnosticProvider.Options options) -> void
\ No newline at end of file
...@@ -10,22 +10,24 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler ...@@ -10,22 +10,24 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler
internal class ExportIncrementalAnalyzerProviderAttribute : ExportAttribute internal class ExportIncrementalAnalyzerProviderAttribute : ExportAttribute
{ {
public bool HighPriorityForActiveFile { get; } public bool HighPriorityForActiveFile { get; }
public string Name { get; }
public string[] WorkspaceKinds { get; } public string[] WorkspaceKinds { get; }
public ExportIncrementalAnalyzerProviderAttribute(params string[] workspaceKinds) public ExportIncrementalAnalyzerProviderAttribute(string name, string[] workspaceKinds)
: base(typeof(IIncrementalAnalyzerProvider)) : base(typeof(IIncrementalAnalyzerProvider))
{ {
if (workspaceKinds == null) if (name == null)
{ {
throw new ArgumentNullException(nameof(workspaceKinds)); throw new ArgumentNullException(nameof(name));
} }
this.WorkspaceKinds = workspaceKinds; this.WorkspaceKinds = workspaceKinds;
this.Name = name;
this.HighPriorityForActiveFile = false; this.HighPriorityForActiveFile = false;
} }
public ExportIncrementalAnalyzerProviderAttribute(bool highPriorityForActiveFile, params string[] workspaceKinds) public ExportIncrementalAnalyzerProviderAttribute(bool highPriorityForActiveFile, string name, string[] workspaceKinds)
: this(workspaceKinds) : this(name, workspaceKinds)
{ {
this.HighPriorityForActiveFile = highPriorityForActiveFile; this.HighPriorityForActiveFile = highPriorityForActiveFile;
} }
......
...@@ -8,11 +8,13 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler ...@@ -8,11 +8,13 @@ namespace Microsoft.CodeAnalysis.SolutionCrawler
internal class IncrementalAnalyzerProviderMetadata internal class IncrementalAnalyzerProviderMetadata
{ {
public bool HighPriorityForActiveFile { get; } public bool HighPriorityForActiveFile { get; }
public string Name { get; }
public string[] WorkspaceKinds { get; } public string[] WorkspaceKinds { get; }
public IncrementalAnalyzerProviderMetadata(IDictionary<string, object> data) public IncrementalAnalyzerProviderMetadata(IDictionary<string, object> data)
{ {
this.HighPriorityForActiveFile = (bool)data.GetValueOrDefault("HighPriorityForActiveFile"); this.HighPriorityForActiveFile = (bool)data.GetValueOrDefault("HighPriorityForActiveFile");
this.Name = (string)data.GetValueOrDefault("Name");
this.WorkspaceKinds = (string[])data.GetValueOrDefault("WorkspaceKinds"); this.WorkspaceKinds = (string[])data.GetValueOrDefault("WorkspaceKinds");
} }
} }
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Composition;
using Microsoft.CodeAnalysis.Host.Mef;
namespace Microsoft.CodeAnalysis.SolutionCrawler
{
/// <summary>
/// null implementation of the service. it doesn't do anything since there is no way to observe
/// its impact in this layer.
/// </summary>
[ExportWorkspaceService(typeof(ISolutionCrawlerRegistrationService), ServiceLayer.Default), Shared]
internal partial class NullSolutionCrawlerRegistrationService : ISolutionCrawlerRegistrationService
{
public void Register(Workspace workspace)
{
// base implementation do nothing.
}
public void Unregister(Workspace workspace, bool blockingShutdown = false)
{
// base implementation do nothing.
}
}
}
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
namespace Microsoft.CodeAnalysis.SolutionCrawler
{
internal static class WellKnownSolutionCrawlerAnalyzers
{
public const string Diagnostic = nameof(Diagnostic);
}
}
...@@ -334,8 +334,15 @@ ...@@ -334,8 +334,15 @@
<Compile Include="CodeGeneration\CodeGenerationSymbolFactory.cs" /> <Compile Include="CodeGeneration\CodeGenerationSymbolFactory.cs" />
<Compile Include="CodeGeneration\CodeGenerator.cs" /> <Compile Include="CodeGeneration\CodeGenerator.cs" />
<Compile Include="Diagnostics\DiagnosticData.cs" /> <Compile Include="Diagnostics\DiagnosticData.cs" />
<Compile Include="Diagnostics\DiagnosticProvider.cs" />
<Compile Include="Diagnostics\Extensions.cs" /> <Compile Include="Diagnostics\Extensions.cs" />
<Compile Include="Diagnostics\InternalDiagnosticsOptions.cs" /> <Compile Include="Diagnostics\InternalDiagnosticsOptions.cs" />
<Compile Include="Diagnostics\InternalRuntimeDiagnosticOptions.cs" />
<Compile Include="SolutionCrawler\ExportIncrementalAnalyzerProviderAttribute.cs" />
<Compile Include="SolutionCrawler\IIncrementalAnalyzer.cs" />
<Compile Include="SolutionCrawler\IIncrementalAnalyzerProvider.cs" />
<Compile Include="SolutionCrawler\IncrementalAnalyzerProviderMetadata.cs" />
<Compile Include="SolutionCrawler\ISolutionCrawlerRegistrationService.cs" />
<Compile Include="Diagnostics\IWorkspaceVenusSpanMappingService.cs" /> <Compile Include="Diagnostics\IWorkspaceVenusSpanMappingService.cs" />
<Compile Include="Diagnostics\WellKnownDiagnosticPropertyNames.cs" /> <Compile Include="Diagnostics\WellKnownDiagnosticPropertyNames.cs" />
<Compile Include="Editing\DeclarationKind.cs" /> <Compile Include="Editing\DeclarationKind.cs" />
...@@ -398,6 +405,8 @@ ...@@ -398,6 +405,8 @@
<Compile Include="Packaging\IPackageSearchService.cs" /> <Compile Include="Packaging\IPackageSearchService.cs" />
<Compile Include="FindSymbols\SymbolTree\ISymbolTreeInfoCacheService.cs" /> <Compile Include="FindSymbols\SymbolTree\ISymbolTreeInfoCacheService.cs" />
<Compile Include="FindSymbols\FindReferences\MetadataUnifyingEquivalenceComparer.cs" /> <Compile Include="FindSymbols\FindReferences\MetadataUnifyingEquivalenceComparer.cs" />
<Compile Include="SolutionCrawler\NullSolutionCrawlerRegisterationService.cs" />
<Compile Include="SolutionCrawler\WellKnownSolutionCrawlerAnalyzers.cs" />
<Compile Include="Utilities\ArraySlice.cs" /> <Compile Include="Utilities\ArraySlice.cs" />
<Compile Include="Utilities\BKTree.cs" /> <Compile Include="Utilities\BKTree.cs" />
<Compile Include="FindSymbols\SyntaxTree\AbstractSyntaxTreeInfo.cs" /> <Compile Include="FindSymbols\SyntaxTree\AbstractSyntaxTreeInfo.cs" />
...@@ -978,4 +987,4 @@ ...@@ -978,4 +987,4 @@
<ImportGroup Label="Targets"> <ImportGroup Label="Targets">
<Import Project="..\..\..\..\build\Targets\VSL.Imports.targets" /> <Import Project="..\..\..\..\build\Targets\VSL.Imports.targets" />
</ImportGroup> </ImportGroup>
</Project> </Project>
\ No newline at end of file
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册