-
Notifications
You must be signed in to change notification settings - Fork 467
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add CA2024: Do not use 'StreamReader.EndOfStream' in async methods (#…
…7390) * Add CA2024: Do not use 'StreamReader.EndOfStream' in async methods This analyzer detects when 'StreamReader.EndOfStream' is used in an async method, which can prevent I/O from being done asynchronously. * Use VerifyAnalyzerAsync instead of VerifyCodeFixAsync * Explicitly specify diagnostic ID in test markup * Check symbols first before checking async context Using the Stream type, or more specifically, the EndOfStream property of the Stream type, should be much rarer than async methods in general, so we check the symbols first. * Remove IsAsyncContext * Remove unnecessary containing type check
- Loading branch information
Showing
22 changed files
with
811 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
81 changes: 81 additions & 0 deletions
81
...etAnalyzers/Core/Microsoft.NetCore.Analyzers/Runtime/DoNotUseEndOfStreamInAsyncMethods.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,81 @@ | ||
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the MIT license. See License.txt in the project root for license information. | ||
|
||
using System.Collections.Immutable; | ||
using System.Linq; | ||
using Analyzer.Utilities; | ||
using Analyzer.Utilities.Extensions; | ||
using Microsoft.CodeAnalysis; | ||
using Microsoft.CodeAnalysis.Diagnostics; | ||
using Microsoft.CodeAnalysis.Operations; | ||
|
||
namespace Microsoft.NetCore.Analyzers.Runtime | ||
{ | ||
using static MicrosoftNetCoreAnalyzersResources; | ||
|
||
/// <summary> | ||
/// CA2024: <inheritdoc cref="DoNotUseEndOfStreamInAsyncMethodsTitle"/> | ||
/// </summary> | ||
[DiagnosticAnalyzer(LanguageNames.CSharp, LanguageNames.VisualBasic)] | ||
public sealed class DoNotUseEndOfStreamInAsyncMethodsAnalyzer : DiagnosticAnalyzer | ||
{ | ||
private const string RuleId = "CA2024"; | ||
private const string EndOfStream = nameof(EndOfStream); | ||
|
||
private static readonly DiagnosticDescriptor Rule = DiagnosticDescriptorHelper.Create( | ||
RuleId, | ||
CreateLocalizableResourceString(nameof(DoNotUseEndOfStreamInAsyncMethodsTitle)), | ||
CreateLocalizableResourceString(nameof(DoNotUseEndOfStreamInAsyncMethodsMessage)), | ||
DiagnosticCategory.Reliability, | ||
RuleLevel.BuildWarning, | ||
CreateLocalizableResourceString(nameof(DoNotUseEndOfStreamInAsyncMethodsDescription)), | ||
isPortedFxCopRule: false, | ||
isDataflowRule: false); | ||
|
||
public sealed override ImmutableArray<DiagnosticDescriptor> SupportedDiagnostics { get; } = ImmutableArray.Create(Rule); | ||
|
||
public sealed override void Initialize(AnalysisContext context) | ||
{ | ||
context.EnableConcurrentExecution(); | ||
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None); | ||
context.RegisterCompilationStartAction(OnCompilationStart); | ||
} | ||
|
||
private void OnCompilationStart(CompilationStartAnalysisContext context) | ||
{ | ||
var streamReaderType = context.Compilation.GetOrCreateTypeByMetadataName(WellKnownTypeNames.SystemIOStreamReader); | ||
|
||
if (streamReaderType is null) | ||
{ | ||
return; | ||
} | ||
|
||
var endOfStreamProperty = streamReaderType.GetMembers(EndOfStream) | ||
.OfType<IPropertySymbol>() | ||
.FirstOrDefault(); | ||
|
||
if (endOfStreamProperty is null) | ||
{ | ||
return; | ||
} | ||
|
||
context.RegisterOperationAction(AnalyzePropertyReference, OperationKind.PropertyReference); | ||
|
||
void AnalyzePropertyReference(OperationAnalysisContext context) | ||
{ | ||
var operation = (IPropertyReferenceOperation)context.Operation; | ||
|
||
if (!SymbolEqualityComparer.Default.Equals(endOfStreamProperty, operation.Member)) | ||
{ | ||
return; | ||
} | ||
|
||
var containingSymbol = operation.TryGetContainingAnonymousFunctionOrLocalFunction() ?? context.ContainingSymbol; | ||
|
||
if (containingSymbol is IMethodSymbol containingMethod && containingMethod.IsAsync) | ||
{ | ||
context.ReportDiagnostic(operation.CreateDiagnostic(Rule, operation.Syntax.ToString())); | ||
} | ||
} | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.