Skip to content

Commit

Permalink
Show previous definition of duplicate impl item
Browse files Browse the repository at this point in the history
  • Loading branch information
sanxiyn committed Apr 20, 2016
1 parent 3dd88f6 commit f532685
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 17 deletions.
9 changes: 0 additions & 9 deletions src/librustc_typeck/coherence/mod.rs
Expand Up @@ -34,9 +34,7 @@ use CrateCtxt;
use rustc::infer::{self, InferCtxt, TypeOrigin, new_infer_ctxt};
use std::cell::RefCell;
use std::rc::Rc;
use syntax::ast;
use syntax::codemap::Span;
use syntax::errors::DiagnosticBuilder;
use util::nodemap::{DefIdMap, FnvHashMap};
use rustc::dep_graph::DepNode;
use rustc::hir::map as hir_map;
Expand Down Expand Up @@ -517,13 +515,6 @@ fn enforce_trait_manually_implementable(tcx: &TyCtxt, sp: Span, trait_def_id: De
err.emit();
}

// Factored out into helper because the error cannot be defined in multiple locations.
pub fn report_duplicate_item<'tcx>(tcx: &TyCtxt<'tcx>, sp: Span, name: ast::Name)
-> DiagnosticBuilder<'tcx>
{
struct_span_err!(tcx.sess, sp, E0201, "duplicate definitions with name `{}`:", name)
}

pub fn check_coherence(crate_context: &CrateCtxt) {
let _task = crate_context.tcx.dep_graph.in_task(DepNode::Coherence);
let infcx = new_infer_ctxt(crate_context.tcx,
Expand Down
23 changes: 17 additions & 6 deletions src/librustc_typeck/collect.rs
Expand Up @@ -63,7 +63,6 @@ use lint;
use hir::def::Def;
use hir::def_id::DefId;
use constrained_type_params as ctp;
use coherence;
use middle::lang_items::SizedTraitLangItem;
use middle::resolve_lifetime;
use middle::const_val::ConstVal;
Expand All @@ -80,13 +79,14 @@ use rscope::*;
use rustc::dep_graph::DepNode;
use rustc::hir::map as hir_map;
use util::common::{ErrorReported, MemoizationMap};
use util::nodemap::{FnvHashMap, FnvHashSet};
use util::nodemap::FnvHashMap;
use write_ty_to_tcx;

use rustc_const_math::ConstInt;

use std::cell::RefCell;
use std::collections::HashSet;
use std::collections::hash_map::Entry::{Occupied, Vacant};
use std::rc::Rc;

use syntax::abi;
Expand Down Expand Up @@ -742,16 +742,27 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) {

// Convert all the associated consts.
// Also, check if there are any duplicate associated items
let mut seen_type_items = FnvHashSet();
let mut seen_value_items = FnvHashSet();
let mut seen_type_items = FnvHashMap();
let mut seen_value_items = FnvHashMap();

for impl_item in impl_items {
let seen_items = match impl_item.node {
hir::ImplItemKind::Type(_) => &mut seen_type_items,
_ => &mut seen_value_items,
};
if !seen_items.insert(impl_item.name) {
coherence::report_duplicate_item(tcx, impl_item.span, impl_item.name).emit();
match seen_items.entry(impl_item.name) {
Occupied(entry) => {
let mut err = struct_span_err!(tcx.sess, impl_item.span, E0201,
"duplicate definitions with name `{}`:",
impl_item.name);
span_note!(&mut err, *entry.get(),
"previous definition of `{}` here",
impl_item.name);
err.emit();
}
Vacant(entry) => {
entry.insert(impl_item.span);
}
}

if let hir::ImplItemKind::Const(ref ty, _) = impl_item.node {
Expand Down
5 changes: 3 additions & 2 deletions src/test/compile-fail/impl-duplicate-methods.rs
Expand Up @@ -9,9 +9,10 @@
// except according to those terms.

struct Foo;

impl Foo {
fn orange(&self){}
fn orange(&self){} //~ ERROR duplicate definitions
fn orange(&self) {} //~ NOTE previous definition of `orange` here
fn orange(&self) {} //~ ERROR duplicate definitions with name `orange`
}

fn main() {}

0 comments on commit f532685

Please sign in to comment.