From d603892ea7649f5b1a31f871a2ddc54c18d6a02b Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 3 Aug 2016 20:42:05 +0200 Subject: [PATCH 1/3] Add span method for hir::Generics struct --- src/librustc/hir/mod.rs | 34 +++++++++++++++++++++++++++++++++- 1 file changed, 33 insertions(+), 1 deletion(-) diff --git a/src/librustc/hir/mod.rs b/src/librustc/hir/mod.rs index 20bf4f7d3edbb..9212fda650253 100644 --- a/src/librustc/hir/mod.rs +++ b/src/librustc/hir/mod.rs @@ -36,7 +36,7 @@ use hir::def::Def; use hir::def_id::DefId; use util::nodemap::{NodeMap, FnvHashSet}; -use syntax_pos::{mk_sp, Span, ExpnId}; +use syntax_pos::{BytePos, mk_sp, Span, ExpnId}; use syntax::codemap::{self, respan, Spanned}; use syntax::abi::Abi; use syntax::ast::{Name, NodeId, DUMMY_NODE_ID, AsmDialect}; @@ -326,6 +326,38 @@ impl Generics { pub fn is_parameterized(&self) -> bool { self.is_lt_parameterized() || self.is_type_parameterized() } + + // Does return a span which includes lifetimes and type parameters, + // not where clause. + pub fn span(&self) -> Option { + if !self.is_parameterized() { + None + } else { + let mut span: Option = None; + for lifetime in self.lifetimes.iter() { + if let Some(ref mut span) = span { + let life_span = lifetime.lifetime.span; + span.hi = if span.hi > life_span.hi { span.hi } else { life_span.hi }; + span.lo = if span.lo < life_span.lo { span.lo } else { life_span.lo }; + } else { + span = Some(lifetime.lifetime.span.clone()); + } + } + for ty_param in self.ty_params.iter() { + if let Some(ref mut span) = span { + span.lo = if span.lo < ty_param.span.lo { span.lo } else { ty_param.span.lo }; + span.hi = if span.hi > ty_param.span.hi { span.hi } else { ty_param.span.hi }; + } else { + span = Some(ty_param.span.clone()); + } + } + if let Some(ref mut span) = span { + span.lo = span.lo - BytePos(1); + span.hi = span.hi + BytePos(1); + } + span + } + } } /// A `where` clause in a definition From 9b690c94f042a49f5f06c417cb9c5ab401dd0be8 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 3 Aug 2016 20:42:42 +0200 Subject: [PATCH 2/3] Update E0132 to new format --- src/librustc_typeck/lib.rs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/librustc_typeck/lib.rs b/src/librustc_typeck/lib.rs index 3b2d02dc861c4..6f0892cdcdf16 100644 --- a/src/librustc_typeck/lib.rs +++ b/src/librustc_typeck/lib.rs @@ -261,8 +261,11 @@ fn check_start_fn_ty(ccx: &CrateCtxt, match it.node { hir::ItemFn(_,_,_,_,ref ps,_) if ps.is_parameterized() => { - span_err!(tcx.sess, start_span, E0132, - "start function is not allowed to have type parameters"); + struct_span_err!(tcx.sess, start_span, E0132, + "start function is not allowed to have type parameters") + .span_label(ps.span().unwrap(), + &format!("start function cannot have type parameters")) + .emit(); return; } _ => () From 1607d5b437d613908aee08cb9d2bc7330abf5b96 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 3 Aug 2016 23:13:48 +0200 Subject: [PATCH 3/3] Add note test for E0132 --- src/test/compile-fail/E0132.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/test/compile-fail/E0132.rs b/src/test/compile-fail/E0132.rs index ff19a577f903d..1a33fb24ca1a1 100644 --- a/src/test/compile-fail/E0132.rs +++ b/src/test/compile-fail/E0132.rs @@ -12,6 +12,7 @@ #[start] fn f() {} //~ ERROR E0132 + //~| NOTE start function cannot have type parameters fn main() { }