提交 d03a0131 编写于 作者: H Heejae Chang

fix the issue where build diagnostics put into semantic slot doesn't de-dup to...

fix the issue where build diagnostics put into semantic slot doesn't de-dup to live on open file in some cases.

issue is build diagnostics can't be distinguished between syntax/semantic/nonlocal and everything is dump to semantic slot.

unfortunately this can't be fixed until build output more data than what it is output right now.
上级 52d22ace
......@@ -164,6 +164,18 @@ public bool OnDocumentReset(IEnumerable<StateSet> stateSets, Document document)
return removed;
}
public async Task<bool> OnDocumentOpenedAsync(IEnumerable<StateSet> stateSets, Document document)
{
// can not be cancelled
var opened = false;
foreach (var stateSet in stateSets)
{
opened |= await stateSet.OnDocumentOpenedAsync(document).ConfigureAwait(false);
}
return opened;
}
public async Task<bool> OnDocumentClosedAsync(IEnumerable<StateSet> stateSets, Document document)
{
// can not be cancelled
......
......@@ -3,6 +3,7 @@
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;
using Roslyn.Utilities;
......@@ -144,6 +145,30 @@ public ProjectState GetProjectState(ProjectId projectId)
return _projectStates.GetOrAdd(projectId, id => new ProjectState(this, id));
}
public async Task<bool> OnDocumentOpenedAsync(Document document)
{
// can not be cancelled
ProjectState projectState;
if (!TryGetProjectState(document.Project.Id, out projectState) ||
projectState.IsEmpty(document.Id))
{
// nothing to do
return false;
}
// always load data
var avoidLoadingData = false;
var result = await projectState.GetAnalysisDataAsync(document, avoidLoadingData, CancellationToken.None).ConfigureAwait(false);
// put project state to active file state
var activeFileState = GetActiveFileState(document.Id);
activeFileState.Save(AnalysisKind.Syntax, new DocumentAnalysisData(result.Version, result.GetResultOrEmpty(result.SyntaxLocals, document.Id)));
activeFileState.Save(AnalysisKind.Semantic, new DocumentAnalysisData(result.Version, result.GetResultOrEmpty(result.SemanticLocals, document.Id)));
return true;
}
public async Task<bool> OnDocumentClosedAsync(Document document)
{
// can not be cancelled
......
......@@ -106,15 +106,15 @@ public override async Task AnalyzeProjectAsync(Project project, bool semanticsCh
}
}
public override Task DocumentOpenAsync(Document document, CancellationToken cancellationToken)
public override async Task DocumentOpenAsync(Document document, CancellationToken cancellationToken)
{
using (Logger.LogBlock(FunctionId.Diagnostics_DocumentOpen, GetOpenLogMessage, document, cancellationToken))
{
var stateSets = _stateManager.GetStateSets(document.Project);
// let other component knows about this event
_compilationManager.OnDocumentOpened();
// here we dont need to raise any event, it will be taken cared by analyze methods.
return SpecializedTasks.EmptyTask;
await _stateManager.OnDocumentOpenedAsync(stateSets, document).ConfigureAwait(false);
}
}
......@@ -244,6 +244,18 @@ private IEnumerable<StateSet> GetStateSetsForFullSolutionAnalysis(IEnumerable<St
return stateSets.Where(s => ShouldRunForFullProject(s.Analyzer, project));
}
private bool ShouldRunForFullProject(DiagnosticAnalyzer analyzer, Project project)
{
// PERF: Don't query descriptors for compiler analyzer, always execute it.
if (HostAnalyzerManager.IsCompilerDiagnosticAnalyzer(project.Language, analyzer))
{
return true;
}
// most of analyzers, number of descriptor is quite small, so this should be cheap.
return Owner.GetDiagnosticDescriptors(analyzer).Any(d => GetEffectiveSeverity(d, project.CompilationOptions) != ReportDiagnostic.Hidden);
}
private void RaiseProjectDiagnosticsIfNeeded(
Project project,
IEnumerable<StateSet> stateSets,
......@@ -391,17 +403,5 @@ private void RaiseProjectDiagnosticsRemoved(StateSet stateSet, ProjectId project
RaiseDiagnosticsRemoved(projectId, nullSolution, stateSet, raiseEvents);
}
private bool ShouldRunForFullProject(DiagnosticAnalyzer analyzer, Project project)
{
// PERF: Don't query descriptors for compiler analyzer, always execute it.
if (HostAnalyzerManager.IsCompilerDiagnosticAnalyzer(project.Language, analyzer))
{
return true;
}
// most of analyzers, number of descriptor is quite small, so this should be cheap.
return Owner.GetDiagnosticDescriptors(analyzer).Any(d => GetEffectiveSeverity(d, project.CompilationOptions) != ReportDiagnostic.Hidden);
}
}
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册