summary refs log tree commit diff
path: root/compiler/rustc_parse/src/parser/mod.rs
AgeCommit message (Collapse)AuthorLines
2022-05-11ast: Introduce some traits to get AST node properties genericallyVadim Petrochenkov-3/+3
And use them to avoid constructing some artificial `Nonterminal` tokens during expansion
2022-05-04Auto merge of #96546 - nnethercote:overhaul-MacArgs, r=petrochenkovbors-10/+3
Overhaul `MacArgs` Motivation: - Clarify some code that I found hard to understand. - Eliminate one use of three places where `TokenKind::Interpolated` values are created. r? `@petrochenkov`
2022-05-05Overhaul `MacArgs::Eq`.Nicholas Nethercote-10/+3
The value in `MacArgs::Eq` is currently represented as a `Token`. Because of `TokenKind::Interpolated`, `Token` can be either a token or an arbitrary AST fragment. In practice, a `MacArgs::Eq` starts out as a literal or macro call AST fragment, and then is later lowered to a literal token. But this is very non-obvious. `Token` is a much more general type than what is needed. This commit restricts things, by introducing a new type `MacArgsEqKind` that is either an AST expression (pre-lowering) or an AST literal (post-lowering). The downside is that the code is a bit more verbose in a few places. The benefit is that makes it much clearer what the possibilities are (though also shorter in some other places). Also, it removes one use of `TokenKind::Interpolated`, taking us a step closer to removing that variant, which will let us make `Token` impl `Copy` and remove many "handle Interpolated" code paths in the parser. Things to note: - Error messages have improved. Messages like this: ``` unexpected token: `"bug" + "found"` ``` now say "unexpected expression", which makes more sense. Although arbitrary expressions can exist within tokens thanks to `TokenKind::Interpolated`, that's not obvious to anyone who doesn't know compiler internals. - In `parse_mac_args_common`, we no longer need to collect tokens for the value expression.
2022-04-29errors: `span_suggestion` takes `impl ToString`David Wood-2/+2
Change `span_suggestion` (and variants) to take `impl ToString` rather than `String` for the suggested code, as this simplifies the requirements on the diagnostic derive. Signed-off-by: David Wood <david.wood@huawei.com>
2022-04-28rustc_ast: Harmonize delimiter naming with `proc_macro::Delimiter`Vadim Petrochenkov-26/+26
2022-04-27Avoid producing `NoDelim` values in `TokenCursorFrame`.Nicholas Nethercote-21/+13
2022-04-21Introduced `Cursor::next_with_spacing_ref`.Nicholas Nethercote-5/+5
This lets us clone just the parts within a `TokenTree` that need cloning, rather than the entire thing. This is a surprisingly large performance win, up to 4% on `async-std-1.10.0`.
2022-04-21Produce `CloseDelim` and pop the stack at the same time.Nicholas Nethercote-27/+34
This makes `CloseDelim` handling more like `OpenDelim` handling, which produces `OpenDelim` and pushes the stack at the same time. It requires some adjustment to `parse_token_tree` now that we don't remain within the frame after getting the `CloseDelim`.
2022-04-21Avoid some tuple destructuring.Nicholas Nethercote-5/+7
Surprisingly, this is a non-trivial performance win.
2022-04-20Remove `Eof` sanity check in `Parser::inlined_bump_with`.Nicholas Nethercote-6/+0
A Google search of the error message fails to return any relevant resuts, suggesting this has never occurred in practice. And removeing it reduces instruction counts by up to 2% on some benchmarks.
2022-04-20Only record `fallback_span` when necessary.Nicholas Nethercote-1/+1
2022-04-20Remove the loop from `Parser::bump()`.Nicholas Nethercote-29/+34
The loop is there to handle a `NoDelim` open/close token. This commit changes `TokenCursor::inlined_next` so it never returns such a token. This is a performance win because the conditional test in `bump()` is removed. If the parser needs changing in the future to handle `NoDelim` tokens, then `inlined_next()` can easily be changed to return them.
2022-04-20Remove `TokenCursorFrame::open_delim`.Nicholas Nethercote-20/+5
Because it's now always true.
2022-04-20Use `true` for `open_delim`/`close_delim` in one spot.Nicholas Nethercote-2/+2
The `DelimToken` here is `NoDelim`, which means the returned delim tokens will just be ignored by `Parser::bump()`. This commit changes things so the delim tokens won't be returned.
2022-04-20Add a size assertion for `Parser`.Nicholas Nethercote-0/+5
2022-04-20Move desugaring code into its own function.Nicholas Nethercote-67/+60
It's not hot, so shouldn't be within the always inlined part.
2022-04-19Handle `Delimited` opening immediately.Nicholas Nethercote-1/+3
Instead of letting the next iteration of the loop handle it.
2022-04-19Add {open,close}_delim arguments to `TokenCursorFrame::new()`.Nicholas Nethercote-12/+13
This will facilitate the change in the next commit. `boolean` arguments aren't great, but the function is only used in three places within this one file.
2022-04-19Rearrange `TokenCursor::inlined_next()`.Nicholas Nethercote-17/+20
In particular, avoid wrapping a token within `TokenTree::Token` and then immediately matching it and returning the token within. Just return the token immediately.
2022-04-19Merge `TokenCursor::{next,next_desugared}`.Nicholas Nethercote-74/+65
And likewise for the inlined variants. I did this for simplicity, but interesting it was a performance win as well.
2022-04-19Inline and remove `Parser::next_tok()`.Nicholas Nethercote-32/+26
It has a single call site.
2022-04-19Inline and remove `TokenTree::{open_tt,close_tt}`.Nicholas Nethercote-2/+2
They both have a single call site.
2022-04-16Rollup merge of #94985 - dtolnay:constattr, r=pnkfelixDylan DPC-2/+2
Parse inner attributes on inline const block According to https://github.com/rust-lang/rust/pull/84414#issuecomment-826150936, inner attributes are intended to be supported *"in all containers for statements (or some subset of statements)"*. This PR adds inner attribute parsing and pretty-printing for inline const blocks (https://github.com/rust-lang/rust/issues/76001), which contain statements just like an unsafe block or a loop body. ```rust let _ = const { #![allow(...)] let x = (); x }; ```
2022-04-07Shrink `Nonterminal`.Nicholas Nethercote-1/+1
By heap allocating the argument within `NtPath`, `NtVis`, and `NtStmt`. This slightly reduces cumulative and peak allocation amounts, most notably on `deep-vector`.
2022-04-05span: move `MultiSpan`David Wood-2/+2
`MultiSpan` contains labels, which are more complicated with the introduction of diagnostic translation and will use types from `rustc_errors` - however, `rustc_errors` depends on `rustc_span` so `rustc_span` cannot use types like `DiagnosticMessage` without dependency cycles. Introduce a new `rustc_error_messages` crate that can contain `DiagnosticMessage` and `MultiSpan`. Signed-off-by: David Wood <david.wood@huawei.com>
2022-03-30Spellchecking compiler commentsYuri Astrakhan-1/+1
This PR cleans up the rest of the spelling mistakes in the compiler comments. This PR does not change any literal or code spelling issues.
2022-03-28Remove `Nonterminal::NtTT`.Nicholas Nethercote-1/+7
It's only needed for macro expansion, not as a general element in the AST. This commit removes it, adds `NtOrTt` for the parser and macro expansion cases, and renames the variants in `NamedMatch` to better match the new type.
2022-03-22Split `TokenCursor::{next,next_desugared}` into inlined and non-inlined halves.Nicholas Nethercote-5/+18
2022-03-22Split `Parser::bump_with` into inlined and non-inlined halves.Nicholas Nethercote-2/+9
The call site within `Parser::bump` is hot. Also add an inline annotation to `Parser::next_tok`. It was already being inlined by the compiler; this just makes sure that continues.
2022-03-15Parse inner attributes on inline const blockDavid Tolnay-2/+2
2022-03-02rename ErrorReported -> ErrorGuaranteedmark-3/+5
2022-02-28Rollup merge of #94445 - c410-f3r:more-let-chains, r=cjgillotMatthias Krüger-5/+5
4 - Make more use of `let_chains` Continuation of #94376. cc #53667
2022-02-28Tweak diagnosticsEsteban Kuber-1/+1
* Recover from invalid `'label: ` before block. * Make suggestion to enclose statements in a block multipart. * Point at `match`, `while`, `loop` and `unsafe` keywords when failing to parse their expression. * Do not suggest `{ ; }`. * Do not suggest `|` when very unlikely to be what was wanted (in `let` statements).
2022-02-284 - Make more use of `let_chains`Caio-5/+5
Continuation of #94376. cc #53667
2022-02-23rustc_errors: let `DiagnosticBuilder::emit` return a "guarantee of emission".Eduard-Mihai Burtescu-3/+3
2022-02-23rustc_errors: take `self` by value in `DiagnosticBuilder::cancel`.Eduard-Mihai Burtescu-1/+1
2021-12-04Do not add `;` to expected tokens list when it's wrongMichael Howell-0/+1
There's a few spots where semicolons are checked for to do error recovery, and should not be suggested (or checked for other stuff). Fixes #87647
2021-11-22Split inline const to two feature gatesGary Guo-2/+6
2021-10-17Some "parenthesis" and "parentheses" fixesr00ster91-1/+1
2021-09-09Emit proper errors on missing closure bracesSasha Pourcelot-5/+98
This commit focuses on emitting clean errors for the following syntax error: ``` Some(42).map(|a| dbg!(a); a ); ``` Previous implementation tried to recover after parsing the closure body (the `dbg` expression) by replacing the next `;` with a `,`, which made the next expression belong to the next function argument. As such, the following errors were emitted (among others): - the semicolon token was not expected, - a is not in scope, - Option::map is supposed to take one argument, not two. This commit allows us to gracefully handle this situation by adding giving the parser the ability to remember when it has just parsed a closure body inside a function call. When this happens, we can treat the unexpected `;` specifically and try to parse as much statements as possible in order to eat the whole block. When we can't parse statements anymore, we generate a clean error indicating that the braces are missing, and return an ExprKind::Err.
2021-09-03Auto merge of #88386 - estebank:unmatched-delims, r=jackh726bors-2/+7
Point at unclosed delimiters as part of the primary MultiSpan Both the place where the parser encounters a needed closed delimiter and the unclosed opening delimiter are important, so they should get the same level of highlighting in the output. _Context: https://twitter.com/mwk4/status/1430631546432675840_
2021-08-29Auto merge of #88262 - klensy:pprust-cow, r=nagisabors-1/+1
Cow'ify some pprust methods Reduce number of potential needless de/allocations by using `Cow<'static, str>` instead of explicit `String` type.
2021-08-27Point at unclosed delimiters as part of the primary MultiSpanEsteban Kuber-2/+7
Both the place where the parser encounters a needed closed delimiter and the unclosed opening delimiter are important, so they should get the same level of highlighting in the output.
2021-08-25Convert some functions to return Cow<'static,str> instead of String to ↵klensy-1/+1
reduce potential reallocations
2021-08-22Fix typos “a”→“an”Frank Steffahn-6/+6
2021-07-14Suggest a path separator if a stray colon is found in a match armFabian Wolff-1/+1
Co-authored-by: Esteban Kuber <estebank@users.noreply.github.com>
2021-06-06parser: Ensure that all nonterminals have tokens after parsingVadim Petrochenkov-0/+1
2021-05-18Stabilize extended_key_value_attributesJoshua Nelson-13/+0
# Stabilization report ## Summary This stabilizes using macro expansion in key-value attributes, like so: ```rust #[doc = include_str!("my_doc.md")] struct S; #[path = concat!(env!("OUT_DIR"), "/generated.rs")] mod m; ``` See the changes to the reference for details on what macros are allowed; see Petrochenkov's excellent blog post [on internals](https://internals.rust-lang.org/t/macro-expansion-points-in-attributes/11455) for alternatives that were considered and rejected ("why accept no more and no less?") This has been available on nightly since 1.50 with no major issues. ## Notes ### Accepted syntax The parser accepts arbitrary Rust expressions in this position, but any expression other than a macro invocation will ultimately lead to an error because it is not expected by the built-in expression forms (e.g., `#[doc]`). Note that decorators and the like may be able to observe other expression forms. ### Expansion ordering Expansion of macro expressions in "inert" attributes occurs after decorators have executed, analogously to macro expressions appearing in the function body or other parts of decorator input. There is currently no way for decorators to accept macros in key-value position if macro expansion must be performed before the decorator executes (if the macro can simply be copied into the output for later expansion, that can work). ## Test cases - https://github.com/rust-lang/rust/blob/master/src/test/ui/attributes/key-value-expansion-on-mac.rs - https://github.com/rust-lang/rust/blob/master/src/test/rustdoc/external-doc.rs The feature has also been dogfooded extensively in the compiler and standard library: - https://github.com/rust-lang/rust/pull/83329 - https://github.com/rust-lang/rust/pull/83230 - https://github.com/rust-lang/rust/pull/82641 - https://github.com/rust-lang/rust/pull/80534 ## Implementation history - Initial proposal: https://github.com/rust-lang/rust/issues/55414#issuecomment-554005412 - Experiment to see how much code it would break: https://github.com/rust-lang/rust/pull/67121 - Preliminary work to restrict expansion that would conflict with this feature: https://github.com/rust-lang/rust/pull/77271 - Initial implementation: https://github.com/rust-lang/rust/pull/78837 - Fix for an ICE: https://github.com/rust-lang/rust/pull/80563 ## Unresolved Questions ~~https://github.com/rust-lang/rust/pull/83366#issuecomment-805180738 listed some concerns, but they have been resolved as of this final report.~~ ## Additional Information There are two workarounds that have a similar effect for `#[doc]` attributes on nightly. One is to emulate this behavior by using a limited version of this feature that was stabilized for historical reasons: ```rust macro_rules! forward_inner_docs { ($e:expr => $i:item) => { #[doc = $e] $i }; } forward_inner_docs!(include_str!("lib.rs") => struct S {}); ``` This also works for other attributes (like `#[path = concat!(...)]`). The other is to use `doc(include)`: ```rust #![feature(external_doc)] #[doc(include = "lib.rs")] struct S {} ``` The first works, but is non-trivial for people to discover, and difficult to read and maintain. The second is a strange special-case for a particular use of the macro. This generalizes it to work for any use case, not just including files. I plan to remove `doc(include)` when this is stabilized. The `forward_inner_docs` workaround will still compile without warnings, but I expect it to be used less once it's no longer necessary.
2021-05-10Auto merge of #85104 - hi-rustin:rustin-patch-typo, r=jonas-schievinkbors-1/+1
Fix typo
2021-05-09Fix typohi-rustin-1/+1