diff --git a/src/rustc/middle/typeck.rs b/src/rustc/middle/typeck.rs index 41ddedcb5266..d8db45d89196 100644 --- a/src/rustc/middle/typeck.rs +++ b/src/rustc/middle/typeck.rs @@ -559,20 +559,27 @@ fn ast_path_to_ty( /* Instantiates the path for the given iface reference, assuming that it's bound to a valid iface type. Returns the def_id for the defining - iface + iface. Fails if the type is a type other than an iface type. */ fn instantiate_iface_ref(ccx: @crate_ctxt, t: @ast::iface_ref, rp: ast::region_param) -> (ast::def_id, ty_param_substs_and_ty) { + let sp = t.path.span, err = "can only implement interface types", + sess = ccx.tcx.sess; + alt lookup_def_tcx(ccx.tcx, t.path.span, t.id) { ast::def_ty(t_id) { - (t_id, ast_path_to_ty(ccx, type_rscope(rp), t_id, t.path, t.id)) + let tpt = ast_path_to_ty(ccx, type_rscope(rp), t_id, t.path, t.id); + alt ty::get(tpt.ty).struct { + ty::ty_iface(*) { + (t_id, tpt) + } + _ { sess.span_fatal(sp, err); } + } } _ { - ccx.tcx.sess.span_fatal( - t.path.span, - "can only implement interface types"); + sess.span_fatal(sp, err); } } } diff --git a/src/test/compile-fail/issue-2330.rs b/src/test/compile-fail/issue-2330.rs new file mode 100644 index 000000000000..355b90bb2aac --- /dev/null +++ b/src/test/compile-fail/issue-2330.rs @@ -0,0 +1,13 @@ +enum chan { } + +iface channel { + fn send(v: T); +} + +// `chan` is not an iface, it's an enum +impl of chan for int { //! ERROR can only implement interface types + fn send(v: int) { fail } +} + +fn main() { +}