Skip to content

Commit

Permalink
Auto merge of rust-lang#133760 - GuillaumeGomez:rollup-2c1y8c3, r=Gui…
Browse files Browse the repository at this point in the history
…llaumeGomez

Rollup of 13 pull requests

Successful merges:

 - rust-lang#133603 (Eliminate magic numbers from expression precedence)
 - rust-lang#133715 (rustdoc-json: Include safety of `static`s)
 - rust-lang#133721 (rustdoc-json: Add test for `impl Trait for dyn Trait`)
 - rust-lang#133725 (Remove `//@ compare-output-lines-by-subset`)
 - rust-lang#133730 (Add pretty-printer parenthesis insertion test)
 - rust-lang#133736 (Add `needs-target-has-atomic` directive)
 - rust-lang#133739 (Re-add myself to rotation)
 - rust-lang#133743 (Fix docs for `<[T]>::as_array`.)
 - rust-lang#133744 (Fix typo README.md)
 - rust-lang#133745 (Remove static HashSet for default IDs list)
 - rust-lang#133749 (mir validator: don't store mir phase)
 - rust-lang#133751 (remove `Ty::is_copy_modulo_regions`)
 - rust-lang#133757 (`impl Default for EarlyDiagCtxt`)

r? `@ghost`
`@rustbot` modify labels: rollup
  • Loading branch information
bors committed Dec 2, 2024
2 parents 32eea2f + 586591f commit d49be02
Show file tree
Hide file tree
Showing 54 changed files with 813 additions and 397 deletions.
22 changes: 10 additions & 12 deletions compiler/rustc_ast/src/ast.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,9 +39,7 @@ pub use crate::format::*;
use crate::ptr::P;
use crate::token::{self, CommentKind, Delimiter};
use crate::tokenstream::{DelimSpan, LazyAttrTokenStream, TokenStream};
use crate::util::parser::{
AssocOp, PREC_CLOSURE, PREC_JUMP, PREC_PREFIX, PREC_RANGE, PREC_UNAMBIGUOUS,
};
use crate::util::parser::{AssocOp, ExprPrecedence};

/// A "Label" is an identifier of some point in sources,
/// e.g. in the following code:
Expand Down Expand Up @@ -1317,29 +1315,29 @@ impl Expr {
Some(P(Ty { kind, id: self.id, span: self.span, tokens: None }))
}

pub fn precedence(&self) -> i8 {
pub fn precedence(&self) -> ExprPrecedence {
match self.kind {
ExprKind::Closure(..) => PREC_CLOSURE,
ExprKind::Closure(..) => ExprPrecedence::Closure,

ExprKind::Break(..)
| ExprKind::Continue(..)
| ExprKind::Ret(..)
| ExprKind::Yield(..)
| ExprKind::Yeet(..)
| ExprKind::Become(..) => PREC_JUMP,
| ExprKind::Become(..) => ExprPrecedence::Jump,

// `Range` claims to have higher precedence than `Assign`, but `x .. x = x` fails to
// parse, instead of parsing as `(x .. x) = x`. Giving `Range` a lower precedence
// ensures that `pprust` will add parentheses in the right places to get the desired
// parse.
ExprKind::Range(..) => PREC_RANGE,
ExprKind::Range(..) => ExprPrecedence::Range,

// Binop-like expr kinds, handled by `AssocOp`.
ExprKind::Binary(op, ..) => AssocOp::from_ast_binop(op.node).precedence() as i8,
ExprKind::Cast(..) => AssocOp::As.precedence() as i8,
ExprKind::Binary(op, ..) => AssocOp::from_ast_binop(op.node).precedence(),
ExprKind::Cast(..) => ExprPrecedence::Cast,

ExprKind::Assign(..) |
ExprKind::AssignOp(..) => AssocOp::Assign.precedence() as i8,
ExprKind::AssignOp(..) => ExprPrecedence::Assign,

// Unary, prefix
ExprKind::AddrOf(..)
Expand All @@ -1348,7 +1346,7 @@ impl Expr {
// need parens sometimes. E.g. we can print `(let _ = a) && b` as `let _ = a && b`
// but we need to print `(let _ = a) < b` as-is with parens.
| ExprKind::Let(..)
| ExprKind::Unary(..) => PREC_PREFIX,
| ExprKind::Unary(..) => ExprPrecedence::Prefix,

// Never need parens
ExprKind::Array(_)
Expand Down Expand Up @@ -1381,7 +1379,7 @@ impl Expr {
| ExprKind::Underscore
| ExprKind::While(..)
| ExprKind::Err(_)
| ExprKind::Dummy => PREC_UNAMBIGUOUS,
| ExprKind::Dummy => ExprPrecedence::Unambiguous,
}
}

Expand Down
75 changes: 51 additions & 24 deletions compiler/rustc_ast/src/util/parser.rs
Original file line number Diff line number Diff line change
Expand Up @@ -128,21 +128,21 @@ impl AssocOp {
}

/// Gets the precedence of this operator
pub fn precedence(&self) -> usize {
pub fn precedence(&self) -> ExprPrecedence {
use AssocOp::*;
match *self {
As => 14,
Multiply | Divide | Modulus => 13,
Add | Subtract => 12,
ShiftLeft | ShiftRight => 11,
BitAnd => 10,
BitXor => 9,
BitOr => 8,
Less | Greater | LessEqual | GreaterEqual | Equal | NotEqual => 7,
LAnd => 6,
LOr => 5,
DotDot | DotDotEq => 4,
Assign | AssignOp(_) => 2,
As => ExprPrecedence::Cast,
Multiply | Divide | Modulus => ExprPrecedence::Product,
Add | Subtract => ExprPrecedence::Sum,
ShiftLeft | ShiftRight => ExprPrecedence::Shift,
BitAnd => ExprPrecedence::BitAnd,
BitXor => ExprPrecedence::BitXor,
BitOr => ExprPrecedence::BitOr,
Less | Greater | LessEqual | GreaterEqual | Equal | NotEqual => ExprPrecedence::Compare,
LAnd => ExprPrecedence::LAnd,
LOr => ExprPrecedence::LOr,
DotDot | DotDotEq => ExprPrecedence::Range,
Assign | AssignOp(_) => ExprPrecedence::Assign,
}
}

Expand Down Expand Up @@ -229,26 +229,53 @@ impl AssocOp {
}
}

pub const PREC_CLOSURE: i8 = -40;
pub const PREC_JUMP: i8 = -30;
pub const PREC_RANGE: i8 = -10;
// The range 2..=14 is reserved for AssocOp binary operator precedences.
pub const PREC_PREFIX: i8 = 50;
pub const PREC_UNAMBIGUOUS: i8 = 60;
pub const PREC_FORCE_PAREN: i8 = 100;
#[derive(Clone, Copy, PartialEq, PartialOrd)]
pub enum ExprPrecedence {
Closure,
// return, break, yield
Jump,
// = += -= *= /= %= &= |= ^= <<= >>=
Assign,
// .. ..=
Range,
// ||
LOr,
// &&
LAnd,
// == != < > <= >=
Compare,
// |
BitOr,
// ^
BitXor,
// &
BitAnd,
// << >>
Shift,
// + -
Sum,
// * / %
Product,
// as
Cast,
// unary - * ! & &mut
Prefix,
// paths, loops, function calls, array indexing, field expressions, method calls
Unambiguous,
}

/// In `let p = e`, operators with precedence `<=` this one requires parentheses in `e`.
pub fn prec_let_scrutinee_needs_par() -> usize {
AssocOp::LAnd.precedence()
pub fn prec_let_scrutinee_needs_par() -> ExprPrecedence {
ExprPrecedence::LAnd
}

/// Suppose we have `let _ = e` and the `order` of `e`.
/// Is the `order` such that `e` in `let _ = e` needs parentheses when it is on the RHS?
///
/// Conversely, suppose that we have `(let _ = a) OP b` and `order` is that of `OP`.
/// Can we print this as `let _ = a OP b`?
pub fn needs_par_as_let_scrutinee(order: i8) -> bool {
order <= prec_let_scrutinee_needs_par() as i8
pub fn needs_par_as_let_scrutinee(order: ExprPrecedence) -> bool {
order <= prec_let_scrutinee_needs_par()
}

/// Expressions that syntactically contain an "exterior" struct literal i.e., not surrounded by any
Expand Down
Loading

0 comments on commit d49be02

Please sign in to comment.