Skip to content

Commit

Permalink
Unrolled build for rust-lang#123091
Browse files Browse the repository at this point in the history
Rollup merge of rust-lang#123091 - Bryanskiy:delegation-fixes, r=petrochenkov

Delegation: fix ICE on wrong `self` resolution

fixes rust-lang#122874

Delegation item should be wrapped in a `rib` to behave like a regular function during name resolution.

r? `@petrochenkov`
  • Loading branch information
rust-timer committed Mar 26, 2024
2 parents 536606b + 17c6101 commit 0d06245
Show file tree
Hide file tree
Showing 3 changed files with 145 additions and 11 deletions.
53 changes: 42 additions & 11 deletions compiler/rustc_resolve/src/late.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2531,7 +2531,17 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
}

ItemKind::Delegation(ref delegation) => {
self.resolve_delegation(delegation);
let span = delegation.path.segments.last().unwrap().ident.span;
self.with_generic_param_rib(
&[],
RibKind::Item(HasGenericParams::Yes(span), def_kind),
LifetimeRibKind::Generics {
binder: item.id,
kind: LifetimeBinderKind::Function,
span,
},
|this| this.resolve_delegation(delegation),
);
}

ItemKind::ExternCrate(..) => {}
Expand Down Expand Up @@ -2819,7 +2829,16 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
walk_assoc_item(self, generics, LifetimeBinderKind::Function, item);
}
AssocItemKind::Delegation(delegation) => {
self.resolve_delegation(delegation);
self.with_generic_param_rib(
&[],
RibKind::AssocItem,
LifetimeRibKind::Generics {
binder: item.id,
kind: LifetimeBinderKind::Function,
span: delegation.path.segments.last().unwrap().ident.span,
},
|this| this.resolve_delegation(delegation),
);
}
AssocItemKind::Type(box TyAlias { generics, .. }) => self
.with_lifetime_rib(LifetimeRibKind::AnonymousReportError, |this| {
Expand Down Expand Up @@ -3069,16 +3088,28 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
}
AssocItemKind::Delegation(box delegation) => {
debug!("resolve_implementation AssocItemKind::Delegation");
self.check_trait_item(
item.id,
item.ident,
&item.kind,
ValueNS,
item.span,
seen_trait_items,
|i, s, c| MethodNotMemberOfTrait(i, s, c),
self.with_generic_param_rib(
&[],
RibKind::AssocItem,
LifetimeRibKind::Generics {
binder: item.id,
kind: LifetimeBinderKind::Function,
span: delegation.path.segments.last().unwrap().ident.span,
},
|this| {
this.check_trait_item(
item.id,
item.ident,
&item.kind,
ValueNS,
item.span,
seen_trait_items,
|i, s, c| MethodNotMemberOfTrait(i, s, c),
);

this.resolve_delegation(delegation)
},
);
self.resolve_delegation(delegation);
}
AssocItemKind::MacCall(_) => {
panic!("unexpanded macro in resolve!")
Expand Down
38 changes: 38 additions & 0 deletions tests/ui/delegation/target-expr.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
#![feature(fn_delegation)]
#![allow(incomplete_features)]

trait Trait {
fn static_method(x: i32) -> i32 { x }
}

struct F;

struct S(F);
impl Trait for S {}

fn foo(x: i32) -> i32 { x }

fn bar<T: Default>(_: T) {
reuse Trait::static_method {
//~^ ERROR delegation with early bound generics is not supported yet
//~| ERROR mismatched types
let _ = T::Default();
//~^ ERROR can't use generic parameters from outer item
}
}

fn main() {
let y = 0;
reuse <S as Trait>::static_method {
let x = y;
//~^ ERROR can't capture dynamic environment in a fn item
foo(self);

let reuse_ptr: fn(i32) -> i32 = static_method;
reuse_ptr(0)
}
self.0;
//~^ ERROR expected value, found module `self`
let z = x;
//~^ ERROR cannot find value `x` in this scope
}
65 changes: 65 additions & 0 deletions tests/ui/delegation/target-expr.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
error[E0401]: can't use generic parameters from outer item
--> $DIR/target-expr.rs:19:17
|
LL | fn bar<T: Default>(_: T) {
| - type parameter from outer item
LL | reuse Trait::static_method {
| - help: try introducing a local generic parameter here: `T,`
...
LL | let _ = T::Default();
| ^^^^^^^^^^ use of generic parameter from outer item

error[E0434]: can't capture dynamic environment in a fn item
--> $DIR/target-expr.rs:27:17
|
LL | let x = y;
| ^
|
= help: use the `|| { ... }` closure form instead

error[E0424]: expected value, found module `self`
--> $DIR/target-expr.rs:34:5
|
LL | fn main() {
| ---- this function can't have a `self` parameter
...
LL | self.0;
| ^^^^ `self` value is a keyword only available in methods with a `self` parameter

error[E0425]: cannot find value `x` in this scope
--> $DIR/target-expr.rs:36:13
|
LL | let z = x;
| ^
|
help: the binding `x` is available in a different scope in the same function
--> $DIR/target-expr.rs:27:13
|
LL | let x = y;
| ^

error: delegation with early bound generics is not supported yet
--> $DIR/target-expr.rs:16:18
|
LL | fn static_method(x: i32) -> i32 { x }
| ------------------------------- callee defined here
...
LL | reuse Trait::static_method {
| ^^^^^^^^^^^^^

error[E0308]: mismatched types
--> $DIR/target-expr.rs:16:32
|
LL | reuse Trait::static_method {
| ________________________________^
LL | |
LL | |
LL | | let _ = T::Default();
LL | |
LL | | }
| |_____^ expected `i32`, found `()`

error: aborting due to 6 previous errors

Some errors have detailed explanations: E0308, E0401, E0424, E0425, E0434.
For more information about an error, try `rustc --explain E0308`.

0 comments on commit 0d06245

Please sign in to comment.