treetop 1.6.6 → 1.6.11

Sign up to get free protection for your applications and to get access to all the features.
Files changed (66) hide show
  1. checksums.yaml +5 -5
  2. data/Gemfile +18 -0
  3. data/History.txt +18 -0
  4. data/README.md +2 -0
  5. data/Rakefile +10 -43
  6. data/Treetop.tmbundle/Preferences/Comments.tmPreferences +28 -0
  7. data/Treetop.tmbundle/Snippets/grammar ___ end.tmSnippet +20 -0
  8. data/Treetop.tmbundle/Snippets/rule ___ end.tmSnippet +18 -0
  9. data/Treetop.tmbundle/Support/nibs/SyntaxTreeViewer.nib/designable.nib +1524 -0
  10. data/Treetop.tmbundle/Support/nibs/SyntaxTreeViewer.nib/keyedobjects.nib +0 -0
  11. data/Treetop.tmbundle/Support/syntax_tree_viewer.rb +117 -0
  12. data/Treetop.tmbundle/Syntaxes/Treetop Grammar.tmLanguage +358 -0
  13. data/Treetop.tmbundle/info.plist +10 -0
  14. data/doc/pitfalls_and_advanced_techniques.markdown +6 -0
  15. data/doc/syntactic_recognition.markdown +2 -2
  16. data/lib/treetop/compiler/grammar_compiler.rb +6 -3
  17. data/lib/treetop/compiler/metagrammar.rb +97 -77
  18. data/lib/treetop/compiler/metagrammar.treetop +1 -1
  19. data/lib/treetop/compiler/ruby_builder.rb +2 -2
  20. data/lib/treetop/ruby_extensions/string.rb +0 -6
  21. data/lib/treetop/runtime/compiled_parser.rb +15 -2
  22. data/lib/treetop/version.rb +1 -1
  23. data/treetop.gemspec +25 -157
  24. metadata +15 -61
  25. data/doc/site.rb +0 -112
  26. data/doc/sitegen.rb +0 -65
  27. data/spec/compiler/and_predicate_spec.rb +0 -36
  28. data/spec/compiler/anything_symbol_spec.rb +0 -47
  29. data/spec/compiler/character_class_spec.rb +0 -304
  30. data/spec/compiler/choice_spec.rb +0 -89
  31. data/spec/compiler/circular_compilation_spec.rb +0 -30
  32. data/spec/compiler/failure_propagation_functional_spec.rb +0 -21
  33. data/spec/compiler/grammar_compiler_spec.rb +0 -113
  34. data/spec/compiler/grammar_spec.rb +0 -44
  35. data/spec/compiler/multibyte_chars_spec.rb +0 -38
  36. data/spec/compiler/namespace_spec.rb +0 -42
  37. data/spec/compiler/nonterminal_symbol_spec.rb +0 -40
  38. data/spec/compiler/not_predicate_spec.rb +0 -52
  39. data/spec/compiler/occurrence_range_spec.rb +0 -186
  40. data/spec/compiler/one_or_more_spec.rb +0 -35
  41. data/spec/compiler/optional_spec.rb +0 -37
  42. data/spec/compiler/parenthesized_expression_spec.rb +0 -34
  43. data/spec/compiler/parsing_rule_spec.rb +0 -61
  44. data/spec/compiler/repeated_subrule_spec.rb +0 -29
  45. data/spec/compiler/semantic_predicate_spec.rb +0 -176
  46. data/spec/compiler/sequence_spec.rb +0 -129
  47. data/spec/compiler/terminal_spec.rb +0 -177
  48. data/spec/compiler/terminal_symbol_spec.rb +0 -40
  49. data/spec/compiler/test_grammar.treetop +0 -7
  50. data/spec/compiler/test_grammar.tt +0 -7
  51. data/spec/compiler/test_grammar_do.treetop +0 -7
  52. data/spec/compiler/test_grammar_magic_coding.treetop +0 -8
  53. data/spec/compiler/test_grammar_magic_encoding.treetop +0 -8
  54. data/spec/compiler/tt_compiler_spec.rb +0 -224
  55. data/spec/compiler/zero_or_more_spec.rb +0 -58
  56. data/spec/composition/a.treetop +0 -11
  57. data/spec/composition/b.treetop +0 -11
  58. data/spec/composition/c.treetop +0 -10
  59. data/spec/composition/d.treetop +0 -10
  60. data/spec/composition/f.treetop +0 -17
  61. data/spec/composition/grammar_composition_spec.rb +0 -40
  62. data/spec/composition/subfolder/e_includes_c.treetop +0 -15
  63. data/spec/ruby_extensions/string_spec.rb +0 -32
  64. data/spec/runtime/compiled_parser_spec.rb +0 -153
  65. data/spec/runtime/syntax_node_spec.rb +0 -77
  66. data/spec/spec_helper.rb +0 -123
@@ -1,58 +0,0 @@
1
- require 'spec_helper'
2
-
3
- module ZeroOrMoreSpec
4
- class Foo < Treetop::Runtime::SyntaxNode
5
- end
6
-
7
- describe "zero or more of a terminal symbol followed by a node class declaration and a block" do
8
- # testing_expression '("foo" { def b_method; end } )* <ZeroOrMoreSpec::Foo> { def a_method; end }'
9
- # testing_expression '("foo" { def a_method; end } )* <ZeroOrMoreSpec::Foo>'
10
- testing_expression '"foo"* <ZeroOrMoreSpec::Foo> { def a_method; end }'
11
-
12
- it "successfully parses epsilon, returning an instance declared node class and recording a terminal failure" do
13
- parse('') do |result|
14
- result.should_not be_nil
15
- result.should be_an_instance_of(Foo)
16
- result.should respond_to(:a_method)
17
-
18
- terminal_failures = parser.terminal_failures
19
- terminal_failures.size.should == 1
20
- failure = terminal_failures.first
21
- failure.index.should == 0
22
- failure.expected_string.should == '"foo"'
23
- end
24
- end
25
-
26
- it "successfully parses two of that terminal in a row, returning an instance of the declared node class and recording a failure representing the third attempt " do
27
- parse("foofoo") do |result|
28
- result.should_not be_nil
29
- result.should be_an_instance_of(Foo)
30
-
31
- terminal_failures = parser.terminal_failures
32
- terminal_failures.size.should == 1
33
- failure = terminal_failures.first
34
- failure.index.should == 6
35
- failure.expected_string.should == '"foo"'
36
- end
37
- end
38
- end
39
-
40
- describe "Zero or more of a sequence" do
41
- testing_expression '("foo" "bar")*'
42
-
43
- it "resets the index appropriately following partially matcing input" do
44
- parse('foobarfoo', :consume_all_input => false) do |result|
45
- result.should_not be_nil
46
- result.interval.should == (0...6)
47
- end
48
- end
49
- end
50
-
51
- describe "Zero or more of a choice" do
52
- testing_expression '("a" / "bb")*'
53
-
54
- it "successfully parses matching input" do
55
- parse('abba').should_not be_nil
56
- end
57
- end
58
- end
@@ -1,11 +0,0 @@
1
- module Test
2
- grammar A
3
- rule a
4
- 'a'
5
- end
6
-
7
- rule inherit
8
- 'super'
9
- end
10
- end
11
- end
@@ -1,11 +0,0 @@
1
- module Test
2
- grammar B
3
- rule b
4
- 'bb'
5
- end
6
-
7
- rule inherit
8
- super 'keyword'
9
- end
10
- end
11
- end
@@ -1,10 +0,0 @@
1
- module Test
2
- grammar C
3
- include A
4
- include B
5
-
6
- rule c
7
- a b 'c'
8
- end
9
- end
10
- end
@@ -1,10 +0,0 @@
1
- module Test
2
- grammar D
3
- include A
4
- include B
5
-
6
- rule inherit
7
- super 'works'
8
- end
9
- end
10
- end
@@ -1,17 +0,0 @@
1
-
2
- require "a"
3
-
4
- require File.dirname(__FILE__) + "/b"
5
- require File.dirname(__FILE__) + "/subfolder/e_includes_c"
6
-
7
- module Test
8
- grammar F
9
- include A
10
- include B
11
- include E
12
-
13
- rule f
14
- c e 'f'
15
- end
16
- end
17
- end
@@ -1,40 +0,0 @@
1
- require 'spec_helper'
2
-
3
- module GrammarCompositionSpec
4
- describe "several composed grammars" do
5
- before do
6
- dir = File.dirname(__FILE__)
7
- Treetop.load File.join(dir, 'a')
8
- Treetop.load File.join(dir, 'b')
9
- Treetop.load File.join(dir, 'c')
10
- # Check that polyglot finds d.treetop and loads it:
11
- $: << dir
12
- require 'd'
13
-
14
- @c = ::Test::CParser.new
15
- @d = ::Test::DParser.new
16
- end
17
-
18
- specify "rules in C have access to rules defined in A and B" do
19
- @c.parse('abbc').should_not be_nil
20
- end
21
-
22
- specify "rules in C can override rules in A and B with super semantics" do
23
- @d.parse('superkeywordworks').should_not be_nil
24
- end
25
- end
26
-
27
- describe "composed grammar chaining with require" do
28
- before do
29
- # Load f with polyglot without using the load path:
30
- require File.dirname(__FILE__) + '/f'
31
-
32
- @f = ::Test::FParser.new
33
- end
34
-
35
- specify "rules in F have access to rule defined in E" do
36
- @f.parse('abbcef').should_not be_nil
37
- end
38
-
39
- end
40
- end
@@ -1,15 +0,0 @@
1
- require File.dirname(__FILE__) + "/../c"
2
-
3
- module Test
4
- grammar E
5
- include C
6
-
7
- rule e
8
- 'e'
9
- end
10
-
11
- rule inherit
12
- 'super'
13
- end
14
- end
15
- end
@@ -1,32 +0,0 @@
1
- require 'spec_helper'
2
-
3
- describe String do
4
- before do
5
- @string = %{
6
- 0123456789
7
- 012345
8
- 01234567
9
- 0123
10
- }.tabto(0).strip
11
- end
12
-
13
- it "can translate indices to column numbers" do
14
- @string.column_of(0).should == 1
15
- @string.column_of(5).should == 6
16
- @string.column_of(10).should == 11
17
- @string.column_of(11).should == 1
18
- @string.column_of(17).should == 7
19
- @string.column_of(18).should == 1
20
- @string.column_of(24).should == 7
21
- end
22
-
23
- it "can translate indices to line numbers" do
24
- @string.line_of(0).should == 1
25
- @string.line_of(5).should == 1
26
- @string.line_of(10).should == 1
27
- @string.line_of(11).should == 2
28
- @string.line_of(17).should == 2
29
- @string.line_of(18).should == 3
30
- @string.line_of(24).should == 3
31
- end
32
- end
@@ -1,153 +0,0 @@
1
- require 'spec_helper'
2
-
3
- module CompiledParserSpec
4
- describe Runtime::CompiledParser, "for a grammar with two rules" do
5
- attr_reader :parser
6
-
7
- testing_grammar %{
8
- grammar TwoRules
9
- rule a
10
- 'a'
11
- end
12
-
13
- rule b
14
- 'bb'
15
- end
16
- end
17
- }
18
-
19
- before do
20
- @parser = parser_class_under_test.new
21
- end
22
-
23
- it "allows its root to be specified" do
24
- parser.parse('a').should_not be_nil
25
- parser.parse('b').should be_nil
26
-
27
- # Check that the temporary-override works:
28
- parser.parse('bb', :root => :b).should_not be_nil
29
- parser.parse('a', :root => :b).should be_nil
30
-
31
- # Check that the temporary-override isn't sticky:
32
- parser.parse('a').should_not be_nil
33
-
34
- # Try a permanent override:
35
- parser.root = :b
36
- parser.parse('bb').should_not be_nil
37
- parser.parse('a').should be_nil
38
- end
39
-
40
- it "allows the requirement that all input be consumed to be disabled" do
41
- parser.parse('ab').should be_nil
42
-
43
- # Try a temporary override, and check it's not sticky:
44
- result = parser.parse('ab', :consume_all_input => false)
45
- result.should_not be_nil
46
- result.interval.should == (0...1)
47
- parser.parse('ab').should be_nil
48
-
49
- # Now a permanent override:
50
- parser.consume_all_input = false
51
- result = parser.parse('ab')
52
- result.should_not be_nil
53
- result.interval.should == (0...1)
54
- end
55
-
56
- it "allows input to be parsed at a given index" do
57
- parser.parse('ba').should be_nil
58
- parser.parse('ba', :index => 1).should_not be_nil
59
- # Check that the index defaults again to zero:
60
- parser.parse('a').should_not be_nil
61
-
62
- result = parser.parse('ba', :consume_all_input => false, :index => 1)
63
- result.should_not be_nil
64
- result.interval.should == (1...2)
65
- end
66
-
67
- end
68
-
69
- describe Runtime::CompiledParser, "for a grammar with a choice between terminals" do
70
- attr_reader :parser
71
-
72
- testing_grammar %{
73
- grammar Choice
74
- rule choice
75
- 'a' / 'b' / 'c'
76
- end
77
- end
78
- }
79
-
80
- before do
81
- @parser = parser_class_under_test.new
82
- end
83
-
84
- it "provides #failure_reason, #failure_column, and #failure_line when there is a parse failure" do
85
- parser.parse('z').should be_nil
86
- parser.failure_reason.should == "Expected one of 'a', 'b', 'c' at line 1, column 1 (byte 1)"
87
- parser.failure_line.should == 1
88
- parser.failure_column.should == 1
89
- end
90
- end
91
-
92
- describe Runtime::CompiledParser, "#terminal_failures" do
93
- attr_reader:parser
94
-
95
- testing_grammar %{
96
- grammar SequenceOfTerminals
97
- rule foo
98
- 'a' 'b' 'c'
99
- end
100
- end
101
- }
102
-
103
- before do
104
- @parser = parser_class_under_test.new
105
- end
106
-
107
- it "is reset between parses" do
108
- parser.parse('ac')
109
- terminal_failures = parser.terminal_failures
110
- terminal_failures.size.should == 1
111
- failure = terminal_failures.first
112
- failure.index.should == 1
113
- failure.expected_string.should == "'b'"
114
-
115
- parser.parse('b')
116
- terminal_failures = parser.terminal_failures
117
- terminal_failures.size.should == 1
118
- failure = terminal_failures.first
119
- failure.index.should == 0
120
- failure.expected_string.should == "'a'"
121
- end
122
- end
123
-
124
- describe "a SyntaxNode" do
125
- attr_reader :parser
126
-
127
- testing_grammar %{
128
- grammar Alternates
129
- rule main
130
- aa &{|s| s[0].elements[0].parent.should == s[0] }
131
- / ab &{|s| s[0].elements[0].parent.should == s[0] }
132
- end
133
-
134
- rule aa
135
- 'a' 'a'
136
- end
137
-
138
- rule ab
139
- 'a' 'b'
140
- end
141
- end
142
- }
143
-
144
- before do
145
- @parser = parser_class_under_test.new
146
- end
147
-
148
- it "should have its parent set and reset" do
149
- parser.parse('ab')
150
- end
151
- end
152
-
153
- end
@@ -1,77 +0,0 @@
1
- require 'spec_helper'
2
-
3
- module SyntaxNodeSpec
4
- describe "A new terminal syntax node" do
5
- attr_reader :node
6
-
7
- before do
8
- @node = Runtime::SyntaxNode.new("input", 0...3)
9
- end
10
-
11
- it "reports itself as terminal" do
12
- node.should be_terminal
13
- node.should_not be_nonterminal
14
- end
15
-
16
- it "has a text value based on the input and the interval" do
17
- node.text_value.should == "inp"
18
- end
19
-
20
- it "has itself as its only element" do
21
- node.elements.should be_nil
22
- end
23
- end
24
-
25
- describe "A new nonterminal syntax node" do
26
- attr_reader :node
27
-
28
- before do
29
- @elements = [Runtime::SyntaxNode.new('input', 0...3)]
30
- @node = Runtime::SyntaxNode.new('input', 0...3, @elements)
31
- end
32
-
33
- it "reports itself as nonterminal" do
34
- node.should be_nonterminal
35
- node.should_not be_terminal
36
- end
37
-
38
- it "has a text value based on the input and the interval" do
39
- node.text_value.should == "inp"
40
- end
41
-
42
- it "has the elements with which it was instantiated" do
43
- node.elements.should == @elements
44
- end
45
-
46
- it "sets itself as the parent of its elements" do
47
- node.elements.each do |element|
48
- element.parent.should == node
49
- end
50
- end
51
- end
52
-
53
- describe "A new nonterminal syntax node with all children lazily instantiated" do
54
- attr_reader :node
55
-
56
- it "should lazily instantiate its child nodes" do
57
- @node = Runtime::SyntaxNode.new('input', 0...3, [true, true, true])
58
- node.elements.size.should == 3
59
- node.elements.first.interval.should == (0...1)
60
- node.elements.first.parent.should == node
61
- end
62
-
63
- it "should lazily replace stand-in child nodes around real ones" do
64
- @input = "input"
65
- child1 = Runtime::SyntaxNode.new(@input, 1...2)
66
- child2 = Runtime::SyntaxNode.new(@input, 3...4)
67
- @node = Runtime::SyntaxNode.new(@input, 0...5, [true, child1, true, child2, true])
68
- node.elements.size.should == 5
69
-
70
- node.elements[0].interval.should == (0...1)
71
- node.elements[0].parent.should == node
72
- 0.upto(4) do |index|
73
- node.elements[index].text_value.should == @input[index, 1]
74
- end
75
- end
76
- end
77
- end