• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * [The "BSD license"]
3  *  Copyright (c) 2010 Terence Parr
4  *  All rights reserved.
5  *
6  *  Redistribution and use in source and binary forms, with or without
7  *  modification, are permitted provided that the following conditions
8  *  are met:
9  *  1. Redistributions of source code must retain the above copyright
10  *      notice, this list of conditions and the following disclaimer.
11  *  2. Redistributions in binary form must reproduce the above copyright
12  *      notice, this list of conditions and the following disclaimer in the
13  *      documentation and/or other materials provided with the distribution.
14  *  3. The name of the author may not be used to endorse or promote products
15  *      derived from this software without specific prior written permission.
16  *
17  *  THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18  *  IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19  *  OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20  *  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21  *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22  *  NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23  *  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24  *  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26  *  THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 package org.antlr.test;
29 
30 import org.junit.Test;
31 
32 import static org.junit.Assert.*;
33 
34 public class TestTreeParsing extends BaseTest {
testFlatList()35 	@Test public void testFlatList() throws Exception {
36 		String grammar =
37 			"grammar T;\n" +
38 			"options {output=AST;}\n" +
39 			"a : ID INT;\n" +
40 			"ID : 'a'..'z'+ ;\n" +
41 			"INT : '0'..'9'+;\n" +
42 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
43 
44 		String treeGrammar =
45 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
46 			"a : ID INT\n" +
47 			"    {System.out.println($ID+\", \"+$INT);}\n" +
48 			"  ;\n";
49 
50 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
51 				    treeGrammar, "TP", "TLexer", "a", "a", "abc 34");
52 		assertEquals("abc, 34\n", found);
53 	}
54 
testSimpleTree()55 	@Test public void testSimpleTree() throws Exception {
56 		String grammar =
57 			"grammar T;\n" +
58 			"options {output=AST;}\n" +
59 			"a : ID INT -> ^(ID INT);\n" +
60 			"ID : 'a'..'z'+ ;\n" +
61 			"INT : '0'..'9'+;\n" +
62 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
63 
64 		String treeGrammar =
65 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
66 			"a : ^(ID INT)\n" +
67 			"    {System.out.println($ID+\", \"+$INT);}\n" +
68 			"  ;\n";
69 
70 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
71 				    treeGrammar, "TP", "TLexer", "a", "a", "abc 34");
72 		assertEquals("abc, 34\n", found);
73 	}
74 
testFlatVsTreeDecision()75 	@Test public void testFlatVsTreeDecision() throws Exception {
76 		String grammar =
77 			"grammar T;\n" +
78 			"options {output=AST;}\n" +
79 			"a : b c ;\n" +
80 			"b : ID INT -> ^(ID INT);\n" +
81 			"c : ID INT;\n" +
82 			"ID : 'a'..'z'+ ;\n" +
83 			"INT : '0'..'9'+;\n" +
84 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
85 
86 		String treeGrammar =
87 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
88 			"a : b b ;\n" +
89 			"b : ID INT    {System.out.print($ID+\" \"+$INT);}\n" +
90 			"  | ^(ID INT) {System.out.print(\"^(\"+$ID+\" \"+$INT+')');}\n" +
91 			"  ;\n";
92 
93 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
94 				    treeGrammar, "TP", "TLexer", "a", "a", "a 1 b 2");
95 		assertEquals("^(a 1)b 2\n", found);
96 	}
97 
testFlatVsTreeDecision2()98 	@Test public void testFlatVsTreeDecision2() throws Exception {
99 		String grammar =
100 			"grammar T;\n" +
101 			"options {output=AST;}\n" +
102 			"a : b c ;\n" +
103 			"b : ID INT+ -> ^(ID INT+);\n" +
104 			"c : ID INT+;\n" +
105 			"ID : 'a'..'z'+ ;\n" +
106 			"INT : '0'..'9'+;\n" +
107 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
108 
109 		String treeGrammar =
110 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
111 			"a : b b ;\n" +
112 			"b : ID INT+    {System.out.print($ID+\" \"+$INT);}\n" +
113 			"  | ^(x=ID (y=INT)+) {System.out.print(\"^(\"+$x+' '+$y+')');}\n" +
114 			"  ;\n";
115 
116 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
117 				    treeGrammar, "TP", "TLexer", "a", "a",
118 				    "a 1 2 3 b 4 5");
119 		assertEquals("^(a 3)b 5\n", found);
120 	}
121 
testCyclicDFALookahead()122 	@Test public void testCyclicDFALookahead() throws Exception {
123 		String grammar =
124 			"grammar T;\n" +
125 			"options {output=AST;}\n" +
126 			"a : ID INT+ PERIOD;\n" +
127 			"ID : 'a'..'z'+ ;\n" +
128 			"INT : '0'..'9'+;\n" +
129 			"SEMI : ';' ;\n"+
130 			"PERIOD : '.' ;\n"+
131 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
132 
133 		String treeGrammar =
134 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
135 			"a : ID INT+ PERIOD {System.out.print(\"alt 1\");}"+
136 			"  | ID INT+ SEMI   {System.out.print(\"alt 2\");}\n" +
137 			"  ;\n";
138 
139 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
140 				    treeGrammar, "TP", "TLexer", "a", "a", "a 1 2 3.");
141 		assertEquals("alt 1\n", found);
142 	}
143 
testTemplateOutput()144 	@Test public void testTemplateOutput() throws Exception {
145 		String grammar =
146 			"grammar T;\n" +
147 			"options {output=AST;}\n" +
148 			"a : ID INT;\n" +
149 			"ID : 'a'..'z'+ ;\n" +
150 			"INT : '0'..'9'+;\n" +
151 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
152 
153 		String treeGrammar =
154 			"tree grammar TP;\n" +
155 			"options {output=template; ASTLabelType=CommonTree;}\n" +
156 			"s : a {System.out.println($a.st);};\n" +
157 			"a : ID INT -> {new StringTemplate($INT.text)}\n" +
158 			"  ;\n";
159 
160 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
161 				    treeGrammar, "TP", "TLexer", "a", "s", "abc 34");
162 		assertEquals("34\n", found);
163 	}
164 
testNullableChildList()165 	@Test public void testNullableChildList() throws Exception {
166 		String grammar =
167 			"grammar T;\n" +
168 			"options {output=AST;}\n" +
169 			"a : ID INT? -> ^(ID INT?);\n" +
170 			"ID : 'a'..'z'+ ;\n" +
171 			"INT : '0'..'9'+;\n" +
172 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
173 
174 		String treeGrammar =
175 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
176 			"a : ^(ID INT?)\n" +
177 			"    {System.out.println($ID);}\n" +
178 			"  ;\n";
179 
180 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
181 				    treeGrammar, "TP", "TLexer", "a", "a", "abc");
182 		assertEquals("abc\n", found);
183 	}
184 
testNullableChildList2()185 	@Test public void testNullableChildList2() throws Exception {
186 		String grammar =
187 			"grammar T;\n" +
188 			"options {output=AST;}\n" +
189 			"a : ID INT? SEMI -> ^(ID INT?) SEMI ;\n" +
190 			"ID : 'a'..'z'+ ;\n" +
191 			"INT : '0'..'9'+;\n" +
192 			"SEMI : ';' ;\n"+
193 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
194 
195 		String treeGrammar =
196 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
197 			"a : ^(ID INT?) SEMI\n" +
198 			"    {System.out.println($ID);}\n" +
199 			"  ;\n";
200 
201 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
202 				    treeGrammar, "TP", "TLexer", "a", "a", "abc;");
203 		assertEquals("abc\n", found);
204 	}
205 
testNullableChildList3()206 	@Test public void testNullableChildList3() throws Exception {
207 		String grammar =
208 			"grammar T;\n" +
209 			"options {output=AST;}\n" +
210 			"a : x=ID INT? (y=ID)? SEMI -> ^($x INT? $y?) SEMI ;\n" +
211 			"ID : 'a'..'z'+ ;\n" +
212 			"INT : '0'..'9'+;\n" +
213 			"SEMI : ';' ;\n"+
214 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
215 
216 		String treeGrammar =
217 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
218 			"a : ^(ID INT? b) SEMI\n" +
219 			"    {System.out.println($ID+\", \"+$b.text);}\n" +
220 			"  ;\n"+
221 			"b : ID? ;\n";
222 
223 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
224 				    treeGrammar, "TP", "TLexer", "a", "a", "abc def;");
225 		assertEquals("abc, def\n", found);
226 	}
227 
testActionsAfterRoot()228 	@Test public void testActionsAfterRoot() throws Exception {
229 		String grammar =
230 			"grammar T;\n" +
231 			"options {output=AST;}\n" +
232 			"a : x=ID INT? SEMI -> ^($x INT?) ;\n" +
233 			"ID : 'a'..'z'+ ;\n" +
234 			"INT : '0'..'9'+;\n" +
235 			"SEMI : ';' ;\n"+
236 			"WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
237 
238 		String treeGrammar =
239 			"tree grammar TP; options {ASTLabelType=CommonTree;}\n" +
240 			"a @init {int x=0;} : ^(ID {x=1;} {x=2;} INT?)\n" +
241 			"    {System.out.println($ID+\", \"+x);}\n" +
242 			"  ;\n";
243 
244 		String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
245 				    treeGrammar, "TP", "TLexer", "a", "a", "abc;");
246 		assertEquals("abc, 2\n", found);
247 	}
248 
testWildcardLookahead()249     @Test public void testWildcardLookahead() throws Exception {
250         String grammar =
251             "grammar T;\n" +
252             "options {output=AST;}\n" +
253             "a : ID '+'^ INT;\n" +
254             "ID : 'a'..'z'+ ;\n" +
255             "INT : '0'..'9'+;\n" +
256             "SEMI : ';' ;\n"+
257             "PERIOD : '.' ;\n"+
258             "WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
259 
260         String treeGrammar =
261             "tree grammar TP; options {tokenVocab=T; ASTLabelType=CommonTree;}\n" +
262             "a : ^('+' . INT) {System.out.print(\"alt 1\");}"+
263             "  ;\n";
264 
265         String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
266                     treeGrammar, "TP", "TLexer", "a", "a", "a + 2");
267         assertEquals("alt 1\n", found);
268     }
269 
testWildcardLookahead2()270     @Test public void testWildcardLookahead2() throws Exception {
271         String grammar =
272             "grammar T;\n" +
273             "options {output=AST;}\n" +
274             "a : ID '+'^ INT;\n" +
275             "ID : 'a'..'z'+ ;\n" +
276             "INT : '0'..'9'+;\n" +
277             "SEMI : ';' ;\n"+
278             "PERIOD : '.' ;\n"+
279             "WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
280 
281         String treeGrammar =
282             "tree grammar TP; options {tokenVocab=T; ASTLabelType=CommonTree;}\n" +
283             "a : ^('+' . INT) {System.out.print(\"alt 1\");}"+
284             "  | ^('+' . .)   {System.out.print(\"alt 2\");}\n" +
285             "  ;\n";
286 
287         // AMBIG upon '+' DOWN INT UP etc.. but so what.
288 
289         String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
290                     treeGrammar, "TP", "TLexer", "a", "a", "a + 2");
291         assertEquals("alt 1\n", found);
292     }
293 
testWildcardLookahead3()294     @Test public void testWildcardLookahead3() throws Exception {
295         String grammar =
296             "grammar T;\n" +
297             "options {output=AST;}\n" +
298             "a : ID '+'^ INT;\n" +
299             "ID : 'a'..'z'+ ;\n" +
300             "INT : '0'..'9'+;\n" +
301             "SEMI : ';' ;\n"+
302             "PERIOD : '.' ;\n"+
303             "WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
304 
305         String treeGrammar =
306             "tree grammar TP; options {tokenVocab=T; ASTLabelType=CommonTree;}\n" +
307             "a : ^('+' ID INT) {System.out.print(\"alt 1\");}"+
308             "  | ^('+' . .)   {System.out.print(\"alt 2\");}\n" +
309             "  ;\n";
310 
311         // AMBIG upon '+' DOWN INT UP etc.. but so what.
312 
313         String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
314                     treeGrammar, "TP", "TLexer", "a", "a", "a + 2");
315         assertEquals("alt 1\n", found);
316     }
317 
testWildcardPlusLookahead()318     @Test public void testWildcardPlusLookahead() throws Exception {
319         String grammar =
320             "grammar T;\n" +
321             "options {output=AST;}\n" +
322             "a : ID '+'^ INT;\n" +
323             "ID : 'a'..'z'+ ;\n" +
324             "INT : '0'..'9'+;\n" +
325             "SEMI : ';' ;\n"+
326             "PERIOD : '.' ;\n"+
327             "WS : (' '|'\\n') {$channel=HIDDEN;} ;\n";
328 
329         String treeGrammar =
330             "tree grammar TP; options {tokenVocab=T; ASTLabelType=CommonTree;}\n" +
331             "a : ^('+' INT INT ) {System.out.print(\"alt 1\");}"+
332             "  | ^('+' .+)   {System.out.print(\"alt 2\");}\n" +
333             "  ;\n";
334 
335         // AMBIG upon '+' DOWN INT UP etc.. but so what.
336 
337         String found = execTreeParser("T.g", grammar, "TParser", "TP.g",
338                     treeGrammar, "TP", "TLexer", "a", "a", "a + 2");
339         assertEquals("alt 2\n", found);
340     }
341 
342 }
343