Skip to content

Commit

Permalink
Auto merge of #64151 - estebank:binding-error, r=varkor
Browse files Browse the repository at this point in the history
On obligation errors point at the unfulfilled binding when possible

CC #42855, #64130, #64135. Fix #61860.
  • Loading branch information
bors committed Sep 22, 2019
2 parents 1dd1884 + ff75124 commit c0b7e71
Show file tree
Hide file tree
Showing 175 changed files with 904 additions and 737 deletions.
2 changes: 2 additions & 0 deletions src/etc/generate-deriving-span-tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
os.path.join(os.path.dirname(__file__), '../test/ui/derives/'))

TEMPLATE = """\
// ignore-x86
// ^ due to stderr output differences
// This file was auto-generated using 'src/etc/generate-deriving-span-tests.py'
{error_deriving}
Expand Down
5 changes: 4 additions & 1 deletion src/librustc/hir/lowering.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1893,10 +1893,13 @@ impl<'a> LoweringContext<'a> {
if let Ok(snippet) = self.sess.source_map().span_to_snippet(data.span) {
// Do not suggest going from `Trait()` to `Trait<>`
if data.inputs.len() > 0 {
let split = snippet.find('(').unwrap();
let trait_name = &snippet[0..split];
let args = &snippet[split + 1 .. snippet.len() - 1];
err.span_suggestion(
data.span,
"use angle brackets instead",
format!("<{}>", &snippet[1..snippet.len() - 1]),
format!("{}<{}>", trait_name, args),
Applicability::MaybeIncorrect,
);
}
Expand Down
12 changes: 12 additions & 0 deletions src/librustc/hir/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2750,3 +2750,15 @@ pub enum Node<'hir> {

Crate,
}

impl Node<'_> {
pub fn ident(&self) -> Option<Ident> {
match self {
Node::TraitItem(TraitItem { ident, .. }) |
Node::ImplItem(ImplItem { ident, .. }) |
Node::ForeignItem(ForeignItem { ident, .. }) |
Node::Item(Item { ident, .. }) => Some(*ident),
_ => None,
}
}
}
29 changes: 25 additions & 4 deletions src/librustc/traits/error_reporting.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,10 +40,12 @@ use syntax::symbol::{sym, kw};
use syntax_pos::{DUMMY_SP, Span, ExpnKind};

impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
pub fn report_fulfillment_errors(&self,
errors: &[FulfillmentError<'tcx>],
body_id: Option<hir::BodyId>,
fallback_has_occurred: bool) {
pub fn report_fulfillment_errors(
&self,
errors: &[FulfillmentError<'tcx>],
body_id: Option<hir::BodyId>,
fallback_has_occurred: bool,
) {
#[derive(Debug)]
struct ErrorDescriptor<'tcx> {
predicate: ty::Predicate<'tcx>,
Expand Down Expand Up @@ -1053,6 +1055,13 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
.filter(|c| !c.is_whitespace())
.take_while(|c| *c == '&')
.count();
if let Some('\'') = snippet.chars()
.filter(|c| !c.is_whitespace())
.skip(refs_number)
.next()
{ // Do not suggest removal of borrow from type arguments.
return;
}

let mut trait_type = trait_ref.self_ty();

Expand Down Expand Up @@ -1651,6 +1660,18 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
err.note(&msg);
}
}
ObligationCauseCode::BindingObligation(item_def_id, span) => {
let item_name = tcx.def_path_str(item_def_id);
let msg = format!("required by this bound in `{}`", item_name);
if let Some(ident) = tcx.opt_item_name(item_def_id) {
err.span_label(ident.span, "");
}
if span != DUMMY_SP {
err.span_label(span, &msg);
} else {
err.note(&msg);
}
}
ObligationCauseCode::ObjectCastObligation(object_ty) => {
err.note(&format!("required for the cast to the object type `{}`",
self.ty_to_string(object_ty)));
Expand Down
3 changes: 3 additions & 0 deletions src/librustc/traits/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,9 @@ pub enum ObligationCauseCode<'tcx> {
/// also implement all supertraits of `X`.
ItemObligation(DefId),

/// Like `ItemObligation`, but with extra detail on the source of the obligation.
BindingObligation(DefId, Span),

/// A type like `&'a T` is WF only if `T: 'a`.
ReferenceOutlivesReferent(Ty<'tcx>),

Expand Down
1 change: 1 addition & 0 deletions src/librustc/traits/structural_impls.rs
Original file line number Diff line number Diff line change
Expand Up @@ -472,6 +472,7 @@ impl<'a, 'tcx> Lift<'tcx> for traits::ObligationCauseCode<'a> {
super::TupleElem => Some(super::TupleElem),
super::ProjectionWf(proj) => tcx.lift(&proj).map(super::ProjectionWf),
super::ItemObligation(def_id) => Some(super::ItemObligation(def_id)),
super::BindingObligation(def_id, span) => Some(super::BindingObligation(def_id, span)),
super::ReferenceOutlivesReferent(ty) => {
tcx.lift(&ty).map(super::ReferenceOutlivesReferent)
}
Expand Down
4 changes: 4 additions & 0 deletions src/librustc/ty/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2797,6 +2797,10 @@ impl<'tcx> TyCtxt<'tcx> {
})
}

pub fn opt_item_name(self, def_id: DefId) -> Option<Ident> {
self.hir().as_local_hir_id(def_id).and_then(|hir_id| self.hir().get(hir_id).ident())
}

pub fn opt_associated_item(self, def_id: DefId) -> Option<AssocItem> {
let is_associated_item = if let Some(hir_id) = self.hir().as_local_hir_id(def_id) {
match self.hir().get(hir_id) {
Expand Down
12 changes: 6 additions & 6 deletions src/librustc_typeck/check/callee.rs
Original file line number Diff line number Diff line change
Expand Up @@ -263,7 +263,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

fn confirm_builtin_call(
&self,
call_expr: &hir::Expr,
call_expr: &'tcx hir::Expr,
callee_ty: Ty<'tcx>,
arg_exprs: &'tcx [hir::Expr],
expected: Expectation<'tcx>,
Expand Down Expand Up @@ -425,7 +425,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
);
self.check_argument_types(
call_expr.span,
call_expr.span,
call_expr,
inputs,
&expected_arg_tys[..],
arg_exprs,
Expand All @@ -439,7 +439,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

fn confirm_deferred_closure_call(
&self,
call_expr: &hir::Expr,
call_expr: &'tcx hir::Expr,
arg_exprs: &'tcx [hir::Expr],
expected: Expectation<'tcx>,
fn_sig: ty::FnSig<'tcx>,
Expand All @@ -458,7 +458,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

self.check_argument_types(
call_expr.span,
call_expr.span,
call_expr,
fn_sig.inputs(),
&expected_arg_tys,
arg_exprs,
Expand All @@ -472,14 +472,14 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

fn confirm_overloaded_call(
&self,
call_expr: &hir::Expr,
call_expr: &'tcx hir::Expr,
arg_exprs: &'tcx [hir::Expr],
expected: Expectation<'tcx>,
method_callee: MethodCallee<'tcx>,
) -> Ty<'tcx> {
let output_type = self.check_method_argument_types(
call_expr.span,
call_expr.span,
call_expr,
Ok(method_callee),
arg_exprs,
TupleArgumentsFlag::TupleArguments,
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_typeck/check/expr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -796,7 +796,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// Call the generic checker.
self.check_method_argument_types(
span,
expr.span,
expr,
method,
&args[1..],
DontTupleArguments,
Expand Down
Loading

0 comments on commit c0b7e71

Please sign in to comment.