diff --git a/src/comp/front/test.rs b/src/comp/front/test.rs index fa48c9fbfb88a..0def097992854 100644 --- a/src/comp/front/test.rs +++ b/src/comp/front/test.rs @@ -302,7 +302,7 @@ fn mk_test_wrapper(cx: test_ctxt, span: span) -> @ast::expr { let call_expr: ast::expr = { id: cx.next_node_id(), - node: ast::expr_call(@fn_path_expr, []), + node: ast::expr_call(@fn_path_expr, [], false), span: span }; @@ -401,7 +401,7 @@ fn mk_test_main_call(cx: test_ctxt) -> @ast::expr { let test_path_expr: ast::expr = {id: cx.next_node_id(), node: test_path_expr_, span: dummy_sp()}; - let test_call_expr_: ast::expr_ = ast::expr_call(@test_path_expr, []); + let test_call_expr_ = ast::expr_call(@test_path_expr, [], false); let test_call_expr: ast::expr = {id: cx.next_node_id(), node: test_call_expr_, span: dummy_sp()}; @@ -419,7 +419,7 @@ fn mk_test_main_call(cx: test_ctxt) -> @ast::expr { let test_main_call_expr_: ast::expr_ = ast::expr_call(@test_main_path_expr, - [@args_path_expr, @test_call_expr]); + [@args_path_expr, @test_call_expr], false); let test_main_call_expr: ast::expr = {id: cx.next_node_id(), node: test_main_call_expr_, span: dummy_sp()}; diff --git a/src/comp/middle/alias.rs b/src/comp/middle/alias.rs index 36f6d0f0017e8..5b96bddfe3f3f 100644 --- a/src/comp/middle/alias.rs +++ b/src/comp/middle/alias.rs @@ -93,7 +93,7 @@ fn visit_fn(cx: @ctx, f: ast::_fn, _tp: [ast::ty_param], sp: span, fn visit_expr(cx: @ctx, ex: @ast::expr, sc: scope, v: vt) { let handled = true; alt ex.node { - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { check_call(*cx, f, args); handled = false; } @@ -667,7 +667,7 @@ fn expr_root(cx: ctx, ex: @ast::expr, autoderef: bool) } if is_none(path_def_id(cx, base_root.ex)) { alt base_root.ex.node { - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { let fty = ty::expr_ty(cx.tcx, f); alt ty::ty_fn_ret_style(cx.tcx, fty) { ast::return_ref(mut, arg_n) { diff --git a/src/comp/middle/fn_usage.rs b/src/comp/middle/fn_usage.rs index 3f6b2908c201e..e7c3033ce1f20 100644 --- a/src/comp/middle/fn_usage.rs +++ b/src/comp/middle/fn_usage.rs @@ -42,7 +42,7 @@ fn fn_usage_expr(expr: @ast::expr, } } - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { let f_ctx = {unsafe_fn_legal: true, generic_bare_fn_legal: true with ctx}; v.visit_expr(f, f_ctx, v); diff --git a/src/comp/middle/kind.rs b/src/comp/middle/kind.rs index da908f55429be..81032c6a91f43 100644 --- a/src/comp/middle/kind.rs +++ b/src/comp/middle/kind.rs @@ -174,7 +174,7 @@ fn need_shared_or_pinned_ctor(tcx: ty::ctxt, a: @ast::expr, descr: str) { fn pinned_ctor(a: @ast::expr) -> bool { // FIXME: Technically a lambda block is also a pinned ctor alt a.node { - ast::expr_call(cexpr, _) { + ast::expr_call(cexpr, _, _) { // Assuming that if it's a call that it's safe to move in, mostly // because I don't know offhand how to ensure that it's a call // specifically to a resource constructor @@ -224,7 +224,7 @@ fn check_expr(tcx: ty::ctxt, e: @ast::expr) { ast::expr_fail(option::some(a)) { need_expr_kind(tcx, a, ast::kind_shared, "'fail' operand"); } - ast::expr_call(callee, _) { + ast::expr_call(callee, _, _) { let tpt = ty::expr_ty_params_and_ty(tcx, callee); // If we have typarams, we're calling an item; we need to check diff --git a/src/comp/middle/mut.rs b/src/comp/middle/mut.rs index 9dfddd2ae9779..4c286e6cab437 100644 --- a/src/comp/middle/mut.rs +++ b/src/comp/middle/mut.rs @@ -150,7 +150,7 @@ fn visit_decl(cx: @ctx, d: @decl, &&e: (), v: visit::vt<()>) { fn visit_expr(cx: @ctx, ex: @expr, &&e: (), v: visit::vt<()>) { alt ex.node { - expr_call(f, args) { check_call(cx, f, args); } + expr_call(f, args, _) { check_call(cx, f, args); } expr_swap(lhs, rhs) { check_lval(cx, lhs, msg_assign); check_lval(cx, rhs, msg_assign); diff --git a/src/comp/middle/trans.rs b/src/comp/middle/trans.rs index 6f9456dea2aaa..d47ee48734166 100644 --- a/src/comp/middle/trans.rs +++ b/src/comp/middle/trans.rs @@ -3147,7 +3147,7 @@ fn expr_is_lval(tcx: ty::ctxt, e: @ast::expr) -> bool { ty::ty_rec(_) { true } } } - ast::expr_call(f, _) { + ast::expr_call(f, _, _) { let fty = ty::expr_ty(tcx, f); ast_util::ret_by_ref(ty::ty_fn_ret_style(tcx, fty)) } @@ -3198,7 +3198,7 @@ fn trans_lval(cx: @block_ctxt, e: @ast::expr) -> lval_result { ret lval_owned(sub.bcx, val); } // This is a by-ref returning call. Regular calls are not lval - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { let cell = empty_dest_cell(); let bcx = trans_call(cx, f, args, e.id, by_val(cell)); ret lval_owned(bcx, *cell); @@ -4175,7 +4175,7 @@ fn trans_expr(bcx: @block_ctxt, e: @ast::expr, dest: dest) -> @block_ctxt { ast::expr_anon_obj(anon_obj) { ret trans_anon_obj(bcx, e.span, anon_obj, e.id, dest); } - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { ret trans_call(bcx, f, args, e.id, dest); } ast::expr_field(_, _) { diff --git a/src/comp/middle/tstate/auxiliary.rs b/src/comp/middle/tstate/auxiliary.rs index 6ffd10c02bdf0..b8544e2b5add3 100644 --- a/src/comp/middle/tstate/auxiliary.rs +++ b/src/comp/middle/tstate/auxiliary.rs @@ -607,7 +607,7 @@ fn exprs_to_constr_args(tcx: ty::ctxt, args: [@expr]) -> [@constr_arg_use] { fn expr_to_constr(tcx: ty::ctxt, e: @expr) -> sp_constr { alt e.node { - expr_call(operator, args) { + expr_call(operator, args, _) { alt operator.node { expr_path(p) { ret respan(e.span, diff --git a/src/comp/middle/tstate/collect_locals.rs b/src/comp/middle/tstate/collect_locals.rs index 28d9c288aa7b4..b3c8d71a3bf7c 100644 --- a/src/comp/middle/tstate/collect_locals.rs +++ b/src/comp/middle/tstate/collect_locals.rs @@ -32,7 +32,7 @@ fn collect_pred(e: @expr, cx: ctxt, v: visit::vt) { // If it's a call, generate appropriate instances of the // call's constraints. - expr_call(operator, operands) { + expr_call(operator, operands, _) { for c: @ty::constr in constraints_expr(cx.tcx, operator) { let ct: sp_constr = respan(c.span, diff --git a/src/comp/middle/tstate/pre_post_conditions.rs b/src/comp/middle/tstate/pre_post_conditions.rs index dee66e6df4dc7..d0832142d3e74 100644 --- a/src/comp/middle/tstate/pre_post_conditions.rs +++ b/src/comp/middle/tstate/pre_post_conditions.rs @@ -309,7 +309,7 @@ fn find_pre_post_expr(fcx: fn_ctxt, e: @expr) { alt e.node { - expr_call(operator, operands) { + expr_call(operator, operands, _) { /* copy */ let args = operands; diff --git a/src/comp/middle/tstate/states.rs b/src/comp/middle/tstate/states.rs index 39f87f0f11458..2af37f22867ad 100644 --- a/src/comp/middle/tstate/states.rs +++ b/src/comp/middle/tstate/states.rs @@ -335,7 +335,7 @@ fn find_pre_post_state_expr(fcx: fn_ctxt, pres: prestate, e: @expr) -> bool { vec::len(elts)), elts, return_val); } - expr_call(operator, operands) { + expr_call(operator, operands, _) { ret find_pre_post_state_call(fcx, pres, operator, e.id, callee_arg_init_ops(fcx, operator.id), operands, diff --git a/src/comp/middle/typeck.rs b/src/comp/middle/typeck.rs index 7e4c80d5a2791..a20ab23f9f61a 100644 --- a/src/comp/middle/typeck.rs +++ b/src/comp/middle/typeck.rs @@ -2072,7 +2072,7 @@ fn check_expr_with_unifier(fcx: @fn_ctxt, expr: @ast::expr, unify: unifier, out_args, rt, cf, constrs); write::ty_only_fixup(fcx, id, ft); } - ast::expr_call(f, args) { + ast::expr_call(f, args, _) { bot = check_call_full(fcx, expr.span, f, args, expr.id); } ast::expr_self_method(ident) { @@ -2535,7 +2535,7 @@ fn check_pred_expr(fcx: @fn_ctxt, e: @ast::expr) -> bool { /* e must be a call expr where all arguments are either literals or slots */ alt e.node { - ast::expr_call(operator, operands) { + ast::expr_call(operator, operands, _) { if !ty::is_pred_ty(fcx.ccx.tcx, expr_ty(fcx.ccx.tcx, operator)) { fcx.ccx.tcx.sess.span_err (operator.span, @@ -2632,7 +2632,7 @@ fn check_constraints(fcx: @fn_ctxt, cs: [@ast::constr], args: [ast::arg]) { let call_expr_id = fcx.ccx.tcx.sess.next_node_id(); let call_expr = @{id: call_expr_id, - node: ast::expr_call(oper, c_args), + node: ast::expr_call(oper, c_args, false), span: c.span}; check_pred_expr(fcx, call_expr); } diff --git a/src/comp/syntax/ast.rs b/src/comp/syntax/ast.rs index a971653c5f11c..9abab55333105 100644 --- a/src/comp/syntax/ast.rs +++ b/src/comp/syntax/ast.rs @@ -184,7 +184,7 @@ type expr = {id: node_id, node: expr_, span: span}; tag expr_ { expr_vec([@expr], mutability); expr_rec([field], option::t<@expr>); - expr_call(@expr, [@expr]); + expr_call(@expr, [@expr], bool); expr_tup([@expr]); expr_self_method(ident); expr_bind(@expr, [option::t<@expr>]); diff --git a/src/comp/syntax/ast_util.rs b/src/comp/syntax/ast_util.rs index 3d4fe27d98071..b10ce87a6979c 100644 --- a/src/comp/syntax/ast_util.rs +++ b/src/comp/syntax/ast_util.rs @@ -163,7 +163,7 @@ fn is_exported(i: ident, m: _mod) -> bool { } pure fn is_call_expr(e: @expr) -> bool { - alt e.node { expr_call(_, _) { true } _ { false } } + alt e.node { expr_call(_, _, _) { true } _ { false } } } fn is_constraint_arg(e: @expr) -> bool { diff --git a/src/comp/syntax/ext/fmt.rs b/src/comp/syntax/ext/fmt.rs index b51db707daf52..f3fb25acaf900 100644 --- a/src/comp/syntax/ext/fmt.rs +++ b/src/comp/syntax/ext/fmt.rs @@ -79,7 +79,7 @@ fn pieces_to_expr(cx: ext_ctxt, sp: span, pieces: [piece], args: [@ast::expr]) fn make_call(cx: ext_ctxt, sp: span, fn_path: [ast::ident], args: [@ast::expr]) -> @ast::expr { let pathexpr = make_path_expr(cx, sp, fn_path); - let callexpr = ast::expr_call(pathexpr, args); + let callexpr = ast::expr_call(pathexpr, args, false); ret @{id: cx.next_id(), node: callexpr, span: sp}; } fn make_rec_expr(cx: ext_ctxt, sp: span, diff --git a/src/comp/syntax/fold.rs b/src/comp/syntax/fold.rs index 276967b792b63..e79ca1adf9811 100644 --- a/src/comp/syntax/fold.rs +++ b/src/comp/syntax/fold.rs @@ -348,8 +348,9 @@ fn noop_fold_expr(e: expr_, fld: ast_fold) -> expr_ { option::map(fld.fold_expr, maybe_expr)) } expr_tup(elts) { expr_tup(vec::map(fld.fold_expr, elts)) } - expr_call(f, args) { - expr_call(fld.fold_expr(f), fld.map_exprs(fld.fold_expr, args)) + expr_call(f, args, blk) { + expr_call(fld.fold_expr(f), fld.map_exprs(fld.fold_expr, args), + blk) } expr_self_method(id) { expr_self_method(fld.fold_ident(id)) } expr_bind(f, args) { diff --git a/src/comp/syntax/parse/parser.rs b/src/comp/syntax/parse/parser.rs index 1a29a033f5621..8f632165772be 100644 --- a/src/comp/syntax/parse/parser.rs +++ b/src/comp/syntax/parse/parser.rs @@ -977,7 +977,7 @@ fn parse_bottom_expr(p: parser) -> @ast::expr { parse_seq(token::LPAREN, token::RPAREN, some(token::COMMA), parse_expr, p); hi = es.span.hi; - ex = ast::expr_call(f, es.node); + ex = ast::expr_call(f, es.node, false); } else if p.peek() == token::MOD_SEP || is_ident(p.peek()) && !is_word(p, "true") && !is_word(p, "false") { @@ -1051,7 +1051,7 @@ fn parse_dot_or_call_expr_with(p: parser, e: @ast::expr) -> @ast::expr { let es = parse_seq(token::LPAREN, token::RPAREN, some(token::COMMA), parse_expr, p); hi = es.span.hi; - let nd = ast::expr_call(e, es.node); + let nd = ast::expr_call(e, es.node, false); e = mk_expr(p, lo, hi, nd); } } @@ -1073,19 +1073,6 @@ fn parse_dot_or_call_expr_with(p: parser, e: @ast::expr) -> @ast::expr { t { unexpected(p, t); } } } - token::LBRACE. when is_bar(p.look_ahead(1u)) { - p.bump(); - let blk = parse_fn_block_expr(p); - alt e.node { - ast::expr_call(f, args) { - e = @{node: ast::expr_call(f, args + [blk]) with *e}; - } - _ { - e = mk_expr(p, lo, p.get_last_hi_pos(), - ast::expr_call(e, [blk])); - } - } - } _ { ret e; } } } @@ -1569,7 +1556,6 @@ fn parse_source_stmt(p: parser) -> @ast::stmt { let decl = parse_let(p); ret @spanned(lo, decl.span.hi, ast::stmt_decl(decl, p.get_id())); } else { - let item_attrs; alt parse_outer_attrs_or_ext(p) { none. { item_attrs = []; } @@ -1589,7 +1575,6 @@ fn parse_source_stmt(p: parser) -> @ast::stmt { } } - alt maybe_item { some(i) { let hi = i.span.hi; @@ -1599,6 +1584,21 @@ fn parse_source_stmt(p: parser) -> @ast::stmt { none. { // Remainder are line-expr stmts. let e = parse_expr(p); + // See if it is a block call + if p.peek() == token::LBRACE && is_bar(p.look_ahead(1u)) { + p.bump(); + let blk = parse_fn_block_expr(p); + alt e.node { + ast::expr_call(f, args, false) { + e = @{node: ast::expr_call(f, args + [blk], true) + with *e}; + } + _ { + e = mk_expr(p, lo, p.get_last_hi_pos(), + ast::expr_call(e, [blk], true)); + } + } + } ret @spanned(lo, e.span.hi, ast::stmt_expr(e, p.get_id())); } _ { p.fatal("expected statement"); } @@ -1624,6 +1624,7 @@ fn expr_has_value(e: @ast::expr) -> bool { ast::expr_for(_, _, blk) | ast::expr_do_while(blk, _) { !option::is_none(blk.node.expr) } + ast::expr_call(_, _, true) { false } _ { true } } } diff --git a/src/comp/syntax/print/pprust.rs b/src/comp/syntax/print/pprust.rs index 9a7944f47c83e..91e3f2ffb5992 100644 --- a/src/comp/syntax/print/pprust.rs +++ b/src/comp/syntax/print/pprust.rs @@ -727,11 +727,19 @@ fn print_expr(s: ps, &&expr: @ast::expr) { commasep_exprs(s, inconsistent, exprs); pclose(s); } - ast::expr_call(func, args) { + ast::expr_call(func, args, has_block) { print_expr_parens_if_not_bot(s, func); - popen(s); - commasep_exprs(s, inconsistent, args); - pclose(s); + let base_args = args, blk = none; + if has_block { blk = some(vec::pop(base_args)); } + if !has_block || vec::len(base_args) > 0u { + popen(s); + commasep_exprs(s, inconsistent, base_args); + pclose(s); + } + if has_block { + nbsp(s); + print_expr(s, option::get(blk)); + } } ast::expr_self_method(ident) { word(s.s, "self."); diff --git a/src/comp/syntax/visit.rs b/src/comp/syntax/visit.rs index 3cd44fe10da32..0725611eb04dc 100644 --- a/src/comp/syntax/visit.rs +++ b/src/comp/syntax/visit.rs @@ -245,7 +245,7 @@ fn visit_expr(ex: @expr, e: E, v: vt) { visit_expr_opt(base, e, v); } expr_tup(elts) { for el in elts { v.visit_expr(el, e, v); } } - expr_call(callee, args) { + expr_call(callee, args, _) { visit_exprs(args, e, v); v.visit_expr(callee, e, v); }