YkLib 0.1.0
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.
- checksums.yaml +7 -0
- data/.gitignore +11 -0
- data/.rspec +3 -0
- data/.travis.yml +6 -0
- data/CODE_OF_CONDUCT.md +74 -0
- data/Gemfile +7 -0
- data/Gemfile.lock +34 -0
- data/LICENSE.txt +21 -0
- data/README.md +44 -0
- data/Rakefile +6 -0
- data/YkLib.gemspec +29 -0
- data/bin/console +14 -0
- data/bin/setup +8 -0
- data/lib/YkLib/Yk/__advance__.rb +151 -0
- data/lib/YkLib/Yk/__defun__.rb +44 -0
- data/lib/YkLib/Yk/__hook__.rb +244 -0
- data/lib/YkLib/Yk/__minmax__.rb +123 -0
- data/lib/YkLib/Yk/__stdlog.rb +329 -0
- data/lib/YkLib/Yk/adhocLiterals/email.rb +119 -0
- data/lib/YkLib/Yk/adhocLiterals/path.rb +402 -0
- data/lib/YkLib/Yk/adhocLiterals/tag.rb +19 -0
- data/lib/YkLib/Yk/adhocLiterals/url.rb +36 -0
- data/lib/YkLib/Yk/adhocLiterals.rb +199 -0
- data/lib/YkLib/Yk/auto_escseq.rb +5 -0
- data/lib/YkLib/Yk/auto_pstore.rb +179 -0
- data/lib/YkLib/Yk/bsearch.rb +120 -0
- data/lib/YkLib/Yk/clambda.rb +309 -0
- data/lib/YkLib/Yk/confLine.rb +423 -0
- data/lib/YkLib/Yk/create_tty_width_available.rb +24 -0
- data/lib/YkLib/Yk/crypt.rb +26 -0
- data/lib/YkLib/Yk/debug2 +1 -0
- data/lib/YkLib/Yk/debug2.rb +473 -0
- data/lib/YkLib/Yk/debugout.rb +139 -0
- data/lib/YkLib/Yk/email_tz.rb +533 -0
- data/lib/YkLib/Yk/enum_expect.rb +170 -0
- data/lib/YkLib/Yk/errlog.rb +5 -0
- data/lib/YkLib/Yk/escseq.rb +59 -0
- data/lib/YkLib/Yk/eval_alt.rb +281 -0
- data/lib/YkLib/Yk/expector.rb +93 -0
- data/lib/YkLib/Yk/fetch.rb +556 -0
- data/lib/YkLib/Yk/fetch_old.rb +290 -0
- data/lib/YkLib/Yk/fib.rb +158 -0
- data/lib/YkLib/Yk/file_aux.rb +843 -0
- data/lib/YkLib/Yk/file_aux2.rb +919 -0
- data/lib/YkLib/Yk/file_aux_old.rb +160 -0
- data/lib/YkLib/Yk/filemod.rb +19 -0
- data/lib/YkLib/Yk/force_escseq.rb +3 -0
- data/lib/YkLib/Yk/generator__.rb +144 -0
- data/lib/YkLib/Yk/generator__.rb.org +139 -0
- data/lib/YkLib/Yk/indenter/argless_case.rb +46 -0
- data/lib/YkLib/Yk/indenter/each_token.rb +671 -0
- data/lib/YkLib/Yk/indenter/free_case.rb +313 -0
- data/lib/YkLib/Yk/indenter/if_less.rb +53 -0
- data/lib/YkLib/Yk/indenter/independent_ensure.rb +23 -0
- data/lib/YkLib/Yk/indenter/independent_rescue.rb +23 -0
- data/lib/YkLib/Yk/indenter/operand_circumflex.rb +0 -0
- data/lib/YkLib/Yk/indenter/operand_period.rb +16 -0
- data/lib/YkLib/Yk/indenter/parenless_and.rb +37 -0
- data/lib/YkLib/Yk/indenter/post_test.rb +48 -0
- data/lib/YkLib/Yk/indenter/token.rb +1525 -0
- data/lib/YkLib/Yk/indenter.rb +1382 -0
- data/lib/YkLib/Yk/inot.rb +265 -0
- data/lib/YkLib/Yk/intf.rb +815 -0
- data/lib/YkLib/Yk/io_aux.rb +1332 -0
- data/lib/YkLib/Yk/ioctl.rb +60 -0
- data/lib/YkLib/Yk/ipcc.rb +87 -0
- data/lib/YkLib/Yk/ipcountry.rb +207 -0
- data/lib/YkLib/Yk/ipv4adr.rb +318 -0
- data/lib/YkLib/Yk/localmail.rb +276 -0
- data/lib/YkLib/Yk/method_chain.rb +359 -0
- data/lib/YkLib/Yk/misc_tz.rb +1716 -0
- data/lib/YkLib/Yk/missing_method.rb +50 -0
- data/lib/YkLib/Yk/mojiConv.rb +257 -0
- data/lib/YkLib/Yk/nostdlog.rb +4 -0
- data/lib/YkLib/Yk/on_marshal.rb +20 -0
- data/lib/YkLib/Yk/overrider.rb +47 -0
- data/lib/YkLib/Yk/path.rb +293 -0
- data/lib/YkLib/Yk/path_aux.rb +883 -0
- data/lib/YkLib/Yk/path_aux_alt.rb +0 -0
- data/lib/YkLib/Yk/path_rep.rb +1267 -0
- data/lib/YkLib/Yk/pg_setup.rb +917 -0
- data/lib/YkLib/Yk/procinfo.rb +314 -0
- data/lib/YkLib/Yk/proclist.rb +492 -0
- data/lib/YkLib/Yk/property.rb +863 -0
- data/lib/YkLib/Yk/ranger.rb +606 -0
- data/lib/YkLib/Yk/resolv_tz.rb +88 -0
- data/lib/YkLib/Yk/rlprompt.rb +73 -0
- data/lib/YkLib/Yk/rootexec.rb +48 -0
- data/lib/YkLib/Yk/rpm-packageproxy.rb +784 -0
- data/lib/YkLib/Yk/rpm-packageproxy2.rb +1430 -0
- data/lib/YkLib/Yk/rwhen.rb +21 -0
- data/lib/YkLib/Yk/selector.rb +124 -0
- data/lib/YkLib/Yk/set.rb +170 -0
- data/lib/YkLib/Yk/shellquote.rb +300 -0
- data/lib/YkLib/Yk/sio.rb +1001 -0
- data/lib/YkLib/Yk/sio0.rb +835 -0
- data/lib/YkLib/Yk/sio_aux.rb +1524 -0
- data/lib/YkLib/Yk/sio_inot.rb +86 -0
- data/lib/YkLib/Yk/sock_aux.rb +42 -0
- data/lib/YkLib/Yk/spipe.rb +843 -0
- data/lib/YkLib/Yk/sql_table.rb +565 -0
- data/lib/YkLib/Yk/stdlog.rb +4 -0
- data/lib/YkLib/Yk/syscommand.rb +173 -0
- data/lib/YkLib/Yk/sysinit.rb +75 -0
- data/lib/YkLib/Yk/ttyFontWidth.rb +46113 -0
- data/lib/YkLib/Yk/tty_char.dump +0 -0
- data/lib/YkLib/Yk/tty_char.rb +47 -0
- data/lib/YkLib/Yk/tty_char_create.rb +437031 -0
- data/lib/YkLib/Yk/tty_char_static.rb +437016 -0
- data/lib/YkLib/Yk/tty_rewrite.rb +142 -0
- data/lib/YkLib/Yk/tty_str.rb +461 -0
- data/lib/YkLib/Yk/tty_width.dat.rb +114 -0
- data/lib/YkLib/Yk/tty_width.rb +180 -0
- data/lib/YkLib/Yk/tty_width_available +569 -0
- data/lib/YkLib/Yk/tty_width_list +0 -0
- data/lib/YkLib/Yk/tty_width_list.linux +280 -0
- data/lib/YkLib/Yk/tty_width_list.windows +324 -0
- data/lib/YkLib/Yk/tz_tty +0 -0
- data/lib/YkLib/Yk/tz_tty.rb +0 -0
- data/lib/YkLib/Yk/uprepos.rb +94 -0
- data/lib/YkLib/Yk/userinfo.rb +91 -0
- data/lib/YkLib/Yk/with.rb +109 -0
- data/lib/YkLib/version.rb +3 -0
- data/lib/YkLib.rb +6 -0
- metadata +170 -0
|
@@ -0,0 +1,1382 @@
|
|
|
1
|
+
|
|
2
|
+
require 'binding_of_caller'
|
|
3
|
+
|
|
4
|
+
require 'Yk/indenter/token'
|
|
5
|
+
|
|
6
|
+
require 'Yk/eval_alt'
|
|
7
|
+
require 'Yk/adhocLiterals'
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class << self
|
|
11
|
+
alias __org_using__ using
|
|
12
|
+
def using *args
|
|
13
|
+
GrammerExt::using *args
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
module Kernel
|
|
18
|
+
p 123123
|
|
19
|
+
alias __org_require__ require
|
|
20
|
+
module_function
|
|
21
|
+
def require *args #second load
|
|
22
|
+
begin
|
|
23
|
+
p :require, args
|
|
24
|
+
ret = __org_require__ *args
|
|
25
|
+
p :require_finish, args
|
|
26
|
+
ret
|
|
27
|
+
rescue GrammerExt::RequireFinished
|
|
28
|
+
p "finish", args
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
def __get_args__ *args, **opts
|
|
32
|
+
args, opts
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
class BasicObject
|
|
37
|
+
def __translate__ expr, f, lno, bl = nil, :mode = :eval, this = nil
|
|
38
|
+
....
|
|
39
|
+
expr
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
class GrammerExt
|
|
44
|
+
class RequireFinished < Exception
|
|
45
|
+
end
|
|
46
|
+
UsedFrom = {}
|
|
47
|
+
def self.usedFrom grammers, f, lno, b
|
|
48
|
+
lns = IO.readlines f
|
|
49
|
+
p [:exec, f, lno + 1]
|
|
50
|
+
p lns[lno + 1 .. lno + 10].join
|
|
51
|
+
mod.doEval(lns[lno + 1 .. -1].join, f, lno + 2)
|
|
52
|
+
p [:exec_finish, f, lno + 1]
|
|
53
|
+
if !(binding.of_caller(2) rescue nil)
|
|
54
|
+
p :exitting
|
|
55
|
+
exit 0
|
|
56
|
+
else
|
|
57
|
+
raise RequireFinished.new("finished")
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
def self.using *args, **opts
|
|
61
|
+
args.flatten!
|
|
62
|
+
p :bbbbbbbbbbbb
|
|
63
|
+
b = binding.of_caller(2)
|
|
64
|
+
mods = []
|
|
65
|
+
if !UsedFrom.key? f
|
|
66
|
+
grammers = []
|
|
67
|
+
f, lno = b.source_location
|
|
68
|
+
p [f, lno, :require]
|
|
69
|
+
f = File.expand_path(f)
|
|
70
|
+
lno = lno.to_i - 1
|
|
71
|
+
hasGram = false
|
|
72
|
+
args.each do |arg|
|
|
73
|
+
if arg.is_a?(GrammerExt)
|
|
74
|
+
if !(UsedFrom[f] ||= {}).key? arg
|
|
75
|
+
UsedFrom[f][arg] ||= true
|
|
76
|
+
grammers.push arg
|
|
77
|
+
end
|
|
78
|
+
else
|
|
79
|
+
mods.push arg
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
if !grammers.empty?
|
|
83
|
+
lns = IO.readlines f
|
|
84
|
+
p [:exec, f, lno + 1]
|
|
85
|
+
p lns[lno + 1 .. lno + 10].join
|
|
86
|
+
doEval(mods, grammers, opts, lns[lno + 1, -1], f, lno, b)
|
|
87
|
+
if !(binding.of_caller(3) rescue nil)
|
|
88
|
+
p :exitting
|
|
89
|
+
exit 0
|
|
90
|
+
else
|
|
91
|
+
raise RequireFinished.new("finished")
|
|
92
|
+
end
|
|
93
|
+
end
|
|
94
|
+
else
|
|
95
|
+
args.each do |arg|
|
|
96
|
+
if arg.is_a?(GrammerExt)
|
|
97
|
+
if !(UsedFrom[f] ||= {}).key? arg
|
|
98
|
+
raise ArgumentError.new("already used grammer, #{arg.inspect}")
|
|
99
|
+
end
|
|
100
|
+
else
|
|
101
|
+
mods.push arg
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
end
|
|
105
|
+
mods.each do |m|
|
|
106
|
+
b.eval("__org_using__ ::ObjectSpace.__id2ref(#{m.__id__})")
|
|
107
|
+
end
|
|
108
|
+
end
|
|
109
|
+
def self.doEval modules, grammers, opts, toEval, f, lno, b
|
|
110
|
+
start = 0
|
|
111
|
+
lns = toEval.lines
|
|
112
|
+
firstLine = lns.shift
|
|
113
|
+
if firstLine !~ /^\s*using\b([^<"'%]*)(#|$)/
|
|
114
|
+
raise ArgumentError.new("using a grammer, cannot contain any literal expressions")
|
|
115
|
+
end
|
|
116
|
+
lns.each_line do |ln|
|
|
117
|
+
#process first using for each GrammerExt
|
|
118
|
+
case ln
|
|
119
|
+
when /^\s*using\b([^<"'%/`]*)(#|$)/
|
|
120
|
+
begin
|
|
121
|
+
args, nopts = TOPLEVEL_BINDING.eval("__get_args__(" + $1 + ")").flatten
|
|
122
|
+
opts.merge nopts
|
|
123
|
+
args.each do |e|
|
|
124
|
+
if e.is_a? GrammerExt
|
|
125
|
+
if !grammers.include? e
|
|
126
|
+
grammers.push e
|
|
127
|
+
end
|
|
128
|
+
else
|
|
129
|
+
if !modules.include? e
|
|
130
|
+
modules.push e
|
|
131
|
+
end
|
|
132
|
+
end
|
|
133
|
+
end
|
|
134
|
+
rescue
|
|
135
|
+
break
|
|
136
|
+
end
|
|
137
|
+
when /^\s*(#|$)/
|
|
138
|
+
else
|
|
139
|
+
break
|
|
140
|
+
end
|
|
141
|
+
start += 1
|
|
142
|
+
end
|
|
143
|
+
toEval = lns[start .. -1].join
|
|
144
|
+
modules.each do |m|
|
|
145
|
+
b.eval("__org_using__ ::ObjectSpace.__id2ref(#{m.__id__})")
|
|
146
|
+
end
|
|
147
|
+
grammers.each do |g|
|
|
148
|
+
toEval = g.translate(opts, toEval, f, lno + start)
|
|
149
|
+
end
|
|
150
|
+
TOPLEVEL_BINDING.eval(toEval, f, lno + start)
|
|
151
|
+
end
|
|
152
|
+
def initialize name
|
|
153
|
+
@name = name
|
|
154
|
+
end
|
|
155
|
+
def inspect
|
|
156
|
+
@name
|
|
157
|
+
end
|
|
158
|
+
def to_s
|
|
159
|
+
@name
|
|
160
|
+
end
|
|
161
|
+
end
|
|
162
|
+
|
|
163
|
+
class Indenter < GrammerExt
|
|
164
|
+
def getTranslateOptions opts
|
|
165
|
+
::AdhocLiterals.resolveRequirement opts
|
|
166
|
+
end
|
|
167
|
+
class CaseCondList
|
|
168
|
+
def initialize vn, cn
|
|
169
|
+
@vn = vn
|
|
170
|
+
@cn = cn
|
|
171
|
+
@list = []
|
|
172
|
+
end
|
|
173
|
+
def add c
|
|
174
|
+
@list.push c
|
|
175
|
+
end
|
|
176
|
+
def head
|
|
177
|
+
<<~Out
|
|
178
|
+
#{@vn}.pushCondProxy
|
|
179
|
+
begin
|
|
180
|
+
begin
|
|
181
|
+
#{getSubHead}
|
|
182
|
+
rescue #{@vn}.FinishCond
|
|
183
|
+
end
|
|
184
|
+
if #{@vn}.hasTrue?
|
|
185
|
+
Out
|
|
186
|
+
end
|
|
187
|
+
def getSubHead
|
|
188
|
+
emb = ""
|
|
189
|
+
@list.each do |e|
|
|
190
|
+
if e.is_a? CaseCondList
|
|
191
|
+
emb += e.getSubHead
|
|
192
|
+
else
|
|
193
|
+
case e
|
|
194
|
+
when /\A(when|in)\b/
|
|
195
|
+
emb += <<~Out
|
|
196
|
+
if case #{@vn}.case #{e}; true; else false end
|
|
197
|
+
#{@vn}.pushCond true
|
|
198
|
+
#{@vn}.finishCond
|
|
199
|
+
else
|
|
200
|
+
#{@vn}.pushCond false
|
|
201
|
+
end
|
|
202
|
+
Out
|
|
203
|
+
when /\Afor\b/
|
|
204
|
+
emb += <<~Out
|
|
205
|
+
if case #{@vn}.case when #{$'}; true; else false end
|
|
206
|
+
#{@vn}.pushCond true
|
|
207
|
+
else
|
|
208
|
+
#{@vn}.pushCond false
|
|
209
|
+
end
|
|
210
|
+
Out
|
|
211
|
+
end
|
|
212
|
+
end
|
|
213
|
+
end
|
|
214
|
+
emb
|
|
215
|
+
end
|
|
216
|
+
def tail
|
|
217
|
+
emb += <<~Out
|
|
218
|
+
#{
|
|
219
|
+
if ["when", "in"].include? @cn
|
|
220
|
+
#{@vn}.finish
|
|
221
|
+
end
|
|
222
|
+
}
|
|
223
|
+
end # if #{@vn}.hasTrue?
|
|
224
|
+
ensure
|
|
225
|
+
#{@vn}.popCondProxy
|
|
226
|
+
end
|
|
227
|
+
Out
|
|
228
|
+
end
|
|
229
|
+
end
|
|
230
|
+
class TranslationError << Exception
|
|
231
|
+
end
|
|
232
|
+
class Restart << Exception
|
|
233
|
+
end
|
|
234
|
+
RBRACE_MODE = StrBegin + [:bare, :path]
|
|
235
|
+
def getOpponent c
|
|
236
|
+
case c
|
|
237
|
+
when ?{
|
|
238
|
+
?}
|
|
239
|
+
when ?[
|
|
240
|
+
?]
|
|
241
|
+
when ?(
|
|
242
|
+
?)
|
|
243
|
+
when ?}
|
|
244
|
+
?{
|
|
245
|
+
when ?]
|
|
246
|
+
?[
|
|
247
|
+
when ?)
|
|
248
|
+
?(
|
|
249
|
+
when ?<
|
|
250
|
+
?>
|
|
251
|
+
when ?>
|
|
252
|
+
?<
|
|
253
|
+
end
|
|
254
|
+
end
|
|
255
|
+
def getLno pos
|
|
256
|
+
@lnoBase + @expr.count_until("\n", pos)
|
|
257
|
+
end
|
|
258
|
+
def getStringEndExceptSlash pos
|
|
259
|
+
lnoBase = getLno(pos)
|
|
260
|
+
self.class.new @expr[pos .. - 1], @@opts, @@fName, lnoBase, :path_quote do |qed|
|
|
261
|
+
if qed
|
|
262
|
+
return pos + qed
|
|
263
|
+
else
|
|
264
|
+
return nil
|
|
265
|
+
end
|
|
266
|
+
end
|
|
267
|
+
end
|
|
268
|
+
def getClosing pos
|
|
269
|
+
open = @expr[pos]
|
|
270
|
+
close = getOpponent open
|
|
271
|
+
s = 0
|
|
272
|
+
while o = @expr[i]
|
|
273
|
+
case o
|
|
274
|
+
when open #orphan
|
|
275
|
+
s += 1
|
|
276
|
+
break
|
|
277
|
+
when close
|
|
278
|
+
s -= 1
|
|
279
|
+
if s == 0
|
|
280
|
+
return i
|
|
281
|
+
end
|
|
282
|
+
when "#" #embeded expression do not allow first ".", "/", "?", "*", "{}", "[]", otherwise use #wpd{...}, w:wild([],{}.?,*), p:period(.), d:directory(/)
|
|
283
|
+
k = checkExtendedEmbExpr(@@expr, i, :path)
|
|
284
|
+
end
|
|
285
|
+
if !k
|
|
286
|
+
i += 1
|
|
287
|
+
else
|
|
288
|
+
i = k + 1
|
|
289
|
+
k = nil
|
|
290
|
+
end
|
|
291
|
+
end
|
|
292
|
+
return nil
|
|
293
|
+
end
|
|
294
|
+
def getOpening pos
|
|
295
|
+
cl = @expr[pos]
|
|
296
|
+
op = getOpponent cl
|
|
297
|
+
pos -= 1
|
|
298
|
+
cnt = 1
|
|
299
|
+
while pos > 0
|
|
300
|
+
case @expr[pos]
|
|
301
|
+
when cl
|
|
302
|
+
cnt += 1
|
|
303
|
+
when op
|
|
304
|
+
cnt -= 1
|
|
305
|
+
if cnt == 0
|
|
306
|
+
return pos
|
|
307
|
+
end
|
|
308
|
+
when "\n"
|
|
309
|
+
if @expr[0..pos - 1] =~ /#.*$/
|
|
310
|
+
end
|
|
311
|
+
end
|
|
312
|
+
pos -= 1
|
|
313
|
+
end
|
|
314
|
+
nil
|
|
315
|
+
end
|
|
316
|
+
def setRegexp start
|
|
317
|
+
[:f_regexp, :regexp].each do |m|
|
|
318
|
+
testExpr = @expr[start .. - 1]
|
|
319
|
+
self.class.new testExpr, @opts, @fName, getLno(start), m do |red|
|
|
320
|
+
if red
|
|
321
|
+
red += start - 1
|
|
322
|
+
@expr[start .. -1] = REGEXP_HEAD + testExpr[0 .. red] + ")" + testExpr[red + 1 .. -1]
|
|
323
|
+
raise Restart.new
|
|
324
|
+
else
|
|
325
|
+
next
|
|
326
|
+
end
|
|
327
|
+
end
|
|
328
|
+
raise Error.new("#{getLno(start)}: cannot find end of regular expression")
|
|
329
|
+
end
|
|
330
|
+
end
|
|
331
|
+
def checkExtendedEmbExpr start, kind = :bare, til = nil
|
|
332
|
+
sr = til ? @expr[start...til] : @expr
|
|
333
|
+
start = sr.index(/#(([^{\s\\]|\\.)*)\{/)&.+(til ? start : 0)
|
|
334
|
+
if start && checkEmbedPrefix(prefix = $1) && $`[/\\*$/].size % 2 == 0
|
|
335
|
+
lbrace_pos = start + prefix.size + 1
|
|
336
|
+
if @expr[lbrace_pos + 1, EMBED_START.size] != EMBED_START
|
|
337
|
+
altExpr = @expr[lbrace_pos .. -1]
|
|
338
|
+
lnoBase = getLno lbrace_pos
|
|
339
|
+
self.class.new altExpr, @opts, @fName, lnoBase, kind do |ed, mode, led, pstack|
|
|
340
|
+
if ed
|
|
341
|
+
pre = "#{EMBED_START}#{' ' * 6}, '#{prefix}', #{mode.inspect}, ("
|
|
342
|
+
post = "))"
|
|
343
|
+
emb = "\#{" + pre + altExpr[1 .. ed - 1] + post + "}"
|
|
344
|
+
emb[EMBED_START.size + 2, 6] = sprintf('%6d', emb.size)
|
|
345
|
+
@expr[start .. -1] = emb + altExpr[ed + 1 .. -1]
|
|
346
|
+
diff = emb.size - ed + start
|
|
347
|
+
case mode
|
|
348
|
+
when :email
|
|
349
|
+
when :path
|
|
350
|
+
pstack.map!{|e| e + diff}
|
|
351
|
+
checkPrevIsPath nil, start, diff + led, pstack
|
|
352
|
+
when :url
|
|
353
|
+
end
|
|
354
|
+
raise Restart.new
|
|
355
|
+
else
|
|
356
|
+
raise Error.new("#{getLno(start)}: cannot find end of embedded expression")
|
|
357
|
+
end
|
|
358
|
+
end
|
|
359
|
+
else
|
|
360
|
+
if @expr.index /\d+/, lbrace_pos + 1 + EMBED_START.size
|
|
361
|
+
return $&.to_i + start
|
|
362
|
+
else
|
|
363
|
+
raise Error.new("#{getLno(start)}: cannot find length of embedded expression")
|
|
364
|
+
end
|
|
365
|
+
end
|
|
366
|
+
else
|
|
367
|
+
nil
|
|
368
|
+
end
|
|
369
|
+
end
|
|
370
|
+
def removeCComment dprev
|
|
371
|
+
tab_stop = @opts[:tab_stop]
|
|
372
|
+
if @expr.index("*/", dprev.first + 2)
|
|
373
|
+
toReplace = @expr[dprev.first .. til + 1]
|
|
374
|
+
rln_pos = toReplace.rindex("\n")
|
|
375
|
+
begin
|
|
376
|
+
if rln_pos
|
|
377
|
+
@expr[dprev.first .. til + 1] = toReplace.count("\n") * (Token.stuffer(:hidden_nl) + "\\\n") + " " * TTYWidth.width toReplace[rln_pos + 1 .. -1], tab_stop, 0
|
|
378
|
+
else
|
|
379
|
+
@expr[dprev.first .. til + 1] = " " * (TTYWidth.width(toReplace[dprev.first .. til + 1], tab_stop, dprev.tty_pos) - dprev.tty_pos)
|
|
380
|
+
end
|
|
381
|
+
rescue ArgumentError
|
|
382
|
+
if t.prevNL || rln_pos
|
|
383
|
+
raise $!
|
|
384
|
+
else
|
|
385
|
+
@expr[dprev.first .. til + 1] = " "
|
|
386
|
+
end
|
|
387
|
+
end
|
|
388
|
+
raise Restart.new
|
|
389
|
+
else
|
|
390
|
+
raise TranslationError.new("unclosed C-style comment : #{t.str} in #{t.lno}:#{t.cno}")
|
|
391
|
+
end
|
|
392
|
+
end
|
|
393
|
+
EMBED_START = "GrammerExt::__embed__("
|
|
394
|
+
REGEXP_HEAD = "GrammerExt::__regexp__("
|
|
395
|
+
def checkEmbedPrefix pfx
|
|
396
|
+
if pfx == "" || pfx =~ /^\w+$/
|
|
397
|
+
true
|
|
398
|
+
elsif pfx =~ /^\W+$/
|
|
399
|
+
pfin = ""
|
|
400
|
+
pfx.each_char do |c|
|
|
401
|
+
if pfin.index c
|
|
402
|
+
return false
|
|
403
|
+
end
|
|
404
|
+
pfin += c
|
|
405
|
+
end
|
|
406
|
+
else
|
|
407
|
+
false
|
|
408
|
+
end
|
|
409
|
+
end
|
|
410
|
+
def themeExpr tk
|
|
411
|
+
case tk
|
|
412
|
+
when :"&."
|
|
413
|
+
"___theme_period"
|
|
414
|
+
when :"::"
|
|
415
|
+
"___theme_double_colon"
|
|
416
|
+
when :on_period
|
|
417
|
+
"___theme_period"
|
|
418
|
+
end
|
|
419
|
+
end
|
|
420
|
+
def initialize expr, opts, f, lnoBase = 0, ebmode = nil
|
|
421
|
+
@lnoBase = lnoBase
|
|
422
|
+
@expr = expr
|
|
423
|
+
@opts = opts
|
|
424
|
+
@fName = f
|
|
425
|
+
case ebmode
|
|
426
|
+
when :f_regexp
|
|
427
|
+
i = 1
|
|
428
|
+
while i = @expr.index(/\/|\#/, i)
|
|
429
|
+
next if $` =~ /\\+$/ && $&.size % 2 == 1
|
|
430
|
+
case @expr[i..-1]
|
|
431
|
+
when /^#(([^{\s\\]|\\.)*)\{/
|
|
432
|
+
begin
|
|
433
|
+
ed = checkExtendedEmbExpr i + $&.size - 1, :on_regexp_beg
|
|
434
|
+
if ed
|
|
435
|
+
i = ed
|
|
436
|
+
end
|
|
437
|
+
rescue Restart
|
|
438
|
+
end
|
|
439
|
+
when /^#.*\n/
|
|
440
|
+
@expr[i] = "\n"
|
|
441
|
+
i = 1
|
|
442
|
+
when /^\/\*.*\*\//m
|
|
443
|
+
@expr[i, $&.size] = " " + "\n" * $&.count("\n")
|
|
444
|
+
i = 1
|
|
445
|
+
when /^\/(\w*)/
|
|
446
|
+
if !$1.include? "x"
|
|
447
|
+
yield nil
|
|
448
|
+
else
|
|
449
|
+
yield i + $&.size - 1
|
|
450
|
+
end
|
|
451
|
+
end
|
|
452
|
+
i += 1
|
|
453
|
+
end
|
|
454
|
+
yield nil #do not return
|
|
455
|
+
when :regexp
|
|
456
|
+
i = 1
|
|
457
|
+
while i = @expr.index(/\/|\#/, i)
|
|
458
|
+
next if $` =~ /\\+$/ && $&.size % 2 == 1
|
|
459
|
+
case @expr[i..-1]
|
|
460
|
+
when /^#(([^{\s\\]|\\.)*)\{/
|
|
461
|
+
begin
|
|
462
|
+
ed = checkExtendedEmbExpr i + $&.size - 1, :on_regexp_beg
|
|
463
|
+
if ed
|
|
464
|
+
i = ed
|
|
465
|
+
end
|
|
466
|
+
rescue Restart
|
|
467
|
+
end
|
|
468
|
+
when /^\/(\w*)/
|
|
469
|
+
yield i + $&.size - 1
|
|
470
|
+
end
|
|
471
|
+
i += 1
|
|
472
|
+
end
|
|
473
|
+
yield nil #do not return
|
|
474
|
+
end
|
|
475
|
+
# tab_stop : 1
|
|
476
|
+
# cjk_width : :mintty, :ms, :xterm
|
|
477
|
+
allTokens = []
|
|
478
|
+
begin
|
|
479
|
+
while true
|
|
480
|
+
t = Token.next expr, opts, f, lnoBase, ebmode
|
|
481
|
+
if t.kind == :/ || (t.kind == :on_regexp_beg && t.str == "/" && (@expr[t.first - REGEXP_HEAD.size, REGEXP_HEAD.size] != REGEXP_HEAD))
|
|
482
|
+
checkPrevIsPath tenum if AdhocLiterals[:path]
|
|
483
|
+
if @expr[t.first + 1] == "*"
|
|
484
|
+
removeCComment dprev if defined?(CComment)
|
|
485
|
+
else
|
|
486
|
+
# regexp
|
|
487
|
+
checkPath t.first if AdhocLiterals[:path]
|
|
488
|
+
# check regexp
|
|
489
|
+
if t.kind == :on_regexp_beg
|
|
490
|
+
setRegexp dprev.first
|
|
491
|
+
end
|
|
492
|
+
end
|
|
493
|
+
end
|
|
494
|
+
|
|
495
|
+
#if (t.dprev&.dprev&.kind == :on_ident && t.dprev.dprev.maybeItertor? || [:while, :do, :until].include?(t.dprev&.dprev&.kind)) \
|
|
496
|
+
#&& [t.dprev&.kind, t.kind] == [:on_symbeg, :on_ident]
|
|
497
|
+
if AdhocLiterals[:url] || AdhocLiterals[:path]
|
|
498
|
+
if [:on_ident, :on_const].include?(t.dprev&.dprev&.kind) && t.dprev.kind == :on_symbeg && t.realToken?
|
|
499
|
+
checkURL t.dprev.dprev.first if AdhocLiterals[:url] || AdhocLiterals[:path]
|
|
500
|
+
end
|
|
501
|
+
if (t.dprev&.kind == :on_label) && t.realToken?
|
|
502
|
+
checkURL t.dprev.first
|
|
503
|
+
end
|
|
504
|
+
end
|
|
505
|
+
if AdhocLiterals[:email] && t.dprev&.kind == :on_ivar && t.dprev.dprev&.str !~ /\s/ && (t.dprev.str.size != 1 || @expr[t.dprev&.first + 1] == "[")
|
|
506
|
+
checkEmail t.dprev&.first
|
|
507
|
+
end
|
|
508
|
+
if AdhocLiterals[:tag] && t&.kind == :< && \
|
|
509
|
+
(c = @expr[t.first + 1];
|
|
510
|
+
c == ?_ \
|
|
511
|
+
|| c == ?: \
|
|
512
|
+
|| c == ?? \
|
|
513
|
+
|| c == ?! \
|
|
514
|
+
|| ?a.ord <= c.ord && c.ord <= ?z.ord \
|
|
515
|
+
|| ?A.ord <= c.ord && c.ord <= ?Z.ord \
|
|
516
|
+
|| 0x70 < c.ord)
|
|
517
|
+
checkTag(t.first)
|
|
518
|
+
end
|
|
519
|
+
if t.kind == :on_tstring_content
|
|
520
|
+
if mode == :path_quote && t.cur.parStack.size == 1 && t.parent.kind == :on_tstring_beg
|
|
521
|
+
if t.str.include "/"
|
|
522
|
+
raise Error.new("path element cannot contain '/'")
|
|
523
|
+
end
|
|
524
|
+
end
|
|
525
|
+
if t.parent.kind == :on_heredoc_beg && t.parent.str !~ /^\<\<(\~|\-|)'(.+)'$/
|
|
526
|
+
k = t.parent.str =~ /\`/ ? :on_backtick : :on_tstring_beg
|
|
527
|
+
elsif StrBegin.include?(t.parent.kind) && !["'", ":'", "%q", "%w", "%i", "%s"].include?(t.parent.str[0, 2])
|
|
528
|
+
k = t.parent.kind
|
|
529
|
+
end
|
|
530
|
+
ep = t.first
|
|
531
|
+
checkExtendedEmbExpr ep, k, ep + t.str.size
|
|
532
|
+
end
|
|
533
|
+
# concatenate path
|
|
534
|
+
mayConcatenatePath t if AdhocLiterals[:path] || AdhocLiterals[:url]
|
|
535
|
+
# insert embedding information although non-extended embed expression
|
|
536
|
+
if t.kind == :on_embexpr_beg
|
|
537
|
+
checkExtendedEmbExpr t.first, t.parent.kind
|
|
538
|
+
end
|
|
539
|
+
case t.kind
|
|
540
|
+
when :on_heredoc_beg
|
|
541
|
+
t.addModAfter SET_LINE
|
|
542
|
+
end
|
|
543
|
+
|
|
544
|
+
|
|
545
|
+
# ./file&{.r?}.open
|
|
546
|
+
# _1.gets
|
|
547
|
+
# braces for hash
|
|
548
|
+
|
|
549
|
+
# foo \n \n : pi
|
|
550
|
+
# goo goo : t
|
|
551
|
+
if defined?(Endless) && (pi = t&.prev) == :on_nl && t.realToken?
|
|
552
|
+
ti = t.cur.idtStack.last
|
|
553
|
+
if !ti
|
|
554
|
+
res = 0 <=> t.tty_pos
|
|
555
|
+
else
|
|
556
|
+
if ti.tty_pos < t.tty_pos
|
|
557
|
+
res = -1 # indent-in
|
|
558
|
+
elsif ti.unindent_pos > t.tty_pos
|
|
559
|
+
res = 1
|
|
560
|
+
else
|
|
561
|
+
res = 0 # same
|
|
562
|
+
end
|
|
563
|
+
end
|
|
564
|
+
if res < 0 # check iterator : indent-in
|
|
565
|
+
s = ti.parStackI&.last&.entity
|
|
566
|
+
case t.prev_non_sp.kind
|
|
567
|
+
when :on_lparen, :on_lbrace, :on_lbracket # t.prev_non_sp == s
|
|
568
|
+
when :"&.", :"::", :on_period #should not be operand, "foo.\n"
|
|
569
|
+
toPush = t.prev_non_sp
|
|
570
|
+
else
|
|
571
|
+
if s&.isStarterAll?
|
|
572
|
+
if s.requireArg? # while if ....
|
|
573
|
+
s.closeSentence pi
|
|
574
|
+
else # if ...;
|
|
575
|
+
# no need
|
|
576
|
+
end
|
|
577
|
+
elsif %i{argless_case_lower argless_case}.include? s&.kind
|
|
578
|
+
s.addArglessCaseLower pi
|
|
579
|
+
else #!s.isStarterAll? # iterator
|
|
580
|
+
if (pi.iteratorMethod = t.parent.iteratorCand)&.setupIteratorLabel
|
|
581
|
+
s.iteratorCand = nil
|
|
582
|
+
else
|
|
583
|
+
raise Error.new("cannot find iterator method for indentation-in")
|
|
584
|
+
end
|
|
585
|
+
end
|
|
586
|
+
toPush = pi # :on_nl, previous line end interpreted as iterator
|
|
587
|
+
end
|
|
588
|
+
if toPush
|
|
589
|
+
toPush.implementStarterMayBrace
|
|
590
|
+
toPush.spush
|
|
591
|
+
t.parent = toPush
|
|
592
|
+
end # toPush is nil : previous line ending with '(\n', '{\n', '[\n'
|
|
593
|
+
t.ipush #setup indent-in
|
|
594
|
+
else # indent-out or same-level
|
|
595
|
+
toInsert = ""
|
|
596
|
+
seach = proc do |sList, isCurrent|
|
|
597
|
+
sList.each_with_index do |s, i|
|
|
598
|
+
toInsert = s.closeBeginner(pi) + toInsert
|
|
599
|
+
# remove below
|
|
600
|
+
if s.isStarterAll?
|
|
601
|
+
case s.kind
|
|
602
|
+
when :on_nl
|
|
603
|
+
c = s.iteratorMethod
|
|
604
|
+
s.addModPrev, "do"
|
|
605
|
+
if !(ins = c.trySetupIterator(:preset, s))
|
|
606
|
+
ins = "end"
|
|
607
|
+
end
|
|
608
|
+
when :"\\"
|
|
609
|
+
c = s.iteratorMethod
|
|
610
|
+
barg_op = s.argRange ? "|" : ""
|
|
611
|
+
s.addModReplace "do #{barg_op}"
|
|
612
|
+
s.argEnd.addModPrev barg_op
|
|
613
|
+
if c
|
|
614
|
+
if !(ins = c.trySetupIterator(:preset, s))
|
|
615
|
+
ins = "end"
|
|
616
|
+
end
|
|
617
|
+
else
|
|
618
|
+
s.addModReplace " ::Kernel::proc do #{barg_op}\n"
|
|
619
|
+
s.argEnd.addModPrev barg_op
|
|
620
|
+
ins = "end"
|
|
621
|
+
if s.isSentenceHead?
|
|
622
|
+
if !s.argRange
|
|
623
|
+
ins += ".call"
|
|
624
|
+
else
|
|
625
|
+
raise Error.new("orphan proc with argumnents")
|
|
626
|
+
end
|
|
627
|
+
end
|
|
628
|
+
end
|
|
629
|
+
when :"&.", :on_period, :"::"
|
|
630
|
+
if (tmp = s.prev).kind == :on_rparen && tmp.beginner.isOperand?
|
|
631
|
+
if s.kind == :"&." && tmp.beginner.multiArgument?
|
|
632
|
+
raise Error.new("multiple theme for &. is not allowed")
|
|
633
|
+
end
|
|
634
|
+
# (Table1, Table2)::\n ... -> ____theme_double_colon___(Table1, Table2){ ... }
|
|
635
|
+
tmp.beginner.addModPrev themeExpr.(s.kind)
|
|
636
|
+
s.addModReplace "{"
|
|
637
|
+
else # a::\n ... -> a::____theme_double_colon___{ ... }
|
|
638
|
+
s.addModAfter themeExpr.(s.kind) + "{"
|
|
639
|
+
end
|
|
640
|
+
############ implement ".", "@foo", "&&"
|
|
641
|
+
ins = "}"
|
|
642
|
+
when :on_tlambda
|
|
643
|
+
case s.body
|
|
644
|
+
when :on_lambeg
|
|
645
|
+
when :do
|
|
646
|
+
when nil
|
|
647
|
+
if s.argEnd != :on_nl
|
|
648
|
+
raise Error.new("descrepant -> args")
|
|
649
|
+
end
|
|
650
|
+
s.argEnd.addModReplace s.argEnd.str + "{"
|
|
651
|
+
ins = "}"
|
|
652
|
+
end
|
|
653
|
+
when :do
|
|
654
|
+
if c = s.iteratorMethod
|
|
655
|
+
if s.parent.iteratorCand == c
|
|
656
|
+
s.parent.iteratorCand = nil
|
|
657
|
+
end
|
|
658
|
+
c.setupIteratorLabel
|
|
659
|
+
if !(ins = c.trySetupIterator(:preset, s))
|
|
660
|
+
ins = "end"
|
|
661
|
+
end
|
|
662
|
+
else
|
|
663
|
+
s.addModPrev " ::Kernel::proc "
|
|
664
|
+
ins = "end"
|
|
665
|
+
end
|
|
666
|
+
when :case, :free_case # free case
|
|
667
|
+
ins = finalizeCase(s, pi) + "end"
|
|
668
|
+
else
|
|
669
|
+
if s.isIflessStarter?
|
|
670
|
+
finalizeIfless(s)
|
|
671
|
+
ins = "end"
|
|
672
|
+
elsif ![:until, :while].include?(s.kind) || !(ins = s.trySetupIterator(:forward, s))
|
|
673
|
+
ins = (s.requireArg? ?
|
|
674
|
+
(s.closeSentence(t.prev); s.argEnd = t.prev; ?;)
|
|
675
|
+
: ' ') + "end"
|
|
676
|
+
end
|
|
677
|
+
end
|
|
678
|
+
#toInsert = ins + Token.stuffer(:for_indent_out) + toInsert
|
|
679
|
+
toInsert = ins + toInsert
|
|
680
|
+
if isCurrent == :continue_clause
|
|
681
|
+
if !sList[i + 1] || !sList[i + 1].isStarter? || !sList[i + 1].requireArg?
|
|
682
|
+
raise Error.new("cannot continue '#{sList[i + 1].str}'")
|
|
683
|
+
end
|
|
684
|
+
break
|
|
685
|
+
end
|
|
686
|
+
elsif s.arglessCaseUpper
|
|
687
|
+
if !s.lines
|
|
688
|
+
raise Error.new("empty line under argless case")
|
|
689
|
+
end
|
|
690
|
+
s.lines.each_with_index do |item, i|
|
|
691
|
+
item.first.addModPrev "#{i == 0 ? "#{')&&(' if s.kind == :on_nl}(" : ') ||'}("
|
|
692
|
+
end
|
|
693
|
+
# case
|
|
694
|
+
# x ( x
|
|
695
|
+
# a ) ||( a
|
|
696
|
+
# b )&&( ( b
|
|
697
|
+
# c ) ||( c
|
|
698
|
+
# d ) ||( d )
|
|
699
|
+
# e ) ||( e
|
|
700
|
+
# f ) ||( f )
|
|
701
|
+
if s.kind == :argless_case
|
|
702
|
+
s.addModReplace ""
|
|
703
|
+
end
|
|
704
|
+
toInsert = ")" + toInsert
|
|
705
|
+
else
|
|
706
|
+
#if %i{post_test_while post_test_until}.include? (sc = s.currentClause).kind # should be argument is not closed
|
|
707
|
+
# if !sc.requireArg?
|
|
708
|
+
# raise Error.new("descrepant post test clause")
|
|
709
|
+
# end
|
|
710
|
+
# sc.argEnd = pi
|
|
711
|
+
# sc.closeSentence
|
|
712
|
+
# toInsert = postTestFinalize(pi) + toInsert
|
|
713
|
+
#els
|
|
714
|
+
if !isCurrent || isCurrent == :continue_clause
|
|
715
|
+
# if ( { [ left raise error
|
|
716
|
+
raise Error.new("unclosed '#{s.str}' before unindentation")
|
|
717
|
+
else
|
|
718
|
+
break
|
|
719
|
+
end
|
|
720
|
+
end
|
|
721
|
+
pi.spop
|
|
722
|
+
end
|
|
723
|
+
end
|
|
724
|
+
ri = t.cur.idtStack.rindex do |e|
|
|
725
|
+
e.unindent_pos <= t.first
|
|
726
|
+
end
|
|
727
|
+
if !ri
|
|
728
|
+
raise Error.new("unknown error")
|
|
729
|
+
end
|
|
730
|
+
# get indent-in parStack
|
|
731
|
+
chkList = []
|
|
732
|
+
(t.cur.idtStack.size - 1).downto ri - 1 do |i|
|
|
733
|
+
t.cur.idtStack[i].parStackI.reverse_each do |w|
|
|
734
|
+
chkList.unshift w.orgEntity
|
|
735
|
+
end
|
|
736
|
+
t.cur.idtStack.pop
|
|
737
|
+
end
|
|
738
|
+
|
|
739
|
+
# get same level parStack
|
|
740
|
+
t.cur.idtStack[ri].unindent_pos = t.first
|
|
741
|
+
t.cur.idtStack[ri].parStackI.reverse_each do |w|
|
|
742
|
+
lastList.unshift w.orgEntity
|
|
743
|
+
end
|
|
744
|
+
|
|
745
|
+
seach[chkList, toInsert, false]
|
|
746
|
+
|
|
747
|
+
if t.kind == :continue_clause
|
|
748
|
+
seach[lastList, toInsert, :continue_clause]
|
|
749
|
+
else
|
|
750
|
+
case t.cur.idtStack[ri].parStackI.last&.entity
|
|
751
|
+
when ->{_1.nativeContinue?(t.kind)},
|
|
752
|
+
->{ defined?(PostTestWhile) && _1.kind == :do &&
|
|
753
|
+
!_1.parent.iteratorCand &&
|
|
754
|
+
%i{while until}.include?(t.kind) &&
|
|
755
|
+
(_1.setPostTest(t) ; true) }
|
|
756
|
+
seach[lastList, toInsert, true]
|
|
757
|
+
if t.parent.kind == :on_lbrace && t.kind != :on_rbrace && t.prev_non_sp != t.parent
|
|
758
|
+
t.parent.kind = :lbrace_clause # determine clause, not hash
|
|
759
|
+
end
|
|
760
|
+
|
|
761
|
+
end
|
|
762
|
+
end
|
|
763
|
+
if !toInsert.empty?
|
|
764
|
+
pi.addModReplace toInsert + pi.str
|
|
765
|
+
end
|
|
766
|
+
end
|
|
767
|
+
s = t.cur.idtStack.last.parStackI.last.entity #maybe newly pushed
|
|
768
|
+
end
|
|
769
|
+
# free case, free ensure, free rescue, ::{}, .{}
|
|
770
|
+
if [t.prev, t.prev_non_sp].find{[t.parent, t.parent.sentences&.last&.last].include?(_1)} && t.realToken?
|
|
771
|
+
t.parent.openSentence t
|
|
772
|
+
end
|
|
773
|
+
# argless_case
|
|
774
|
+
if %i{on_semicolon on_nl}.include? t.kind # already disposed
|
|
775
|
+
t.parent.closeSentence t
|
|
776
|
+
t.parent.iteratorCand = nil
|
|
777
|
+
if t.parent.kind == :case
|
|
778
|
+
if !t.parent.argStart
|
|
779
|
+
t.parent.kind = :argless_case
|
|
780
|
+
end
|
|
781
|
+
end
|
|
782
|
+
end
|
|
783
|
+
#seup iterator candidate
|
|
784
|
+
if [:on_ident, :on_const].include?(t.kind) || t.maybeIteratorLabel?
|
|
785
|
+
t.parent.iteratorCand ||= t
|
|
786
|
+
elsif [:"'", :'"'].include?(t.kind)
|
|
787
|
+
if t.parent.iteratorCand == t.dprev
|
|
788
|
+
t.parent.iteratorCand = t
|
|
789
|
+
else
|
|
790
|
+
t.parent.iteratorCand ||= t
|
|
791
|
+
end
|
|
792
|
+
elsif t.kind == :on_rparen && t.beginner.prev.kind == :'."' # ."(method_unbound)
|
|
793
|
+
t.parent.iteratorCand ||= t
|
|
794
|
+
elsif [:on_semicolon, :on_nl, :and, :or, :not].include?(t.kind)
|
|
795
|
+
t.parent.iteratorCand = nil
|
|
796
|
+
elsif t.dprev == t.parent.iteratorCand && t.continues? && !t.nonBinary?
|
|
797
|
+
if t.parent.kind == :on_lbrace && t.kind == :on_comma && t.parent.iteratorCand == nil &&
|
|
798
|
+
(t.parent.next == :on_label || t.parent.next_non_sp == :on_label)
|
|
799
|
+
t.parent.kind = :hash_beg
|
|
800
|
+
end
|
|
801
|
+
if t.parent.kind == :on_lbrace && t.kind == :"=>" && t.parent.iteratorCand == nil
|
|
802
|
+
if t.parent.firstRightAssign
|
|
803
|
+
t.parent.kind = :hash_beg
|
|
804
|
+
else
|
|
805
|
+
t.parent.firstRightAssign = t
|
|
806
|
+
end
|
|
807
|
+
t.parent.kind = :hash_beg
|
|
808
|
+
end
|
|
809
|
+
t.parent.iteratorCand = nil
|
|
810
|
+
elsif t.prev == t.parent.iteratorCand && t.dprev == :on_sp && t.realToken?
|
|
811
|
+
if t.kind == :on_period && !t.isOperand? || # method call operand start 'iterator.foo'
|
|
812
|
+
t.continues? && # include :&., :. (non operand) 'iterator +'
|
|
813
|
+
#(![:"::", :~, :"!", :"<:", :"@+", :"@-", :"@!", :"@~", # unary operator 'iterator ::foo', 'iterator ~foo'
|
|
814
|
+
# :on_lbrace, :on_lbracket, :on_lparen, :"..", :"..."].include?(t.kind) && #'iterator [...]'
|
|
815
|
+
#!([:*, :**, :+, :-, :&].include?(t.kind) && t.dnext != :on_sp) && # another unary operator with post-non-space
|
|
816
|
+
#(!defined?(PinClassOp) || (t.kind == :^ && t.dnext != :on_sp))
|
|
817
|
+
#)
|
|
818
|
+
!unary? && !callArgOp? && !t.themeLParen?
|
|
819
|
+
t.parent.iteratorCand = nil # 'iterator + ...' 'iterator , ...'
|
|
820
|
+
end
|
|
821
|
+
end
|
|
822
|
+
# setup hash
|
|
823
|
+
if t.parent.kind == :on_lbrace && t.kind == :on_comma && t.parent.iteratorCand == nil
|
|
824
|
+
&& (t.parent.next == :on_label || t.parent.next_non_sp == :on_label)
|
|
825
|
+
t.parent.kind = :hash_beg
|
|
826
|
+
end
|
|
827
|
+
if t.parent.kind == :on_lbrace && t.kind == :"=>" && t.parent.iteratorCand == nil
|
|
828
|
+
if t.parent.firstRightAssign
|
|
829
|
+
t.parent.kind = :hash_beg
|
|
830
|
+
else
|
|
831
|
+
t.parent.firstRightAssign = t
|
|
832
|
+
end
|
|
833
|
+
t.parent.kind = :hash_beg
|
|
834
|
+
end
|
|
835
|
+
|
|
836
|
+
# instant variable by '>'
|
|
837
|
+
if t.var_able? && (tp = t.dprev).kind == :>
|
|
838
|
+
if tp.dprev.terminal?
|
|
839
|
+
tp.addModReplace "._____insert_var"
|
|
840
|
+
t.addModReplace "(#{t.str} = :#{t.str})"
|
|
841
|
+
elsif [:if, :unless].include? tp.dprev.kind
|
|
842
|
+
tp.addModReplace ""
|
|
843
|
+
t.addModAfter(" = ")
|
|
844
|
+
end
|
|
845
|
+
end
|
|
846
|
+
# instant variable by '>' for when, for
|
|
847
|
+
if %i{when free_when for}.include?((wh = t.parent).kind) && t == wh.argEnd
|
|
848
|
+
if wh.dnext.kind == :> && (whv = wh.dnext.dnext).var_able?
|
|
849
|
+
cs = wh.case
|
|
850
|
+
cs.requireIfConversion = true
|
|
851
|
+
wh.ifConverted = true
|
|
852
|
+
cmp = -> r, ord, head do
|
|
853
|
+
Token.addMod r, head + " _____case_comp_insert_var(#{whv.str} = :#{whv.str}, #{ord}, "
|
|
854
|
+
end
|
|
855
|
+
cmp.(wh.first ... whv.last, 0, "")
|
|
856
|
+
(cms = wh.argCommas).each_with_index do |cm, ord|
|
|
857
|
+
cmp.(cm.range, ord + 1, "), ")
|
|
858
|
+
end
|
|
859
|
+
Token.addMod wh.argEnd.first, ")"
|
|
860
|
+
end
|
|
861
|
+
wh.eachArgs do |a|
|
|
862
|
+
if a.kind == :lbrace_clause || (a.kind == :on_lbrace && a.next.kind != :on_label && a.maybeRightMatch? && a.kind = :lbrace_clause)
|
|
863
|
+
Token.addMod a.first, "->#{a.spVarName}" # dummy argument for lambda
|
|
864
|
+
end
|
|
865
|
+
end
|
|
866
|
+
end
|
|
867
|
+
case t.kind
|
|
868
|
+
when :on_semicolon
|
|
869
|
+
if t.parent.kind == :on_lbrace
|
|
870
|
+
t.parent.kind = :lbrace_clause
|
|
871
|
+
end
|
|
872
|
+
when :and, :or, :not
|
|
873
|
+
if [:on_lbracket, :on_lparen].include?(t.parent)
|
|
874
|
+
t.parent.hasAndOp = true
|
|
875
|
+
end
|
|
876
|
+
when :on_ivar
|
|
877
|
+
if t.str == "@"
|
|
878
|
+
t.eachParent do |par|
|
|
879
|
+
case par.kind
|
|
880
|
+
when :on_lbrace
|
|
881
|
+
if %{for free_when when}.include? par.parent.kind
|
|
882
|
+
if %i{on_comma for free_for free_when when}.include? :on_comma
|
|
883
|
+
|
|
884
|
+
end
|
|
885
|
+
end
|
|
886
|
+
when
|
|
887
|
+
if %{case free_case}.include? par.kind
|
|
888
|
+
|
|
889
|
+
par.spVarName
|
|
890
|
+
end
|
|
891
|
+
end
|
|
892
|
+
end
|
|
893
|
+
when :on_comma
|
|
894
|
+
case t.parent
|
|
895
|
+
when :on_lparen, :on_lbrace
|
|
896
|
+
if !t.parent.iteratorCand
|
|
897
|
+
t.parent.setComma t
|
|
898
|
+
end
|
|
899
|
+
when :on_lbrace
|
|
900
|
+
if !t.parent.iteratorCand
|
|
901
|
+
t.parent.setComma t
|
|
902
|
+
if t.parent.firstRightAssign
|
|
903
|
+
t.parent.maybeRightMatch = true
|
|
904
|
+
end
|
|
905
|
+
end
|
|
906
|
+
end
|
|
907
|
+
when :on_period
|
|
908
|
+
if t.isOperand? # should not be parent
|
|
909
|
+
if [:on_ident, :on_const].include?(t.next_meaningful.kind)
|
|
910
|
+
Token.addMod(t.first, "___theme_by_period")
|
|
911
|
+
elsif ambiguousPeriodTheme?
|
|
912
|
+
raise Error.new("Nested theme is referenced by single '.'")
|
|
913
|
+
else
|
|
914
|
+
Token.addMod(t.range, "___theme_by_period")
|
|
915
|
+
end
|
|
916
|
+
end
|
|
917
|
+
when :|
|
|
918
|
+
if [:do, :on_lbrace].include?(t.prev_non_sp) && t.parent == t.prev_non_sp
|
|
919
|
+
if t.parent == :on_lbrace
|
|
920
|
+
t.parent = :lbrace_clause
|
|
921
|
+
end
|
|
922
|
+
t.implementOpener
|
|
923
|
+
t.spush
|
|
924
|
+
elsif t.parent.kind == :|
|
|
925
|
+
t.spop
|
|
926
|
+
else
|
|
927
|
+
raise Error.new("unclosed iterator arg")
|
|
928
|
+
end
|
|
929
|
+
when :on_lambeg
|
|
930
|
+
if t.parent.kind == :on_tlambda && !t.parent.body
|
|
931
|
+
t.parent.setBody t
|
|
932
|
+
end
|
|
933
|
+
when :on_lparen, :on_lbracket,
|
|
934
|
+
:on_regexp_beg, :on_backtick, :on_embexpr_beg,
|
|
935
|
+
:on_tstring_beg, :on_qwords_beg,:on_words_beg, :on_symbeg, :on_qsymbols_beg, :on_symbols_beg
|
|
936
|
+
t.spush
|
|
937
|
+
when :on_rparen, :on_rbracket, :on_rbrace, :on_embexpr_end
|
|
938
|
+
first = true
|
|
939
|
+
if !t.parent.opponent?(t)
|
|
940
|
+
toInsert = ""
|
|
941
|
+
while t.parent.isStarter?
|
|
942
|
+
toInsert = (!t.parent.requireArg? ? ' ' : ?;) + "end" + toInsert
|
|
943
|
+
t.spop
|
|
944
|
+
end
|
|
945
|
+
if !t.parent.opponent?(t)
|
|
946
|
+
raise Error.new("#{t.parent.str()} is not closed")
|
|
947
|
+
end
|
|
948
|
+
if !toInsert.empty?
|
|
949
|
+
@expr[t.range] = toInsert + @expr[t.range]
|
|
950
|
+
raise Restart.new
|
|
951
|
+
end
|
|
952
|
+
end
|
|
953
|
+
t.spop
|
|
954
|
+
case t.kind
|
|
955
|
+
when :on_rparen, :on_rbracket
|
|
956
|
+
t.beginner.checkAndOp
|
|
957
|
+
when :on_rbrace
|
|
958
|
+
if t.beginner.kind == :hash_beg
|
|
959
|
+
Token.addMod t.beginner.first, " ("
|
|
960
|
+
Token.addMod t.last, ")"
|
|
961
|
+
end
|
|
962
|
+
if t.cur.parStack.size == 0 && RBRACE_MODE.include?(ebmode)
|
|
963
|
+
if ebmode == :bare
|
|
964
|
+
if AdhocLiterals[:url]
|
|
965
|
+
checkUrl t.first do |led|
|
|
966
|
+
yield t.first, :url #back track
|
|
967
|
+
end
|
|
968
|
+
end
|
|
969
|
+
if AdhocLiterals[:email]
|
|
970
|
+
checkEmail t.first do |led|
|
|
971
|
+
yield t.first, :email #back track
|
|
972
|
+
end
|
|
973
|
+
end
|
|
974
|
+
if AdhocLiterals[:path]
|
|
975
|
+
checkPath t.first do |led, pstack|
|
|
976
|
+
yield t.first, :path, led, pstack #back track
|
|
977
|
+
end
|
|
978
|
+
end
|
|
979
|
+
else
|
|
980
|
+
yield t.first, emode
|
|
981
|
+
end
|
|
982
|
+
# do not return : raise Restart.new
|
|
983
|
+
elsif [:on_lbrace, :lbrace_clause].include? t.beginner.kind # check iterator
|
|
984
|
+
if [:"&.", :on_period, :"::"].include?((tbp = t.beginner.prev).kind)
|
|
985
|
+
tbp.closeBeginner t
|
|
986
|
+
#if (tbpp = tbp.prev).kind == :on_rparen && (tbppb = tbpp.beginner).isOperand?
|
|
987
|
+
# # foo (a,b,c)::{...} -> foo ___theme(a,b,c){...}
|
|
988
|
+
# if tbp.kind == :"&." && tbpp.beginner.multiArgument?
|
|
989
|
+
# raise Error.new("multiple theme for '&.' operator is not allowed")
|
|
990
|
+
# end
|
|
991
|
+
# Token.addMod tbppb.first, themeExpr.(tbp)
|
|
992
|
+
# Token.addMod tbp.range, ""
|
|
993
|
+
#else
|
|
994
|
+
# # foo(a,b,c)::{...} -> foo(a,b,c)::___theme{...}
|
|
995
|
+
# Token.addMod t.beginner.first, themeExpr.(tbp)
|
|
996
|
+
# # lexical tree analysis with [], ||, &&, ?:, override output
|
|
997
|
+
#end
|
|
998
|
+
else
|
|
999
|
+
case (tt = t.beginner.prev).kind
|
|
1000
|
+
when :on_rparen
|
|
1001
|
+
case (ttt = tt.beginner.prev).kind
|
|
1002
|
+
when :"&.", :on_period # foo&.(...){...}, foo.(...){...}
|
|
1003
|
+
######## (Table1, Table2)::{....}
|
|
1004
|
+
t.beginner.iterator_method = ttt
|
|
1005
|
+
# &.(...){...} -> NG
|
|
1006
|
+
# .(...){...} -> OK
|
|
1007
|
+
when :"::" #foo::(...){...}
|
|
1008
|
+
raise Error.new("foo::(...){...} is not implemented")
|
|
1009
|
+
else
|
|
1010
|
+
unless t.beginner.iterator_method = ttt.trySetupIterator(:back, t.beginner.argEnd, t) # foo:label(...){...}
|
|
1011
|
+
raise Error.new("cannot find iterator method like 'foo' in 'foo(...){...}'") # foo(...){...}
|
|
1012
|
+
end
|
|
1013
|
+
end
|
|
1014
|
+
# foo'(...){...}
|
|
1015
|
+
# foo"(...){...}
|
|
1016
|
+
# foo."(...)(...){...}
|
|
1017
|
+
# .(...){...}
|
|
1018
|
+
when :on_rbracket
|
|
1019
|
+
t.beginner.iterator_method = tt.beginner # a[...]{...} ':[]' is iterator method
|
|
1020
|
+
else
|
|
1021
|
+
t.beginner.iterator_method = tt.trySetupIterator(:back, t.beginner.argEnd, t) # foo:label{...}
|
|
1022
|
+
raise Error.new("cannot find iterator method like 'foo' in 'foo{...}'") # foo {...}
|
|
1023
|
+
end
|
|
1024
|
+
end
|
|
1025
|
+
end
|
|
1026
|
+
end
|
|
1027
|
+
end
|
|
1028
|
+
when :on_heredoc_end
|
|
1029
|
+
t.spop
|
|
1030
|
+
when :on_tstring_end
|
|
1031
|
+
case t.parent.kind
|
|
1032
|
+
when :on_tstring_beg
|
|
1033
|
+
Token.addmod t.range, SET_LINE
|
|
1034
|
+
t.spop
|
|
1035
|
+
when :on_qwords_beg,:on_words_beg, :on_symbeg, :on_qsymbols_beg, :on_symbols_beg, :on_backtick
|
|
1036
|
+
t.spop
|
|
1037
|
+
else
|
|
1038
|
+
raise Error.new("ERROR: String content closing at #{t.pos} is missing beginning\n")
|
|
1039
|
+
end
|
|
1040
|
+
if t.cur.parStack.size == 0 && mode.to_s =~ /_quote$/
|
|
1041
|
+
yield t.first # do not return : raise Retart.new
|
|
1042
|
+
end
|
|
1043
|
+
when :on_label_end
|
|
1044
|
+
if t.parent.kind == :on_tstring_beg
|
|
1045
|
+
t.spop
|
|
1046
|
+
else
|
|
1047
|
+
raise Error.new("ERROR: String content closing at #{t.pos} is missing beginning\n")
|
|
1048
|
+
end
|
|
1049
|
+
when :on_regexp_end
|
|
1050
|
+
if t.parent.kind == :on_regexp_beg
|
|
1051
|
+
t.spop
|
|
1052
|
+
else
|
|
1053
|
+
raise Error.new("ERROR: Reglar expression closing at #{t.pos} is missing beginning\n")
|
|
1054
|
+
end
|
|
1055
|
+
end
|
|
1056
|
+
# check Starters status
|
|
1057
|
+
h = t.parent
|
|
1058
|
+
if h.requireArg?
|
|
1059
|
+
if !h.argStart
|
|
1060
|
+
case t.kind
|
|
1061
|
+
when :on_semicolon, :on_nl
|
|
1062
|
+
if defined?(Endless) || t.kind == :on_semicolon
|
|
1063
|
+
if h.in
|
|
1064
|
+
raise Error.new("missing argument for 'in'")
|
|
1065
|
+
else
|
|
1066
|
+
case h.kind
|
|
1067
|
+
when *%i{if elsif unless while until on_tlambda post_test_while post_test_until \\ =}
|
|
1068
|
+
raise Error.new("missing argument for '#{h.str}'")
|
|
1069
|
+
when :case
|
|
1070
|
+
if !defined?(ArglessCase)
|
|
1071
|
+
raise Error.new("missing argument for '#{h.str}'")
|
|
1072
|
+
end
|
|
1073
|
+
when :for
|
|
1074
|
+
if !h.trySetUnderCase
|
|
1075
|
+
raise Error.new("new line or semicolon is not allowed after 'for' arguments")
|
|
1076
|
+
end
|
|
1077
|
+
else
|
|
1078
|
+
case h.parent.wrapped.orgEntity.kind
|
|
1079
|
+
when :case #traditional case, when, in
|
|
1080
|
+
raise Error.new("missing argument for '#{h.str}' of traditional style 'case'")
|
|
1081
|
+
when :in, :for, :when # free case when, in, for without argument
|
|
1082
|
+
end
|
|
1083
|
+
end
|
|
1084
|
+
end
|
|
1085
|
+
end
|
|
1086
|
+
h.argEnd = t # :rescue is unconditionally close argument
|
|
1087
|
+
when :in
|
|
1088
|
+
if h.kind == :for
|
|
1089
|
+
raise Error.new("missing argument for '#{h.str}' before 'in'")
|
|
1090
|
+
else # in without for
|
|
1091
|
+
h.argEnd = t
|
|
1092
|
+
end
|
|
1093
|
+
when :on_lambeg, :do
|
|
1094
|
+
if h.kind == :on_tlambda
|
|
1095
|
+
h.argEnd = t
|
|
1096
|
+
end
|
|
1097
|
+
when :"=" # one line method # def a(x,y) = x * y
|
|
1098
|
+
if defined?(Endless)
|
|
1099
|
+
if t.prev.kind == :on_lparen && t.prev.beginner.prev == :def
|
|
1100
|
+
h.changeEntity t
|
|
1101
|
+
end
|
|
1102
|
+
else
|
|
1103
|
+
if t.prev_non_sp.kind == :on_lparen && t.prev_non_sp.beginner.prev_non_sp.kind == :def
|
|
1104
|
+
h.changeEntity t
|
|
1105
|
+
end
|
|
1106
|
+
end
|
|
1107
|
+
else
|
|
1108
|
+
if t.realToken?
|
|
1109
|
+
h.argStart ||= t
|
|
1110
|
+
end
|
|
1111
|
+
end
|
|
1112
|
+
else
|
|
1113
|
+
if t.kind == :in && h.kind == :for
|
|
1114
|
+
h.setIn t #argEnd is also set with this method
|
|
1115
|
+
elsif t.kind == :on_semicolon || t.kind == :on_nl
|
|
1116
|
+
case h.kind
|
|
1117
|
+
when :for
|
|
1118
|
+
if !t.in?
|
|
1119
|
+
if t.trySetUnderCase
|
|
1120
|
+
t.kind = :free_for
|
|
1121
|
+
else
|
|
1122
|
+
raise Error.new("new line or semicolon is not allowed after 'for' arguments")
|
|
1123
|
+
end
|
|
1124
|
+
end
|
|
1125
|
+
when :on_tlambda
|
|
1126
|
+
if !defined?(Endless) || t.kind == :on_semicolon
|
|
1127
|
+
raise Error.new("new line or semicolon is not allowed after '->' arguments")
|
|
1128
|
+
end
|
|
1129
|
+
when :"="
|
|
1130
|
+
t.spop
|
|
1131
|
+
when :post_test_while, :post_test_until
|
|
1132
|
+
postTestFinalize t
|
|
1133
|
+
end
|
|
1134
|
+
h.argEnd = t
|
|
1135
|
+
elsif [:when, :in].include?(t.kind) && h.wrapped.orgEntity.kind == :case \ # case foo in goo (same line)
|
|
1136
|
+
|| t.kind == :then && [:if, :elsif, :unless, :in, :when, :rescue].include?(h.kind) \
|
|
1137
|
+
|| t.kind == :do && \
|
|
1138
|
+
( (h.kind == :for && h.in) \
|
|
1139
|
+
|| [:until, :while].include?(h.kind) \
|
|
1140
|
+
|| h.kind == :on_tlambda
|
|
1141
|
+
)
|
|
1142
|
+
h.argEnd = t
|
|
1143
|
+
elsif t.kind == :on_lbrace && h.kind == :on_tlambda
|
|
1144
|
+
h.argEnd = t
|
|
1145
|
+
end
|
|
1146
|
+
end
|
|
1147
|
+
end
|
|
1148
|
+
#check starters
|
|
1149
|
+
case t.kind
|
|
1150
|
+
when :"\\" #onSetKind
|
|
1151
|
+
if t.prev_non_sp.continues? || t.isSentenceHead?
|
|
1152
|
+
t.spush # without method
|
|
1153
|
+
else
|
|
1154
|
+
if (t.iteratorMethod = t.parent&.iteratorCand)&.setupIteratorLabel
|
|
1155
|
+
t.parent.iteratorCand = nil
|
|
1156
|
+
t.spush
|
|
1157
|
+
else
|
|
1158
|
+
raise Error.new("cannot find iterator method")
|
|
1159
|
+
end
|
|
1160
|
+
end
|
|
1161
|
+
when :then #checkStarter
|
|
1162
|
+
if t.parent&.thenRelated?(t.prev_non_sp)
|
|
1163
|
+
t.parent.setThen t
|
|
1164
|
+
elsif defined?(Ifless) && defined?(Endless) && t.prev_nl?
|
|
1165
|
+
t.spush
|
|
1166
|
+
t.kind = :ifless_then
|
|
1167
|
+
else
|
|
1168
|
+
raise Error.new("orphan then")
|
|
1169
|
+
end
|
|
1170
|
+
when :on_tlambda #onSetKind
|
|
1171
|
+
t.spush
|
|
1172
|
+
when :do #onSetKind
|
|
1173
|
+
if !t.prev_non_sp.continues? && t.parent&.doRelated?
|
|
1174
|
+
t.parent.setDo t
|
|
1175
|
+
elsif !t.prev_non_sp.continues? && t.parent.kind = :on_tlambda && !t.parent.body
|
|
1176
|
+
t.parent.setBody t
|
|
1177
|
+
else
|
|
1178
|
+
if !t.prev_non_sp.continues? && !t.isSentenceHead?
|
|
1179
|
+
if t.iteratorMethod = t.parent&.iteratorCand
|
|
1180
|
+
# omit "t.parent.iteratorCand = nil" 'cause maybe :post_test_while, not iterator
|
|
1181
|
+
else
|
|
1182
|
+
raise Error.new("cannot find iterator method")
|
|
1183
|
+
end
|
|
1184
|
+
end
|
|
1185
|
+
t.spush
|
|
1186
|
+
end
|
|
1187
|
+
when :else
|
|
1188
|
+
if t.continuedClause?
|
|
1189
|
+
t.parent.clauseElse t
|
|
1190
|
+
elsif defined?(Ifless) && defined?(Endless) && t.prev_nl?
|
|
1191
|
+
t.spush
|
|
1192
|
+
t.kind = :ifless_else
|
|
1193
|
+
else
|
|
1194
|
+
raise Error.new("orphan else")
|
|
1195
|
+
end
|
|
1196
|
+
when :elsif
|
|
1197
|
+
if t.continuedClause?
|
|
1198
|
+
t.clauseElsif t
|
|
1199
|
+
elsif defined?(Ifless) && defined?(Endless) && t.prev_nl?
|
|
1200
|
+
t.spush
|
|
1201
|
+
t.kind = :ifless_elsif
|
|
1202
|
+
else
|
|
1203
|
+
raise Error.new("orphan elsif")
|
|
1204
|
+
end
|
|
1205
|
+
when :if, :unless, :case, :module, :begin, :for, :def
|
|
1206
|
+
t.spush
|
|
1207
|
+
when :class
|
|
1208
|
+
mth = t.findParent{%i{module class def origin}.include? _1.kind}
|
|
1209
|
+
if defined?(Endless)
|
|
1210
|
+
n = t.next
|
|
1211
|
+
else
|
|
1212
|
+
n = t.next_non_sp
|
|
1213
|
+
end
|
|
1214
|
+
if (if mth.kind == :def
|
|
1215
|
+
n.kind == :<<
|
|
1216
|
+
else
|
|
1217
|
+
%i{<< on_const ::}.include? n.kind
|
|
1218
|
+
end)
|
|
1219
|
+
then
|
|
1220
|
+
t.spush # singleton class
|
|
1221
|
+
else
|
|
1222
|
+
t.kind = :on_ident
|
|
1223
|
+
Token.addMod t.pos, "self."
|
|
1224
|
+
end
|
|
1225
|
+
when :in
|
|
1226
|
+
if t.continuedClause?
|
|
1227
|
+
if t.parent.kind == :case
|
|
1228
|
+
t.parent.clauseIn t
|
|
1229
|
+
elsif t.parent.kind == :in
|
|
1230
|
+
if t.parent.argEnd
|
|
1231
|
+
t.parent.clauseIn t
|
|
1232
|
+
else
|
|
1233
|
+
# right assignment 'in'
|
|
1234
|
+
end
|
|
1235
|
+
end
|
|
1236
|
+
elsif t.parent&.kind == :for && t.cur.idtStack.last == t.parent
|
|
1237
|
+
t.parent.setIn t
|
|
1238
|
+
else
|
|
1239
|
+
if t.isSentenceHead?
|
|
1240
|
+
if defined?(FreeCase) && t.trySetUnderCase
|
|
1241
|
+
t.kind = :free_in
|
|
1242
|
+
t.spush
|
|
1243
|
+
else
|
|
1244
|
+
raise Error.new("orphan in")
|
|
1245
|
+
end
|
|
1246
|
+
else
|
|
1247
|
+
# right assignment 'in'
|
|
1248
|
+
end
|
|
1249
|
+
end
|
|
1250
|
+
when :when
|
|
1251
|
+
if t.continuedClause?
|
|
1252
|
+
t.parent.clauseWhen t
|
|
1253
|
+
else
|
|
1254
|
+
if defined?(FreeCase) && t.trySetUnderCase
|
|
1255
|
+
t.kind = :free_when
|
|
1256
|
+
t.spush
|
|
1257
|
+
else
|
|
1258
|
+
raise Error.new("orphan when")
|
|
1259
|
+
end
|
|
1260
|
+
end
|
|
1261
|
+
when :rescue
|
|
1262
|
+
if t.continuedClause?
|
|
1263
|
+
t.parent.clauseRescue t
|
|
1264
|
+
else #independent rescue
|
|
1265
|
+
if defined?(IndependentRescue)
|
|
1266
|
+
t.spush
|
|
1267
|
+
else
|
|
1268
|
+
raise Error.new("found orphan 'rescue'")
|
|
1269
|
+
end
|
|
1270
|
+
end
|
|
1271
|
+
when :ensure
|
|
1272
|
+
if t.continuedClause?
|
|
1273
|
+
t.parent.clauseEnsure t
|
|
1274
|
+
else #independent ensure
|
|
1275
|
+
if defined?(IndependentEnsure)
|
|
1276
|
+
t.spush
|
|
1277
|
+
else
|
|
1278
|
+
raise Error.new("found orphan 'ensure'")
|
|
1279
|
+
end
|
|
1280
|
+
end
|
|
1281
|
+
when :end
|
|
1282
|
+
if t.continuedClause?
|
|
1283
|
+
Token.addMod t.range, t.parent.wrapped.orgEntity.closeBeginner(t)
|
|
1284
|
+
t.spop
|
|
1285
|
+
else
|
|
1286
|
+
raise Error.new("found extra end")
|
|
1287
|
+
end
|
|
1288
|
+
############ remove below #############
|
|
1289
|
+
case t.parent.kind
|
|
1290
|
+
when :case, :free_case
|
|
1291
|
+
finalizeCase(t.parent, t)
|
|
1292
|
+
when :ensure
|
|
1293
|
+
finalizeFreeEnsure.(t.parent)
|
|
1294
|
+
when :rescue
|
|
1295
|
+
finalizeFreeRescue.(t.parent)
|
|
1296
|
+
else
|
|
1297
|
+
if t.parent.isIflessStarter?
|
|
1298
|
+
finalizeIfless(t.parent)
|
|
1299
|
+
elsif t.continuedClause?
|
|
1300
|
+
# protect over pop indentation
|
|
1301
|
+
case (lo = t.parent.wrapped.orgEntity).kind # without iterator method information 'cause may start post test while or until
|
|
1302
|
+
when :do ########### do"
|
|
1303
|
+
if c = lo.parent.iteratorCand
|
|
1304
|
+
if lo.iteratorMethod = c.trySetupIterator :preset, lo, t
|
|
1305
|
+
lo.parent.iteratorCand = nil
|
|
1306
|
+
end
|
|
1307
|
+
else
|
|
1308
|
+
case lop = lo.prev
|
|
1309
|
+
when :on_rbracket
|
|
1310
|
+
lo.iteratorMethod = lop.beginner
|
|
1311
|
+
when :on_rparen
|
|
1312
|
+
tt = lop.beginner.prev
|
|
1313
|
+
lo.iteratorMethod = tt.trySetupIterator :back, lo, t
|
|
1314
|
+
end
|
|
1315
|
+
end
|
|
1316
|
+
if !lo.iteratorMethod
|
|
1317
|
+
raise Error.new("cannot find iterator method identifier for 'do'")
|
|
1318
|
+
end
|
|
1319
|
+
when :until, :while
|
|
1320
|
+
lo.trySetupIterator :forward, lo, t
|
|
1321
|
+
when :then, :else, :elsif # ifless
|
|
1322
|
+
finalizeIfless t
|
|
1323
|
+
end
|
|
1324
|
+
t.spop
|
|
1325
|
+
else
|
|
1326
|
+
raise Error.new("found extra end")
|
|
1327
|
+
end
|
|
1328
|
+
end
|
|
1329
|
+
when :while, :until
|
|
1330
|
+
if t.parent.kind == :do && !t.parent.iteratorCand && defined?(PostTestDo)
|
|
1331
|
+
t.parent.setPostTest t
|
|
1332
|
+
else
|
|
1333
|
+
t.spush
|
|
1334
|
+
end
|
|
1335
|
+
end
|
|
1336
|
+
#check label
|
|
1337
|
+
if t.kind == :on_label &&
|
|
1338
|
+
if (t.str == "do:") ||
|
|
1339
|
+
(["while:", "until:"].include?(t.str) && ([:on_nl, :on_semicolon].include?(t.dprev.prev.kind) || t.dprev.prev.continues?))
|
|
1340
|
+
|
|
1341
|
+
if t.maybeIteratorLabel? true
|
|
1342
|
+
# NG do:label [,):};\n]
|
|
1343
|
+
# NG do:label ^ foo # cannot be interpreted as unary operator
|
|
1344
|
+
# OK do:label ! foo # unary operator
|
|
1345
|
+
# OK do:label + 1 # interpreted as unary operator
|
|
1346
|
+
# do not need check :post_test_do because 'do ... while:label cond' is not allowed
|
|
1347
|
+
t.setupIteratorLabel
|
|
1348
|
+
t.spush
|
|
1349
|
+
end
|
|
1350
|
+
end
|
|
1351
|
+
end
|
|
1352
|
+
allTokens.push t
|
|
1353
|
+
end
|
|
1354
|
+
rescue Restart
|
|
1355
|
+
allTokens.clear
|
|
1356
|
+
@restarted = true
|
|
1357
|
+
retry
|
|
1358
|
+
rescue StopIteration
|
|
1359
|
+
end
|
|
1360
|
+
if mode
|
|
1361
|
+
if mode.to_s =~ /_quote$/
|
|
1362
|
+
raise Error.new("cannot find closing end of quotation")
|
|
1363
|
+
else
|
|
1364
|
+
raise Error.new("cannot find closing end of brace")
|
|
1365
|
+
end
|
|
1366
|
+
end
|
|
1367
|
+
end
|
|
1368
|
+
attr_reader :pos, :kind, :str, :stat, :restarted
|
|
1369
|
+
def self.translate opts, expr, f, lno
|
|
1370
|
+
new expr, opts, f, lno
|
|
1371
|
+
end
|
|
1372
|
+
end
|
|
1373
|
+
|
|
1374
|
+
|
|
1375
|
+
|
|
1376
|
+
|
|
1377
|
+
|
|
1378
|
+
|
|
1379
|
+
|
|
1380
|
+
|
|
1381
|
+
|
|
1382
|
+
|