packcr 0.0.4 → 0.0.6

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 (75) hide show
  1. checksums.yaml +4 -4
  2. data/exe/packcr +3 -0
  3. data/lib/packcr/broadcast.rb +17 -0
  4. data/lib/packcr/cli.rb +25 -0
  5. data/lib/packcr/code_block.rb +2 -3
  6. data/lib/packcr/context.rb +59 -56
  7. data/lib/packcr/generator.rb +13 -11
  8. data/lib/packcr/node/action_node.rb +14 -5
  9. data/lib/packcr/node/alternate_node.rb +20 -12
  10. data/lib/packcr/node/capture_node.rb +11 -11
  11. data/lib/packcr/node/charclass_node.rb +37 -13
  12. data/lib/packcr/node/eof_node.rb +23 -0
  13. data/lib/packcr/node/error_node.rb +17 -12
  14. data/lib/packcr/node/expand_node.rb +11 -5
  15. data/lib/packcr/node/predicate_node.rb +15 -24
  16. data/lib/packcr/node/quantity_node.rb +23 -18
  17. data/lib/packcr/node/reference_node.rb +21 -5
  18. data/lib/packcr/node/root_node.rb +60 -0
  19. data/lib/packcr/node/rule_node.rb +26 -3
  20. data/lib/packcr/node/sequence_node.rb +46 -31
  21. data/lib/packcr/node/string_node.rb +12 -12
  22. data/lib/packcr/node.rb +35 -4
  23. data/lib/packcr/parser.rb +2939 -2661
  24. data/lib/packcr/stream.rb +8 -13
  25. data/lib/packcr/templates/context/header.c.erb +29 -0
  26. data/lib/packcr/templates/context/source.c.erb +1292 -0
  27. data/lib/packcr/templates/context/source.rb.erb +406 -0
  28. data/lib/packcr/templates/node/action.c.erb +16 -0
  29. data/lib/packcr/templates/node/action.rb.erb +21 -0
  30. data/lib/packcr/templates/node/alternate.c.erb +34 -0
  31. data/lib/packcr/templates/node/alternate.rb.erb +40 -0
  32. data/lib/packcr/templates/node/capture.c.erb +17 -0
  33. data/lib/packcr/templates/node/capture.rb.erb +14 -0
  34. data/lib/packcr/templates/node/charclass.c.erb +47 -0
  35. data/lib/packcr/templates/node/charclass.rb.erb +49 -0
  36. data/lib/packcr/templates/node/charclass_any.c.erb +5 -0
  37. data/lib/packcr/templates/node/charclass_any.rb.erb +7 -0
  38. data/lib/packcr/templates/node/charclass_fail.c.erb +1 -0
  39. data/lib/packcr/templates/node/charclass_fail.rb.erb +1 -0
  40. data/lib/packcr/templates/node/charclass_one.c.erb +19 -0
  41. data/lib/packcr/templates/node/charclass_one.rb.erb +23 -0
  42. data/lib/packcr/templates/node/charclass_utf8.c.erb +49 -0
  43. data/lib/packcr/templates/node/charclass_utf8.rb.erb +50 -0
  44. data/lib/packcr/templates/node/charclass_utf8_reverse.rb.erb +51 -0
  45. data/lib/packcr/templates/node/eof.c.erb +1 -0
  46. data/lib/packcr/templates/node/eof.rb.erb +3 -0
  47. data/lib/packcr/templates/node/error.c.erb +28 -0
  48. data/lib/packcr/templates/node/error.rb.erb +34 -0
  49. data/lib/packcr/templates/node/expand.c.erb +16 -0
  50. data/lib/packcr/templates/node/expand.rb.erb +16 -0
  51. data/lib/packcr/templates/node/predicate.c.erb +30 -0
  52. data/lib/packcr/templates/node/predicate.rb.erb +28 -0
  53. data/lib/packcr/templates/node/predicate_neg.c.erb +23 -0
  54. data/lib/packcr/templates/node/predicate_neg.rb.erb +22 -0
  55. data/lib/packcr/templates/node/quantify_many.c.erb +45 -0
  56. data/lib/packcr/templates/node/quantify_many.rb.erb +47 -0
  57. data/lib/packcr/templates/node/quantify_one.c.erb +21 -0
  58. data/lib/packcr/templates/node/quantify_one.rb.erb +23 -0
  59. data/lib/packcr/templates/node/reference.c.erb +5 -0
  60. data/lib/packcr/templates/node/reference.rb.erb +9 -0
  61. data/lib/packcr/templates/node/reference_reverse.rb.erb +9 -0
  62. data/lib/packcr/templates/node/rule.c.erb +19 -0
  63. data/lib/packcr/templates/node/rule.rb.erb +23 -0
  64. data/lib/packcr/templates/node/sequence.c.erb +12 -0
  65. data/lib/packcr/templates/node/sequence.rb.erb +12 -0
  66. data/lib/packcr/templates/node/string_many.c.erb +11 -0
  67. data/lib/packcr/templates/node/string_many.rb.erb +10 -0
  68. data/lib/packcr/templates/node/string_one.c.erb +8 -0
  69. data/lib/packcr/templates/node/string_one.rb.erb +10 -0
  70. data/lib/packcr/tokenizer.rb +2948 -0
  71. data/lib/packcr/util.rb +0 -8
  72. data/lib/packcr/version.rb +1 -1
  73. data/lib/packcr.rb +1 -2
  74. metadata +87 -8
  75. data/lib/packcr/buffer.rb +0 -47
@@ -0,0 +1,406 @@
1
+ # A packrat parser generated by PackCR <%= Packcr::VERSION %>
2
+ <%- if !code(:source).empty? -%>
3
+
4
+ <%- code(:source).each do |code| -%>
5
+ <%= stream.get_code_block(code, 0, @iname) -%>
6
+ <%- end -%>
7
+ <%- end -%>
8
+
9
+ class <%= class_name %>
10
+ def initialize(<% if @auxil_type %><%= auxil_type %>, <% end %>debug: false)
11
+ <%- if @utf8 -%>
12
+ @buffer = +""
13
+ <%- else -%>
14
+ @buffer = +"".b
15
+ <%- end %>
16
+ @pos = 0
17
+ @cur = 0
18
+ @level = 0
19
+ @lrstack = []
20
+ @thunk = ThunkNode.new([], nil, 0)
21
+ @heads = {}
22
+ @memos = LrMemoTable.new
23
+ @debug = debug
24
+ @global_values = {}
25
+ <%- if @location -%>
26
+ @pos_loc = Location.new
27
+ @cur_loc = Location.new
28
+ <%- end -%>
29
+ <%- code(:init).each do |code| -%>
30
+ <%- %><%= stream.get_code_block(code, 4, @iname) -%>
31
+ <%- end -%>
32
+ end
33
+
34
+ def debug
35
+ yield if @debug
36
+ end
37
+
38
+ def getc
39
+ <%- if @utf8 -%>
40
+ $stdin.getc
41
+ <%- else -%>
42
+ $stdin.getc&.b
43
+ <%- end -%>
44
+ end
45
+
46
+ def refill_buffer(num, mode = nil)
47
+ len = @buffer.length
48
+ if len >= @cur + num
49
+ return len - @cur
50
+ end
51
+ while len < @cur + num
52
+ c = getc
53
+ break if !c
54
+ @buffer << c
55
+ len = @buffer.length
56
+ end
57
+ return len - @cur
58
+ end
59
+
60
+ def commit_buffer
61
+ @buffer = @buffer[@cur, @buffer.length - @cur]
62
+ @pos += @cur
63
+ @heads.clear
64
+ @memos.clear
65
+ @cur = 0
66
+ <%- if @location -%>
67
+ @pos_loc = @pos_loc + @cur_loc
68
+ @cur_loc = Location.new
69
+ <%- end -%>
70
+ end
71
+
72
+ def parse
73
+ pos = @pos
74
+ <%- if !@root.rules.empty? -%>
75
+ if apply_rule(:evaluate_rule_<%= @root.rules[0].name %>, @thunk.thunks, nil, 0)
76
+ @thunk.do_action(self, nil, 0)
77
+ else
78
+ raise SyntaxError, "can't parse"
79
+ end
80
+ commit_buffer
81
+ <%- end -%>
82
+ @thunk.clear
83
+ refill_buffer(1) >= 1 && pos != @pos
84
+ end
85
+
86
+ def run
87
+ nil while parse
88
+ end
89
+
90
+ <%- @root.rules.each do |rule| -%>
91
+ <%- rule.codes.each do |code| -%>
92
+ def action_<%= rule.name %>_<%= code.index %>(__pcc_in, __pcc_vars, __pcc_index)
93
+ ____ = (__pcc_vars[__pcc_index] ||= Value.new).value if __pcc_vars
94
+ <%- code.vars.each do |ref| -%>
95
+ <%= ref.var %> = (__pcc_in.value_refs[<%= ref.index %>] ||= Value.new).value
96
+ <%- end -%>
97
+ __0 = __pcc_in.capt0.capture_string(@buffer)
98
+ __0s = @pos + __pcc_in.capt0.range_start
99
+ __0e = @pos + __pcc_in.capt0.range_end
100
+ <%- if @location -%>
101
+ __0sl = @pos_loc + __pcc_in.capt0.start_loc
102
+ __0el = @pos_loc + __pcc_in.capt0.end_loc
103
+ <%- end -%>
104
+ <%- if @capture_in_code -%>
105
+ __0c = __pcc_in.capt0
106
+ <%- end -%>
107
+ <%- code.capts.each do |capture| -%>
108
+ __<%= capture.index + 1 %> = __pcc_in.capts[<%= capture.index %>].capture_string(@buffer)
109
+ __<%= capture.index + 1 %>s = @pos + __pcc_in.capts[<%= capture.index %>].range_start
110
+ __<%= capture.index + 1 %>e = @pos + __pcc_in.capts[<%= capture.index %>].range_end
111
+ <%- if @location -%>
112
+ __<%= capture.index + 1 %>sl = @pos_loc + __pcc_in.capts[<%= capture.index %>].start_loc
113
+ __<%= capture.index + 1 %>el = @pos_loc + __pcc_in.capts[<%= capture.index %>].end_loc
114
+ <%- end -%>
115
+ <%- if @capture_in_code -%>
116
+ __<%= capture.index + 1 %>c = __pcc_in.capts[<%= capture.index %>]
117
+ <%- end -%>
118
+ <%- end -%>
119
+ <%- %><%= stream.get_code_block(code.code, 4, @iname) -%>
120
+
121
+ __pcc_vars[__pcc_index].value = ____ if __pcc_vars
122
+ end
123
+
124
+ <%- end -%>
125
+ <%- end -%>
126
+ <%- @root.rules.each do |rule| -%>
127
+ def evaluate_rule_<%= rule.name %>
128
+ answer = ThunkChunk.new
129
+ answer.pos = @cur
130
+ <%- if @location -%>
131
+ answer.pos_loc = @cur_loc
132
+ <%- end -%>
133
+ <%- gen = ::Packcr::Generator.new(rule, @ascii, @location, :rb) -%>
134
+ <%- -%><%= gen.generate_code(rule, 0, 4, false) -%>
135
+ end
136
+
137
+ <%- end -%>
138
+ def setup_lr(rule, lr)
139
+ lr.head ||= LrHead.new(rule)
140
+ @lrstack.reverse_each do |lrentry|
141
+ if lrentry.head == lr.head
142
+ break
143
+ end
144
+ lrentry.head = lr.head
145
+ lr.head.involved_set[lrentry.rule] = true
146
+ end
147
+ end
148
+
149
+ def grow_lr(rule, memo, head, pos<% if @location %>, p_loc<% end %>)
150
+ @heads[pos] = head
151
+ while true
152
+ @cur = pos - @pos
153
+ <%- if @location -%>
154
+ @cur_loc = p_loc - @pos_loc
155
+ <%- end -%>
156
+ head.involved_set_to_eval_set
157
+ answer = public_send(rule)
158
+ if !answer || @pos + @cur <= memo.pos
159
+ break
160
+ end
161
+ memo.answer = answer
162
+ memo.pos = @pos + @cur
163
+ <%- if @location -%>
164
+ memo.pos_loc = @pos_loc + @cur_loc
165
+ <%- end -%>
166
+ end
167
+ @heads[pos] = nil
168
+ @cur = memo.pos - @pos
169
+ <%- if @location -%>
170
+ @cur_loc = memo.pos_loc - @pos_loc
171
+ <%- end -%>
172
+ memo.answer
173
+ end
174
+
175
+ def lr_answer(rule, memo, pos<% if @location %>, p_loc<% end %>)
176
+ head = memo.lr.head
177
+ if head.rule_name != rule
178
+ return memo.lr.seed
179
+ end
180
+
181
+ memo.answer = memo.lr.seed
182
+ if !memo.answer
183
+ return nil
184
+ end
185
+ grow_lr(rule, memo, head, pos<% if @location %>, p_loc<% end %>)
186
+ end
187
+
188
+ def rule_answer(rule)
189
+ pos = @pos + @cur
190
+ <%- if @location -%>
191
+ p_loc = @pos_loc + @cur_loc
192
+ <%- end -%>
193
+ memo = @memos[pos, rule]
194
+ head = @heads[pos]
195
+
196
+ if head
197
+ if !memo && rule != head.rule_name && !head.involved_set[rule]
198
+ return nil
199
+ end
200
+ if head.eval_set.delete(rule)
201
+ return public_send(rule)
202
+ end
203
+ end
204
+
205
+ if memo
206
+ @cur = memo.pos - @pos
207
+ <%- if @location -%>
208
+ @cur_loc = memo.pos_loc - @pos_loc
209
+ <%- end -%>
210
+ if !memo.lr
211
+ return memo.answer
212
+ end
213
+ setup_lr(rule, memo.lr)
214
+ return memo.lr.seed
215
+ end
216
+
217
+ lr = LrEntry.new
218
+ lr.rule = rule
219
+ @lrstack.push(lr)
220
+ memo = LrMemo.new(lr, pos<% if @location %>, p_loc<% end %>)
221
+ @memos[pos, rule] = memo
222
+ answer = public_send(rule)
223
+ @lrstack.pop
224
+ memo.pos = @pos + @cur
225
+ <%- if @location -%>
226
+ memo.pos_loc = @pos_loc + @cur_loc
227
+ <%- end -%>
228
+ if !lr.head
229
+ memo.answer = answer
230
+ return answer
231
+ end
232
+
233
+ lr.seed = answer
234
+ lr_answer(rule, memo, pos<% if @location %>, p_loc<% end %>)
235
+ end
236
+
237
+ def apply_rule(rule, thunks, values, index)
238
+ answer = rule_answer(rule)
239
+ if !answer
240
+ return false
241
+ end
242
+ values ||= @global_values
243
+ thunks << ThunkNode.new(answer.thunks, values, index)
244
+ return true
245
+ end
246
+
247
+ def do_action(thunks, values, index)
248
+ thunks.each do |thunk|
249
+ thunk.do_action(self, values, index)
250
+ end
251
+ end
252
+
253
+ <%- code(:location).each do |code| -%>
254
+ <%- %><%= stream.get_code_block(code, 2, @iname) -%>
255
+
256
+ <%- end -%>
257
+ class LrMemoTable
258
+ def initialize
259
+ @memos = {}
260
+ end
261
+
262
+ def clear
263
+ @memos.clear
264
+ end
265
+
266
+ def []=(index, rule_name, memo)
267
+ entry = @memos[index] ||= {}
268
+ entry[rule_name] = memo
269
+ end
270
+
271
+ def [](index, rule_name)
272
+ @memos.dig(index, rule_name)
273
+ end
274
+ end
275
+
276
+ class LrHead
277
+ attr_accessor :rule_name, :involved_set, :eval_set
278
+
279
+ def initialize(rule_name)
280
+ @rule_name = rule_name
281
+ @involved_set = {}
282
+ @eval_set = {}
283
+ end
284
+
285
+ def involved_set_to_eval_set
286
+ @eval_set.clear
287
+ @involved_set.each do |k, v|
288
+ @eval_set[k] = true
289
+ end
290
+ end
291
+ end
292
+
293
+ class ThunkChunk
294
+ attr_accessor :thunks, :capts, :pos, :values
295
+ <%- if @location -%>
296
+ attr_accessor :pos_loc
297
+ <%- end -%>
298
+
299
+ def initialize
300
+ super
301
+ @thunks = []
302
+ @capts = {}
303
+ @pos = 0
304
+ @values = {}
305
+ end
306
+
307
+ def resize_captures(len)
308
+ len.times do |i|
309
+ @capts[i] = Capture.new
310
+ end
311
+ end
312
+ end
313
+
314
+ class Thunk
315
+ end
316
+
317
+ class ThunkLeaf < Thunk
318
+ attr_accessor :capt0, :capts, :value_refs, :action
319
+
320
+ def initialize(action, capt0 = Capture.new, value_refs = {}, capts = {})
321
+ @value_refs = value_refs
322
+ @capts = capts
323
+ @capt0 = capt0
324
+ @action = action
325
+ end
326
+
327
+ def do_action(ctx, values, index)
328
+ ctx.public_send(action, self, values, index)
329
+ end
330
+ end
331
+
332
+ class ThunkNode < Thunk
333
+ attr_accessor :thunks, :values, :index
334
+
335
+ def initialize(thunks, values, index)
336
+ @thunks = thunks
337
+ @values = values
338
+ @index = index
339
+ values[index] ||= Value.new if values
340
+ end
341
+
342
+ def do_action(ctx, _values, _index)
343
+ @thunks.each do |thunk|
344
+ thunk.do_action(ctx, @values, @index)
345
+ end
346
+ end
347
+
348
+ def clear
349
+ @thunks.clear
350
+ end
351
+ end
352
+
353
+ class LrEntry
354
+ attr_accessor :rule, :head, :seed
355
+ end
356
+
357
+ class Capture
358
+ attr_accessor :range_start, :range_end
359
+ <%- if @location -%>
360
+ attr_accessor :start_loc, :end_loc
361
+ <%- end -%>
362
+
363
+ def initialize(range_start = 0, range_end = 0<% if @location %>, start_loc = nil, end_loc = nil<% end%>)
364
+ @range_start = range_start
365
+ @range_end = range_end
366
+ <%- if @location -%>
367
+ @start_loc = start_loc || Location.new
368
+ @end_loc = end_loc || Location.new
369
+ <%- end -%>
370
+ end
371
+
372
+ def capture_string(buffer)
373
+ @string ||= buffer[@range_start, @range_end - @range_start]
374
+ end
375
+ end
376
+
377
+ class LrMemo
378
+ attr_accessor :lr, :answer, :pos
379
+ <%- if @location -%>
380
+ attr_accessor :pos_loc
381
+ <%- end -%>
382
+
383
+ def initialize(lr, pos<% if @location %>, pos_loc<% end %>)
384
+ @pos = pos
385
+ <%- if @location -%>
386
+ @pos_loc = pos_loc
387
+ <%- end -%>
388
+ @lr = lr
389
+ end
390
+
391
+ def answer=(answer)
392
+ @lr = nil
393
+ @answer = answer
394
+ end
395
+ end
396
+
397
+ class Value
398
+ attr_accessor :value
399
+ end
400
+ end
401
+ <%- if !code(:lsource).empty? -%>
402
+
403
+ <%- code(:lsource).each do |code| -%>
404
+ <%= stream.get_code_block(code, 0, @iname) -%>
405
+ <%- end -%>
406
+ <%- end -%>
@@ -0,0 +1,16 @@
1
+ {
2
+ pcc_thunk_t *const thunk = pcc_thunk__create_leaf(ctx->auxil, pcc_action_<%= gen.rule.name %>_<%= index %>, <%= gen.rule.vars.length %>, <%= gen.rule.capts.length %>);
3
+ <%- vars.each do |var| -%>
4
+ thunk->data.leaf.values.buf[<%= var.index %>] = &(chunk->values.buf[<%= var.index %>]);
5
+ <%- end -%>
6
+ <%- capts.each do |capt| -%>
7
+ thunk->data.leaf.capts.buf[<%= capt.index %>] = &(chunk->capts.buf[<%= capt.index %>]);
8
+ <%- end -%>
9
+ thunk->data.leaf.capt0.range.start = chunk->pos;
10
+ thunk->data.leaf.capt0.range.end = ctx->cur;
11
+ <%- if gen.location -%>
12
+ thunk->data.leaf.capt0.range.start_loc_ptr = &chunk->pos_loc;
13
+ thunk->data.leaf.capt0.range.end_loc_ptr = &ctx->cur_loc;
14
+ <%- end -%>
15
+ pcc_thunk_array__add(ctx->auxil, &chunk->thunks, thunk);
16
+ }
@@ -0,0 +1,21 @@
1
+ answer.thunks.push(
2
+ ThunkLeaf.new(
3
+ :action_<%= gen.rule.name %>_<%= index %>,
4
+ Capture.new(
5
+ answer.pos, @cur,
6
+ <%- if gen.location -%>
7
+ answer.pos_loc, @cur_loc,
8
+ <%- end -%>
9
+ ),
10
+ <%- if vars.empty? -%>
11
+ {},
12
+ <%- else -%>
13
+ answer.values.slice(<% vars.each_with_index do |var, i| %><%= ", " if i > 0 %><%= var.index %><% end %>),
14
+ <%- end -%>
15
+ <%- if capts.empty? -%>
16
+ {},
17
+ <%- else -%>
18
+ answer.capts.slice(<% capts.each_with_index do |capt, i| %><%= ", " if i > 0 %><%= capt.index %><% end %>),
19
+ <%- end -%>
20
+ )
21
+ )
@@ -0,0 +1,34 @@
1
+ <%- m = gen.next_label -%>
2
+ {
3
+ const size_t p = ctx->cur;
4
+ <%- if gen.location -%>
5
+ const pcc_location_t p_loc = ctx->cur_loc;
6
+ <%- end -%>
7
+ const size_t n = chunk->thunks.len;
8
+ <%- nodes.each_with_index do |expr, i| -%>
9
+ <%- c = i + 1 < nodes.length -%>
10
+ <%- l = gen.next_label -%>
11
+ <%- r = expr.reachability -%>
12
+ <%- -%><%= gen.generate_code(expr, l, 4, false) -%>
13
+ <%- if r == Packcr::CODE_REACH__ALWAYS_SUCCEED -%>
14
+ <%- if c -%>
15
+ /* unreachable codes omitted */
16
+ <%- end -%>
17
+ <%- break -%>
18
+ <%- else -%>
19
+ <%- if r == Packcr::CODE_REACH__BOTH -%>
20
+ goto L<%= "%04d" % m %>;
21
+ <%- end -%>
22
+ <%- end -%>
23
+ L<%= "%04d" % l %>:;
24
+ ctx->cur = p;
25
+ <%- if gen.location -%>
26
+ ctx->cur_loc = p_loc;
27
+ <%- end -%>
28
+ pcc_thunk_array__revert(ctx->auxil, &chunk->thunks, n);
29
+ <%- if !c -%>
30
+ goto L<%= "%04d" % onfail %>;
31
+ <%- end -%>
32
+ <%- end -%>
33
+ L<%= "%04d" % m %>:;
34
+ }
@@ -0,0 +1,40 @@
1
+ <%- m = gen.next_label -%>
2
+ catch(<%= m %>) do
3
+ pos<%= gen.level %> = @cur
4
+ <%- if gen.location -%>
5
+ p_loc<%= gen.level %> = @cur_loc
6
+ <%- end -%>
7
+ n<%= gen.level %> = answer.thunks.length
8
+ <%- nodes.each_with_index do |expr, i| -%>
9
+ <%- c = i + 1 < nodes.length -%>
10
+ <%- if expr.reversible?(gen) -%>
11
+ <%- r = expr.reachability -%>
12
+ <%- %><%= gen.generate_code(expr, m, 2, false, reverse: true, oncut: onfail) -%>
13
+ <%- else -%>
14
+ <%- l = gen.next_label -%>
15
+ catch(<%= l %>) do
16
+ <%- r = expr.reachability -%>
17
+ <%- %><%= gen.generate_code(expr, l, 4, false, oncut: onfail) -%>
18
+ <%- if r == Packcr::CODE_REACH__ALWAYS_SUCCEED -%>
19
+ <%- if c -%>
20
+ # unreachable codes omitted
21
+ <%- end -%>
22
+ end
23
+ <%- break -%>
24
+ <%- else -%>
25
+ <%- if r == Packcr::CODE_REACH__BOTH -%>
26
+ throw(<%= m %>)
27
+ <%- end -%>
28
+ <%- end -%>
29
+ end
30
+ <%- end -%>
31
+ @cur = pos<%= gen.level %>
32
+ <%- if gen.location -%>
33
+ @cur_loc = p_loc<%= gen.level %>
34
+ <%- end -%>
35
+ answer.thunks[n<%= gen.level %>..-1] = []
36
+ <%- if !c -%>
37
+ throw(<%= onfail %>)
38
+ <%- end -%>
39
+ <%- end -%>
40
+ end
@@ -0,0 +1,17 @@
1
+ {
2
+ const size_t p = ctx->cur;
3
+ size_t q;
4
+ <%- if gen.location -%>
5
+ pcc_location_t p_loc = ctx->cur_loc;
6
+ pcc_location_t q_loc;
7
+ <%- end -%>
8
+ <%= gen.generate_code(expr, onfail, 4, false) -%>
9
+ q = ctx->cur;
10
+ chunk->capts.buf[<%= index %>].range.start = p;
11
+ chunk->capts.buf[<%= index %>].range.end = q;
12
+ <%- if gen.location -%>
13
+ q_loc = ctx->cur_loc;
14
+ *chunk->capts.buf[<%= index %>].range.start_loc_ptr = p_loc;
15
+ *chunk->capts.buf[<%= index %>].range.end_loc_ptr = q_loc;
16
+ <%- end -%>
17
+ }
@@ -0,0 +1,14 @@
1
+ pos<%= gen.level %> = @cur
2
+ <%- if gen.location -%>
3
+ p_loc<%= gen.level %> = @cur_loc
4
+ <%- end -%>
5
+ <%- %><%= gen.generate_code(expr, onfail, 0, false) -%>
6
+ q<%= gen.level %> = @cur
7
+ capt<%= gen.level %> = answer.capts[<%= index %>]
8
+ capt<%= gen.level %>.range_start = pos<%= gen.level %>
9
+ capt<%= gen.level %>.range_end = q<%= gen.level %>
10
+ <%- if gen.location -%>
11
+ q_loc<%= gen.level %> = @cur_loc
12
+ capt<%= gen.level %>.start_loc = p_loc<%= gen.level %>
13
+ capt<%= gen.level %>.end_loc = q_loc<%= gen.level %>
14
+ <%- end -%>
@@ -0,0 +1,47 @@
1
+ {
2
+ <%- if !a && charclass =~ /\A[^\\]-.\z/ -%>
3
+ char c;
4
+ if (pcc_refill_buffer(ctx, 1) < 1) goto L<%= "%04d" % onfail %>;
5
+ c = ctx->buffer.buf[ctx->cur];
6
+ <%- if a -%>
7
+ if (c >= '<%= Packcr.escape_character(charclass[0]) %>' && c <= '<%= Packcr.escape_character(charclass[2]) %>') goto L<%= "%04d" % onfail %>;
8
+ <%- else -%>
9
+ if (!(c >= '<%= Packcr.escape_character(charclass[0]) %>' && c <= '<%= Packcr.escape_character(charclass[2]) %>')) goto L<%= "%04d" % onfail %>;
10
+ <%- end -%>
11
+ <%- if gen.location -%>
12
+ pcc_location_forward(&ctx->cur_loc, ctx->buffer.buf + ctx->cur, 1);
13
+ <%- end -%>
14
+ ctx->cur++;
15
+ <%- else -%>
16
+ char c;
17
+ if (pcc_refill_buffer(ctx, 1) < 1) goto L<%= "%04d" % onfail %>;
18
+ c = ctx->buffer.buf[ctx->cur];
19
+ <%- if a -%>
20
+ if (
21
+ <%- else -%>
22
+ if (!(
23
+ <%- end -%>
24
+ <%- i = 0 -%>
25
+ <%- while i < n -%>
26
+ <%- if charclass[i] == "\\" && i + 1 < n -%>
27
+ <%- i += 1 -%>
28
+ <%- end -%>
29
+ <%- if i + 2 < n && charclass[i + 1] == '-' -%>
30
+ (c >= '<%= Packcr.escape_character(charclass[i]) %>' && c <= '<%= Packcr.escape_character(charclass[i + 2]) %>')<%= (i + 3 == n) ? "" : " ||" %>
31
+ <%- i += 2 -%>
32
+ <%- else -%>
33
+ c == '<%= Packcr.escape_character(charclass[i]) %>'<%= (i + 1 == n) ? "" : " ||" %>
34
+ <%- end -%>
35
+ <%- i += 1 -%>
36
+ <%- end -%>
37
+ <%- if a -%>
38
+ ) goto L<%= "%04d" % onfail %>;
39
+ <%- else -%>
40
+ )) goto L<%= "%04d" % onfail %>;
41
+ <%- end -%>
42
+ <%- if gen.location -%>
43
+ pcc_location_forward(&ctx->cur_loc, ctx->buffer.buf + ctx->cur, 1);
44
+ <%- end -%>
45
+ ctx->cur++;
46
+ <%- end -%>
47
+ }
@@ -0,0 +1,49 @@
1
+ <%- if !a && charclass =~ /\A[^\\]-.\z/ -%>
2
+ if refill_buffer(1) < 1
3
+ throw(<%= onfail %>)
4
+ end
5
+ c<%= gen.level %> = @buffer[@cur]
6
+ <%- if a -%>
7
+ if c<%= gen.level %> >= "<%= Packcr.escape_character(charclass[0]) %>" && c<%= gen.level %> <= "<%= Packcr.escape_character(charclass[2]) %>"
8
+ throw(<%= onfail %>)
9
+ end
10
+ <%- else -%>
11
+ unless c<%= gen.level %> >= "<%= Packcr.escape_character(charclass[0]) %>" && c<%= gen.level %> <= "<%= Packcr.escape_character(charclass[2]) %>"
12
+ throw(<%= onfail %>)
13
+ end
14
+ <%- end -%>
15
+ <%- if gen.location -%>
16
+ @cur_loc = @cur_loc.forward(@buffer, @cur, 1)
17
+ <%- end -%>
18
+ @cur += 1
19
+ <%- else -%>
20
+ if refill_buffer(1) < 1
21
+ throw(<%= onfail %>)
22
+ end
23
+ c<%= gen.level %> = @buffer[@cur]
24
+ <%- if a -%>
25
+ if (
26
+ <%- else -%>
27
+ unless (
28
+ <%- end -%>
29
+ <%- i = 0 -%>
30
+ <%- while i < n -%>
31
+ <%- if charclass[i] == "\\" && i + 1 < n -%>
32
+ <%- i += 1 -%>
33
+ <%- end -%>
34
+ <%- if i + 2 < n && charclass[i + 1] == '-' -%>
35
+ (c<%= gen.level %> >= "<%= Packcr.escape_character(charclass[i]) %>" && c<%= gen.level %> <= "<%= Packcr.escape_character(charclass[i + 2]) %>")<%= (i + 3 == n) ? "" : " ||" %>
36
+ <%- i += 2 -%>
37
+ <%- else -%>
38
+ c<%= gen.level %> == "<%= Packcr.escape_character(charclass[i]) %>"<%= (i + 1 == n) ? "" : " ||" %>
39
+ <%- end -%>
40
+ <%- i += 1 -%>
41
+ <%- end -%>
42
+ )
43
+ throw(<%= onfail %>)
44
+ end
45
+ <%- if gen.location -%>
46
+ @cur_loc = @cur_loc.forward(@buffer, @cur, 1)
47
+ <%- end -%>
48
+ @cur += 1
49
+ <%- end -%>
@@ -0,0 +1,5 @@
1
+ if (pcc_refill_buffer(ctx, 1) < 1) goto L<%= "%04d" % onfail %>;
2
+ <%- if gen.location -%>
3
+ pcc_location_forward(&ctx->cur, ctx->buffer.buf + ctx->cur, 1);
4
+ <%- end -%>
5
+ ctx->cur++;
@@ -0,0 +1,7 @@
1
+ if refill_buffer(1) < 1
2
+ throw(<%= onfail %>)
3
+ end
4
+ <%- if gen.location -%>
5
+ @cur_loc = @cur_loc.forward(@buffer, @cur, 1)
6
+ <%- end -%>
7
+ @cur += 1
@@ -0,0 +1 @@
1
+ goto L<%= "%04d" % onfail %>;
@@ -0,0 +1 @@
1
+ throw(<%= onfail %>)
@@ -0,0 +1,19 @@
1
+ <%- if a -%>
2
+ if (
3
+ pcc_refill_buffer(ctx, 1) < 1 ||
4
+ ctx->buffer.buf[ctx->cur] == '<%= Packcr.escape_character(charclass[i]) %>'
5
+ ) goto L<%= "%04d" % onfail %>;
6
+ <%- if gen.location -%>
7
+ pcc_location_forward(&ctx->cur_loc, ctx->buffer.buf + ctx->cur, 1);
8
+ <%- end -%>
9
+ ctx->cur++;
10
+ <%- else -%>
11
+ if (
12
+ pcc_refill_buffer(ctx, 1) < 1 ||
13
+ ctx->buffer.buf[ctx->cur] != '<%= Packcr.escape_character(charclass[0]) %>'
14
+ ) goto L<%= "%04d" % onfail %>;
15
+ <%- if gen.location -%>
16
+ pcc_location_forward(&ctx->cur_loc, ctx->buffer.buf + ctx->cur, 1);
17
+ <%- end -%>
18
+ ctx->cur++;
19
+ <%- end -%>