Commit graph

923 commits

Author SHA1 Message Date
Vadim Petrochenkov 0195758c1a ast: Standardize visiting order for attributes and node IDs 2024-06-24 16:08:51 +03:00
Nicholas Nethercote e2aa38e6ab Rework pattern and expression nonterminal kinds.
Merge `PatParam`/`PatWithOr`, and `Expr`/`Expr2021`, for a few reasons.

- It's conceptually nice, because the two pattern kinds and the two
  expression kinds are very similar.

- With expressions in particular, there are several places where both
  expression kinds get the same treatment.

- It removes one unreachable match arm.

- Most importantly, for #124141 I will need to introduce a new type
  `MetaVarKind` that is very similar to `NonterminalKind`, but records a
  couple of extra fields for expression metavars. It's nicer to have a
  single `MetaVarKind::Expr` expression variant to hold those extra
  fields instead of duplicating them across two variants
  `MetaVarKind::{Expr,Expr2021}`. And then it makes sense for patterns
  to be treated the same way, and for `NonterminalKind` to also be
  treated the same way.

I also clarified the comments, because I have long found them a little
hard to understand.
2024-06-23 15:57:24 +10:00
Matthias Krüger f577d808b7
Rollup merge of #126767 - compiler-errors:static-foreign-item, r=spastorino
`StaticForeignItem` and `StaticItem` are the same

The struct `StaticItem` and `StaticForeignItem` are the same, so remove `StaticForeignItem`. Having them be separate is unique to `static` items -- unlike `ForeignItemKind::{Fn,TyAlias}`, which use the normal AST item.

r? ``@spastorino`` or ``@oli-obk``
2024-06-21 09:12:37 +02:00
Matthias Krüger 3bd84f18bc
Rollup merge of #126700 - compiler-errors:fragment, r=fmease
Make edition dependent `:expr` macro fragment act like the edition-dependent `:pat` fragment does

Parse the `:expr` fragment as `:expr_2021` in editions <=2021, and as `:expr` in edition 2024. This is similar to how we parse `:pat` as `:pat_param` in edition <=2018 and `:pat_with_or` in >=2021, and means we can get rid of a span dependency from `nonterminal_may_begin_with`.

Specifically, this fixes a theoretical regression since the `expr_2021` macro fragment previously would allow `const {}` if the *caller* is edition 2024. This is inconsistent with the way that the `pat` macro fragment was upgraded, and also leads to surprising behavior when a macro *caller* crate upgrades to edtion 2024, since they may have parsing changes that they never asked for (with no way of opting out of it).

This PR also allows using `expr_2021` in all editions. Why was this was disallowed in the first place? It's purely additive, and also it's still feature gated?

r? ```@fmease``` ```@eholk``` cc ```@vincenzopalazzo```
cc #123865

Tracking:

- https://github.com/rust-lang/rust/issues/123742
2024-06-21 09:12:36 +02:00
Michael Goulet 3e59f0c3c5 StaticForeignItem and StaticItem are the same 2024-06-20 19:51:09 -04:00
Nicholas Nethercote c6f78270b6 Introduce can_begin_string_literal.
We currently use `can_begin_literal_maybe_minus` in a couple of places
where only string literals are allowed. This commit introduces a
more specific function, which makes things clearer. It doesn't change
behaviour because the two functions affected (`is_unsafe_foreign_mod`
and `check_keyword_case`) are always followed by a call to `parse_abi`,
which checks again for a string literal.
2024-06-20 04:50:40 +10:00
Nicholas Nethercote 7d9a92ba31 Inline can_begin_literal_maybe_minus call into two places.
It's clearer this way, because the `Interpolated` cases in
`can_begin_const_arg` and `is_pat_range_end_start` are more permissive
than the `Interpolated` cases in `can_begin_literal_maybe_minus`.
2024-06-20 04:50:38 +10:00
Michael Goulet 3e8898a4e1 Allow naming expr_2021 in all editions 2024-06-19 12:37:49 -04:00
bors 894f7a4ba6 Auto merge of #126678 - nnethercote:fix-duplicated-attrs-on-nt-expr, r=petrochenkov
Fix duplicated attributes on nonterminal expressions

This PR fixes a long-standing bug (#86055) whereby expression attributes can be duplicated when expanded through declarative macros.

First, consider how items are parsed in declarative macros:
```
Items:
- parse_nonterminal
  - parse_item(ForceCollect::Yes)
    - parse_item_
      - attrs = parse_outer_attributes
      - parse_item_common(attrs)
        - maybe_whole!
        - collect_tokens_trailing_token
```
The important thing is that the parsing of outer attributes is outside token collection, so the item's tokens don't include the attributes. This is how it's supposed to be.

Now consider how expression are parsed in declarative macros:
```
Exprs:
- parse_nonterminal
  - parse_expr_force_collect
    - collect_tokens_no_attrs
      - collect_tokens_trailing_token
        - parse_expr
          - parse_expr_res(None)
            - parse_expr_assoc_with
              - parse_expr_prefix
                - parse_or_use_outer_attributes
                - parse_expr_dot_or_call
```
The important thing is that the parsing of outer attributes is inside token collection, so the the expr's tokens do include the attributes, i.e. in `AttributesData::tokens`.

This PR fixes the bug by rearranging expression parsing to that outer attribute parsing happens outside of token collection. This requires a number of small refactorings because expression parsing is somewhat complicated. While doing so the PR makes the code a bit cleaner and simpler, by eliminating `parse_or_use_outer_attributes` and `Option<AttrWrapper>` arguments (in favour of the simpler `parse_outer_attributes` and `AttrWrapper` arguments), and simplifying `LhsExpr`.

r? `@petrochenkov`
2024-06-19 13:58:21 +00:00
Nicholas Nethercote 219389360c Add a comment.
Something that was non-obvious to me.
2024-06-19 18:53:24 +10:00
许杰友 Jieyou Xu (Joe) f8ce1cfbf5
Rollup merge of #124135 - petrochenkov:deleglob, r=fmease
delegation: Implement glob delegation

Support delegating to all trait methods in one go.
Overriding globs with explicit definitions is also supported.

The implementation is generally based on the design from https://github.com/rust-lang/rfcs/pull/3530#issuecomment-2020869823, but unlike with list delegation in https://github.com/rust-lang/rust/pull/123413 we cannot expand glob delegation eagerly.
We have to enqueue it into the queue of unexpanded macros (most other macros are processed this way too), and then a glob delegation waits in that queue until its trait path is resolved, and enough code expands to generate the identifier list produced from the glob.

Glob delegation is only allowed in impls, and can only point to traits.
Supporting it in other places gives very little practical benefit, but significantly raises the implementation complexity.

Part of https://github.com/rust-lang/rust/issues/118212.
2024-06-19 01:51:36 +01:00
Michael Goulet b1efe1ab5d Rework precise capturing syntax 2024-06-17 22:35:25 -04:00
Vadim Petrochenkov 22d0b1ee18 delegation: Implement glob delegation 2024-06-14 19:27:51 +03:00
Nicholas Nethercote 75b164d836 Use tidy to sort crate attributes for all compiler crates.
We already do this for a number of crates, e.g. `rustc_middle`,
`rustc_span`, `rustc_metadata`, `rustc_span`, `rustc_errors`.

For the ones we don't, in many cases the attributes are a mess.
- There is no consistency about order of attribute kinds (e.g.
  `allow`/`deny`/`feature`).
- Within attribute kind groups (e.g. the `feature` attributes),
  sometimes the order is alphabetical, and sometimes there is no
  particular order.
- Sometimes the attributes of a particular kind aren't even grouped
  all together, e.g. there might be a `feature`, then an `allow`, then
  another `feature`.

This commit extends the existing sorting to all compiler crates,
increasing consistency. If any new attribute line is added there is now
only one place it can go -- no need for arbitrary decisions.

Exceptions:
- `rustc_log`, `rustc_next_trait_solver` and `rustc_type_ir_macros`,
  because they have no crate attributes.
- `rustc_codegen_gcc`, because it's quasi-external to rustc (e.g. it's
  ignored in `rustfmt.toml`).
2024-06-12 15:49:10 +10:00
Matthias Krüger 6e534c73c3
Rollup merge of #124214 - carbotaniuman:parse_unsafe_attrs, r=michaelwoerister
Parse unsafe attributes

Initial parse implementation for #123757

This is the initial work to parse unsafe attributes, which is represented as an extra `unsafety` field in `MetaItem` and `AttrItem`. There's two areas in the code where it appears that parsing is done manually and not using the parser stuff, and I'm not sure how I'm supposed to thread the change there.
2024-06-07 20:14:28 +02:00
Oli Scherer cbee17d502 Revert "Create const block DefIds in typeck instead of ast lowering"
This reverts commit ddc5f9b6c1.
2024-06-07 08:33:58 +00:00
carbotaniuman 8aa2553b50 Change comment to FIXME 2024-06-06 20:27:25 -05:00
carbotaniuman 87be1bae73 Fix build 2024-06-06 20:27:25 -05:00
carbotaniuman 67f5dd1ef1 Parse unsafe attributes 2024-06-06 20:26:27 -05:00
Santiago Pastorino bac72cf7cf
Add safe/unsafe to static inside extern blocks 2024-06-04 14:19:43 -03:00
Santiago Pastorino 2a377122dd
Handle safety keyword for extern block inner items 2024-06-04 14:19:42 -03:00
Matthias Krüger 379233242b
Rollup merge of #125635 - fmease:mv-type-binding-assoc-item-constraint, r=compiler-errors
Rename HIR `TypeBinding` to `AssocItemConstraint` and related cleanup

Rename `hir::TypeBinding` and `ast::AssocConstraint` to `AssocItemConstraint` and update all items and locals using the old terminology.

Motivation: The terminology *type binding* is extremely outdated. "Type bindings" not only include constraints on associated *types* but also on associated *constants* (feature `associated_const_equality`) and on RPITITs of associated *functions* (feature `return_type_notation`). Hence the word *item* in the new name. Furthermore, the word *binding* commonly refers to a mapping from a binder/identifier to a "value" for some definition of "value". Its use in "type binding" made sense when equality constraints (e.g., `AssocTy = Ty`) were the only kind of associated item constraint. Nowadays however, we also have *associated type bounds* (e.g., `AssocTy: Bound`) for which the term *binding* doesn't make sense.

---

Old terminology (HIR, rustdoc):

```
`TypeBinding`: (associated) type binding
├── `Constraint`: associated type bound
└── `Equality`: (associated) equality constraint (?)
    ├── `Ty`: (associated) type binding
    └── `Const`: associated const equality (constraint)
```

Old terminology (AST, abbrev.):

```
`AssocConstraint`
├── `Bound`
└── `Equality`
    ├── `Ty`
    └── `Const`
```

New terminology (AST, HIR, rustdoc):

```
`AssocItemConstraint`: associated item constraint
├── `Bound`: associated type bound
└── `Equality`: associated item equality constraint OR associated item binding (for short)
    ├── `Ty`: associated type equality constraint OR associated type binding (for short)
    └── `Const`: associated const equality constraint OR associated const binding (for short)
```

r? compiler-errors
2024-05-31 08:50:22 +02:00
León Orell Valerian Liehr 34c56c45cf
Rename HIR TypeBinding to AssocItemConstraint and related cleanup 2024-05-30 22:52:33 +02:00
Vadim Petrochenkov 6e67eaa311 ast: Revert a breaking attribute visiting order change 2024-05-29 21:55:24 +03:00
Oli Scherer ddc5f9b6c1 Create const block DefIds in typeck instead of ast lowering 2024-05-28 13:38:43 +00:00
Matthias Krüger 3c79f0cd69
Rollup merge of #125316 - nnethercote:tweak-Spacing, r=petrochenkov
Tweak `Spacing` use

Some clean-up precursors to #125174.

r? ``@petrochenkov``
2024-05-23 07:41:18 +02:00
Nicholas Nethercote a1b6d46e04 Use JointHidden in a couple of suitable places.
This has no notable effect, but it's appropriate because the relevant
tokens are followed by delimiters.
2024-05-23 06:03:17 +10:00
León Orell Valerian Liehr 5b485f04de
Rollup merge of #125049 - dtolnay:castbrace, r=compiler-errors
Disallow cast with trailing braced macro in let-else

This fixes an edge case I noticed while porting #118880 and #119062 to syn.

Previously, rustc incorrectly accepted code such as:

```rust
let foo = &std::ptr::null as &'static dyn std::ops::Fn() -> *const primitive! {
    8
} else {
    return;
};
```

even though a right curl brace `}` directly before `else` in a `let...else` statement is not supposed to be valid syntax.
2024-05-22 19:04:44 +02:00
bors b54dd08a84 Auto merge of #125326 - weiznich:move/do_not_recommend_to_diganostic_namespace, r=compiler-errors
Move `#[do_not_recommend]` to the `#[diagnostic]` namespace

This commit moves the `#[do_not_recommend]` attribute to the `#[diagnostic]` namespace. It still requires
`#![feature(do_not_recommend)]` to work.

r? `@compiler-errors`
2024-05-22 04:14:08 +00:00
Georg Semmler 2cff3e90bc
Move #[do_not_recommend] to the #[diagnostic] namespace
This commit moves the `#[do_not_recommend]` attribute to the
`#[diagnostic]` namespace. It still requires
`#![feature(do_not_recommend)]` to work.
2024-05-21 13:14:41 +02:00
Michael Goulet a502e7ac1d Implement BOXED_SLICE_INTO_ITER 2024-05-20 19:21:30 -04:00
Pietro Albini 3ce9b2f95b
document what the span of UseTreeKind::Nested is 2024-05-19 10:22:19 +02:00
bors eb1a5c9bb3 Auto merge of #125077 - spastorino:add-new-fnsafety-enum2, r=jackh726
Rename Unsafe to Safety

Alternative to #124455, which is to just have one Safety enum to use everywhere, this opens the posibility of adding `ast::Safety::Safe` that's useful for unsafe extern blocks.

This leaves us today with:

```rust
enum ast::Safety {
    Unsafe(Span),
    Default,
    // Safe (going to be added for unsafe extern blocks)
}

enum hir::Safety {
    Unsafe,
    Safe,
}
```

We would convert from `ast::Safety::Default` into the right Safety level according the context.
2024-05-18 19:35:24 +00:00
Matthias Krüger f9bf759e83
Rollup merge of #125117 - dev-ardi:improve-parser, r=wesleywiser,fmease
Improve parser

Fixes #124935.

- Add a few more help diagnostics to incorrect semicolons
- Overall improved that function
- Addded a few comments
- Renamed diff_marker fns to git_diff_marker
2024-05-18 18:44:14 +02:00
bors 9b75a43881 Auto merge of #123865 - eholk:expr_2021, r=fmease
Update `expr` matcher for Edition 2024 and add `expr_2021` nonterminal

This commit adds a new nonterminal `expr_2021` in macro patterns, and `expr_fragment_specifier_2024` feature flag.

This change also updates `expr` so that on Edition 2024 it will also match `const { ... }` blocks, while `expr_2021` preserves the current behavior of `expr`, matching expressions without `const` blocks.

Joint work with `@vincenzopalazzo.`

Issue #123742
2024-05-17 21:54:14 +00:00
Santiago Pastorino 6b46a919e1
Rename Unsafe to Safety 2024-05-17 18:33:37 -03:00
Vadim Petrochenkov c30b41012d delegation: Implement list delegation
```rust
reuse prefix::{a, b, c}
```
2024-05-15 02:32:59 +03:00
ardi 8dc6a5d145 improve maybe_consume_incorrect_semicolon 2024-05-14 23:07:40 +02:00
Nicholas Nethercote 95e519ecbf Remove NtIdent and NtLifetime.
The extra span is now recorded in the new `TokenKind::NtIdent` and
`TokenKind::NtLifetime`. These both consist of a single token, and so
there's no operator precedence problems with inserting them directly
into the token stream.

The other way to do this would be to wrap the ident/lifetime in invisible
delimiters, but there's a lot of code that assumes an interpolated
ident/lifetime fits in a single token, and changing all that code to work with
invisible delimiters would have been a pain. (Maybe it could be done in a
follow-up.)

This change might not seem like much of a win, but it's a first step toward the
much bigger and long-desired removal of `Nonterminal` and
`TokenKind::Interpolated`. That change is big and complex enough that it's
worth doing this piece separately. (Indeed, this commit is based on part of a
late commit in #114647, a prior attempt at that big and complex change.)
2024-05-14 08:19:58 +10:00
Eric Holk f364011955
Apply code review suggestions
- use feature_err to report unstable expr_2021
- Update downlevel expr_2021 diagnostics

Co-authored-by: León Orell Valerian Liehr <me@fmease.dev>
2024-05-13 11:55:38 -07:00
Eric Holk 73303c3b45
expr_2021 should be allowed on edition 2021 and later 2024-05-13 11:27:41 -07:00
Eric Holk ef6478ba5f
Add expr_2021 nonterminal and feature flag
This commit adds a new nonterminal `expr_2021` in macro patterns, and
`expr_fragment_specifier_2024` feature flag. For now, `expr` and
`expr_2021` are treated the same, but in future PRs we will update
`expr` to match to new grammar.

Co-authored-by: Vincezo Palazzo <vincenzopalazzodev@gmail.com>
2024-05-13 11:27:26 -07:00
David Tolnay a36b94d088
Disallow cast with trailing braced macro in let-else 2024-05-12 21:50:14 -07:00
Nicholas Nethercote 9a63a42cb7 Remove a Span from TokenKind::Interpolated.
This span records the declaration of the metavariable in the LHS of the macro.
It's used in a couple of error messages. Unfortunately, it gets in the way of
the long-term goal of removing `TokenKind::Interpolated`. So this commit
removes it, which degrades a couple of (obscure) error messages but makes
things simpler and enables the next commit.
2024-05-13 10:30:30 +10:00
David Tolnay 10227eaee7
Add classify::expr_is_complete 2024-05-11 18:18:20 -07:00
David Tolnay 9e1cf2098d
Macro call with braces does not require semicolon to be statement
This commit by itself is supposed to have no effect on behavior. All of
the call sites are updated to preserve their previous behavior.

The behavior changes are in the commits that follow.
2024-05-11 15:48:59 -07:00
David Tolnay cbb8714a3f
Mark expr_requires_semi_to_be_stmt call sites
For each of these, we need to decide whether they need to be using
`expr_requires_semi_to_be_stmt`, or `expr_requires_comma_to_be_match_arm`,
which are supposed to be 2 different behaviors. Previously they were
conflated into one, causing either too much or too little
parenthesization.
2024-05-11 15:48:58 -07:00
David Tolnay b431eec6f2
Expand on expr_requires_semi_to_be_stmt documentation 2024-05-11 15:48:57 -07:00
Nicholas Nethercote fd91925bce Add ErrorGuaranteed to Recovered::Yes and use it more.
The starting point for this was identical comments on two different
fields, in `ast::VariantData::Struct` and `hir::VariantData::Struct`:
```
    // FIXME: investigate making this a `Option<ErrorGuaranteed>`
    recovered: bool
```
I tried that, and then found that I needed to add an `ErrorGuaranteed`
to `Recovered::Yes`. Then I ended up using `Recovered` instead of
`Option<ErrorGuaranteed>` for these two places and elsewhere, which
required moving `ErrorGuaranteed` from `rustc_parse` to `rustc_ast`.

This makes things more consistent, because `Recovered` is used in more
places, and there are fewer uses of `bool` and
`Option<ErrorGuaranteed>`. And safer, because it's difficult/impossible
to set `recovered` to `Recovered::Yes` without having emitted an error.
2024-05-09 20:12:07 +10:00
Matthias Krüger d8a3a69ad1
Rollup merge of #124587 - reitermarkus:use-generic-nonzero, r=dtolnay
Generic `NonZero` post-stabilization changes.

Tracking issue: https://github.com/rust-lang/rust/issues/120257

r? ``@dtolnay``
2024-05-08 23:33:25 +02:00