Skip to content
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

Do not suggest using implicit type for stackalloc initialization #22779

Merged
merged 3 commits into from
Nov 3, 2017

Conversation

OmarTawfik
Copy link
Contributor

@OmarTawfik OmarTawfik commented Oct 19, 2017

@OmarTawfik OmarTawfik added this to the 15.later milestone Oct 19, 2017
@OmarTawfik OmarTawfik self-assigned this Oct 19, 2017
Copy link
Member

@jcouv jcouv left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM Thanks

var initializer = variable.Initializer.Value;

// Discourage using "var pointer = stackalloc", after introducing C# 7.2, as it might be confusing to users expecting a Span<>
// Check descendant nodes as well, because Span-creating stackallocs can be nested in other nodes (like conditional operators and casts).
Copy link
Member

@CyrusNajmabadi CyrusNajmabadi Oct 19, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

that seems odd... what if i had something like Type t = foo(... stackalloc ...);

This would still be a location where converting to 'var' woudl be ok, right? #Resolved

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what if the stackalloc is inside a lambda that is on the right hand side? it seems weird that this would disable this feature at this level.

Copy link
Contributor Author

@OmarTawfik OmarTawfik Oct 20, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Such syntax is disabled. Please check #22046 #Closed

Copy link
Member

@CyrusNajmabadi CyrusNajmabadi Oct 20, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can't have a stackalloc inside lambda on the RHS? #Pending

Copy link
Contributor Author

@OmarTawfik OmarTawfik Oct 23, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can. I'll test that as well.

return false;
}

if (AssignmentSupportsStylePreference(variable.Identifier, typeName, initializer, semanticModel, optionSet, cancellationToken))
Copy link
Member

@CyrusNajmabadi CyrusNajmabadi Oct 19, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i woudl keep the wrapping as it was before. #Resolved

semanticModel, optionSet, cancellationToken))
var initializer = variable.Initializer.Value;

// Discourage using "var pointer = stackalloc", after introducing C# 7.2, as it might be confusing to users expecting a Span<>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❗️ This analyzer isn't the place to do this. The new C# 7.2 features do not affect the use of var from the perspective of this analyzer.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sharwell can you please explain? the IDE should never suggest that particular pattern in that case.

// Discourage using "var pointer = stackalloc", after introducing C# 7.2, as it might be confusing to users expecting a Span<>
// Check descendant nodes as well, because Span-creating stackallocs can be nested in other nodes (like conditional operators and casts).
// https://github.com/dotnet/roslyn/issues/22768
if (initializer.DescendantNodesAndSelf().Any(node => node.IsKind(SyntaxKind.StackAllocArrayCreationExpression)))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❓ Why is this needed? We already have the following block which is intended to catch exactly this case. For example, no special casing is needed for IFormattable f = $"";.

var conversion = semanticModel.GetConversion(expression, cancellationToken);
if (conversion.Exists && conversion.IsImplicit && !conversion.IsIdentity)
{
return false;
}

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because in cases where compiler can bind the node successfully without errors, it will be replaced with a BoundConvertedStackAllocExpression. That's what the semantic model will return.

{
unsafe static void M()
{
[|int*|] x = stackalloc int [10];
Copy link
Member

@sharwell sharwell Oct 20, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❗️ For the ImplicitTypeEverywhere() options, this should report a diagnostic. Span<T> is not a special case, the same way string interpolation with IFormattable is not a special case.

if (!variableDeclaration.Type.IsKind(SyntaxKind.PointerType)
&& initializer
.DescendantNodesAndSelf(descendIntoChildren: node => !node.IsAnyLambdaOrAnonymousMethod())
.Any(node => node.IsKind(SyntaxKind.StackAllocArrayCreationExpression)))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

FWIW, i would prefer really long expressions like this get broken out into either a helper method, or into statements. i.e.:

var isPointerType = ...
var containsStackAlloc = ...

if (!isPointerType && containsStackAlloc) { ...

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's just much more readable to me that way (IMO).

@OmarTawfik
Copy link
Contributor Author

@sharwell any other comments?

@OmarTawfik
Copy link
Contributor Author

@sharwell can you please take a look?

@jinujoseph
Copy link
Contributor

@OmarTawfik , submitting this for shiproom barcheck...can you fill in the ask mode template .
Once approved you are re-target this to master branch.
Thanks for taking care of this

@OmarTawfik
Copy link
Contributor Author

@jinujoseph filled the questions in the VSO bug. Please let me know if I should do anything else.

@sharwell sharwell changed the base branch from post-dev15.5-contrib to master October 31, 2017 19:37
@sharwell sharwell changed the base branch from master to post-dev15.5-contrib October 31, 2017 19:37
@sharwell
Copy link
Member

@OmarTawfik this will need to be rebased so we can target master.

@OmarTawfik OmarTawfik changed the base branch from post-dev15.5-contrib to master November 2, 2017 00:02
@OmarTawfik OmarTawfik changed the base branch from master to merges/master-to-post-dev15.5-contrib-20171031-070016 November 2, 2017 00:13
@OmarTawfik OmarTawfik changed the base branch from merges/master-to-post-dev15.5-contrib-20171031-070016 to post-dev15.5-contrib November 2, 2017 00:13
@OmarTawfik
Copy link
Contributor Author

@sharwell it is not going to be a pretty/straightforward rebase :(
I'll move these changes to another PR against master if it gets approved for 15.5.

@sharwell sharwell force-pushed the fix-22768-suggest-var-for-stackalloc branch from 4fa5c0d to e7e9fa4 Compare November 2, 2017 11:40
@sharwell sharwell changed the base branch from post-dev15.5-contrib to master November 2, 2017 11:41
@sharwell
Copy link
Member

sharwell commented Nov 2, 2017

@OmarTawfik I went ahead and did the rebase and changed the base branch of this PR to master. This will allow the tests to complete for the correct target so we're ready if approval comes through. If it doesn't get approved, we'll just switch the base branch back to 15.6 - a second rebase would not be required. 👍

@jinujoseph
Copy link
Contributor

Pre-approved to merge via link

@sharwell sharwell merged commit 089a2d3 into master Nov 3, 2017
@sharwell sharwell deleted the fix-22768-suggest-var-for-stackalloc branch November 3, 2017 12:44
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants