From 20083c1e1f6916eb79e3d967c1c9ab63342c71ae Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Mon, 28 Sep 2015 15:00:15 +1300 Subject: Move `for` loop desugaring to lowering --- src/libsyntax/ast.rs | 4 ++ src/libsyntax/ext/expand.rs | 96 +-------------------------------------------- 2 files changed, 6 insertions(+), 94 deletions(-) (limited to 'src/libsyntax') diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index ce00505b0b4..bf43b87b267 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -375,6 +375,10 @@ pub const CRATE_NODE_ID: NodeId = 0; /// small, positive ids. pub const DUMMY_NODE_ID: NodeId = !0; +pub trait NodeIdAssigner { + fn next_node_id(&self) -> NodeId; +} + /// The AST represents all type param bounds as types. /// typeck::collect::compute_bounds matches these against /// the "special" built-in traits (see middle::lang_items) and diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index b15c51490a1..8cfad6341de 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -360,102 +360,10 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { fld.cx.expr(span, ast::ExprLoop(loop_block, opt_ident)) } - // Desugar ExprForLoop - // From: `[opt_ident]: for in ` ast::ExprForLoop(pat, head, body, opt_ident) => { - // to: - // - // { - // let result = match ::std::iter::IntoIterator::into_iter() { - // mut iter => { - // [opt_ident]: loop { - // match ::std::iter::Iterator::next(&mut iter) { - // ::std::option::Option::Some() => , - // ::std::option::Option::None => break - // } - // } - // } - // }; - // result - // } - - push_compiler_expansion(fld, span, CompilerExpansionFormat::ForLoop); - - let span = fld.new_span(span); - - // expand let head = fld.fold_expr(head); - - let iter = token::gensym_ident("iter"); - - let pat_span = fld.new_span(pat.span); - // `::std::option::Option::Some() => ` - let pat_arm = { - let body_expr = fld.cx.expr_block(body); - let pat = fld.fold_pat(pat); - let some_pat = fld.cx.pat_some(pat_span, pat); - - fld.cx.arm(pat_span, vec![some_pat], body_expr) - }; - - // `::std::option::Option::None => break` - let break_arm = { - let break_expr = fld.cx.expr_break(span); - - fld.cx.arm(span, vec![fld.cx.pat_none(span)], break_expr) - }; - - // `match ::std::iter::Iterator::next(&mut iter) { ... }` - let match_expr = { - let next_path = { - let strs = fld.cx.std_path(&["iter", "Iterator", "next"]); - - fld.cx.path_global(span, strs) - }; - let ref_mut_iter = fld.cx.expr_mut_addr_of(span, fld.cx.expr_ident(span, iter)); - let next_expr = - fld.cx.expr_call(span, fld.cx.expr_path(next_path), vec![ref_mut_iter]); - let arms = vec![pat_arm, break_arm]; - - fld.cx.expr(pat_span, - ast::ExprMatch(next_expr, arms, ast::MatchSource::ForLoopDesugar)) - }; - - // `[opt_ident]: loop { ... }` - let loop_block = fld.cx.block_expr(match_expr); - let (loop_block, opt_ident) = expand_loop_block(loop_block, opt_ident, fld); - let loop_expr = fld.cx.expr(span, ast::ExprLoop(loop_block, opt_ident)); - - // `mut iter => { ... }` - let iter_arm = { - let iter_pat = - fld.cx.pat_ident_binding_mode(span, iter, ast::BindByValue(ast::MutMutable)); - fld.cx.arm(span, vec![iter_pat], loop_expr) - }; - - // `match ::std::iter::IntoIterator::into_iter() { ... }` - let into_iter_expr = { - let into_iter_path = { - let strs = fld.cx.std_path(&["iter", "IntoIterator", - "into_iter"]); - - fld.cx.path_global(span, strs) - }; - - fld.cx.expr_call(span, fld.cx.expr_path(into_iter_path), vec![head]) - }; - - let match_expr = fld.cx.expr_match(span, into_iter_expr, vec![iter_arm]); - - // `{ let result = ...; result }` - let result_ident = token::gensym_ident("result"); - let result = fld.cx.expr_block( - fld.cx.block_all( - span, - vec![fld.cx.stmt_let(span, false, result_ident, match_expr)], - Some(fld.cx.expr_ident(span, result_ident)))); - fld.cx.bt_pop(); - result + let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); + fld.cx.expr(span, ast::ExprForLoop(pat, head, body, opt_ident)) } ast::ExprClosure(capture_clause, fn_decl, block) => { -- cgit 1.4.1-3-g733a5 From bc364b4a0d678b29cba92ce948d948aee9d76b25 Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Mon, 28 Sep 2015 17:24:42 +1300 Subject: if let and while let --- src/librustc_front/lowering.rs | 169 ++++++++++++++++++++++++++++++++++++----- src/libsyntax/ext/expand.rs | 144 +---------------------------------- 2 files changed, 154 insertions(+), 159 deletions(-) (limited to 'src/libsyntax') diff --git a/src/librustc_front/lowering.rs b/src/librustc_front/lowering.rs index c8f5f89b669..d9b834fe9fc 100644 --- a/src/librustc_front/lowering.rs +++ b/src/librustc_front/lowering.rs @@ -786,10 +786,28 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { ExprAddrOf(m, ref ohs) => { hir::ExprAddrOf(lower_mutability(lctx, m), lower_expr(lctx, ohs)) } - ExprIf(ref cond, ref tr, ref fl) => { + // More complicated than you might expect because the else branch + // might be `if let`. + ExprIf(ref cond, ref blk, ref else_opt) => { + let else_opt = else_opt.as_ref().map(|els| match els.node { + ExprIfLet(..) => { + // wrap the if-let expr in a block + let span = els.span; + let blk = P(hir::Block { + stmts: vec![], + expr: Some(lower_expr(lctx, els)), + id: lctx.next_id(), + rules: hir::DefaultBlock, + span: span + }); + expr_block(lctx, blk) + } + _ => lower_expr(lctx, els) + }); + hir::ExprIf(lower_expr(lctx, cond), - lower_block(lctx, tr), - fl.as_ref().map(|x| lower_expr(lctx, x))) + lower_block(lctx, blk), + else_opt) } ExprWhile(ref cond, ref body, opt_ident) => { hir::ExprWhile(lower_expr(lctx, cond), @@ -880,16 +898,123 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { ExprInPlace(..) => { panic!("todo"); } - ExprIfLet(..) => { - panic!("todo"); + + // Desugar ExprIfLet + // From: `if let = []` + ExprIfLet(ref pat, ref sub_expr, ref body, ref else_opt) => { + // to: + // + // match { + // => , + // [_ if => ,] + // _ => [ | ()] + // } + + // ` => ` + let pat_arm = { + let body_expr = expr_block(lctx, lower_block(lctx, body)); + arm(vec![lower_pat(lctx, pat)], body_expr) + }; + + // `[_ if => ,]` + let mut else_opt = else_opt.as_ref().map(|e| lower_expr(lctx, e)); + let else_if_arms = { + let mut arms = vec![]; + loop { + let else_opt_continue = else_opt + .and_then(|els| els.and_then(|els| match els.node { + // else if + hir::ExprIf(cond, then, else_opt) => { + let pat_under = pat_wild(lctx, e.span); + arms.push(hir::Arm { + attrs: vec![], + pats: vec![pat_under], + guard: Some(cond), + body: expr_block(lctx, then) + }); + else_opt.map(|else_opt| (else_opt, true)) + } + _ => Some((P(els), false)) + })); + match else_opt_continue { + Some((e, true)) => { + else_opt = Some(e); + } + Some((e, false)) => { + else_opt = Some(e); + break; + } + None => { + else_opt = None; + break; + } + } + } + arms + }; + + let contains_else_clause = else_opt.is_some(); + + // `_ => [ | ()]` + let else_arm = { + let pat_under = pat_wild(lctx, e.span); + let else_expr = else_opt.unwrap_or_else(|| expr_tuple(lctx, e.span, vec![])); + arm(vec![pat_under], else_expr) + }; + + let mut arms = Vec::with_capacity(else_if_arms.len() + 2); + arms.push(pat_arm); + arms.extend(else_if_arms); + arms.push(else_arm); + + let match_expr = expr(lctx, + e.span, + hir::ExprMatch(lower_expr(lctx, sub_expr), arms, + hir::MatchSource::IfLetDesugar { + contains_else_clause: contains_else_clause, + })); + return match_expr; } - ExprWhileLet(..) => { - panic!("todo"); + + // Desugar ExprWhileLet + // From: `[opt_ident]: while let = ` + ExprWhileLet(ref pat, ref sub_expr, ref body, opt_ident) => { + // to: + // + // [opt_ident]: loop { + // match { + // => , + // _ => break + // } + // } + + // ` => ` + let pat_arm = { + let body_expr = expr_block(lctx, lower_block(lctx, body)); + arm(vec![lower_pat(lctx, pat)], body_expr) + }; + + // `_ => break` + let break_arm = { + let pat_under = pat_wild(lctx, e.span); + let break_expr = expr_break(lctx, e.span); + arm(vec![pat_under], break_expr) + }; + + // // `match { ... }` + let arms = vec![pat_arm, break_arm]; + let match_expr = expr(lctx, + e.span, + hir::ExprMatch(lower_expr(lctx, sub_expr), arms, hir::MatchSource::WhileLetDesugar)); + + // `[opt_ident]: loop { ... }` + let loop_block = block_expr(lctx, match_expr); + return expr(lctx, e.span, hir::ExprLoop(loop_block, opt_ident)); } // Desugar ExprForLoop // From: `[opt_ident]: for in ` - ExprForLoop(ref pat, ref head, ref body, ref opt_ident) => { + ExprForLoop(ref pat, ref head, ref body, opt_ident) => { // to: // // { @@ -952,7 +1077,7 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // `[opt_ident]: loop { ... }` let loop_block = block_expr(lctx, match_expr); - let loop_expr = expr(lctx, e.span, hir::ExprLoop(loop_block, opt_ident.clone())); + let loop_expr = expr(lctx, e.span, hir::ExprLoop(loop_block, opt_ident)); // `mut iter => { ... }` let iter_arm = { @@ -976,16 +1101,14 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // `{ let result = ...; result }` let result_ident = token::gensym_ident("result"); - let result = expr_block(lctx, - block_all(lctx, - e.span, - vec![stmt_let(lctx, - e.span, - false, - result_ident, - match_expr)], - Some(expr_ident(lctx, e.span, result_ident)))); - return result; + return expr_block(lctx, + block_all(lctx, + e.span, + vec![stmt_let(lctx, e.span, + false, + result_ident, + match_expr)], + Some(expr_ident(lctx, e.span, result_ident)))) } ExprMac(_) => panic!("Shouldn't exist here"), @@ -1137,6 +1260,10 @@ fn expr_block(lctx: &LoweringContext, b: P) -> P { expr(lctx, b.span, hir::ExprBlock(b)) } +fn expr_tuple(lctx: &LoweringContext, sp: Span, exprs: Vec>) -> P { + expr(lctx, sp, hir::ExprTup(exprs)) +} + fn expr(lctx: &LoweringContext, span: Span, node: hir::Expr_) -> P { P(hir::Expr { id: lctx.next_id(), @@ -1208,6 +1335,10 @@ fn pat_ident_binding_mode(lctx: &LoweringContext, pat(lctx, span, pat_ident) } +fn pat_wild(lctx: &LoweringContext, span: Span) -> P { + pat(lctx, span, hir::PatWild(hir::PatWildSingle)) +} + fn pat(lctx: &LoweringContext, span: Span, pat: hir::Pat_) -> P { P(hir::Pat { id: lctx.next_id(), node: pat, span: span }) } diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index 8cfad6341de..f6767bc4e47 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -212,147 +212,11 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { fld.cx.expr(span, ast::ExprWhile(cond, body, opt_ident)) } - // Desugar ExprWhileLet - // From: `[opt_ident]: while let = ` ast::ExprWhileLet(pat, expr, body, opt_ident) => { - // to: - // - // [opt_ident]: loop { - // match { - // => , - // _ => break - // } - // } - - push_compiler_expansion(fld, span, CompilerExpansionFormat::WhileLet); - - // ` => ` - let pat_arm = { - let body_expr = fld.cx.expr_block(body); - fld.cx.arm(pat.span, vec![pat], body_expr) - }; - - // `_ => break` - let break_arm = { - let pat_under = fld.cx.pat_wild(span); - let break_expr = fld.cx.expr_break(span); - fld.cx.arm(span, vec![pat_under], break_expr) - }; - - // `match { ... }` - let arms = vec![pat_arm, break_arm]; - let match_expr = fld.cx.expr(span, - ast::ExprMatch(expr, arms, ast::MatchSource::WhileLetDesugar)); - - // `[opt_ident]: loop { ... }` - let loop_block = fld.cx.block_expr(match_expr); - let (loop_block, opt_ident) = expand_loop_block(loop_block, opt_ident, fld); - let result = fld.cx.expr(span, ast::ExprLoop(loop_block, opt_ident)); - fld.cx.bt_pop(); - result - } - - // Desugar ExprIfLet - // From: `if let = []` - ast::ExprIfLet(pat, expr, body, mut elseopt) => { - // to: - // - // match { - // => , - // [_ if => ,] - // _ => [ | ()] - // } - - push_compiler_expansion(fld, span, CompilerExpansionFormat::IfLet); - - // ` => ` - let pat_arm = { - let body_expr = fld.cx.expr_block(body); - fld.cx.arm(pat.span, vec![pat], body_expr) - }; - - // `[_ if => ,]` - let else_if_arms = { - let mut arms = vec![]; - loop { - let elseopt_continue = elseopt - .and_then(|els| els.and_then(|els| match els.node { - // else if - ast::ExprIf(cond, then, elseopt) => { - let pat_under = fld.cx.pat_wild(span); - arms.push(ast::Arm { - attrs: vec![], - pats: vec![pat_under], - guard: Some(cond), - body: fld.cx.expr_block(then) - }); - elseopt.map(|elseopt| (elseopt, true)) - } - _ => Some((P(els), false)) - })); - match elseopt_continue { - Some((e, true)) => { - elseopt = Some(e); - } - Some((e, false)) => { - elseopt = Some(e); - break; - } - None => { - elseopt = None; - break; - } - } - } - arms - }; - - let contains_else_clause = elseopt.is_some(); - - // `_ => [ | ()]` - let else_arm = { - let pat_under = fld.cx.pat_wild(span); - let else_expr = elseopt.unwrap_or_else(|| fld.cx.expr_tuple(span, vec![])); - fld.cx.arm(span, vec![pat_under], else_expr) - }; - - let mut arms = Vec::with_capacity(else_if_arms.len() + 2); - arms.push(pat_arm); - arms.extend(else_if_arms); - arms.push(else_arm); - - let match_expr = fld.cx.expr(span, - ast::ExprMatch(expr, arms, - ast::MatchSource::IfLetDesugar { - contains_else_clause: contains_else_clause, - })); - let result = fld.fold_expr(match_expr); - fld.cx.bt_pop(); - result - } - - // Desugar support for ExprIfLet in the ExprIf else position - ast::ExprIf(cond, blk, elseopt) => { - let elseopt = elseopt.map(|els| els.and_then(|els| match els.node { - ast::ExprIfLet(..) => { - push_compiler_expansion(fld, span, CompilerExpansionFormat::IfLet); - // wrap the if-let expr in a block - let span = els.span; - let blk = P(ast::Block { - stmts: vec![], - expr: Some(P(els)), - id: ast::DUMMY_NODE_ID, - rules: ast::DefaultBlock, - span: span - }); - let result = fld.cx.expr_block(blk); - fld.cx.bt_pop(); - result - } - _ => P(els) - })); - let if_expr = fld.cx.expr(span, ast::ExprIf(cond, blk, elseopt)); - if_expr.map(|e| noop_fold_expr(e, fld)) + let pat = fld.fold_pat(pat); + let expr = fld.fold_expr(expr); + let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); + fld.cx.expr(span, ast::ExprWhileLet(pat, expr, body, opt_ident)) } ast::ExprLoop(loop_block, opt_ident) => { -- cgit 1.4.1-3-g733a5 From 7f469ba6c5b0167949540d6c2afe51a0454767f5 Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Tue, 29 Sep 2015 13:17:46 +1300 Subject: Move placement in desugaring to lowering --- src/librustc_front/lowering.rs | 106 +++++++++++++++++++++++++++- src/libsyntax/ext/expand.rs | 157 +---------------------------------------- 2 files changed, 106 insertions(+), 157 deletions(-) (limited to 'src/libsyntax') diff --git a/src/librustc_front/lowering.rs b/src/librustc_front/lowering.rs index d9b834fe9fc..8a8620cbcca 100644 --- a/src/librustc_front/lowering.rs +++ b/src/librustc_front/lowering.rs @@ -752,6 +752,83 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { ExprBox(ref e) => { hir::ExprBox(lower_expr(lctx, e)) } + + // Desugar ExprBox: `in (PLACE) EXPR` + ExprInPlace(Some(ref placer), ref value_expr) => { + // to: + // + // let p = PLACE; + // let mut place = Placer::make_place(p); + // let raw_place = Place::pointer(&mut place); + // push_unsafe!({ + // std::intrinsics::move_val_init(raw_place, pop_unsafe!( EXPR )); + // InPlace::finalize(place) + // }) + + // TODO + println!("{}", lctx.foo); + + let placer_expr = lower_expr(lctx, placer); + let value_expr = lower_expr(lctx, value_expr); + + let placer_ident = token::gensym_ident("placer"); + let agent_ident = token::gensym_ident("place"); + let p_ptr_ident = token::gensym_ident("p_ptr"); + + let make_place = ["ops", "Placer", "make_place"]; + let place_pointer = ["ops", "Place", "pointer"]; + let move_val_init = ["intrinsics", "move_val_init"]; + let inplace_finalize = ["ops", "InPlace", "finalize"]; + + let make_call = |lctx, p, args| { + let path = core_path(lctx, e.span, p); + let path = expr_path(lctx, path); + expr_call(lctx, e.span, path, args) + }; + + let mk_stmt_let = |lctx, bind, expr| { + stmt_let(lctx, e.span, false, bind, expr) + }; + let mk_stmt_let_mut = |lctx, bind, expr| { + stmt_let(lctx, e.span, true, bind, expr) + }; + + // let placer = ; + let s1 = mk_stmt_let(lctx, placer_ident, placer_expr); + + // let mut place = Placer::make_place(placer); + let s2 = { + let call = make_call(lctx, &make_place, vec![expr_ident(lctx, e.span, placer_ident)]); + mk_stmt_let_mut(lctx, agent_ident, call) + }; + + // let p_ptr = Place::pointer(&mut place); + let s3 = { + let args = vec![expr_mut_addr_of(lctx, e.span, expr_ident(lctx, e.span, agent_ident))]; + let call = make_call(lctx, &place_pointer, args); + mk_stmt_let(lctx, p_ptr_ident, call) + }; + + // pop_unsafe!(EXPR)); + let pop_unsafe_expr = pop_unsafe_expr(lctx, value_expr, e.span); + + // push_unsafe!({ + // ptr::write(p_ptr, pop_unsafe!()); + // InPlace::finalize(place) + // }) + let expr = { + let call_move_val_init = hir::StmtSemi(make_call( + lctx, &move_val_init, vec![expr_ident(lctx, e.span, p_ptr_ident), pop_unsafe_expr]), lctx.next_id()); + let call_move_val_init = respan(e.span, call_move_val_init); + + let call = make_call(lctx, &inplace_finalize, vec![expr_ident(lctx, e.span, agent_ident)]); + Some(push_unsafe_expr(lctx, vec![P(call_move_val_init)], call, e.span)) + }; + + let block = block_all(lctx, e.span, vec![s1, s2, s3], expr); + return expr_block(lctx, block); + } + ExprVec(ref exprs) => { hir::ExprVec(exprs.iter().map(|x| lower_expr(lctx, x)).collect()) } @@ -895,9 +972,6 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { ExprParen(ref ex) => { return lower_expr(lctx, ex); } - ExprInPlace(..) => { - panic!("todo"); - } // Desugar ExprIfLet // From: `if let = []` @@ -1393,3 +1467,29 @@ fn std_path(lctx: &LoweringContext, components: &[&str]) -> Vec { v.extend(components.iter().map(|s| str_to_ident(s))); return v } + +// Given suffix ["b","c","d"], returns path `::std::b::c::d` when +// `fld.cx.use_std`, and `::core::b::c::d` otherwise. +fn core_path(lctx: &LoweringContext, span: Span, components: &[&str]) -> hir::Path { + let idents = std_path(lctx, components); + path_global(span, idents) +} + +fn push_unsafe_expr(lctx: &LoweringContext, stmts: Vec>, + expr: P, span: Span) + -> P { + let rules = hir::PushUnsafeBlock(hir::CompilerGenerated); + expr_block(lctx, P(hir::Block { + rules: rules, span: span, id: lctx.next_id(), + stmts: stmts, expr: Some(expr), + })) +} + +fn pop_unsafe_expr(lctx: &LoweringContext, expr: P, span: Span) + -> P { + let rules = hir::PopUnsafeBlock(hir::CompilerGenerated); + expr_block(lctx, P(hir::Block { + rules: rules, span: span, id: lctx.next_id(), + stmts: vec![], expr: Some(expr), + })) +} diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index f6767bc4e47..abda406dcc8 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -20,53 +20,20 @@ use attr; use attr::AttrMetaMethods; use codemap; use codemap::{Span, Spanned, ExpnInfo, NameAndSpan, MacroBang, MacroAttribute}; -use codemap::{CompilerExpansion, CompilerExpansionFormat}; use ext::base::*; use feature_gate::{self, Features, GatedCfg}; use fold; use fold::*; use parse; use parse::token::{fresh_mark, fresh_name, intern}; -use parse::token; use ptr::P; use util::small_vector::SmallVector; use visit; use visit::Visitor; use std_inject; -// Given suffix ["b","c","d"], returns path `::std::b::c::d` when -// `fld.cx.use_std`, and `::core::b::c::d` otherwise. -fn mk_core_path(fld: &mut MacroExpander, - span: Span, - suffix: &[&'static str]) -> ast::Path { - let idents = fld.cx.std_path(suffix); - fld.cx.path_global(span, idents) -} pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { - fn push_compiler_expansion(fld: &mut MacroExpander, span: Span, - expansion_type: CompilerExpansionFormat) { - fld.cx.bt_push(ExpnInfo { - call_site: span, - callee: NameAndSpan { - format: CompilerExpansion(expansion_type), - - // This does *not* mean code generated after - // `push_compiler_expansion` is automatically exempt - // from stability lints; must also tag such code with - // an appropriate span from `fld.cx.backtrace()`. - allow_internal_unstable: true, - - span: None, - }, - }); - } - - // Sets the expn_id so that we can use unstable methods. - fn allow_unstable(fld: &mut MacroExpander, span: Span) -> Span { - Span { expn_id: fld.cx.backtrace(), ..span } - } - let expr_span = e.span; return e.and_then(|ast::Expr {id, node, span}| match node { @@ -94,118 +61,18 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { }) } - // Desugar ExprInPlace: `in PLACE { EXPR }` ast::ExprInPlace(placer, value_expr) => { - // to: - // - // let p = PLACE; - // let mut place = Placer::make_place(p); - // let raw_place = Place::pointer(&mut place); - // push_unsafe!({ - // std::intrinsics::move_val_init(raw_place, pop_unsafe!( EXPR )); - // InPlace::finalize(place) - // }) - // Ensure feature-gate is enabled feature_gate::check_for_placement_in( fld.cx.ecfg.features, &fld.cx.parse_sess.span_diagnostic, expr_span); - push_compiler_expansion(fld, expr_span, CompilerExpansionFormat::PlacementIn); - - let value_span = value_expr.span; - let placer_span = placer.span; - - let placer_expr = fld.fold_expr(placer); + let placer = fld.fold_expr(placer); let value_expr = fld.fold_expr(value_expr); - - let placer_ident = token::gensym_ident("placer"); - let agent_ident = token::gensym_ident("place"); - let p_ptr_ident = token::gensym_ident("p_ptr"); - - let placer = fld.cx.expr_ident(span, placer_ident); - let agent = fld.cx.expr_ident(span, agent_ident); - let p_ptr = fld.cx.expr_ident(span, p_ptr_ident); - - let make_place = ["ops", "Placer", "make_place"]; - let place_pointer = ["ops", "Place", "pointer"]; - let move_val_init = ["intrinsics", "move_val_init"]; - let inplace_finalize = ["ops", "InPlace", "finalize"]; - - let make_call = |fld: &mut MacroExpander, p, args| { - // We feed in the `expr_span` because codemap's span_allows_unstable - // allows the call_site span to inherit the `allow_internal_unstable` - // setting. - let span_unstable = allow_unstable(fld, expr_span); - let path = mk_core_path(fld, span_unstable, p); - let path = fld.cx.expr_path(path); - let expr_span_unstable = allow_unstable(fld, span); - fld.cx.expr_call(expr_span_unstable, path, args) - }; - - let stmt_let = |fld: &mut MacroExpander, bind, expr| { - fld.cx.stmt_let(placer_span, false, bind, expr) - }; - let stmt_let_mut = |fld: &mut MacroExpander, bind, expr| { - fld.cx.stmt_let(placer_span, true, bind, expr) - }; - - // let placer = ; - let s1 = stmt_let(fld, placer_ident, placer_expr); - - // let mut place = Placer::make_place(placer); - let s2 = { - let call = make_call(fld, &make_place, vec![placer]); - stmt_let_mut(fld, agent_ident, call) - }; - - // let p_ptr = Place::pointer(&mut place); - let s3 = { - let args = vec![fld.cx.expr_mut_addr_of(placer_span, agent.clone())]; - let call = make_call(fld, &place_pointer, args); - stmt_let(fld, p_ptr_ident, call) - }; - - // pop_unsafe!(EXPR)); - let pop_unsafe_expr = pop_unsafe_expr(fld.cx, value_expr, value_span); - - // push_unsafe!({ - // ptr::write(p_ptr, pop_unsafe!()); - // InPlace::finalize(place) - // }) - let expr = { - let call_move_val_init = StmtSemi(make_call( - fld, &move_val_init, vec![p_ptr, pop_unsafe_expr]), ast::DUMMY_NODE_ID); - let call_move_val_init = codemap::respan(value_span, call_move_val_init); - - let call = make_call(fld, &inplace_finalize, vec![agent]); - Some(push_unsafe_expr(fld.cx, vec![P(call_move_val_init)], call, span)) - }; - - let block = fld.cx.block_all(span, vec![s1, s2, s3], expr); - let result = fld.cx.expr_block(block); - fld.cx.bt_pop(); - result + fld.cx.expr(span, ast::ExprBox(Some(placer), value_expr)) } - // Issue #22181: - // Eventually a desugaring for `box EXPR` - // (similar to the desugaring above for `in PLACE BLOCK`) - // should go here, desugaring - // - // to: - // - // let mut place = BoxPlace::make_place(); - // let raw_place = Place::pointer(&mut place); - // let value = $value; - // unsafe { - // ::std::ptr::write(raw_place, value); - // Boxed::finalize(place) - // } - // - // But for now there are type-inference issues doing that. - ast::ExprWhile(cond, body, opt_ident) => { let cond = fld.fold_expr(cond); let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); @@ -225,6 +92,7 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { } ast::ExprForLoop(pat, head, body, opt_ident) => { + let pat = fld.fold_pat(pat); let head = fld.fold_expr(head); let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); fld.cx.expr(span, ast::ExprForLoop(pat, head, body, opt_ident)) @@ -247,25 +115,6 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { }, fld)) } }); - - fn push_unsafe_expr(cx: &mut ExtCtxt, stmts: Vec>, - expr: P, span: Span) - -> P { - let rules = ast::PushUnsafeBlock(ast::CompilerGenerated); - cx.expr_block(P(ast::Block { - rules: rules, span: span, id: ast::DUMMY_NODE_ID, - stmts: stmts, expr: Some(expr), - })) - } - - fn pop_unsafe_expr(cx: &mut ExtCtxt, expr: P, span: Span) - -> P { - let rules = ast::PopUnsafeBlock(ast::CompilerGenerated); - cx.expr_block(P(ast::Block { - rules: rules, span: span, id: ast::DUMMY_NODE_ID, - stmts: vec![], expr: Some(expr), - })) - } } /// Expand a (not-ident-style) macro invocation. Returns the result -- cgit 1.4.1-3-g733a5 From e0c74868c3964abdd6898886e7d12041c8b3139d Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Tue, 29 Sep 2015 13:46:01 +1300 Subject: Fix stability --- src/librustc/middle/effect.rs | 2 +- src/librustc/middle/stability.rs | 31 +++++++++++++++-- src/librustc_front/hir.rs | 3 ++ src/librustc_front/lowering.rs | 68 ++++++++++++++++++++++++++------------ src/librustc_front/print/pprust.rs | 8 +++-- src/librustc_typeck/check/mod.rs | 2 +- src/libsyntax/ext/expand.rs | 2 +- src/libsyntax/feature_gate.rs | 2 +- 8 files changed, 87 insertions(+), 31 deletions(-) (limited to 'src/libsyntax') diff --git a/src/librustc/middle/effect.rs b/src/librustc/middle/effect.rs index 8a206e3d88e..f849580871c 100644 --- a/src/librustc/middle/effect.rs +++ b/src/librustc/middle/effect.rs @@ -102,7 +102,6 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> { fn visit_block(&mut self, block: &hir::Block) { let old_unsafe_context = self.unsafe_context; match block.rules { - hir::DefaultBlock => {} hir::UnsafeBlock(source) => { // By default only the outermost `unsafe` block is // "used" and so nested unsafe blocks are pointless @@ -131,6 +130,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> { self.unsafe_context.push_unsafe_count = self.unsafe_context.push_unsafe_count.checked_sub(1).unwrap(); } + hir::DefaultBlock | hir::PushUnstableBlock | hir:: PopUnstableBlock => {} } visit::walk_block(self, block); diff --git a/src/librustc/middle/stability.rs b/src/librustc/middle/stability.rs index be227e620b8..c2235591cee 100644 --- a/src/librustc/middle/stability.rs +++ b/src/librustc/middle/stability.rs @@ -270,7 +270,8 @@ pub fn check_unstable_api_usage(tcx: &ty::ctxt) let mut checker = Checker { tcx: tcx, active_features: active_features, - used_features: FnvHashMap() + used_features: FnvHashMap(), + in_skip_block: 0, }; let krate = tcx.map.krate(); @@ -283,14 +284,23 @@ pub fn check_unstable_api_usage(tcx: &ty::ctxt) struct Checker<'a, 'tcx: 'a> { tcx: &'a ty::ctxt<'tcx>, active_features: FnvHashSet, - used_features: FnvHashMap + used_features: FnvHashMap, + // Within a block where feature gate checking can be skipped. + in_skip_block: u32, } impl<'a, 'tcx> Checker<'a, 'tcx> { fn check(&mut self, id: DefId, span: Span, stab: &Option<&Stability>) { // Only the cross-crate scenario matters when checking unstable APIs let cross_crate = !id.is_local(); - if !cross_crate { return } + if !cross_crate { + return + } + + // We don't need to check for stability - presumably compiler generated code. + if self.in_skip_block > 0 { + return; + } match *stab { Some(&Stability { level: attr::Unstable, ref feature, ref reason, issue, .. }) => { @@ -369,6 +379,21 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Checker<'a, 'tcx> { &mut |id, sp, stab| self.check(id, sp, stab)); visit::walk_pat(self, pat) } + + fn visit_block(&mut self, b: &hir::Block) { + let old_skip_count = self.in_skip_block; + match b.rules { + hir::BlockCheckMode::PushUnstableBlock => { + self.in_skip_block += 1; + } + hir::BlockCheckMode::PopUnstableBlock => { + self.in_skip_block = self.in_skip_block.checked_sub(1).unwrap(); + } + _ => {} + } + visit::walk_block(self, b); + self.in_skip_block = old_skip_count; + } } /// Helper for discovering nodes to check for stability diff --git a/src/librustc_front/hir.rs b/src/librustc_front/hir.rs index a89bc26ec09..c9f13da0633 100644 --- a/src/librustc_front/hir.rs +++ b/src/librustc_front/hir.rs @@ -574,6 +574,9 @@ pub enum BlockCheckMode { UnsafeBlock(UnsafeSource), PushUnsafeBlock(UnsafeSource), PopUnsafeBlock(UnsafeSource), + // Within this block (but outside a PopUnstableBlock), we suspend checking of stability. + PushUnstableBlock, + PopUnstableBlock, } #[derive(Clone, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug, Copy)] diff --git a/src/librustc_front/lowering.rs b/src/librustc_front/lowering.rs index 8a8620cbcca..2b63e0615ee 100644 --- a/src/librustc_front/lowering.rs +++ b/src/librustc_front/lowering.rs @@ -749,12 +749,28 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { P(hir::Expr { id: e.id, node: match e.node { + // Issue #22181: + // Eventually a desugaring for `box EXPR` + // (similar to the desugaring above for `in PLACE BLOCK`) + // should go here, desugaring + // + // to: + // + // let mut place = BoxPlace::make_place(); + // let raw_place = Place::pointer(&mut place); + // let value = $value; + // unsafe { + // ::std::ptr::write(raw_place, value); + // Boxed::finalize(place) + // } + // + // But for now there are type-inference issues doing that. ExprBox(ref e) => { hir::ExprBox(lower_expr(lctx, e)) } // Desugar ExprBox: `in (PLACE) EXPR` - ExprInPlace(Some(ref placer), ref value_expr) => { + ExprInPlace(ref placer, ref value_expr) => { // to: // // let p = PLACE; @@ -810,23 +826,43 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { }; // pop_unsafe!(EXPR)); - let pop_unsafe_expr = pop_unsafe_expr(lctx, value_expr, e.span); + let pop_unsafe_expr = + signal_block_expr(lctx, + vec![], + signal_block_expr(lctx, + vec![], + value_expr, + e.span, + hir::PopUnstableBlock), + e.span, + hir::PopUnsafeBlock(hir::CompilerGenerated)); // push_unsafe!({ - // ptr::write(p_ptr, pop_unsafe!()); + // std::intrinsics::move_val_init(raw_place, pop_unsafe!( EXPR )); // InPlace::finalize(place) // }) let expr = { - let call_move_val_init = hir::StmtSemi(make_call( - lctx, &move_val_init, vec![expr_ident(lctx, e.span, p_ptr_ident), pop_unsafe_expr]), lctx.next_id()); + let call_move_val_init = + hir::StmtSemi(make_call(lctx, + &move_val_init, + vec![expr_ident(lctx, e.span, p_ptr_ident), + pop_unsafe_expr]), + lctx.next_id()); let call_move_val_init = respan(e.span, call_move_val_init); let call = make_call(lctx, &inplace_finalize, vec![expr_ident(lctx, e.span, agent_ident)]); - Some(push_unsafe_expr(lctx, vec![P(call_move_val_init)], call, e.span)) + signal_block_expr(lctx, + vec![P(call_move_val_init)], + call, + e.span, + hir::PushUnsafeBlock(hir::CompilerGenerated)) }; - let block = block_all(lctx, e.span, vec![s1, s2, s3], expr); - return expr_block(lctx, block); + return signal_block_expr(lctx, + vec![s1, s2, s3], + expr, + e.span, + hir::PushUnstableBlock); } ExprVec(ref exprs) => { @@ -1475,21 +1511,9 @@ fn core_path(lctx: &LoweringContext, span: Span, components: &[&str]) -> hir::Pa path_global(span, idents) } -fn push_unsafe_expr(lctx: &LoweringContext, stmts: Vec>, - expr: P, span: Span) - -> P { - let rules = hir::PushUnsafeBlock(hir::CompilerGenerated); +fn signal_block_expr(lctx: &LoweringContext, stmts: Vec>, expr: P, span: Span, rule: hir::BlockCheckMode) -> P { expr_block(lctx, P(hir::Block { - rules: rules, span: span, id: lctx.next_id(), + rules: rule, span: span, id: lctx.next_id(), stmts: stmts, expr: Some(expr), })) } - -fn pop_unsafe_expr(lctx: &LoweringContext, expr: P, span: Span) - -> P { - let rules = hir::PopUnsafeBlock(hir::CompilerGenerated); - expr_block(lctx, P(hir::Block { - rules: rules, span: span, id: lctx.next_id(), - stmts: vec![], expr: Some(expr), - })) -} diff --git a/src/librustc_front/print/pprust.rs b/src/librustc_front/print/pprust.rs index db0981728ac..80b0a984681 100644 --- a/src/librustc_front/print/pprust.rs +++ b/src/librustc_front/print/pprust.rs @@ -1089,8 +1089,12 @@ impl<'a> State<'a> { close_box: bool) -> io::Result<()> { match blk.rules { - hir::UnsafeBlock(..) | hir::PushUnsafeBlock(..) => try!(self.word_space("unsafe")), - hir::DefaultBlock | hir::PopUnsafeBlock(..) => (), + hir::UnsafeBlock(..) => try!(self.word_space("unsafe")), + hir::PushUnsafeBlock(..) => try!(self.word_space("push_unsafe")), + hir::PopUnsafeBlock(..) => try!(self.word_space("pop_unsafe")), + hir::PushUnstableBlock => try!(self.word_space("push_unstable")), + hir::PopUnstableBlock => try!(self.word_space("pop_unstable")), + hir::DefaultBlock => (), } try!(self.maybe_print_comment(blk.span.lo)); try!(self.ann.pre(self, NodeBlock(blk))); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 278aa9450ee..0978ea2295b 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -269,7 +269,7 @@ impl UnsafetyState { (unsafety, blk.id, self.unsafe_push_count.checked_sub(1).unwrap()), hir::UnsafeBlock(..) => (hir::Unsafety::Unsafe, blk.id, self.unsafe_push_count), - hir::DefaultBlock => + hir::DefaultBlock | hir::PushUnstableBlock | hir:: PopUnstableBlock => (unsafety, self.def, self.unsafe_push_count), }; UnsafetyState{ def: def, diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index abda406dcc8..72d89e246ad 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -70,7 +70,7 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { let placer = fld.fold_expr(placer); let value_expr = fld.fold_expr(value_expr); - fld.cx.expr(span, ast::ExprBox(Some(placer), value_expr)) + fld.cx.expr(span, ast::ExprInPlace(placer, value_expr)) } ast::ExprWhile(cond, body, opt_ident) => { diff --git a/src/libsyntax/feature_gate.rs b/src/libsyntax/feature_gate.rs index 18c6d74d62e..49835afbfa5 100644 --- a/src/libsyntax/feature_gate.rs +++ b/src/libsyntax/feature_gate.rs @@ -726,7 +726,7 @@ impl<'a, 'v> Visitor<'v> for MacroVisitor<'a> { } struct PostExpansionVisitor<'a> { - context: &'a Context<'a> + context: &'a Context<'a>, } impl<'a> PostExpansionVisitor<'a> { -- cgit 1.4.1-3-g733a5 From 08f3752270098fb26ff41fc2e5cfbeca2dffeec0 Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Wed, 30 Sep 2015 12:19:45 +1300 Subject: hygiene for `for` loops, `if let`, `while let` and some unrelated test cleanups --- src/librustc/middle/region.rs | 2 +- src/librustc_lint/unused.rs | 10 +-- src/librustc_typeck/check/mod.rs | 2 +- src/libsyntax/ext/expand.rs | 87 ++++++++++++++++++---- src/test/compile-fail/for-expn-2.rs | 18 ----- .../for-loop-refutable-pattern-error-message.rs | 4 +- src/test/compile-fail/issue-15167.rs | 13 ++++ src/test/compile-fail/issue-15381.rs | 6 +- 8 files changed, 94 insertions(+), 48 deletions(-) delete mode 100644 src/test/compile-fail/for-expn-2.rs (limited to 'src/libsyntax') diff --git a/src/librustc/middle/region.rs b/src/librustc/middle/region.rs index 0f9ba50e788..bdf01f941c4 100644 --- a/src/librustc/middle/region.rs +++ b/src/librustc/middle/region.rs @@ -377,7 +377,7 @@ impl RegionMaps { self.code_extents.borrow()[e.0 as usize] } pub fn each_encl_scope(&self, mut e:E) where E: FnMut(&CodeExtent, &CodeExtent) { - for child_id in (1..self.code_extents.borrow().len()) { + for child_id in 1..self.code_extents.borrow().len() { let child = CodeExtent(child_id as u32); if let Some(parent) = self.opt_encl_scope(child) { e(&child, &parent) diff --git a/src/librustc_lint/unused.rs b/src/librustc_lint/unused.rs index e63bc5f7c4f..9c030d8892a 100644 --- a/src/librustc_lint/unused.rs +++ b/src/librustc_lint/unused.rs @@ -363,12 +363,10 @@ impl EarlyLintPass for UnusedParens { let (value, msg, struct_lit_needs_parens) = match e.node { ast::ExprIf(ref cond, _, _) => (cond, "`if` condition", true), ast::ExprWhile(ref cond, _, _) => (cond, "`while` condition", true), - ast::ExprMatch(ref head, _, source) => match source { - ast::MatchSource::Normal => (head, "`match` head expression", true), - ast::MatchSource::IfLetDesugar { .. } => (head, "`if let` head expression", true), - ast::MatchSource::WhileLetDesugar => (head, "`while let` head expression", true), - ast::MatchSource::ForLoopDesugar => (head, "`for` head expression", true), - }, + ast::ExprIfLet(_, ref cond, _, _) => (cond, "`if let` head expression", true), + ast::ExprWhileLet(_, ref cond, _, _) => (cond, "`while let` head expression", true), + ast::ExprForLoop(_, ref cond, _, _) => (cond, "`for` head expression", true), + ast::ExprMatch(ref head, _, _) => (head, "`match` head expression", true), ast::ExprRet(Some(ref value)) => (value, "`return` value", false), ast::ExprAssign(_, ref value) => (value, "assigned value", false), ast::ExprAssignOp(_, _, ref value) => (value, "assigned value", false), diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 0978ea2295b..705b564a1ad 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1810,7 +1810,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { // There is a possibility that this algorithm will have to run an arbitrary number of times // to terminate so we bound it by the compiler's recursion limit. - for _ in (0..self.tcx().sess.recursion_limit.get()) { + for _ in 0..self.tcx().sess.recursion_limit.get() { // First we try to solve all obligations, it is possible that the last iteration // has made it possible to make more progress. self.select_obligations_where_possible(); diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index 72d89e246ad..b1b4605d5ec 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -82,8 +82,18 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { ast::ExprWhileLet(pat, expr, body, opt_ident) => { let pat = fld.fold_pat(pat); let expr = fld.fold_expr(expr); - let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); - fld.cx.expr(span, ast::ExprWhileLet(pat, expr, body, opt_ident)) + + // Hygienic renaming of the body. + let ((body, opt_ident), mut rewritten_pats) = + rename_in_scope(vec![pat], + fld, + (body, opt_ident), + |rename_fld, fld, (body, opt_ident)| { + expand_loop_block(rename_fld.fold_block(body), opt_ident, fld) + }); + assert!(rewritten_pats.len() == 1); + + fld.cx.expr(span, ast::ExprWhileLet(rewritten_pats.remove(0), expr, body, opt_ident)) } ast::ExprLoop(loop_block, opt_ident) => { @@ -93,9 +103,37 @@ pub fn expand_expr(e: P, fld: &mut MacroExpander) -> P { ast::ExprForLoop(pat, head, body, opt_ident) => { let pat = fld.fold_pat(pat); + + // Hygienic renaming of the for loop body (for loop binds its pattern). + let ((body, opt_ident), mut rewritten_pats) = + rename_in_scope(vec![pat], + fld, + (body, opt_ident), + |rename_fld, fld, (body, opt_ident)| { + expand_loop_block(rename_fld.fold_block(body), opt_ident, fld) + }); + assert!(rewritten_pats.len() == 1); + let head = fld.fold_expr(head); - let (body, opt_ident) = expand_loop_block(body, opt_ident, fld); - fld.cx.expr(span, ast::ExprForLoop(pat, head, body, opt_ident)) + fld.cx.expr(span, ast::ExprForLoop(rewritten_pats.remove(0), head, body, opt_ident)) + } + + ast::ExprIfLet(pat, sub_expr, body, else_opt) => { + let pat = fld.fold_pat(pat); + + // Hygienic renaming of the body. + let (body, mut rewritten_pats) = + rename_in_scope(vec![pat], + fld, + body, + |rename_fld, fld, body| { + fld.fold_block(rename_fld.fold_block(body)) + }); + assert!(rewritten_pats.len() == 1); + + let else_opt = else_opt.map(|else_opt| fld.fold_expr(else_opt)); + let sub_expr = fld.fold_expr(sub_expr); + fld.cx.expr(span, ast::ExprIfLet(rewritten_pats.remove(0), sub_expr, body, else_opt)) } ast::ExprClosure(capture_clause, fn_decl, block) => { @@ -569,18 +607,18 @@ fn expand_arm(arm: ast::Arm, fld: &mut MacroExpander) -> ast::Arm { if expanded_pats.is_empty() { panic!("encountered match arm with 0 patterns"); } - // all of the pats must have the same set of bindings, so use the - // first one to extract them and generate new names: - let idents = pattern_bindings(&*expanded_pats[0]); - let new_renames = idents.into_iter().map(|id| (id, fresh_name(id))).collect(); - // apply the renaming, but only to the PatIdents: - let mut rename_pats_fld = PatIdentRenamer{renames:&new_renames}; - let rewritten_pats = expanded_pats.move_map(|pat| rename_pats_fld.fold_pat(pat)); + // apply renaming and then expansion to the guard and the body: - let mut rename_fld = IdentRenamer{renames:&new_renames}; - let rewritten_guard = - arm.guard.map(|g| fld.fold_expr(rename_fld.fold_expr(g))); - let rewritten_body = fld.fold_expr(rename_fld.fold_expr(arm.body)); + let ((rewritten_guard, rewritten_body), rewritten_pats) = + rename_in_scope(expanded_pats, + fld, + (arm.guard, arm.body), + |rename_fld, fld, (ag, ab)|{ + let rewritten_guard = ag.map(|g| fld.fold_expr(rename_fld.fold_expr(g))); + let rewritten_body = fld.fold_expr(rename_fld.fold_expr(ab)); + (rewritten_guard, rewritten_body) + }); + ast::Arm { attrs: fold::fold_attrs(arm.attrs, fld), pats: rewritten_pats, @@ -589,6 +627,25 @@ fn expand_arm(arm: ast::Arm, fld: &mut MacroExpander) -> ast::Arm { } } +fn rename_in_scope(pats: Vec>, + fld: &mut MacroExpander, + x: X, + f: F) + -> (X, Vec>) + where F: Fn(&mut IdentRenamer, &mut MacroExpander, X) -> X +{ + // all of the pats must have the same set of bindings, so use the + // first one to extract them and generate new names: + let idents = pattern_bindings(&*pats[0]); + let new_renames = idents.into_iter().map(|id| (id, fresh_name(id))).collect(); + // apply the renaming, but only to the PatIdents: + let mut rename_pats_fld = PatIdentRenamer{renames:&new_renames}; + let rewritten_pats = pats.move_map(|pat| rename_pats_fld.fold_pat(pat)); + + let mut rename_fld = IdentRenamer{ renames:&new_renames }; + (f(&mut rename_fld, fld, x), rewritten_pats) +} + /// A visitor that extracts the PatIdent (binding) paths /// from a given thingy and puts them in a mutable /// array diff --git a/src/test/compile-fail/for-expn-2.rs b/src/test/compile-fail/for-expn-2.rs deleted file mode 100644 index ce2315f3a38..00000000000 --- a/src/test/compile-fail/for-expn-2.rs +++ /dev/null @@ -1,18 +0,0 @@ -// Copyright 2015 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 or the MIT license -// , at your -// option. This file may not be copied, modified, or distributed -// except according to those terms. - -// Test that we get an expansion stack for `for` loops. - -// error-pattern:in this expansion of for loop expansion - -fn main() { - for t in &foo { - } -} diff --git a/src/test/compile-fail/for-loop-refutable-pattern-error-message.rs b/src/test/compile-fail/for-loop-refutable-pattern-error-message.rs index ab6dc2bab3e..81c4db68628 100644 --- a/src/test/compile-fail/for-loop-refutable-pattern-error-message.rs +++ b/src/test/compile-fail/for-loop-refutable-pattern-error-message.rs @@ -9,7 +9,5 @@ // except according to those terms. fn main() { - for - &1 //~ ERROR refutable pattern in `for` loop binding - in [1].iter() {} + for &1 in [1].iter() {} //~ ERROR refutable pattern in `for` loop binding } diff --git a/src/test/compile-fail/issue-15167.rs b/src/test/compile-fail/issue-15167.rs index a1663772bad..898e6be6fc8 100644 --- a/src/test/compile-fail/issue-15167.rs +++ b/src/test/compile-fail/issue-15167.rs @@ -16,4 +16,17 @@ fn main() -> (){ for n in 0..1 { println!("{}", f!()); //~ ERROR unresolved name `n` } + + if let Some(n) = None { + println!("{}", f!()); //~ ERROR unresolved name `n` + } + + if false { + } else if let Some(n) = None { + println!("{}", f!()); //~ ERROR unresolved name `n` + } + + while let Some(n) = None { + println!("{}", f!()); //~ ERROR unresolved name `n` + } } diff --git a/src/test/compile-fail/issue-15381.rs b/src/test/compile-fail/issue-15381.rs index 653ba165e74..ec29a84f44e 100644 --- a/src/test/compile-fail/issue-15381.rs +++ b/src/test/compile-fail/issue-15381.rs @@ -13,10 +13,8 @@ fn main() { let values: Vec = vec![1,2,3,4,5,6,7,8]; - for - [x,y,z] -//~^ ERROR refutable pattern in `for` loop binding: `[]` not covered - in values.chunks(3).filter(|&xs| xs.len() == 3) { + for [x,y,z] in values.chunks(3).filter(|&xs| xs.len() == 3) { + //~^ ERROR refutable pattern in `for` loop binding: `[]` not covered println!("y={}", y); } } -- cgit 1.4.1-3-g733a5 From 21205f4f9e61469b55a853cf6be478cd6bc7a073 Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Wed, 30 Sep 2015 16:17:37 +1300 Subject: Cache ids between lowering runs So that lowering is reproducible --- src/librustc/session/mod.rs | 4 ++ src/librustc_driver/driver.rs | 9 ++-- src/librustc_driver/pretty.rs | 3 +- src/librustc_front/lowering.rs | 83 +++++++++++++++++++++++++++++++------ src/librustc_trans/save/dump_csv.rs | 2 +- src/librustc_trans/save/mod.rs | 8 ++-- src/libsyntax/ast.rs | 1 + 7 files changed, 86 insertions(+), 24 deletions(-) (limited to 'src/libsyntax') diff --git a/src/librustc/session/mod.rs b/src/librustc/session/mod.rs index 1eb90580b48..0a1df25f115 100644 --- a/src/librustc/session/mod.rs +++ b/src/librustc/session/mod.rs @@ -318,6 +318,10 @@ impl NodeIdAssigner for Session { fn next_node_id(&self) -> NodeId { self.reserve_node_ids(1) } + + fn peek_node_id(&self) -> NodeId { + self.next_node_id.get().checked_add(1).unwrap() + } } fn split_msg_into_multilines(msg: &str) -> Option { diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index 6f989811ed2..3db484ef930 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -112,8 +112,7 @@ pub fn compile_input(sess: Session, let expanded_crate = assign_node_ids(&sess, expanded_crate); // Lower ast -> hir. - let foo = &42; - let lcx = LoweringContext::new(foo, &sess, &expanded_crate); + let lcx = LoweringContext::new(&sess, &expanded_crate); let mut hir_forest = time(sess.time_passes(), "lowering ast -> hir", || hir_map::Forest::new(lower_crate(&lcx, &expanded_crate))); @@ -282,7 +281,7 @@ pub struct CompileState<'a, 'ast: 'a, 'tcx: 'a> { pub ast_map: Option<&'a hir_map::Map<'ast>>, pub analysis: Option<&'a ty::CrateAnalysis>, pub tcx: Option<&'a ty::ctxt<'tcx>>, - pub lcx: Option<&'a LoweringContext<'a, 'tcx>>, + pub lcx: Option<&'a LoweringContext<'a>>, pub trans: Option<&'a trans::CrateTranslation>, } @@ -340,7 +339,7 @@ impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> { krate: &'a ast::Crate, hir_crate: &'a hir::Crate, crate_name: &'a str, - lcx: &'a LoweringContext<'a, 'tcx>) + lcx: &'a LoweringContext<'a>) -> CompileState<'a, 'ast, 'tcx> { CompileState { crate_name: Some(crate_name), @@ -359,7 +358,7 @@ impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> { hir_crate: &'a hir::Crate, analysis: &'a ty::CrateAnalysis, tcx: &'a ty::ctxt<'tcx>, - lcx: &'a LoweringContext<'a, 'tcx>) + lcx: &'a LoweringContext<'a>) -> CompileState<'a, 'ast, 'tcx> { CompileState { analysis: Some(analysis), diff --git a/src/librustc_driver/pretty.rs b/src/librustc_driver/pretty.rs index 09a1d6f6851..73961c8d757 100644 --- a/src/librustc_driver/pretty.rs +++ b/src/librustc_driver/pretty.rs @@ -670,8 +670,7 @@ pub fn pretty_print_input(sess: Session, // There is some twisted, god-forsaken tangle of lifetimes here which makes // the ordering of stuff super-finicky. let mut hir_forest; - let foo = &42; - let lcx = LoweringContext::new(foo, &sess, &krate); + let lcx = LoweringContext::new(&sess, &krate); let arenas = ty::CtxtArenas::new(); let ast_map = if compute_ast_map { hir_forest = hir_map::Forest::new(lower_crate(&lcx, &krate)); diff --git a/src/librustc_front/lowering.rs b/src/librustc_front/lowering.rs index 2b63e0615ee..27ae39acbf4 100644 --- a/src/librustc_front/lowering.rs +++ b/src/librustc_front/lowering.rs @@ -12,6 +12,8 @@ use hir; +use std::collections::HashMap; + use syntax::ast::*; use syntax::ptr::P; use syntax::codemap::{respan, Spanned, Span}; @@ -19,15 +21,17 @@ use syntax::owned_slice::OwnedSlice; use syntax::parse::token::{self, str_to_ident}; use syntax::std_inject; -pub struct LoweringContext<'a, 'hir> { - // TODO - foo: &'hir i32, - id_assigner: &'a NodeIdAssigner, +use std::cell::{Cell, RefCell}; + +pub struct LoweringContext<'a> { crate_root: Option<&'static str>, + id_cache: RefCell>, + id_assigner: &'a NodeIdAssigner, + cached_id: Cell, } -impl<'a, 'hir> LoweringContext<'a, 'hir> { - pub fn new(foo: &'hir i32, id_assigner: &'a NodeIdAssigner, c: &Crate) -> LoweringContext<'a, 'hir> { +impl<'a, 'hir> LoweringContext<'a> { + pub fn new(id_assigner: &'a NodeIdAssigner, c: &Crate) -> LoweringContext<'a> { let crate_root = if std_inject::no_core(c) { None } else if std_inject::no_std(c) { @@ -37,14 +41,21 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { }; LoweringContext { - foo: foo, - id_assigner: id_assigner, crate_root: crate_root, + id_cache: RefCell::new(HashMap::new()), + id_assigner: id_assigner, + cached_id: Cell::new(0), } } fn next_id(&self) -> NodeId { - self.id_assigner.next_node_id() + let cached = self.cached_id.get(); + if cached == 0 { + return self.id_assigner.next_node_id() + } + + self.cached_id.set(cached + 1); + cached } } @@ -745,6 +756,49 @@ pub fn lower_pat(_lctx: &LoweringContext, p: &Pat) -> P { }) } +// RAII utility for setting and unsetting the cached id. +struct CachedIdSetter<'a> { + reset: bool, + lctx: &'a LoweringContext<'a>, +} + +impl<'a> CachedIdSetter<'a> { + fn new(lctx: &'a LoweringContext, expr_id: NodeId) -> CachedIdSetter<'a> { + let id_cache: &mut HashMap<_, _> = &mut lctx.id_cache.borrow_mut(); + + if id_cache.contains_key(&expr_id) { + let cached_id = lctx.cached_id.get(); + if cached_id == 0 { + // We're entering a node where we need to track ids, but are not + // yet tracking. + lctx.cached_id.set(id_cache[&expr_id]); + } else { + // We're already tracking - check that the tracked id is the same + // as the expected id. + assert!(cached_id == id_cache[&expr_id], "id mismatch"); + } + } else { + id_cache.insert(expr_id, lctx.id_assigner.peek_node_id()); + } + + CachedIdSetter { + // Only reset the id if it was previously 0, i.e., was not cached. + // If it was cached, we are in a nested node, but our id count will + // still count towards the parent's count. + reset: lctx.cached_id.get() == 0, + lctx: lctx, + } + } +} + +impl<'a> Drop for CachedIdSetter<'a> { + fn drop(&mut self) { + if self.reset { + self.lctx.cached_id.set(0); + } + } +} + pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { P(hir::Expr { id: e.id, @@ -780,9 +834,7 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // std::intrinsics::move_val_init(raw_place, pop_unsafe!( EXPR )); // InPlace::finalize(place) // }) - - // TODO - println!("{}", lctx.foo); + let _old_cached = CachedIdSetter::new(lctx, e.id); let placer_expr = lower_expr(lctx, placer); let value_expr = lower_expr(lctx, value_expr); @@ -903,6 +955,7 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // might be `if let`. ExprIf(ref cond, ref blk, ref else_opt) => { let else_opt = else_opt.as_ref().map(|els| match els.node { + let _old_cached = CachedIdSetter::new(lctx, e.id); ExprIfLet(..) => { // wrap the if-let expr in a block let span = els.span; @@ -1019,6 +1072,8 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // [_ if => ,] // _ => [ | ()] // } + + let _old_cached = CachedIdSetter::new(lctx, e.id); // ` => ` let pat_arm = { @@ -1098,6 +1153,8 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // } // } + let _old_cached = CachedIdSetter::new(lctx, e.id); + // ` => ` let pat_arm = { let body_expr = expr_block(lctx, lower_block(lctx, body)); @@ -1141,6 +1198,8 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // result // } + let _old_cached = CachedIdSetter::new(lctx, e.id); + // expand let head = lower_expr(lctx, head); diff --git a/src/librustc_trans/save/dump_csv.rs b/src/librustc_trans/save/dump_csv.rs index 256774756b8..09825f1f919 100644 --- a/src/librustc_trans/save/dump_csv.rs +++ b/src/librustc_trans/save/dump_csv.rs @@ -76,7 +76,7 @@ pub struct DumpCsvVisitor<'l, 'tcx: 'l> { impl <'l, 'tcx> DumpCsvVisitor<'l, 'tcx> { pub fn new(tcx: &'l ty::ctxt<'tcx>, - lcx: &'l LoweringContext<'l, 'tcx>, + lcx: &'l LoweringContext<'l>, analysis: &'l ty::CrateAnalysis, output_file: Box) -> DumpCsvVisitor<'l, 'tcx> { diff --git a/src/librustc_trans/save/mod.rs b/src/librustc_trans/save/mod.rs index 5e26322ebda..72f665f63bf 100644 --- a/src/librustc_trans/save/mod.rs +++ b/src/librustc_trans/save/mod.rs @@ -38,7 +38,7 @@ mod dump_csv; pub struct SaveContext<'l, 'tcx: 'l> { tcx: &'l ty::ctxt<'tcx>, - lcx: &'l lowering::LoweringContext<'l, 'tcx>, + lcx: &'l lowering::LoweringContext<'l>, span_utils: SpanUtils<'l>, } @@ -178,14 +178,14 @@ pub struct MethodCallData { impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> { pub fn new(tcx: &'l ty::ctxt<'tcx>, - lcx: &'l lowering::LoweringContext<'l, 'tcx>) + lcx: &'l lowering::LoweringContext<'l>) -> SaveContext<'l, 'tcx> { let span_utils = SpanUtils::new(&tcx.sess); SaveContext::from_span_utils(tcx, lcx, span_utils) } pub fn from_span_utils(tcx: &'l ty::ctxt<'tcx>, - lcx: &'l lowering::LoweringContext<'l, 'tcx>, + lcx: &'l lowering::LoweringContext<'l>, span_utils: SpanUtils<'l>) -> SaveContext<'l, 'tcx> { SaveContext { @@ -711,7 +711,7 @@ impl<'v> Visitor<'v> for PathCollector { } pub fn process_crate<'l, 'tcx>(tcx: &'l ty::ctxt<'tcx>, - lcx: &'l lowering::LoweringContext<'l, 'tcx>, + lcx: &'l lowering::LoweringContext<'l>, krate: &ast::Crate, analysis: &ty::CrateAnalysis, odir: Option<&Path>) { diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index bf43b87b267..02cd648b6d8 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -377,6 +377,7 @@ pub const DUMMY_NODE_ID: NodeId = !0; pub trait NodeIdAssigner { fn next_node_id(&self) -> NodeId; + fn peek_node_id(&self) -> NodeId; } /// The AST represents all type param bounds as types. -- cgit 1.4.1-3-g733a5 From ba43c228b55d9620d3d480246ee2d9295484a336 Mon Sep 17 00:00:00 2001 From: Nick Cameron Date: Wed, 30 Sep 2015 17:18:09 +1300 Subject: Some cleanup of no longer used AST things --- src/librustc_front/lowering.rs | 17 +++-------------- src/librustc_lint/unused.rs | 2 +- src/librustdoc/core.rs | 3 +-- src/librustdoc/test.rs | 3 +-- src/libsyntax/ast.rs | 13 ++----------- src/libsyntax/codemap.rs | 22 ---------------------- src/libsyntax/config.rs | 4 ++-- src/libsyntax/diagnostic.rs | 1 - src/libsyntax/ext/base.rs | 7 ++----- src/libsyntax/ext/build.rs | 2 +- src/libsyntax/fold.rs | 5 ++--- src/libsyntax/parse/parser.rs | 4 ++-- src/libsyntax/print/pprust.rs | 2 +- src/libsyntax/visit.rs | 2 +- 14 files changed, 19 insertions(+), 68 deletions(-) (limited to 'src/libsyntax') diff --git a/src/librustc_front/lowering.rs b/src/librustc_front/lowering.rs index 27ae39acbf4..546b298a92b 100644 --- a/src/librustc_front/lowering.rs +++ b/src/librustc_front/lowering.rs @@ -955,8 +955,8 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { // might be `if let`. ExprIf(ref cond, ref blk, ref else_opt) => { let else_opt = else_opt.as_ref().map(|els| match els.node { - let _old_cached = CachedIdSetter::new(lctx, e.id); ExprIfLet(..) => { + let _old_cached = CachedIdSetter::new(lctx, e.id); // wrap the if-let expr in a block let span = els.span; let blk = P(hir::Block { @@ -984,10 +984,10 @@ pub fn lower_expr(lctx: &LoweringContext, e: &Expr) -> P { hir::ExprLoop(lower_block(lctx, body), opt_ident) } - ExprMatch(ref expr, ref arms, ref source) => { + ExprMatch(ref expr, ref arms) => { hir::ExprMatch(lower_expr(lctx, expr), arms.iter().map(|x| lower_arm(lctx, x)).collect(), - lower_match_source(lctx, source)) + hir::MatchSource::Normal) } ExprClosure(capture_clause, ref decl, ref body) => { hir::ExprClosure(lower_capture_clause(lctx, capture_clause), @@ -1310,17 +1310,6 @@ pub fn lower_stmt(_lctx: &LoweringContext, s: &Stmt) -> P { } } -pub fn lower_match_source(_lctx: &LoweringContext, m: &MatchSource) -> hir::MatchSource { - match *m { - MatchSource::Normal => hir::MatchSource::Normal, - MatchSource::IfLetDesugar { contains_else_clause } => { - hir::MatchSource::IfLetDesugar { contains_else_clause: contains_else_clause } - } - MatchSource::WhileLetDesugar => hir::MatchSource::WhileLetDesugar, - MatchSource::ForLoopDesugar => hir::MatchSource::ForLoopDesugar, - } -} - pub fn lower_capture_clause(_lctx: &LoweringContext, c: CaptureClause) -> hir::CaptureClause { match c { CaptureByValue => hir::CaptureByValue, diff --git a/src/librustc_lint/unused.rs b/src/librustc_lint/unused.rs index 9c030d8892a..6eee6872be2 100644 --- a/src/librustc_lint/unused.rs +++ b/src/librustc_lint/unused.rs @@ -366,7 +366,7 @@ impl EarlyLintPass for UnusedParens { ast::ExprIfLet(_, ref cond, _, _) => (cond, "`if let` head expression", true), ast::ExprWhileLet(_, ref cond, _, _) => (cond, "`while let` head expression", true), ast::ExprForLoop(_, ref cond, _, _) => (cond, "`for` head expression", true), - ast::ExprMatch(ref head, _, _) => (head, "`match` head expression", true), + ast::ExprMatch(ref head, _) => (head, "`match` head expression", true), ast::ExprRet(Some(ref value)) => (value, "`return` value", false), ast::ExprAssign(_, ref value) => (value, "assigned value", false), ast::ExprAssignOp(_, _, ref value) => (value, "assigned value", false), diff --git a/src/librustdoc/core.rs b/src/librustdoc/core.rs index f62148c16fa..2ab4e6b9299 100644 --- a/src/librustdoc/core.rs +++ b/src/librustdoc/core.rs @@ -135,8 +135,7 @@ pub fn run_core(search_paths: SearchPaths, cfgs: Vec, externs: Externs, let krate = driver::assign_node_ids(&sess, krate); // Lower ast -> hir. - let foo = &42; - let lcx = LoweringContext::new(foo, &sess, &krate); + let lcx = LoweringContext::new(&sess, &krate); let mut hir_forest = hir_map::Forest::new(lower_crate(&lcx, &krate)); let arenas = ty::CtxtArenas::new(); let hir_map = driver::make_map(&sess, &mut hir_forest); diff --git a/src/librustdoc/test.rs b/src/librustdoc/test.rs index dec2ed789e0..0dafc89a798 100644 --- a/src/librustdoc/test.rs +++ b/src/librustdoc/test.rs @@ -83,8 +83,7 @@ pub fn run(input: &str, "rustdoc-test", None) .expect("phase_2_configure_and_expand aborted in rustdoc!"); let krate = driver::assign_node_ids(&sess, krate); - let foo = &42; - let lcx = LoweringContext::new(foo, &sess, &krate); + let lcx = LoweringContext::new(&sess, &krate); let krate = lower_crate(&lcx, &krate); let opts = scrape_test_config(&krate); diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index 02cd648b6d8..34b99ab8cce 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -855,9 +855,8 @@ pub enum Expr_ { /// /// `'label: loop { block }` ExprLoop(P, Option), - /// A `match` block, with a source that indicates whether or not it is - /// the result of a desugaring, and if so, which kind. - ExprMatch(P, Vec, MatchSource), + /// A `match` block. + ExprMatch(P, Vec), /// A closure (for example, `move |a, b, c| {a + b + c}`) ExprClosure(CaptureClause, P, P), /// A block (`{ ... }`) @@ -936,14 +935,6 @@ pub struct QSelf { pub position: usize } -#[derive(Clone, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug, Copy)] -pub enum MatchSource { - Normal, - IfLetDesugar { contains_else_clause: bool }, - WhileLetDesugar, - ForLoopDesugar, -} - #[derive(Clone, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug, Copy)] pub enum CaptureClause { CaptureByValue, diff --git a/src/libsyntax/codemap.rs b/src/libsyntax/codemap.rs index aa4dd1d53c5..a73fd4534c9 100644 --- a/src/libsyntax/codemap.rs +++ b/src/libsyntax/codemap.rs @@ -29,7 +29,6 @@ use std::io::{self, Read}; use serialize::{Encodable, Decodable, Encoder, Decoder}; -use parse::token::intern; use ast::Name; // _____________________________________________________________________________ @@ -269,28 +268,8 @@ pub enum ExpnFormat { MacroAttribute(Name), /// e.g. `format!()` MacroBang(Name), - /// Syntax sugar expansion performed by the compiler (libsyntax::expand). - CompilerExpansion(CompilerExpansionFormat), } -#[derive(Clone, Copy, Hash, Debug, PartialEq, Eq)] -pub enum CompilerExpansionFormat { - IfLet, - PlacementIn, - WhileLet, - ForLoop, -} - -impl CompilerExpansionFormat { - pub fn name(self) -> &'static str { - match self { - CompilerExpansionFormat::IfLet => "if let expansion", - CompilerExpansionFormat::PlacementIn => "placement-in expansion", - CompilerExpansionFormat::WhileLet => "while let expansion", - CompilerExpansionFormat::ForLoop => "for loop expansion", - } - } -} #[derive(Clone, Hash, Debug)] pub struct NameAndSpan { /// The format with which the macro was invoked. @@ -310,7 +289,6 @@ impl NameAndSpan { match self.format { ExpnFormat::MacroAttribute(s) => s, ExpnFormat::MacroBang(s) => s, - ExpnFormat::CompilerExpansion(ce) => intern(ce.name()), } } } diff --git a/src/libsyntax/config.rs b/src/libsyntax/config.rs index 889a0d7e440..2d266be3242 100644 --- a/src/libsyntax/config.rs +++ b/src/libsyntax/config.rs @@ -225,10 +225,10 @@ fn fold_expr(cx: &mut Context, expr: P) -> P where fold::noop_fold_expr(ast::Expr { id: id, node: match node { - ast::ExprMatch(m, arms, source) => { + ast::ExprMatch(m, arms) => { ast::ExprMatch(m, arms.into_iter() .filter(|a| (cx.in_cfg)(&a.attrs)) - .collect(), source) + .collect()) } _ => node }, diff --git a/src/libsyntax/diagnostic.rs b/src/libsyntax/diagnostic.rs index 6b4a5538501..2a8cdf138b0 100644 --- a/src/libsyntax/diagnostic.rs +++ b/src/libsyntax/diagnostic.rs @@ -737,7 +737,6 @@ impl EmitterWriter { let (pre, post) = match ei.callee.format { codemap::MacroAttribute(..) => ("#[", "]"), codemap::MacroBang(..) => ("", "!"), - codemap::CompilerExpansion(..) => ("", ""), }; // Don't print recursive invocations if ei.call_site != last_span { diff --git a/src/libsyntax/ext/base.rs b/src/libsyntax/ext/base.rs index aaaca8bd4d8..a3df7727598 100644 --- a/src/libsyntax/ext/base.rs +++ b/src/libsyntax/ext/base.rs @@ -13,7 +13,7 @@ pub use self::SyntaxExtension::*; use ast; use ast::Name; use codemap; -use codemap::{CodeMap, Span, ExpnId, ExpnInfo, NO_EXPANSION, CompilerExpansion}; +use codemap::{CodeMap, Span, ExpnId, ExpnInfo, NO_EXPANSION}; use ext; use ext::expand; use ext::tt::macro_rules; @@ -651,10 +651,7 @@ impl<'a> ExtCtxt<'a> { return None; } expn_id = i.call_site.expn_id; - match i.callee.format { - CompilerExpansion(..) => (), - _ => last_macro = Some(i.call_site), - } + last_macro = Some(i.call_site); return Some(()); }) }).is_none() { diff --git a/src/libsyntax/ext/build.rs b/src/libsyntax/ext/build.rs index a20080dcbf0..efea85f9162 100644 --- a/src/libsyntax/ext/build.rs +++ b/src/libsyntax/ext/build.rs @@ -868,7 +868,7 @@ impl<'a> AstBuilder for ExtCtxt<'a> { } fn expr_match(&self, span: Span, arg: P, arms: Vec) -> P { - self.expr(span, ast::ExprMatch(arg, arms, ast::MatchSource::Normal)) + self.expr(span, ast::ExprMatch(arg, arms)) } fn expr_if(&self, span: Span, cond: P, diff --git a/src/libsyntax/fold.rs b/src/libsyntax/fold.rs index 914b08265fe..3c1aa992a3c 100644 --- a/src/libsyntax/fold.rs +++ b/src/libsyntax/fold.rs @@ -1256,10 +1256,9 @@ pub fn noop_fold_expr(Expr {id, node, span}: Expr, folder: &mut T) -> ExprLoop(folder.fold_block(body), opt_ident.map(|i| folder.fold_ident(i))) } - ExprMatch(expr, arms, source) => { + ExprMatch(expr, arms) => { ExprMatch(folder.fold_expr(expr), - arms.move_map(|x| folder.fold_arm(x)), - source) + arms.move_map(|x| folder.fold_arm(x))) } ExprClosure(capture_clause, decl, body) => { ExprClosure(capture_clause, diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index f47dfeb1d34..443cea696b6 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -37,7 +37,7 @@ use ast::{LifetimeDef, Lit, Lit_}; use ast::{LitBool, LitChar, LitByte, LitByteStr}; use ast::{LitStr, LitInt, Local}; use ast::{MacStmtWithBraces, MacStmtWithSemicolon, MacStmtWithoutBraces}; -use ast::{MutImmutable, MutMutable, Mac_, MatchSource}; +use ast::{MutImmutable, MutMutable, Mac_}; use ast::{MutTy, BiMul, Mutability}; use ast::{MethodImplItem, NamedField, UnNeg, NoReturn, UnNot}; use ast::{Pat, PatBox, PatEnum, PatIdent, PatLit, PatQPath, PatMac, PatRange}; @@ -2927,7 +2927,7 @@ impl<'a> Parser<'a> { } let hi = self.span.hi; try!(self.bump()); - return Ok(self.mk_expr(lo, hi, ExprMatch(discriminant, arms, MatchSource::Normal))); + return Ok(self.mk_expr(lo, hi, ExprMatch(discriminant, arms))); } pub fn parse_arm_nopanic(&mut self) -> PResult { diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index 405fd9b8cc7..f5f3907a4e6 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -2045,7 +2045,7 @@ impl<'a> State<'a> { try!(space(&mut self.s)); try!(self.print_block(&**blk)); } - ast::ExprMatch(ref expr, ref arms, _) => { + ast::ExprMatch(ref expr, ref arms) => { try!(self.cbox(indent_unit)); try!(self.ibox(4)); try!(self.word_nbsp("match")); diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index 67e4927a52f..091580b9bd8 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -731,7 +731,7 @@ pub fn walk_expr<'v, V: Visitor<'v>>(visitor: &mut V, expression: &'v Expr) { visitor.visit_block(block); walk_opt_ident(visitor, expression.span, opt_ident) } - ExprMatch(ref subexpression, ref arms, _) => { + ExprMatch(ref subexpression, ref arms) => { visitor.visit_expr(subexpression); walk_list!(visitor, visit_arm, arms); } -- cgit 1.4.1-3-g733a5