Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 40 additions & 13 deletions compiler/rustc_resolve/src/ident.rs
Original file line number Diff line number Diff line change
Expand Up @@ -645,11 +645,20 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
return None;
}

// preemptively look for ambiguities for panic macros to ensure we don't
// speculatively resolve to a non-prelude item when an ambiguity that we'd
// downgrade is present
let is_issue_147319_hack = || ctxt.edition()
<= Edition::Edition2024
&& matches!(orig_ident.name, sym::panic)
&& (this.is_specific_builtin_macro(binding.res(), sym::std_panic) || this.is_specific_builtin_macro(binding.res(), sym::core_panic));
let finalizing = !matches!(finalize, None | Some(Finalize { stage: Stage::Late, .. }));

// Below we report various ambiguity errors.
// We do not need to report them if we are either in speculative resolution,
// or in late resolution when everything is already imported and expanded
// and no ambiguities exist.
if matches!(finalize, None | Some(Finalize { stage: Stage::Late, .. })) {
if !finalizing && !is_issue_147319_hack() {
return Some(Ok(binding));
}

Expand Down Expand Up @@ -720,8 +729,20 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
let is_issue_147319_hack = ctxt.edition()
<= Edition::Edition2024
&& matches!(orig_ident.name, sym::panic)
&& this.is_builtin_macro(binding.res())
&& this.is_builtin_macro(innermost_binding.res());
&& matches!(scope, Scope::StdLibPrelude)
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this handles the case where we're firing on two globs where neither is from the implicit prelude import (the glob vs multiouter test) and turning it into a hard error. We probably want this to be a warning but I think the tiebreak logic as I wrote it may be broken in this case and depend on import expansion order.

&& ((this.is_specific_builtin_macro(
binding.res(),
sym::std_panic,
) && this.is_specific_builtin_macro(
innermost_binding.res(),
sym::core_panic,
)) || (this.is_specific_builtin_macro(
binding.res(),
sym::core_panic,
) && this.is_specific_builtin_macro(
innermost_binding.res(),
sym::std_panic,
)));

let warning = if is_issue_147319_hack {
Some(AmbiguityWarning::PanicImport)
Expand All @@ -740,16 +761,22 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
AmbiguityErrorMisc::None
}
};
this.get_mut().ambiguity_errors.push(AmbiguityError {
kind,
ident: orig_ident,
b1: innermost_binding,
b2: binding,
warning,
misc1: misc(innermost_flags),
misc2: misc(flags),
});
return Some(Ok(innermost_binding));
if finalizing {
this.get_mut().ambiguity_errors.push(AmbiguityError {
kind,
ident: orig_ident,
b1: innermost_binding,
b2: binding,
warning,
misc1: misc(innermost_flags),
misc2: misc(flags),
});
}
if is_issue_147319_hack {
return Some(Ok(binding));
} else {
return Some(Ok(innermost_binding));
}
}
}
} else {
Expand Down
4 changes: 4 additions & 0 deletions compiler/rustc_resolve/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1857,6 +1857,10 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
self.get_macro(res).is_some_and(|macro_data| macro_data.ext.builtin_name.is_some())
}

fn is_specific_builtin_macro(&self, res: Res, symbol: Symbol) -> bool {
self.get_macro(res).is_some_and(|macro_data| macro_data.ext.builtin_name == Some(symbol))
}

fn macro_def(&self, mut ctxt: SyntaxContext) -> DefId {
loop {
match ctxt.outer_expn_data().macro_def_id {
Expand Down
5 changes: 1 addition & 4 deletions tests/ui/imports/ambiguous-panic-glob-vs-multiouter.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
//@ edition: 2024
//@ check-pass
#![crate_type = "lib"]
mod m1 {
pub use core::prelude::v1::*;
Expand All @@ -14,7 +13,5 @@ use m2::*;
fn foo() {
use m1::*;

panic!();
//~^ WARN: `panic` is ambiguous [ambiguous_panic_imports]
//~| WARN: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
panic!(); //~ ERROR: `panic` is ambiguous [E0659]
}
14 changes: 6 additions & 8 deletions tests/ui/imports/ambiguous-panic-glob-vs-multiouter.stderr
Original file line number Diff line number Diff line change
@@ -1,25 +1,23 @@
warning: `panic` is ambiguous
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:20:5
error[E0659]: `panic` is ambiguous
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:19:5
|
LL | panic!();
| ^^^^^ ambiguous name
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
= note: for more information, see issue #147319 <https://github.com/rust-lang/rust/issues/147319>
= note: ambiguous because of a conflict between a name from a glob import and an outer scope during import or macro resolution
note: `panic` could refer to the macro imported here
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:15:9
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:14:9
|
LL | use m1::*;
| ^^^^^
= help: consider adding an explicit import of `panic` to disambiguate
note: `panic` could also refer to the macro imported here
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:13:5
--> $DIR/ambiguous-panic-glob-vs-multiouter.rs:12:5
|
LL | use m2::*;
| ^^^^^
= help: use `crate::panic` to refer to this macro unambiguously
= note: `#[warn(ambiguous_panic_imports)]` (part of `#[warn(future_incompatible)]`) on by default

warning: 1 warning emitted
error: aborting due to 1 previous error

For more information about this error, try `rustc --explain E0659`.
4 changes: 2 additions & 2 deletions tests/ui/imports/ambiguous-panic-pick-core.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
//@ edition: 2018
//@ check-pass
#![crate_type = "lib"]
#![no_std]

Expand All @@ -10,5 +9,6 @@ fn f() {
panic!(std::string::String::new());
//~^ WARN: `panic` is ambiguous [ambiguous_panic_imports]
//~| WARN: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
//~| WARN: panic message is not a string literal [non_fmt_panics]
//~| ERROR: mismatched types [E0308]

}
27 changes: 15 additions & 12 deletions tests/ui/imports/ambiguous-panic-pick-core.stderr
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
warning: `panic` is ambiguous
--> $DIR/ambiguous-panic-pick-core.rs:10:5
--> $DIR/ambiguous-panic-pick-core.rs:9:5
|
LL | panic!(std::string::String::new());
| ^^^^^ ambiguous name
Expand All @@ -8,7 +8,7 @@ LL | panic!(std::string::String::new());
= note: for more information, see issue #147319 <https://github.com/rust-lang/rust/issues/147319>
= note: ambiguous because of a conflict between a name from a glob import and an outer scope during import or macro resolution
note: `panic` could refer to the macro imported here
--> $DIR/ambiguous-panic-pick-core.rs:7:5
--> $DIR/ambiguous-panic-pick-core.rs:6:5
|
LL | use ::std::prelude::v1::*;
| ^^^^^^^^^^^^^^^^^^^^^
Expand All @@ -18,19 +18,22 @@ note: `panic` could also refer to a macro from prelude
--> $SRC_DIR/core/src/prelude/mod.rs:LL:COL
= note: `#[warn(ambiguous_panic_imports)]` (part of `#[warn(future_incompatible)]`) on by default

warning: panic message is not a string literal
--> $DIR/ambiguous-panic-pick-core.rs:10:12
error[E0308]: mismatched types
--> $DIR/ambiguous-panic-pick-core.rs:9:12
|
LL | panic!(std::string::String::new());
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
| -------^^^^^^^^^^^^^^^^^^^^^^^^^^-
| | |
| | expected `&str`, found `String`
| arguments to this function are incorrect
|
= note: this usage of `panic!()` is deprecated; it will be a hard error in Rust 2021
= note: for more information, see <https://doc.rust-lang.org/edition-guide/rust-2021/panic-macro-consistency.html>
= note: `#[warn(non_fmt_panics)]` (part of `#[warn(rust_2021_compatibility)]`) on by default
help: add a "{}" format string to `Display` the message
note: function defined here
--> $SRC_DIR/core/src/panicking.rs:LL:COL
help: consider borrowing here
|
LL | panic!("{}", std::string::String::new());
| +++++
LL | panic!(&std::string::String::new());
| +

warning: 2 warnings emitted
error: aborting due to 1 previous error; 1 warning emitted

For more information about this error, try `rustc --explain E0308`.
3 changes: 2 additions & 1 deletion tests/ui/imports/ambiguous-panic-pick-std.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
//@ edition: 2018
//@ check-pass
#![crate_type = "lib"]
use ::core::prelude::v1::*;

Expand All @@ -7,5 +8,5 @@ fn f() {
panic!(std::string::String::new());
//~^ WARN: `panic` is ambiguous [ambiguous_panic_imports]
//~| WARN: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
//~| ERROR: mismatched types [E0308]
//~| WARN: panic message is not a string literal [non_fmt_panics]
}
27 changes: 12 additions & 15 deletions tests/ui/imports/ambiguous-panic-pick-std.stderr
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
warning: `panic` is ambiguous
--> $DIR/ambiguous-panic-pick-std.rs:7:5
--> $DIR/ambiguous-panic-pick-std.rs:8:5
|
LL | panic!(std::string::String::new());
| ^^^^^ ambiguous name
Expand All @@ -8,7 +8,7 @@ LL | panic!(std::string::String::new());
= note: for more information, see issue #147319 <https://github.com/rust-lang/rust/issues/147319>
= note: ambiguous because of a conflict between a name from a glob import and an outer scope during import or macro resolution
note: `panic` could refer to the macro imported here
--> $DIR/ambiguous-panic-pick-std.rs:3:5
--> $DIR/ambiguous-panic-pick-std.rs:4:5
|
LL | use ::core::prelude::v1::*;
| ^^^^^^^^^^^^^^^^^^^^^^
Expand All @@ -18,22 +18,19 @@ note: `panic` could also refer to a macro from prelude
--> $SRC_DIR/std/src/prelude/mod.rs:LL:COL
= note: `#[warn(ambiguous_panic_imports)]` (part of `#[warn(future_incompatible)]`) on by default

error[E0308]: mismatched types
--> $DIR/ambiguous-panic-pick-std.rs:7:12
warning: panic message is not a string literal
--> $DIR/ambiguous-panic-pick-std.rs:8:12
|
LL | panic!(std::string::String::new());
| -------^^^^^^^^^^^^^^^^^^^^^^^^^^-
| | |
| | expected `&str`, found `String`
| arguments to this function are incorrect
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
|
note: function defined here
--> $SRC_DIR/core/src/panicking.rs:LL:COL
help: consider borrowing here
= note: this usage of `panic!()` is deprecated; it will be a hard error in Rust 2021
= note: for more information, see <https://doc.rust-lang.org/edition-guide/rust-2021/panic-macro-consistency.html>
= note: `#[warn(non_fmt_panics)]` (part of `#[warn(rust_2021_compatibility)]`) on by default
help: add a "{}" format string to `Display` the message
|
LL | panic!(&std::string::String::new());
| +
LL | panic!("{}", std::string::String::new());
| +++++

error: aborting due to 1 previous error; 1 warning emitted
warning: 2 warnings emitted

For more information about this error, try `rustc --explain E0308`.
3 changes: 1 addition & 2 deletions tests/ui/imports/ambiguous-panic-rename-builtin.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,5 @@ use m1::*;
fn xx() {
panic!();
//~^ ERROR: `env!()` takes 1 or 2 arguments
//~| WARN: `panic` is ambiguous [ambiguous_panic_imports]
//~| WARN: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
//~| ERROR: `panic` is ambiguous [E0659]
}
8 changes: 3 additions & 5 deletions tests/ui/imports/ambiguous-panic-rename-builtin.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,12 @@ error: `env!()` takes 1 or 2 arguments
LL | panic!();
| ^^^^^^^^

warning: `panic` is ambiguous
error[E0659]: `panic` is ambiguous
--> $DIR/ambiguous-panic-rename-builtin.rs:12:5
|
LL | panic!();
| ^^^^^ ambiguous name
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
= note: for more information, see issue #147319 <https://github.com/rust-lang/rust/issues/147319>
= note: ambiguous because of a conflict between a name from a glob import and an outer scope during import or macro resolution
note: `panic` could refer to the macro imported here
--> $DIR/ambiguous-panic-rename-builtin.rs:9:5
Expand All @@ -22,7 +20,7 @@ LL | use m1::*;
= help: or use `crate::panic` to refer to this macro unambiguously
note: `panic` could also refer to a macro from prelude
--> $SRC_DIR/core/src/prelude/mod.rs:LL:COL
= note: `#[warn(ambiguous_panic_imports)]` (part of `#[warn(future_incompatible)]`) on by default

error: aborting due to 1 previous error; 1 warning emitted
error: aborting due to 2 previous errors

For more information about this error, try `rustc --explain E0659`.
Loading