-
Notifications
You must be signed in to change notification settings - Fork 13.9k
rustc: introduce {ast,hir}::AnonConst to consolidate so-called "embedded constants". #50851
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
Conversation
src/libsyntax/ast.rs
Outdated
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.
It's a bit strange that const and static initializers are not treated as Const and not visited by fn visit_const, for example, despite being same "constant single-expression bodies".
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.
Is it necessary to introduce Const in AST, btw?
New node ids can be assigned during lowering to HIR too.
At least from syntax/expansion point of view Const is "just an expression".
(I see that some stuff in resolve becomes shorter, but I haven't looked in detail yet.)
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.
Those have items (or trait/impl associated items) they're directly attached to, so they don't need any changes, but also changing them would complicate a bunch of logic that's straight-forward today and would have to jump through an extra hoop.
There's one potential exception to this, which is that static could be considered to be "more disjoint" from its initializer than const and separating them could allow better bookkeeping of the "allocation" vs "value the allocation is initialized with" (cc @oli-obk), but even then it seems a bit stretched.
I wanted to avoid calling the type EmbeddedConst because it's long and potentially even more confusing, but if anyone has a better suggestion, it could use being more explicit.
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.
the static vs its value won't get easier by changing this. Miri's bookkeeping about that is completely sane now.
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.
Is it necessary to introduce
Constin AST, btw?
New node ids can be assigned during lowering to HIR too.
Sadly, yes, because the DefId tree is built from the AST, and nodes inside a Const need to be its descendants (this is where some of the ICEs for closures came from).
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.
So, what criterion should a constant Expr satisfy to become Const then? No direct parent with DefId?
Discriminants in enums have a direct parent with DefId to which they are attached - the variant itself, in this sense I don't see how they are different from consts or statics. Is preferring Const just a matter of convenience in this case?
Could all this be documented in a comment for Const?
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.
Also, expressions in range patterns have very similar properties to array sizes, etc (THIS ... AND_THIS), but I guess they don't need a body because you can't smuggle arbitrary expressions into them, paths at most.
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.
The criterion is a requirement of separate const-evaluation (which requires separate type-checking).
Array type lengths and enum discriminants don't (necessarily) have a parent body so they need a separate DefId and body to even be type-checked (array type lengths could have a DefId attached to the NodeId of the TyArray, but enum variants already have a DefId with a different meaning).
The count of an ExprRepeat is technically guaranteed to be nested inside another body, but type-checking the ExprRepeat requires const-evaluating the count, which currently can't be done without the count being a separate body.
In contrast, const and static
Also, expressions in range patterns have very similar properties to array sizes
It might be a good idea to keep those separate too, but type-checking them could require inference from the outer body (because of associated consts), so it's tricky.
I think long-term we should perhaps keep such constant expressions (including ones from paths involving const generics, in the future), in a separate body but type-check them like closures (sharing the inference context of their parent body), while retaining the ability to const-eval them.
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.
Oh. will this make the difference between a variant's discriminant and it's isize value clearer?
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.
will this make the difference between a variant's discriminant and it's isize value clearer?
Doubful.
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.
huzzah 🎉
src/libsyntax/ast.rs
Outdated
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.
Maybe we should call this an AnonymousConst or something like that? This would address @petrochenkov's concern about const vs static items to some extent, since they are clearly not anonymous.
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.
Yeah, Const seems too generic for this thing that has a very specific technical purpose rather than represents constant expressions in general.
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.
I was thinking of ty::Const when I picked the name, TBH, but that doesn't make as much sense in the AST/HIR.
I guess AnonConst would work pretty well, thanks!
|
r=me once we settle this bikeshed |
|
@bors r=nikomatsakis |
|
📌 Commit 26aad25 has been approved by |
rustc: introduce {ast,hir}::AnonConst to consolidate so-called "embedded constants".
Previously, constants in array lengths and enum variant discriminants were "merely an expression", and had no separate ID for, e.g. type-checking or const-eval, instead reusing the expression's.
That complicated code working with bodies, because such constants were the only special case where the "owner" of the body wasn't the HIR parent, but rather the same node as the body itself.
Also, if the body happened to be a closure, we had no way to allocate a `DefId` for both the constant *and* the closure, leading to *several* bugs (mostly ICEs where type errors were expected).
This PR rectifies the situation by adding another (`{ast,hir}::AnonConst`) node around every such constant. Also, const generics are expected to rely on the new `AnonConst` nodes, as well (cc @varkor).
* fixes #48838
* fixes #50600
* fixes #50688
* fixes #50689
* obsoletes #50623
r? @nikomatsakis
|
☀️ Test successful - status-appveyor, status-travis |
Previously, constants in array lengths and enum variant discriminants were "merely an expression", and had no separate ID for, e.g. type-checking or const-eval, instead reusing the expression's.
That complicated code working with bodies, because such constants were the only special case where the "owner" of the body wasn't the HIR parent, but rather the same node as the body itself.
Also, if the body happened to be a closure, we had no way to allocate a
DefIdfor both the constant and the closure, leading to several bugs (mostly ICEs where type errors were expected).This PR rectifies the situation by adding another (
{ast,hir}::AnonConst) node around every such constant. Also, const generics are expected to rely on the newAnonConstnodes, as well (cc @varkor).r? @nikomatsakis