opal 0.3.26 → 0.3.27

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.
Files changed (74) hide show
  1. data/.gitignore +1 -6
  2. data/.travis.yml +1 -4
  3. data/Gemfile +1 -1
  4. data/README.md +3 -8
  5. data/Rakefile +26 -3
  6. data/core/array.rb +33 -91
  7. data/core/boolean.rb +1 -4
  8. data/core/class.rb +25 -71
  9. data/core/error.rb +5 -3
  10. data/core/hash.rb +3 -2
  11. data/core/kernel.rb +40 -1
  12. data/core/load_order +1 -1
  13. data/core/nil_class.rb +1 -3
  14. data/core/runtime.js +4 -44
  15. data/core/template.rb +20 -0
  16. data/core/{opal-spec → test_runner}/runner.js +0 -6
  17. data/lib/opal.rb +1 -12
  18. data/lib/opal/builder.rb +3 -10
  19. data/lib/opal/lexer.rb +1095 -1110
  20. data/lib/opal/parser.rb +229 -26
  21. data/lib/opal/rake_task.rb +3 -3
  22. data/lib/opal/version.rb +1 -1
  23. data/opal.gemspec +2 -2
  24. data/spec/core/array/assoc_spec.rb +2 -3
  25. data/spec/core/array/comparison_spec.rb +16 -0
  26. data/spec/core/array/constructor_spec.rb +0 -9
  27. data/spec/core/array/drop_spec.rb +21 -0
  28. data/spec/core/array/dup_spec.rb +15 -0
  29. data/spec/core/array/{eql_spec.rb → equal_value_spec.rb} +0 -0
  30. data/spec/core/array/index_spec.rb +26 -0
  31. data/spec/core/array/inspect_spec.rb +13 -0
  32. data/spec/core/array/intersection_spec.rb +22 -0
  33. data/spec/core/array/join_spec.rb +9 -0
  34. data/spec/core/array/keep_if_spec.rb +7 -0
  35. data/spec/core/array/minus_spec.rb +19 -9
  36. data/spec/core/array/multiply_spec.rb +13 -0
  37. data/spec/core/array/new_spec.rb +40 -0
  38. data/spec/core/array/rindex_spec.rb +21 -0
  39. data/spec/core/array/select_spec.rb +13 -0
  40. data/spec/core/array/shift_spec.rb +51 -0
  41. data/spec/core/array/slice_spec.rb +37 -0
  42. data/spec/core/array/take_spec.rb +21 -0
  43. data/spec/core/array/take_while_spec.rb +13 -0
  44. data/spec/core/array/to_a_spec.rb +7 -0
  45. data/spec/core/array/unshift_spec.rb +29 -0
  46. data/spec/core/hash/constructor_spec.rb +13 -0
  47. data/spec/core/hash/default_proc_spec.rb +20 -0
  48. data/spec/core/hash/default_spec.rb +8 -0
  49. data/spec/core/hash/delete_spec.rb +11 -0
  50. data/spec/core/hash/dup_spec.rb +10 -0
  51. data/spec/core/hash/reject_spec.rb +18 -0
  52. data/spec/core/hash/to_a_spec.rb +13 -0
  53. data/spec/core/kernel/Array_spec.rb +10 -0
  54. data/spec/core/kernel/class_spec.rb +6 -0
  55. data/spec/core/kernel/equal_spec.rb +12 -0
  56. data/spec/core/kernel/extend_spec.rb +21 -0
  57. data/spec/core/kernel/instance_eval_spec.rb +28 -0
  58. data/spec/core/kernel/instance_variable_get_spec.rb +14 -0
  59. data/spec/core/kernel/instance_variable_set_spec.rb +10 -0
  60. data/spec/core/kernel/match_spec.rb +5 -0
  61. data/spec/core/module/alias_method_spec.rb +10 -0
  62. data/spec/core/module/ancestors_spec.rb +11 -0
  63. data/spec/core/module/append_features_spec.rb +14 -0
  64. data/spec/core/proc/call_spec.rb +21 -0
  65. data/spec/core/proc/proc_tricks_spec.rb +1 -1
  66. data/spec/language/alias_spec.rb +1 -1
  67. data/spec/opal/class/instance_methods_spec.rb +13 -0
  68. data/spec/opal/kernel/attribute_spec.rb +57 -0
  69. data/spec/spec_helper.rb +1 -1
  70. data/spec/test_case.html +13 -0
  71. metadata +88 -12
  72. data/core/erb.rb +0 -32
  73. data/lib/opal/erb_parser.rb +0 -20
  74. data/spec/opal/erb/erb_spec.rb +0 -23
data/core/error.rb CHANGED
@@ -3,7 +3,9 @@ class Exception < `Error`
3
3
 
4
4
  def self.new(message = '')
5
5
  %x{
6
- return new Error(message);
6
+ var err = new Error(message);
7
+ err._klass = #{self};
8
+ return err;
7
9
  }
8
10
  end
9
11
 
@@ -12,10 +14,10 @@ class Exception < `Error`
12
14
  var backtrace = #{self}.stack;
13
15
 
14
16
  if (typeof(backtrace) === 'string') {
15
- return backtrace.split("\\n");
17
+ return backtrace.split("\\n").slice(0, 15);
16
18
  }
17
19
  else if (backtrace) {
18
- return backtrace;
20
+ return backtrace.slice(0, 15);
19
21
  }
20
22
 
21
23
  return [];
data/core/hash.rb CHANGED
@@ -166,12 +166,13 @@ class Hash
166
166
  var map = #{self}.map, result;
167
167
 
168
168
  if (result = map[key]) {
169
- result = bucket[1];
169
+ result = result[1];
170
170
 
171
171
  delete map[key];
172
+ return result;
172
173
  }
173
174
 
174
- return result;
175
+ return nil;
175
176
  }
176
177
  end
177
178
 
data/core/kernel.rb CHANGED
@@ -32,6 +32,32 @@ module Kernel
32
32
  }
33
33
  end
34
34
 
35
+ def attribute_get(name)
36
+ %x{
37
+ var meth = '$' + name;
38
+ if (#{self}[meth]) {
39
+ return #{self}[meth]();
40
+ }
41
+
42
+ meth += '?';
43
+ if (#{self}[meth]) {
44
+ return #{self}[meth]()
45
+ }
46
+
47
+ return nil;
48
+ }
49
+ end
50
+
51
+ def attribute_set(name, value)
52
+ %x{
53
+ if (#{self}['$' + name + '=']) {
54
+ return #{self}['$' + name + '='](value);
55
+ }
56
+
57
+ return nil;
58
+ }
59
+ end
60
+
35
61
  def class
36
62
  `return #{self}._klass`
37
63
  end
@@ -83,7 +109,7 @@ module Kernel
83
109
  no_block_given();
84
110
  }
85
111
 
86
- return block.call(#{self});
112
+ return block.call(#{self}, #{self});
87
113
  }
88
114
  end
89
115
 
@@ -213,6 +239,19 @@ module Kernel
213
239
 
214
240
  def singleton_class
215
241
  %x{
242
+ if (#{self}._isClass) {
243
+ if (#{self}._singleton) {
244
+ return #{self}._singleton;
245
+ }
246
+
247
+ var meta = new __opal.Class;
248
+ meta._klass = __opal.Class;
249
+ #{self}._singleton = meta;
250
+ meta.prototype = #{self};
251
+
252
+ return meta;
253
+ }
254
+
216
255
  if (!#{self}._isObject) {
217
256
  return #{self}._klass;
218
257
  }
data/core/load_order CHANGED
@@ -15,4 +15,4 @@ proc
15
15
  range
16
16
  time
17
17
  json
18
- erb
18
+ template
data/core/nil_class.rb CHANGED
@@ -48,6 +48,4 @@ class NilClass
48
48
  def to_s
49
49
  ''
50
50
  end
51
- end
52
-
53
- NIL = nil
51
+ end
data/core/runtime.js CHANGED
@@ -7,9 +7,6 @@ function Object(){}
7
7
  // Class' class
8
8
  function Class(){}
9
9
 
10
- // Modules are just classes that cannot be instantiated
11
- var Module = Class;
12
-
13
10
  // the class of nil
14
11
  function NilClass(){}
15
12
 
@@ -38,38 +35,6 @@ Opal.cvars = {};
38
35
  // Globals table
39
36
  Opal.gvars = {};
40
37
 
41
- // Runtime method used to either define a new class, or re-open an old
42
- // class. The base may be an object (rather than a class), which is
43
- // always the case when defining classes in the top level as the top
44
- // level is just the 'main' Object instance.
45
- //
46
- // The given ruby code:
47
- //
48
- // class Foo
49
- // 42
50
- // end
51
- //
52
- // class Bar < Foo
53
- // 3.142
54
- // end
55
- //
56
- // Would be compiled to something like:
57
- //
58
- // var __klass = Opal.klass;
59
- //
60
- // __klass(this, null, 'Foo', function() {
61
- // return 42;
62
- // });
63
- //
64
- // __klass(this, __scope.Foo, 'Bar', function() {
65
- // return 3.142;
66
- // });
67
- //
68
- // @param [RubyObject] base the scope in which to define the class
69
- // @param [RubyClass] superklass the superklass, may be null
70
- // @param [String] id the name for the class
71
- // @param [Function] body the class body
72
- // @return returns last value from running body
73
38
  Opal.klass = function(base, superklass, id, constructor) {
74
39
  var klass;
75
40
  if (base._isObject) {
@@ -121,7 +86,7 @@ Opal.module = function(base, id, constructor) {
121
86
  klass = base._scope[id];
122
87
  }
123
88
  else {
124
- klass = boot_class(Module, constructor);
89
+ klass = boot_class(Class, constructor);
125
90
  klass._name = (base === Object ? id : base._name + '::' + id);
126
91
 
127
92
  klass._isModule = true;
@@ -227,7 +192,7 @@ var bridge_class = function(constructor) {
227
192
  constructor['$==='] = module_eqq;
228
193
  constructor.$to_s = module_to_s;
229
194
 
230
- var smethods = constructor._smethods = Module._methods.slice();
195
+ var smethods = constructor._smethods = Class._methods.slice();
231
196
  for (var i = 0, length = smethods.length; i < length; i++) {
232
197
  var m = smethods[i];
233
198
  constructor[m] = Object[m];
@@ -256,14 +221,9 @@ boot_defclass('Object', Object);
256
221
  boot_defclass('Class', Class, Object);
257
222
 
258
223
  Class.prototype = Function.prototype;
259
-
260
224
  Object._klass = Class._klass = Class;
261
225
 
262
- Module._donate = function(defined) {
263
- // ...
264
- };
265
-
266
- // Implementation of Module#===
226
+ // Implementation of Class#===
267
227
  function module_eqq(object) {
268
228
  if (object == null) {
269
229
  return false;
@@ -282,7 +242,7 @@ function module_eqq(object) {
282
242
  return false;
283
243
  }
284
244
 
285
- // Implementation of Module#to_s
245
+ // Implementation of Class#to_s
286
246
  function module_to_s() {
287
247
  return this._name;
288
248
  }
data/core/template.rb ADDED
@@ -0,0 +1,20 @@
1
+ class Template
2
+ @_cache = {}
3
+ def self.[](name)
4
+ @_cache[name]
5
+ end
6
+
7
+ def self.[]=(name, instance)
8
+ @_cache[name] = instance
9
+ end
10
+
11
+ def initialize(name, &body)
12
+ @body = body
13
+ @name = name
14
+ Template[name] = self
15
+ end
16
+
17
+ def render(ctx=self)
18
+ ctx.instance_eval(&@body)
19
+ end
20
+ end
@@ -1,10 +1,4 @@
1
1
  var args = phantom.args;
2
-
3
- if (args.length !== 1) {
4
- console.log("Usage: " + phantom.scriptName + " <URL>");
5
- phantom.exit(1);
6
- }
7
-
8
2
  var page = require('webpage').create();
9
3
 
10
4
  page.onConsoleMessage = function(msg) {
data/lib/opal.rb CHANGED
@@ -1,15 +1,4 @@
1
- unless Symbol.instance_methods.include?(:[])
2
- unless String == Symbol
3
- class Symbol
4
- def []key
5
- to_s[key]
6
- end
7
- end
8
- end
9
- end
10
-
11
1
  require 'opal/parser'
12
- require 'opal/erb_parser'
13
2
  require 'opal/builder'
14
3
  require 'opal/version'
15
4
 
@@ -26,7 +15,7 @@ module Opal
26
15
  # @param [String] file the filename to use when parsing
27
16
  # @return [String] the resulting javascript code
28
17
  def self.parse(str, file='(file)')
29
- "(#{ Parser.new.parse str, file })();"
18
+ Parser.new.parse str, file
30
19
  end
31
20
 
32
21
  # Returns opal runtime js code (string)
data/lib/opal/builder.rb CHANGED
@@ -30,8 +30,8 @@ module Opal
30
30
  sources.each do |s|
31
31
  s = File.expand_path(File.join @dir, s)
32
32
  if File.directory? s
33
- files.push *Dir[File.join(s, '**/*.{rb,js,erb}')]
34
- elsif %w(.rb .js .erb).include? File.extname(s)
33
+ files.push *Dir[File.join(s, '**/*.rb')]
34
+ elsif File.extname(s) == '.rb'
35
35
  files << s
36
36
  end
37
37
  end
@@ -70,16 +70,9 @@ module Opal
70
70
  if File.extname(file) == '.rb'
71
71
  code = @parser.parse File.read(file), lib_name
72
72
  @requires[lib_name] = @parser.requires
73
- elsif File.extname(file) == '.erb'
74
- template_name = lib_name_for(file).chomp(File.extname(file))
75
- code = Opal::ERBParser.new.parse File.read(file), template_name
76
- @requires[lib_name] = []
77
- else # javascript
78
- code = "function() {\n #{ File.read file }\n}"
79
- @requires[lib_name] = []
80
73
  end
81
74
 
82
- @files[lib_name] = "// #{ parser_name }\n(#{ code })();"
75
+ @files[lib_name] = "// #{ parser_name }\n#{ code }"
83
76
  end
84
77
 
85
78
  def parser_name_for(file)
data/lib/opal/lexer.rb CHANGED
@@ -14,1376 +14,1361 @@ module Opal
14
14
 
15
15
  class Grammar < Racc::Parser
16
16
 
17
- attr_reader :line
17
+ attr_reader :line
18
18
 
19
- def initialize
20
- @lex_state = :expr_beg
21
- @cond = 0
22
- @cmdarg = 0
23
- @line = 1
24
- @scopes = []
19
+ def initialize
20
+ @lex_state = :expr_beg
21
+ @cond = 0
22
+ @cmdarg = 0
23
+ @line = 1
24
+ @scopes = []
25
25
 
26
- @string_parse_stack = []
27
- end
28
-
29
- def s(*parts)
30
- sexp = Sexp.new(parts)
31
- sexp.line = @line
32
- sexp
33
- end
34
-
35
- def parse(source, file = '(string)')
36
- @file = file
37
- @scanner = StringScanner.new source
38
- push_scope
39
- result = do_parse
40
- pop_scope
41
-
42
- result
43
- end
26
+ @string_parse_stack = []
27
+ end
44
28
 
45
- def on_error(t, val, vstack)
46
- raise OpalParseError, "parse error on value #{val.inspect} (line #{@line})"
47
- end
29
+ def s(*parts)
30
+ sexp = Sexp.new(parts)
31
+ sexp.line = @line
32
+ sexp
33
+ end
48
34
 
49
- class LexerScope
50
- attr_reader :locals
51
- attr_accessor :parent
35
+ def parse(source, file = '(string)')
36
+ @file = file
37
+ @scanner = StringScanner.new source
38
+ push_scope
39
+ result = do_parse
40
+ pop_scope
52
41
 
53
- def initialize type
54
- @block = type == :block
55
- @locals = []
56
- @parent = nil
42
+ result
57
43
  end
58
44
 
59
- def add_local local
60
- @locals << local
45
+ def on_error(t, val, vstack)
46
+ raise OpalParseError, "parse error on value #{val.inspect} (line #{@line})"
61
47
  end
62
48
 
63
- def has_local? local
64
- return true if @locals.include? local
65
- return @parent.has_local?(local) if @parent and @block
66
- false
67
- end
68
- end
49
+ class LexerScope
50
+ attr_reader :locals
51
+ attr_accessor :parent
69
52
 
70
- def push_scope type = nil
71
- top = @scopes.last
72
- scope = LexerScope.new type
73
- scope.parent = top
74
- @scopes << scope
75
- @scope = scope
76
- end
53
+ def initialize(type)
54
+ @block = type == :block
55
+ @locals = []
56
+ @parent = nil
57
+ end
77
58
 
78
- def pop_scope
79
- @scopes.pop
80
- @scope = @scopes.last
81
- end
59
+ def add_local(local)
60
+ @locals << local
61
+ end
82
62
 
83
- def new_block stmt = nil
84
- s = s(:block)
85
- s << stmt if stmt
86
- s
87
- end
63
+ def has_local?(local)
64
+ return true if @locals.include? local
65
+ return @parent.has_local?(local) if @parent and @block
66
+ false
67
+ end
68
+ end
88
69
 
89
- def new_compstmt block
90
- if block.size == 1
91
- nil
92
- elsif block.size == 2
93
- block[1]
94
- else
95
- block.line = block[1].line
96
- block
70
+ def push_scope(type = nil)
71
+ top = @scopes.last
72
+ scope = LexerScope.new type
73
+ scope.parent = top
74
+ @scopes << scope
75
+ @scope = scope
97
76
  end
98
- end
99
77
 
100
- def new_body(compstmt, res, els, ens)
101
- s = compstmt || s(:block)
78
+ def pop_scope
79
+ @scopes.pop
80
+ @scope = @scopes.last
81
+ end
102
82
 
103
- if compstmt
104
- # s = s(:block, compstmt) unless compstmt[0] == :block
105
- s.line = compstmt.line
83
+ def new_block(stmt = nil)
84
+ s = s(:block)
85
+ s << stmt if stmt
86
+ s
106
87
  end
107
88
 
108
- if res
109
- s = s(:rescue, s)
110
- res.each { |r| s << r }
111
- s << els if els
89
+ def new_compstmt(block)
90
+ if block.size == 1
91
+ nil
92
+ elsif block.size == 2
93
+ block[1]
94
+ else
95
+ block.line = block[1].line
96
+ block
97
+ end
112
98
  end
113
99
 
114
- if ens
115
- s = s(:ensure, s, ens)
100
+ def new_body(compstmt, res, els, ens)
101
+ s = compstmt || s(:block)
102
+ s.line = compstmt.line if compstmt
103
+
104
+ if res
105
+ s = s(:rescue, s)
106
+ res.each { |r| s << r }
107
+ s << els if els
108
+ end
109
+
110
+ ens ? s(:ensure, s, ens) : s
116
111
  end
117
112
 
118
- s
119
- end
113
+ def new_defn(line, name, args, body)
114
+ body = s(:block, body) if body[0] != :block
115
+ scope = s(:scope, body)
116
+ body << s(:nil) if body.size == 1
117
+ scope.line = body.line
118
+ args.line = line
119
+ s = s(:defn, name.to_sym, args, scope)
120
+ s.line = line
121
+ s.end_line = @line
122
+ s
123
+ end
120
124
 
121
- def new_defn line, name, args, body
122
- body = s(:block, body) if body[0] != :block
123
- scope = s(:scope, body)
124
- body << s(:nil) if body.size == 1
125
- scope.line = body.line
126
- args.line = line
127
- s = s(:defn, name.to_sym, args, scope)
128
- s.line = line
129
- s.end_line = @line
130
- s
131
- end
125
+ def new_defs(line, recv, name, args, body)
126
+ scope = s(:scope, body)
127
+ scope.line = body.line
128
+ s = s(:defs, recv, name.to_sym, args, scope)
129
+ s.line = line
130
+ s.end_line = @line
131
+ s
132
+ end
132
133
 
133
- def new_defs line, recv, name, args, body
134
- scope = s(:scope, body)
135
- scope.line = body.line
136
- s = s(:defs, recv, name.to_sym, args, scope)
137
- s.line = line
138
- s.end_line = @line
139
- s
140
- end
134
+ def new_class(path, sup, body)
135
+ scope = s(:scope)
136
+ scope << body unless body.size == 1
137
+ scope.line = body.line
138
+ s = s(:class, path, sup, scope)
139
+ s
140
+ end
141
141
 
142
- def new_class path, sup, body
143
- scope = s(:scope)
144
- scope << body unless body.size == 1
145
- scope.line = body.line
146
- s = s(:class, path, sup, scope)
147
- s
148
- end
142
+ def new_sclass(expr, body)
143
+ scope = s(:scope)
144
+ scope << body #unless body.size == 1
145
+ scope.line = body.line
146
+ s = s(:sclass, expr, scope)
147
+ s
148
+ end
149
149
 
150
- def new_sclass expr, body
151
- scope = s(:scope)
152
- scope << body #unless body.size == 1
153
- scope.line = body.line
154
- s = s(:sclass, expr, scope)
155
- s
156
- end
150
+ def new_module(path, body)
151
+ scope = s(:scope)
152
+ scope << body unless body.size == 1
153
+ scope.line = body.line
154
+ s = s(:module, path, scope)
155
+ s
156
+ end
157
157
 
158
- def new_module path, body
159
- scope = s(:scope)
160
- scope << body unless body.size == 1
161
- scope.line = body.line
162
- s = s(:module, path, scope)
163
- s
164
- end
158
+ def new_iter(call, args, body)
159
+ s = s(:iter, call, args)
160
+ s << body if body
161
+ s.end_line = @line
162
+ s
163
+ end
165
164
 
166
- def new_iter call, args, body
167
- s = s(:iter, call, args)
168
- s << body if body
169
- s.end_line = @line
170
- s
171
- end
165
+ def new_if(expr, stmt, tail)
166
+ s = s(:if, expr, stmt, tail)
167
+ s.line = expr.line
168
+ s.end_line = @line
169
+ s
170
+ end
172
171
 
173
- def new_if expr, stmt, tail
174
- s = s(:if, expr, stmt, tail)
175
- s.line = expr.line
176
- s.end_line = @line
177
- s
178
- end
172
+ def new_args(norm, opt, rest, block)
173
+ res = s(:args)
179
174
 
180
- def new_args norm, opt, rest, block
181
- res = s(:args)
175
+ if norm
176
+ norm.each do |arg|
177
+ @scope.add_local arg
178
+ res << arg
179
+ end
180
+ end
182
181
 
183
- if norm
184
- norm.each do |arg|
185
- @scope.add_local arg
186
- res << arg
182
+ if opt
183
+ opt[1..-1].each do |_opt|
184
+ res << _opt[1]
185
+ end
187
186
  end
188
- end
189
187
 
190
- if opt
191
- opt[1..-1].each do |_opt|
192
- res << _opt[1]
188
+ if rest
189
+ res << rest
190
+ @scope.add_local begin
191
+ rest.to_s[1..-1].to_sym
192
+ rescue ArgumentError => e
193
+ # Rescue from empty symbol error on Ruby 1.8
194
+ raise unless e.message =~ /empty/
195
+ ''
196
+ end
193
197
  end
194
- end
195
198
 
196
- if rest
197
- res << rest
198
- @scope.add_local begin
199
- rest.to_s[1..-1].to_sym
200
- rescue ArgumentError => e
201
- # Rescue from empty symbol error on Ruby 1.8
202
- raise unless e.message =~ /empty/
203
- ''
199
+ if block
200
+ res << block
201
+ @scope.add_local block.to_s[1..-1].to_sym
204
202
  end
205
- end
206
203
 
207
- if block
208
- res << block
209
- @scope.add_local block.to_s[1..-1].to_sym
204
+ res << opt if opt
205
+
206
+ res
210
207
  end
211
208
 
212
- res << opt if opt
209
+ def new_block_args(norm, opt, rest, block)
210
+ res = s(:array)
213
211
 
214
- res
215
- end
212
+ if norm
213
+ norm.each do |arg|
214
+ @scope.add_local arg
215
+ res << s(:lasgn, arg)
216
+ end
217
+ end
216
218
 
217
- def new_block_args norm, opt, rest, block
218
- res = s(:array)
219
+ if opt
220
+ opt[1..-1].each do |_opt|
221
+ res << s(:lasgn, _opt[1])
222
+ end
223
+ end
219
224
 
220
- if norm
221
- norm.each do |arg|
222
- @scope.add_local arg
223
- res << s(:lasgn, arg)
225
+ if rest
226
+ r = rest.to_s[1..-1].to_sym
227
+ res << s(:splat, s(:lasgn, r))
228
+ @scope.add_local r
224
229
  end
225
- end
226
230
 
227
- if opt
228
- opt[1..-1].each do |_opt|
229
- res << s(:lasgn, _opt[1])
231
+ if block
232
+ b = block.to_s[1..-1].to_sym
233
+ res << s(:block_pass, s(:lasgn, b))
234
+ @scope.add_local b
230
235
  end
231
- end
232
236
 
233
- if rest
234
- r = rest.to_s[1..-1].to_sym
235
- res << s(:splat, s(:lasgn, r))
236
- @scope.add_local r
237
- end
237
+ res << opt if opt
238
238
 
239
- if block
240
- b = block.to_s[1..-1].to_sym
241
- res << s(:block_pass, s(:lasgn, b))
242
- @scope.add_local b
239
+ res.size == 2 && norm ? res[1] : s(:masgn, res)
243
240
  end
244
241
 
245
- res << opt if opt
242
+ def new_call(recv, meth, args = nil)
243
+ call = s(:call, recv, meth)
244
+ args = s(:arglist) unless args
245
+ args[0] = :arglist if args[0] == :array
246
+ call << args
246
247
 
247
- res.size == 2 && norm ? res[1] : s(:masgn, res)
248
- end
248
+ if recv
249
+ call.line = recv.line
250
+ elsif args[1]
251
+ call.line = args[1].line
252
+ end
249
253
 
250
- def new_call recv, meth, args = nil
251
- call = s(:call, recv, meth)
252
- args = s(:arglist) unless args
253
- args[0] = :arglist if args[0] == :array
254
- call << args
254
+ # fix arglist spilling over into next line if no args
255
+ if args.length == 1
256
+ args.line = call.line
257
+ else
258
+ args.line = args[1].line
259
+ end
255
260
 
256
- if recv
257
- call.line = recv.line
258
- elsif args[1]
259
- call.line = args[1].line
261
+ call
260
262
  end
261
263
 
262
- # fix arglist spilling over into next line if no args
263
- if args.length == 1
264
- args.line = call.line
265
- else
266
- args.line = args[1].line
264
+ def add_block_pass(arglist, block)
265
+ arglist << block if block
266
+ arglist
267
267
  end
268
268
 
269
- call
270
- end
271
-
272
- def add_block_pass arglist, block
273
- arglist << block if block
274
- arglist
275
- end
269
+ def new_op_asgn(op, lhs, rhs)
270
+ case op
271
+ when :"||"
272
+ result = s(:op_asgn_or, new_gettable(lhs))
273
+ result << (lhs << rhs)
274
+ when :"&&"
275
+ result = s(:op_asgn_and, new_gettable(lhs))
276
+ result << (lhs << rhs)
277
+ else
278
+ result = lhs
279
+ result << new_call(new_gettable(lhs), op, s(:arglist, rhs))
280
+
281
+ end
276
282
 
277
- def new_op_asgn op, lhs, rhs
278
- case op
279
- when :"||"
280
- result = s(:op_asgn_or, new_gettable(lhs))
281
- result << (lhs << rhs)
282
- when :"&&"
283
- result = s(:op_asgn_and, new_gettable(lhs))
284
- result << (lhs << rhs)
285
- else
286
- result = lhs
287
- result << new_call(new_gettable(lhs), op, s(:arglist, rhs))
288
-
283
+ result.line = lhs.line
284
+ result
289
285
  end
290
286
 
291
- result.line = lhs.line
292
- result
293
- end
294
-
295
- def new_assign lhs, rhs
296
- case lhs[0]
297
- when :iasgn, :cdecl, :lasgn, :gasgn, :cvdecl
298
- lhs << rhs
299
- lhs
300
- when :call, :attrasgn
301
- lhs.last << rhs
302
- lhs
303
- else
304
- raise "Bad lhs for new_assign: #{lhs[0]}"
287
+ def new_assign(lhs, rhs)
288
+ case lhs[0]
289
+ when :iasgn, :cdecl, :lasgn, :gasgn, :cvdecl
290
+ lhs << rhs
291
+ lhs
292
+ when :call, :attrasgn
293
+ lhs.last << rhs
294
+ lhs
295
+ else
296
+ raise "Bad lhs for new_assign: #{lhs[0]}"
297
+ end
305
298
  end
306
- end
307
299
 
308
- def new_assignable ref
309
- case ref[0]
310
- when :ivar
311
- ref[0] = :iasgn
312
- when :const
313
- ref[0] = :cdecl
314
- when :identifier
315
- @scope.add_local ref[1] unless @scope.has_local? ref[1]
316
- ref[0] = :lasgn
317
- when :gvar
318
- ref[0] = :gasgn
319
- when :cvar
320
- ref[0] = :cvdecl
321
- else
322
- raise "Bad new_assignable type: #{ref[0]}"
323
- end
300
+ def new_assignable(ref)
301
+ case ref[0]
302
+ when :ivar
303
+ ref[0] = :iasgn
304
+ when :const
305
+ ref[0] = :cdecl
306
+ when :identifier
307
+ @scope.add_local ref[1] unless @scope.has_local? ref[1]
308
+ ref[0] = :lasgn
309
+ when :gvar
310
+ ref[0] = :gasgn
311
+ when :cvar
312
+ ref[0] = :cvdecl
313
+ else
314
+ raise "Bad new_assignable type: #{ref[0]}"
315
+ end
324
316
 
325
- ref
326
- end
317
+ ref
318
+ end
327
319
 
328
- def new_gettable ref
329
- res = case ref[0]
330
- when :lasgn
331
- s(:lvar, ref[1])
332
- when :iasgn
333
- s(:ivar, ref[1])
334
- when :gasgn
335
- s(:gvar, ref[1])
336
- when :cvdecl
337
- s(:cvar, ref[1])
338
- else
339
- raise "Bad new_gettable ref: #{ref[0]}"
340
- end
320
+ def new_gettable(ref)
321
+ res = case ref[0]
322
+ when :lasgn
323
+ s(:lvar, ref[1])
324
+ when :iasgn
325
+ s(:ivar, ref[1])
326
+ when :gasgn
327
+ s(:gvar, ref[1])
328
+ when :cvdecl
329
+ s(:cvar, ref[1])
330
+ else
331
+ raise "Bad new_gettable ref: #{ref[0]}"
332
+ end
341
333
 
342
- res.line = ref.line
343
- res
344
- end
334
+ res.line = ref.line
335
+ res
336
+ end
345
337
 
346
- def new_var_ref ref
347
- case ref[0]
348
- when :self, :nil, :true, :false, :line, :file
349
- ref
350
- when :const
351
- ref
352
- when :ivar, :gvar, :cvar
353
- ref
354
- when :lit
355
- # this is when we passed __LINE__ which is converted into :lit
356
- ref
357
- when :str
358
- # returns for __FILE__ as it is converted into str
359
- ref
360
- when :identifier
361
- if @scope.has_local? ref[1]
362
- s(:lvar, ref[1])
338
+ def new_var_ref(ref)
339
+ case ref[0]
340
+ when :self, :nil, :true, :false, :line, :file
341
+ ref
342
+ when :const
343
+ ref
344
+ when :ivar, :gvar, :cvar
345
+ ref
346
+ when :lit
347
+ # this is when we passed __LINE__ which is converted into :lit
348
+ ref
349
+ when :str
350
+ # returns for __FILE__ as it is converted into str
351
+ ref
352
+ when :identifier
353
+ if @scope.has_local? ref[1]
354
+ s(:lvar, ref[1])
355
+ else
356
+ s(:call, nil, ref[1], s(:arglist))
357
+ end
363
358
  else
364
- s(:call, nil, ref[1], s(:arglist))
359
+ raise "Bad var_ref type: #{ref[0]}"
365
360
  end
366
- else
367
- raise "Bad var_ref type: #{ref[0]}"
368
361
  end
369
- end
370
-
371
- def new_super args
372
- args = (args || s(:arglist))[1..-1]
373
- s(:super, *args)
374
- end
375
362
 
376
- def new_yield args
377
- args = (args || s(:arglist))[1..-1]
378
- s(:yield, *args)
379
- end
363
+ def new_super(args)
364
+ args = (args || s(:arglist))[1..-1]
365
+ s(:super, *args)
366
+ end
380
367
 
381
- def new_xstr str
382
- return s(:xstr, '') unless str
383
- case str[0]
384
- when :str then str[0] = :xstr
385
- when :dstr then str[0] = :dxstr
386
- when :evstr then str = s(:dxstr, '', str)
368
+ def new_yield(args)
369
+ args = (args || s(:arglist))[1..-1]
370
+ s(:yield, *args)
387
371
  end
388
372
 
389
- str
390
- end
373
+ def new_xstr(str)
374
+ return s(:xstr, '') unless str
375
+ case str[0]
376
+ when :str then str[0] = :xstr
377
+ when :dstr then str[0] = :dxstr
378
+ when :evstr then str = s(:dxstr, '', str)
379
+ end
391
380
 
392
- def new_dsym str
393
- return s(:nil) unless str
394
- case str[0]
395
- when :str
396
- str[0] = :lit
397
- str[1] = str[1].to_sym
398
- when :dstr
399
- str[0] = :dsym
381
+ str
400
382
  end
401
383
 
402
- str
403
- end
384
+ def new_dsym(str)
385
+ return s(:nil) unless str
386
+ case str[0]
387
+ when :str
388
+ str[0] = :lit
389
+ str[1] = str[1].to_sym
390
+ when :dstr
391
+ str[0] = :dsym
392
+ end
404
393
 
405
- def new_str str
406
- # cover empty strings
407
- return s(:str, "") unless str
408
- # catch s(:str, "", other_str)
409
- if str.size == 3 and str[1] == "" and str[0] == :str
410
- return str[2]
411
- # catch s(:str, "content", more_content)
412
- elsif str[0] == :str && str.size > 3
413
- str[0] = :dstr
414
- str
415
- # top level evstr should be a dstr
416
- elsif str[0] == :evstr
417
- s(:dstr, "", str)
418
- else
419
394
  str
420
395
  end
421
- end
422
396
 
423
- def new_regexp reg, ending
424
- return s(:lit, //) unless reg
425
- case reg[0]
426
- when :str
427
- s(:lit, Regexp.new(reg[1], ending))
428
- when :evstr
429
- res = s(:dregx, "", reg)
430
- when :dstr
431
- reg[0] = :dregx
432
- reg
397
+ def new_str(str)
398
+ # cover empty strings
399
+ return s(:str, "") unless str
400
+ # catch s(:str, "", other_str)
401
+ if str.size == 3 and str[1] == "" and str[0] == :str
402
+ return str[2]
403
+ # catch s(:str, "content", more_content)
404
+ elsif str[0] == :str && str.size > 3
405
+ str[0] = :dstr
406
+ str
407
+ # top level evstr should be a dstr
408
+ elsif str[0] == :evstr
409
+ s(:dstr, "", str)
410
+ else
411
+ str
412
+ end
413
+ end
414
+
415
+ def new_regexp(reg, ending)
416
+ return s(:lit, //) unless reg
417
+ case reg[0]
418
+ when :str
419
+ s(:lit, Regexp.new(reg[1], ending))
420
+ when :evstr
421
+ res = s(:dregx, "", reg)
422
+ when :dstr
423
+ reg[0] = :dregx
424
+ reg
425
+ end
433
426
  end
434
- end
435
427
 
436
- def str_append str, str2
437
- return str2 unless str
438
- return str unless str2
428
+ def str_append(str, str2)
429
+ return str2 unless str
430
+ return str unless str2
439
431
 
440
- if str.first == :evstr
441
- str = s(:dstr, "", str)
442
- elsif str.first == :str
443
- str = s(:dstr, str[1])
444
- else
445
- #puts str.first
432
+ if str.first == :evstr
433
+ str = s(:dstr, "", str)
434
+ elsif str.first == :str
435
+ str = s(:dstr, str[1])
436
+ else
437
+ #puts str.first
438
+ end
439
+ str << str2
440
+ str
446
441
  end
447
- str << str2
448
- str
449
- end
450
442
 
451
- def next_token
452
- t = get_next_token
453
- # puts "returning token #{t.inspect}"
454
- t
455
- end
443
+ def cond_push(n)
444
+ @cond = (@cond << 1) | (n & 1)
445
+ end
456
446
 
457
- def cond_push(n)
458
- @cond = (@cond << 1) | (n & 1)
459
- end
447
+ def cond_pop
448
+ @cond = @cond >> 1
449
+ end
460
450
 
461
- def cond_pop
462
- @cond = @cond >> 1
463
- end
451
+ def cond_lexpop
452
+ @cond = (@cond >> 1) | (@cond & 1)
453
+ end
464
454
 
465
- def cond_lexpop
466
- @cond = (@cond >> 1) | (@cond & 1)
467
- end
455
+ def cond?
456
+ (@cond & 1) != 0
457
+ end
468
458
 
469
- def cond?
470
- (@cond & 1) != 0
471
- end
459
+ def cmdarg_push(n)
460
+ @cmdarg = (@cmdarg << 1) | (n & 1)
461
+ end
472
462
 
473
- def cmdarg_push(n)
474
- @cmdarg = (@cmdarg << 1) | (n & 1)
475
- end
463
+ def cmdarg_pop
464
+ @cmdarg = @cmdarg >> 1
465
+ end
476
466
 
477
- def cmdarg_pop
478
- @cmdarg = @cmdarg >> 1
479
- end
467
+ def cmdarg_lexpop
468
+ @cmdarg = (@cmdarg >> 1) | (@cmdarg & 1)
469
+ end
480
470
 
481
- def cmdarg_lexpop
482
- @cmdarg = (@cmdarg >> 1) | (@cmdarg & 1)
483
- end
471
+ def cmdarg?
472
+ (@cmdarg & 1) != 0
473
+ end
484
474
 
485
- def cmdarg?
486
- (@cmdarg & 1) != 0
487
- end
475
+ def next_string_token
476
+ # str_parse, scanner = current_string_parse, @scanner
477
+ str_parse = @string_parse
478
+ scanner = @scanner
479
+ space = false
488
480
 
489
- def next_string_token
490
- # str_parse, scanner = current_string_parse, @scanner
491
- str_parse = @string_parse
492
- scanner = @scanner
493
- space = false
481
+ # everything bar single quote and lower case bare wrds can interpolate
482
+ interpolate = str_parse[:interpolate]
494
483
 
495
- # everything bar single quote and lower case bare wrds can interpolate
496
- interpolate = str_parse[:interpolate]
484
+ words = ['w', 'W'].include? str_parse[:beg]
497
485
 
498
- words = ['w', 'W'].include? str_parse[:beg]
486
+ space = true if ['w', 'W'].include?(str_parse[:beg]) and scanner.scan(/\s+/)
499
487
 
500
- space = true if ['w', 'W'].include?(str_parse[:beg]) and scanner.scan(/\s+/)
488
+ # if not end of string, so we must be parsing contents
489
+ str_buffer = []
501
490
 
502
- # if not end of string, so we must be parsing contents
503
- str_buffer = []
491
+ # see if we can read end of string/xstring/regecp markers
492
+ # if scanner.scan /#{str_parse[:end]}/
493
+ if scanner.scan Regexp.new(Regexp.escape(str_parse[:end]))
494
+ if words && !str_parse[:done_last_space]#&& space
495
+ str_parse[:done_last_space] = true
496
+ scanner.pos -= 1
497
+ return :SPACE, ' '
498
+ end
499
+ @string_parse = nil
504
500
 
505
- # see if we can read end of string/xstring/regecp markers
506
- # if scanner.scan /#{str_parse[:end]}/
507
- if scanner.scan Regexp.new(Regexp.escape(str_parse[:end]))
508
- if words && !str_parse[:done_last_space]#&& space
509
- str_parse[:done_last_space] = true
510
- scanner.pos -= 1
511
- return :SPACE, ' '
512
- end
513
- @string_parse = nil
501
+ # return :SPACE, ' ' if words && space
514
502
 
515
- # return :SPACE, ' ' if words && space
503
+ # if in %Q{, we should balance { with } before ending.
504
+ if str_parse[:balance]
505
+ if str_parse[:nesting] == 0
506
+ @lex_state = :expr_end
507
+ return :STRING_END, scanner.matched
508
+ else
509
+ #puts "nesting not 0!"
510
+ #puts str_parse[:nesting]
511
+ str_buffer << scanner.matched
512
+ str_parse[:nesting] -= 1
513
+ # make sure we carry on string parse (its set to nil above)
514
+ @string_parse = str_parse
515
+ end
516
516
 
517
- # if in %Q{, we should balance { with } before ending.
518
- if str_parse[:balance]
519
- if str_parse[:nesting] == 0
517
+ elsif ['"', "'"].include? str_parse[:beg]
520
518
  @lex_state = :expr_end
521
519
  return :STRING_END, scanner.matched
522
- else
523
- #puts "nesting not 0!"
524
- #puts str_parse[:nesting]
525
- str_buffer << scanner.matched
526
- str_parse[:nesting] -= 1
527
- # make sure we carry on string parse (its set to nil above)
528
- @string_parse = str_parse
529
- end
530
-
531
- elsif ['"', "'"].include? str_parse[:beg]
532
- @lex_state = :expr_end
533
- return :STRING_END, scanner.matched
534
520
 
535
- elsif str_parse[:beg] == '`'
536
- @lex_state = :expr_end
537
- return :STRING_END, scanner.matched
521
+ elsif str_parse[:beg] == '`'
522
+ @lex_state = :expr_end
523
+ return :STRING_END, scanner.matched
538
524
 
539
- elsif str_parse[:beg] == '/'
540
- result = scanner.scan(/\w+/)
541
- @lex_state = :expr_end
542
- return :REGEXP_END, result
525
+ elsif str_parse[:beg] == '/'
526
+ result = scanner.scan(/\w+/)
527
+ @lex_state = :expr_end
528
+ return :REGEXP_END, result
543
529
 
544
- else
545
- @lex_state = :expr_end
546
- return :STRING_END, scanner.matched
530
+ else
531
+ @lex_state = :expr_end
532
+ return :STRING_END, scanner.matched
533
+ end
547
534
  end
548
- end
549
535
 
550
- return :SPACE, ' ' if space
536
+ return :SPACE, ' ' if space
551
537
 
552
- if str_parse[:balance] and scanner.scan Regexp.new(Regexp.escape(str_parse[:beg]))
553
- #puts "matced beg balance!"
554
- str_buffer << scanner.matched
555
- str_parse[:nesting] += 1
556
- elsif scanner.check(/#[@$]/)
557
- scanner.scan(/#/)
558
- if interpolate
559
- return :STRING_DVAR, scanner.matched
560
- else
538
+ if str_parse[:balance] and scanner.scan Regexp.new(Regexp.escape(str_parse[:beg]))
539
+ #puts "matced beg balance!"
561
540
  str_buffer << scanner.matched
562
- end
541
+ str_parse[:nesting] += 1
542
+ elsif scanner.check(/#[@$]/)
543
+ scanner.scan(/#/)
544
+ if interpolate
545
+ return :STRING_DVAR, scanner.matched
546
+ else
547
+ str_buffer << scanner.matched
548
+ end
563
549
 
564
- elsif scanner.scan(/#\{/)
565
- if interpolate
566
- # we are into ruby code, so stop parsing content (for now)
567
- return :STRING_DBEG, scanner.matched
568
- else
569
- str_buffer << scanner.matched
550
+ elsif scanner.scan(/#\{/)
551
+ if interpolate
552
+ # we are into ruby code, so stop parsing content (for now)
553
+ return :STRING_DBEG, scanner.matched
554
+ else
555
+ str_buffer << scanner.matched
556
+ end
557
+
558
+ # causes error, so we will just collect it later on with other text
559
+ elsif scanner.scan(/\#/)
560
+ str_buffer << '#'
570
561
  end
571
562
 
572
- # causes error, so we will just collect it later on with other text
573
- elsif scanner.scan(/\#/)
574
- str_buffer << '#'
563
+ add_string_content str_buffer, str_parse
564
+ complete_str = str_buffer.join ''
565
+ @line += complete_str.count("\n")
566
+ return :STRING_CONTENT, complete_str
575
567
  end
576
568
 
577
- add_string_content str_buffer, str_parse
578
- complete_str = str_buffer.join ''
579
- @line += complete_str.count("\n")
580
- return :STRING_CONTENT, complete_str
581
- end
569
+ def add_string_content(str_buffer, str_parse)
570
+ scanner = @scanner
571
+ # regexp for end of string/regexp
572
+ # end_str_re = /#{str_parse[:end]}/
573
+ end_str_re = Regexp.new(Regexp.escape(str_parse[:end]))
574
+ # can be interpolate
575
+ interpolate = str_parse[:interpolate]
576
+
577
+ words = ['W', 'w'].include? str_parse[:beg]
578
+
579
+ until scanner.eos?
580
+ c = nil
581
+ handled = true
582
+
583
+ if scanner.check end_str_re
584
+ # eos
585
+ # if its just balancing, add it ass normal content..
586
+ if str_parse[:balance] && (str_parse[:nesting] != 0)
587
+ # we only checked above, so actually scan it
588
+ scanner.scan end_str_re
589
+ c = scanner.matched
590
+ str_parse[:nesting] -= 1
591
+ else
592
+ # not balancing, so break (eos!)
593
+ break
594
+ end
582
595
 
583
- def add_string_content(str_buffer, str_parse)
584
- scanner = @scanner
585
- # regexp for end of string/regexp
586
- # end_str_re = /#{str_parse[:end]}/
587
- end_str_re = Regexp.new(Regexp.escape(str_parse[:end]))
588
- # can be interpolate
589
- interpolate = str_parse[:interpolate]
590
-
591
- words = ['W', 'w'].include? str_parse[:beg]
592
-
593
- until scanner.eos?
594
- c = nil
595
- handled = true
596
-
597
- if scanner.check end_str_re
598
- # eos
599
- # if its just balancing, add it ass normal content..
600
- if str_parse[:balance] && (str_parse[:nesting] != 0)
601
- # we only checked above, so actually scan it
602
- scanner.scan end_str_re
596
+ elsif str_parse[:balance] and scanner.scan Regexp.new(Regexp.escape(str_parse[:beg]))
597
+ str_parse[:nesting] += 1
603
598
  c = scanner.matched
604
- str_parse[:nesting] -= 1
605
- else
606
- # not balancing, so break (eos!)
607
- break
608
- end
609
-
610
- elsif str_parse[:balance] and scanner.scan Regexp.new(Regexp.escape(str_parse[:beg]))
611
- str_parse[:nesting] += 1
612
- c = scanner.matched
613
599
 
614
- elsif words && scanner.scan(/\s/)
615
- scanner.pos -= 1
616
- break
600
+ elsif words && scanner.scan(/\s/)
601
+ scanner.pos -= 1
602
+ break
617
603
 
618
- elsif interpolate && scanner.check(/#(?=[\$\@\{])/)
619
- break
604
+ elsif interpolate && scanner.check(/#(?=[\$\@\{])/)
605
+ break
620
606
 
621
- #elsif scanner.scan(/\\\\/)
622
- #c = scanner.matched
607
+ #elsif scanner.scan(/\\\\/)
608
+ #c = scanner.matched
623
609
 
624
- elsif scanner.scan(/\\/)
625
- if str_parse[:regexp]
626
- if scanner.scan(/(.)/)
627
- c = "\\" + scanner.matched
610
+ elsif scanner.scan(/\\/)
611
+ if str_parse[:regexp]
612
+ if scanner.scan(/(.)/)
613
+ c = "\\" + scanner.matched
614
+ end
615
+ else
616
+ c = if scanner.scan(/n/)
617
+ "\n"
618
+ elsif scanner.scan(/r/)
619
+ "\r"
620
+ elsif scanner.scan(/\n/)
621
+ "\n"
622
+ else
623
+ # escaped char doesnt need escaping, so just return it
624
+ scanner.scan(/./)
625
+ scanner.matched
626
+ end
628
627
  end
629
628
  else
630
- c = if scanner.scan(/n/)
631
- "\n"
632
- elsif scanner.scan(/r/)
633
- "\r"
634
- elsif scanner.scan(/\n/)
635
- "\n"
636
- else
637
- # escaped char doesnt need escaping, so just return it
638
- scanner.scan(/./)
639
- scanner.matched
640
- end
629
+ handled = false
641
630
  end
642
- else
643
- handled = false
644
- end
645
631
 
646
- unless handled
647
- reg = if words
648
- Regexp.new("[^#{Regexp.escape str_parse[:end]}\#\0\n\ \\\\]+|.")
649
- elsif str_parse[:balance]
650
- #puts "using tis regexp"
651
- Regexp.new("[^#{Regexp.escape str_parse[:end]}#{Regexp.escape str_parse[:beg]}\#\0\\\\]+|.")
652
- else
653
- Regexp.new("[^#{Regexp.escape str_parse[:end]}\#\0\\\\]+|.")
654
- end
632
+ unless handled
633
+ reg = if words
634
+ Regexp.new("[^#{Regexp.escape str_parse[:end]}\#\0\n\ \\\\]+|.")
635
+ elsif str_parse[:balance]
636
+ #puts "using tis regexp"
637
+ Regexp.new("[^#{Regexp.escape str_parse[:end]}#{Regexp.escape str_parse[:beg]}\#\0\\\\]+|.")
638
+ else
639
+ Regexp.new("[^#{Regexp.escape str_parse[:end]}\#\0\\\\]+|.")
640
+ end
641
+
642
+ scanner.scan reg
643
+ #puts scanner.matched
644
+ c = scanner.matched
645
+ end
655
646
 
656
- scanner.scan reg
657
- #puts scanner.matched
658
- c = scanner.matched
647
+ c ||= scanner.matched
648
+ str_buffer << c
659
649
  end
660
650
 
661
- c ||= scanner.matched
662
- str_buffer << c
651
+ raise "reached EOF while in string" if scanner.eos?
663
652
  end
664
653
 
665
- raise "reached EOF while in string" if scanner.eos?
666
- end
654
+ def next_token
655
+ # if we are trying to parse a string, then delegate to that
656
+ return next_string_token if @string_parse
667
657
 
668
- def get_next_token
669
- if @string_parse
670
- return next_string_token
671
- end
658
+ # scanner, space_seen, cmd_start, c = @scanner, false, false, ''
659
+ scanner = @scanner
660
+ space_seen = false
661
+ cmd_start = false
662
+ c = ''
672
663
 
673
- # scanner, space_seen, cmd_start, c = @scanner, false, false, ''
674
- scanner = @scanner
675
- space_seen = false
676
- cmd_start = false
677
- c = ''
678
-
679
- while true
680
- if scanner.scan(/\ |\t|\r/)
681
- space_seen = true
682
- next
683
-
684
- elsif scanner.scan(/(\n|#)/)
685
- c = scanner.matched
686
- if c == '#' then scanner.scan(/(.*)/) else @line += 1; end
687
-
688
- scanner.scan(/(\n+)/)
689
- @line += scanner.matched.length if scanner.matched
690
-
691
- next if [:expr_beg, :expr_dot].include? @lex_state
692
-
693
- cmd_start = true
694
- @lex_state = :expr_beg
695
- return '\\n', '\\n'
696
-
697
- elsif scanner.scan(/\;/)
698
- @lex_state = :expr_beg
699
- return ';', ';'
700
-
701
- elsif scanner.scan(/\"/)
702
- @string_parse = { :beg => '"', :end => '"', :interpolate => true }
703
- return :STRING_BEG, scanner.matched
704
-
705
- elsif scanner.scan(/\'/)
706
- @string_parse = { :beg => "'", :end => "'" }
707
- return :STRING_BEG, scanner.matched
708
-
709
- elsif scanner.scan(/\`/)
710
- @string_parse = { :beg => "`", :end => "`", :interpolate => true }
711
- return :XSTRING_BEG, scanner.matched
712
-
713
- elsif scanner.scan(/\%W/)
714
- start_word = scanner.scan(/./)
715
- end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
716
- @string_parse = { :beg => 'W', :end => end_word, :interpolate => true }
717
- scanner.scan(/\s*/)
718
- return :WORDS_BEG, scanner.matched
719
-
720
- elsif scanner.scan(/\%w/)
721
- start_word = scanner.scan(/./)
722
- end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
723
- @string_parse = { :beg => 'w', :end => end_word }
724
- scanner.scan(/\s*/)
725
- return :AWORDS_BEG, scanner.matched
726
-
727
- elsif scanner.scan(/\%[Qq]/)
728
- interpolate = scanner.matched.end_with? 'Q'
729
- start_word = scanner.scan(/./)
730
- end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
731
- @string_parse = { :beg => start_word, :end => end_word, :balance => true, :nesting => 0, :interpolate => interpolate }
732
- return :STRING_BEG, scanner.matched
733
-
734
- elsif scanner.scan(/\%x/)
735
- start_word = scanner.scan(/./)
736
- end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
737
- @string_parse = { :beg => start_word, :end => end_word, :balance => true, :nesting => 0, :interpolate => true }
738
- return :XSTRING_BEG, scanner.matched
739
-
740
- elsif scanner.scan(/\//)
741
- if [:expr_beg, :expr_mid].include? @lex_state
742
- @string_parse = { :beg => '/', :end => '/', :interpolate => true, :regexp => true }
743
- return :REGEXP_BEG, scanner.matched
744
- elsif scanner.scan(/\=/)
745
- @lex_state = :expr_beg
746
- return :OP_ASGN, '/'
747
- elsif @lex_state == :expr_fname
748
- @lex_state = :expr_end
749
- end
664
+ while true
665
+ if scanner.scan(/\ |\t|\r/)
666
+ space_seen = true
667
+ next
668
+
669
+ elsif scanner.scan(/(\n|#)/)
670
+ c = scanner.matched
671
+ if c == '#' then scanner.scan(/(.*)/) else @line += 1; end
672
+
673
+ scanner.scan(/(\n+)/)
674
+ @line += scanner.matched.length if scanner.matched
750
675
 
751
- return '/', '/'
676
+ next if [:expr_beg, :expr_dot].include? @lex_state
752
677
 
753
- elsif scanner.scan(/\%/)
754
- if scanner.scan(/\=/)
678
+ cmd_start = true
755
679
  @lex_state = :expr_beg
756
- return :OP_ASGN, '%'
757
- end
758
- @lex_state = @lex_state == :expr_fname ? :expr_end : :expr_beg
759
- return '%', '%'
760
-
761
- elsif scanner.scan(/\(/)
762
- result = scanner.matched
763
- if [:expr_beg, :expr_mid].include? @lex_state
764
- result = :PAREN_BEG
765
- elsif space_seen
766
- result = '('
767
- end
680
+ return '\\n', '\\n'
768
681
 
769
- @lex_state = :expr_beg
770
- cond_push 0
771
- cmdarg_push 0
682
+ elsif scanner.scan(/\;/)
683
+ @lex_state = :expr_beg
684
+ return ';', ';'
772
685
 
773
- return result, scanner.matched
686
+ elsif scanner.scan(/\"/)
687
+ @string_parse = { :beg => '"', :end => '"', :interpolate => true }
688
+ return :STRING_BEG, scanner.matched
774
689
 
775
- elsif scanner.scan(/\)/)
776
- cond_lexpop
777
- cmdarg_lexpop
778
- @lex_state = :expr_end
779
- return ')', scanner.matched
690
+ elsif scanner.scan(/\'/)
691
+ @string_parse = { :beg => "'", :end => "'" }
692
+ return :STRING_BEG, scanner.matched
693
+
694
+ elsif scanner.scan(/\`/)
695
+ @string_parse = { :beg => "`", :end => "`", :interpolate => true }
696
+ return :XSTRING_BEG, scanner.matched
697
+
698
+ elsif scanner.scan(/\%W/)
699
+ start_word = scanner.scan(/./)
700
+ end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
701
+ @string_parse = { :beg => 'W', :end => end_word, :interpolate => true }
702
+ scanner.scan(/\s*/)
703
+ return :WORDS_BEG, scanner.matched
704
+
705
+ elsif scanner.scan(/\%w/)
706
+ start_word = scanner.scan(/./)
707
+ end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
708
+ @string_parse = { :beg => 'w', :end => end_word }
709
+ scanner.scan(/\s*/)
710
+ return :AWORDS_BEG, scanner.matched
711
+
712
+ elsif scanner.scan(/\%[Qq]/)
713
+ interpolate = scanner.matched.end_with? 'Q'
714
+ start_word = scanner.scan(/./)
715
+ end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
716
+ @string_parse = { :beg => start_word, :end => end_word, :balance => true, :nesting => 0, :interpolate => interpolate }
717
+ return :STRING_BEG, scanner.matched
718
+
719
+ elsif scanner.scan(/\%x/)
720
+ start_word = scanner.scan(/./)
721
+ end_word = { '(' => ')', '[' => ']', '{' => '}' }[start_word] || start_word
722
+ @string_parse = { :beg => start_word, :end => end_word, :balance => true, :nesting => 0, :interpolate => true }
723
+ return :XSTRING_BEG, scanner.matched
724
+
725
+ elsif scanner.scan(/\//)
726
+ if [:expr_beg, :expr_mid].include? @lex_state
727
+ @string_parse = { :beg => '/', :end => '/', :interpolate => true, :regexp => true }
728
+ return :REGEXP_BEG, scanner.matched
729
+ elsif scanner.scan(/\=/)
730
+ @lex_state = :expr_beg
731
+ return :OP_ASGN, '/'
732
+ elsif @lex_state == :expr_fname
733
+ @lex_state = :expr_end
734
+ end
780
735
 
781
- elsif scanner.scan(/\[/)
782
- result = scanner.matched
736
+ return '/', '/'
783
737
 
784
- if [:expr_fname, :expr_dot].include? @lex_state
785
- @lex_state = :expr_arg
786
- if scanner.scan(/\]=/)
787
- return '[]=', '[]='
788
- elsif scanner.scan(/\]/)
789
- return '[]', '[]'
790
- else
791
- raise "Unexpected '[' token"
738
+ elsif scanner.scan(/\%/)
739
+ if scanner.scan(/\=/)
740
+ @lex_state = :expr_beg
741
+ return :OP_ASGN, '%'
792
742
  end
793
- elsif [:expr_beg, :expr_mid].include?(@lex_state) || space_seen
794
- @lex_state = :expr_beg
795
- cond_push 0
796
- cmdarg_push 0
797
- return '[', scanner.matched
798
- else
743
+ @lex_state = @lex_state == :expr_fname ? :expr_end : :expr_beg
744
+ return '%', '%'
745
+
746
+ elsif scanner.scan(/\(/)
747
+ result = scanner.matched
748
+ if [:expr_beg, :expr_mid].include? @lex_state
749
+ result = :PAREN_BEG
750
+ elsif space_seen
751
+ result = '('
752
+ end
753
+
799
754
  @lex_state = :expr_beg
800
755
  cond_push 0
801
756
  cmdarg_push 0
802
- return '[@', scanner.matched
803
- end
804
-
805
- elsif scanner.scan(/\]/)
806
- cond_lexpop
807
- cmdarg_lexpop
808
- @lex_state = :expr_end
809
- return ']', scanner.matched
810
757
 
811
- elsif scanner.scan(/\}/)
812
- cond_lexpop
813
- cmdarg_lexpop
814
- @lex_state = :expr_end
758
+ return result, scanner.matched
815
759
 
816
- return '}', scanner.matched
760
+ elsif scanner.scan(/\)/)
761
+ cond_lexpop
762
+ cmdarg_lexpop
763
+ @lex_state = :expr_end
764
+ return ')', scanner.matched
765
+
766
+ elsif scanner.scan(/\[/)
767
+ result = scanner.matched
768
+
769
+ if [:expr_fname, :expr_dot].include? @lex_state
770
+ @lex_state = :expr_arg
771
+ if scanner.scan(/\]=/)
772
+ return '[]=', '[]='
773
+ elsif scanner.scan(/\]/)
774
+ return '[]', '[]'
775
+ else
776
+ raise "Unexpected '[' token"
777
+ end
778
+ elsif [:expr_beg, :expr_mid].include?(@lex_state) || space_seen
779
+ @lex_state = :expr_beg
780
+ cond_push 0
781
+ cmdarg_push 0
782
+ return '[', scanner.matched
783
+ else
784
+ @lex_state = :expr_beg
785
+ cond_push 0
786
+ cmdarg_push 0
787
+ return '[@', scanner.matched
788
+ end
817
789
 
818
- elsif scanner.scan(/\.\.\./)
819
- @lex_state = :expr_beg
820
- return '...', scanner.matched
790
+ elsif scanner.scan(/\]/)
791
+ cond_lexpop
792
+ cmdarg_lexpop
793
+ @lex_state = :expr_end
794
+ return ']', scanner.matched
821
795
 
822
- elsif scanner.scan(/\.\./)
823
- @lex_state = :expr_beg
824
- return '..', scanner.matched
796
+ elsif scanner.scan(/\}/)
797
+ cond_lexpop
798
+ cmdarg_lexpop
799
+ @lex_state = :expr_end
825
800
 
826
- elsif scanner.scan(/\./)
827
- @lex_state = :expr_dot unless @lex_state == :expr_fname
828
- return '.', scanner.matched
801
+ return '}', scanner.matched
829
802
 
830
- elsif scanner.scan(/\*\*\=/)
831
- @lex_state = :expr_beg
832
- return :OP_ASGN, '**'
803
+ elsif scanner.scan(/\.\.\./)
804
+ @lex_state = :expr_beg
805
+ return '...', scanner.matched
833
806
 
834
- elsif scanner.scan(/\*\*/)
835
- return '**', '**'
807
+ elsif scanner.scan(/\.\./)
808
+ @lex_state = :expr_beg
809
+ return '..', scanner.matched
836
810
 
837
- elsif scanner.scan(/\*\=/)
838
- @lex_state = :expr_beg
839
- return :OP_ASGN, '*'
811
+ elsif scanner.scan(/\./)
812
+ @lex_state = :expr_dot unless @lex_state == :expr_fname
813
+ return '.', scanner.matched
840
814
 
841
- elsif scanner.scan(/\*/)
842
- result = scanner.matched
843
- if @lex_state == :expr_fname
844
- @lex_state = :expr_end
845
- return '*', result
846
- elsif space_seen && scanner.check(/\S/)
847
- @lex_state = :expr_beg
848
- return :SPLAT, result
849
- elsif [:expr_beg, :expr_mid].include? @lex_state
850
- @lex_state = :expr_beg
851
- return :SPLAT, result
852
- else
815
+ elsif scanner.scan(/\*\*\=/)
853
816
  @lex_state = :expr_beg
854
- return '*', result
855
- end
817
+ return :OP_ASGN, '**'
856
818
 
857
- elsif scanner.scan(/\:\:/)
858
- if [:expr_beg, :expr_mid, :expr_class].include? @lex_state
859
- @lex_state = :expr_beg
860
- return '::@', scanner.matched
861
- end
819
+ elsif scanner.scan(/\*\*/)
820
+ return '**', '**'
862
821
 
863
- @lex_state = :expr_dot
864
- return '::', scanner.matched
822
+ elsif scanner.scan(/\*\=/)
823
+ @lex_state = :expr_beg
824
+ return :OP_ASGN, '*'
865
825
 
866
- elsif scanner.scan(/\:/)
867
- if [:expr_end, :expr_endarg].include?(@lex_state) || scanner.check(/\s/)
868
- unless scanner.check(/\w/)
826
+ elsif scanner.scan(/\*/)
827
+ result = scanner.matched
828
+ if @lex_state == :expr_fname
829
+ @lex_state = :expr_end
830
+ return '*', result
831
+ elsif space_seen && scanner.check(/\S/)
832
+ @lex_state = :expr_beg
833
+ return :SPLAT, result
834
+ elsif [:expr_beg, :expr_mid].include? @lex_state
835
+ @lex_state = :expr_beg
836
+ return :SPLAT, result
837
+ else
869
838
  @lex_state = :expr_beg
870
- return ':', ':'
839
+ return '*', result
871
840
  end
872
841
 
873
- @lex_state = :expr_fname
874
- return :SYMBOL_BEG, ':'
875
- end
842
+ elsif scanner.scan(/\:\:/)
843
+ if [:expr_beg, :expr_mid, :expr_class].include? @lex_state
844
+ @lex_state = :expr_beg
845
+ return '::@', scanner.matched
846
+ end
876
847
 
877
- if scanner.scan(/\'/)
878
- @string_parse = { :beg => "'", :end => "'" }
879
- elsif scanner.scan(/\"/)
880
- @string_parse = { :beg => '"', :end => '"', :interpolate => true }
881
- end
848
+ @lex_state = :expr_dot
849
+ return '::', scanner.matched
882
850
 
883
- @lex_state = :expr_fname
884
- return :SYMBOL_BEG, ':'
851
+ elsif scanner.scan(/\:/)
852
+ if [:expr_end, :expr_endarg].include?(@lex_state) || scanner.check(/\s/)
853
+ unless scanner.check(/\w/)
854
+ @lex_state = :expr_beg
855
+ return ':', ':'
856
+ end
885
857
 
886
- elsif scanner.check(/\|/)
887
- if scanner.scan(/\|\|\=/)
888
- @lex_state = :expr_beg
889
- return :OP_ASGN, '||'
890
- elsif scanner.scan(/\|\|/)
891
- @lex_state = :expr_beg
892
- return '||', '||'
893
- elsif scanner.scan(/\|\=/)
894
- @lex_state = :expr_beg
895
- return :OP_ASGN, '|'
896
- elsif scanner.scan(/\|/)
897
- if @lex_state == :expr_fname
898
- @lex_state = :expr_end
899
- return '|', scanner.matched
900
- else
901
- @lex_state = :expr_beg
902
- return '|', scanner.matched
858
+ @lex_state = :expr_fname
859
+ return :SYMBOL_BEG, ':'
903
860
  end
904
- end
905
861
 
906
- elsif scanner.scan(/\^\=/)
907
- @lex_state = :exor_beg
908
- return :OP_ASGN, '^'
909
- elsif scanner.scan(/\^/)
910
- if @lex_state == :expr_fname
911
- @lex_state = :expr_end
912
- return '^', scanner.matched
913
- end
862
+ if scanner.scan(/\'/)
863
+ @string_parse = { :beg => "'", :end => "'" }
864
+ elsif scanner.scan(/\"/)
865
+ @string_parse = { :beg => '"', :end => '"', :interpolate => true }
866
+ end
914
867
 
915
- @lex_state = :expr_beg
916
- return '^', scanner.matched
868
+ @lex_state = :expr_fname
869
+ return :SYMBOL_BEG, ':'
917
870
 
918
- elsif scanner.check(/\&/)
919
- if scanner.scan(/\&\&\=/)
920
- @lex_state = :expr_beg
921
- return :OP_ASGN, '&&'
922
- elsif scanner.scan(/\&\&/)
923
- @lex_state = :expr_beg
924
- return '&&', scanner.matched
925
- elsif scanner.scan(/\&\=/)
926
- @lex_state = :expr_beg
927
- return :OP_ASGN, '&'
928
- elsif scanner.scan(/\&/)
929
- if space_seen && !scanner.check(/\s/) && (@lex_state == :expr_cmdarg || @lex_state == :expr_arg)
930
- return '&@', '&'
931
- elsif [:expr_beg, :expr_mid].include? @lex_state
932
- return '&@', '&'
933
- else
934
- return '&', '&'
871
+ elsif scanner.check(/\|/)
872
+ if scanner.scan(/\|\|\=/)
873
+ @lex_state = :expr_beg
874
+ return :OP_ASGN, '||'
875
+ elsif scanner.scan(/\|\|/)
876
+ @lex_state = :expr_beg
877
+ return '||', '||'
878
+ elsif scanner.scan(/\|\=/)
879
+ @lex_state = :expr_beg
880
+ return :OP_ASGN, '|'
881
+ elsif scanner.scan(/\|/)
882
+ if @lex_state == :expr_fname
883
+ @lex_state = :expr_end
884
+ return '|', scanner.matched
885
+ else
886
+ @lex_state = :expr_beg
887
+ return '|', scanner.matched
888
+ end
935
889
  end
936
- end
937
890
 
938
- elsif scanner.check(/\</)
939
- if scanner.scan(/\<\<\=/)
940
- @lex_state = :expr_beg
941
- return :OP_ASGN, '<<'
942
- elsif scanner.scan(/\<\</)
891
+ elsif scanner.scan(/\^\=/)
892
+ @lex_state = :exor_beg
893
+ return :OP_ASGN, '^'
894
+ elsif scanner.scan(/\^/)
943
895
  if @lex_state == :expr_fname
944
896
  @lex_state = :expr_end
945
- return '<<', '<<'
946
- elsif ![:expr_end, :expr_dot, :expr_endarg, :expr_class].include?(@lex_state) && space_seen
947
- if scanner.scan(/(-?)(\w+)/)
948
- heredoc = scanner[2]
949
- # for now just scrap rest of line + skip down one line for
950
- # string content
951
- scanner.scan(/.*\n/)
952
- @string_parse = { :beg => heredoc, :end => heredoc, :interpolate => true }
953
- return :STRING_BEG, heredoc
954
- end
955
- @lex_state = :expr_beg
956
- return '<<', '<<'
897
+ return '^', scanner.matched
957
898
  end
899
+
958
900
  @lex_state = :expr_beg
959
- return '<<', '<<'
960
- elsif scanner.scan(/\<\=\>/)
961
- if @lex_state == :expr_fname
962
- @lex_state = :expr_end
963
- else
901
+ return '^', scanner.matched
902
+
903
+ elsif scanner.check(/\&/)
904
+ if scanner.scan(/\&\&\=/)
964
905
  @lex_state = :expr_beg
965
- end
966
- return '<=>', '<=>'
967
- elsif scanner.scan(/\<\=/)
968
- if @lex_state == :expr_fname
969
- @lex_state = :expr_end
970
- else
906
+ return :OP_ASGN, '&&'
907
+ elsif scanner.scan(/\&\&/)
971
908
  @lex_state = :expr_beg
972
- end
973
- return '<=', '<='
974
- elsif scanner.scan(/\</)
975
- if @lex_state == :expr_fname
976
- @lex_state = :expr_end
977
- else
909
+ return '&&', scanner.matched
910
+ elsif scanner.scan(/\&\=/)
978
911
  @lex_state = :expr_beg
912
+ return :OP_ASGN, '&'
913
+ elsif scanner.scan(/\&/)
914
+ if space_seen && !scanner.check(/\s/) && (@lex_state == :expr_cmdarg || @lex_state == :expr_arg)
915
+ return '&@', '&'
916
+ elsif [:expr_beg, :expr_mid].include? @lex_state
917
+ return '&@', '&'
918
+ else
919
+ return '&', '&'
920
+ end
979
921
  end
980
- return '<', '<'
981
- end
982
922
 
983
- elsif scanner.check(/\>/)
984
- if scanner.scan(/\>\>\=/)
985
- return :OP_ASGN, '>>'
986
- elsif scanner.scan(/\>\>/)
987
- return '>>', '>>'
988
- elsif scanner.scan(/\>\=/)
989
- if @lex_state == :expr_fname
990
- @lex_state = :expr_end
991
- else
923
+ elsif scanner.check(/\</)
924
+ if scanner.scan(/\<\<\=/)
992
925
  @lex_state = :expr_beg
993
- end
994
- return '>=', scanner.matched
995
- elsif scanner.scan(/\>/)
996
- if @lex_state == :expr_fname
997
- @lex_state = :expr_end
998
- else
926
+ return :OP_ASGN, '<<'
927
+ elsif scanner.scan(/\<\</)
928
+ if @lex_state == :expr_fname
929
+ @lex_state = :expr_end
930
+ return '<<', '<<'
931
+ elsif ![:expr_end, :expr_dot, :expr_endarg, :expr_class].include?(@lex_state) && space_seen
932
+ if scanner.scan(/(-?)(\w+)/)
933
+ heredoc = scanner[2]
934
+ # for now just scrap rest of line + skip down one line for
935
+ # string content
936
+ scanner.scan(/.*\n/)
937
+ @string_parse = { :beg => heredoc, :end => heredoc, :interpolate => true }
938
+ return :STRING_BEG, heredoc
939
+ end
940
+ @lex_state = :expr_beg
941
+ return '<<', '<<'
942
+ end
999
943
  @lex_state = :expr_beg
944
+ return '<<', '<<'
945
+ elsif scanner.scan(/\<\=\>/)
946
+ if @lex_state == :expr_fname
947
+ @lex_state = :expr_end
948
+ else
949
+ @lex_state = :expr_beg
950
+ end
951
+ return '<=>', '<=>'
952
+ elsif scanner.scan(/\<\=/)
953
+ if @lex_state == :expr_fname
954
+ @lex_state = :expr_end
955
+ else
956
+ @lex_state = :expr_beg
957
+ end
958
+ return '<=', '<='
959
+ elsif scanner.scan(/\</)
960
+ if @lex_state == :expr_fname
961
+ @lex_state = :expr_end
962
+ else
963
+ @lex_state = :expr_beg
964
+ end
965
+ return '<', '<'
1000
966
  end
1001
- return '>', '>'
1002
- end
1003
967
 
1004
- elsif scanner.scan(/->/)
1005
- @lex_state = :expr_arg
1006
- @start_of_lambda = true
1007
- return [:LAMBDA, scanner.matched]
968
+ elsif scanner.check(/\>/)
969
+ if scanner.scan(/\>\>\=/)
970
+ return :OP_ASGN, '>>'
971
+ elsif scanner.scan(/\>\>/)
972
+ return '>>', '>>'
973
+ elsif scanner.scan(/\>\=/)
974
+ if @lex_state == :expr_fname
975
+ @lex_state = :expr_end
976
+ else
977
+ @lex_state = :expr_beg
978
+ end
979
+ return '>=', scanner.matched
980
+ elsif scanner.scan(/\>/)
981
+ if @lex_state == :expr_fname
982
+ @lex_state = :expr_end
983
+ else
984
+ @lex_state = :expr_beg
985
+ end
986
+ return '>', '>'
987
+ end
1008
988
 
1009
- elsif scanner.scan(/[+-]/)
1010
- result = scanner.matched
1011
- sign = result + '@'
989
+ elsif scanner.scan(/->/)
990
+ @lex_state = :expr_arg
991
+ @start_of_lambda = true
992
+ return [:LAMBDA, scanner.matched]
1012
993
 
1013
- if @lex_state == :expr_beg || @lex_state == :expr_mid
1014
- @lex_state = :expr_mid
1015
- return [sign, sign]
1016
- elsif @lex_state == :expr_fname
1017
- @lex_state = :expr_end
1018
- return [:IDENTIFIER, result + scanner.matched] if scanner.scan(/@/)
1019
- return [result, result]
1020
- end
994
+ elsif scanner.scan(/[+-]/)
995
+ result = scanner.matched
996
+ sign = result + '@'
997
+
998
+ if @lex_state == :expr_beg || @lex_state == :expr_mid
999
+ @lex_state = :expr_mid
1000
+ return [sign, sign]
1001
+ elsif @lex_state == :expr_fname
1002
+ @lex_state = :expr_end
1003
+ return [:IDENTIFIER, result + scanner.matched] if scanner.scan(/@/)
1004
+ return [result, result]
1005
+ end
1006
+
1007
+ if scanner.scan(/\=/)
1008
+ @lex_state = :expr_beg
1009
+ return [:OP_ASGN, result]
1010
+ end
1021
1011
 
1022
- if scanner.scan(/\=/)
1023
1012
  @lex_state = :expr_beg
1024
- return [:OP_ASGN, result]
1025
- end
1013
+ return [result, result]
1026
1014
 
1027
- @lex_state = :expr_beg
1028
- return [result, result]
1015
+ elsif scanner.scan(/\?/)
1016
+ # FIXME: :expr_arg shouldnt really be here
1017
+ if [:expr_end, :expr_endarg, :expr_arg].include?(@lex_state)
1018
+ @lex_state = :expr_beg
1019
+ return '?', scanner.matched
1020
+ end
1029
1021
 
1030
- elsif scanner.scan(/\?/)
1031
- # FIXME: :expr_arg shouldnt really be here
1032
- if [:expr_end, :expr_endarg, :expr_arg].include?(@lex_state)
1022
+ #if scanner.scan(/\\/)
1023
+ #c = if scanner.scan(/n/)
1024
+ #"\n"
1025
+ #else
1026
+ #scanner.scan(/./)
1027
+ #scanner.matched
1028
+ #end
1029
+ #else
1030
+ #c = scanner.scan(/./)
1031
+ #end
1032
+
1033
+ #@lex_state = :expr_end
1034
+ #return :STRING, c
1033
1035
  @lex_state = :expr_beg
1034
1036
  return '?', scanner.matched
1035
- end
1036
1037
 
1037
- #if scanner.scan(/\\/)
1038
- #c = if scanner.scan(/n/)
1039
- #"\n"
1040
- #else
1041
- #scanner.scan(/./)
1042
- #scanner.matched
1043
- #end
1044
- #else
1045
- #c = scanner.scan(/./)
1046
- #end
1047
-
1048
- #@lex_state = :expr_end
1049
- #return :STRING, c
1050
- @lex_state = :expr_beg
1051
- return '?', scanner.matched
1052
-
1053
- elsif scanner.scan(/\=\=\=/)
1054
- if @lex_state == :expr_fname
1055
- @lex_state = :expr_end
1038
+ elsif scanner.scan(/\=\=\=/)
1039
+ if @lex_state == :expr_fname
1040
+ @lex_state = :expr_end
1041
+ return '===', '==='
1042
+ end
1043
+ @lex_state = :expr_beg
1056
1044
  return '===', '==='
1057
- end
1058
- @lex_state = :expr_beg
1059
- return '===', '==='
1060
1045
 
1061
- elsif scanner.scan(/\=\=/)
1062
- if @lex_state == :expr_fname
1063
- @lex_state = :expr_end
1046
+ elsif scanner.scan(/\=\=/)
1047
+ if @lex_state == :expr_fname
1048
+ @lex_state = :expr_end
1049
+ return '==', '=='
1050
+ end
1051
+ @lex_state = :expr_beg
1064
1052
  return '==', '=='
1065
- end
1066
- @lex_state = :expr_beg
1067
- return '==', '=='
1068
1053
 
1069
- elsif scanner.scan(/\=\~/)
1070
- if @lex_state == :expr_fname
1071
- @lex_state = :expr_end
1054
+ elsif scanner.scan(/\=\~/)
1055
+ if @lex_state == :expr_fname
1056
+ @lex_state = :expr_end
1057
+ return '=~', '=~'
1058
+ end
1059
+ @lex_state = :expr_beg
1072
1060
  return '=~', '=~'
1073
- end
1074
- @lex_state = :expr_beg
1075
- return '=~', '=~'
1076
1061
 
1077
- elsif scanner.scan(/\=\>/)
1078
- @lex_state = :expr_beg
1079
- return '=>', '=>'
1062
+ elsif scanner.scan(/\=\>/)
1063
+ @lex_state = :expr_beg
1064
+ return '=>', '=>'
1080
1065
 
1081
- elsif scanner.scan(/\=/)
1082
- @lex_state = :expr_beg
1083
- return '=', '='
1066
+ elsif scanner.scan(/\=/)
1067
+ @lex_state = :expr_beg
1068
+ return '=', '='
1084
1069
 
1085
- elsif scanner.scan(/\!\=/)
1086
- if @lex_state == :expr_fname
1087
- @lex_state == :expr_end
1070
+ elsif scanner.scan(/\!\=/)
1071
+ if @lex_state == :expr_fname
1072
+ @lex_state == :expr_end
1073
+ return '!=', '!='
1074
+ end
1075
+ @lex_state = :expr_beg
1088
1076
  return '!=', '!='
1089
- end
1090
- @lex_state = :expr_beg
1091
- return '!=', '!='
1092
1077
 
1093
- elsif scanner.scan(/\!\~/)
1094
- @lex_state = :expr_beg
1095
- return '!~', '!~'
1078
+ elsif scanner.scan(/\!\~/)
1079
+ @lex_state = :expr_beg
1080
+ return '!~', '!~'
1096
1081
 
1097
- elsif scanner.scan(/\!/)
1098
- if @lex_state == :expr_fname
1099
- @lex_state = :expr_end
1082
+ elsif scanner.scan(/\!/)
1083
+ if @lex_state == :expr_fname
1084
+ @lex_state = :expr_end
1085
+ return '!', '!'
1086
+ end
1087
+ @lex_state = :expr_beg
1100
1088
  return '!', '!'
1101
- end
1102
- @lex_state = :expr_beg
1103
- return '!', '!'
1104
1089
 
1105
- elsif scanner.scan(/\~/)
1106
- if @lex_state == :expr_fname
1107
- @lex_state = :expr_end
1090
+ elsif scanner.scan(/\~/)
1091
+ if @lex_state == :expr_fname
1092
+ @lex_state = :expr_end
1093
+ return '~', '~'
1094
+ end
1095
+ @lex_state = :expr_beg
1108
1096
  return '~', '~'
1109
- end
1110
- @lex_state = :expr_beg
1111
- return '~', '~'
1112
-
1113
- elsif scanner.scan(/\$[\+\'\`\&!@\"~*$?\/\\:;=.,<>_]/)
1114
- @lex_state = :expr_end
1115
- return :GVAR, scanner.matched
1116
1097
 
1117
- elsif scanner.scan(/\$\w+/)
1118
- @lex_state = :expr_end
1119
- return :GVAR, scanner.matched
1098
+ elsif scanner.scan(/\$[\+\'\`\&!@\"~*$?\/\\:;=.,<>_]/)
1099
+ @lex_state = :expr_end
1100
+ return :GVAR, scanner.matched
1120
1101
 
1121
- elsif scanner.scan(/\@\@\w*/)
1122
- @lex_state = :expr_end
1123
- return :CVAR, scanner.matched
1102
+ elsif scanner.scan(/\$\w+/)
1103
+ @lex_state = :expr_end
1104
+ return :GVAR, scanner.matched
1124
1105
 
1125
- elsif scanner.scan(/\@\w*/)
1126
- @lex_state = :expr_end
1127
- return :IVAR, scanner.matched
1106
+ elsif scanner.scan(/\@\@\w*/)
1107
+ @lex_state = :expr_end
1108
+ return :CVAR, scanner.matched
1128
1109
 
1129
- elsif scanner.scan(/\,/)
1130
- @lex_state = :expr_beg
1131
- return ',', scanner.matched
1110
+ elsif scanner.scan(/\@\w*/)
1111
+ @lex_state = :expr_end
1112
+ return :IVAR, scanner.matched
1132
1113
 
1133
- elsif scanner.scan(/\{/)
1134
- if @start_of_lambda
1135
- @start_of_lambda = false
1114
+ elsif scanner.scan(/\,/)
1136
1115
  @lex_state = :expr_beg
1137
- return [:LAMBEG, scanner.matched]
1116
+ return ',', scanner.matched
1138
1117
 
1139
- elsif [:expr_end, :expr_arg, :expr_cmdarg].include? @lex_state
1140
- result = :LCURLY
1141
- elsif @lex_state == :expr_endarg
1142
- result = :LBRACE_ARG
1143
- else
1144
- result = '{'
1145
- end
1118
+ elsif scanner.scan(/\{/)
1119
+ if @start_of_lambda
1120
+ @start_of_lambda = false
1121
+ @lex_state = :expr_beg
1122
+ return [:LAMBEG, scanner.matched]
1146
1123
 
1147
- @lex_state = :expr_beg
1148
- cond_push 0
1149
- cmdarg_push 0
1150
- return result, scanner.matched
1151
-
1152
- elsif scanner.check(/[0-9]/)
1153
- @lex_state = :expr_end
1154
- if scanner.scan(/[\d_]+\.[\d_]+\b/)
1155
- return [:FLOAT, scanner.matched.gsub(/_/, '').to_f]
1156
- elsif scanner.scan(/[\d_]+\b/)
1157
- return [:INTEGER, scanner.matched.gsub(/_/, '').to_i]
1158
- elsif scanner.scan(/0(x|X)(\d|[a-f]|[A-F])+/)
1159
- return [:INTEGER, scanner.matched.to_i]
1160
- else
1161
- raise "Lexing error on numeric type: `#{scanner.peek 5}`"
1162
- end
1124
+ elsif [:expr_end, :expr_arg, :expr_cmdarg].include? @lex_state
1125
+ result = :LCURLY
1126
+ elsif @lex_state == :expr_endarg
1127
+ result = :LBRACE_ARG
1128
+ else
1129
+ result = '{'
1130
+ end
1163
1131
 
1164
- elsif scanner.scan(/(\w)+[\?\!]?/)
1165
- matched = scanner.matched
1166
- if scanner.peek(2) != '::' && scanner.scan(/:/)
1167
1132
  @lex_state = :expr_beg
1168
- return :LABEL, "#{matched}"
1169
- end
1133
+ cond_push 0
1134
+ cmdarg_push 0
1135
+ return result, scanner.matched
1170
1136
 
1171
- case matched
1172
- when 'class'
1173
- if @lex_state == :expr_dot
1174
- @lex_state = :expr_end
1175
- return :IDENTIFIER, matched
1137
+ elsif scanner.check(/[0-9]/)
1138
+ @lex_state = :expr_end
1139
+ if scanner.scan(/[\d_]+\.[\d_]+\b/)
1140
+ return [:FLOAT, scanner.matched.gsub(/_/, '').to_f]
1141
+ elsif scanner.scan(/[\d_]+\b/)
1142
+ return [:INTEGER, scanner.matched.gsub(/_/, '').to_i]
1143
+ elsif scanner.scan(/0(x|X)(\d|[a-f]|[A-F])+/)
1144
+ return [:INTEGER, scanner.matched.to_i]
1145
+ else
1146
+ raise "Lexing error on numeric type: `#{scanner.peek 5}`"
1176
1147
  end
1177
- @lex_state = :expr_class
1178
- return :CLASS, matched
1179
-
1180
- when 'module'
1181
- return :IDENTIFIER, matched if @lex_state == :expr_dot
1182
- @lex_state = :expr_class
1183
- return :MODULE, matched
1184
1148
 
1185
- when 'defined?'
1186
- return :IDENTIFIER, matched if @lex_state == :expr_dot
1187
- @lex_state = :expr_arg
1188
- return :DEFINED, 'defined?'
1189
-
1190
- when 'def'
1191
- @lex_state = :expr_fname
1192
- @scope_line = @line
1193
- return :DEF, matched
1149
+ elsif scanner.scan(/(\w)+[\?\!]?/)
1150
+ matched = scanner.matched
1151
+ if scanner.peek(2) != '::' && scanner.scan(/:/)
1152
+ @lex_state = :expr_beg
1153
+ return :LABEL, "#{matched}"
1154
+ end
1194
1155
 
1195
- when 'undef'
1196
- @lex_state = :expr_fname
1197
- return :UNDEF, matched
1156
+ case matched
1157
+ when 'class'
1158
+ if @lex_state == :expr_dot
1159
+ @lex_state = :expr_end
1160
+ return :IDENTIFIER, matched
1161
+ end
1162
+ @lex_state = :expr_class
1163
+ return :CLASS, matched
1164
+
1165
+ when 'module'
1166
+ return :IDENTIFIER, matched if @lex_state == :expr_dot
1167
+ @lex_state = :expr_class
1168
+ return :MODULE, matched
1169
+
1170
+ when 'defined?'
1171
+ return :IDENTIFIER, matched if @lex_state == :expr_dot
1172
+ @lex_state = :expr_arg
1173
+ return :DEFINED, 'defined?'
1174
+
1175
+ when 'def'
1176
+ @lex_state = :expr_fname
1177
+ @scope_line = @line
1178
+ return :DEF, matched
1179
+
1180
+ when 'undef'
1181
+ @lex_state = :expr_fname
1182
+ return :UNDEF, matched
1183
+
1184
+ when 'end'
1185
+ if [:expr_dot, :expr_fname].include? @lex_state
1186
+ @lex_state = :expr_end
1187
+ return :IDENTIFIER, matched
1188
+ end
1198
1189
 
1199
- when 'end'
1200
- if [:expr_dot, :expr_fname].include? @lex_state
1201
1190
  @lex_state = :expr_end
1202
- return :IDENTIFIER, matched
1203
- end
1204
-
1205
- @lex_state = :expr_end
1206
- return :END, matched
1191
+ return :END, matched
1192
+
1193
+ when 'do'
1194
+ #puts cond?
1195
+ #puts cmdarg?
1196
+ #nputs @lex_state
1197
+ if @start_of_lambda
1198
+ @start_of_lambda = false
1199
+ @lex_state = :expr_beg
1200
+ return [:DO_LAMBDA, scanner.matched]
1201
+ elsif cond?
1202
+ @lex_state = :expr_beg
1203
+ return :DO_COND, matched
1204
+ elsif cmdarg? && @lex_state != :expr_cmdarg
1205
+ @lex_state = :expr_beg
1206
+ return :DO_BLOCK, matched
1207
+ elsif @lex_state == :expr_endarg
1208
+ return :DO_BLOCK, matched
1209
+ else
1210
+ @lex_state = :expr_beg
1211
+ return :DO, matched
1212
+ end
1207
1213
 
1208
- when 'do'
1209
- #puts cond?
1210
- #puts cmdarg?
1211
- #nputs @lex_state
1212
- if @start_of_lambda
1213
- @start_of_lambda = false
1214
- @lex_state = :expr_beg
1215
- return [:DO_LAMBDA, scanner.matched]
1216
- elsif cond?
1217
- @lex_state = :expr_beg
1218
- return :DO_COND, matched
1219
- elsif cmdarg? && @lex_state != :expr_cmdarg
1220
- @lex_state = :expr_beg
1221
- return :DO_BLOCK, matched
1222
- elsif @lex_state == :expr_endarg
1223
- return :DO_BLOCK, matched
1224
- else
1214
+ when 'if'
1215
+ return :IF, matched if @lex_state == :expr_beg
1225
1216
  @lex_state = :expr_beg
1226
- return :DO, matched
1227
- end
1217
+ return :IF_MOD, matched
1228
1218
 
1229
- when 'if'
1230
- return :IF, matched if @lex_state == :expr_beg
1231
- @lex_state = :expr_beg
1232
- return :IF_MOD, matched
1219
+ when 'unless'
1220
+ return :UNLESS, matched if @lex_state == :expr_beg
1221
+ @lex_state = :expr_beg
1222
+ return :UNLESS_MOD, matched
1233
1223
 
1234
- when 'unless'
1235
- return :UNLESS, matched if @lex_state == :expr_beg
1236
- @lex_state = :expr_beg
1237
- return :UNLESS_MOD, matched
1224
+ when 'else'
1225
+ return :ELSE, matched
1238
1226
 
1239
- when 'else'
1240
- return :ELSE, matched
1227
+ when 'elsif'
1228
+ return :ELSIF, matched
1241
1229
 
1242
- when 'elsif'
1243
- return :ELSIF, matched
1230
+ when 'self'
1231
+ @lex_state = :expr_end unless @lex_state == :expr_fname
1232
+ return :SELF, matched
1244
1233
 
1245
- when 'self'
1246
- @lex_state = :expr_end unless @lex_state == :expr_fname
1247
- return :SELF, matched
1234
+ when 'true'
1235
+ @lex_state = :expr_end
1236
+ return :TRUE, matched
1248
1237
 
1249
- when 'true'
1250
- @lex_state = :expr_end
1251
- return :TRUE, matched
1238
+ when 'false'
1239
+ @lex_state = :expr_end
1240
+ return :FALSE, matched
1252
1241
 
1253
- when 'false'
1254
- @lex_state = :expr_end
1255
- return :FALSE, matched
1242
+ when 'nil'
1243
+ @lex_state = :expr_end
1244
+ return :NIL, matched
1256
1245
 
1257
- when 'nil'
1258
- @lex_state = :expr_end
1259
- return :NIL, matched
1246
+ when '__LINE__'
1247
+ @lex_state = :expr_end
1248
+ return :LINE, @line.to_s
1260
1249
 
1261
- when '__LINE__'
1262
- @lex_state = :expr_end
1263
- return :LINE, @line.to_s
1250
+ when '__FILE__'
1251
+ @lex_state = :expr_end
1252
+ return :FILE, matched
1264
1253
 
1265
- when '__FILE__'
1266
- @lex_state = :expr_end
1267
- return :FILE, matched
1254
+ when 'begin'
1255
+ if [:expr_dot, :expr_fname].include? @lex_state
1256
+ @lex_state = :expr_end
1257
+ return :IDENTIFIER, matched
1258
+ end
1259
+ @lex_state = :expr_beg
1260
+ return :BEGIN, matched
1268
1261
 
1269
- when 'begin'
1270
- if [:expr_dot, :expr_fname].include? @lex_state
1271
- @lex_state = :expr_end
1272
- return :IDENTIFIER, matched
1273
- end
1274
- @lex_state = :expr_beg
1275
- return :BEGIN, matched
1262
+ when 'rescue'
1263
+ return :IDENTIFIER, matched if [:expr_dot, :expr_fname].include? @lex_state
1264
+ return :RESCUE, matched if @lex_state == :expr_beg
1265
+ @lex_state = :expr_beg
1266
+ return :RESCUE_MOD, matched
1276
1267
 
1277
- when 'rescue'
1278
- return :IDENTIFIER, matched if [:expr_dot, :expr_fname].include? @lex_state
1279
- return :RESCUE, matched if @lex_state == :expr_beg
1280
- @lex_state = :expr_beg
1281
- return :RESCUE_MOD, matched
1268
+ when 'ensure'
1269
+ @lex_state = :expr_beg
1270
+ return :ENSURE, matched
1282
1271
 
1283
- when 'ensure'
1284
- @lex_state = :expr_beg
1285
- return :ENSURE, matched
1272
+ when 'case'
1273
+ @lex_state = :expr_beg
1274
+ return :CASE, matched
1286
1275
 
1287
- when 'case'
1288
- @lex_state = :expr_beg
1289
- return :CASE, matched
1276
+ when 'when'
1277
+ @lex_state = :expr_beg
1278
+ return :WHEN, matched
1290
1279
 
1291
- when 'when'
1292
- @lex_state = :expr_beg
1293
- return :WHEN, matched
1280
+ when 'or'
1281
+ @lex_state = :expr_beg
1282
+ return :OR, matched
1294
1283
 
1295
- when 'or'
1296
- @lex_state = :expr_beg
1297
- return :OR, matched
1284
+ when 'and'
1285
+ @lex_state = :expr_beg
1286
+ return :AND, matched
1298
1287
 
1299
- when 'and'
1300
- @lex_state = :expr_beg
1301
- return :AND, matched
1288
+ when 'not'
1289
+ @lex_state = :expr_beg
1290
+ return :NOT, matched
1302
1291
 
1303
- when 'not'
1304
- @lex_state = :expr_beg
1305
- return :NOT, matched
1292
+ when 'return'
1293
+ @lex_state = :expr_mid
1294
+ return :RETURN, matched
1306
1295
 
1307
- when 'return'
1308
- @lex_state = :expr_mid
1309
- return :RETURN, matched
1296
+ when 'next'
1297
+ if @lex_state == :expr_dot || @lex_state == :expr_fname
1298
+ @lex_state = :expr_end
1299
+ return :IDENTIFIER, matched
1300
+ end
1310
1301
 
1311
- when 'next'
1312
- if @lex_state == :expr_dot || @lex_state == :expr_fname
1313
- @lex_state = :expr_end
1314
- return :IDENTIFIER, matched
1315
- end
1302
+ @lex_state = :expr_mid
1303
+ return :NEXT, matched
1316
1304
 
1317
- @lex_state = :expr_mid
1318
- return :NEXT, matched
1305
+ when 'redo'
1306
+ if @lex_state == :expr_dot || @lex_state == :expr_fname
1307
+ @lex_state = :expr_end
1308
+ return :IDENTIFIER, matched
1309
+ end
1319
1310
 
1320
- when 'redo'
1321
- if @lex_state == :expr_dot || @lex_state == :expr_fname
1322
- @lex_state = :expr_end
1323
- return :IDENTIFIER, matched
1324
- end
1311
+ @lex_state = :expr_mid
1312
+ return :REDO, matched
1325
1313
 
1326
- @lex_state = :expr_mid
1327
- return :REDO, matched
1314
+ when 'break'
1315
+ @lex_state = :expr_mid
1316
+ return :BREAK, matched
1328
1317
 
1329
- when 'break'
1330
- @lex_state = :expr_mid
1331
- return :BREAK, matched
1318
+ when 'super'
1319
+ @lex_state = :expr_arg
1320
+ return :SUPER, matched
1332
1321
 
1333
- when 'super'
1334
- @lex_state = :expr_arg
1335
- return :SUPER, matched
1322
+ when 'then'
1323
+ return :THEN, matched
1336
1324
 
1337
- when 'then'
1338
- return :THEN, matched
1325
+ when 'while'
1326
+ return :WHILE, matched if @lex_state == :expr_beg
1327
+ @lex_state = :expr_beg
1328
+ return :WHILE_MOD, matched
1339
1329
 
1340
- when 'while'
1341
- return :WHILE, matched if @lex_state == :expr_beg
1342
- @lex_state = :expr_beg
1343
- return :WHILE_MOD, matched
1330
+ when 'until'
1331
+ return :UNTIL, matched if @lex_state == :expr_beg
1332
+ @lex_state = :expr_beg
1333
+ return :UNTIL_MOD, matched
1344
1334
 
1345
- when 'until'
1346
- return :UNTIL, matched if @lex_state == :expr_beg
1347
- @lex_state = :expr_beg
1348
- return :UNTIL_MOD, matched
1335
+ when 'yield'
1336
+ @lex_state = :expr_arg
1337
+ return :YIELD, matched
1349
1338
 
1350
- when 'yield'
1351
- @lex_state = :expr_arg
1352
- return :YIELD, matched
1339
+ when 'alias'
1340
+ @lex_state = :expr_fname
1341
+ return :ALIAS, matched
1342
+ end
1353
1343
 
1354
- when 'alias'
1355
- @lex_state = :expr_fname
1356
- return :ALIAS, matched
1357
- end
1344
+ matched = matched
1345
+ if scanner.peek(2) != '::' && scanner.scan(/\:/)
1346
+ return :LABEL, matched
1347
+ end
1358
1348
 
1359
- matched = matched
1360
- if scanner.peek(2) != '::' && scanner.scan(/\:/)
1361
- return :LABEL, matched
1362
- end
1349
+ if @lex_state == :expr_fname
1350
+ if scanner.scan(/\=/)
1351
+ @lex_state = :expr_end
1352
+ return :IDENTIFIER, matched + scanner.matched
1353
+ end
1354
+ end
1363
1355
 
1364
- if @lex_state == :expr_fname
1365
- if scanner.scan(/\=/)
1356
+ if [:expr_beg, :expr_dot, :expr_mid, :expr_arg, :expr_cmdarg].include? @lex_state
1357
+ # old:
1358
+ #@lex_state = :expr_cmdarg
1359
+ # new:
1360
+ @lex_state = cmd_start ? :expr_cmdarg : :expr_arg
1361
+ else
1366
1362
  @lex_state = :expr_end
1367
- return :IDENTIFIER, matched + scanner.matched
1368
1363
  end
1369
- end
1370
1364
 
1371
- if [:expr_beg, :expr_dot, :expr_mid, :expr_arg, :expr_cmdarg].include? @lex_state
1372
- # old:
1373
- #@lex_state = :expr_cmdarg
1374
- # new:
1375
- @lex_state = cmd_start ? :expr_cmdarg : :expr_arg
1376
- else
1377
- @lex_state = :expr_end
1378
- end
1365
+ return [matched =~ /[A-Z]/ ? :CONSTANT : :IDENTIFIER, matched]
1379
1366
 
1380
- return [matched =~ /[A-Z]/ ? :CONSTANT : :IDENTIFIER, matched]
1367
+ end
1368
+ return [false, false] if scanner.eos?
1381
1369
 
1370
+ raise OpalParseError, "Unexpected content in parsing stream `#{scanner.peek 5}`"
1382
1371
  end
1383
- return [false, false] if scanner.eos?
1384
-
1385
- raise OpalParseError, "Unexpected content in parsing stream `#{scanner.peek 5}`"
1386
1372
  end
1387
1373
  end
1388
1374
  end
1389
- end