about summary refs log tree commit diff
path: root/src/comp/middle
diff options
context:
space:
mode:
authorBrian Anderson <banderson@mozilla.com>2011-10-14 15:16:05 -0700
committerBrian Anderson <banderson@mozilla.com>2011-10-20 18:23:48 -0700
commit354bfc829248965fa23c14cccd8c4db1685f3701 (patch)
tree2ca43b9a565ffac885ac9c0c7fcbe61dcad6c501 /src/comp/middle
parent3bb020aaf8ae2947bbfc26e589c77967b922a215 (diff)
downloadrust-354bfc829248965fa23c14cccd8c4db1685f3701.tar.gz
rust-354bfc829248965fa23c14cccd8c4db1685f3701.zip
Bare functions can coerce to shared closures
Diffstat (limited to 'src/comp/middle')
-rw-r--r--src/comp/middle/typeck.rs21
1 files changed, 15 insertions, 6 deletions
diff --git a/src/comp/middle/typeck.rs b/src/comp/middle/typeck.rs
index c8b3c67bfa0..1e4fe0d6f3c 100644
--- a/src/comp/middle/typeck.rs
+++ b/src/comp/middle/typeck.rs
@@ -891,7 +891,7 @@ fn do_autoderef(fcx: @fn_ctxt, sp: span, t: ty::t) -> ty::t {
     fail;
 }
 
-fn do_fn_block_coerce(fcx: @fn_ctxt, sp: span, actual: ty::t, expected: ty::t)
+fn do_fn_ty_coerce(fcx: @fn_ctxt, sp: span, actual: ty::t, expected: ty::t)
    -> ty::t {
 
     // fns can be silently coerced to blocks when being used as
@@ -910,6 +910,15 @@ fn do_fn_block_coerce(fcx: @fn_ctxt, sp: span, actual: ty::t, expected: ty::t)
               _ { actual }
             }
           }
+          some(ty::ty_fn(ast::proto_bare., args, ret_ty, cf, constrs)) {
+            alt structure_of_maybe(fcx, sp, expected) {
+              some(ty::ty_fn(ast::proto_fn., _, _, _, _)) {
+                ty::mk_fn(fcx.ccx.tcx, ast::proto_fn, args, ret_ty, cf,
+                          constrs)
+              }
+              _ { actual }
+            }
+          }
           _ { actual }
         }
 }
@@ -932,7 +941,7 @@ mod demand {
        ty::t {
         full(fcx, sp, expected, actual, [], false).ty
     }
-    fn block_coerce(fcx: @fn_ctxt, sp: span, expected: ty::t, actual: ty::t)
+    fn fn_coerce(fcx: @fn_ctxt, sp: span, expected: ty::t, actual: ty::t)
        -> ty::t {
         full(fcx, sp, expected, actual, [], true).ty
     }
@@ -945,10 +954,10 @@ mod demand {
     // Requires that the two types unify, and prints an error message if they
     // don't. Returns the unified type and the type parameter substitutions.
     fn full(fcx: @fn_ctxt, sp: span, expected: ty::t, actual: ty::t,
-            ty_param_substs_0: [ty::t], do_block_coerce: bool) ->
+            ty_param_substs_0: [ty::t], do_fn_coerce: bool) ->
        ty_param_substs_and_ty {
-        if do_block_coerce {
-            actual = do_fn_block_coerce(fcx, sp, actual, expected);
+        if do_fn_coerce {
+            actual = do_fn_ty_coerce(fcx, sp, actual, expected);
         }
 
         let ty_param_substs: [mutable ty::t] = [mutable];
@@ -1676,7 +1685,7 @@ fn check_expr_with_unifier(fcx: @fn_ctxt, expr: @ast::expr, unify: unifier,
                         if is_block == check_blocks {
                             bot |=
                                 check_expr_with_unifier(fcx, a,
-                                                        demand::block_coerce,
+                                                        demand::fn_coerce,
                                                         arg_tys[i].ty);
                         }
                       }