public async Task <AnalysisData> GetProjectAnalysisDataAsync( DiagnosticAnalyzer provider, ProviderId providerId, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver) { try { var project = analyzerDriver.Project; var cancellationToken = analyzerDriver.CancellationToken; var state = AnalyzersAndState.GetOrCreateDiagnosticState(StateType.Project, providerId, provider, project.Id, project.Language); var existingData = await state.TryGetExistingDataAsync(project, cancellationToken).ConfigureAwait(false); if (CheckSemanticVersions(project, existingData, versions)) { return(existingData); } // TODO: remove ForceAnalyzeAllDocuments at some point var diagnosticData = await GetProjectDiagnosticsAsync(providerId, provider, analyzerDriver, _owner.ForceAnalyzeAllDocuments).ConfigureAwait(false); return(new AnalysisData(VersionStamp.Default, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty())); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task <AnalysisData> GetDocumentBodyAnalysisDataAsync( StateSet stateSet, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver, SyntaxNode root, SyntaxNode member, int memberId, bool supportsSemanticInSpan, MemberRangeMap.MemberRanges ranges) { try { var document = analyzerDriver.Document; var cancellationToken = analyzerDriver.CancellationToken; var state = stateSet.GetState(StateType.Document); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); ImmutableArray <DiagnosticData> diagnosticData; if (supportsSemanticInSpan && CanUseRange(memberId, ranges.Ranges) && CanUseDocumentState(existingData, ranges.TextVersion, versions.DataVersion)) { var memberDxData = await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); diagnosticData = _owner.UpdateDocumentDiagnostics(existingData, ranges.Ranges, memberDxData.AsImmutableOrEmpty(), root.SyntaxTree, member, memberId); ValidateMemberDiagnostics(stateSet.Analyzer, document, root, diagnosticData); } else { // if we can't re-use existing document state, only option we have is updating whole document state here. var dx = await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); diagnosticData = dx.AsImmutableOrEmpty(); } return(new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData)); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task<AnalysisData> GetDocumentBodyAnalysisDataAsync( StateSet stateSet, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver, SyntaxNode root, SyntaxNode member, int memberId, bool supportsSemanticInSpan, MemberRangeMap.MemberRanges ranges) { try { var document = analyzerDriver.Document; var cancellationToken = analyzerDriver.CancellationToken; var state = stateSet.GetState(StateType.Document); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); ImmutableArray<DiagnosticData> diagnosticData; if (supportsSemanticInSpan && CanUseRange(memberId, ranges.Ranges) && CanUseDocumentState(existingData, ranges.TextVersion, versions.DataVersion)) { var memberDxData = await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); diagnosticData = _owner.UpdateDocumentDiagnostics(existingData, ranges.Ranges, memberDxData.AsImmutableOrEmpty(), root.SyntaxTree, member, memberId); ValidateMemberDiagnostics(stateSet.Analyzer, document, root, diagnosticData); } else { // if we can't re-use existing document state, only option we have is updating whole document state here. var dx = await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); diagnosticData = dx.AsImmutableOrEmpty(); } return new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeDocumentAsync(Document document, SyntaxNode bodyOpt, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(document.Project.Solution.Workspace, document.Project.Language, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await document.Project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.Project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion, projectVersion); if (bodyOpt == null) { await AnalyzeDocumentAsync(document, versions, diagnosticIds, skipClosedFileChecks, cancellationToken).ConfigureAwait(false); } else { // only open file can go this route await AnalyzeBodyDocumentAsync(document, bodyOpt, versions, cancellationToken).ConfigureAwait(false); } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public void SetValue_Valid() { var sut = new VersionArgument(NAME, DESCRIPTION); sut.SetValue(VERSION); Assert.AreEqual(Version.Parse(VERSION), sut.Value); }
public async Task <AnalysisData> GetDocumentAnalysisDataAsync( DiagnosticAnalyzer provider, ProviderId providerId, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDrvier) { try { var document = analyzerDrvier.Document; var cancellationToken = analyzerDrvier.CancellationToken; var state = AnalyzersAndState.GetOrCreateDiagnosticState(StateType.Document, providerId, provider, document.Project.Id, document.Project.Language); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); if (CheckSemanticVersions(document, existingData, versions)) { return(existingData); } var diagnosticData = await GetSemanticDiagnosticsAsync(providerId, provider, analyzerDrvier).ConfigureAwait(false); return(new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty())); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeSyntaxAsync(Document document, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(document.Project.Solution.Workspace, document.Project.Language, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.GetSyntaxVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, _diagnosticLogAggregator, cancellationToken); var options = document.Project.CompilationOptions; var openedDocument = document.IsOpen(); foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(document.Project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; if (IsAnalyzerSuppressed(provider, options, userDiagnosticDriver)) { await HandleSuppressedAnalyzerAsync(document, StateType.Syntax, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Syntax, provider, userDiagnosticDriver, diagnosticIds) && (skipClosedFileChecks || ShouldRunProviderForClosedFile(openedDocument, provider))) { var data = await _executor.GetSyntaxAnalysisDataAsync(provider, providerId, versions, userDiagnosticDriver).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Syntax, document.Id, providerId, new SolutionArgument(document), data.Items); continue; } var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Syntax, providerId, provider, document.Project.Id, document.Project.Language); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDiagnosticsUpdatedIfNeeded(StateType.Syntax, document, providerId, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeProjectAsync(Project project, CancellationToken cancellationToken) { try { // Compilation actions can report diagnostics on open files, so "documentOpened = true" if (!CheckOption(project.Solution.Workspace, project.Language, documentOpened: true)) { return; } var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, cancellationToken); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(project)) { // Compilation actions can report diagnostics on open files, so we skipClosedFileChecks. if (SkipRunningAnalyzer(project.CompilationOptions, analyzerDriver, openedDocument: true, skipClosedFileChecks: true, stateSet: stateSet)) { await ClearExistingDiagnostics(project, stateSet, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Project, diagnosticIds: null)) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdated(project, stateSet, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, data.OldItems, data.Items); } } _solutionCrawlerAnalysisState.OnProjectAnalyzed(project); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeSyntaxAsync(Document document, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(document.Project.Solution.Workspace, document.Project.Language, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.GetSyntaxVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, this, cancellationToken); var openedDocument = document.IsOpen(); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(document.Project)) { if (SkipRunningAnalyzer(document.Project.CompilationOptions, userDiagnosticDriver, openedDocument, skipClosedFileChecks, stateSet)) { await ClearExistingDiagnostics(document, stateSet, StateType.Syntax, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Syntax, diagnosticIds)) { var data = await _executor.GetSyntaxAnalysisDataAsync(userDiagnosticDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Syntax, document.Id, stateSet, new SolutionArgument(document), data.Items); continue; } var state = stateSet.GetState(StateType.Syntax); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Syntax, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public void SetValue_Invalid() { try { var sut = new VersionArgument(NAME, DESCRIPTION); sut.SetValue("bogus"); } catch (Exception ex) { Assert.AreEqual("Argument 'name' is invalid", ex.Message); throw; } }
public void Constructor_Required() { var sut = new VersionArgument(NAME, DESCRIPTION, true); Assert.AreEqual(sut.Name, NAME); Assert.AreEqual(sut.Description, DESCRIPTION); Assert.IsNull(sut.DefaultValue); Assert.AreEqual(" /name description", sut.GetUsage()); Assert.IsTrue(sut.IsRequired); Assert.AreEqual("/name <Version>", sut.Syntax); Assert.AreEqual("Version", sut.Type); Assert.IsNull(sut.Value); }
public void Constructor_With_Default() { var sut = new VersionArgument(NAME, DESCRIPTION, true, Version.Parse(VERSION)); Assert.AreEqual(sut.Name, NAME); Assert.AreEqual(sut.Description, DESCRIPTION); Assert.AreEqual(Version.Parse(VERSION), sut.DefaultValue); Assert.AreEqual(" /name description (default: 1.2.3.4)", sut.GetUsage()); Assert.IsFalse(sut.IsRequired); Assert.AreEqual("[/name <Version>]", sut.Syntax); Assert.AreEqual("Version", sut.Type); Assert.AreEqual(Version.Parse(VERSION), sut.Value); }
private async Task AnalyzeProjectAsync(Project project, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(project.Solution.Workspace, project.Language, documentOpened: project.Documents.Any(d => d.IsOpen()))) { return; } var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var userDiagnosticDriver = new DiagnosticAnalyzerDriver(project, _diagnosticLogAggregator, cancellationToken); var options = project.CompilationOptions; var versions = new VersionArgument(VersionStamp.Default, semanticVersion, projectVersion); foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; if (IsAnalyzerSuppressed(provider, options, userDiagnosticDriver)) { await HandleSuppressedAnalyzerAsync(project, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Project, provider, userDiagnosticDriver, diagnosticIds) && (skipClosedFileChecks || ShouldRunProviderForClosedFile(openedDocument: false, provider: provider))) { var data = await _executor.GetProjectAnalysisDataAsync(provider, providerId, versions, userDiagnosticDriver).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Project, project.Id, providerId, new SolutionArgument(project), data.Items); continue; } var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Project, providerId, provider, project.Id, project.Language); await state.PersistAsync(project, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDiagnosticsUpdatedIfNeeded(project, providerId, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeProjectAsync(Project project, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(project.Solution.Workspace, project.Language, documentOpened: project.Documents.Any(d => d.IsOpen()))) { return; } var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, cancellationToken); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); foreach (var stateSet in _stateManger.GetOrUpdateStateSets(project)) { if (analyzerDriver.IsAnalyzerSuppressed(stateSet.Analyzer)) { await HandleSuppressedAnalyzerAsync(project, stateSet, cancellationToken).ConfigureAwait(false); } else if (ShouldRunAnalyzerForStateType(analyzerDriver, stateSet.Analyzer, StateType.Project, diagnosticIds) && (skipClosedFileChecks || ShouldRunAnalyzerForClosedFile(openedDocument: false, analyzer: stateSet.Analyzer))) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdated(project, stateSet.Analyzer, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet.Analyzer, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeDocumentAsync(Document document, VersionArgument versions, ImmutableHashSet <string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, this, ConcurrentAnalysis, ReportSuppressedDiagnostics, cancellationToken); bool openedDocument = document.IsOpen(); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(document.Project)) { if (SkipRunningAnalyzer(document.Project.CompilationOptions, userDiagnosticDriver, openedDocument, skipClosedFileChecks, stateSet)) { await ClearExistingDiagnostics(document, stateSet, StateType.Document, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Document, diagnosticIds)) { var data = await _executor.GetDocumentAnalysisDataAsync(userDiagnosticDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsCreatedFromCacheIfNeeded(StateType.Document, document, stateSet, data.Items); continue; } if (openedDocument) { _memberRangeMap.Touch(stateSet.Analyzer, document, versions.TextVersion); } var state = stateSet.GetState(StateType.Document); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Document, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task<AnalysisData> GetDocumentAnalysisDataAsync(DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, VersionArgument versions) { try { var document = analyzerDriver.Document; var cancellationToken = analyzerDriver.CancellationToken; var state = stateSet.GetState(StateType.Document); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); if (CheckSemanticVersions(document, existingData, versions)) { return existingData; } var diagnosticData = await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); return new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty()); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task<AnalysisData> GetSyntaxAnalysisDataAsync( DiagnosticAnalyzer provider, ProviderId providerId, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver) { try { var document = analyzerDriver.Document; var cancellationToken = analyzerDriver.CancellationToken; var state = AnalyzersAndState.GetOrCreateDiagnosticState(StateType.Syntax, providerId, provider, document.Project.Id, document.Project.Language); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); if (CheckSyntaxVersions(document, existingData, versions)) { return existingData; } var diagnosticData = await GetSyntaxDiagnosticsAsync(providerId, provider, analyzerDriver).ConfigureAwait(false); return new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty()); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected abstract Task<AnalysisData> GetDiagnosticAnalysisDataAsync(Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions);
public async Task <AnalysisData> GetProjectAnalysisDataAsync(DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, VersionArgument versions) { try { var project = analyzerDriver.Project; var cancellationToken = analyzerDriver.CancellationToken; var state = stateSet.GetState(StateType.Project); var existingData = await GetExistingProjectAnalysisDataAsync(project, state, cancellationToken).ConfigureAwait(false); if (CheckSemanticVersions(project, existingData, versions)) { return(existingData); } var diagnosticData = await GetProjectDiagnosticsAsync(analyzerDriver, stateSet.Analyzer, _owner.ForceAnalyzeAllDocuments).ConfigureAwait(false); return(new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty())); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected abstract Task <AnalysisData> GetSpecificDiagnosticsAsync(Solution solution, DiagnosticAnalyzer provider, ProviderId providerId, StateType stateType, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver);
public void VersionArgumentNotImplementedDefaultValue() { var version = new VersionArgument(); var val = version.DefaultValue; }
private async Task AnalyzeProjectAsync(Project project, CancellationToken cancellationToken) { try { if (!CheckOption(project.Solution.Workspace, project.Language, documentOpened: false)) { return; } var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, cancellationToken); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(project)) { if (SkipRunningAnalyzer(project.CompilationOptions, analyzerDriver, openedDocument: false, skipClosedFileChecks: false, stateSet: stateSet)) { await ClearExistingDiagnostics(project, stateSet, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Project, diagnosticIds: null)) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdated(project, stateSet, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, data.OldItems, data.Items); } } _solutionCrawlerAnalysisState.OnProjectAnalyzed(project); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private static bool CheckSemanticVersions(Project project, AnalysisData existingData, VersionArgument versions) { if (existingData == null) { return false; } return VersionStamp.CanReusePersistedVersion(versions.TextVersion, existingData.TextVersion) && project.CanReusePersistedDependentSemanticVersion(versions.ProjectVersion, versions.DataVersion, existingData.DataVersion); }
private async Task AnalyzeBodyDocumentAsync(Document document, SyntaxNode member, VersionArgument versions, CancellationToken cancellationToken) { try { // syntax facts service must exist, otherwise, this method won't have called. var syntaxFacts = document.Project.LanguageServices.GetService <ISyntaxFactsService>(); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var memberId = syntaxFacts.GetMethodLevelMemberId(root, member); var spanBasedDriver = new DiagnosticAnalyzerDriver(document, member.FullSpan, root, _diagnosticLogAggregator, cancellationToken); var documentBasedDriver = new DiagnosticAnalyzerDriver(document, root.FullSpan, root, _diagnosticLogAggregator, cancellationToken); var options = document.Project.CompilationOptions; foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(document.Project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; bool supportsSemanticInSpan; if (IsAnalyzerSuppressed(provider, options, spanBasedDriver)) { await HandleSuppressedAnalyzerAsync(document, StateType.Document, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Document, provider, spanBasedDriver, out supportsSemanticInSpan)) { var userDiagnosticDriver = supportsSemanticInSpan ? spanBasedDriver : documentBasedDriver; var ranges = _memberRangeMap.GetSavedMemberRange(providerId, document); var data = await _executor.GetDocumentBodyAnalysisDataAsync( provider, providerId, versions, userDiagnosticDriver, root, member, memberId, supportsSemanticInSpan, ranges).ConfigureAwait(false); _memberRangeMap.UpdateMemberRange(providerId, document, versions.TextVersion, memberId, member.FullSpan, ranges); var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Document, providerId, provider, document.Project.Id, document.Project.Language); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, providerId, new SolutionArgument(document), data.Items); continue; } RaiseDiagnosticsUpdatedIfNeeded(StateType.Document, document, providerId, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeBodyDocumentAsync(Document document, SyntaxNode member, VersionArgument versions, CancellationToken cancellationToken) { try { // syntax facts service must exist, otherwise, this method won't have called. var syntaxFacts = document.Project.LanguageServices.GetService<ISyntaxFactsService>(); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var memberId = syntaxFacts.GetMethodLevelMemberId(root, member); var spanBasedDriver = new DiagnosticAnalyzerDriver(document, member.FullSpan, root, this, cancellationToken); var documentBasedDriver = new DiagnosticAnalyzerDriver(document, root.FullSpan, root, this, cancellationToken); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(document.Project)) { if (Owner.IsAnalyzerSuppressed(stateSet.Analyzer, document.Project)) { await ClearExistingDiagnostics(document, stateSet, StateType.Document, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Document)) { var supportsSemanticInSpan = stateSet.Analyzer.SupportsSpanBasedSemanticDiagnosticAnalysis(); var userDiagnosticDriver = supportsSemanticInSpan ? spanBasedDriver : documentBasedDriver; var ranges = _memberRangeMap.GetSavedMemberRange(stateSet.Analyzer, document); var data = await _executor.GetDocumentBodyAnalysisDataAsync( stateSet, versions, userDiagnosticDriver, root, member, memberId, supportsSemanticInSpan, ranges).ConfigureAwait(false); _memberRangeMap.UpdateMemberRange(stateSet.Analyzer, document, versions.TextVersion, memberId, member.FullSpan, ranges); var state = stateSet.GetState(StateType.Document); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, stateSet, new SolutionArgument(document), data.Items); continue; } RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Document, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeSyntaxAsync(Document document, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(document.Project.Solution.Workspace, document.Project.Language, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.GetSyntaxVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, this, cancellationToken); var openedDocument = document.IsOpen(); foreach (var stateSet in _stateManger.GetOrUpdateStateSets(document.Project)) { if (userDiagnosticDriver.IsAnalyzerSuppressed(stateSet.Analyzer)) { await HandleSuppressedAnalyzerAsync(document, stateSet, StateType.Syntax, cancellationToken).ConfigureAwait(false); } else if (await ShouldRunAnalyzerForStateTypeAsync(userDiagnosticDriver, stateSet.Analyzer, StateType.Syntax, diagnosticIds).ConfigureAwait(false) && (skipClosedFileChecks || ShouldRunAnalyzerForClosedFile(openedDocument, stateSet.Analyzer))) { var data = await _executor.GetSyntaxAnalysisDataAsync(userDiagnosticDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Syntax, document.Id, stateSet, new SolutionArgument(document), data.Items); continue; } var state = stateSet.GetState(StateType.Syntax); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Syntax, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected override async Task<AnalysisData> GetDiagnosticAnalysisDataAsync( Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions) { // we don't care about result switch (stateType) { case StateType.Syntax: await GetSyntaxDiagnosticsAsync(analyzerDriver, _analyzer).ConfigureAwait(false); break; case StateType.Document: await GetSemanticDiagnosticsAsync(analyzerDriver, _analyzer).ConfigureAwait(false); break; case StateType.Project: default: return Contract.FailWithReturn<AnalysisData>("Can't reach here"); } return AnalysisData.Empty; }
public void VersionArgumentGetValue() { var version = new VersionArgument(); Assert.IsNotNull(version.GetValue(string.Empty)); }
public void VersionArgumentValidOption() { var version = new VersionArgument(); version.ValidArgument(string.Empty); }
public void VersionArgumentNotImplementedPropertyMap() { var version = new VersionArgument(); var val = version.PropertyMap; }
private async Task AnalyzeProjectAsync(Project project, CancellationToken cancellationToken) { try { if (!CheckOptions(project, forceAnalysis: false)) { return; } // PERF: Ensure that we explicitly ignore the skipped analyzers while creating the analyzer driver, otherwise we might end up running hidden analyzers on closed files. var stateSets = _stateManager.GetOrUpdateStateSets(project).ToImmutableArray(); var skipAnalyzersMap = new Dictionary<DiagnosticAnalyzer, bool>(stateSets.Length); var shouldRunAnalyzersMap = new Dictionary<DiagnosticAnalyzer, bool>(stateSets.Length); var analyzersBuilder = ImmutableArray.CreateBuilder<DiagnosticAnalyzer>(stateSets.Length); foreach (var stateSet in stateSets) { var skip = await SkipRunningAnalyzerAsync(project, stateSet.Analyzer, openedDocument: false, skipClosedFileCheck: true, cancellationToken: cancellationToken).ConfigureAwait(false); skipAnalyzersMap.Add(stateSet.Analyzer, skip); var shouldRun = !skip && ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Project, diagnosticIds: null); shouldRunAnalyzersMap.Add(stateSet.Analyzer, shouldRun); if (shouldRun) { analyzersBuilder.Add(stateSet.Analyzer); } } var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, analyzersBuilder.ToImmutable(), ConcurrentAnalysis, ReportSuppressedDiagnostics, cancellationToken); var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); foreach (var stateSet in stateSets) { // Compilation actions can report diagnostics on open files, so we skipClosedFileChecks. if (skipAnalyzersMap[stateSet.Analyzer]) { await ClearExistingDiagnostics(project, stateSet, cancellationToken).ConfigureAwait(false); continue; } if (shouldRunAnalyzersMap[stateSet.Analyzer]) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, ImmutableArray<DiagnosticData>.Empty, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public void VersionUsageText() { var verArgument = new VersionArgument(); Assert.IsNotNull(verArgument.UsageText); }
private async Task AnalyzeDocumentAsync(Document document, SyntaxNode bodyOpt, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(document.Project.Solution.Workspace, document.Project.Language, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await document.Project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.Project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion, projectVersion); if (bodyOpt == null) { await AnalyzeDocumentAsync(document, versions, diagnosticIds, skipClosedFileChecks, cancellationToken).ConfigureAwait(false); } else { // only open file can go this route await AnalyzeBodyDocumentAsync(document, bodyOpt, versions, cancellationToken).ConfigureAwait(false); } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task<AnalysisData> GetProjectAnalysisDataAsync( DiagnosticAnalyzer provider, ProviderId providerId, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver) { try { var project = analyzerDriver.Project; var cancellationToken = analyzerDriver.CancellationToken; var state = AnalyzersAndState.GetOrCreateDiagnosticState(StateType.Project, providerId, provider, project.Id, project.Language); var existingData = await state.TryGetExistingDataAsync(project, cancellationToken).ConfigureAwait(false); if (CheckSemanticVersions(project, existingData, versions)) { return existingData; } // TODO: remove ForceAnalyzeAllDocuments at some point var diagnosticData = await GetProjectDiagnosticsAsync(providerId, provider, analyzerDriver, _owner.ForceAnalyzeAllDocuments).ConfigureAwait(false); return new AnalysisData(VersionStamp.Default, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty()); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeDocumentAsync(Document document, VersionArgument versions, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, this, cancellationToken); bool openedDocument = document.IsOpen(); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(document.Project)) { if (SkipRunningAnalyzer(document.Project.CompilationOptions, userDiagnosticDriver, openedDocument, skipClosedFileChecks, stateSet)) { await ClearExistingDiagnostics(document, stateSet, StateType.Document, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Document, diagnosticIds)) { var data = await _executor.GetDocumentAnalysisDataAsync(userDiagnosticDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, stateSet, new SolutionArgument(document), data.Items); continue; } if (openedDocument) { _memberRangeMap.Touch(stateSet.Analyzer, document, versions.TextVersion); } var state = stateSet.GetState(StateType.Document); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Document, document, stateSet, data.OldItems, data.Items); } } _solutionCrawlerAnalysisState.OnDocumentAnalyzed(document); } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private static bool CheckSyntaxVersions(Document document, AnalysisData existingData, VersionArgument versions) { if (existingData == null) { return(false); } return(document.CanReusePersistedTextVersion(versions.TextVersion, existingData.TextVersion) && document.CanReusePersistedSyntaxTreeVersion(versions.DataVersion, existingData.DataVersion)); }
private static bool CheckSyntaxVersions(Document document, AnalysisData existingData, VersionArgument versions) { if (existingData == null) { return false; } return document.CanReusePersistedTextVersion(versions.TextVersion, existingData.TextVersion) && document.CanReusePersistedSyntaxTreeVersion(versions.DataVersion, existingData.DataVersion); }
protected abstract Task <AnalysisData> GetDiagnosticAnalysisDataAsync(Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions);
private async Task AnalyzeProjectAsync(Project project, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(project.Solution.Workspace, project.Language, documentOpened: project.Documents.Any(d => d.IsOpen()))) { return; } var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, cancellationToken); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); foreach (var stateSet in _stateManger.GetOrUpdateStateSets(project)) { if (analyzerDriver.IsAnalyzerSuppressed(stateSet.Analyzer)) { await HandleSuppressedAnalyzerAsync(project, stateSet, cancellationToken).ConfigureAwait(false); } else if (await ShouldRunAnalyzerForStateTypeAsync(analyzerDriver, stateSet.Analyzer, StateType.Project, diagnosticIds).ConfigureAwait(false) && (skipClosedFileChecks || ShouldRunAnalyzerForClosedFile(openedDocument: false, analyzer: stateSet.Analyzer))) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdated(project, stateSet, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected override Task <AnalysisData> GetDiagnosticAnalysisDataAsync( Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions) { switch (stateType) { case StateType.Syntax: return(this.AnalyzerExecutor.GetSyntaxAnalysisDataAsync(analyzerDriver, stateSet, versions)); case StateType.Document: return(this.AnalyzerExecutor.GetDocumentAnalysisDataAsync(analyzerDriver, stateSet, versions)); case StateType.Project: return(this.AnalyzerExecutor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions)); default: return(Contract.FailWithReturn <Task <AnalysisData> >("Can't reach here")); } }
private async Task AnalyzeBodyDocumentAsync(Document document, SyntaxNode member, VersionArgument versions, CancellationToken cancellationToken) { try { // syntax facts service must exist, otherwise, this method won't have called. var syntaxFacts = document.Project.LanguageServices.GetService<ISyntaxFactsService>(); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var memberId = syntaxFacts.GetMethodLevelMemberId(root, member); var spanBasedDriver = new DiagnosticAnalyzerDriver(document, member.FullSpan, root, _diagnosticLogAggregator, cancellationToken); var documentBasedDriver = new DiagnosticAnalyzerDriver(document, root.FullSpan, root, _diagnosticLogAggregator, cancellationToken); var options = document.Project.CompilationOptions; foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(document.Project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; bool supportsSemanticInSpan; if (IsAnalyzerSuppressed(provider, options, spanBasedDriver)) { await HandleSuppressedAnalyzerAsync(document, StateType.Document, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Document, provider, spanBasedDriver, out supportsSemanticInSpan)) { var userDiagnosticDriver = supportsSemanticInSpan ? spanBasedDriver : documentBasedDriver; var ranges = _memberRangeMap.GetSavedMemberRange(providerId, document); var data = await _executor.GetDocumentBodyAnalysisDataAsync( provider, providerId, versions, userDiagnosticDriver, root, member, memberId, supportsSemanticInSpan, ranges).ConfigureAwait(false); _memberRangeMap.UpdateMemberRange(providerId, document, versions.TextVersion, memberId, member.FullSpan, ranges); var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Document, providerId, provider, document.Project.Id, document.Project.Language); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, providerId, new SolutionArgument(document), data.Items); continue; } RaiseDiagnosticsUpdatedIfNeeded(StateType.Document, document, providerId, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public void VersionArgument_SupportDefault() { var verArgument = new VersionArgument(); Assert.IsFalse(verArgument.SupportsDefaultValue); }
private async Task AnalyzeBodyDocumentAsync(Document document, SyntaxNode member, VersionArgument versions, CancellationToken cancellationToken) { try { // syntax facts service must exist, otherwise, this method won't have called. var syntaxFacts = document.Project.LanguageServices.GetService <ISyntaxFactsService>(); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var memberId = syntaxFacts.GetMethodLevelMemberId(root, member); var spanBasedDriver = new DiagnosticAnalyzerDriver(document, member.FullSpan, root, this, cancellationToken); var documentBasedDriver = new DiagnosticAnalyzerDriver(document, root.FullSpan, root, this, cancellationToken); foreach (var stateSet in _stateManager.GetOrUpdateStateSets(document.Project)) { if (Owner.IsAnalyzerSuppressed(stateSet.Analyzer, document.Project)) { await ClearExistingDiagnostics(document, stateSet, StateType.Document, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Document)) { var supportsSemanticInSpan = stateSet.Analyzer.SupportsSpanBasedSemanticDiagnosticAnalysis(); var userDiagnosticDriver = supportsSemanticInSpan ? spanBasedDriver : documentBasedDriver; var ranges = _memberRangeMap.GetSavedMemberRange(stateSet.Analyzer, document); var data = await _executor.GetDocumentBodyAnalysisDataAsync( stateSet, versions, userDiagnosticDriver, root, member, memberId, supportsSemanticInSpan, ranges).ConfigureAwait(false); _memberRangeMap.UpdateMemberRange(stateSet.Analyzer, document, versions.TextVersion, memberId, member.FullSpan, ranges); var state = stateSet.GetState(StateType.Document); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, stateSet, new SolutionArgument(document), data.Items); continue; } RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Document, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeDocumentAsync(Document document, VersionArgument versions, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var userDiagnosticDriver = new DiagnosticAnalyzerDriver(document, fullSpan, root, _diagnosticLogAggregator, cancellationToken); bool openedDocument = document.IsOpen(); var options = document.Project.CompilationOptions; foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(document.Project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; if (IsAnalyzerSuppressed(provider, options, userDiagnosticDriver)) { await HandleSuppressedAnalyzerAsync(document, StateType.Document, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Document, provider, userDiagnosticDriver, diagnosticIds) && (skipClosedFileChecks || ShouldRunProviderForClosedFile(openedDocument, provider))) { var data = await _executor.GetDocumentAnalysisDataAsync(provider, providerId, versions, userDiagnosticDriver).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Document, document.Id, providerId, new SolutionArgument(document), data.Items); continue; } if (openedDocument) { _memberRangeMap.Touch(providerId, document, versions.TextVersion); } var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Document, providerId, provider, document.Project.Id, document.Project.Language); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDiagnosticsUpdatedIfNeeded(StateType.Document, document, providerId, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private static bool CheckSemanticVersions(Project project, AnalysisData existingData, VersionArgument versions) { if (existingData == null) { return(false); } return(VersionStamp.CanReusePersistedVersion(versions.TextVersion, existingData.TextVersion) && project.CanReusePersistedDependentSemanticVersion(versions.ProjectVersion, versions.DataVersion, existingData.DataVersion)); }
private async Task AnalyzeProjectAsync(Project project, ImmutableHashSet<string> diagnosticIds, bool skipClosedFileChecks, CancellationToken cancellationToken) { try { if (!skipClosedFileChecks && !CheckOption(project.Solution.Workspace, project.Language, documentOpened: project.Documents.Any(d => d.IsOpen()))) { return; } var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var userDiagnosticDriver = new DiagnosticAnalyzerDriver(project, _diagnosticLogAggregator, cancellationToken); var options = project.CompilationOptions; var versions = new VersionArgument(VersionStamp.Default, semanticVersion, projectVersion); foreach (var providerAndId in await _analyzersAndState.GetAllProviderAndIdsAsync(project, cancellationToken).ConfigureAwait(false)) { var provider = providerAndId.Key; var providerId = providerAndId.Value; if (IsAnalyzerSuppressed(provider, options, userDiagnosticDriver)) { await HandleSuppressedAnalyzerAsync(project, providerId, provider, cancellationToken).ConfigureAwait(false); } else if (ShouldRunProviderForStateType(StateType.Project, provider, userDiagnosticDriver, diagnosticIds) && (skipClosedFileChecks || ShouldRunProviderForClosedFile(openedDocument: false, provider: provider))) { var data = await _executor.GetProjectAnalysisDataAsync(provider, providerId, versions, userDiagnosticDriver).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsUpdated(StateType.Project, project.Id, providerId, new SolutionArgument(project), data.Items); continue; } var state = _analyzersAndState.GetOrCreateDiagnosticState(StateType.Project, providerId, provider, project.Id, project.Language); await state.PersistAsync(project, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDiagnosticsUpdatedIfNeeded(project, providerId, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected override async Task <AnalysisData> GetDiagnosticAnalysisDataAsync( Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions) { // we don't care about result switch (stateType) { case StateType.Syntax: await GetSyntaxDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); break; case StateType.Document: await GetSemanticDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); break; case StateType.Project: default: return(Contract.FailWithReturn <AnalysisData>("Can't reach here")); } return(AnalysisData.Empty); }
private async Task AnalyzeSyntaxAsync(Document document, ImmutableHashSet<string> diagnosticIds, CancellationToken cancellationToken) { try { if (!CheckOptions(document.Project, document.IsOpen())) { return; } var textVersion = await document.GetTextVersionAsync(cancellationToken).ConfigureAwait(false); var dataVersion = await document.GetSyntaxVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(textVersion, dataVersion); var root = await document.GetSyntaxRootAsync(cancellationToken).ConfigureAwait(false); var fullSpan = root == null ? null : (TextSpan?)root.FullSpan; var openedDocument = document.IsOpen(); var stateSets = _stateManager.GetOrUpdateStateSets(document.Project); var analyzers = stateSets.Select(s => s.Analyzer); var userDiagnosticDriver = new DiagnosticAnalyzerDriver( document, fullSpan, root, this, analyzers, ConcurrentAnalysis, ReportSuppressedDiagnostics, cancellationToken); foreach (var stateSet in stateSets) { if (await SkipRunningAnalyzerAsync(document.Project, stateSet.Analyzer, openedDocument, skipClosedFileCheck: false, cancellationToken: cancellationToken).ConfigureAwait(false)) { await ClearExistingDiagnostics(document, stateSet, StateType.Syntax, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Syntax, diagnosticIds)) { var data = await _executor.GetSyntaxAnalysisDataAsync(userDiagnosticDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseDiagnosticsCreatedFromCacheIfNeeded(StateType.Syntax, document, stateSet, data.Items); continue; } var state = stateSet.GetState(StateType.Syntax); await state.PersistAsync(document, data.ToPersistData(), cancellationToken).ConfigureAwait(false); RaiseDocumentDiagnosticsUpdatedIfNeeded(StateType.Syntax, document, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
public async Task <AnalysisData> GetSyntaxAnalysisDataAsync(DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, VersionArgument versions) { try { var document = analyzerDriver.Document; var cancellationToken = analyzerDriver.CancellationToken; var state = stateSet.GetState(StateType.Syntax); var existingData = await state.TryGetExistingDataAsync(document, cancellationToken).ConfigureAwait(false); if (CheckSyntaxVersions(document, existingData, versions)) { return(existingData); } var diagnosticData = await GetSyntaxDiagnosticsAsync(analyzerDriver, stateSet.Analyzer).ConfigureAwait(false); return(new AnalysisData(versions.TextVersion, versions.DataVersion, GetExistingItems(existingData), diagnosticData.AsImmutableOrEmpty())); } catch (Exception e) when(FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
private async Task AnalyzeProjectAsync(Project project, CancellationToken cancellationToken) { try { if (!CheckOptions(project, forceAnalysis: false)) { return; } var projectTextVersion = await project.GetLatestDocumentVersionAsync(cancellationToken).ConfigureAwait(false); var semanticVersion = await project.GetDependentSemanticVersionAsync(cancellationToken).ConfigureAwait(false); var projectVersion = await project.GetDependentVersionAsync(cancellationToken).ConfigureAwait(false); var versions = new VersionArgument(projectTextVersion, semanticVersion, projectVersion); var stateSets = _stateManager.GetOrUpdateStateSets(project); var analyzers = stateSets.Select(s => s.Analyzer); var analyzerDriver = new DiagnosticAnalyzerDriver(project, this, analyzers, ConcurrentAnalysis, ReportSuppressedDiagnostics, cancellationToken); foreach (var stateSet in stateSets) { // Compilation actions can report diagnostics on open files, so we skipClosedFileChecks. if (await SkipRunningAnalyzerAsync(project, stateSet.Analyzer, openedDocument: false, skipClosedFileCheck: true, cancellationToken: cancellationToken).ConfigureAwait(false)) { await ClearExistingDiagnostics(project, stateSet, cancellationToken).ConfigureAwait(false); continue; } if (ShouldRunAnalyzerForStateType(stateSet.Analyzer, StateType.Project, diagnosticIds: null)) { var data = await _executor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions).ConfigureAwait(false); if (data.FromCache) { RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, ImmutableArray<DiagnosticData>.Empty, data.Items); continue; } var state = stateSet.GetState(StateType.Project); await PersistProjectData(project, state, data).ConfigureAwait(false); RaiseProjectDiagnosticsUpdatedIfNeeded(project, stateSet, data.OldItems, data.Items); } } } catch (Exception e) when (FatalError.ReportUnlessCanceled(e)) { throw ExceptionUtilities.Unreachable; } }
protected override Task<AnalysisData> GetDiagnosticAnalysisDataAsync( Solution solution, DiagnosticAnalyzerDriver analyzerDriver, StateSet stateSet, StateType stateType, VersionArgument versions) { switch (stateType) { case StateType.Syntax: return this.AnalyzerExecutor.GetSyntaxAnalysisDataAsync(analyzerDriver, stateSet, versions); case StateType.Document: return this.AnalyzerExecutor.GetDocumentAnalysisDataAsync(analyzerDriver, stateSet, versions); case StateType.Project: return this.AnalyzerExecutor.GetProjectAnalysisDataAsync(analyzerDriver, stateSet, versions); default: return Contract.FailWithReturn<Task<AnalysisData>>("Can't reach here"); } }
protected abstract Task<AnalysisData> GetSpecificDiagnosticsAsync(Solution solution, DiagnosticAnalyzer provider, ProviderId providerId, StateType stateType, VersionArgument versions, DiagnosticAnalyzerDriver analyzerDriver);