rockit 0.7.1 → 0.7.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README +24 -160
- data/TODO +17 -17
- data/VERSION +1 -1
- data/doc/rockit_paper.pdf +0 -0
- data/lib/packrat/grammar.rb +139 -84
- data/rakefile +27 -9
- data/tests/acceptance/packrat/java/atest_java.rb +37 -0
- data/tests/acceptance/packrat/java/java.rb +136 -0
- data/tests/acceptance/packrat/java/t.rb +10 -0
- data/tests/acceptance/packrat/java/todo +10 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/Java.rats +446 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaConstant.rats +111 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaCore.rats +508 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaIdentifier.rats +62 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaSymbol.rats +38 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaTree.rats +40 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/JavaType.rats +61 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/Spacing.rats +36 -0
- data/tests/acceptance/packrat/java/xtc.lang.java/Symbol.rats +77 -0
- data/tests/acceptance/packrat/minibasic/README +13 -0
- data/tests/acceptance/packrat/minibasic/atest_minibasic.rb +151 -13
- data/tests/acceptance/packrat/minibasic/minibasic.rb +94 -76
- data/tests/acceptance/packrat/minibasic/mult3.basic +6 -0
- data/tests/acceptance/packrat/minibasic/sumeven.basic +19 -0
- data/tests/unit/packrat/test_ast.rb +116 -0
- data/tests/unit/packrat/test_interpreting_parser.rb +15 -55
- metadata +22 -59
- data/lib/rockit/prettyprint/box.rb +0 -60
- data/lib/rockit/prettyprint/renderer.rb +0 -41
- data/lib/rockit/prettyprint/text_renderer.rb +0 -47
- data/lib/rockit/tree/base.rb +0 -223
- data/lib/rockit/tree/enter_leave_visitor.rb +0 -12
- data/lib/rockit/tree/graphviz.rb +0 -69
- data/lib/rockit/tree/visitor.rb +0 -12
- data/lib/util/array_alternatives.rb +0 -20
- data/lib/util/enter_leave_visitor.rb +0 -69
- data/lib/util/graphviz_dot.rb +0 -182
- data/lib/util/string_location.rb +0 -42
- data/lib/util/visitor.rb +0 -49
- data/lib/util/visitor_combinators.rb +0 -14
- data/tests/acceptance/rockit/dparser/atest_any_operator.rb +0 -33
- data/tests/acceptance/rockit/dparser/atest_arithmetic_grammar.rb +0 -30
- data/tests/acceptance/rockit/dparser/atest_list_operator.rb +0 -57
- data/tests/acceptance/rockit/dparser/atest_mult_operator.rb +0 -60
- data/tests/acceptance/rockit/dparser/atest_operator_grammar.rb +0 -61
- data/tests/acceptance/rockit/dparser/atest_plus_operator.rb +0 -55
- data/tests/acceptance/rockit/dparser/atest_samples_calculator.rb +0 -14
- data/tests/acceptance/rockit/dparser/atest_samples_minibasic.rb +0 -20
- data/tests/acceptance/rockit/dparser/atest_samples_multifunccalculator.rb +0 -36
- data/tests/acceptance/rockit/dparser/atest_simple_grammar.rb +0 -34
- data/tests/acceptance/rockit/dparser/atest_speculative_code_action.rb +0 -128
- data/tests/acceptance/rockit/dparser/calc_tests_common.rb +0 -103
- data/tests/unit/parse/utest_ebnf_grammar.rb +0 -50
- data/tests/unit/parse/utest_expand_grammar.rb +0 -23
- data/tests/unit/parse/utest_grammar.rb +0 -160
- data/tests/unit/rockit/assembler/llvm/utest_instructions.rb +0 -41
- data/tests/unit/rockit/assembler/llvm/utest_module.rb +0 -19
- data/tests/unit/rockit/prettyprint/utest_box.rb +0 -44
- data/tests/unit/rockit/tree/utest_tree_base.rb +0 -301
- data/tests/unit/rockit/tree/utest_tree_enter_leave_visitor.rb +0 -69
- data/tests/unit/rockit/tree/utest_tree_visitor.rb +0 -63
- data/tests/unit/rockit/utest_grammar.rb +0 -145
- data/tests/unit/rockit/utest_grammar_symbol.rb +0 -11
- data/tests/unit/rockit/utest_maybe_operator.rb +0 -12
- data/tests/unit/rockit/utest_regexp_terminal.rb +0 -45
- data/tests/unit/rockit/utest_repetition_operators.rb +0 -35
- data/tests/unit/rockit/utest_rule.rb +0 -23
- data/tests/unit/rockit/utest_string_terminal.rb +0 -40
- data/tests/unit/util/utest_array_alternatives.rb +0 -23
- data/tests/unit/util/utest_enter_leave_visitor.rb +0 -89
- data/tests/unit/util/utest_string_location.rb +0 -42
- data/tests/unit/util/utest_visitor.rb +0 -92
- data/tests/unit/util/utest_visitor_combinators.rb +0 -64
@@ -1,60 +0,0 @@
|
|
1
|
-
# A Formatting Language similar to BOX described in
|
2
|
-
# [vandenbrand1996a] and [dejonge2003a]
|
3
|
-
#
|
4
|
-
module Rockit
|
5
|
-
module PrettyPrint
|
6
|
-
module Box
|
7
|
-
# An element of the Box language
|
8
|
-
class Term
|
9
|
-
end
|
10
|
-
|
11
|
-
# H formats its elements horizontally with a given number of spaces
|
12
|
-
# in between.
|
13
|
-
class H < Term
|
14
|
-
attr_reader :num_hdelims, :elements
|
15
|
-
|
16
|
-
def initialize(numHorizontalDelims = 1, *elements)
|
17
|
-
@num_hdelims = numHdelims
|
18
|
-
@elements = elements
|
19
|
-
end
|
20
|
-
end
|
21
|
-
|
22
|
-
# H formats its elements horizontally with a given number of spaces
|
23
|
-
# in between.
|
24
|
-
class V < Term
|
25
|
-
attr_reader :elements
|
26
|
-
|
27
|
-
def initialize(*elements)
|
28
|
-
@elements = elements
|
29
|
-
end
|
30
|
-
end
|
31
|
-
|
32
|
-
# Epsilon is a H operator with no spaces in between
|
33
|
-
class Epsilon < H
|
34
|
-
def initialize(*elements)
|
35
|
-
super(0, *elements)
|
36
|
-
end
|
37
|
-
end
|
38
|
-
end
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
require 'rockit/prettyprint/text_renderer'
|
43
|
-
|
44
|
-
# We must do the def's below after requiring the text_renderer
|
45
|
-
# since there is a circular dependency between the definitions.
|
46
|
-
module Rockit
|
47
|
-
module PrettyPrint
|
48
|
-
module Box
|
49
|
-
class Term
|
50
|
-
def render
|
51
|
-
render_on(Box::TextRenderer.new)
|
52
|
-
end
|
53
|
-
|
54
|
-
def render_on(renderer)
|
55
|
-
renderer.render(self)
|
56
|
-
end
|
57
|
-
end
|
58
|
-
end
|
59
|
-
end
|
60
|
-
end
|
@@ -1,41 +0,0 @@
|
|
1
|
-
# Renderers for Box
|
2
|
-
#
|
3
|
-
module Rockit
|
4
|
-
module PrettyPrint
|
5
|
-
module Box
|
6
|
-
class Renderer
|
7
|
-
def reset_buffer
|
8
|
-
@buffer = ""
|
9
|
-
end
|
10
|
-
|
11
|
-
def string_buffer
|
12
|
-
@buffer
|
13
|
-
end
|
14
|
-
|
15
|
-
def render(boxTree)
|
16
|
-
reset_buffer
|
17
|
-
render_term(boxTree)
|
18
|
-
string_buffer
|
19
|
-
end
|
20
|
-
|
21
|
-
def <<(string)
|
22
|
-
@buffer << string
|
23
|
-
end
|
24
|
-
|
25
|
-
def render_term(boxTree)
|
26
|
-
raise NotImplementedError
|
27
|
-
end
|
28
|
-
|
29
|
-
def render_hdelim(num)
|
30
|
-
render_term(horizontal_delim * num)
|
31
|
-
end
|
32
|
-
end
|
33
|
-
end
|
34
|
-
end
|
35
|
-
end
|
36
|
-
|
37
|
-
class String
|
38
|
-
def render_as_text(renderer)
|
39
|
-
renderer << self
|
40
|
-
end
|
41
|
-
end
|
@@ -1,47 +0,0 @@
|
|
1
|
-
# Basic Text Renderer for Box
|
2
|
-
#
|
3
|
-
require 'rockit/prettyprint/renderer'
|
4
|
-
|
5
|
-
module Rockit
|
6
|
-
module PrettyPrint
|
7
|
-
module Box
|
8
|
-
class TextRenderer < Renderer
|
9
|
-
attr_reader :max_horizontal
|
10
|
-
attr_reader :horizontal_delim, :vertical_delim
|
11
|
-
|
12
|
-
def initialize(maxHorizontal = 80, horizontalDelim = " ",
|
13
|
-
verticalDelim = "\n")
|
14
|
-
@max_horizontal = maxHorizontal
|
15
|
-
@horizontal_delim = horizontalDelim
|
16
|
-
@vertical_delim = verticalDelim
|
17
|
-
end
|
18
|
-
|
19
|
-
def render_term(term)
|
20
|
-
# Instead of fiddling with visitors we simply add a uniquely named
|
21
|
-
# method render_as_text to each Box term we support.
|
22
|
-
term.render_as_text(self)
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
class H < Term
|
27
|
-
def render_as_text(renderer)
|
28
|
-
elements[0..-2].each do |e|
|
29
|
-
renderer.render_term(e)
|
30
|
-
renderer.render_hdelim(num_spaces)
|
31
|
-
end
|
32
|
-
renderer.render_term(elements[-1])
|
33
|
-
end
|
34
|
-
end
|
35
|
-
|
36
|
-
class V < Term
|
37
|
-
def render_as_text(renderer)
|
38
|
-
elements[0..-2].each do |e|
|
39
|
-
renderer.render_term(e)
|
40
|
-
renderer << "\n"
|
41
|
-
end
|
42
|
-
renderer.render_term(elements[-1])
|
43
|
-
end
|
44
|
-
end
|
45
|
-
end
|
46
|
-
end
|
47
|
-
end
|
data/lib/rockit/tree/base.rb
DELETED
@@ -1,223 +0,0 @@
|
|
1
|
-
require 'pp'
|
2
|
-
|
3
|
-
# Make sure Rockit module exists if we are loaded separetely from rest
|
4
|
-
# of Rockit
|
5
|
-
module Rockit; end
|
6
|
-
|
7
|
-
# Rockit::Tree defines a superclass for syntax trees. The trees has methods
|
8
|
-
# for easily creating and pattern matching trees.
|
9
|
-
module Rockit::Tree
|
10
|
-
class Base
|
11
|
-
include Enumerable
|
12
|
-
|
13
|
-
def self.new_tree_class(name, children_names = [])
|
14
|
-
name_as_str = name.to_s
|
15
|
-
unless name_as_str =~ /^[A-Z]/
|
16
|
-
raise NameError, "identifier #{name} needs to be constant"
|
17
|
-
end
|
18
|
-
unless constants.include?(name_as_str)
|
19
|
-
s = <<-EOC
|
20
|
-
class #{name_as_str} < #{self.inspect}
|
21
|
-
#{child_accessor_codes(children_names)}
|
22
|
-
end
|
23
|
-
EOC
|
24
|
-
class_eval s
|
25
|
-
end
|
26
|
-
class_eval "#{name_as_str}"
|
27
|
-
end
|
28
|
-
|
29
|
-
def self.child_accessor_codes(children_names)
|
30
|
-
i, s = 0, ""
|
31
|
-
while i < children_names.length
|
32
|
-
s += child_accessor_code(children_names[i], i)
|
33
|
-
i += 1
|
34
|
-
end
|
35
|
-
s
|
36
|
-
end
|
37
|
-
|
38
|
-
def self.child_accessor_code(children_name, index)
|
39
|
-
name = children_name.to_s
|
40
|
-
s = <<-EOC
|
41
|
-
def #{name}
|
42
|
-
@children[#{index}]
|
43
|
-
end
|
44
|
-
def #{name}=(newValue)
|
45
|
-
@children[#{index}] = newValue
|
46
|
-
end
|
47
|
-
EOC
|
48
|
-
end
|
49
|
-
|
50
|
-
def self.[](*children)
|
51
|
-
new(*children)
|
52
|
-
end
|
53
|
-
|
54
|
-
attr_reader :children
|
55
|
-
|
56
|
-
def initialize(*children)
|
57
|
-
@children = children
|
58
|
-
end
|
59
|
-
|
60
|
-
def [](index)
|
61
|
-
self.children[index]
|
62
|
-
end
|
63
|
-
|
64
|
-
def num_children
|
65
|
-
self.children.length
|
66
|
-
end
|
67
|
-
|
68
|
-
def ==(other)
|
69
|
-
self.class == other.class && self.children == other.children
|
70
|
-
end
|
71
|
-
|
72
|
-
def inspect
|
73
|
-
class_name + "[" +
|
74
|
-
self.children.map {|c| c.inspect}.join(", ") +
|
75
|
-
"]"
|
76
|
-
end
|
77
|
-
|
78
|
-
def class_name
|
79
|
-
self.class.inspect.split("::").last
|
80
|
-
end
|
81
|
-
|
82
|
-
def each_child
|
83
|
-
children.each {|c| yield(c)}
|
84
|
-
end
|
85
|
-
|
86
|
-
alias each each_child
|
87
|
-
|
88
|
-
# Depth-first traversal of (sub)trees in tree
|
89
|
-
def each_tree(&block)
|
90
|
-
block.call(self)
|
91
|
-
self.children.each do |c|
|
92
|
-
if Base === c
|
93
|
-
c.each_tree(&block)
|
94
|
-
else
|
95
|
-
block.call(c)
|
96
|
-
end
|
97
|
-
end
|
98
|
-
end
|
99
|
-
|
100
|
-
# Assuming klass is a subclass of Base
|
101
|
-
def each_tree_of_class(klass, recursive = false, &block)
|
102
|
-
cs = self.children
|
103
|
-
if self.kind_of?(klass)
|
104
|
-
block.call(self)
|
105
|
-
cs = [] unless recursive
|
106
|
-
end
|
107
|
-
cs.each do |c|
|
108
|
-
if Base === c
|
109
|
-
c.each_tree_of_class(klass, recursive, &block)
|
110
|
-
elsif Array === c
|
111
|
-
c.each {|ac|
|
112
|
-
ac.each_tree_of_class(klass, recursive, &block) if Base === ac
|
113
|
-
}
|
114
|
-
end
|
115
|
-
end
|
116
|
-
end
|
117
|
-
|
118
|
-
def match_tree(tree, matches = Hash.new)
|
119
|
-
if self.class == tree.class &&
|
120
|
-
self.num_children == tree.num_children
|
121
|
-
self.each_with_index do |child, i|
|
122
|
-
unless child.match_tree(tree[i], matches)
|
123
|
-
matches = nil
|
124
|
-
break
|
125
|
-
end
|
126
|
-
end
|
127
|
-
matches
|
128
|
-
else
|
129
|
-
nil
|
130
|
-
end
|
131
|
-
end
|
132
|
-
|
133
|
-
def =~(patternTree)
|
134
|
-
pattern = patternTree.upcase_symbols_to_pattern_vars
|
135
|
-
pattern.match_tree(self)
|
136
|
-
end
|
137
|
-
|
138
|
-
def select_trees_of_class(klass, recursive = false)
|
139
|
-
ary = []
|
140
|
-
each_tree_of_class(klass, recursive) {|t| ary << t}
|
141
|
-
ary
|
142
|
-
end
|
143
|
-
|
144
|
-
# Return all subtrees in tree which match the pattern self.
|
145
|
-
def all_matching_trees(tree)
|
146
|
-
# Only the subtrees with a root node of the right type are candidates
|
147
|
-
candidates = tree.select_trees_of_class(self.class, true)
|
148
|
-
pattern = self.upcase_symbols_to_pattern_vars
|
149
|
-
candidates.map do |t|
|
150
|
-
res = pattern.match_tree(t)
|
151
|
-
res ? [res, t] : nil
|
152
|
-
end.compact
|
153
|
-
end
|
154
|
-
|
155
|
-
# Representing a variable in a patternTree
|
156
|
-
class PatternVar
|
157
|
-
attr_reader :name
|
158
|
-
|
159
|
-
def initialize(name)
|
160
|
-
@name = name
|
161
|
-
end
|
162
|
-
|
163
|
-
# A variable match anything and the binding is noted in the matches
|
164
|
-
# hash.
|
165
|
-
def match_tree(tree, matches = Hash.new)
|
166
|
-
matches[@name] = tree
|
167
|
-
matches
|
168
|
-
end
|
169
|
-
|
170
|
-
def inspect
|
171
|
-
"Var_" + @name.to_s
|
172
|
-
end
|
173
|
-
|
174
|
-
# No need to def upcase_symbols_to_pattern_vars here since it
|
175
|
-
# inherits the one defined for Object below
|
176
|
-
end
|
177
|
-
|
178
|
-
# Convert upper case symbols to pattern variables
|
179
|
-
def upcase_symbols_to_pattern_vars
|
180
|
-
new_children = Array.new
|
181
|
-
self.each {|child| new_children << child.upcase_symbols_to_pattern_vars}
|
182
|
-
self.class.new(*new_children)
|
183
|
-
end
|
184
|
-
|
185
|
-
def pretty_print(pp)
|
186
|
-
pp.text class_name
|
187
|
-
pp.group(1, '[', ']') do
|
188
|
-
pp.breakable ""
|
189
|
-
pp.seplist(self.children) {|c| pp.pp c}
|
190
|
-
end
|
191
|
-
end
|
192
|
-
|
193
|
-
# The nodes in a tree are not linked upwards by default but by calling
|
194
|
-
# the set_parents method on the root the parent attribute on each subtree
|
195
|
-
# is set and can then be accessed.
|
196
|
-
attr_accessor :parent
|
197
|
-
|
198
|
-
def set_parents(parent = nil)
|
199
|
-
self.parent = parent
|
200
|
-
each_child {|c| c.set_parents(self) if c.kind_of?(Base)}
|
201
|
-
end
|
202
|
-
end
|
203
|
-
end
|
204
|
-
|
205
|
-
class Object
|
206
|
-
def match_tree(tree, matches = Hash.new)
|
207
|
-
self == tree
|
208
|
-
end
|
209
|
-
|
210
|
-
def upcase_symbols_to_pattern_vars
|
211
|
-
self
|
212
|
-
end
|
213
|
-
end
|
214
|
-
|
215
|
-
class Symbol
|
216
|
-
def upcase_symbols_to_pattern_vars
|
217
|
-
if self.to_s =~ /^[A-Z]/
|
218
|
-
Rockit::Tree::Base::PatternVar.new(self)
|
219
|
-
else
|
220
|
-
self
|
221
|
-
end
|
222
|
-
end
|
223
|
-
end
|
data/lib/rockit/tree/graphviz.rb
DELETED
@@ -1,69 +0,0 @@
|
|
1
|
-
require 'rockit/tree/base'
|
2
|
-
|
3
|
-
class Object
|
4
|
-
def to_graphviz_node_label; inspect; end
|
5
|
-
def to_graphviz_printer(printer); printer; end
|
6
|
-
end
|
7
|
-
|
8
|
-
class Array
|
9
|
-
def to_graphviz_node_label; "[]"; end
|
10
|
-
def to_graphviz_printer(printer)
|
11
|
-
label = printer.unique(self)
|
12
|
-
each do |child|
|
13
|
-
printer.add(label, child)
|
14
|
-
child.to_graphviz_printer(printer)
|
15
|
-
end
|
16
|
-
printer
|
17
|
-
end
|
18
|
-
end
|
19
|
-
|
20
|
-
class DotPrinter
|
21
|
-
def initialize
|
22
|
-
@links = []
|
23
|
-
@counts = Hash.new(0)
|
24
|
-
end
|
25
|
-
|
26
|
-
def unique(obj)
|
27
|
-
num = (@counts[obj.class] += 1)
|
28
|
-
obj.to_graphviz_node_label + " (#{num})"
|
29
|
-
end
|
30
|
-
|
31
|
-
def add(from, to)
|
32
|
-
@links << [from.to_graphviz_node_label, to.to_graphviz_node_label]
|
33
|
-
end
|
34
|
-
|
35
|
-
def to_dot_file
|
36
|
-
"digraph {" +
|
37
|
-
@links.uniq.map {|from, to| "#{from.inspect} -> #{to.inspect};"}.join("\n") +
|
38
|
-
"}"
|
39
|
-
end
|
40
|
-
|
41
|
-
def write_to_file(filename, format = "ps")
|
42
|
-
tmpfilename = "temp" + Time.now.strftime("%M%S_") + rand(1e10).inspect
|
43
|
-
File.open(tmpfilename, "w") do |fh|
|
44
|
-
fh.write self.to_dot_file
|
45
|
-
system "dot -T#{format} #{tmpfilename} > #{filename}"
|
46
|
-
end
|
47
|
-
# File.delete(tmpfilename)
|
48
|
-
end
|
49
|
-
end
|
50
|
-
|
51
|
-
module Rockit::Tree
|
52
|
-
class Base
|
53
|
-
def to_graphviz_printer(printer = DotPrinter.new)
|
54
|
-
children.each do |child|
|
55
|
-
printer.add(self, child)
|
56
|
-
child.to_graphviz_printer(printer)
|
57
|
-
end
|
58
|
-
printer
|
59
|
-
end
|
60
|
-
|
61
|
-
def to_graphviz_node_label
|
62
|
-
class_name_as_string
|
63
|
-
end
|
64
|
-
|
65
|
-
def class_name_as_string
|
66
|
-
self.class.inspect.split("::").last
|
67
|
-
end
|
68
|
-
end
|
69
|
-
end
|