-
Notifications
You must be signed in to change notification settings - Fork 12.8k
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
*Syntactically* permit visibilities on trait items & enum variants #66183
Conversation
This comment has been minimized.
This comment has been minimized.
eff6bbe
to
24ccd5b
Compare
| ^^^ unexpected token | ||
| -^^^^^^ expected one of 7 possible tokens here | ||
| | | ||
| help: `}` may belong here |
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.
This is... unfortunate.
LGTM, but saw that @petrochenkov self-assigned, letting him sign off on it. |
So, I agree with the (direction of) the change for trait items, because that's a part of the syntactic unification of free/trait/impl/foreign items. I don't agree with accepting empty |
This comment has been minimized.
This comment has been minimized.
21e6c21
to
a428ba2
Compare
:vis
before trait item & enum variant
@petrochenkov Adjusted the PR to syntactically accept any visibility on enum variants & trait items now (discussion in https://rust-lang.zulipchat.com/#narrow/stream/213817-t-lang/topic/.2366183 -- cc @rust-lang/lang again in case anyone missed it) |
This comment has been minimized.
This comment has been minimized.
LGTM, but needs commit squashing and a pprust test update. |
Let's pass this through an FCP, I'm not sure the enum variant change has enough motivation and thus don't want to take responsibility for it. |
Your PR failed (pretty log, raw log). Through arcane magic we have determined that the following fragments from the build log may contain information about the problem. Click to expand the log.
I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact |
💔 Test failed - checks-azure |
@bors retry |
…rochenkov *Syntactically* permit visibilities on trait items & enum variants Fixes rust-lang#65041 Suppose we have `$vis trait_item` or `$vis enum_variant` and `$vis` is a `:vis` macro fragment. Before this PR, this would fail to parse. This is now instead allowed as per language team consensus in rust-lang#65041 (comment). (See added tests for elaboration.) Moreover, we now also permit visibility modifiers on trait items & enum variants *syntactically* but reject them with semantic checks (in `ast_validation`): ```rust #[cfg(FALSE)] trait Foo { pub fn bar(); } // OK #[cfg(FALSE)] enum E { pub U } // OK ```
⌛ Testing commit 9a88364 with merge 6e59650f84e783a1753508623e68e81f58175a85... |
@bors retry in r0llup |
Rollup of 8 pull requests Successful merges: - #66183 (*Syntactically* permit visibilities on trait items & enum variants) - #66566 (Document pitfall with `impl PartialEq<B> for A`) - #66575 (Remove pretty printing of specific nodes in AST) - #66587 (Handle statics in MIR as const pointers) - #66619 (follow the convention in this file to use third-person singular verbs) - #66633 (Error code's long explanation cleanup) - #66637 (fix reoccuring typo: dereferencable -> dereferenceable) - #66639 (resolve: more declarative `fresh_binding`) Failed merges: r? @ghost
@Centril What specifically about this should be mentioned in the release notes? For practical purposes nothing has really changed on the user facing side as far as I can tell, since they will get an error no matter what. |
@XAMPPRocky Most of the time nothing has changed for users. However, in niche circumstances, e.g. with a procedural macro, you can do e.g.: #[my_funky_attr]
enum Foo { pub Bar }
// ...expands to the following because `my_funky_attr` is funky:
struct Bar;
enum Foo { Bar(Bar) } The same logic applies to trait items. |
Version 1.41.0 (2020-01-30) =========================== Language -------- - [You can now pass type parameters to foreign items when implementing traits.][65879] E.g. You can now write `impl<T> From<Foo> for Vec<T> {}`. - [You can now arbitrarily nest receiver types in the `self` position.][64325] E.g. you can now write `fn foo(self: Box<Box<Self>>) {}`. Previously only `Self`, `&Self`, `&mut Self`, `Arc<Self>`, `Rc<Self>`, and `Box<Self>` were allowed. - [You can now use any valid identifier in a `format_args` macro.][66847] Previously identifiers starting with an underscore were not allowed. - [Visibility modifiers (e.g. `pub`) are now syntactically allowed on trait items and enum variants.][66183] These are still rejected semantically, but can be seen and parsed by procedural macros and conditional compilation. Compiler -------- - [Rustc will now warn if you have unused loop `'label`s.][66325] - [Removed support for the `i686-unknown-dragonfly` target.][67255] - [Added tier 3 support\* for the `riscv64gc-unknown-linux-gnu` target.][66661] - [You can now pass an arguments file passing the `@path` syntax to rustc.][66172] Note that the format differs somewhat from what is found in other tooling; please see [the documentation][argfile-docs] for more information. - [You can now provide `--extern` flag without a path, indicating that it is available from the search path or specified with an `-L` flag.][64882] \* Refer to Rust's [platform support page][forge-platform-support] for more information on Rust's tiered platform support. [argfile-docs]: https://doc.rust-lang.org/nightly/rustc/command-line-arguments.html#path-load-command-line-flags-from-a-path Libraries --------- - [The `core::panic` module is now stable.][66771] It was already stable through `std`. - [`NonZero*` numerics now implement `From<NonZero*>` if it's a smaller integer width.][66277] E.g. `NonZeroU16` now implements `From<NonZeroU8>`. - [`MaybeUninit<T>` now implements `fmt::Debug`.][65013] Stabilized APIs --------------- - [`Result::map_or`] - [`Result::map_or_else`] - [`std::rc::Weak::weak_count`] - [`std::rc::Weak::strong_count`] - [`std::sync::Weak::weak_count`] - [`std::sync::Weak::strong_count`] Cargo ----- - [Cargo will now document all the private items for binary crates by default.][cargo/7593] - [`cargo-install` will now reinstall the package if it detects that it is out of date.][cargo/7560] - [Cargo.lock now uses a more git friendly format that should help to reduce merge conflicts.][cargo/7579] - [You can now override specific dependencies's build settings][cargo/7591] E.g. `[profile.dev.overrides.image] opt-level = 2` sets the `image` crate's optimisation level to `2` for debug builds. You can also use `[profile.<profile>.build_overrides]` to override build scripts and their dependencies. Misc ---- - [You can now specify `edition` in documentation code blocks to compile the block for that edition.][66238] E.g. `edition2018` tells rustdoc that the code sample should be compiled the 2018 edition of Rust. - [You can now provide custom themes to rustdoc with `--theme`, and check the current theme with `--check-theme`.][54733] - [You can use `#[cfg(doc)]` to compile an item when building documentation.][61351] Compatibility Notes ------------------- - [As previously announced 1.41.0 will be the last tier 1 release for 32-bit Apple targets.][apple-32bit-drop] This means that the source code is still available to build, but the targets are no longer being tested and release binaries for those platforms will no longer be distributed by the Rust project. Please refer to the linked blog post for more information. [54733]: rust-lang/rust#54733 [61351]: rust-lang/rust#61351 [67255]: rust-lang/rust#67255 [66661]: rust-lang/rust#66661 [66771]: rust-lang/rust#66771 [66847]: rust-lang/rust#66847 [66238]: rust-lang/rust#66238 [66277]: rust-lang/rust#66277 [66325]: rust-lang/rust#66325 [66172]: rust-lang/rust#66172 [66183]: rust-lang/rust#66183 [65879]: rust-lang/rust#65879 [65013]: rust-lang/rust#65013 [64882]: rust-lang/rust#64882 [64325]: rust-lang/rust#64325 [cargo/7560]: rust-lang/cargo#7560 [cargo/7579]: rust-lang/cargo#7579 [cargo/7591]: rust-lang/cargo#7591 [cargo/7593]: rust-lang/cargo#7593 [`Result::map_or_else`]: https://doc.rust-lang.org/std/result/enum.Result.html#method.map_or_else [`Result::map_or`]: https://doc.rust-lang.org/std/result/enum.Result.html#method.map_or [`std::rc::Weak::weak_count`]: https://doc.rust-lang.org/std/rc/struct.Weak.html#method.weak_count [`std::rc::Weak::strong_count`]: https://doc.rust-lang.org/std/rc/struct.Weak.html#method.strong_count [`std::sync::Weak::weak_count`]: https://doc.rust-lang.org/std/sync/struct.Weak.html#method.weak_count [`std::sync::Weak::strong_count`]: https://doc.rust-lang.org/std/sync/struct.Weak.html#method.strong_count [apple-32bit-drop]: https://blog.rust-lang.org/2020/01/03/reducing-support-for-32-bit-apple-targets.html
Concrete use case: DSL for a Java-style enum (https://docs.oracle.com/javase/tutorial/java/javaOO/enum.html). Java: public enum Planet {
MERCURY (3.301e+23, 2.440e+6),
VENUS (4.868e+24, 6.052e+6),
EARTH (5.972e+24, 6.371e+6),
MARS (6.417e+23, 3.390e+6),
JUPITER (1.898e+27, 6.991e+7),
SATURN (5.683e+26, 5.823e+7),
URANUS (8.681e+25, 2.536e+7),
NEPTUNE (1.024e+26, 2.462e+7);
private final double mass;
private final double radius;
Planet(double mass, double radius) {
this.mass = mass;
this.radius = radius;
}
// additional methods
} Rust: #[aux_enum_data]
pub enum Planet {
Mercury = (3.301e+23, 2.440e+6),
Venus = (4.868e+24, 6.052e+6),
Earth = (5.972e+24, 6.371e+6),
Mars = (6.417e+23, 3.390e+6),
Jupiter = (1.898e+27, 6.991e+7),
Saturn = (5.683e+26, 5.823e+7),
Uranus = (8.681e+25, 2.536e+7),
Neptune = (1.024e+26, 2.462e+7),
pub PlanetFacts {
pub mass: f64,
pub radius: f64,
}
} Expands to: #[derive(Copy, Clone, PartialEq, Eq, Hash)]
pub enum Planet {
Mercury,
Venus,
Earth,
Mars,
Jupiter,
Saturn,
Uranus,
Neptune,
}
pub struct PlanetFacts {
pub mass: f64,
pub radius: f64,
}
impl std::ops::Deref for Planet {
type Target = PlanetFacts;
fn deref(&self) -> &Self::Target {
match self {
Planet::Mercury => &PlanetFacts { mass: 3.301e+23, radius: 2.440e+6 },
Planet::Venus => &PlanetFacts { mass: 4.868e+24, radius: 6.052e+6 },
Planet::Earth => &PlanetFacts { mass: 5.972e+24, radius: 6.371e+6 },
Planet::Mars => &PlanetFacts { mass: 6.417e+23, radius: 3.390e+6 },
Planet::Jupiter => &PlanetFacts { mass: 1.898e+27, radius: 6.991e+7 },
Planet::Saturn => &PlanetFacts { mass: 5.683e+26, radius: 5.823e+7 },
Planet::Uranus => &PlanetFacts { mass: 8.681e+25, radius: 2.536e+7 },
Planet::Neptune => &PlanetFacts { mass: 1.024e+26, radius: 2.462e+7 },
}
}
} println!("1 earth mass = {} kg", Earth.mass); |
Syntactically permit unsafety on mods Similar to rust-lang#66183; we will accept these constructs syntactically but reject with a semantic check after macro expansion if a proc macro hasn't replaced it with something else meaningful to Rust. ```rust #[mymacro] unsafe mod m { ... } #[mymacro] unsafe extern "C++" { ... } ``` The intention is that this might be used as a kind of "item-level unsafe" in attribute macro DSLs -- holding things which are unsafe to declare but potentially safe to use. For example I look forward to using this in https://github.com/dtolnay/cxx. In the absence of a procedural macro rewriting them to something else, they'll continue to be rejected at compile time though with a better error message than before. ### Before: ```console error: expected item, found keyword `unsafe` --> src/main.rs:1:1 | 1 | unsafe mod m { | ^^^^^^ expected item ``` ### After: ```console error: module cannot be declared unsafe --> src/main.rs:1:1 | 1 | unsafe mod m { | ^^^^^^ error: extern block cannot be declared unsafe --> src/main.rs:4:1 | 4 | unsafe extern "C++" { | ^^^^^^ ``` Closes rust-lang#68048.
Fixes #65041
Suppose we have
$vis trait_item
or$vis enum_variant
and$vis
is a:vis
macro fragment. Before this PR, this would fail to parse. This is now instead allowed as per language team consensus in #65041 (comment). (See added tests for elaboration.)Moreover, we now also permit visibility modifiers on trait items & enum variants syntactically but reject them with semantic checks (in
ast_validation
):