Skip to content

Commit 8bf0470

Browse files
committed
debug issue
1 parent 22ac606 commit 8bf0470

File tree

7 files changed

+107
-10
lines changed

7 files changed

+107
-10
lines changed

compiler/rustc_errors/src/lib.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -466,6 +466,7 @@ pub enum StashKey {
466466
/// When an invalid lifetime e.g. `'2` should be reinterpreted
467467
/// as a char literal in the parser
468468
LifetimeIsChar,
469+
CallInstanceMethod,
469470
}
470471

471472
fn default_track_diagnostic(_: &Diagnostic) {}

compiler/rustc_hir/src/intravisit.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -697,6 +697,7 @@ pub fn walk_qpath<'v, V: Visitor<'v>>(visitor: &mut V, qpath: &'v QPath<'v>, id:
697697
visitor.visit_path(path, id)
698698
}
699699
QPath::TypeRelative(ref qself, ref segment) => {
700+
debug!("yukang segment: {:?}", segment);
700701
visitor.visit_ty(qself);
701702
visitor.visit_path_segment(segment);
702703
}
@@ -711,6 +712,7 @@ pub fn walk_path<'v, V: Visitor<'v>>(visitor: &mut V, path: &'v Path<'v>) {
711712
}
712713

713714
pub fn walk_path_segment<'v, V: Visitor<'v>>(visitor: &mut V, segment: &'v PathSegment<'v>) {
715+
debug!("yukang walk_path_segment: {:?}", segment);
714716
visitor.visit_ident(segment.ident);
715717
visitor.visit_id(segment.hir_id);
716718
if let Some(ref args) = segment.args {

compiler/rustc_hir_typeck/src/expr.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -520,6 +520,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
520520
args: &'tcx [hir::Expr<'tcx>],
521521
) -> Ty<'tcx> {
522522
let tcx = self.tcx;
523+
debug!("yukang check_expr_path: {:?}", qpath);
523524
let (res, opt_ty, segs) =
524525
self.resolve_ty_and_res_fully_qualified_call(qpath, expr.hir_id, expr.span);
525526
let ty = match res {

compiler/rustc_hir_typeck/src/fn_ctxt/_impl.rs

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ use crate::rvalue_scopes;
44
use crate::{BreakableCtxt, Diverges, Expectation, FnCtxt, LocalTy};
55
use rustc_data_structures::captures::Captures;
66
use rustc_data_structures::fx::FxHashSet;
7-
use rustc_errors::{Applicability, Diagnostic, ErrorGuaranteed, MultiSpan};
7+
use rustc_errors::{Applicability, Diagnostic, ErrorGuaranteed, MultiSpan, StashKey};
88
use rustc_hir as hir;
99
use rustc_hir::def::{CtorOf, DefKind, Res};
1010
use rustc_hir::def_id::DefId;
@@ -863,6 +863,28 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
863863
);
864864
let (ty, qself, item_segment) = match *qpath {
865865
QPath::Resolved(ref opt_qself, ref path) => {
866+
if path.segments.len() == 2 {
867+
debug!("yukang item_segment: {:?}", path.segments);
868+
if let [seg1, seg2] = path.segments
869+
&& let Some(mut diag) = self
870+
.tcx
871+
.sess
872+
.diagnostic()
873+
.steal_diagnostic(seg1.ident.span, StashKey::CallInstanceMethod)
874+
&& let Some(&help) = diag.children.get(0) {
875+
let local_def_span = help.span;
876+
if self.suggest_instance_call(seg1, seg2, &local_def_span) {
877+
diag.set_primary_message(format!(
878+
"need to fix call instance method: {:?}",
879+
seg2.ident
880+
));
881+
diag.emit();
882+
} else {
883+
diag.cancel();
884+
}
885+
}
886+
}
887+
866888
return (
867889
path.res,
868890
opt_qself.as_ref().map(|qself| self.to_ty(qself)),

compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1994,6 +1994,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
19941994
}
19951995
}
19961996
hir::QPath::TypeRelative(_, segment) => {
1997+
debug!("yukang point_at_path_if_possible segment={:?}", segment);
19971998
if self.point_at_generic_if_possible(error, def_id, param, segment) {
19981999
return true;
19992000
}

compiler/rustc_hir_typeck/src/method/suggest.rs

Lines changed: 60 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,11 @@ use rustc_trait_selection::traits::{
2929
FulfillmentError, Obligation, ObligationCause, ObligationCauseCode, OnUnimplementedNote,
3030
};
3131

32-
use std::cmp::Ordering;
33-
use std::iter;
34-
3532
use super::probe::{AutorefOrPtrAdjustment, IsSuggestion, Mode, ProbeScope};
3633
use super::{CandidateSource, MethodError, NoMatchData};
34+
use rustc_hir::intravisit::Visitor;
35+
use std::cmp::Ordering;
36+
use std::iter;
3737

3838
impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
3939
fn is_fn_ty(&self, ty: Ty<'tcx>, span: Span) -> bool {
@@ -1407,6 +1407,63 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
14071407
false
14081408
}
14091409

1410+
pub(crate) fn suggest_instance_call(
1411+
&self,
1412+
seg1: &hir::PathSegment<'_>,
1413+
seg2: &hir::PathSegment<'_>,
1414+
local_span: Span,
1415+
) -> bool {
1416+
let map = self.infcx.tcx.hir();
1417+
let body_id = map.body_owned_by(seg1.hir_id.owner.def_id);
1418+
let body = map.body(body_id);
1419+
1420+
struct LetVisitor<'a> {
1421+
local_span: Span,
1422+
result: Option<&'a Ty<'a>>,
1423+
}
1424+
1425+
impl<'v> Visitor<'v> for LetVisitor<'_> {
1426+
fn visit_stmt(&mut self, ex: &'v hir::Stmt<'v>) {
1427+
if self.result.is_some() {
1428+
return;
1429+
}
1430+
if let hir::StmtKind::Local(hir::Local {
1431+
span, ty, init: None, ..
1432+
}) = &ex.kind && span.contains(self.local_span) {
1433+
self.result = ty;
1434+
}
1435+
hir::intravisit::walk_stmt(self, ex);
1436+
}
1437+
}
1438+
1439+
let mut visitor = LetVisitor { local_span, result: None };
1440+
visitor.visit_body(&body);
1441+
1442+
let parent = self.tcx.hir().get_parent_node(seg1.hir_id);
1443+
let parent_expr = self.tcx.hir().find(parent);
1444+
debug!("yukang parent_expr: {:?}", parent_expr);
1445+
let node = self.tcx.hir().get_parent_node(seg1.hir_id);
1446+
let ty = self.typeck_results.borrow().node_type_opt(node);
1447+
1448+
debug!("yukang suggest_instance_call ty: {:?}", ty);
1449+
if let Some(Node::Expr(call_expr)) = self.tcx.hir().find(parent) &&
1450+
let Some(self_ty) = ty {
1451+
debug!("yukang trying to prob method");
1452+
let probe = self.lookup_probe(
1453+
seg1.ident.span,
1454+
seg2.ident,
1455+
self_ty,
1456+
call_expr,
1457+
ProbeScope::TraitsInScope,
1458+
);
1459+
1460+
if let Ok(_pick) = probe {
1461+
return true;
1462+
}
1463+
}
1464+
return false;
1465+
}
1466+
14101467
fn check_for_field_method(
14111468
&self,
14121469
err: &mut Diagnostic,

compiler/rustc_resolve/src/diagnostics.rs

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2022,7 +2022,7 @@ impl<'a> Resolver<'a> {
20222022
// 3. check whether the name refers to an item in local scope
20232023
if suggestion.is_none() &&
20242024
let Some(ribs) = ribs &&
2025-
let Some(LexicalScopeBinding::Res(Res::Local(_))) = self.resolve_ident_in_lexical_scope(
2025+
let Some(LexicalScopeBinding::Res(Res::Local(local_id))) = self.resolve_ident_in_lexical_scope(
20262026
ident,
20272027
ValueNS,
20282028
parent_scope,
@@ -2033,21 +2033,34 @@ impl<'a> Resolver<'a> {
20332033
{
20342034
let sm = self.session.source_map();
20352035
let code_span = sm
2036-
.span_extend_while(ident.span.shrink_to_hi(), |c| c != '\n')
2036+
.span_extend_while(ident.span.shrink_to_hi(), |c| c == ':')
20372037
.unwrap_or(ident.span);
20382038
let code = sm.span_to_snippet(code_span).unwrap();
2039-
if code.starts_with("::") && code.matches("::").count() == 1 {
2040-
suggestion = Some((
2039+
if code == "::" {
2040+
let local_span = *self.pat_span_map.get(&local_id).unwrap();
2041+
let mut err = struct_span_err!(
2042+
self.session,
2043+
ident.span,
2044+
E0434,
2045+
"{}",
2046+
format!(
2047+
"`{}` is not a crate or module, maybe you meant to call instance method",
2048+
ident
2049+
)
2050+
);
2051+
err.span_warn(local_span, "ident is defined at here");
2052+
err.stash(ident.span, rustc_errors::StashKey::CallInstanceMethod);
2053+
/* suggestion = Some((
20412054
vec![(
2042-
sm.span_extend_while(ident.span, |c| c == ':').unwrap(),
2055+
sm.span_extend_while(id ent.span, |c| c == ':').unwrap(),
20432056
format!("{}.", ident),
20442057
)],
20452058
format!(
20462059
"`{}` is not a crate or module, maybe you meant to call instance method",
20472060
ident
20482061
),
20492062
Applicability::MaybeIncorrect,
2050-
))
2063+
)) */
20512064
}
20522065
};
20532066
(format!("use of undeclared crate or module `{}`", ident), suggestion)

0 commit comments

Comments
 (0)