aboutsummaryrefslogtreecommitdiff
path: root/src/parser/grammar
diff options
context:
space:
mode:
Diffstat (limited to 'src/parser/grammar')
-rw-r--r--src/parser/grammar/attributes.rs4
-rw-r--r--src/parser/grammar/expressions.rs61
-rw-r--r--src/parser/grammar/mod.rs2
3 files changed, 50 insertions, 17 deletions
diff --git a/src/parser/grammar/attributes.rs b/src/parser/grammar/attributes.rs
index 7f1c0401a..c411d4d7f 100644
--- a/src/parser/grammar/attributes.rs
+++ b/src/parser/grammar/attributes.rs
@@ -36,7 +36,7 @@ fn meta_item(p: &mut Parser) {
36 match p.current() { 36 match p.current() {
37 EQ => { 37 EQ => {
38 p.bump(); 38 p.bump();
39 if !expressions::literal(p) { 39 if expressions::literal(p).is_none() {
40 p.error("expected literal"); 40 p.error("expected literal");
41 } 41 }
42 } 42 }
@@ -56,7 +56,7 @@ fn meta_item_arg_list(p: &mut Parser) {
56 match p.current() { 56 match p.current() {
57 EOF | R_PAREN => break, 57 EOF | R_PAREN => break,
58 IDENT => meta_item(p), 58 IDENT => meta_item(p),
59 c => if !expressions::literal(p) { 59 c => if expressions::literal(p).is_none() {
60 let message = "expected attribute"; 60 let message = "expected attribute";
61 61
62 if items::ITEM_FIRST.contains(c) { 62 if items::ITEM_FIRST.contains(c) {
diff --git a/src/parser/grammar/expressions.rs b/src/parser/grammar/expressions.rs
index ece698248..92aaafa3d 100644
--- a/src/parser/grammar/expressions.rs
+++ b/src/parser/grammar/expressions.rs
@@ -13,39 +13,72 @@ use super::*;
13// let _ = b"e"; 13// let _ = b"e";
14// let _ = br"f"; 14// let _ = br"f";
15// } 15// }
16pub(super) fn literal(p: &mut Parser) -> bool { 16pub(super) fn literal(p: &mut Parser) -> Option<CompletedMarker> {
17 match p.current() { 17 match p.current() {
18 TRUE_KW | FALSE_KW | INT_NUMBER | FLOAT_NUMBER | BYTE | CHAR | STRING | RAW_STRING 18 TRUE_KW | FALSE_KW | INT_NUMBER | FLOAT_NUMBER | BYTE | CHAR | STRING | RAW_STRING
19 | BYTE_STRING | RAW_BYTE_STRING => { 19 | BYTE_STRING | RAW_BYTE_STRING => {
20 let lit = p.start(); 20 let m = p.start();
21 p.bump(); 21 p.bump();
22 lit.complete(p, LITERAL); 22 Some(m.complete(p, LITERAL))
23 true
24 } 23 }
25 _ => false, 24 _ => None,
26 } 25 }
27} 26}
28 27
29pub(super) fn expr(p: &mut Parser) { 28pub(super) fn expr(p: &mut Parser) {
30 if literal(p) { 29 let mut lhs = atom_expr(p);
31 return; 30
31 while let Some(m) = lhs {
32 match p.current() {
33 L_PAREN => lhs = Some(call_expr(p, m)),
34 _ => break,
35 }
36 }
37}
38
39fn atom_expr(p: &mut Parser) -> Option<CompletedMarker> {
40 match literal(p) {
41 Some(m) => return Some(m),
42 None => (),
32 } 43 }
33 if paths::is_path_start(p) { 44 if paths::is_path_start(p) {
34 return path_expr(p); 45 return Some(path_expr(p));
35 } 46 }
36 47
37 match p.current() { 48 match p.current() {
38 L_PAREN => tuple_expr(p), 49 L_PAREN => Some(tuple_expr(p)),
39 _ => p.error("expected expression"), 50 _ => {
51 p.error("expected expression");
52 None
53 }
40 } 54 }
41} 55}
42 56
43fn tuple_expr(p: &mut Parser) { 57fn tuple_expr(p: &mut Parser) -> CompletedMarker {
44 assert!(p.at(L_PAREN)); 58 assert!(p.at(L_PAREN));
45 let m = p.start(); 59 let m = p.start();
46 p.expect(L_PAREN); 60 p.expect(L_PAREN);
47 p.expect(R_PAREN); 61 p.expect(R_PAREN);
48 m.complete(p, TUPLE_EXPR); 62 m.complete(p, TUPLE_EXPR)
63}
64
65// test call_expr
66// fn foo() {
67// let _ = f();
68// let _ = f()(1)(1, 2,);
69// }
70fn call_expr(p: &mut Parser, lhs: CompletedMarker) -> CompletedMarker {
71 assert!(p.at(L_PAREN));
72 let m = lhs.precede(p);
73 p.bump();
74 while !p.at(R_PAREN) && !p.at(EOF) {
75 expr(p);
76 if !p.at(R_PAREN) && !p.expect(COMMA) {
77 break;
78 }
79 }
80 p.eat(R_PAREN);
81 m.complete(p, CALL_EXPR)
49} 82}
50 83
51// test path_expr 84// test path_expr
@@ -54,9 +87,9 @@ fn tuple_expr(p: &mut Parser) {
54// let _ = a::b; 87// let _ = a::b;
55// let _ = ::a::<b>; 88// let _ = ::a::<b>;
56// } 89// }
57fn path_expr(p: &mut Parser) { 90fn path_expr(p: &mut Parser) -> CompletedMarker {
58 assert!(paths::is_path_start(p)); 91 assert!(paths::is_path_start(p));
59 let m = p.start(); 92 let m = p.start();
60 paths::expr_path(p); 93 paths::expr_path(p);
61 m.complete(p, PATH_EXPR); 94 m.complete(p, PATH_EXPR)
62} 95}
diff --git a/src/parser/grammar/mod.rs b/src/parser/grammar/mod.rs
index e4823eadb..63ad2782e 100644
--- a/src/parser/grammar/mod.rs
+++ b/src/parser/grammar/mod.rs
@@ -31,7 +31,7 @@ mod type_args;
31mod types; 31mod types;
32 32
33use { 33use {
34 parser::{parser::Parser, token_set::TokenSet}, 34 parser::{parser::{Parser, CompletedMarker}, token_set::TokenSet},
35 SyntaxKind::{self, *}, 35 SyntaxKind::{self, *},
36}; 36};
37 37