/// <summary> /// Return all cached local diagnostics (syntax, semantic) that belong to given document for the given StateSet (analyzer). /// Also returns empty diagnostics for suppressed analyzer. /// Returns null if the diagnostics need to be computed. /// </summary> private static DocumentAnalysisData?TryGetCachedDocumentAnalysisData( TextDocument document, StateSet stateSet, AnalysisKind kind, VersionStamp version, BackgroundAnalysisScope analysisScope, bool isActiveDocument, bool isOpenDocument, bool isGeneratedRazorDocument, CancellationToken cancellationToken) { Debug.Assert(isActiveDocument || isOpenDocument || isGeneratedRazorDocument); try { var state = stateSet.GetOrCreateActiveFileState(document.Id); var existingData = state.GetAnalysisData(kind); if (existingData.Version == version) { return(existingData); } // Perf optimization: Check whether analyzer is suppressed for project or document and avoid getting diagnostics if suppressed. if (!AnalyzerHelper.IsAnalyzerEnabledForProject(stateSet.Analyzer, document.Project) || !IsAnalyzerEnabledForDocument(stateSet.Analyzer, analysisScope, isActiveDocument, isOpenDocument, isGeneratedRazorDocument)) { return(new DocumentAnalysisData(version, existingData.Items, ImmutableArray <DiagnosticData> .Empty)); } return(null); } catch (Exception e) when(FatalError.ReportAndPropagateUnlessCanceled(e, cancellationToken)) { throw ExceptionUtilities.Unreachable; }
private static bool TryGetItemWithOverriddenAnalysisScope( WorkItem item, ImmutableArray <IIncrementalAnalyzer> allAnalyzers, OptionSet options, BackgroundAnalysisScope analysisScope, IAsynchronousOperationListener listener, [NotNullWhen(returnValue: true)] out WorkItem?newWorkItem ) { var analyzersToExecute = item.GetApplicableAnalyzers(allAnalyzers); var analyzersWithOverriddenAnalysisScope = analyzersToExecute .Where( a => a.GetOverriddenBackgroundAnalysisScope(options, analysisScope) != analysisScope ) .ToImmutableHashSet(); if (!analyzersWithOverriddenAnalysisScope.IsEmpty) { newWorkItem = item.With( analyzersWithOverriddenAnalysisScope, listener.BeginAsyncOperation("WorkItem") ); return(true); } newWorkItem = null; return(false); }
private Options( string analyzerPath, string solutionPath, ImmutableHashSet <string> analyzerIds, bool runConcurrent, bool reportSuppressedDiagnostics, bool showStats, bool useAll, int iterations, bool testDocuments, Func <string, bool> testDocumentMatch, int testDocumentIterations, string logFileName, string profileRoot, bool usePersistentStorage, BackgroundAnalysisScope analysisScope, ImmutableList <string> incrementalAnalyzerNames) { AnalyzerPath = analyzerPath; SolutionPath = solutionPath; AnalyzerNames = analyzerIds; RunConcurrent = runConcurrent; ReportSuppressedDiagnostics = reportSuppressedDiagnostics; ShowStats = showStats; UseAll = useAll; Iterations = iterations; TestDocuments = testDocuments; TestDocumentMatch = testDocumentMatch; TestDocumentIterations = testDocumentIterations; LogFileName = logFileName; ProfileRoot = profileRoot; UsePersistentStorage = usePersistentStorage; AnalysisScope = analysisScope; IncrementalAnalyzerNames = incrementalAnalyzerNames; }
public static BackgroundAnalysisScope GetOverriddenBackgroundAnalysisScope( this IIncrementalAnalyzer incrementalAnalyzer, OptionSet options, BackgroundAnalysisScope defaultBackgroundAnalysisScope ) { // Unit testing analyzer has special semantics for analysis scope. if (incrementalAnalyzer is UnitTestingIncrementalAnalyzer) { return(UnitTestingIncrementalAnalyzer.GetBackgroundAnalysisScope(options)); } return(defaultBackgroundAnalysisScope); }
static bool IsAnalyzerEnabledForDocument( DiagnosticAnalyzer analyzer, BackgroundAnalysisScope analysisScope, bool isActiveDocument, bool isOpenDocument, bool isGeneratedRazorDocument) { Debug.Assert(!isActiveDocument || isOpenDocument || isGeneratedRazorDocument); if (isGeneratedRazorDocument) { // This is a generated Razor document, and they always want all analyzer diagnostics. return(true); } if (analyzer.IsCompilerAnalyzer()) { // Compiler analyzer is treated specially. // It is executed for all documents (open and closed) for 'BackgroundAnalysisScope.FullSolution' // and executed for just open documents for other analysis scopes. return(analysisScope == BackgroundAnalysisScope.FullSolution || isOpenDocument); } else { return(analysisScope switch { // Analyzers are disabled for all documents. BackgroundAnalysisScope.None => false, // Analyzers are enabled for active document. BackgroundAnalysisScope.ActiveFile => isActiveDocument, // Analyzers are enabled for all open documents. BackgroundAnalysisScope.OpenFiles => isOpenDocument, // Analyzers are enabled for all documents. BackgroundAnalysisScope.FullSolution => true, _ => throw ExceptionUtilities.UnexpectedValue(analysisScope) });
static bool IsAnalyzerEnabledForDocument( DiagnosticAnalyzer analyzer, DocumentAnalysisData previousData, BackgroundAnalysisScope analysisScope, CompilerDiagnosticsScope compilerDiagnosticsScope, bool isActiveDocument, bool isVisibleDocument, bool isOpenDocument, bool isGeneratedRazorDocument) { Debug.Assert(!isActiveDocument || isOpenDocument || isGeneratedRazorDocument); if (isGeneratedRazorDocument) { // This is a generated Razor document, and they always want all analyzer diagnostics. return(true); } if (analyzer.IsCompilerAnalyzer()) { return(compilerDiagnosticsScope switch { // Compiler diagnostics are disabled for all documents. CompilerDiagnosticsScope.None => false, // Compiler diagnostics are enabled for visible documents and open documents which had errors/warnings in prior snapshot. CompilerDiagnosticsScope.VisibleFilesAndFilesWithPreviouslyReportedDiagnostics => isVisibleDocument || (isOpenDocument && !previousData.Items.IsEmpty), // Compiler diagnostics are enabled for all open documents. CompilerDiagnosticsScope.OpenFiles => isOpenDocument, // Compiler diagnostics are enabled for all documents. CompilerDiagnosticsScope.FullSolution => true, _ => throw ExceptionUtilities.UnexpectedValue(analysisScope) });
public static CompilerDiagnosticsScope ToEquivalentCompilerDiagnosticsScope(this BackgroundAnalysisScope backgroundAnalysisScope) => backgroundAnalysisScope switch {