about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--src/librustc_typeck/check/closure.rs14
-rw-r--r--src/librustc_typeck/check/mod.rs4
-rw-r--r--src/test/compile-fail/borrowck-move-by-capture.rs2
-rw-r--r--src/test/compile-fail/issue-19141.rs15
-rw-r--r--src/test/compile-fail/issue-20193.rs24
-rw-r--r--src/test/compile-fail/issue-20228-1.rs20
-rw-r--r--src/test/compile-fail/issue-20228-2.rs20
7 files changed, 96 insertions, 3 deletions
diff --git a/src/librustc_typeck/check/closure.rs b/src/librustc_typeck/check/closure.rs
index e25543ea992..c396dc5c6cb 100644
--- a/src/librustc_typeck/check/closure.rs
+++ b/src/librustc_typeck/check/closure.rs
@@ -19,11 +19,13 @@ use middle::ty::{mod, Ty};
 use rscope::RegionScope;
 use syntax::abi;
 use syntax::ast;
+use syntax::ast::CaptureClause::*;
 use syntax::ast_util;
 use util::ppaux::Repr;
 
 pub fn check_expr_closure<'a,'tcx>(fcx: &FnCtxt<'a,'tcx>,
                                    expr: &ast::Expr,
+                                   capture: ast::CaptureClause,
                                    opt_kind: Option<ast::UnboxedClosureKind>,
                                    decl: &ast::FnDecl,
                                    body: &ast::Block,
@@ -48,12 +50,24 @@ pub fn check_expr_closure<'a,'tcx>(fcx: &FnCtxt<'a,'tcx>,
                                                                    fcx.infcx(),
                                                                    expr.span,
                                                                    &None);
+
                     check_boxed_closure(fcx,
                                         expr,
                                         ty::RegionTraitStore(region, ast::MutMutable),
                                         decl,
                                         body,
                                         expected);
+
+                    match capture {
+                        CaptureByValue => {
+                            fcx.ccx.tcx.sess.span_err(
+                                expr.span,
+                                "boxed closures can't capture by value, \
+                                if you want to use an unboxed closure, \
+                                explicitly annotate its kind: e.g. `move |:|`");
+                        },
+                        CaptureByRef => {}
+                    }
                 }
                 Some((sig, kind)) => {
                     check_unboxed_closure(fcx, expr, kind, decl, body, Some(sig));
diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs
index abcd00ddcce..7660806f5b0 100644
--- a/src/librustc_typeck/check/mod.rs
+++ b/src/librustc_typeck/check/mod.rs
@@ -3958,8 +3958,8 @@ fn check_expr_with_unifier<'a, 'tcx, F>(fcx: &FnCtxt<'a, 'tcx>,
       ast::ExprMatch(ref discrim, ref arms, match_src) => {
         _match::check_match(fcx, expr, &**discrim, arms.as_slice(), expected, match_src);
       }
-      ast::ExprClosure(_, opt_kind, ref decl, ref body) => {
-          closure::check_expr_closure(fcx, expr, opt_kind, &**decl, &**body, expected);
+      ast::ExprClosure(capture, opt_kind, ref decl, ref body) => {
+          closure::check_expr_closure(fcx, expr, capture, opt_kind, &**decl, &**body, expected);
       }
       ast::ExprBlock(ref b) => {
         check_block_with_expected(fcx, &**b, expected);
diff --git a/src/test/compile-fail/borrowck-move-by-capture.rs b/src/test/compile-fail/borrowck-move-by-capture.rs
index aae661e5c53..9c9641bccfa 100644
--- a/src/test/compile-fail/borrowck-move-by-capture.rs
+++ b/src/test/compile-fail/borrowck-move-by-capture.rs
@@ -11,6 +11,6 @@
 pub fn main() {
     let bar = box 3;
     let _g = || {
-        let _h = move|| -> int { *bar }; //~ ERROR cannot move out of captured outer variable
+        let _h = move |:| -> int { *bar }; //~ ERROR cannot move out of captured outer variable
     };
 }
diff --git a/src/test/compile-fail/issue-19141.rs b/src/test/compile-fail/issue-19141.rs
new file mode 100644
index 00000000000..545e3f8acb1
--- /dev/null
+++ b/src/test/compile-fail/issue-19141.rs
@@ -0,0 +1,15 @@
+// Copyright 2014 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.
+
+fn main() {
+    let n = 0u;
+
+    let f = move || n += 1;  //~error boxed closures can't capture by value
+}
diff --git a/src/test/compile-fail/issue-20193.rs b/src/test/compile-fail/issue-20193.rs
new file mode 100644
index 00000000000..e5d8d332719
--- /dev/null
+++ b/src/test/compile-fail/issue-20193.rs
@@ -0,0 +1,24 @@
+// Copyright 2014 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.
+
+fn foo(t: &mut int){
+    println!("{}", t);
+}
+
+fn main() {
+    let test = 10;
+
+    let h = move || {  //~error boxed closures can't capture by value
+        let mut r = &mut test.clone();
+        foo(r);
+    };
+
+    h();
+}
diff --git a/src/test/compile-fail/issue-20228-1.rs b/src/test/compile-fail/issue-20228-1.rs
new file mode 100644
index 00000000000..3ff4557ae80
--- /dev/null
+++ b/src/test/compile-fail/issue-20228-1.rs
@@ -0,0 +1,20 @@
+// Copyright 2014 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.
+
+struct S;
+
+impl S {
+    fn foo(&self) {
+        let _ = move || { self };  //~error boxed closures can't capture by value
+    }
+}
+
+fn main() {
+}
diff --git a/src/test/compile-fail/issue-20228-2.rs b/src/test/compile-fail/issue-20228-2.rs
new file mode 100644
index 00000000000..5fec4268bf7
--- /dev/null
+++ b/src/test/compile-fail/issue-20228-2.rs
@@ -0,0 +1,20 @@
+// Copyright 2014 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.
+
+struct S;
+
+impl S {
+    fn foo(&self) {
+        let _ = move || { self.foo() };  //~error boxed closures can't capture by value
+    }
+}
+
+fn main() {
+}