about summary refs log tree commit diff
path: root/src/libsyntax/parse/parser.rs
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2014-09-30 23:17:20 +0000
committerbors <bors@rust-lang.org>2014-09-30 23:17:20 +0000
commit57a05cf49b3149427e3fe190c07f8343a29ad86c (patch)
treee936d71b10c6f881337d44a960e1b8901cd50b38 /src/libsyntax/parse/parser.rs
parent88d1a22f76a774b2df3c904ceb54c86e58a859c3 (diff)
parente723051a2eb840a710f2b79afc1b42b0b707d0e4 (diff)
downloadrust-57a05cf49b3149427e3fe190c07f8343a29ad86c.tar.gz
rust-57a05cf49b3149427e3fe190c07f8343a29ad86c.zip
auto merge of #17634 : jakub-/rust/if_let, r=kballard
Continuation of https://github.com/rust-lang/rust/pull/16741.
Diffstat (limited to 'src/libsyntax/parse/parser.rs')
-rw-r--r--src/libsyntax/parse/parser.rs39
1 files changed, 29 insertions, 10 deletions
diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs
index 415ff6a4097..0780e68a062 100644
--- a/src/libsyntax/parse/parser.rs
+++ b/src/libsyntax/parse/parser.rs
@@ -23,7 +23,7 @@ use ast::{DeclLocal, DefaultBlock, UnDeref, BiDiv, EMPTY_CTXT, EnumDef, Explicit
 use ast::{Expr, Expr_, ExprAddrOf, ExprMatch, ExprAgain};
 use ast::{ExprAssign, ExprAssignOp, ExprBinary, ExprBlock, ExprBox};
 use ast::{ExprBreak, ExprCall, ExprCast};
-use ast::{ExprField, ExprTupField, ExprFnBlock, ExprIf, ExprIndex, ExprSlice};
+use ast::{ExprField, ExprTupField, ExprFnBlock, ExprIf, ExprIfLet, ExprIndex, ExprSlice};
 use ast::{ExprLit, ExprLoop, ExprMac};
 use ast::{ExprMethodCall, ExprParen, ExprPath, ExprProc};
 use ast::{ExprRepeat, ExprRet, ExprStruct, ExprTup, ExprUnary, ExprUnboxedFn};
@@ -38,7 +38,7 @@ use ast::{ItemMac, ItemMod, ItemStruct, ItemTrait, ItemTy};
 use ast::{LifetimeDef, Lit, Lit_};
 use ast::{LitBool, LitChar, LitByte, LitBinary};
 use ast::{LitNil, LitStr, LitInt, Local, LocalLet};
-use ast::{MutImmutable, MutMutable, Mac_, MacInvocTT, Matcher, MatchNonterminal};
+use ast::{MutImmutable, MutMutable, Mac_, MacInvocTT, Matcher, MatchNonterminal, MatchNormal};
 use ast::{MatchSeq, MatchTok, Method, MutTy, BiMul, Mutability};
 use ast::{MethodImplItem, NamedField, UnNeg, NoReturn, UnNot};
 use ast::{Pat, PatEnum, PatIdent, PatLit, PatRange, PatRegion, PatStruct};
@@ -576,12 +576,11 @@ impl<'a> Parser<'a> {
     /// If the next token is the given keyword, eat it and return
     /// true. Otherwise, return false.
     pub fn eat_keyword(&mut self, kw: keywords::Keyword) -> bool {
-        match self.token {
-            token::IDENT(sid, false) if kw.to_name() == sid.name => {
-                self.bump();
-                true
-            }
-            _ => false
+        if self.is_keyword(kw) {
+            self.bump();
+            true
+        } else {
+            false
         }
     }
 
@@ -2860,8 +2859,11 @@ impl<'a> Parser<'a> {
         }
     }
 
-    /// Parse an 'if' expression ('if' token already eaten)
+    /// Parse an 'if' or 'if let' expression ('if' token already eaten)
     pub fn parse_if_expr(&mut self) -> P<Expr> {
+        if self.is_keyword(keywords::Let) {
+            return self.parse_if_let_expr();
+        }
         let lo = self.last_span.lo;
         let cond = self.parse_expr_res(RestrictionNoStructLiteral);
         let thn = self.parse_block();
@@ -2875,6 +2877,23 @@ impl<'a> Parser<'a> {
         self.mk_expr(lo, hi, ExprIf(cond, thn, els))
     }
 
+    /// Parse an 'if let' expression ('if' token already eaten)
+    pub fn parse_if_let_expr(&mut self) -> P<Expr> {
+        let lo = self.last_span.lo;
+        self.expect_keyword(keywords::Let);
+        let pat = self.parse_pat();
+        self.expect(&token::EQ);
+        let expr = self.parse_expr_res(RestrictionNoStructLiteral);
+        let thn = self.parse_block();
+        let (hi, els) = if self.eat_keyword(keywords::Else) {
+            let expr = self.parse_else_expr();
+            (expr.span.hi, Some(expr))
+        } else {
+            (thn.span.hi, None)
+        };
+        self.mk_expr(lo, hi, ExprIfLet(pat, expr, thn, els))
+    }
+
     // `|args| expr`
     pub fn parse_lambda_expr(&mut self, capture_clause: CaptureClause)
                              -> P<Expr> {
@@ -2956,7 +2975,7 @@ impl<'a> Parser<'a> {
         }
         let hi = self.span.hi;
         self.bump();
-        return self.mk_expr(lo, hi, ExprMatch(discriminant, arms));
+        return self.mk_expr(lo, hi, ExprMatch(discriminant, arms, MatchNormal));
     }
 
     pub fn parse_arm(&mut self) -> Arm {