ty::pretty: prevent infinite recursion for extern crate paths.

This commit is contained in:
Eduard-Mihai Burtescu 2021-10-10 18:50:44 +03:00
parent 152e40377a
commit f14e8dd4e7
6 changed files with 74 additions and 1 deletions

View file

@ -360,7 +360,14 @@ pub trait PrettyPrinter<'tcx>:
return Ok((self.path_crate(cnum)?, true));
}
return Ok((self.print_def_path(def_id, &[])?, true));
// Disable `try_print_trimmed_def_path` behavior within
// the `print_def_path` call, to avoid infinite recursion
// in cases where the `extern crate foo` has non-trivial
// parents, e.g. it's nested in `impl foo::Trait for Bar`
// (see also issues #55779 and #87932).
self = with_no_visible_paths(|| self.print_def_path(def_id, &[]))?;
return Ok((self, true));
}
(ExternCrateSource::Path, LOCAL_CRATE) => {
return Ok((self.path_crate(cnum)?, true));

View file

@ -0,0 +1 @@
pub trait Trait { fn no_op(&self); }

View file

@ -0,0 +1,3 @@
pub trait Deserialize {
fn deserialize();
}

View file

@ -0,0 +1,29 @@
// run-pass
// edition:2018
// aux-crate:issue_55779_extern_trait=issue-55779-extern-trait.rs
use issue_55779_extern_trait::Trait;
struct Local;
struct Helper;
impl Trait for Local {
fn no_op(&self)
{
// (Unused) extern crate declaration necessary to reproduce bug
extern crate issue_55779_extern_trait;
// This one works
// impl Trait for Helper { fn no_op(&self) { } }
// This one infinite-loops
const _IMPL_SERIALIZE_FOR_HELPER: () = {
// (extern crate can also appear here to reproduce bug,
// as in originating example from serde)
impl Trait for Helper { fn no_op(&self) { } }
};
}
}
fn main() { }

View file

@ -0,0 +1,15 @@
// edition:2018
// aux-crate:issue_87932_a=issue-87932-a.rs
pub struct A {}
impl issue_87932_a::Deserialize for A {
fn deserialize() {
extern crate issue_87932_a as _a;
}
}
fn main() {
A::deserialize();
//~^ ERROR no function or associated item named `deserialize` found for struct `A`
}

View file

@ -0,0 +1,18 @@
error[E0599]: no function or associated item named `deserialize` found for struct `A` in the current scope
--> $DIR/issue-87932.rs:13:8
|
LL | pub struct A {}
| ------------ function or associated item `deserialize` not found for this
...
LL | A::deserialize();
| ^^^^^^^^^^^ function or associated item not found in `A`
|
= help: items from traits can only be used if the trait is in scope
help: the following trait is implemented but not in scope; perhaps add a `use` for it:
|
LL | use <crate::A as issue_87932_a::Deserialize>::deserialize::_a::Deserialize;
|
error: aborting due to previous error
For more information about this error, try `rustc --explain E0599`.