-
Notifications
You must be signed in to change notification settings - Fork 463
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add DoNotPassStructToArgumentNullExceptionThrowIfNullAnalyzer #6815
Conversation
# Conflicts: # src/NetAnalyzers/Core/Microsoft.NetCore.Analyzers/MicrosoftNetCoreAnalyzersResources.resx # src/Utilities/Compiler/DiagnosticCategoryAndIdRanges.txt
Codecov ReportAttention:
Additional details and impacted files@@ Coverage Diff @@
## main #6815 +/- ##
========================================
Coverage 96.45% 96.46%
========================================
Files 1422 1427 +5
Lines 340585 341582 +997
Branches 11230 11246 +16
========================================
+ Hits 328511 329503 +992
+ Misses 9236 9234 -2
- Partials 2838 2845 +7 |
Thanks, @CollinAlpert. I suggest we broaden this slightly. The reason structs don't make sense here is because they'll be boxed to objects and then will never be null, making the whole operation an expensive nop. That same reasoning applies to other misuse, as well, for example accidentally passing a |
...Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNull.Fixer.cs
Outdated
Show resolved
Hide resolved
var typeProvider = WellKnownTypeProvider.GetOrCreate(context.Compilation); | ||
var throwIfNullMethod = typeProvider.GetOrCreateTypeByMetadataName(WellKnownTypeNames.SystemArgumentNullException) | ||
?.GetMembers("ThrowIfNull") | ||
.FirstOrDefault(m => m is IMethodSymbol method && method.Parameters[0].Type.SpecialType == SpecialType.System_Object); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
.FirstOrDefault(m => m is IMethodSymbol method && method.Parameters[0].Type.SpecialType == SpecialType.System_Object); | |
.FirstOrDefault(m => m is IMethodSymbol method && method.Parameters.Length > 0 && method.Parameters[0].Type.SpecialType == SpecialType.System_Object); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You could go further if you want:
m is IMethodSymbol { Parameters: [{ Type.SpecialType: SpecialType.System_Object }, ..] }
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Show resolved
Hide resolved
# Conflicts: # src/NetAnalyzers/RulesMissingDocumentation.md
@stephentoub @Youssef1313 Thank you for your feedback, I have addressed it and added appropriate tests. |
Seems like |
<target state="new">Do not call 'ArgumentNullException.ThrowIfNull' with a struct</target> | ||
<note /> | ||
</trans-unit> | ||
<trans-unit id="DoNotPassNullableStructToArgumentNullExceptionThrowIfNullDescription"> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Do we really need this? SharpLab suggests that release builds will not box a non-null value in this case.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you share an example? I can see the box
instruction here.
# Conflicts: # src/NetAnalyzers/Core/AnalyzerReleases.Unshipped.md # src/NetAnalyzers/Core/Microsoft.NetCore.Analyzers/MicrosoftNetCoreAnalyzersResources.resx # src/NetAnalyzers/Microsoft.CodeAnalysis.NetAnalyzers.md # src/Utilities/Compiler/DiagnosticCategoryAndIdRanges.txt
# Conflicts: # src/NetAnalyzers/Core/AnalyzerReleases.Unshipped.md # src/NetAnalyzers/Core/Microsoft.NetCore.Analyzers/MicrosoftNetCoreAnalyzersResources.resx # src/NetAnalyzers/Microsoft.CodeAnalysis.NetAnalyzers.md # src/NetAnalyzers/Microsoft.CodeAnalysis.NetAnalyzers.sarif # src/NetAnalyzers/RulesMissingDocumentation.md
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sorry for delayed review @CollinAlpert, left some comments/questions, mostly NITs. Overall the PR looks great, thank you!
Testing with runtime got 1 valid hit, the analyzer/fixer works well in functional testing.
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Show resolved
Hide resolved
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Outdated
Show resolved
Hide resolved
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Outdated
Show resolved
Hide resolved
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Outdated
Show resolved
Hide resolved
src/NetAnalyzers/Core/Microsoft.NetCore.Analyzers/MicrosoftNetCoreAnalyzersResources.resx
Outdated
Show resolved
Hide resolved
src/NetAnalyzers/Core/Microsoft.NetCore.Analyzers/MicrosoftNetCoreAnalyzersResources.resx
Outdated
Show resolved
Hide resolved
...NetCore.Analyzers/Usage/DoNotPassNonNullableValueToArgumentNullExceptionThrowIfNull.Fixer.cs
Outdated
Show resolved
Hide resolved
.../Microsoft.NetCore.Analyzers/Usage/DoNotPassStructToArgumentNullExceptionThrowIfNullTests.cs
Show resolved
Hide resolved
...NetCore.Analyzers/Usage/DoNotPassNonNullableValueToArgumentNullExceptionThrowIfNull.Fixer.cs
Outdated
Show resolved
Hide resolved
...osoft.NetCore.Analyzers/Usage/DoNotPassNonNullableValueToArgumentNullExceptionThrowIfNull.cs
Show resolved
Hide resolved
# Conflicts: # src/NetAnalyzers/Core/AnalyzerReleases.Unshipped.md # src/NetAnalyzers/Microsoft.CodeAnalysis.NetAnalyzers.md # src/NetAnalyzers/RulesMissingDocumentation.md
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM, thank you @CollinAlpert!
Fixes dotnet/runtime#85154