From 8b1111f50b4f0d33b6cf6934c0106d86944feb36 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?G=C3=A9rald=20Barr=C3=A9?= Date: Sat, 21 Sep 2024 12:37:45 -0400 Subject: [PATCH] MA0100 support labels --- .../Internals/OperationExtensions.cs | 13 +++++ ...aitTaskBeforeDisposingResourcesAnalyzer.cs | 7 +-- ...skBeforeDisposingResourcesAnalyzerTests.cs | 47 +++++++++++++------ 3 files changed, 49 insertions(+), 18 deletions(-) diff --git a/src/Meziantou.Analyzer/Internals/OperationExtensions.cs b/src/Meziantou.Analyzer/Internals/OperationExtensions.cs index ebc13927d..e0718764e 100644 --- a/src/Meziantou.Analyzer/Internals/OperationExtensions.cs +++ b/src/Meziantou.Analyzer/Internals/OperationExtensions.cs @@ -109,6 +109,19 @@ public static IOperation UnwrapConversionOperations(this IOperation operation) return operation; } + public static IOperation? UnwrapLabelOperations(this IOperation operation) + { + if (operation is ILabeledOperation label) + { + if (label.Operation is null) + return null; + + return UnwrapLabelOperations(label.Operation); + } + + return operation; + } + public static bool HasArgumentOfType(this IInvocationOperation operation, ITypeSymbol argumentTypeSymbol) { foreach (var arg in operation.Arguments) diff --git a/src/Meziantou.Analyzer/Rules/AwaitTaskBeforeDisposingResourcesAnalyzer.cs b/src/Meziantou.Analyzer/Rules/AwaitTaskBeforeDisposingResourcesAnalyzer.cs index e822aa34a..cf336ae25 100644 --- a/src/Meziantou.Analyzer/Rules/AwaitTaskBeforeDisposingResourcesAnalyzer.cs +++ b/src/Meziantou.Analyzer/Rules/AwaitTaskBeforeDisposingResourcesAnalyzer.cs @@ -1,4 +1,5 @@ using System.Collections.Immutable; +using System.Linq; using System.Threading.Tasks; using Meziantou.Analyzer.Internals; using Microsoft.CodeAnalysis; @@ -66,7 +67,7 @@ public void AnalyzeReturn(OperationAnalysisContext context) private static bool IsInUsingOperation(IOperation operation) { - foreach (var parent in operation.Ancestors()) + foreach (var parent in operation.Ancestors().Select(operation => operation.UnwrapLabelOperations())) { if (parent is IAnonymousFunctionOperation or ILocalFunctionOperation) return false; @@ -76,9 +77,9 @@ private static bool IsInUsingOperation(IOperation operation) if (parent is IBlockOperation block) { - foreach (var blockOperation in block.Operations) + foreach (var blockOperation in block.Operations.Select(operation => operation.UnwrapLabelOperations())) { - if (blockOperation == parent) + if (blockOperation == operation) break; if (blockOperation is IUsingDeclarationOperation) diff --git a/tests/Meziantou.Analyzer.Test/Rules/AwaitTaskBeforeDisposingResourcesAnalyzerTests.cs b/tests/Meziantou.Analyzer.Test/Rules/AwaitTaskBeforeDisposingResourcesAnalyzerTests.cs index 54a458615..09b1bf0ec 100755 --- a/tests/Meziantou.Analyzer.Test/Rules/AwaitTaskBeforeDisposingResourcesAnalyzerTests.cs +++ b/tests/Meziantou.Analyzer.Test/Rules/AwaitTaskBeforeDisposingResourcesAnalyzerTests.cs @@ -487,25 +487,42 @@ await CreateProjectBuilder() } [Fact] - public async Task UsingBlockBeforeAReturn() - { - var originalCode = """ - class TestClass - { - System.Threading.Tasks.Task Test() - { - using (var disposable = (System.IDisposable)null) + public Task UsingBlockBeforeAReturn() + => CreateProjectBuilder() + .WithSourceCode(""" + class TestClass { + System.Threading.Tasks.Task Test() + { + using (var disposable = (System.IDisposable)null) + { + } + + return System.Threading.Tasks.Task.Delay(1); + } } + """) + .WithLanguageVersion(Microsoft.CodeAnalysis.CSharp.LanguageVersion.CSharp8) + .ValidateAsync(); - return System.Threading.Tasks.Task.Delay(1); - } - } - """; + [Fact] + public Task UsingBeforeAReturnWithLabel() + => CreateProjectBuilder() + .WithSourceCode(""" + class TestClass + { + System.Threading.Tasks.Task Test(bool test) + { + if (test) goto a; + return System.Threading.Tasks.Task.Delay(1); - await CreateProjectBuilder() - .WithSourceCode(originalCode) + a: + using var disposable = (System.IDisposable) null; + [||]return System.Threading.Tasks.Task.Delay(1); + } + + } + """) .WithLanguageVersion(Microsoft.CodeAnalysis.CSharp.LanguageVersion.CSharp8) .ValidateAsync(); - } }