about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMasaki Hara <ackie.h.gmai@gmail.com>2017-05-15 15:21:01 +0900
committerMasaki Hara <ackie.h.gmai@gmail.com>2017-05-15 15:21:01 +0900
commit2a20073c9430ff433b7863bc9ffc1b36177d2ab4 (patch)
tree6a76bee7bce9793641666ad19fa0fc5344146d2e
parent63ecd6aa0f2c8a6807528d8bdf5eb30211b3fcd4 (diff)
downloadrust-2a20073c9430ff433b7863bc9ffc1b36177d2ab4.tar.gz
rust-2a20073c9430ff433b7863bc9ffc1b36177d2ab4.zip
Prohibit parenthesized params in bounds etc.
-rw-r--r--src/librustc_typeck/astconv.rs11
-rw-r--r--src/librustc_typeck/check/mod.rs3
-rw-r--r--src/test/compile-fail/issue-32995-2.rs25
-rw-r--r--src/test/compile-fail/issue-32995.rs16
4 files changed, 54 insertions, 1 deletions
diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs
index 93411493b17..d8a3ebe063a 100644
--- a/src/librustc_typeck/astconv.rs
+++ b/src/librustc_typeck/astconv.rs
@@ -372,6 +372,8 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o {
         self_ty: Ty<'tcx>)
         -> ty::TraitRef<'tcx>
     {
+        self.prohibit_type_params(trait_ref.path.segments.split_last().unwrap().1);
+
         let trait_def_id = self.trait_def_id(trait_ref);
         self.ast_path_to_mono_trait_ref(trait_ref.path.span,
                                         trait_def_id,
@@ -404,6 +406,8 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o {
 
         debug!("ast_path_to_poly_trait_ref({:?}, def_id={:?})", trait_ref, trait_def_id);
 
+        self.prohibit_type_params(trait_ref.path.segments.split_last().unwrap().1);
+
         let (substs, assoc_bindings) =
             self.create_substs_for_ast_trait_ref(trait_ref.path.span,
                                                  trait_def_id,
@@ -625,6 +629,13 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o {
                                                         dummy_self,
                                                         &mut projection_bounds);
 
+        for trait_bound in trait_bounds[1..].iter() {
+            // Sanity check for non-principal trait bounds
+            self.instantiate_poly_trait_ref(trait_bound,
+                                            dummy_self,
+                                            &mut vec![]);
+        }
+
         let (auto_traits, trait_bounds) = split_auto_traits(tcx, &trait_bounds[1..]);
 
         if !trait_bounds.is_empty() {
diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs
index 127ffc60cf4..05594cff8a0 100644
--- a/src/librustc_typeck/check/mod.rs
+++ b/src/librustc_typeck/check/mod.rs
@@ -4495,7 +4495,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
                     (&data.lifetimes[..], &data.types[..], data.infer_types, &data.bindings[..])
                 }
                 Some(&hir::ParenthesizedParameters(_)) => {
-                    span_bug!(span, "parenthesized parameters cannot appear in ExprPath");
+                    AstConv::prohibit_parenthesized_params(self, &segment.as_ref().unwrap().0);
+                    (&[][..], &[][..], true, &[][..])
                 }
                 None => (&[][..], &[][..], true, &[][..])
             }
diff --git a/src/test/compile-fail/issue-32995-2.rs b/src/test/compile-fail/issue-32995-2.rs
new file mode 100644
index 00000000000..80113d3b4ec
--- /dev/null
+++ b/src/test/compile-fail/issue-32995-2.rs
@@ -0,0 +1,25 @@
+// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+#![feature(conservative_impl_trait)]
+
+fn main() {
+    { fn f<X: ::std::marker()::Send>() {} }
+    //~^ ERROR parenthesized parameters may only be used with a trait
+
+    { fn f() -> impl ::std::marker()::Send { } }
+    //~^ ERROR parenthesized parameters may only be used with a trait
+}
+
+#[derive(Clone)]
+struct X;
+
+impl ::std::marker()::Copy for X {}
+//~^ ERROR parenthesized parameters may only be used with a trait
diff --git a/src/test/compile-fail/issue-32995.rs b/src/test/compile-fail/issue-32995.rs
index 2fb22e68beb..d38bec45513 100644
--- a/src/test/compile-fail/issue-32995.rs
+++ b/src/test/compile-fail/issue-32995.rs
@@ -17,6 +17,22 @@ fn main() {
 
     let b: ::std::boxed()::Box<_> = Box::new(1);
     //~^ ERROR parenthesized parameters may only be used with a trait
+
+    macro_rules! pathexpr {
+        ($p:path) => { $p }
+    }
+
+    let p = pathexpr!(::std::str()::from_utf8)(b"foo").unwrap();
+    //~^ ERROR parenthesized parameters may only be used with a trait
+
+    let p = pathexpr!(::std::str::from_utf8())(b"foo").unwrap();
+    //~^ ERROR parenthesized parameters may only be used with a trait
+
+    let o : Box<::std::marker()::Send> = Box::new(1);
+    //~^ ERROR parenthesized parameters may only be used with a trait
+
+    let o : Box<Send + ::std::marker()::Sync> = Box::new(1);
+    //~^ ERROR parenthesized parameters may only be used with a trait
 }
 
 fn foo<X:Default>() {