]> git.lizzy.rs Git - rust.git/commitdiff
Adjust feature gates to allow for parenthetical notation to be used
authorNiko Matsakis <niko@alum.mit.edu>
Tue, 25 Nov 2014 16:45:50 +0000 (11:45 -0500)
committerNiko Matsakis <niko@alum.mit.edu>
Sun, 14 Dec 2014 09:21:56 +0000 (04:21 -0500)
with the fn traits

src/librustc/diagnostics.rs
src/librustc/middle/lang_items.rs
src/librustc_typeck/astconv.rs
src/librustc_typeck/check/closure.rs
src/librustc_typeck/check/mod.rs
src/libsyntax/feature_gate.rs

index fcac718b3708cbf1576ff7ddf4979975563104d3..dd5cb8e3b4d242bfa19ed8c776acebdeee785aad 100644 (file)
@@ -67,5 +67,6 @@
     E0173,
     E0174,
     E0177,
-    E0178
+    E0178,
+    E0179 // parenthesized params may only be used with a trait
 )
index 4a20c92d8e21e5bc3002b61e6b1b6dc0a1301ae0..8d5528b3709ad1a7c608fc10810735acefd57aa6 100644 (file)
@@ -114,6 +114,22 @@ pub fn to_builtin_kind(&self, id: ast::DefId) -> Option<ty::BuiltinBound> {
         }
     }
 
+    pub fn fn_trait_kind(&self, id: ast::DefId) -> Option<ty::UnboxedClosureKind> {
+        let def_id_kinds = [
+            (self.fn_trait(), ty::FnUnboxedClosureKind),
+            (self.fn_mut_trait(), ty::FnMutUnboxedClosureKind),
+            (self.fn_once_trait(), ty::FnOnceUnboxedClosureKind),
+            ];
+
+        for &(opt_def_id, kind) in def_id_kinds.iter() {
+            if Some(id) == opt_def_id {
+                return Some(kind);
+            }
+        }
+
+        None
+    }
+
     $(
         #[allow(dead_code)]
         pub fn $method(&self) -> Option<ast::DefId> {
index 4ad0d2b8293e1664980deff4de312a7f549e8d1e..7ee627dbe14551a5883269fe709885696b65c496 100644 (file)
@@ -235,7 +235,7 @@ fn ast_path_substs_for_ty<'tcx,AC,RS>(
             convert_angle_bracketed_parameters(this, rscope, data)
         }
         ast::ParenthesizedParameters(ref data) => {
-            span_err!(tcx.sess, path.span, E0169,
+            span_err!(tcx.sess, path.span, E0173,
                       "parenthesized parameters may only be used with a trait");
             (Vec::new(), convert_parenthesized_parameters(this, data), Vec::new())
         }
@@ -581,6 +581,19 @@ fn ast_path_to_trait_ref<'tcx,AC,RS>(
             convert_angle_bracketed_parameters(this, &shifted_rscope, data)
         }
         ast::ParenthesizedParameters(ref data) => {
+            // For now, require that parenthetical notation be used
+            // only with `Fn()` etc.
+            if !this.tcx().sess.features.borrow().unboxed_closures &&
+                this.tcx().lang_items.fn_trait_kind(trait_def_id).is_none()
+            {
+                this.tcx().sess.span_err(path.span,
+                                         "parenthetical notation is only stable when \
+                                         used with the `Fn` family of traits");
+                span_help!(this.tcx().sess, path.span,
+                           "add `#![feature(unboxed_closures)]` to \
+                            the crate attributes to enable");
+            }
+
             (Vec::new(), convert_parenthesized_parameters(this, data), Vec::new())
         }
     };
index 2b34b4a55b7c11460c753f8fcd1373ac0dba9a88..4e027005931a9f089e0bc5d7d86a3c2cd22f5ae7 100644 (file)
@@ -188,42 +188,35 @@ fn deduce_unboxed_closure_expectations_from_trait_ref<'a,'tcx>(
     debug!("deduce_unboxed_closure_expectations_from_object_type({})",
            trait_ref.repr(tcx));
 
-    let def_id_kinds = [
-        (tcx.lang_items.fn_trait(), ty::FnUnboxedClosureKind),
-        (tcx.lang_items.fn_mut_trait(), ty::FnMutUnboxedClosureKind),
-        (tcx.lang_items.fn_once_trait(), ty::FnOnceUnboxedClosureKind),
-    ];
-
-    for &(def_id, kind) in def_id_kinds.iter() {
-        if Some(trait_ref.def_id) == def_id {
-            debug!("found object type {}", kind);
-
-            let arg_param_ty = *trait_ref.substs.types.get(subst::TypeSpace, 0);
-            let arg_param_ty = fcx.infcx().resolve_type_vars_if_possible(arg_param_ty);
-            debug!("arg_param_ty {}", arg_param_ty.repr(tcx));
-
-            let input_tys = match arg_param_ty.sty {
-                ty::ty_tup(ref tys) => { (*tys).clone() }
-                _ => { continue; }
-            };
-            debug!("input_tys {}", input_tys.repr(tcx));
+    let kind = match tcx.lang_items.fn_trait_kind(trait_ref.def_id) {
+        Some(k) => k,
+        None => { return None; }
+    };
 
-            let ret_param_ty = *trait_ref.substs.types.get(subst::TypeSpace, 1);
-            let ret_param_ty = fcx.infcx().resolve_type_vars_if_possible(ret_param_ty);
-            debug!("ret_param_ty {}", ret_param_ty.repr(tcx));
+    debug!("found object type {}", kind);
 
-            let fn_sig = ty::FnSig {
-                inputs: input_tys,
-                output: ty::FnConverging(ret_param_ty),
-                variadic: false
-            };
-            debug!("fn_sig {}", fn_sig.repr(tcx));
+    let arg_param_ty = *trait_ref.substs.types.get(subst::TypeSpace, 0);
+    let arg_param_ty = fcx.infcx().resolve_type_vars_if_possible(arg_param_ty);
+    debug!("arg_param_ty {}", arg_param_ty.repr(tcx));
 
-            return Some((fn_sig, kind));
-        }
-    }
+    let input_tys = match arg_param_ty.sty {
+        ty::ty_tup(ref tys) => { (*tys).clone() }
+        _ => { return None; }
+    };
+    debug!("input_tys {}", input_tys.repr(tcx));
 
-    None
+    let ret_param_ty = *trait_ref.substs.types.get(subst::TypeSpace, 1);
+    let ret_param_ty = fcx.infcx().resolve_type_vars_if_possible(ret_param_ty);
+    debug!("ret_param_ty {}", ret_param_ty.repr(tcx));
+
+    let fn_sig = ty::FnSig {
+        inputs: input_tys,
+        output: ty::FnConverging(ret_param_ty),
+        variadic: false
+    };
+    debug!("fn_sig {}", fn_sig.repr(tcx));
+
+    return Some((fn_sig, kind));
 }
 
 fn deduce_unboxed_closure_expectations_from_obligations<'a,'tcx>(
index 18a773fb949fcec1ec1c3b4e728d9b57031f557d..77460bb6b269a39167aeb9dbdc37724c0697c6f2 100644 (file)
@@ -5159,6 +5159,8 @@ fn push_explicit_parameters_from_segment_to_substs<'a, 'tcx>(
             }
 
             ast::ParenthesizedParameters(ref data) => {
+                span_err!(fcx.tcx().sess, span, E0173,
+                          "parenthesized parameters may only be used with a trait");
                 push_explicit_parenthesized_parameters_from_segment_to_substs(
                     fcx, space, span, type_defs, data, substs);
             }
index b8f60e77601cfb63b51d53d40073977c5e17877b..2ee4957ec0fa08af83575114ea47b49cdf96af63 100644 (file)
@@ -374,19 +374,6 @@ fn visit_fn(&mut self,
         }
         visit::walk_fn(self, fn_kind, fn_decl, block, span);
     }
-
-    fn visit_path_parameters(&mut self, path_span: Span, parameters: &'v ast::PathParameters) {
-        match *parameters {
-            ast::ParenthesizedParameters(..) => {
-                self.gate_feature("unboxed_closures",
-                                  path_span,
-                                  "parenthetical parameter notation is subject to change");
-            }
-            ast::AngleBracketedParameters(..) => { }
-        }
-
-        visit::walk_path_parameters(self, path_span, parameters)
-    }
 }
 
 pub fn check_crate(span_handler: &SpanHandler, krate: &ast::Crate) -> (Features, Vec<Span>) {