Skip to content

Commit 2600d62

Browse files
Add lookup_probe_for_diagnostic
1 parent 38491c6 commit 2600d62

File tree

5 files changed

+98
-74
lines changed

5 files changed

+98
-74
lines changed

compiler/rustc_hir_typeck/src/callee.rs

+4-6
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use super::method::probe::{IsSuggestion, Mode, ProbeScope};
1+
use super::method::probe::ProbeScope;
22
use super::method::MethodCallee;
33
use super::{Expectation, FnCtxt, TupleArgumentsFlag};
44

@@ -496,16 +496,14 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
496496
// any strange errors. If it's successful, then we'll do a true
497497
// method lookup.
498498
let Ok(pick) = self
499-
.probe_for_name(
500-
Mode::MethodCall,
499+
.lookup_probe_for_diagnostic(
501500
segment.ident,
502-
expected.only_has_type(self),
503-
IsSuggestion(true),
504501
callee_ty,
505-
call_expr.hir_id,
502+
call_expr,
506503
// We didn't record the in scope traits during late resolution
507504
// so we need to probe AllTraits unfortunately
508505
ProbeScope::AllTraits,
506+
expected.only_has_type(self),
509507
) else {
510508
return None;
511509
};

compiler/rustc_hir_typeck/src/demand.rs

+9-12
Original file line numberDiff line numberDiff line change
@@ -303,11 +303,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
303303
// Get the evaluated type *after* calling the method call, so that the influence
304304
// of the arguments can be reflected in the receiver type. The receiver
305305
// expression has the type *before* theis analysis is done.
306-
let ty = match self.lookup_probe(
306+
let ty = match self.lookup_probe_for_diagnostic(
307307
segment.ident,
308308
rcvr_ty,
309309
expr,
310310
probe::ProbeScope::TraitsInScope,
311+
None,
311312
) {
312313
Ok(pick) => pick.self_ty,
313314
Err(_) => rcvr_ty,
@@ -557,14 +558,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
557558
let Some(self_ty) = self.typeck_results.borrow().expr_ty_adjusted_opt(base) else { return; };
558559

559560
let Ok(pick) = self
560-
.probe_for_name(
561-
probe::Mode::MethodCall,
561+
.lookup_probe_for_diagnostic(
562562
path.ident,
563-
None,
564-
probe::IsSuggestion(true),
565563
self_ty,
566-
deref.hir_id,
564+
deref,
567565
probe::ProbeScope::TraitsInScope,
566+
None,
568567
) else {
569568
return;
570569
};
@@ -1835,7 +1834,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
18351834
pub fn check_for_range_as_method_call(
18361835
&self,
18371836
err: &mut Diagnostic,
1838-
expr: &hir::Expr<'_>,
1837+
expr: &hir::Expr<'tcx>,
18391838
checked_ty: Ty<'tcx>,
18401839
expected_ty: Ty<'tcx>,
18411840
) {
@@ -1876,14 +1875,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
18761875
let hir::ExprKind::Path(hir::QPath::Resolved(None, p)) = method_name.kind else { return; };
18771876
let [hir::PathSegment { ident, .. }] = p.segments else { return; };
18781877
let self_ty = self.typeck_results.borrow().expr_ty(start.expr);
1879-
let Ok(_pick) = self.probe_for_name(
1880-
probe::Mode::MethodCall,
1878+
let Ok(_pick) = self.lookup_probe_for_diagnostic(
18811879
*ident,
1882-
expectation,
1883-
probe::IsSuggestion(true),
18841880
self_ty,
1885-
expr.hir_id,
1881+
expr,
18861882
probe::ProbeScope::AllTraits,
1883+
expectation,
18871884
) else { return; };
18881885
let mut sugg = ".";
18891886
let mut span = start.expr.span.between(end.expr.span);

compiler/rustc_hir_typeck/src/expr.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -2431,7 +2431,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
24312431

24322432
fn ban_private_field_access(
24332433
&self,
2434-
expr: &hir::Expr<'_>,
2434+
expr: &hir::Expr<'tcx>,
24352435
expr_t: Ty<'tcx>,
24362436
field: Ident,
24372437
base_did: DefId,
@@ -2462,7 +2462,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
24622462
err.emit();
24632463
}
24642464

2465-
fn ban_take_value_of_method(&self, expr: &hir::Expr<'_>, expr_t: Ty<'tcx>, field: Ident) {
2465+
fn ban_take_value_of_method(&self, expr: &hir::Expr<'tcx>, expr_t: Ty<'tcx>, field: Ident) {
24662466
let mut err = type_error_struct!(
24672467
self.tcx().sess,
24682468
field.span,

compiler/rustc_hir_typeck/src/method/mod.rs

+49-26
Original file line numberDiff line numberDiff line change
@@ -132,18 +132,16 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
132132
msg: &str,
133133
method_name: Ident,
134134
self_ty: Ty<'tcx>,
135-
call_expr: &hir::Expr<'_>,
135+
call_expr: &hir::Expr<'tcx>,
136136
span: Option<Span>,
137137
) {
138138
let params = self
139-
.probe_for_name(
140-
probe::Mode::MethodCall,
139+
.lookup_probe_for_diagnostic(
141140
method_name,
142-
None,
143-
IsSuggestion(true),
144141
self_ty,
145-
call_expr.hir_id,
142+
call_expr,
146143
ProbeScope::TraitsInScope,
144+
None,
147145
)
148146
.map(|pick| {
149147
let sig = self.tcx.fn_sig(pick.item.def_id);
@@ -224,25 +222,30 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
224222
}
225223

226224
// We probe again, taking all traits into account (not only those in scope).
227-
let candidates =
228-
match self.lookup_probe(segment.ident, self_ty, call_expr, ProbeScope::AllTraits) {
229-
// If we find a different result the caller probably forgot to import a trait.
230-
Ok(ref new_pick) if pick.differs_from(new_pick) => {
231-
vec![new_pick.item.container_id(self.tcx)]
232-
}
233-
Err(Ambiguity(ref sources)) => sources
234-
.iter()
235-
.filter_map(|source| {
236-
match *source {
237-
// Note: this cannot come from an inherent impl,
238-
// because the first probing succeeded.
239-
CandidateSource::Impl(def) => self.tcx.trait_id_of_impl(def),
240-
CandidateSource::Trait(_) => None,
241-
}
242-
})
243-
.collect(),
244-
_ => Vec::new(),
245-
};
225+
let candidates = match self.lookup_probe_for_diagnostic(
226+
segment.ident,
227+
self_ty,
228+
call_expr,
229+
ProbeScope::AllTraits,
230+
None,
231+
) {
232+
// If we find a different result the caller probably forgot to import a trait.
233+
Ok(ref new_pick) if pick.differs_from(new_pick) => {
234+
vec![new_pick.item.container_id(self.tcx)]
235+
}
236+
Err(Ambiguity(ref sources)) => sources
237+
.iter()
238+
.filter_map(|source| {
239+
match *source {
240+
// Note: this cannot come from an inherent impl,
241+
// because the first probing succeeded.
242+
CandidateSource::Impl(def) => self.tcx.trait_id_of_impl(def),
243+
CandidateSource::Trait(_) => None,
244+
}
245+
})
246+
.collect(),
247+
_ => Vec::new(),
248+
};
246249

247250
return Err(IllegalSizedBound { candidates, needs_mut, bound_span: span, self_expr });
248251
}
@@ -255,7 +258,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
255258
&self,
256259
method_name: Ident,
257260
self_ty: Ty<'tcx>,
258-
call_expr: &'tcx hir::Expr<'tcx>,
261+
call_expr: &hir::Expr<'_>,
259262
scope: ProbeScope,
260263
) -> probe::PickResult<'tcx> {
261264
let pick = self.probe_for_name(
@@ -271,6 +274,26 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
271274
Ok(pick)
272275
}
273276

277+
pub fn lookup_probe_for_diagnostic(
278+
&self,
279+
method_name: Ident,
280+
self_ty: Ty<'tcx>,
281+
call_expr: &hir::Expr<'_>,
282+
scope: ProbeScope,
283+
return_type: Option<Ty<'tcx>>,
284+
) -> probe::PickResult<'tcx> {
285+
let pick = self.probe_for_name(
286+
probe::Mode::MethodCall,
287+
method_name,
288+
return_type,
289+
IsSuggestion(true),
290+
self_ty,
291+
call_expr.hir_id,
292+
scope,
293+
)?;
294+
Ok(pick)
295+
}
296+
274297
pub(super) fn obligation_for_method(
275298
&self,
276299
cause: ObligationCause<'tcx>,

compiler/rustc_hir_typeck/src/method/suggest.rs

+34-28
Original file line numberDiff line numberDiff line change
@@ -370,8 +370,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
370370
self.suggest_fn_call(&mut err, rcvr_expr, rcvr_ty, |output_ty| {
371371
let call_expr =
372372
self.tcx.hir().expect_expr(self.tcx.hir().parent_id(rcvr_expr.hir_id));
373-
let probe =
374-
self.lookup_probe(item_name, output_ty, call_expr, ProbeScope::AllTraits);
373+
let probe = self.lookup_probe_for_diagnostic(
374+
item_name,
375+
output_ty,
376+
call_expr,
377+
ProbeScope::AllTraits,
378+
expected.only_has_type(self),
379+
);
375380
probe.is_ok()
376381
});
377382
}
@@ -1386,14 +1391,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
13861391
let range_ty =
13871392
self.tcx.bound_type_of(range_def_id).subst(self.tcx, &[actual.into()]);
13881393

1389-
let pick = self.probe_for_name(
1390-
Mode::MethodCall,
1394+
let pick = self.lookup_probe_for_diagnostic(
13911395
item_name,
1392-
None,
1393-
IsSuggestion(true),
13941396
range_ty,
1395-
expr.hir_id,
1397+
expr,
13961398
ProbeScope::AllTraits,
1399+
None,
13971400
);
13981401
if pick.is_ok() {
13991402
let range_span = parent_expr.span.with_hi(expr.span.hi());
@@ -1573,11 +1576,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
15731576
&& let Some(expr) = visitor.result
15741577
&& let Some(self_ty) = self.node_ty_opt(expr.hir_id)
15751578
{
1576-
let probe = self.lookup_probe(
1579+
let probe = self.lookup_probe_for_diagnostic(
15771580
seg2.ident,
15781581
self_ty,
15791582
call_expr,
15801583
ProbeScope::TraitsInScope,
1584+
None,
15811585
);
15821586
if probe.is_ok() {
15831587
let sm = self.infcx.tcx.sess.source_map();
@@ -1624,14 +1628,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
16241628
self.check_for_nested_field_satisfying(
16251629
span,
16261630
&|_, field_ty| {
1627-
self.probe_for_name(
1628-
Mode::MethodCall,
1631+
self.lookup_probe_for_diagnostic(
16291632
item_name,
1630-
return_type,
1631-
IsSuggestion(true),
16321633
field_ty,
1633-
call_expr.hir_id,
1634+
call_expr,
16341635
ProbeScope::TraitsInScope,
1636+
return_type,
16351637
)
16361638
.map_or(false, |pick| {
16371639
!never_mention_traits
@@ -1697,9 +1699,15 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
16971699
return None;
16981700
}
16991701

1700-
self.lookup_probe(item_name, field_ty, call_expr, ProbeScope::TraitsInScope)
1701-
.ok()
1702-
.map(|pick| (variant, field, pick))
1702+
self.lookup_probe_for_diagnostic(
1703+
item_name,
1704+
field_ty,
1705+
call_expr,
1706+
ProbeScope::TraitsInScope,
1707+
None,
1708+
)
1709+
.ok()
1710+
.map(|pick| (variant, field, pick))
17031711
})
17041712
.collect();
17051713

@@ -1763,11 +1771,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
17631771
ty::AdtKind::Struct | ty::AdtKind::Union => {
17641772
let [first] = ***substs else { return; };
17651773
let ty::GenericArgKind::Type(ty) = first.unpack() else { return; };
1766-
let Ok(pick) = self.lookup_probe(
1774+
let Ok(pick) = self.lookup_probe_for_diagnostic(
17671775
item_name,
17681776
ty,
17691777
call_expr,
17701778
ProbeScope::TraitsInScope,
1779+
None,
17711780
) else { return; };
17721781

17731782
let name = self.ty_to_value_string(actual);
@@ -2243,14 +2252,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
22432252
(self.tcx.mk_mut_ref(self.tcx.lifetimes.re_erased, rcvr_ty), "&mut "),
22442253
(self.tcx.mk_imm_ref(self.tcx.lifetimes.re_erased, rcvr_ty), "&"),
22452254
] {
2246-
match self.probe_for_name(
2247-
Mode::MethodCall,
2255+
match self.lookup_probe_for_diagnostic(
22482256
item_name,
2249-
return_type,
2250-
IsSuggestion(true),
22512257
*rcvr_ty,
2252-
rcvr.hir_id,
2258+
rcvr,
22532259
ProbeScope::AllTraits,
2260+
return_type,
22542261
) {
22552262
Ok(pick) => {
22562263
// If the method is defined for the receiver we have, it likely wasn't `use`d.
@@ -2284,14 +2291,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
22842291
(self.tcx.mk_diagnostic_item(*rcvr_ty, sym::Rc), "Rc::new"),
22852292
] {
22862293
if let Some(new_rcvr_t) = *rcvr_ty
2287-
&& let Ok(pick) = self.probe_for_name(
2288-
Mode::MethodCall,
2294+
&& let Ok(pick) = self.lookup_probe_for_diagnostic(
22892295
item_name,
2290-
return_type,
2291-
IsSuggestion(true),
22922296
new_rcvr_t,
2293-
rcvr.hir_id,
2297+
rcvr,
22942298
ProbeScope::AllTraits,
2299+
return_type,
22952300
)
22962301
{
22972302
debug!("try_alt_rcvr: pick candidate {:?}", pick);
@@ -2670,11 +2675,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
26702675
name: Symbol::intern(&format!("{}_else", method_name.as_str())),
26712676
span: method_name.span,
26722677
};
2673-
let probe = self.lookup_probe(
2678+
let probe = self.lookup_probe_for_diagnostic(
26742679
new_name,
26752680
self_ty,
26762681
self_expr,
26772682
ProbeScope::TraitsInScope,
2683+
Some(expected),
26782684
);
26792685

26802686
// check the method arguments number

0 commit comments

Comments
 (0)