Ruby  2.0.0p451(2014-02-24revision45167)
parse.y
Go to the documentation of this file.
1 /**********************************************************************
2 
3  parse.y -
4 
5  $Author: nagachika $
6  created at: Fri May 28 18:02:42 JST 1993
7 
8  Copyright (C) 1993-2007 Yukihiro Matsumoto
9 
10 **********************************************************************/
11 
12 %{
13 
14 #ifndef PARSER_DEBUG
15 #define PARSER_DEBUG 0
16 #endif
17 #define YYDEBUG 1
18 #define YYERROR_VERBOSE 1
19 #define YYSTACK_USE_ALLOCA 0
20 
21 #include "ruby/ruby.h"
22 #include "ruby/st.h"
23 #include "ruby/encoding.h"
24 #include "internal.h"
25 #include "node.h"
26 #include "parse.h"
27 #include "id.h"
28 #include "regenc.h"
29 #include <stdio.h>
30 #include <errno.h>
31 #include <ctype.h>
32 #include "probes.h"
33 
34 #define numberof(array) (int)(sizeof(array) / sizeof((array)[0]))
35 
36 #define YYMALLOC(size) rb_parser_malloc(parser, (size))
37 #define YYREALLOC(ptr, size) rb_parser_realloc(parser, (ptr), (size))
38 #define YYCALLOC(nelem, size) rb_parser_calloc(parser, (nelem), (size))
39 #define YYFREE(ptr) rb_parser_free(parser, (ptr))
40 #define malloc YYMALLOC
41 #define realloc YYREALLOC
42 #define calloc YYCALLOC
43 #define free YYFREE
44 
45 #ifndef RIPPER
46 static ID register_symid(ID, const char *, long, rb_encoding *);
47 static ID register_symid_str(ID, VALUE);
48 #define REGISTER_SYMID(id, name) register_symid((id), (name), strlen(name), enc)
49 #include "id.c"
50 #endif
51 
52 #define is_notop_id(id) ((id)>tLAST_OP_ID)
53 #define is_local_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_LOCAL)
54 #define is_global_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_GLOBAL)
55 #define is_instance_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_INSTANCE)
56 #define is_attrset_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_ATTRSET)
57 #define is_const_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_CONST)
58 #define is_class_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_CLASS)
59 #define is_junk_id(id) (is_notop_id(id)&&((id)&ID_SCOPE_MASK)==ID_JUNK)
60 #define id_type(id) (is_notop_id(id) ? (int)((id)&ID_SCOPE_MASK) : -1)
61 
62 #define is_asgn_or_id(id) ((is_notop_id(id)) && \
63  (((id)&ID_SCOPE_MASK) == ID_GLOBAL || \
64  ((id)&ID_SCOPE_MASK) == ID_INSTANCE || \
65  ((id)&ID_SCOPE_MASK) == ID_CLASS))
66 
68  EXPR_BEG_bit, /* ignore newline, +/- is a sign. */
69  EXPR_END_bit, /* newline significant, +/- is an operator. */
70  EXPR_ENDARG_bit, /* ditto, and unbound braces. */
71  EXPR_ENDFN_bit, /* ditto, and unbound braces. */
72  EXPR_ARG_bit, /* newline significant, +/- is an operator. */
73  EXPR_CMDARG_bit, /* newline significant, +/- is an operator. */
74  EXPR_MID_bit, /* newline significant, +/- is an operator. */
75  EXPR_FNAME_bit, /* ignore newline, no reserved words. */
76  EXPR_DOT_bit, /* right after `.' or `::', no reserved words. */
77  EXPR_CLASS_bit, /* immediate after `class', no here document. */
78  EXPR_VALUE_bit, /* alike EXPR_BEG but label is disallowed. */
80 };
81 /* examine combinations */
83 #define DEF_EXPR(n) EXPR_##n = (1 << EXPR_##n##_bit)
85  DEF_EXPR(END),
86  DEF_EXPR(ENDARG),
87  DEF_EXPR(ENDFN),
88  DEF_EXPR(ARG),
89  DEF_EXPR(CMDARG),
90  DEF_EXPR(MID),
91  DEF_EXPR(FNAME),
92  DEF_EXPR(DOT),
93  DEF_EXPR(CLASS),
94  DEF_EXPR(VALUE),
95  EXPR_BEG_ANY = (EXPR_BEG | EXPR_VALUE | EXPR_MID | EXPR_CLASS),
96  EXPR_ARG_ANY = (EXPR_ARG | EXPR_CMDARG),
97  EXPR_END_ANY = (EXPR_END | EXPR_ENDARG | EXPR_ENDFN)
98 };
99 #define IS_lex_state_for(x, ls) ((x) & (ls))
100 #define IS_lex_state(ls) IS_lex_state_for(lex_state, (ls))
101 
102 #if PARSER_DEBUG
103 static const char *lex_state_name(enum lex_state_e state);
104 #endif
105 
107 
108 # define BITSTACK_PUSH(stack, n) ((stack) = ((stack)<<1)|((n)&1))
109 # define BITSTACK_POP(stack) ((stack) = (stack) >> 1)
110 # define BITSTACK_LEXPOP(stack) ((stack) = ((stack) >> 1) | ((stack) & 1))
111 # define BITSTACK_SET_P(stack) ((stack)&1)
112 
113 #define COND_PUSH(n) BITSTACK_PUSH(cond_stack, (n))
114 #define COND_POP() BITSTACK_POP(cond_stack)
115 #define COND_LEXPOP() BITSTACK_LEXPOP(cond_stack)
116 #define COND_P() BITSTACK_SET_P(cond_stack)
117 
118 #define CMDARG_PUSH(n) BITSTACK_PUSH(cmdarg_stack, (n))
119 #define CMDARG_POP() BITSTACK_POP(cmdarg_stack)
120 #define CMDARG_LEXPOP() BITSTACK_LEXPOP(cmdarg_stack)
121 #define CMDARG_P() BITSTACK_SET_P(cmdarg_stack)
122 
123 struct vtable {
124  ID *tbl;
125  int pos;
126  int capa;
127  struct vtable *prev;
128 };
129 
130 struct local_vars {
131  struct vtable *args;
132  struct vtable *vars;
133  struct vtable *used;
134  struct local_vars *prev;
135  stack_type cmdargs;
136 };
137 
138 #define DVARS_INHERIT ((void*)1)
139 #define DVARS_TOPSCOPE NULL
140 #define DVARS_SPECIAL_P(tbl) (!POINTER_P(tbl))
141 #define POINTER_P(val) ((VALUE)(val) & ~(VALUE)3)
142 
143 static int
144 vtable_size(const struct vtable *tbl)
145 {
146  if (POINTER_P(tbl)) {
147  return tbl->pos;
148  }
149  else {
150  return 0;
151  }
152 }
153 
154 #define VTBL_DEBUG 0
155 
156 static struct vtable *
158 {
159  struct vtable *tbl = ALLOC(struct vtable);
160  tbl->pos = 0;
161  tbl->capa = 8;
162  tbl->tbl = ALLOC_N(ID, tbl->capa);
163  tbl->prev = prev;
164  if (VTBL_DEBUG) printf("vtable_alloc: %p\n", (void *)tbl);
165  return tbl;
166 }
167 
168 static void
170 {
171  if (VTBL_DEBUG)printf("vtable_free: %p\n", (void *)tbl);
172  if (POINTER_P(tbl)) {
173  if (tbl->tbl) {
174  xfree(tbl->tbl);
175  }
176  xfree(tbl);
177  }
178 }
179 
180 static void
181 vtable_add(struct vtable *tbl, ID id)
182 {
183  if (!POINTER_P(tbl)) {
184  rb_bug("vtable_add: vtable is not allocated (%p)", (void *)tbl);
185  }
186  if (VTBL_DEBUG) printf("vtable_add: %p, %s\n", (void *)tbl, rb_id2name(id));
187 
188  if (tbl->pos == tbl->capa) {
189  tbl->capa = tbl->capa * 2;
190  REALLOC_N(tbl->tbl, ID, tbl->capa);
191  }
192  tbl->tbl[tbl->pos++] = id;
193 }
194 
195 static int
196 vtable_included(const struct vtable * tbl, ID id)
197 {
198  int i;
199 
200  if (POINTER_P(tbl)) {
201  for (i = 0; i < tbl->pos; i++) {
202  if (tbl->tbl[i] == id) {
203  return i+1;
204  }
205  }
206  }
207  return 0;
208 }
209 
210 
211 #ifndef RIPPER
212 typedef struct token_info {
213  const char *token;
214  int linenum;
215  int column;
216  int nonspc;
217  struct token_info *next;
218 } token_info;
219 #endif
220 
221 /*
222  Structure of Lexer Buffer:
223 
224  lex_pbeg tokp lex_p lex_pend
225  | | | |
226  |-----------+--------------+------------|
227  |<------------>|
228  token
229 */
230 struct parser_params {
231  int is_ripper;
232  NODE *heap;
233 
235  VALUE eofp;
236 
239  stack_type parser_cond_stack;
240  stack_type parser_cmdarg_stack;
241  int parser_class_nest;
242  int parser_paren_nest;
243  int parser_lpar_beg;
244  int parser_in_single;
245  int parser_in_def;
246  int parser_brace_nest;
249  int parser_in_defined;
250  char *parser_tokenbuf;
251  int parser_tokidx;
252  int parser_toksiz;
253  int parser_tokline;
257  const char *parser_lex_pbeg;
258  const char *parser_lex_p;
259  const char *parser_lex_pend;
260  int parser_heredoc_end;
263  long parser_lex_gets_ptr;
265  struct local_vars *parser_lvtbl;
267  int line_count;
268  int has_shebang;
269  char *parser_ruby_sourcefile; /* current source file */
270  int parser_ruby_sourceline; /* current line no. */
271  rb_encoding *enc;
272 
273  int parser_yydebug;
274 
275 #ifndef RIPPER
276  /* Ruby core only */
280  VALUE coverage;
281  int nerr;
282 
285 #else
286  /* Ripper only */
287  VALUE parser_ruby_sourcefile_string;
288  const char *tokp;
289  VALUE delayed;
290  int delayed_line;
291  int delayed_col;
292 
293  VALUE value;
294  VALUE result;
295  VALUE parsing_thread;
296  int toplevel_p;
297 #endif
298 };
299 
300 #define STR_NEW(p,n) rb_enc_str_new((p),(n),current_enc)
301 #define STR_NEW0() rb_enc_str_new(0,0,current_enc)
302 #define STR_NEW2(p) rb_enc_str_new((p),strlen(p),current_enc)
303 #define STR_NEW3(p,n,e,func) parser_str_new((p),(n),(e),(func),current_enc)
304 #define ENC_SINGLE(cr) ((cr)==ENC_CODERANGE_7BIT)
305 #define TOK_INTERN(mb) rb_intern3(tok(), toklen(), current_enc)
306 
307 static int parser_yyerror(struct parser_params*, const char*);
308 #define yyerror(msg) parser_yyerror(parser, (msg))
309 
310 #define lex_strterm (parser->parser_lex_strterm)
311 #define lex_state (parser->parser_lex_state)
312 #define cond_stack (parser->parser_cond_stack)
313 #define cmdarg_stack (parser->parser_cmdarg_stack)
314 #define class_nest (parser->parser_class_nest)
315 #define paren_nest (parser->parser_paren_nest)
316 #define lpar_beg (parser->parser_lpar_beg)
317 #define brace_nest (parser->parser_brace_nest)
318 #define in_single (parser->parser_in_single)
319 #define in_def (parser->parser_in_def)
320 #define compile_for_eval (parser->parser_compile_for_eval)
321 #define cur_mid (parser->parser_cur_mid)
322 #define in_defined (parser->parser_in_defined)
323 #define tokenbuf (parser->parser_tokenbuf)
324 #define tokidx (parser->parser_tokidx)
325 #define toksiz (parser->parser_toksiz)
326 #define tokline (parser->parser_tokline)
327 #define lex_input (parser->parser_lex_input)
328 #define lex_lastline (parser->parser_lex_lastline)
329 #define lex_nextline (parser->parser_lex_nextline)
330 #define lex_pbeg (parser->parser_lex_pbeg)
331 #define lex_p (parser->parser_lex_p)
332 #define lex_pend (parser->parser_lex_pend)
333 #define heredoc_end (parser->parser_heredoc_end)
334 #define command_start (parser->parser_command_start)
335 #define deferred_nodes (parser->parser_deferred_nodes)
336 #define lex_gets_ptr (parser->parser_lex_gets_ptr)
337 #define lex_gets (parser->parser_lex_gets)
338 #define lvtbl (parser->parser_lvtbl)
339 #define ruby__end__seen (parser->parser_ruby__end__seen)
340 #define ruby_sourceline (parser->parser_ruby_sourceline)
341 #define ruby_sourcefile (parser->parser_ruby_sourcefile)
342 #define current_enc (parser->enc)
343 #define yydebug (parser->parser_yydebug)
344 #ifdef RIPPER
345 #else
346 #define ruby_eval_tree (parser->parser_eval_tree)
347 #define ruby_eval_tree_begin (parser->parser_eval_tree_begin)
348 #define ruby_debug_lines (parser->debug_lines)
349 #define ruby_coverage (parser->coverage)
350 #endif
351 
352 #if YYPURE
353 static int yylex(void*, void*);
354 #else
355 static int yylex(void*);
356 #endif
357 
358 #ifndef RIPPER
359 #define yyparse ruby_yyparse
360 
361 static NODE* node_newnode(struct parser_params *, enum node_type, VALUE, VALUE, VALUE);
362 #define rb_node_newnode(type, a1, a2, a3) node_newnode(parser, (type), (a1), (a2), (a3))
363 
364 static NODE *cond_gen(struct parser_params*,NODE*);
365 #define cond(node) cond_gen(parser, (node))
366 static NODE *logop_gen(struct parser_params*,enum node_type,NODE*,NODE*);
367 #define logop(type,node1,node2) logop_gen(parser, (type), (node1), (node2))
368 
369 static NODE *newline_node(NODE*);
370 static void fixpos(NODE*,NODE*);
371 
372 static int value_expr_gen(struct parser_params*,NODE*);
373 static void void_expr_gen(struct parser_params*,NODE*);
374 static NODE *remove_begin(NODE*);
375 #define value_expr(node) value_expr_gen(parser, (node) = remove_begin(node))
376 #define void_expr0(node) void_expr_gen(parser, (node))
377 #define void_expr(node) void_expr0((node) = remove_begin(node))
378 static void void_stmts_gen(struct parser_params*,NODE*);
379 #define void_stmts(node) void_stmts_gen(parser, (node))
380 static void reduce_nodes_gen(struct parser_params*,NODE**);
381 #define reduce_nodes(n) reduce_nodes_gen(parser,(n))
382 static void block_dup_check_gen(struct parser_params*,NODE*,NODE*);
383 #define block_dup_check(n1,n2) block_dup_check_gen(parser,(n1),(n2))
384 
385 static NODE *block_append_gen(struct parser_params*,NODE*,NODE*);
386 #define block_append(h,t) block_append_gen(parser,(h),(t))
387 static NODE *list_append_gen(struct parser_params*,NODE*,NODE*);
388 #define list_append(l,i) list_append_gen(parser,(l),(i))
389 static NODE *list_concat_gen(struct parser_params*,NODE*,NODE*);
390 #define list_concat(h,t) list_concat_gen(parser,(h),(t))
391 static NODE *arg_append_gen(struct parser_params*,NODE*,NODE*);
392 #define arg_append(h,t) arg_append_gen(parser,(h),(t))
393 static NODE *arg_concat_gen(struct parser_params*,NODE*,NODE*);
394 #define arg_concat(h,t) arg_concat_gen(parser,(h),(t))
395 static NODE *literal_concat_gen(struct parser_params*,NODE*,NODE*);
396 #define literal_concat(h,t) literal_concat_gen(parser,(h),(t))
397 static int literal_concat0(struct parser_params *, VALUE, VALUE);
398 static NODE *new_evstr_gen(struct parser_params*,NODE*);
399 #define new_evstr(n) new_evstr_gen(parser,(n))
400 static NODE *evstr2dstr_gen(struct parser_params*,NODE*);
401 #define evstr2dstr(n) evstr2dstr_gen(parser,(n))
402 static NODE *splat_array(NODE*);
403 
404 static NODE *call_bin_op_gen(struct parser_params*,NODE*,ID,NODE*);
405 #define call_bin_op(recv,id,arg1) call_bin_op_gen(parser, (recv),(id),(arg1))
406 static NODE *call_uni_op_gen(struct parser_params*,NODE*,ID);
407 #define call_uni_op(recv,id) call_uni_op_gen(parser, (recv),(id))
408 
409 static NODE *new_args_gen(struct parser_params*,NODE*,NODE*,ID,NODE*,NODE*);
410 #define new_args(f,o,r,p,t) new_args_gen(parser, (f),(o),(r),(p),(t))
411 static NODE *new_args_tail_gen(struct parser_params*,NODE*,ID,ID);
412 #define new_args_tail(k,kr,b) new_args_tail_gen(parser, (k),(kr),(b))
413 
414 static NODE *negate_lit(NODE*);
415 static NODE *ret_args_gen(struct parser_params*,NODE*);
416 #define ret_args(node) ret_args_gen(parser, (node))
417 static NODE *arg_blk_pass(NODE*,NODE*);
418 static NODE *new_yield_gen(struct parser_params*,NODE*);
419 #define new_yield(node) new_yield_gen(parser, (node))
420 static NODE *dsym_node_gen(struct parser_params*,NODE*);
421 #define dsym_node(node) dsym_node_gen(parser, (node))
422 
423 static NODE *gettable_gen(struct parser_params*,ID);
424 #define gettable(id) gettable_gen(parser,(id))
425 static NODE *assignable_gen(struct parser_params*,ID,NODE*);
426 #define assignable(id,node) assignable_gen(parser, (id), (node))
427 
428 static NODE *aryset_gen(struct parser_params*,NODE*,NODE*);
429 #define aryset(node1,node2) aryset_gen(parser, (node1), (node2))
430 static NODE *attrset_gen(struct parser_params*,NODE*,ID);
431 #define attrset(node,id) attrset_gen(parser, (node), (id))
432 
433 static void rb_backref_error_gen(struct parser_params*,NODE*);
434 #define rb_backref_error(n) rb_backref_error_gen(parser,(n))
435 static NODE *node_assign_gen(struct parser_params*,NODE*,NODE*);
436 #define node_assign(node1, node2) node_assign_gen(parser, (node1), (node2))
437 
438 static NODE *new_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs);
439 static NODE *new_attr_op_assign_gen(struct parser_params *parser, NODE *lhs, ID attr, ID op, NODE *rhs);
440 #define new_attr_op_assign(lhs, type, attr, op, rhs) new_attr_op_assign_gen(parser, (lhs), (attr), (op), (rhs))
441 static NODE *new_const_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs);
442 #define new_const_op_assign(lhs, op, rhs) new_const_op_assign_gen(parser, (lhs), (op), (rhs))
443 
444 static NODE *match_op_gen(struct parser_params*,NODE*,NODE*);
445 #define match_op(node1,node2) match_op_gen(parser, (node1), (node2))
446 
447 static ID *local_tbl_gen(struct parser_params*);
448 #define local_tbl() local_tbl_gen(parser)
449 
450 static void fixup_nodes(NODE **);
451 
452 static VALUE reg_compile_gen(struct parser_params*, VALUE, int);
453 #define reg_compile(str,options) reg_compile_gen(parser, (str), (options))
454 static void reg_fragment_setenc_gen(struct parser_params*, VALUE, int);
455 #define reg_fragment_setenc(str,options) reg_fragment_setenc_gen(parser, (str), (options))
456 static int reg_fragment_check_gen(struct parser_params*, VALUE, int);
457 #define reg_fragment_check(str,options) reg_fragment_check_gen(parser, (str), (options))
458 static NODE *reg_named_capture_assign_gen(struct parser_params* parser, VALUE regexp, NODE *match);
459 #define reg_named_capture_assign(regexp,match) reg_named_capture_assign_gen(parser,(regexp),(match))
460 
461 #define get_id(id) (id)
462 #define get_value(val) (val)
463 #else
464 #define value_expr(node) ((void)(node))
465 #define remove_begin(node) (node)
466 #define rb_dvar_defined(id) 0
467 #define rb_local_defined(id) 0
468 static ID ripper_get_id(VALUE);
469 #define get_id(id) ripper_get_id(id)
470 static VALUE ripper_get_value(VALUE);
471 #define get_value(val) ripper_get_value(val)
472 static VALUE assignable_gen(struct parser_params*,VALUE);
473 #define assignable(lhs,node) assignable_gen(parser, (lhs))
474 static int id_is_var_gen(struct parser_params *parser, ID id);
475 #define id_is_var(id) id_is_var_gen(parser, (id))
476 
477 #define node_assign(node1, node2) dispatch2(assign, (node1), (node2))
478 
479 static VALUE new_op_assign_gen(struct parser_params *parser, VALUE lhs, VALUE op, VALUE rhs);
480 static VALUE new_attr_op_assign_gen(struct parser_params *parser, VALUE lhs, VALUE type, VALUE attr, VALUE op, VALUE rhs);
481 #define new_attr_op_assign(lhs, type, attr, op, rhs) new_attr_op_assign_gen(parser, (lhs), (type), (attr), (op), (rhs))
482 
483 #endif /* !RIPPER */
484 
485 #define new_op_assign(lhs, op, rhs) new_op_assign_gen(parser, (lhs), (op), (rhs))
486 
487 static ID formal_argument_gen(struct parser_params*, ID);
488 #define formal_argument(id) formal_argument_gen(parser, (id))
489 static ID shadowing_lvar_gen(struct parser_params*,ID);
490 #define shadowing_lvar(name) shadowing_lvar_gen(parser, (name))
491 static void new_bv_gen(struct parser_params*,ID);
492 #define new_bv(id) new_bv_gen(parser, (id))
493 
494 static void local_push_gen(struct parser_params*,int);
495 #define local_push(top) local_push_gen(parser,(top))
496 static void local_pop_gen(struct parser_params*);
497 #define local_pop() local_pop_gen(parser)
498 static int local_var_gen(struct parser_params*, ID);
499 #define local_var(id) local_var_gen(parser, (id))
500 static int arg_var_gen(struct parser_params*, ID);
501 #define arg_var(id) arg_var_gen(parser, (id))
502 static int local_id_gen(struct parser_params*, ID);
503 #define local_id(id) local_id_gen(parser, (id))
504 static ID internal_id_gen(struct parser_params*);
505 #define internal_id() internal_id_gen(parser)
506 
507 static const struct vtable *dyna_push_gen(struct parser_params *);
508 #define dyna_push() dyna_push_gen(parser)
509 static void dyna_pop_gen(struct parser_params*, const struct vtable *);
510 #define dyna_pop(node) dyna_pop_gen(parser, (node))
511 static int dyna_in_block_gen(struct parser_params*);
512 #define dyna_in_block() dyna_in_block_gen(parser)
513 #define dyna_var(id) local_var(id)
514 static int dvar_defined_gen(struct parser_params*,ID,int);
515 #define dvar_defined(id) dvar_defined_gen(parser, (id), 0)
516 #define dvar_defined_get(id) dvar_defined_gen(parser, (id), 1)
517 static int dvar_curr_gen(struct parser_params*,ID);
518 #define dvar_curr(id) dvar_curr_gen(parser, (id))
519 
520 static int lvar_defined_gen(struct parser_params*, ID);
521 #define lvar_defined(id) lvar_defined_gen(parser, (id))
522 
523 #define RE_OPTION_ONCE (1<<16)
524 #define RE_OPTION_ENCODING_SHIFT 8
525 #define RE_OPTION_ENCODING(e) (((e)&0xff)<<RE_OPTION_ENCODING_SHIFT)
526 #define RE_OPTION_ENCODING_IDX(o) (((o)>>RE_OPTION_ENCODING_SHIFT)&0xff)
527 #define RE_OPTION_ENCODING_NONE(o) ((o)&RE_OPTION_ARG_ENCODING_NONE)
528 #define RE_OPTION_MASK 0xff
529 #define RE_OPTION_ARG_ENCODING_NONE 32
530 
531 #define NODE_STRTERM NODE_ZARRAY /* nothing to gc */
532 #define NODE_HEREDOC NODE_ARRAY /* 1, 3 to gc */
533 #define SIGN_EXTEND(x,n) (((1<<(n)-1)^((x)&~(~0<<(n))))-(1<<(n)-1))
534 #define nd_func u1.id
535 #if SIZEOF_SHORT == 2
536 #define nd_term(node) ((signed short)(node)->u2.id)
537 #else
538 #define nd_term(node) SIGN_EXTEND((node)->u2.id, CHAR_BIT*2)
539 #endif
540 #define nd_paren(node) (char)((node)->u2.id >> CHAR_BIT*2)
541 #define nd_nest u3.cnt
542 
543 /****** Ripper *******/
544 
545 #ifdef RIPPER
546 #define RIPPER_VERSION "0.1.0"
547 
548 #include "eventids1.c"
549 #include "eventids2.c"
550 
551 static VALUE ripper_dispatch0(struct parser_params*,ID);
552 static VALUE ripper_dispatch1(struct parser_params*,ID,VALUE);
553 static VALUE ripper_dispatch2(struct parser_params*,ID,VALUE,VALUE);
554 static VALUE ripper_dispatch3(struct parser_params*,ID,VALUE,VALUE,VALUE);
555 static VALUE ripper_dispatch4(struct parser_params*,ID,VALUE,VALUE,VALUE,VALUE);
556 static VALUE ripper_dispatch5(struct parser_params*,ID,VALUE,VALUE,VALUE,VALUE,VALUE);
557 static VALUE ripper_dispatch7(struct parser_params*,ID,VALUE,VALUE,VALUE,VALUE,VALUE,VALUE,VALUE);
558 
559 #define dispatch0(n) ripper_dispatch0(parser, TOKEN_PASTE(ripper_id_, n))
560 #define dispatch1(n,a) ripper_dispatch1(parser, TOKEN_PASTE(ripper_id_, n), (a))
561 #define dispatch2(n,a,b) ripper_dispatch2(parser, TOKEN_PASTE(ripper_id_, n), (a), (b))
562 #define dispatch3(n,a,b,c) ripper_dispatch3(parser, TOKEN_PASTE(ripper_id_, n), (a), (b), (c))
563 #define dispatch4(n,a,b,c,d) ripper_dispatch4(parser, TOKEN_PASTE(ripper_id_, n), (a), (b), (c), (d))
564 #define dispatch5(n,a,b,c,d,e) ripper_dispatch5(parser, TOKEN_PASTE(ripper_id_, n), (a), (b), (c), (d), (e))
565 #define dispatch7(n,a,b,c,d,e,f,g) ripper_dispatch7(parser, TOKEN_PASTE(ripper_id_, n), (a), (b), (c), (d), (e), (f), (g))
566 
567 #define yyparse ripper_yyparse
568 
569 #define ripper_intern(s) ID2SYM(rb_intern(s))
570 static VALUE ripper_id2sym(ID);
571 #ifdef __GNUC__
572 #define ripper_id2sym(id) ((id) < 256 && rb_ispunct(id) ? \
573  ID2SYM(id) : ripper_id2sym(id))
574 #endif
575 
576 #define arg_new() dispatch0(args_new)
577 #define arg_add(l,a) dispatch2(args_add, (l), (a))
578 #define arg_add_star(l,a) dispatch2(args_add_star, (l), (a))
579 #define arg_add_block(l,b) dispatch2(args_add_block, (l), (b))
580 #define arg_add_optblock(l,b) ((b)==Qundef? (l) : dispatch2(args_add_block, (l), (b)))
581 #define bare_assoc(v) dispatch1(bare_assoc_hash, (v))
582 #define arg_add_assocs(l,b) arg_add((l), bare_assoc(b))
583 
584 #define args2mrhs(a) dispatch1(mrhs_new_from_args, (a))
585 #define mrhs_new() dispatch0(mrhs_new)
586 #define mrhs_add(l,a) dispatch2(mrhs_add, (l), (a))
587 #define mrhs_add_star(l,a) dispatch2(mrhs_add_star, (l), (a))
588 
589 #define mlhs_new() dispatch0(mlhs_new)
590 #define mlhs_add(l,a) dispatch2(mlhs_add, (l), (a))
591 #define mlhs_add_star(l,a) dispatch2(mlhs_add_star, (l), (a))
592 
593 #define params_new(pars, opts, rest, pars2, kws, kwrest, blk) \
594  dispatch7(params, (pars), (opts), (rest), (pars2), (kws), (kwrest), (blk))
595 
596 #define blockvar_new(p,v) dispatch2(block_var, (p), (v))
597 #define blockvar_add_star(l,a) dispatch2(block_var_add_star, (l), (a))
598 #define blockvar_add_block(l,a) dispatch2(block_var_add_block, (l), (a))
599 
600 #define method_optarg(m,a) ((a)==Qundef ? (m) : dispatch2(method_add_arg,(m),(a)))
601 #define method_arg(m,a) dispatch2(method_add_arg,(m),(a))
602 #define method_add_block(m,b) dispatch2(method_add_block, (m), (b))
603 
604 #define escape_Qundef(x) ((x)==Qundef ? Qnil : (x))
605 
606 static inline VALUE
607 new_args_gen(struct parser_params *parser, VALUE f, VALUE o, VALUE r, VALUE p, VALUE tail)
608 {
609  NODE *t = (NODE *)tail;
610  VALUE k = t->u1.value, kr = t->u2.value, b = t->u3.value;
611  return params_new(f, o, r, p, k, kr, escape_Qundef(b));
612 }
613 #define new_args(f,o,r,p,t) new_args_gen(parser, (f),(o),(r),(p),(t))
614 
615 static inline VALUE
616 new_args_tail_gen(struct parser_params *parser, VALUE k, VALUE kr, VALUE b)
617 {
618  return (VALUE)rb_node_newnode(NODE_MEMO, k, kr, b);
619 }
620 #define new_args_tail(k,kr,b) new_args_tail_gen(parser, (k),(kr),(b))
621 
622 #define FIXME 0
623 
624 #endif /* RIPPER */
625 
626 #ifndef RIPPER
627 # define Qnone 0
628 # define ifndef_ripper(x) (x)
629 #else
630 # define Qnone Qnil
631 # define ifndef_ripper(x)
632 #endif
633 
634 #ifndef RIPPER
635 # define rb_warn0(fmt) rb_compile_warn(ruby_sourcefile, ruby_sourceline, (fmt))
636 # define rb_warnI(fmt,a) rb_compile_warn(ruby_sourcefile, ruby_sourceline, (fmt), (a))
637 # define rb_warnS(fmt,a) rb_compile_warn(ruby_sourcefile, ruby_sourceline, (fmt), (a))
638 # define rb_warn4S(file,line,fmt,a) rb_compile_warn((file), (line), (fmt), (a))
639 # define rb_warning0(fmt) rb_compile_warning(ruby_sourcefile, ruby_sourceline, (fmt))
640 # define rb_warningS(fmt,a) rb_compile_warning(ruby_sourcefile, ruby_sourceline, (fmt), (a))
641 #else
642 # define rb_warn0(fmt) ripper_warn0(parser, (fmt))
643 # define rb_warnI(fmt,a) ripper_warnI(parser, (fmt), (a))
644 # define rb_warnS(fmt,a) ripper_warnS(parser, (fmt), (a))
645 # define rb_warn4S(file,line,fmt,a) ripper_warnS(parser, (fmt), (a))
646 # define rb_warning0(fmt) ripper_warning0(parser, (fmt))
647 # define rb_warningS(fmt,a) ripper_warningS(parser, (fmt), (a))
648 static void ripper_warn0(struct parser_params*, const char*);
649 static void ripper_warnI(struct parser_params*, const char*, int);
650 static void ripper_warnS(struct parser_params*, const char*, const char*);
651 static void ripper_warning0(struct parser_params*, const char*);
652 static void ripper_warningS(struct parser_params*, const char*, const char*);
653 #endif
654 
655 #ifdef RIPPER
656 static void ripper_compile_error(struct parser_params*, const char *fmt, ...);
657 # define rb_compile_error ripper_compile_error
658 # define compile_error ripper_compile_error
659 # define PARSER_ARG parser,
660 #else
661 # define rb_compile_error rb_compile_error_with_enc
662 # define compile_error parser->nerr++,rb_compile_error_with_enc
663 # define PARSER_ARG ruby_sourcefile, ruby_sourceline, current_enc,
664 #endif
665 
666 /* Older versions of Yacc set YYMAXDEPTH to a very low value by default (150,
667  for instance). This is too low for Ruby to parse some files, such as
668  date/format.rb, therefore bump the value up to at least Bison's default. */
669 #ifdef OLD_YACC
670 #ifndef YYMAXDEPTH
671 #define YYMAXDEPTH 10000
672 #endif
673 #endif
674 
675 #ifndef RIPPER
676 static void token_info_push(struct parser_params*, const char *token);
677 static void token_info_pop(struct parser_params*, const char *token);
678 #define token_info_push(token) (RTEST(ruby_verbose) ? token_info_push(parser, (token)) : (void)0)
679 #define token_info_pop(token) (RTEST(ruby_verbose) ? token_info_pop(parser, (token)) : (void)0)
680 #else
681 #define token_info_push(token) /* nothing */
682 #define token_info_pop(token) /* nothing */
683 #endif
684 %}
685 
686 %pure-parser
687 %lex-param {struct parser_params *parser}
688 %parse-param {struct parser_params *parser}
689 
690 %union {
691  VALUE val;
692  NODE *node;
693  ID id;
694  int num;
695  const struct vtable *vars;
696 }
697 
698 /*%%%*/
699 %token
700 /*%
701 %token <val>
702 %*/
711  keyword_if
725  keyword_in
726  keyword_do
738  keyword_or
752 
754 %token <node> tINTEGER tFLOAT tSTRING_CONTENT tCHAR
755 %token <node> tNTH_REF tBACK_REF
756 %token <num> tREGEXP_END
757 
758 %type <node> singleton strings string string1 xstring regexp
759 %type <node> string_contents xstring_contents regexp_contents string_content
760 %type <node> words symbols symbol_list qwords qsymbols word_list qword_list qsym_list word
761 %type <node> literal numeric dsym cpath
762 %type <node> top_compstmt top_stmts top_stmt
763 %type <node> bodystmt compstmt stmts stmt_or_begin stmt expr arg primary command command_call method_call
764 %type <node> expr_value arg_value primary_value fcall
765 %type <node> if_tail opt_else case_body cases opt_rescue exc_list exc_var opt_ensure
766 %type <node> args call_args opt_call_args
767 %type <node> paren_args opt_paren_args args_tail opt_args_tail block_args_tail opt_block_args_tail
768 %type <node> command_args aref_args opt_block_arg block_arg var_ref var_lhs
769 %type <node> command_asgn mrhs superclass block_call block_command
770 %type <node> f_block_optarg f_block_opt
771 %type <node> f_arglist f_args f_arg f_arg_item f_optarg f_marg f_marg_list f_margs
772 %type <node> assoc_list assocs assoc undef_list backref string_dvar for_var
773 %type <node> block_param opt_block_param block_param_def f_opt
774 %type <node> f_kwarg f_kw f_block_kwarg f_block_kw
775 %type <node> bv_decls opt_bv_decl bvar
776 %type <node> lambda f_larglist lambda_body
777 %type <node> brace_block cmd_brace_block do_block lhs none fitem
779 %type <id> fsym keyword_variable user_variable sym symbol operation operation2 operation3
780 %type <id> cname fname op f_rest_arg f_block_arg opt_f_block_arg f_norm_arg f_bad_arg
781 %type <id> f_kwrest
782 /*%%%*/
783 /*%
784 %type <val> program reswords then do dot_or_colon
785 %*/
786 %token END_OF_INPUT 0 "end-of-input"
787 %token tUPLUS RUBY_TOKEN(UPLUS) "unary+"
788 %token tUMINUS RUBY_TOKEN(UMINUS) "unary-"
789 %token tPOW RUBY_TOKEN(POW) "**"
790 %token tCMP RUBY_TOKEN(CMP) "<=>"
791 %token tEQ RUBY_TOKEN(EQ) "=="
792 %token tEQQ RUBY_TOKEN(EQQ) "==="
793 %token tNEQ RUBY_TOKEN(NEQ) "!="
794 %token tGEQ RUBY_TOKEN(GEQ) ">="
795 %token tLEQ RUBY_TOKEN(LEQ) "<="
796 %token tANDOP "&&"
797 %token tOROP "||"
799 %token tNMATCH RUBY_TOKEN(NMATCH) "!~"
800 %token tDOT2 RUBY_TOKEN(DOT2) ".."
801 %token tDOT3 RUBY_TOKEN(DOT3) "..."
802 %token tAREF RUBY_TOKEN(AREF) "[]"
803 %token tASET RUBY_TOKEN(ASET) "[]="
804 %token tLSHFT RUBY_TOKEN(LSHFT) "<<"
805 %token tRSHFT RUBY_TOKEN(RSHFT) ">>"
806 %token tCOLON2 "::"
807 %token tCOLON3 ":: at EXPR_BEG"
808 %token <id> tOP_ASGN /* +=, -= etc. */
809 %token tASSOC "=>"
810 %token tLPAREN "("
811 %token tLPAREN_ARG "( arg"
812 %token tRPAREN ")"
813 %token tLBRACK "["
814 %token tLBRACE "{"
815 %token tLBRACE_ARG "{ arg"
816 %token tSTAR "*"
817 %token tDSTAR "**arg"
818 %token tAMPER "&"
819 %token tLAMBDA "->"
822 
823 /*
824  * precedence table
825  */
826 
827 %nonassoc tLOWEST
828 %nonassoc tLBRACE_ARG
829 
832 %right keyword_not
833 %nonassoc keyword_defined
834 %right '=' tOP_ASGN
835 %left modifier_rescue
836 %right '?' ':'
837 %nonassoc tDOT2 tDOT3
838 %left tOROP
839 %left tANDOP
840 %nonassoc tCMP tEQ tEQQ tNEQ tMATCH tNMATCH
841 %left '>' tGEQ '<' tLEQ
842 %left '|' '^'
843 %left '&'
844 %left tLSHFT tRSHFT
845 %left '+' '-'
846 %left '*' '/' '%'
847 %right tUMINUS_NUM tUMINUS
848 %right tPOW
849 %right '!' '~' tUPLUS
850 
852 
853 %%
854 program : {
855  lex_state = EXPR_BEG;
856  /*%%%*/
858  /*%
859  local_push(0);
860  %*/
861  }
862  top_compstmt
863  {
864  /*%%%*/
865  if ($2 && !compile_for_eval) {
866  /* last expression should not be void */
867  if (nd_type($2) != NODE_BLOCK) void_expr($2);
868  else {
869  NODE *node = $2;
870  while (node->nd_next) {
871  node = node->nd_next;
872  }
873  void_expr(node->nd_head);
874  }
875  }
877  /*%
878  $$ = $2;
879  parser->result = dispatch1(program, $$);
880  %*/
881  local_pop();
882  }
883  ;
884 
885 top_compstmt : top_stmts opt_terms
886  {
887  /*%%%*/
890  /*%
891  %*/
892  $$ = $1;
893  }
894  ;
895 
896 top_stmts : none
897  {
898  /*%%%*/
899  $$ = NEW_BEGIN(0);
900  /*%
901  $$ = dispatch2(stmts_add, dispatch0(stmts_new),
902  dispatch0(void_stmt));
903  %*/
904  }
905  | top_stmt
906  {
907  /*%%%*/
908  $$ = newline_node($1);
909  /*%
910  $$ = dispatch2(stmts_add, dispatch0(stmts_new), $1);
911  %*/
912  }
913  | top_stmts terms top_stmt
914  {
915  /*%%%*/
916  $$ = block_append($1, newline_node($3));
917  /*%
918  $$ = dispatch2(stmts_add, $1, $3);
919  %*/
920  }
921  | error top_stmt
922  {
923  $$ = remove_begin($2);
924  }
925  ;
926 
927 top_stmt : stmt
928  | keyword_BEGIN
929  {
930  /*%%%*/
931  /* local_push(0); */
932  /*%
933  %*/
934  }
935  '{' top_compstmt '}'
936  {
937  /*%%%*/
939  $4);
940  /* NEW_PREEXE($4)); */
941  /* local_pop(); */
942  $$ = NEW_BEGIN(0);
943  /*%
944  $$ = dispatch1(BEGIN, $4);
945  %*/
946  }
947  ;
948 
950  opt_rescue
951  opt_else
952  opt_ensure
953  {
954  /*%%%*/
955  $$ = $1;
956  if ($2) {
957  $$ = NEW_RESCUE($1, $2, $3);
958  }
959  else if ($3) {
960  rb_warn0("else without rescue is useless");
961  $$ = block_append($$, $3);
962  }
963  if ($4) {
964  if ($$) {
965  $$ = NEW_ENSURE($$, $4);
966  }
967  else {
968  $$ = block_append($4, NEW_NIL());
969  }
970  }
971  fixpos($$, $1);
972  /*%
973  $$ = dispatch4(bodystmt,
974  escape_Qundef($1),
975  escape_Qundef($2),
976  escape_Qundef($3),
977  escape_Qundef($4));
978  %*/
979  }
980  ;
981 
982 compstmt : stmts opt_terms
983  {
984  /*%%%*/
985  void_stmts($1);
987  /*%
988  %*/
989  $$ = $1;
990  }
991  ;
992 
993 stmts : none
994  {
995  /*%%%*/
996  $$ = NEW_BEGIN(0);
997  /*%
998  $$ = dispatch2(stmts_add, dispatch0(stmts_new),
999  dispatch0(void_stmt));
1000  %*/
1001  }
1002  | stmt_or_begin
1003  {
1004  /*%%%*/
1005  $$ = newline_node($1);
1006  /*%
1007  $$ = dispatch2(stmts_add, dispatch0(stmts_new), $1);
1008  %*/
1009  }
1010  | stmts terms stmt_or_begin
1011  {
1012  /*%%%*/
1013  $$ = block_append($1, newline_node($3));
1014  /*%
1015  $$ = dispatch2(stmts_add, $1, $3);
1016  %*/
1017  }
1018  | error stmt
1019  {
1020  $$ = remove_begin($2);
1021  }
1022  ;
1023 
1025  {
1026  $$ = $1;
1027  }
1028  | keyword_BEGIN
1029  {
1030  yyerror("BEGIN is permitted only at toplevel");
1031  /*%%%*/
1032  /* local_push(0); */
1033  /*%
1034  %*/
1035  }
1036  '{' top_compstmt '}'
1037  {
1038  /*%%%*/
1040  $4);
1041  /* NEW_PREEXE($4)); */
1042  /* local_pop(); */
1043  $$ = NEW_BEGIN(0);
1044  /*%
1045  $$ = dispatch1(BEGIN, $4);
1046  %*/
1047  }
1048 
1049 stmt : keyword_alias fitem {lex_state = EXPR_FNAME;} fitem
1050  {
1051  /*%%%*/
1052  $$ = NEW_ALIAS($2, $4);
1053  /*%
1054  $$ = dispatch2(alias, $2, $4);
1055  %*/
1056  }
1058  {
1059  /*%%%*/
1060  $$ = NEW_VALIAS($2, $3);
1061  /*%
1062  $$ = dispatch2(var_alias, $2, $3);
1063  %*/
1064  }
1066  {
1067  /*%%%*/
1068  char buf[2];
1069  buf[0] = '$';
1070  buf[1] = (char)$3->nd_nth;
1071  $$ = NEW_VALIAS($2, rb_intern2(buf, 2));
1072  /*%
1073  $$ = dispatch2(var_alias, $2, $3);
1074  %*/
1075  }
1077  {
1078  /*%%%*/
1079  yyerror("can't make alias for the number variables");
1080  $$ = NEW_BEGIN(0);
1081  /*%
1082  $$ = dispatch2(var_alias, $2, $3);
1083  $$ = dispatch1(alias_error, $$);
1084  %*/
1085  }
1086  | keyword_undef undef_list
1087  {
1088  /*%%%*/
1089  $$ = $2;
1090  /*%
1091  $$ = dispatch1(undef, $2);
1092  %*/
1093  }
1094  | stmt modifier_if expr_value
1095  {
1096  /*%%%*/
1097  $$ = NEW_IF(cond($3), remove_begin($1), 0);
1098  fixpos($$, $3);
1099  /*%
1100  $$ = dispatch2(if_mod, $3, $1);
1101  %*/
1102  }
1103  | stmt modifier_unless expr_value
1104  {
1105  /*%%%*/
1106  $$ = NEW_UNLESS(cond($3), remove_begin($1), 0);
1107  fixpos($$, $3);
1108  /*%
1109  $$ = dispatch2(unless_mod, $3, $1);
1110  %*/
1111  }
1112  | stmt modifier_while expr_value
1113  {
1114  /*%%%*/
1115  if ($1 && nd_type($1) == NODE_BEGIN) {
1116  $$ = NEW_WHILE(cond($3), $1->nd_body, 0);
1117  }
1118  else {
1119  $$ = NEW_WHILE(cond($3), $1, 1);
1120  }
1121  /*%
1122  $$ = dispatch2(while_mod, $3, $1);
1123  %*/
1124  }
1125  | stmt modifier_until expr_value
1126  {
1127  /*%%%*/
1128  if ($1 && nd_type($1) == NODE_BEGIN) {
1129  $$ = NEW_UNTIL(cond($3), $1->nd_body, 0);
1130  }
1131  else {
1132  $$ = NEW_UNTIL(cond($3), $1, 1);
1133  }
1134  /*%
1135  $$ = dispatch2(until_mod, $3, $1);
1136  %*/
1137  }
1139  {
1140  /*%%%*/
1141  NODE *resq = NEW_RESBODY(0, remove_begin($3), 0);
1142  $$ = NEW_RESCUE(remove_begin($1), resq, 0);
1143  /*%
1144  $$ = dispatch2(rescue_mod, $1, $3);
1145  %*/
1146  }
1147  | keyword_END '{' compstmt '}'
1148  {
1149  if (in_def || in_single) {
1150  rb_warn0("END in method; use at_exit");
1151  }
1152  /*%%%*/
1153  $$ = NEW_POSTEXE(NEW_NODE(
1154  NODE_SCOPE, 0 /* tbl */, $3 /* body */, 0 /* args */));
1155  /*%
1156  $$ = dispatch1(END, $3);
1157  %*/
1158  }
1159  | command_asgn
1160  | mlhs '=' command_call
1161  {
1162  /*%%%*/
1163  value_expr($3);
1164  $1->nd_value = $3;
1165  $$ = $1;
1166  /*%
1167  $$ = dispatch2(massign, $1, $3);
1168  %*/
1169  }
1170  | var_lhs tOP_ASGN command_call
1171  {
1172  value_expr($3);
1173  $$ = new_op_assign($1, $2, $3);
1174  }
1175  | primary_value '[' opt_call_args rbracket tOP_ASGN command_call
1176  {
1177  /*%%%*/
1178  NODE *args;
1179 
1180  value_expr($6);
1181  if (!$3) $3 = NEW_ZARRAY();
1182  args = arg_concat($3, $6);
1183  if ($5 == tOROP) {
1184  $5 = 0;
1185  }
1186  else if ($5 == tANDOP) {
1187  $5 = 1;
1188  }
1189  $$ = NEW_OP_ASGN1($1, $5, args);
1190  fixpos($$, $1);
1191  /*%
1192  $$ = dispatch2(aref_field, $1, escape_Qundef($3));
1193  $$ = dispatch3(opassign, $$, $5, $6);
1194  %*/
1195  }
1196  | primary_value '.' tIDENTIFIER tOP_ASGN command_call
1197  {
1198  value_expr($5);
1199  $$ = new_attr_op_assign($1, ripper_id2sym('.'), $3, $4, $5);
1200  }
1201  | primary_value '.' tCONSTANT tOP_ASGN command_call
1202  {
1203  value_expr($5);
1204  $$ = new_attr_op_assign($1, ripper_id2sym('.'), $3, $4, $5);
1205  }
1206  | primary_value tCOLON2 tCONSTANT tOP_ASGN command_call
1207  {
1208  /*%%%*/
1209  $$ = NEW_COLON2($1, $3);
1210  $$ = new_const_op_assign($$, $4, $5);
1211  /*%
1212  $$ = dispatch2(const_path_field, $1, $3);
1213  $$ = dispatch3(opassign, $$, $4, $5);
1214  %*/
1215  }
1216  | primary_value tCOLON2 tIDENTIFIER tOP_ASGN command_call
1217  {
1218  value_expr($5);
1219  $$ = new_attr_op_assign($1, ripper_intern("::"), $3, $4, $5);
1220  }
1221  | backref tOP_ASGN command_call
1222  {
1223  /*%%%*/
1224  rb_backref_error($1);
1225  $$ = NEW_BEGIN(0);
1226  /*%
1227  $$ = dispatch2(assign, dispatch1(var_field, $1), $3);
1228  $$ = dispatch1(assign_error, $$);
1229  %*/
1230  }
1231  | lhs '=' mrhs
1232  {
1233  /*%%%*/
1234  value_expr($3);
1235  $$ = node_assign($1, $3);
1236  /*%
1237  $$ = dispatch2(assign, $1, $3);
1238  %*/
1239  }
1240  | mlhs '=' arg_value
1241  {
1242  /*%%%*/
1243  $1->nd_value = $3;
1244  $$ = $1;
1245  /*%
1246  $$ = dispatch2(massign, $1, $3);
1247  %*/
1248  }
1249  | mlhs '=' mrhs
1250  {
1251  /*%%%*/
1252  $1->nd_value = $3;
1253  $$ = $1;
1254  /*%
1255  $$ = dispatch2(massign, $1, $3);
1256  %*/
1257  }
1258  | expr
1259  ;
1260 
1261 command_asgn : lhs '=' command_call
1262  {
1263  /*%%%*/
1264  value_expr($3);
1265  $$ = node_assign($1, $3);
1266  /*%
1267  $$ = dispatch2(assign, $1, $3);
1268  %*/
1269  }
1270  | lhs '=' command_asgn
1271  {
1272  /*%%%*/
1273  value_expr($3);
1274  $$ = node_assign($1, $3);
1275  /*%
1276  $$ = dispatch2(assign, $1, $3);
1277  %*/
1278  }
1279  ;
1280 
1281 
1284  {
1285  /*%%%*/
1286  $$ = logop(NODE_AND, $1, $3);
1287  /*%
1288  $$ = dispatch3(binary, $1, ripper_intern("and"), $3);
1289  %*/
1290  }
1291  | expr keyword_or expr
1292  {
1293  /*%%%*/
1294  $$ = logop(NODE_OR, $1, $3);
1295  /*%
1296  $$ = dispatch3(binary, $1, ripper_intern("or"), $3);
1297  %*/
1298  }
1299  | keyword_not opt_nl expr
1300  {
1301  /*%%%*/
1302  $$ = call_uni_op(cond($3), '!');
1303  /*%
1304  $$ = dispatch2(unary, ripper_intern("not"), $3);
1305  %*/
1306  }
1307  | '!' command_call
1308  {
1309  /*%%%*/
1310  $$ = call_uni_op(cond($2), '!');
1311  /*%
1312  $$ = dispatch2(unary, ripper_id2sym('!'), $2);
1313  %*/
1314  }
1315  | arg
1316  ;
1317 
1318 expr_value : expr
1319  {
1320  /*%%%*/
1322  $$ = $1;
1323  if (!$$) $$ = NEW_NIL();
1324  /*%
1325  $$ = $1;
1326  %*/
1327  }
1328  ;
1329 
1330 command_call : command
1331  | block_command
1332  ;
1333 
1334 block_command : block_call
1335  | block_call dot_or_colon operation2 command_args
1336  {
1337  /*%%%*/
1338  $$ = NEW_CALL($1, $3, $4);
1339  /*%
1340  $$ = dispatch3(call, $1, $2, $3);
1341  $$ = method_arg($$, $4);
1342  %*/
1343  }
1344  ;
1345 
1347  {
1348  $<vars>1 = dyna_push();
1349  /*%%%*/
1350  $<num>$ = ruby_sourceline;
1351  /*%
1352  %*/
1353  }
1354  opt_block_param
1355  compstmt
1356  '}'
1357  {
1358  /*%%%*/
1359  $$ = NEW_ITER($3,$4);
1360  nd_set_line($$, $<num>2);
1361  /*%
1362  $$ = dispatch2(brace_block, escape_Qundef($3), $4);
1363  %*/
1364  dyna_pop($<vars>1);
1365  }
1366  ;
1367 
1368 fcall : operation
1369  {
1370  /*%%%*/
1371  $$ = NEW_FCALL($1, 0);
1372  nd_set_line($$, tokline);
1373  /*%
1374  %*/
1375  }
1376  ;
1377 
1378 command : fcall command_args %prec tLOWEST
1379  {
1380  /*%%%*/
1381  $$ = $1;
1382  $$->nd_args = $2;
1383  /*%
1384  $$ = dispatch2(command, $1, $2);
1385  %*/
1386  }
1388  {
1389  /*%%%*/
1390  block_dup_check($2,$3);
1391  $1->nd_args = $2;
1392  $3->nd_iter = $1;
1393  $$ = $3;
1394  fixpos($$, $1);
1395  /*%
1396  $$ = dispatch2(command, $1, $2);
1397  $$ = method_add_block($$, $3);
1398  %*/
1399  }
1400  | primary_value '.' operation2 command_args %prec tLOWEST
1401  {
1402  /*%%%*/
1403  $$ = NEW_CALL($1, $3, $4);
1404  fixpos($$, $1);
1405  /*%
1406  $$ = dispatch4(command_call, $1, ripper_id2sym('.'), $3, $4);
1407  %*/
1408  }
1409  | primary_value '.' operation2 command_args cmd_brace_block
1410  {
1411  /*%%%*/
1412  block_dup_check($4,$5);
1413  $5->nd_iter = NEW_CALL($1, $3, $4);
1414  $$ = $5;
1415  fixpos($$, $1);
1416  /*%
1417  $$ = dispatch4(command_call, $1, ripper_id2sym('.'), $3, $4);
1418  $$ = method_add_block($$, $5);
1419  %*/
1420  }
1421  | primary_value tCOLON2 operation2 command_args %prec tLOWEST
1422  {
1423  /*%%%*/
1424  $$ = NEW_CALL($1, $3, $4);
1425  fixpos($$, $1);
1426  /*%
1427  $$ = dispatch4(command_call, $1, ripper_intern("::"), $3, $4);
1428  %*/
1429  }
1430  | primary_value tCOLON2 operation2 command_args cmd_brace_block
1431  {
1432  /*%%%*/
1433  block_dup_check($4,$5);
1434  $5->nd_iter = NEW_CALL($1, $3, $4);
1435  $$ = $5;
1436  fixpos($$, $1);
1437  /*%
1438  $$ = dispatch4(command_call, $1, ripper_intern("::"), $3, $4);
1439  $$ = method_add_block($$, $5);
1440  %*/
1441  }
1443  {
1444  /*%%%*/
1445  $$ = NEW_SUPER($2);
1446  fixpos($$, $2);
1447  /*%
1448  $$ = dispatch1(super, $2);
1449  %*/
1450  }
1452  {
1453  /*%%%*/
1454  $$ = new_yield($2);
1455  fixpos($$, $2);
1456  /*%
1457  $$ = dispatch1(yield, $2);
1458  %*/
1459  }
1461  {
1462  /*%%%*/
1463  $$ = NEW_RETURN(ret_args($2));
1464  /*%
1465  $$ = dispatch1(return, $2);
1466  %*/
1467  }
1469  {
1470  /*%%%*/
1471  $$ = NEW_BREAK(ret_args($2));
1472  /*%
1473  $$ = dispatch1(break, $2);
1474  %*/
1475  }
1477  {
1478  /*%%%*/
1479  $$ = NEW_NEXT(ret_args($2));
1480  /*%
1481  $$ = dispatch1(next, $2);
1482  %*/
1483  }
1484  ;
1485 
1486 mlhs : mlhs_basic
1487  | tLPAREN mlhs_inner rparen
1488  {
1489  /*%%%*/
1490  $$ = $2;
1491  /*%
1492  $$ = dispatch1(mlhs_paren, $2);
1493  %*/
1494  }
1495  ;
1496 
1498  | tLPAREN mlhs_inner rparen
1499  {
1500  /*%%%*/
1501  $$ = NEW_MASGN(NEW_LIST($2), 0);
1502  /*%
1503  $$ = dispatch1(mlhs_paren, $2);
1504  %*/
1505  }
1506  ;
1507 
1509  {
1510  /*%%%*/
1511  $$ = NEW_MASGN($1, 0);
1512  /*%
1513  $$ = $1;
1514  %*/
1515  }
1517  {
1518  /*%%%*/
1519  $$ = NEW_MASGN(list_append($1,$2), 0);
1520  /*%
1521  $$ = mlhs_add($1, $2);
1522  %*/
1523  }
1525  {
1526  /*%%%*/
1527  $$ = NEW_MASGN($1, $3);
1528  /*%
1529  $$ = mlhs_add_star($1, $3);
1530  %*/
1531  }
1533  {
1534  /*%%%*/
1535  $$ = NEW_MASGN($1, NEW_POSTARG($3,$5));
1536  /*%
1537  $1 = mlhs_add_star($1, $3);
1538  $$ = mlhs_add($1, $5);
1539  %*/
1540  }
1541  | mlhs_head tSTAR
1542  {
1543  /*%%%*/
1544  $$ = NEW_MASGN($1, -1);
1545  /*%
1546  $$ = mlhs_add_star($1, Qnil);
1547  %*/
1548  }
1549  | mlhs_head tSTAR ',' mlhs_post
1550  {
1551  /*%%%*/
1552  $$ = NEW_MASGN($1, NEW_POSTARG(-1, $4));
1553  /*%
1554  $1 = mlhs_add_star($1, Qnil);
1555  $$ = mlhs_add($1, $4);
1556  %*/
1557  }
1558  | tSTAR mlhs_node
1559  {
1560  /*%%%*/
1561  $$ = NEW_MASGN(0, $2);
1562  /*%
1563  $$ = mlhs_add_star(mlhs_new(), $2);
1564  %*/
1565  }
1566  | tSTAR mlhs_node ',' mlhs_post
1567  {
1568  /*%%%*/
1569  $$ = NEW_MASGN(0, NEW_POSTARG($2,$4));
1570  /*%
1571  $2 = mlhs_add_star(mlhs_new(), $2);
1572  $$ = mlhs_add($2, $4);
1573  %*/
1574  }
1575  | tSTAR
1576  {
1577  /*%%%*/
1578  $$ = NEW_MASGN(0, -1);
1579  /*%
1580  $$ = mlhs_add_star(mlhs_new(), Qnil);
1581  %*/
1582  }
1583  | tSTAR ',' mlhs_post
1584  {
1585  /*%%%*/
1586  $$ = NEW_MASGN(0, NEW_POSTARG(-1, $3));
1587  /*%
1588  $$ = mlhs_add_star(mlhs_new(), Qnil);
1589  $$ = mlhs_add($$, $3);
1590  %*/
1591  }
1592  ;
1593 
1595  | tLPAREN mlhs_inner rparen
1596  {
1597  /*%%%*/
1598  $$ = $2;
1599  /*%
1600  $$ = dispatch1(mlhs_paren, $2);
1601  %*/
1602  }
1603  ;
1604 
1605 mlhs_head : mlhs_item ','
1606  {
1607  /*%%%*/
1608  $$ = NEW_LIST($1);
1609  /*%
1610  $$ = mlhs_add(mlhs_new(), $1);
1611  %*/
1612  }
1613  | mlhs_head mlhs_item ','
1614  {
1615  /*%%%*/
1616  $$ = list_append($1, $2);
1617  /*%
1618  $$ = mlhs_add($1, $2);
1619  %*/
1620  }
1621  ;
1622 
1624  {
1625  /*%%%*/
1626  $$ = NEW_LIST($1);
1627  /*%
1628  $$ = mlhs_add(mlhs_new(), $1);
1629  %*/
1630  }
1631  | mlhs_post ',' mlhs_item
1632  {
1633  /*%%%*/
1634  $$ = list_append($1, $3);
1635  /*%
1636  $$ = mlhs_add($1, $3);
1637  %*/
1638  }
1639  ;
1640 
1641 mlhs_node : user_variable
1642  {
1643  $$ = assignable($1, 0);
1644  }
1646  {
1647  $$ = assignable($1, 0);
1648  }
1649  | primary_value '[' opt_call_args rbracket
1650  {
1651  /*%%%*/
1652  $$ = aryset($1, $3);
1653  /*%
1654  $$ = dispatch2(aref_field, $1, escape_Qundef($3));
1655  %*/
1656  }
1657  | primary_value '.' tIDENTIFIER
1658  {
1659  /*%%%*/
1660  $$ = attrset($1, $3);
1661  /*%
1662  $$ = dispatch3(field, $1, ripper_id2sym('.'), $3);
1663  %*/
1664  }
1665  | primary_value tCOLON2 tIDENTIFIER
1666  {
1667  /*%%%*/
1668  $$ = attrset($1, $3);
1669  /*%
1670  $$ = dispatch2(const_path_field, $1, $3);
1671  %*/
1672  }
1673  | primary_value '.' tCONSTANT
1674  {
1675  /*%%%*/
1676  $$ = attrset($1, $3);
1677  /*%
1678  $$ = dispatch3(field, $1, ripper_id2sym('.'), $3);
1679  %*/
1680  }
1681  | primary_value tCOLON2 tCONSTANT
1682  {
1683  /*%%%*/
1684  if (in_def || in_single)
1685  yyerror("dynamic constant assignment");
1686  $$ = NEW_CDECL(0, 0, NEW_COLON2($1, $3));
1687  /*%
1688  if (in_def || in_single)
1689  yyerror("dynamic constant assignment");
1690  $$ = dispatch2(const_path_field, $1, $3);
1691  %*/
1692  }
1693  | tCOLON3 tCONSTANT
1694  {
1695  /*%%%*/
1696  if (in_def || in_single)
1697  yyerror("dynamic constant assignment");
1698  $$ = NEW_CDECL(0, 0, NEW_COLON3($2));
1699  /*%
1700  $$ = dispatch1(top_const_field, $2);
1701  %*/
1702  }
1703  | backref
1704  {
1705  /*%%%*/
1706  rb_backref_error($1);
1707  $$ = NEW_BEGIN(0);
1708  /*%
1709  $$ = dispatch1(var_field, $1);
1710  $$ = dispatch1(assign_error, $$);
1711  %*/
1712  }
1713  ;
1714 
1715 lhs : user_variable
1716  {
1717  $$ = assignable($1, 0);
1718  /*%%%*/
1719  if (!$$) $$ = NEW_BEGIN(0);
1720  /*%
1721  $$ = dispatch1(var_field, $$);
1722  %*/
1723  }
1725  {
1726  $$ = assignable($1, 0);
1727  /*%%%*/
1728  if (!$$) $$ = NEW_BEGIN(0);
1729  /*%
1730  $$ = dispatch1(var_field, $$);
1731  %*/
1732  }
1733  | primary_value '[' opt_call_args rbracket
1734  {
1735  /*%%%*/
1736  $$ = aryset($1, $3);
1737  /*%
1738  $$ = dispatch2(aref_field, $1, escape_Qundef($3));
1739  %*/
1740  }
1741  | primary_value '.' tIDENTIFIER
1742  {
1743  /*%%%*/
1744  $$ = attrset($1, $3);
1745  /*%
1746  $$ = dispatch3(field, $1, ripper_id2sym('.'), $3);
1747  %*/
1748  }
1749  | primary_value tCOLON2 tIDENTIFIER
1750  {
1751  /*%%%*/
1752  $$ = attrset($1, $3);
1753  /*%
1754  $$ = dispatch3(field, $1, ripper_intern("::"), $3);
1755  %*/
1756  }
1757  | primary_value '.' tCONSTANT
1758  {
1759  /*%%%*/
1760  $$ = attrset($1, $3);
1761  /*%
1762  $$ = dispatch3(field, $1, ripper_id2sym('.'), $3);
1763  %*/
1764  }
1765  | primary_value tCOLON2 tCONSTANT
1766  {
1767  /*%%%*/
1768  if (in_def || in_single)
1769  yyerror("dynamic constant assignment");
1770  $$ = NEW_CDECL(0, 0, NEW_COLON2($1, $3));
1771  /*%
1772  $$ = dispatch2(const_path_field, $1, $3);
1773  if (in_def || in_single) {
1774  $$ = dispatch1(assign_error, $$);
1775  }
1776  %*/
1777  }
1778  | tCOLON3 tCONSTANT
1779  {
1780  /*%%%*/
1781  if (in_def || in_single)
1782  yyerror("dynamic constant assignment");
1783  $$ = NEW_CDECL(0, 0, NEW_COLON3($2));
1784  /*%
1785  $$ = dispatch1(top_const_field, $2);
1786  if (in_def || in_single) {
1787  $$ = dispatch1(assign_error, $$);
1788  }
1789  %*/
1790  }
1791  | backref
1792  {
1793  /*%%%*/
1794  rb_backref_error($1);
1795  $$ = NEW_BEGIN(0);
1796  /*%
1797  $$ = dispatch1(assign_error, $1);
1798  %*/
1799  }
1800  ;
1801 
1802 cname : tIDENTIFIER
1803  {
1804  /*%%%*/
1805  yyerror("class/module name must be CONSTANT");
1806  /*%
1807  $$ = dispatch1(class_name_error, $1);
1808  %*/
1809  }
1810  | tCONSTANT
1811  ;
1812 
1813 cpath : tCOLON3 cname
1814  {
1815  /*%%%*/
1816  $$ = NEW_COLON3($2);
1817  /*%
1818  $$ = dispatch1(top_const_ref, $2);
1819  %*/
1820  }
1821  | cname
1822  {
1823  /*%%%*/
1824  $$ = NEW_COLON2(0, $$);
1825  /*%
1826  $$ = dispatch1(const_ref, $1);
1827  %*/
1828  }
1829  | primary_value tCOLON2 cname
1830  {
1831  /*%%%*/
1832  $$ = NEW_COLON2($1, $3);
1833  /*%
1834  $$ = dispatch2(const_path_ref, $1, $3);
1835  %*/
1836  }
1837  ;
1838 
1839 fname : tIDENTIFIER
1840  | tCONSTANT
1841  | tFID
1842  | op
1843  {
1844  lex_state = EXPR_ENDFN;
1845  $$ = $1;
1846  }
1847  | reswords
1848  {
1849  lex_state = EXPR_ENDFN;
1850  /*%%%*/
1851  $$ = $<id>1;
1852  /*%
1853  $$ = $1;
1854  %*/
1855  }
1856  ;
1857 
1858 fsym : fname
1859  | symbol
1860  ;
1861 
1862 fitem : fsym
1863  {
1864  /*%%%*/
1865  $$ = NEW_LIT(ID2SYM($1));
1866  /*%
1867  $$ = dispatch1(symbol_literal, $1);
1868  %*/
1869  }
1870  | dsym
1871  ;
1872 
1873 undef_list : fitem
1874  {
1875  /*%%%*/
1876  $$ = NEW_UNDEF($1);
1877  /*%
1878  $$ = rb_ary_new3(1, $1);
1879  %*/
1880  }
1881  | undef_list ',' {lex_state = EXPR_FNAME;} fitem
1882  {
1883  /*%%%*/
1884  $$ = block_append($1, NEW_UNDEF($4));
1885  /*%
1886  rb_ary_push($1, $4);
1887  %*/
1888  }
1889  ;
1890 
1891 op : '|' { ifndef_ripper($$ = '|'); }
1892  | '^' { ifndef_ripper($$ = '^'); }
1893  | '&' { ifndef_ripper($$ = '&'); }
1894  | tCMP { ifndef_ripper($$ = tCMP); }
1895  | tEQ { ifndef_ripper($$ = tEQ); }
1896  | tEQQ { ifndef_ripper($$ = tEQQ); }
1897  | tMATCH { ifndef_ripper($$ = tMATCH); }
1898  | tNMATCH { ifndef_ripper($$ = tNMATCH); }
1899  | '>' { ifndef_ripper($$ = '>'); }
1900  | tGEQ { ifndef_ripper($$ = tGEQ); }
1901  | '<' { ifndef_ripper($$ = '<'); }
1902  | tLEQ { ifndef_ripper($$ = tLEQ); }
1903  | tNEQ { ifndef_ripper($$ = tNEQ); }
1904  | tLSHFT { ifndef_ripper($$ = tLSHFT); }
1905  | tRSHFT { ifndef_ripper($$ = tRSHFT); }
1906  | '+' { ifndef_ripper($$ = '+'); }
1907  | '-' { ifndef_ripper($$ = '-'); }
1908  | '*' { ifndef_ripper($$ = '*'); }
1909  | tSTAR { ifndef_ripper($$ = '*'); }
1910  | '/' { ifndef_ripper($$ = '/'); }
1911  | '%' { ifndef_ripper($$ = '%'); }
1912  | tPOW { ifndef_ripper($$ = tPOW); }
1913  | tDSTAR { ifndef_ripper($$ = tDSTAR); }
1914  | '!' { ifndef_ripper($$ = '!'); }
1915  | '~' { ifndef_ripper($$ = '~'); }
1916  | tUPLUS { ifndef_ripper($$ = tUPLUS); }
1917  | tUMINUS { ifndef_ripper($$ = tUMINUS); }
1918  | tAREF { ifndef_ripper($$ = tAREF); }
1919  | tASET { ifndef_ripper($$ = tASET); }
1920  | '`' { ifndef_ripper($$ = '`'); }
1921  ;
1922 
1935  ;
1936 
1937 arg : lhs '=' arg
1938  {
1939  /*%%%*/
1940  value_expr($3);
1941  $$ = node_assign($1, $3);
1942  /*%
1943  $$ = dispatch2(assign, $1, $3);
1944  %*/
1945  }
1946  | lhs '=' arg modifier_rescue arg
1947  {
1948  /*%%%*/
1949  value_expr($3);
1950  $3 = NEW_RESCUE($3, NEW_RESBODY(0,$5,0), 0);
1951  $$ = node_assign($1, $3);
1952  /*%
1953  $$ = dispatch2(assign, $1, dispatch2(rescue_mod, $3, $5));
1954  %*/
1955  }
1956  | var_lhs tOP_ASGN arg
1957  {
1958  value_expr($3);
1959  $$ = new_op_assign($1, $2, $3);
1960  }
1961  | var_lhs tOP_ASGN arg modifier_rescue arg
1962  {
1963  /*%%%*/
1964  value_expr($3);
1965  $3 = NEW_RESCUE($3, NEW_RESBODY(0,$5,0), 0);
1966  /*%
1967  $3 = dispatch2(rescue_mod, $3, $5);
1968  %*/
1969  $$ = new_op_assign($1, $2, $3);
1970  }
1971  | primary_value '[' opt_call_args rbracket tOP_ASGN arg
1972  {
1973  /*%%%*/
1974  NODE *args;
1975 
1976  value_expr($6);
1977  if (!$3) $3 = NEW_ZARRAY();
1978  if (nd_type($3) == NODE_BLOCK_PASS) {
1979  args = NEW_ARGSCAT($3, $6);
1980  }
1981  else {
1982  args = arg_concat($3, $6);
1983  }
1984  if ($5 == tOROP) {
1985  $5 = 0;
1986  }
1987  else if ($5 == tANDOP) {
1988  $5 = 1;
1989  }
1990  $$ = NEW_OP_ASGN1($1, $5, args);
1991  fixpos($$, $1);
1992  /*%
1993  $1 = dispatch2(aref_field, $1, escape_Qundef($3));
1994  $$ = dispatch3(opassign, $1, $5, $6);
1995  %*/
1996  }
1997  | primary_value '.' tIDENTIFIER tOP_ASGN arg
1998  {
1999  value_expr($5);
2000  $$ = new_attr_op_assign($1, ripper_id2sym('.'), $3, $4, $5);
2001  }
2002  | primary_value '.' tCONSTANT tOP_ASGN arg
2003  {
2004  value_expr($5);
2005  $$ = new_attr_op_assign($1, ripper_id2sym('.'), $3, $4, $5);
2006  }
2007  | primary_value tCOLON2 tIDENTIFIER tOP_ASGN arg
2008  {
2009  value_expr($5);
2010  $$ = new_attr_op_assign($1, ripper_intern("::"), $3, $4, $5);
2011  }
2012  | primary_value tCOLON2 tCONSTANT tOP_ASGN arg
2013  {
2014  /*%%%*/
2015  $$ = NEW_COLON2($1, $3);
2016  $$ = new_const_op_assign($$, $4, $5);
2017  /*%
2018  $$ = dispatch2(const_path_field, $1, $3);
2019  $$ = dispatch3(opassign, $$, $4, $5);
2020  %*/
2021  }
2023  {
2024  /*%%%*/
2025  $$ = NEW_COLON3($2);
2026  $$ = new_const_op_assign($$, $3, $4);
2027  /*%
2028  $$ = dispatch1(top_const_field, $2);
2029  $$ = dispatch3(opassign, $$, $3, $4);
2030  %*/
2031  }
2032  | backref tOP_ASGN arg
2033  {
2034  /*%%%*/
2035  rb_backref_error($1);
2036  $$ = NEW_BEGIN(0);
2037  /*%
2038  $$ = dispatch1(var_field, $1);
2039  $$ = dispatch3(opassign, $$, $2, $3);
2040  $$ = dispatch1(assign_error, $$);
2041  %*/
2042  }
2043  | arg tDOT2 arg
2044  {
2045  /*%%%*/
2046  value_expr($1);
2047  value_expr($3);
2048  $$ = NEW_DOT2($1, $3);
2049  if (nd_type($1) == NODE_LIT && FIXNUM_P($1->nd_lit) &&
2050  nd_type($3) == NODE_LIT && FIXNUM_P($3->nd_lit)) {
2052  }
2053  /*%
2054  $$ = dispatch2(dot2, $1, $3);
2055  %*/
2056  }
2057  | arg tDOT3 arg
2058  {
2059  /*%%%*/
2060  value_expr($1);
2061  value_expr($3);
2062  $$ = NEW_DOT3($1, $3);
2063  if (nd_type($1) == NODE_LIT && FIXNUM_P($1->nd_lit) &&
2064  nd_type($3) == NODE_LIT && FIXNUM_P($3->nd_lit)) {
2066  }
2067  /*%
2068  $$ = dispatch2(dot3, $1, $3);
2069  %*/
2070  }
2071  | arg '+' arg
2072  {
2073  /*%%%*/
2074  $$ = call_bin_op($1, '+', $3);
2075  /*%
2076  $$ = dispatch3(binary, $1, ID2SYM('+'), $3);
2077  %*/
2078  }
2079  | arg '-' arg
2080  {
2081  /*%%%*/
2082  $$ = call_bin_op($1, '-', $3);
2083  /*%
2084  $$ = dispatch3(binary, $1, ID2SYM('-'), $3);
2085  %*/
2086  }
2087  | arg '*' arg
2088  {
2089  /*%%%*/
2090  $$ = call_bin_op($1, '*', $3);
2091  /*%
2092  $$ = dispatch3(binary, $1, ID2SYM('*'), $3);
2093  %*/
2094  }
2095  | arg '/' arg
2096  {
2097  /*%%%*/
2098  $$ = call_bin_op($1, '/', $3);
2099  /*%
2100  $$ = dispatch3(binary, $1, ID2SYM('/'), $3);
2101  %*/
2102  }
2103  | arg '%' arg
2104  {
2105  /*%%%*/
2106  $$ = call_bin_op($1, '%', $3);
2107  /*%
2108  $$ = dispatch3(binary, $1, ID2SYM('%'), $3);
2109  %*/
2110  }
2111  | arg tPOW arg
2112  {
2113  /*%%%*/
2114  $$ = call_bin_op($1, tPOW, $3);
2115  /*%
2116  $$ = dispatch3(binary, $1, ripper_intern("**"), $3);
2117  %*/
2118  }
2120  {
2121  /*%%%*/
2122  $$ = NEW_CALL(call_bin_op($2, tPOW, $4), tUMINUS, 0);
2123  /*%
2124  $$ = dispatch3(binary, $2, ripper_intern("**"), $4);
2125  $$ = dispatch2(unary, ripper_intern("-@"), $$);
2126  %*/
2127  }
2129  {
2130  /*%%%*/
2131  $$ = NEW_CALL(call_bin_op($2, tPOW, $4), tUMINUS, 0);
2132  /*%
2133  $$ = dispatch3(binary, $2, ripper_intern("**"), $4);
2134  $$ = dispatch2(unary, ripper_intern("-@"), $$);
2135  %*/
2136  }
2137  | tUPLUS arg
2138  {
2139  /*%%%*/
2140  $$ = call_uni_op($2, tUPLUS);
2141  /*%
2142  $$ = dispatch2(unary, ripper_intern("+@"), $2);
2143  %*/
2144  }
2145  | tUMINUS arg
2146  {
2147  /*%%%*/
2148  $$ = call_uni_op($2, tUMINUS);
2149  /*%
2150  $$ = dispatch2(unary, ripper_intern("-@"), $2);
2151  %*/
2152  }
2153  | arg '|' arg
2154  {
2155  /*%%%*/
2156  $$ = call_bin_op($1, '|', $3);
2157  /*%
2158  $$ = dispatch3(binary, $1, ID2SYM('|'), $3);
2159  %*/
2160  }
2161  | arg '^' arg
2162  {
2163  /*%%%*/
2164  $$ = call_bin_op($1, '^', $3);
2165  /*%
2166  $$ = dispatch3(binary, $1, ID2SYM('^'), $3);
2167  %*/
2168  }
2169  | arg '&' arg
2170  {
2171  /*%%%*/
2172  $$ = call_bin_op($1, '&', $3);
2173  /*%
2174  $$ = dispatch3(binary, $1, ID2SYM('&'), $3);
2175  %*/
2176  }
2177  | arg tCMP arg
2178  {
2179  /*%%%*/
2180  $$ = call_bin_op($1, tCMP, $3);
2181  /*%
2182  $$ = dispatch3(binary, $1, ripper_intern("<=>"), $3);
2183  %*/
2184  }
2185  | arg '>' arg
2186  {
2187  /*%%%*/
2188  $$ = call_bin_op($1, '>', $3);
2189  /*%
2190  $$ = dispatch3(binary, $1, ID2SYM('>'), $3);
2191  %*/
2192  }
2193  | arg tGEQ arg
2194  {
2195  /*%%%*/
2196  $$ = call_bin_op($1, tGEQ, $3);
2197  /*%
2198  $$ = dispatch3(binary, $1, ripper_intern(">="), $3);
2199  %*/
2200  }
2201  | arg '<' arg
2202  {
2203  /*%%%*/
2204  $$ = call_bin_op($1, '<', $3);
2205  /*%
2206  $$ = dispatch3(binary, $1, ID2SYM('<'), $3);
2207  %*/
2208  }
2209  | arg tLEQ arg
2210  {
2211  /*%%%*/
2212  $$ = call_bin_op($1, tLEQ, $3);
2213  /*%
2214  $$ = dispatch3(binary, $1, ripper_intern("<="), $3);
2215  %*/
2216  }
2217  | arg tEQ arg
2218  {
2219  /*%%%*/
2220  $$ = call_bin_op($1, tEQ, $3);
2221  /*%
2222  $$ = dispatch3(binary, $1, ripper_intern("=="), $3);
2223  %*/
2224  }
2225  | arg tEQQ arg
2226  {
2227  /*%%%*/
2228  $$ = call_bin_op($1, tEQQ, $3);
2229  /*%
2230  $$ = dispatch3(binary, $1, ripper_intern("==="), $3);
2231  %*/
2232  }
2233  | arg tNEQ arg
2234  {
2235  /*%%%*/
2236  $$ = call_bin_op($1, tNEQ, $3);
2237  /*%
2238  $$ = dispatch3(binary, $1, ripper_intern("!="), $3);
2239  %*/
2240  }
2241  | arg tMATCH arg
2242  {
2243  /*%%%*/
2244  $$ = match_op($1, $3);
2245  if (nd_type($1) == NODE_LIT && RB_TYPE_P($1->nd_lit, T_REGEXP)) {
2246  $$ = reg_named_capture_assign($1->nd_lit, $$);
2247  }
2248  /*%
2249  $$ = dispatch3(binary, $1, ripper_intern("=~"), $3);
2250  %*/
2251  }
2252  | arg tNMATCH arg
2253  {
2254  /*%%%*/
2255  $$ = call_bin_op($1, tNMATCH, $3);
2256  /*%
2257  $$ = dispatch3(binary, $1, ripper_intern("!~"), $3);
2258  %*/
2259  }
2260  | '!' arg
2261  {
2262  /*%%%*/
2263  $$ = call_uni_op(cond($2), '!');
2264  /*%
2265  $$ = dispatch2(unary, ID2SYM('!'), $2);
2266  %*/
2267  }
2268  | '~' arg
2269  {
2270  /*%%%*/
2271  $$ = call_uni_op($2, '~');
2272  /*%
2273  $$ = dispatch2(unary, ID2SYM('~'), $2);
2274  %*/
2275  }
2276  | arg tLSHFT arg
2277  {
2278  /*%%%*/
2279  $$ = call_bin_op($1, tLSHFT, $3);
2280  /*%
2281  $$ = dispatch3(binary, $1, ripper_intern("<<"), $3);
2282  %*/
2283  }
2284  | arg tRSHFT arg
2285  {
2286  /*%%%*/
2287  $$ = call_bin_op($1, tRSHFT, $3);
2288  /*%
2289  $$ = dispatch3(binary, $1, ripper_intern(">>"), $3);
2290  %*/
2291  }
2292  | arg tANDOP arg
2293  {
2294  /*%%%*/
2295  $$ = logop(NODE_AND, $1, $3);
2296  /*%
2297  $$ = dispatch3(binary, $1, ripper_intern("&&"), $3);
2298  %*/
2299  }
2300  | arg tOROP arg
2301  {
2302  /*%%%*/
2303  $$ = logop(NODE_OR, $1, $3);
2304  /*%
2305  $$ = dispatch3(binary, $1, ripper_intern("||"), $3);
2306  %*/
2307  }
2308  | keyword_defined opt_nl {in_defined = 1;} arg
2309  {
2310  /*%%%*/
2311  in_defined = 0;
2312  $$ = NEW_DEFINED($4);
2313  /*%
2314  in_defined = 0;
2315  $$ = dispatch1(defined, $4);
2316  %*/
2317  }
2318  | arg '?' arg opt_nl ':' arg
2319  {
2320  /*%%%*/
2321  value_expr($1);
2322  $$ = NEW_IF(cond($1), $3, $6);
2323  fixpos($$, $1);
2324  /*%
2325  $$ = dispatch3(ifop, $1, $3, $6);
2326  %*/
2327  }
2328  | primary
2329  {
2330  $$ = $1;
2331  }
2332  ;
2333 
2334 arg_value : arg
2335  {
2336  /*%%%*/
2337  value_expr($1);
2338  $$ = $1;
2339  if (!$$) $$ = NEW_NIL();
2340  /*%
2341  $$ = $1;
2342  %*/
2343  }
2344  ;
2345 
2346 aref_args : none
2347  | args trailer
2348  {
2349  $$ = $1;
2350  }
2351  | args ',' assocs trailer
2352  {
2353  /*%%%*/
2354  $$ = arg_append($1, NEW_HASH($3));
2355  /*%
2356  $$ = arg_add_assocs($1, $3);
2357  %*/
2358  }
2359  | assocs trailer
2360  {
2361  /*%%%*/
2362  $$ = NEW_LIST(NEW_HASH($1));
2363  /*%
2364  $$ = arg_add_assocs(arg_new(), $1);
2365  %*/
2366  }
2367  ;
2368 
2369 paren_args : '(' opt_call_args rparen
2370  {
2371  /*%%%*/
2372  $$ = $2;
2373  /*%
2374  $$ = dispatch1(arg_paren, escape_Qundef($2));
2375  %*/
2376  }
2377  ;
2378 
2379 opt_paren_args : none
2380  | paren_args
2381  ;
2382 
2383 opt_call_args : none
2384  | call_args
2385  | args ','
2386  {
2387  $$ = $1;
2388  }
2389  | args ',' assocs ','
2390  {
2391  /*%%%*/
2392  $$ = arg_append($1, NEW_HASH($3));
2393  /*%
2394  $$ = arg_add_assocs($1, $3);
2395  %*/
2396  }
2397  | assocs ','
2398  {
2399  /*%%%*/
2400  $$ = NEW_LIST(NEW_HASH($1));
2401  /*%
2402  $$ = arg_add_assocs(arg_new(), $1);
2403  %*/
2404  }
2405  ;
2406 
2407 call_args : command
2408  {
2409  /*%%%*/
2410  value_expr($1);
2411  $$ = NEW_LIST($1);
2412  /*%
2413  $$ = arg_add(arg_new(), $1);
2414  %*/
2415  }
2416  | args opt_block_arg
2417  {
2418  /*%%%*/
2419  $$ = arg_blk_pass($1, $2);
2420  /*%
2421  $$ = arg_add_optblock($1, $2);
2422  %*/
2423  }
2424  | assocs opt_block_arg
2425  {
2426  /*%%%*/
2427  $$ = NEW_LIST(NEW_HASH($1));
2428  $$ = arg_blk_pass($$, $2);
2429  /*%
2430  $$ = arg_add_assocs(arg_new(), $1);
2431  $$ = arg_add_optblock($$, $2);
2432  %*/
2433  }
2434  | args ',' assocs opt_block_arg
2435  {
2436  /*%%%*/
2437  $$ = arg_append($1, NEW_HASH($3));
2438  $$ = arg_blk_pass($$, $4);
2439  /*%
2440  $$ = arg_add_optblock(arg_add_assocs($1, $3), $4);
2441  %*/
2442  }
2443  | block_arg
2444  /*%c%*/
2445  /*%c
2446  {
2447  $$ = arg_add_block(arg_new(), $1);
2448  }
2449  %*/
2450  ;
2451 
2452 command_args : {
2453  $<val>$ = cmdarg_stack;
2454  CMDARG_PUSH(1);
2455  }
2456  call_args
2457  {
2458  /* CMDARG_POP() */
2459  cmdarg_stack = $<val>1;
2460  $$ = $2;
2461  }
2462  ;
2463 
2464 block_arg : tAMPER arg_value
2465  {
2466  /*%%%*/
2467  $$ = NEW_BLOCK_PASS($2);
2468  /*%
2469  $$ = $2;
2470  %*/
2471  }
2472  ;
2473 
2474 opt_block_arg : ',' block_arg
2475  {
2476  $$ = $2;
2477  }
2478  | none
2479  {
2480  $$ = 0;
2481  }
2482  ;
2483 
2484 args : arg_value
2485  {
2486  /*%%%*/
2487  $$ = NEW_LIST($1);
2488  /*%
2489  $$ = arg_add(arg_new(), $1);
2490  %*/
2491  }
2492  | tSTAR arg_value
2493  {
2494  /*%%%*/
2495  $$ = NEW_SPLAT($2);
2496  /*%
2497  $$ = arg_add_star(arg_new(), $2);
2498  %*/
2499  }
2500  | args ',' arg_value
2501  {
2502  /*%%%*/
2503  NODE *n1;
2504  if ((n1 = splat_array($1)) != 0) {
2505  $$ = list_append(n1, $3);
2506  }
2507  else {
2508  $$ = arg_append($1, $3);
2509  }
2510  /*%
2511  $$ = arg_add($1, $3);
2512  %*/
2513  }
2514  | args ',' tSTAR arg_value
2515  {
2516  /*%%%*/
2517  NODE *n1;
2518  if ((nd_type($4) == NODE_ARRAY) && (n1 = splat_array($1)) != 0) {
2519  $$ = list_concat(n1, $4);
2520  }
2521  else {
2522  $$ = arg_concat($1, $4);
2523  }
2524  /*%
2525  $$ = arg_add_star($1, $4);
2526  %*/
2527  }
2528  ;
2529 
2530 mrhs : args ',' arg_value
2531  {
2532  /*%%%*/
2533  NODE *n1;
2534  if ((n1 = splat_array($1)) != 0) {
2535  $$ = list_append(n1, $3);
2536  }
2537  else {
2538  $$ = arg_append($1, $3);
2539  }
2540  /*%
2541  $$ = mrhs_add(args2mrhs($1), $3);
2542  %*/
2543  }
2544  | args ',' tSTAR arg_value
2545  {
2546  /*%%%*/
2547  NODE *n1;
2548  if (nd_type($4) == NODE_ARRAY &&
2549  (n1 = splat_array($1)) != 0) {
2550  $$ = list_concat(n1, $4);
2551  }
2552  else {
2553  $$ = arg_concat($1, $4);
2554  }
2555  /*%
2556  $$ = mrhs_add_star(args2mrhs($1), $4);
2557  %*/
2558  }
2559  | tSTAR arg_value
2560  {
2561  /*%%%*/
2562  $$ = NEW_SPLAT($2);
2563  /*%
2564  $$ = mrhs_add_star(mrhs_new(), $2);
2565  %*/
2566  }
2567  ;
2568 
2569 primary : literal
2570  | strings
2571  | xstring
2572  | regexp
2573  | words
2574  | qwords
2575  | symbols
2576  | qsymbols
2577  | var_ref
2578  | backref
2579  | tFID
2580  {
2581  /*%%%*/
2582  $$ = NEW_FCALL($1, 0);
2583  /*%
2584  $$ = method_arg(dispatch1(fcall, $1), arg_new());
2585  %*/
2586  }
2587  | k_begin
2588  {
2589  $<val>1 = cmdarg_stack;
2590  cmdarg_stack = 0;
2591  /*%%%*/
2592  $<num>$ = ruby_sourceline;
2593  /*%
2594  %*/
2595  }
2596  bodystmt
2597  k_end
2598  {
2599  cmdarg_stack = $<val>1;
2600  /*%%%*/
2601  if ($3 == NULL) {
2602  $$ = NEW_NIL();
2603  }
2604  else {
2605  if (nd_type($3) == NODE_RESCUE ||
2606  nd_type($3) == NODE_ENSURE)
2607  nd_set_line($3, $<num>2);
2608  $$ = NEW_BEGIN($3);
2609  }
2610  nd_set_line($$, $<num>2);
2611  /*%
2612  $$ = dispatch1(begin, $3);
2613  %*/
2614  }
2615  | tLPAREN_ARG {lex_state = EXPR_ENDARG;} rparen
2616  {
2617  /*%%%*/
2618  $$ = 0;
2619  /*%
2620  $$ = dispatch1(paren, 0);
2621  %*/
2622  }
2623  | tLPAREN_ARG expr {lex_state = EXPR_ENDARG;} rparen
2624  {
2625  /*%%%*/
2626  $$ = $2;
2627  /*%
2628  $$ = dispatch1(paren, $2);
2629  %*/
2630  }
2631  | tLPAREN compstmt ')'
2632  {
2633  /*%%%*/
2634  $$ = $2;
2635  /*%
2636  $$ = dispatch1(paren, $2);
2637  %*/
2638  }
2639  | primary_value tCOLON2 tCONSTANT
2640  {
2641  /*%%%*/
2642  $$ = NEW_COLON2($1, $3);
2643  /*%
2644  $$ = dispatch2(const_path_ref, $1, $3);
2645  %*/
2646  }
2647  | tCOLON3 tCONSTANT
2648  {
2649  /*%%%*/
2650  $$ = NEW_COLON3($2);
2651  /*%
2652  $$ = dispatch1(top_const_ref, $2);
2653  %*/
2654  }
2655  | tLBRACK aref_args ']'
2656  {
2657  /*%%%*/
2658  if ($2 == 0) {
2659  $$ = NEW_ZARRAY(); /* zero length array*/
2660  }
2661  else {
2662  $$ = $2;
2663  }
2664  /*%
2665  $$ = dispatch1(array, escape_Qundef($2));
2666  %*/
2667  }
2668  | tLBRACE assoc_list '}'
2669  {
2670  /*%%%*/
2671  $$ = NEW_HASH($2);
2672  /*%
2673  $$ = dispatch1(hash, escape_Qundef($2));
2674  %*/
2675  }
2676  | keyword_return
2677  {
2678  /*%%%*/
2679  $$ = NEW_RETURN(0);
2680  /*%
2681  $$ = dispatch0(return0);
2682  %*/
2683  }
2684  | keyword_yield '(' call_args rparen
2685  {
2686  /*%%%*/
2687  $$ = new_yield($3);
2688  /*%
2689  $$ = dispatch1(yield, dispatch1(paren, $3));
2690  %*/
2691  }
2692  | keyword_yield '(' rparen
2693  {
2694  /*%%%*/
2695  $$ = NEW_YIELD(0);
2696  /*%
2697  $$ = dispatch1(yield, dispatch1(paren, arg_new()));
2698  %*/
2699  }
2700  | keyword_yield
2701  {
2702  /*%%%*/
2703  $$ = NEW_YIELD(0);
2704  /*%
2705  $$ = dispatch0(yield0);
2706  %*/
2707  }
2708  | keyword_defined opt_nl '(' {in_defined = 1;} expr rparen
2709  {
2710  /*%%%*/
2711  in_defined = 0;
2712  $$ = NEW_DEFINED($5);
2713  /*%
2714  in_defined = 0;
2715  $$ = dispatch1(defined, $5);
2716  %*/
2717  }
2718  | keyword_not '(' expr rparen
2719  {
2720  /*%%%*/
2721  $$ = call_uni_op(cond($3), '!');
2722  /*%
2723  $$ = dispatch2(unary, ripper_intern("not"), $3);
2724  %*/
2725  }
2726  | keyword_not '(' rparen
2727  {
2728  /*%%%*/
2729  $$ = call_uni_op(cond(NEW_NIL()), '!');
2730  /*%
2731  $$ = dispatch2(unary, ripper_intern("not"), Qnil);
2732  %*/
2733  }
2734  | fcall brace_block
2735  {
2736  /*%%%*/
2737  $2->nd_iter = $1;
2738  $$ = $2;
2739  /*%
2740  $$ = method_arg(dispatch1(fcall, $1), arg_new());
2741  $$ = method_add_block($$, $2);
2742  %*/
2743  }
2744  | method_call
2745  | method_call brace_block
2746  {
2747  /*%%%*/
2748  block_dup_check($1->nd_args, $2);
2749  $2->nd_iter = $1;
2750  $$ = $2;
2751  /*%
2752  $$ = method_add_block($1, $2);
2753  %*/
2754  }
2755  | tLAMBDA lambda
2756  {
2757  $$ = $2;
2758  }
2759  | k_if expr_value then
2760  compstmt
2761  if_tail
2762  k_end
2763  {
2764  /*%%%*/
2765  $$ = NEW_IF(cond($2), $4, $5);
2766  fixpos($$, $2);
2767  /*%
2768  $$ = dispatch3(if, $2, $4, escape_Qundef($5));
2769  %*/
2770  }
2771  | k_unless expr_value then
2772  compstmt
2773  opt_else
2774  k_end
2775  {
2776  /*%%%*/
2777  $$ = NEW_UNLESS(cond($2), $4, $5);
2778  fixpos($$, $2);
2779  /*%
2780  $$ = dispatch3(unless, $2, $4, escape_Qundef($5));
2781  %*/
2782  }
2783  | k_while {COND_PUSH(1);} expr_value do {COND_POP();}
2784  compstmt
2785  k_end
2786  {
2787  /*%%%*/
2788  $$ = NEW_WHILE(cond($3), $6, 1);
2789  fixpos($$, $3);
2790  /*%
2791  $$ = dispatch2(while, $3, $6);
2792  %*/
2793  }
2794  | k_until {COND_PUSH(1);} expr_value do {COND_POP();}
2795  compstmt
2796  k_end
2797  {
2798  /*%%%*/
2799  $$ = NEW_UNTIL(cond($3), $6, 1);
2800  fixpos($$, $3);
2801  /*%
2802  $$ = dispatch2(until, $3, $6);
2803  %*/
2804  }
2805  | k_case expr_value opt_terms
2806  case_body
2807  k_end
2808  {
2809  /*%%%*/
2810  $$ = NEW_CASE($2, $4);
2811  fixpos($$, $2);
2812  /*%
2813  $$ = dispatch2(case, $2, $4);
2814  %*/
2815  }
2816  | k_case opt_terms case_body k_end
2817  {
2818  /*%%%*/
2819  $$ = NEW_CASE(0, $3);
2820  /*%
2821  $$ = dispatch2(case, Qnil, $3);
2822  %*/
2823  }
2824  | k_for for_var keyword_in
2825  {COND_PUSH(1);}
2826  expr_value do
2827  {COND_POP();}
2828  compstmt
2829  k_end
2830  {
2831  /*%%%*/
2832  /*
2833  * for a, b, c in e
2834  * #=>
2835  * e.each{|*x| a, b, c = x
2836  *
2837  * for a in e
2838  * #=>
2839  * e.each{|x| a, = x}
2840  */
2841  ID id = internal_id();
2842  ID *tbl = ALLOC_N(ID, 2);
2843  NODE *m = NEW_ARGS_AUX(0, 0);
2844  NODE *args, *scope;
2845 
2846  if (nd_type($2) == NODE_MASGN) {
2847  /* if args.length == 1 && args[0].kind_of?(Array)
2848  * args = args[0]
2849  * end
2850  */
2851  NODE *one = NEW_LIST(NEW_LIT(INT2FIX(1)));
2852  NODE *zero = NEW_LIST(NEW_LIT(INT2FIX(0)));
2853  m->nd_next = block_append(
2854  NEW_IF(
2856  NEW_CALL(NEW_CALL(NEW_DVAR(id), idLength, 0),
2857  idEq, one),
2858  NEW_CALL(NEW_CALL(NEW_DVAR(id), idAREF, zero),
2859  rb_intern("kind_of?"), NEW_LIST(NEW_LIT(rb_cArray))),
2860  0),
2861  NEW_DASGN_CURR(id,
2862  NEW_CALL(NEW_DVAR(id), idAREF, zero)),
2863  0),
2864  node_assign($2, NEW_DVAR(id)));
2865 
2866  args = new_args(m, 0, id, 0, new_args_tail(0, 0, 0));
2867  }
2868  else {
2869  if (nd_type($2) == NODE_LASGN ||
2870  nd_type($2) == NODE_DASGN ||
2871  nd_type($2) == NODE_DASGN_CURR) {
2872  $2->nd_value = NEW_DVAR(id);
2873  m->nd_plen = 1;
2874  m->nd_next = $2;
2875  args = new_args(m, 0, 0, 0, new_args_tail(0, 0, 0));
2876  }
2877  else {
2878  m->nd_next = node_assign(NEW_MASGN(NEW_LIST($2), 0), NEW_DVAR(id));
2879  args = new_args(m, 0, id, 0, new_args_tail(0, 0, 0));
2880  }
2881  }
2882  scope = NEW_NODE(NODE_SCOPE, tbl, $8, args);
2883  tbl[0] = 1; tbl[1] = id;
2884  $$ = NEW_FOR(0, $5, scope);
2885  fixpos($$, $2);
2886  /*%
2887  $$ = dispatch3(for, $2, $5, $8);
2888  %*/
2889  }
2890  | k_class cpath superclass
2891  {
2892  if (in_def || in_single)
2893  yyerror("class definition in method body");
2894  local_push(0);
2895  /*%%%*/
2896  $<num>$ = ruby_sourceline;
2897  /*%
2898  %*/
2899  }
2900  bodystmt
2901  k_end
2902  {
2903  /*%%%*/
2904  $$ = NEW_CLASS($2, $5, $3);
2905  nd_set_line($$, $<num>4);
2906  /*%
2907  $$ = dispatch3(class, $2, $3, $5);
2908  %*/
2909  local_pop();
2910  }
2911  | k_class tLSHFT expr
2912  {
2913  $<num>$ = in_def;
2914  in_def = 0;
2915  }
2916  term
2917  {
2918  $<num>$ = in_single;
2919  in_single = 0;
2920  local_push(0);
2921  }
2922  bodystmt
2923  k_end
2924  {
2925  /*%%%*/
2926  $$ = NEW_SCLASS($3, $7);
2927  fixpos($$, $3);
2928  /*%
2929  $$ = dispatch2(sclass, $3, $7);
2930  %*/
2931  local_pop();
2932  in_def = $<num>4;
2933  in_single = $<num>6;
2934  }
2935  | k_module cpath
2936  {
2937  if (in_def || in_single)
2938  yyerror("module definition in method body");
2939  local_push(0);
2940  /*%%%*/
2941  $<num>$ = ruby_sourceline;
2942  /*%
2943  %*/
2944  }
2945  bodystmt
2946  k_end
2947  {
2948  /*%%%*/
2949  $$ = NEW_MODULE($2, $4);
2950  nd_set_line($$, $<num>3);
2951  /*%
2952  $$ = dispatch2(module, $2, $4);
2953  %*/
2954  local_pop();
2955  }
2956  | k_def fname
2957  {
2958  $<id>$ = cur_mid;
2959  cur_mid = $2;
2960  in_def++;
2961  local_push(0);
2962  }
2963  f_arglist
2964  bodystmt
2965  k_end
2966  {
2967  /*%%%*/
2968  NODE *body = remove_begin($5);
2969  reduce_nodes(&body);
2970  $$ = NEW_DEFN($2, $4, body, NOEX_PRIVATE);
2971  nd_set_line($$, $<num>1);
2972  /*%
2973  $$ = dispatch3(def, $2, $4, $5);
2974  %*/
2975  local_pop();
2976  in_def--;
2977  cur_mid = $<id>3;
2978  }
2979  | k_def singleton dot_or_colon {lex_state = EXPR_FNAME;} fname
2980  {
2981  in_single++;
2982  lex_state = EXPR_ENDFN; /* force for args */
2983  local_push(0);
2984  }
2985  f_arglist
2986  bodystmt
2987  k_end
2988  {
2989  /*%%%*/
2990  NODE *body = remove_begin($8);
2991  reduce_nodes(&body);
2992  $$ = NEW_DEFS($2, $5, $7, body);
2993  nd_set_line($$, $<num>1);
2994  /*%
2995  $$ = dispatch5(defs, $2, $3, $5, $7, $8);
2996  %*/
2997  local_pop();
2998  in_single--;
2999  }
3000  | keyword_break
3001  {
3002  /*%%%*/
3003  $$ = NEW_BREAK(0);
3004  /*%
3005  $$ = dispatch1(break, arg_new());
3006  %*/
3007  }
3008  | keyword_next
3009  {
3010  /*%%%*/
3011  $$ = NEW_NEXT(0);
3012  /*%
3013  $$ = dispatch1(next, arg_new());
3014  %*/
3015  }
3016  | keyword_redo
3017  {
3018  /*%%%*/
3019  $$ = NEW_REDO();
3020  /*%
3021  $$ = dispatch0(redo);
3022  %*/
3023  }
3024  | keyword_retry
3025  {
3026  /*%%%*/
3027  $$ = NEW_RETRY();
3028  /*%
3029  $$ = dispatch0(retry);
3030  %*/
3031  }
3032  ;
3033 
3034 primary_value : primary
3035  {
3036  /*%%%*/
3037  value_expr($1);
3038  $$ = $1;
3039  if (!$$) $$ = NEW_NIL();
3040  /*%
3041  $$ = $1;
3042  %*/
3043  }
3044  ;
3045 
3046 k_begin : keyword_begin
3047  {
3048  token_info_push("begin");
3049  }
3050  ;
3051 
3052 k_if : keyword_if
3053  {
3054  token_info_push("if");
3055  }
3056  ;
3057 
3058 k_unless : keyword_unless
3059  {
3060  token_info_push("unless");
3061  }
3062  ;
3063 
3064 k_while : keyword_while
3065  {
3066  token_info_push("while");
3067  }
3068  ;
3069 
3070 k_until : keyword_until
3071  {
3072  token_info_push("until");
3073  }
3074  ;
3075 
3076 k_case : keyword_case
3077  {
3078  token_info_push("case");
3079  }
3080  ;
3081 
3082 k_for : keyword_for
3083  {
3084  token_info_push("for");
3085  }
3086  ;
3087 
3088 k_class : keyword_class
3089  {
3090  token_info_push("class");
3091  }
3092  ;
3093 
3094 k_module : keyword_module
3095  {
3096  token_info_push("module");
3097  }
3098  ;
3099 
3100 k_def : keyword_def
3101  {
3102  token_info_push("def");
3103  /*%%%*/
3104  $<num>$ = ruby_sourceline;
3105  /*%
3106  %*/
3107  }
3108  ;
3109 
3110 k_end : keyword_end
3111  {
3112  token_info_pop("end");
3113  }
3114  ;
3115 
3116 then : term
3117  /*%c%*/
3118  /*%c
3119  { $$ = Qnil; }
3120  %*/
3121  | keyword_then
3122  | term keyword_then
3123  /*%c%*/
3124  /*%c
3125  { $$ = $2; }
3126  %*/
3127  ;
3128 
3129 do : term
3130  /*%c%*/
3131  /*%c
3132  { $$ = Qnil; }
3133  %*/
3134  | keyword_do_cond
3135  ;
3136 
3137 if_tail : opt_else
3138  | keyword_elsif expr_value then
3139  compstmt
3140  if_tail
3141  {
3142  /*%%%*/
3143  $$ = NEW_IF(cond($2), $4, $5);
3144  fixpos($$, $2);
3145  /*%
3146  $$ = dispatch3(elsif, $2, $4, escape_Qundef($5));
3147  %*/
3148  }
3149  ;
3150 
3151 opt_else : none
3153  {
3154  /*%%%*/
3155  $$ = $2;
3156  /*%
3157  $$ = dispatch1(else, $2);
3158  %*/
3159  }
3160  ;
3161 
3162 for_var : lhs
3163  | mlhs
3164  ;
3165 
3166 f_marg : f_norm_arg
3167  {
3168  $$ = assignable($1, 0);
3169  /*%%%*/
3170  /*%
3171  $$ = dispatch1(mlhs_paren, $$);
3172  %*/
3173  }
3174  | tLPAREN f_margs rparen
3175  {
3176  /*%%%*/
3177  $$ = $2;
3178  /*%
3179  $$ = dispatch1(mlhs_paren, $2);
3180  %*/
3181  }
3182  ;
3183 
3184 f_marg_list : f_marg
3185  {
3186  /*%%%*/
3187  $$ = NEW_LIST($1);
3188  /*%
3189  $$ = mlhs_add(mlhs_new(), $1);
3190  %*/
3191  }
3192  | f_marg_list ',' f_marg
3193  {
3194  /*%%%*/
3195  $$ = list_append($1, $3);
3196  /*%
3197  $$ = mlhs_add($1, $3);
3198  %*/
3199  }
3200  ;
3201 
3202 f_margs : f_marg_list
3203  {
3204  /*%%%*/
3205  $$ = NEW_MASGN($1, 0);
3206  /*%
3207  $$ = $1;
3208  %*/
3209  }
3210  | f_marg_list ',' tSTAR f_norm_arg
3211  {
3212  $$ = assignable($4, 0);
3213  /*%%%*/
3214  $$ = NEW_MASGN($1, $$);
3215  /*%
3216  $$ = mlhs_add_star($1, $$);
3217  %*/
3218  }
3219  | f_marg_list ',' tSTAR f_norm_arg ',' f_marg_list
3220  {
3221  $$ = assignable($4, 0);
3222  /*%%%*/
3223  $$ = NEW_MASGN($1, NEW_POSTARG($$, $6));
3224  /*%
3225  $$ = mlhs_add_star($1, $$);
3226  %*/
3227  }
3228  | f_marg_list ',' tSTAR
3229  {
3230  /*%%%*/
3231  $$ = NEW_MASGN($1, -1);
3232  /*%
3233  $$ = mlhs_add_star($1, Qnil);
3234  %*/
3235  }
3236  | f_marg_list ',' tSTAR ',' f_marg_list
3237  {
3238  /*%%%*/
3239  $$ = NEW_MASGN($1, NEW_POSTARG(-1, $5));
3240  /*%
3241  $$ = mlhs_add_star($1, $5);
3242  %*/
3243  }
3244  | tSTAR f_norm_arg
3245  {
3246  $$ = assignable($2, 0);
3247  /*%%%*/
3248  $$ = NEW_MASGN(0, $$);
3249  /*%
3250  $$ = mlhs_add_star(mlhs_new(), $$);
3251  %*/
3252  }
3253  | tSTAR f_norm_arg ',' f_marg_list
3254  {
3255  $$ = assignable($2, 0);
3256  /*%%%*/
3257  $$ = NEW_MASGN(0, NEW_POSTARG($$, $4));
3258  /*%
3259  #if 0
3260  TODO: Check me
3261  #endif
3262  $$ = mlhs_add_star($$, $4);
3263  %*/
3264  }
3265  | tSTAR
3266  {
3267  /*%%%*/
3268  $$ = NEW_MASGN(0, -1);
3269  /*%
3270  $$ = mlhs_add_star(mlhs_new(), Qnil);
3271  %*/
3272  }
3273  | tSTAR ',' f_marg_list
3274  {
3275  /*%%%*/
3276  $$ = NEW_MASGN(0, NEW_POSTARG(-1, $3));
3277  /*%
3278  $$ = mlhs_add_star(mlhs_new(), Qnil);
3279  %*/
3280  }
3281  ;
3282 
3283 
3284 block_args_tail : f_block_kwarg ',' f_kwrest opt_f_block_arg
3285  {
3286  $$ = new_args_tail($1, $3, $4);
3287  }
3288  | f_block_kwarg opt_f_block_arg
3289  {
3290  $$ = new_args_tail($1, Qnone, $2);
3291  }
3292  | f_kwrest opt_f_block_arg
3293  {
3294  $$ = new_args_tail(Qnone, $1, $2);
3295  }
3296  | f_block_arg
3297  {
3298  $$ = new_args_tail(Qnone, Qnone, $1);
3299  }
3300  ;
3301 
3302 opt_block_args_tail : ',' block_args_tail
3303  {
3304  $$ = $2;
3305  }
3306  | /* none */
3307  {
3308  $$ = new_args_tail(Qnone, Qnone, Qnone);
3309  }
3310  ;
3311 
3312 block_param : f_arg ',' f_block_optarg ',' f_rest_arg opt_block_args_tail
3313  {
3314  $$ = new_args($1, $3, $5, Qnone, $6);
3315  }
3316  | f_arg ',' f_block_optarg ',' f_rest_arg ',' f_arg opt_block_args_tail
3317  {
3318  $$ = new_args($1, $3, $5, $7, $8);
3319  }
3320  | f_arg ',' f_block_optarg opt_block_args_tail
3321  {
3322  $$ = new_args($1, $3, Qnone, Qnone, $4);
3323  }
3324  | f_arg ',' f_block_optarg ',' f_arg opt_block_args_tail
3325  {
3326  $$ = new_args($1, $3, Qnone, $5, $6);
3327  }
3328  | f_arg ',' f_rest_arg opt_block_args_tail
3329  {
3330  $$ = new_args($1, Qnone, $3, Qnone, $4);
3331  }
3332  | f_arg ','
3333  {
3334  $$ = new_args($1, Qnone, 1, Qnone, new_args_tail(Qnone, Qnone, Qnone));
3335  /*%%%*/
3336  /*%
3337  dispatch1(excessed_comma, $$);
3338  %*/
3339  }
3340  | f_arg ',' f_rest_arg ',' f_arg opt_block_args_tail
3341  {
3342  $$ = new_args($1, Qnone, $3, $5, $6);
3343  }
3344  | f_arg opt_block_args_tail
3345  {
3346  $$ = new_args($1, Qnone, Qnone, Qnone, $2);
3347  }
3348  | f_block_optarg ',' f_rest_arg opt_block_args_tail
3349  {
3350  $$ = new_args(Qnone, $1, $3, Qnone, $4);
3351  }
3352  | f_block_optarg ',' f_rest_arg ',' f_arg opt_block_args_tail
3353  {
3354  $$ = new_args(Qnone, $1, $3, $5, $6);
3355  }
3356  | f_block_optarg opt_block_args_tail
3357  {
3358  $$ = new_args(Qnone, $1, Qnone, Qnone, $2);
3359  }
3360  | f_block_optarg ',' f_arg opt_block_args_tail
3361  {
3362  $$ = new_args(Qnone, $1, Qnone, $3, $4);
3363  }
3364  | f_rest_arg opt_block_args_tail
3365  {
3366  $$ = new_args(Qnone, Qnone, $1, Qnone, $2);
3367  }
3368  | f_rest_arg ',' f_arg opt_block_args_tail
3369  {
3370  $$ = new_args(Qnone, Qnone, $1, $3, $4);
3371  }
3372  | block_args_tail
3373  {
3374  $$ = new_args(Qnone, Qnone, Qnone, Qnone, $1);
3375  }
3376  ;
3377 
3378 opt_block_param : none
3379  | block_param_def
3380  {
3381  command_start = TRUE;
3382  }
3383  ;
3384 
3385 block_param_def : '|' opt_bv_decl '|'
3386  {
3387  /*%%%*/
3388  $$ = 0;
3389  /*%
3390  $$ = blockvar_new(params_new(Qnil,Qnil,Qnil,Qnil,Qnil,Qnil,Qnil),
3391  escape_Qundef($2));
3392  %*/
3393  }
3394  | tOROP
3395  {
3396  /*%%%*/
3397  $$ = 0;
3398  /*%
3399  $$ = blockvar_new(params_new(Qnil,Qnil,Qnil,Qnil,Qnil,Qnil,Qnil),
3400  Qnil);
3401  %*/
3402  }
3403  | '|' block_param opt_bv_decl '|'
3404  {
3405  /*%%%*/
3406  $$ = $2;
3407  /*%
3408  $$ = blockvar_new(escape_Qundef($2), escape_Qundef($3));
3409  %*/
3410  }
3411  ;
3412 
3413 
3414 opt_bv_decl : opt_nl
3415  {
3416  $$ = 0;
3417  }
3418  | opt_nl ';' bv_decls opt_nl
3419  {
3420  /*%%%*/
3421  $$ = 0;
3422  /*%
3423  $$ = $3;
3424  %*/
3425  }
3426  ;
3427 
3428 bv_decls : bvar
3429  /*%c%*/
3430  /*%c
3431  {
3432  $$ = rb_ary_new3(1, $1);
3433  }
3434  %*/
3435  | bv_decls ',' bvar
3436  /*%c%*/
3437  /*%c
3438  {
3439  rb_ary_push($1, $3);
3440  }
3441  %*/
3442  ;
3443 
3444 bvar : tIDENTIFIER
3445  {
3446  new_bv(get_id($1));
3447  /*%%%*/
3448  /*%
3449  $$ = get_value($1);
3450  %*/
3451  }
3452  | f_bad_arg
3453  {
3454  $$ = 0;
3455  }
3456  ;
3457 
3458 lambda : {
3459  $<vars>$ = dyna_push();
3460  }
3461  {
3462  $<num>$ = lpar_beg;
3463  lpar_beg = ++paren_nest;
3464  }
3465  f_larglist
3466  {
3467  $<num>$ = ruby_sourceline;
3468  }
3469  lambda_body
3470  {
3471  lpar_beg = $<num>2;
3472  /*%%%*/
3473  $$ = NEW_LAMBDA($3, $5);
3474  nd_set_line($$, $<num>4);
3475  /*%
3476  $$ = dispatch2(lambda, $3, $5);
3477  %*/
3478  dyna_pop($<vars>1);
3479  }
3480  ;
3481 
3482 f_larglist : '(' f_args opt_bv_decl ')'
3483  {
3484  /*%%%*/
3485  $$ = $2;
3486  /*%
3487  $$ = dispatch1(paren, $2);
3488  %*/
3489  }
3490  | f_args
3491  {
3492  /*%%%*/
3493  $$ = $1;
3494  /*%
3495  $$ = $1;
3496  %*/
3497  }
3498  ;
3499 
3500 lambda_body : tLAMBEG compstmt '}'
3501  {
3502  $$ = $2;
3503  }
3505  {
3506  $$ = $2;
3507  }
3508  ;
3509 
3510 do_block : keyword_do_block
3511  {
3512  $<vars>1 = dyna_push();
3513  /*%%%*/
3514  $<num>$ = ruby_sourceline;
3515  /*% %*/
3516  }
3517  opt_block_param
3518  compstmt
3519  keyword_end
3520  {
3521  /*%%%*/
3522  $$ = NEW_ITER($3,$4);
3523  nd_set_line($$, $<num>2);
3524  /*%
3525  $$ = dispatch2(do_block, escape_Qundef($3), $4);
3526  %*/
3527  dyna_pop($<vars>1);
3528  }
3529  ;
3530 
3531 block_call : command do_block
3532  {
3533  /*%%%*/
3534  if (nd_type($1) == NODE_YIELD) {
3535  compile_error(PARSER_ARG "block given to yield");
3536  }
3537  else {
3538  block_dup_check($1->nd_args, $2);
3539  }
3540  $2->nd_iter = $1;
3541  $$ = $2;
3542  fixpos($$, $1);
3543  /*%
3544  $$ = method_add_block($1, $2);
3545  %*/
3546  }
3547  | block_call dot_or_colon operation2 opt_paren_args
3548  {
3549  /*%%%*/
3550  $$ = NEW_CALL($1, $3, $4);
3551  /*%
3552  $$ = dispatch3(call, $1, $2, $3);
3553  $$ = method_optarg($$, $4);
3554  %*/
3555  }
3556  | block_call dot_or_colon operation2 opt_paren_args brace_block
3557  {
3558  /*%%%*/
3559  block_dup_check($4, $5);
3560  $5->nd_iter = NEW_CALL($1, $3, $4);
3561  $$ = $5;
3562  fixpos($$, $1);
3563  /*%
3564  $$ = dispatch4(command_call, $1, $2, $3, $4);
3565  $$ = method_add_block($$, $5);
3566  %*/
3567  }
3568  | block_call dot_or_colon operation2 command_args do_block
3569  {
3570  /*%%%*/
3571  block_dup_check($4, $5);
3572  $5->nd_iter = NEW_CALL($1, $3, $4);
3573  $$ = $5;
3574  fixpos($$, $1);
3575  /*%
3576  $$ = dispatch4(command_call, $1, $2, $3, $4);
3577  $$ = method_add_block($$, $5);
3578  %*/
3579  }
3580  ;
3581 
3582 method_call : fcall paren_args
3583  {
3584  /*%%%*/
3585  $$ = $1;
3586  $$->nd_args = $2;
3587  /*%
3588  $$ = method_arg(dispatch1(fcall, $1), $2);
3589  %*/
3590  }
3591  | primary_value '.' operation2
3592  {
3593  /*%%%*/
3594  $<num>$ = ruby_sourceline;
3595  /*% %*/
3596  }
3597  opt_paren_args
3598  {
3599  /*%%%*/
3600  $$ = NEW_CALL($1, $3, $5);
3601  nd_set_line($$, $<num>4);
3602  /*%
3603  $$ = dispatch3(call, $1, ripper_id2sym('.'), $3);
3604  $$ = method_optarg($$, $5);
3605  %*/
3606  }
3607  | primary_value tCOLON2 operation2
3608  {
3609  /*%%%*/
3610  $<num>$ = ruby_sourceline;
3611  /*% %*/
3612  }
3613  paren_args
3614  {
3615  /*%%%*/
3616  $$ = NEW_CALL($1, $3, $5);
3617  nd_set_line($$, $<num>4);
3618  /*%
3619  $$ = dispatch3(call, $1, ripper_id2sym('.'), $3);
3620  $$ = method_optarg($$, $5);
3621  %*/
3622  }
3623  | primary_value tCOLON2 operation3
3624  {
3625  /*%%%*/
3626  $$ = NEW_CALL($1, $3, 0);
3627  /*%
3628  $$ = dispatch3(call, $1, ripper_intern("::"), $3);
3629  %*/
3630  }
3631  | primary_value '.'
3632  {
3633  /*%%%*/
3634  $<num>$ = ruby_sourceline;
3635  /*% %*/
3636  }
3637  paren_args
3638  {
3639  /*%%%*/
3640  $$ = NEW_CALL($1, rb_intern("call"), $4);
3641  nd_set_line($$, $<num>3);
3642  /*%
3643  $$ = dispatch3(call, $1, ripper_id2sym('.'),
3644  ripper_intern("call"));
3645  $$ = method_optarg($$, $4);
3646  %*/
3647  }
3648  | primary_value tCOLON2
3649  {
3650  /*%%%*/
3651  $<num>$ = ruby_sourceline;
3652  /*% %*/
3653  }
3654  paren_args
3655  {
3656  /*%%%*/
3657  $$ = NEW_CALL($1, rb_intern("call"), $4);
3658  nd_set_line($$, $<num>3);
3659  /*%
3660  $$ = dispatch3(call, $1, ripper_intern("::"),
3661  ripper_intern("call"));
3662  $$ = method_optarg($$, $4);
3663  %*/
3664  }
3665  | keyword_super paren_args
3666  {
3667  /*%%%*/
3668  $$ = NEW_SUPER($2);
3669  /*%
3670  $$ = dispatch1(super, $2);
3671  %*/
3672  }
3673  | keyword_super
3674  {
3675  /*%%%*/
3676  $$ = NEW_ZSUPER();
3677  /*%
3678  $$ = dispatch0(zsuper);
3679  %*/
3680  }
3681  | primary_value '[' opt_call_args rbracket
3682  {
3683  /*%%%*/
3684  if ($1 && nd_type($1) == NODE_SELF)
3685  $$ = NEW_FCALL(tAREF, $3);
3686  else
3687  $$ = NEW_CALL($1, tAREF, $3);
3688  fixpos($$, $1);
3689  /*%
3690  $$ = dispatch2(aref, $1, escape_Qundef($3));
3691  %*/
3692  }
3693  ;
3694 
3695 brace_block : '{'
3696  {
3697  $<vars>1 = dyna_push();
3698  /*%%%*/
3699  $<num>$ = ruby_sourceline;
3700  /*%
3701  %*/
3702  }
3703  opt_block_param
3704  compstmt '}'
3705  {
3706  /*%%%*/
3707  $$ = NEW_ITER($3,$4);
3708  nd_set_line($$, $<num>2);
3709  /*%
3710  $$ = dispatch2(brace_block, escape_Qundef($3), $4);
3711  %*/
3712  dyna_pop($<vars>1);
3713  }
3714  | keyword_do
3715  {
3716  $<vars>1 = dyna_push();
3717  /*%%%*/
3718  $<num>$ = ruby_sourceline;
3719  /*%
3720  %*/
3721  }
3722  opt_block_param
3724  {
3725  /*%%%*/
3726  $$ = NEW_ITER($3,$4);
3727  nd_set_line($$, $<num>2);
3728  /*%
3729  $$ = dispatch2(do_block, escape_Qundef($3), $4);
3730  %*/
3731  dyna_pop($<vars>1);
3732  }
3733  ;
3734 
3735 case_body : keyword_when args then
3736  compstmt
3737  cases
3738  {
3739  /*%%%*/
3740  $$ = NEW_WHEN($2, $4, $5);
3741  /*%
3742  $$ = dispatch3(when, $2, $4, escape_Qundef($5));
3743  %*/
3744  }
3745  ;
3746 
3747 cases : opt_else
3748  | case_body
3749  ;
3750 
3751 opt_rescue : keyword_rescue exc_list exc_var then
3752  compstmt
3753  opt_rescue
3754  {
3755  /*%%%*/
3756  if ($3) {
3757  $3 = node_assign($3, NEW_ERRINFO());
3758  $5 = block_append($3, $5);
3759  }
3760  $$ = NEW_RESBODY($2, $5, $6);
3761  fixpos($$, $2?$2:$5);
3762  /*%
3763  $$ = dispatch4(rescue,
3764  escape_Qundef($2),
3765  escape_Qundef($3),
3766  escape_Qundef($5),
3767  escape_Qundef($6));
3768  %*/
3769  }
3770  | none
3771  ;
3772 
3773 exc_list : arg_value
3774  {
3775  /*%%%*/
3776  $$ = NEW_LIST($1);
3777  /*%
3778  $$ = rb_ary_new3(1, $1);
3779  %*/
3780  }
3781  | mrhs
3782  {
3783  /*%%%*/
3784  if (!($$ = splat_array($1))) $$ = $1;
3785  /*%
3786  $$ = $1;
3787  %*/
3788  }
3789  | none
3790  ;
3791 
3792 exc_var : tASSOC lhs
3793  {
3794  $$ = $2;
3795  }
3796  | none
3797  ;
3798 
3799 opt_ensure : keyword_ensure compstmt
3800  {
3801  /*%%%*/
3802  $$ = $2;
3803  /*%
3804  $$ = dispatch1(ensure, $2);
3805  %*/
3806  }
3807  | none
3808  ;
3809 
3810 literal : numeric
3811  | symbol
3812  {
3813  /*%%%*/
3814  $$ = NEW_LIT(ID2SYM($1));
3815  /*%
3816  $$ = dispatch1(symbol_literal, $1);
3817  %*/
3818  }
3819  | dsym
3820  ;
3821 
3822 strings : string
3823  {
3824  /*%%%*/
3825  NODE *node = $1;
3826  if (!node) {
3827  node = NEW_STR(STR_NEW0());
3828  }
3829  else {
3830  node = evstr2dstr(node);
3831  }
3832  $$ = node;
3833  /*%
3834  $$ = $1;
3835  %*/
3836  }
3837  ;
3838 
3839 string : tCHAR
3840  | string1
3841  | string string1
3842  {
3843  /*%%%*/
3844  $$ = literal_concat($1, $2);
3845  /*%
3846  $$ = dispatch2(string_concat, $1, $2);
3847  %*/
3848  }
3849  ;
3850 
3851 string1 : tSTRING_BEG string_contents tSTRING_END
3852  {
3853  /*%%%*/
3854  $$ = $2;
3855  /*%
3856  $$ = dispatch1(string_literal, $2);
3857  %*/
3858  }
3859  ;
3860 
3861 xstring : tXSTRING_BEG xstring_contents tSTRING_END
3862  {
3863  /*%%%*/
3864  NODE *node = $2;
3865  if (!node) {
3866  node = NEW_XSTR(STR_NEW0());
3867  }
3868  else {
3869  switch (nd_type(node)) {
3870  case NODE_STR:
3871  nd_set_type(node, NODE_XSTR);
3872  break;
3873  case NODE_DSTR:
3874  nd_set_type(node, NODE_DXSTR);
3875  break;
3876  default:
3877  node = NEW_NODE(NODE_DXSTR, Qnil, 1, NEW_LIST(node));
3878  break;
3879  }
3880  }
3881  $$ = node;
3882  /*%
3883  $$ = dispatch1(xstring_literal, $2);
3884  %*/
3885  }
3886  ;
3887 
3888 regexp : tREGEXP_BEG regexp_contents tREGEXP_END
3889  {
3890  /*%%%*/
3891  int options = $3;
3892  NODE *node = $2;
3893  NODE *list, *prev;
3894  if (!node) {
3895  node = NEW_LIT(reg_compile(STR_NEW0(), options));
3896  }
3897  else switch (nd_type(node)) {
3898  case NODE_STR:
3899  {
3900  VALUE src = node->nd_lit;
3901  nd_set_type(node, NODE_LIT);
3902  node->nd_lit = reg_compile(src, options);
3903  }
3904  break;
3905  default:
3906  node = NEW_NODE(NODE_DSTR, STR_NEW0(), 1, NEW_LIST(node));
3907  case NODE_DSTR:
3908  if (options & RE_OPTION_ONCE) {
3910  }
3911  else {
3912  nd_set_type(node, NODE_DREGX);
3913  }
3914  node->nd_cflag = options & RE_OPTION_MASK;
3915  if (!NIL_P(node->nd_lit)) reg_fragment_check(node->nd_lit, options);
3916  for (list = (prev = node)->nd_next; list; list = list->nd_next) {
3917  if (nd_type(list->nd_head) == NODE_STR) {
3918  VALUE tail = list->nd_head->nd_lit;
3919  if (reg_fragment_check(tail, options) && prev && !NIL_P(prev->nd_lit)) {
3920  VALUE lit = prev == node ? prev->nd_lit : prev->nd_head->nd_lit;
3921  if (!literal_concat0(parser, lit, tail)) {
3922  node = 0;
3923  break;
3924  }
3925  rb_str_resize(tail, 0);
3926  prev->nd_next = list->nd_next;
3927  rb_gc_force_recycle((VALUE)list->nd_head);
3928  rb_gc_force_recycle((VALUE)list);
3929  list = prev;
3930  }
3931  else {
3932  prev = list;
3933  }
3934  }
3935  else {
3936  prev = 0;
3937  }
3938  }
3939  if (!node->nd_next) {
3940  VALUE src = node->nd_lit;
3941  nd_set_type(node, NODE_LIT);
3942  node->nd_lit = reg_compile(src, options);
3943  }
3944  break;
3945  }
3946  $$ = node;
3947  /*%
3948  $$ = dispatch2(regexp_literal, $2, $3);
3949  %*/
3950  }
3951  ;
3952 
3953 words : tWORDS_BEG ' ' tSTRING_END
3954  {
3955  /*%%%*/
3956  $$ = NEW_ZARRAY();
3957  /*%
3958  $$ = dispatch0(words_new);
3959  $$ = dispatch1(array, $$);
3960  %*/
3961  }
3962  | tWORDS_BEG word_list tSTRING_END
3963  {
3964  /*%%%*/
3965  $$ = $2;
3966  /*%
3967  $$ = dispatch1(array, $2);
3968  %*/
3969  }
3970  ;
3971 
3972 word_list : /* none */
3973  {
3974  /*%%%*/
3975  $$ = 0;
3976  /*%
3977  $$ = dispatch0(words_new);
3978  %*/
3979  }
3980  | word_list word ' '
3981  {
3982  /*%%%*/
3983  $$ = list_append($1, evstr2dstr($2));
3984  /*%
3985  $$ = dispatch2(words_add, $1, $2);
3986  %*/
3987  }
3988  ;
3989 
3990 word : string_content
3991  /*%c%*/
3992  /*%c
3993  {
3994  $$ = dispatch0(word_new);
3995  $$ = dispatch2(word_add, $$, $1);
3996  }
3997  %*/
3998  | word string_content
3999  {
4000  /*%%%*/
4001  $$ = literal_concat($1, $2);
4002  /*%
4003  $$ = dispatch2(word_add, $1, $2);
4004  %*/
4005  }
4006  ;
4007 
4009  {
4010  /*%%%*/
4011  $$ = NEW_ZARRAY();
4012  /*%
4013  $$ = dispatch0(symbols_new);
4014  $$ = dispatch1(array, $$);
4015  %*/
4016  }
4017  | tSYMBOLS_BEG symbol_list tSTRING_END
4018  {
4019  /*%%%*/
4020  $$ = $2;
4021  /*%
4022  $$ = dispatch1(array, $2);
4023  %*/
4024  }
4025  ;
4026 
4027 symbol_list : /* none */
4028  {
4029  /*%%%*/
4030  $$ = 0;
4031  /*%
4032  $$ = dispatch0(symbols_new);
4033  %*/
4034  }
4035  | symbol_list word ' '
4036  {
4037  /*%%%*/
4038  $2 = evstr2dstr($2);
4039  nd_set_type($2, NODE_DSYM);
4040  $$ = list_append($1, $2);
4041  /*%
4042  $$ = dispatch2(symbols_add, $1, $2);
4043  %*/
4044  }
4045  ;
4046 
4047 qwords : tQWORDS_BEG ' ' tSTRING_END
4048  {
4049  /*%%%*/
4050  $$ = NEW_ZARRAY();
4051  /*%
4052  $$ = dispatch0(qwords_new);
4053  $$ = dispatch1(array, $$);
4054  %*/
4055  }
4056  | tQWORDS_BEG qword_list tSTRING_END
4057  {
4058  /*%%%*/
4059  $$ = $2;
4060  /*%
4061  $$ = dispatch1(array, $2);
4062  %*/
4063  }
4064  ;
4065 
4066 qsymbols : tQSYMBOLS_BEG ' ' tSTRING_END
4067  {
4068  /*%%%*/
4069  $$ = NEW_ZARRAY();
4070  /*%
4071  $$ = dispatch0(qsymbols_new);
4072  $$ = dispatch1(array, $$);
4073  %*/
4074  }
4075  | tQSYMBOLS_BEG qsym_list tSTRING_END
4076  {
4077  /*%%%*/
4078  $$ = $2;
4079  /*%
4080  $$ = dispatch1(array, $2);
4081  %*/
4082  }
4083  ;
4084 
4085 qword_list : /* none */
4086  {
4087  /*%%%*/
4088  $$ = 0;
4089  /*%
4090  $$ = dispatch0(qwords_new);
4091  %*/
4092  }
4093  | qword_list tSTRING_CONTENT ' '
4094  {
4095  /*%%%*/
4096  $$ = list_append($1, $2);
4097  /*%
4098  $$ = dispatch2(qwords_add, $1, $2);
4099  %*/
4100  }
4101  ;
4102 
4103 qsym_list : /* none */
4104  {
4105  /*%%%*/
4106  $$ = 0;
4107  /*%
4108  $$ = dispatch0(qsymbols_new);
4109  %*/
4110  }
4111  | qsym_list tSTRING_CONTENT ' '
4112  {
4113  /*%%%*/
4114  VALUE lit;
4115  lit = $2->nd_lit;
4116  $2->nd_lit = ID2SYM(rb_intern_str(lit));
4117  nd_set_type($2, NODE_LIT);
4118  $$ = list_append($1, $2);
4119  /*%
4120  $$ = dispatch2(qsymbols_add, $1, $2);
4121  %*/
4122  }
4123  ;
4124 
4125 string_contents : /* none */
4126  {
4127  /*%%%*/
4128  $$ = 0;
4129  /*%
4130  $$ = dispatch0(string_content);
4131  %*/
4132  }
4133  | string_contents string_content
4134  {
4135  /*%%%*/
4136  $$ = literal_concat($1, $2);
4137  /*%
4138  $$ = dispatch2(string_add, $1, $2);
4139  %*/
4140  }
4141  ;
4142 
4143 xstring_contents: /* none */
4144  {
4145  /*%%%*/
4146  $$ = 0;
4147  /*%
4148  $$ = dispatch0(xstring_new);
4149  %*/
4150  }
4151  | xstring_contents string_content
4152  {
4153  /*%%%*/
4154  $$ = literal_concat($1, $2);
4155  /*%
4156  $$ = dispatch2(xstring_add, $1, $2);
4157  %*/
4158  }
4159  ;
4160 
4161 regexp_contents: /* none */
4162  {
4163  /*%%%*/
4164  $$ = 0;
4165  /*%
4166  $$ = dispatch0(regexp_new);
4167  %*/
4168  }
4169  | regexp_contents string_content
4170  {
4171  /*%%%*/
4172  NODE *head = $1, *tail = $2;
4173  if (!head) {
4174  $$ = tail;
4175  }
4176  else if (!tail) {
4177  $$ = head;
4178  }
4179  else {
4180  switch (nd_type(head)) {
4181  case NODE_STR:
4182  nd_set_type(head, NODE_DSTR);
4183  break;
4184  case NODE_DSTR:
4185  break;
4186  default:
4187  head = list_append(NEW_DSTR(Qnil), head);
4188  break;
4189  }
4190  $$ = list_append(head, tail);
4191  }
4192  /*%
4193  $$ = dispatch2(regexp_add, $1, $2);
4194  %*/
4195  }
4196  ;
4197 
4198 string_content : tSTRING_CONTENT
4199  | tSTRING_DVAR
4200  {
4201  $<node>$ = lex_strterm;
4202  lex_strterm = 0;
4203  lex_state = EXPR_BEG;
4204  }
4205  string_dvar
4206  {
4207  /*%%%*/
4208  lex_strterm = $<node>2;
4209  $$ = NEW_EVSTR($3);
4210  /*%
4211  lex_strterm = $<node>2;
4212  $$ = dispatch1(string_dvar, $3);
4213  %*/
4214  }
4215  | tSTRING_DBEG
4216  {
4217  $<val>1 = cond_stack;
4218  $<val>$ = cmdarg_stack;
4219  cond_stack = 0;
4220  cmdarg_stack = 0;
4221  }
4222  {
4223  $<node>$ = lex_strterm;
4224  lex_strterm = 0;
4225  lex_state = EXPR_BEG;
4226  }
4227  {
4228  $<num>$ = brace_nest;
4229  brace_nest = 0;
4230  }
4232  {
4233  cond_stack = $<val>1;
4234  cmdarg_stack = $<val>2;
4235  lex_strterm = $<node>3;
4236  brace_nest = $<num>4;
4237  /*%%%*/
4238  if ($5) $5->flags &= ~NODE_FL_NEWLINE;
4239  $$ = new_evstr($5);
4240  /*%
4241  $$ = dispatch1(string_embexpr, $5);
4242  %*/
4243  }
4244  ;
4245 
4246 string_dvar : tGVAR
4247  {
4248  /*%%%*/
4249  $$ = NEW_GVAR($1);
4250  /*%
4251  $$ = dispatch1(var_ref, $1);
4252  %*/
4253  }
4254  | tIVAR
4255  {
4256  /*%%%*/
4257  $$ = NEW_IVAR($1);
4258  /*%
4259  $$ = dispatch1(var_ref, $1);
4260  %*/
4261  }
4262  | tCVAR
4263  {
4264  /*%%%*/
4265  $$ = NEW_CVAR($1);
4266  /*%
4267  $$ = dispatch1(var_ref, $1);
4268  %*/
4269  }
4270  | backref
4271  ;
4272 
4273 symbol : tSYMBEG sym
4274  {
4275  lex_state = EXPR_END;
4276  /*%%%*/
4277  $$ = $2;
4278  /*%
4279  $$ = dispatch1(symbol, $2);
4280  %*/
4281  }
4282  ;
4283 
4284 sym : fname
4285  | tIVAR
4286  | tGVAR
4287  | tCVAR
4288  ;
4289 
4290 dsym : tSYMBEG xstring_contents tSTRING_END
4291  {
4292  lex_state = EXPR_END;
4293  /*%%%*/
4294  $$ = dsym_node($2);
4295  /*%
4296  $$ = dispatch1(dyna_symbol, $2);
4297  %*/
4298  }
4299  ;
4300 
4301 numeric : tINTEGER
4302  | tFLOAT
4303  | tUMINUS_NUM tINTEGER %prec tLOWEST
4304  {
4305  /*%%%*/
4306  $$ = negate_lit($2);
4307  /*%
4308  $$ = dispatch2(unary, ripper_intern("-@"), $2);
4309  %*/
4310  }
4311  | tUMINUS_NUM tFLOAT %prec tLOWEST
4312  {
4313  /*%%%*/
4314  $$ = negate_lit($2);
4315  /*%
4316  $$ = dispatch2(unary, ripper_intern("-@"), $2);
4317  %*/
4318  }
4319  ;
4320 
4321 user_variable : tIDENTIFIER
4322  | tIVAR
4323  | tGVAR
4324  | tCONSTANT
4325  | tCVAR
4326  ;
4327 
4335  ;
4336 
4337 var_ref : user_variable
4338  {
4339  /*%%%*/
4340  if (!($$ = gettable($1))) $$ = NEW_BEGIN(0);
4341  /*%
4342  if (id_is_var(get_id($1))) {
4343  $$ = dispatch1(var_ref, $1);
4344  }
4345  else {
4346  $$ = dispatch1(vcall, $1);
4347  }
4348  %*/
4349  }
4351  {
4352  /*%%%*/
4353  if (!($$ = gettable($1))) $$ = NEW_BEGIN(0);
4354  /*%
4355  $$ = dispatch1(var_ref, $1);
4356  %*/
4357  }
4358  ;
4359 
4360 var_lhs : user_variable
4361  {
4362  $$ = assignable($1, 0);
4363  /*%%%*/
4364  /*%
4365  $$ = dispatch1(var_field, $$);
4366  %*/
4367  }
4369  {
4370  $$ = assignable($1, 0);
4371  /*%%%*/
4372  /*%
4373  $$ = dispatch1(var_field, $$);
4374  %*/
4375  }
4376  ;
4377 
4378 backref : tNTH_REF
4379  | tBACK_REF
4380  ;
4381 
4382 superclass : term
4383  {
4384  /*%%%*/
4385  $$ = 0;
4386  /*%
4387  $$ = Qnil;
4388  %*/
4389  }
4390  | '<'
4391  {
4392  lex_state = EXPR_BEG;
4393  command_start = TRUE;
4394  }
4395  expr_value term
4396  {
4397  $$ = $3;
4398  }
4399  | error term
4400  {
4401  /*%%%*/
4402  yyerrok;
4403  $$ = 0;
4404  /*%
4405  yyerrok;
4406  $$ = Qnil;
4407  %*/
4408  }
4409  ;
4410 
4411 f_arglist : '(' f_args rparen
4412  {
4413  /*%%%*/
4414  $$ = $2;
4415  /*%
4416  $$ = dispatch1(paren, $2);
4417  %*/
4418  lex_state = EXPR_BEG;
4419  command_start = TRUE;
4420  }
4421  | f_args term
4422  {
4423  $$ = $1;
4424  lex_state = EXPR_BEG;
4425  command_start = TRUE;
4426  }
4427  ;
4428 
4429 args_tail : f_kwarg ',' f_kwrest opt_f_block_arg
4430  {
4431  $$ = new_args_tail($1, $3, $4);
4432  }
4433  | f_kwarg opt_f_block_arg
4434  {
4435  $$ = new_args_tail($1, Qnone, $2);
4436  }
4437  | f_kwrest opt_f_block_arg
4438  {
4439  $$ = new_args_tail(Qnone, $1, $2);
4440  }
4441  | f_block_arg
4442  {
4443  $$ = new_args_tail(Qnone, Qnone, $1);
4444  }
4445  ;
4446 
4447 opt_args_tail : ',' args_tail
4448  {
4449  $$ = $2;
4450  }
4451  | /* none */
4452  {
4453  $$ = new_args_tail(Qnone, Qnone, Qnone);
4454  }
4455  ;
4456 
4457 f_args : f_arg ',' f_optarg ',' f_rest_arg opt_args_tail
4458  {
4459  $$ = new_args($1, $3, $5, Qnone, $6);
4460  }
4461  | f_arg ',' f_optarg ',' f_rest_arg ',' f_arg opt_args_tail
4462  {
4463  $$ = new_args($1, $3, $5, $7, $8);
4464  }
4465  | f_arg ',' f_optarg opt_args_tail
4466  {
4467  $$ = new_args($1, $3, Qnone, Qnone, $4);
4468  }
4469  | f_arg ',' f_optarg ',' f_arg opt_args_tail
4470  {
4471  $$ = new_args($1, $3, Qnone, $5, $6);
4472  }
4473  | f_arg ',' f_rest_arg opt_args_tail
4474  {
4475  $$ = new_args($1, Qnone, $3, Qnone, $4);
4476  }
4477  | f_arg ',' f_rest_arg ',' f_arg opt_args_tail
4478  {
4479  $$ = new_args($1, Qnone, $3, $5, $6);
4480  }
4481  | f_arg opt_args_tail
4482  {
4483  $$ = new_args($1, Qnone, Qnone, Qnone, $2);
4484  }
4485  | f_optarg ',' f_rest_arg opt_args_tail
4486  {
4487  $$ = new_args(Qnone, $1, $3, Qnone, $4);
4488  }
4489  | f_optarg ',' f_rest_arg ',' f_arg opt_args_tail
4490  {
4491  $$ = new_args(Qnone, $1, $3, $5, $6);
4492  }
4493  | f_optarg opt_args_tail
4494  {
4495  $$ = new_args(Qnone, $1, Qnone, Qnone, $2);
4496  }
4497  | f_optarg ',' f_arg opt_args_tail
4498  {
4499  $$ = new_args(Qnone, $1, Qnone, $3, $4);
4500  }
4501  | f_rest_arg opt_args_tail
4502  {
4503  $$ = new_args(Qnone, Qnone, $1, Qnone, $2);
4504  }
4505  | f_rest_arg ',' f_arg opt_args_tail
4506  {
4507  $$ = new_args(Qnone, Qnone, $1, $3, $4);
4508  }
4509  | args_tail
4510  {
4511  $$ = new_args(Qnone, Qnone, Qnone, Qnone, $1);
4512  }
4513  | /* none */
4514  {
4515  $$ = new_args_tail(Qnone, Qnone, Qnone);
4516  $$ = new_args(Qnone, Qnone, Qnone, Qnone, $$);
4517  }
4518  ;
4519 
4520 f_bad_arg : tCONSTANT
4521  {
4522  /*%%%*/
4523  yyerror("formal argument cannot be a constant");
4524  $$ = 0;
4525  /*%
4526  $$ = dispatch1(param_error, $1);
4527  %*/
4528  }
4529  | tIVAR
4530  {
4531  /*%%%*/
4532  yyerror("formal argument cannot be an instance variable");
4533  $$ = 0;
4534  /*%
4535  $$ = dispatch1(param_error, $1);
4536  %*/
4537  }
4538  | tGVAR
4539  {
4540  /*%%%*/
4541  yyerror("formal argument cannot be a global variable");
4542  $$ = 0;
4543  /*%
4544  $$ = dispatch1(param_error, $1);
4545  %*/
4546  }
4547  | tCVAR
4548  {
4549  /*%%%*/
4550  yyerror("formal argument cannot be a class variable");
4551  $$ = 0;
4552  /*%
4553  $$ = dispatch1(param_error, $1);
4554  %*/
4555  }
4556  ;
4557 
4558 f_norm_arg : f_bad_arg
4559  | tIDENTIFIER
4560  {
4561  formal_argument(get_id($1));
4562  $$ = $1;
4563  }
4564  ;
4565 
4566 f_arg_item : f_norm_arg
4567  {
4568  arg_var(get_id($1));
4569  /*%%%*/
4570  $$ = NEW_ARGS_AUX($1, 1);
4571  /*%
4572  $$ = get_value($1);
4573  %*/
4574  }
4575  | tLPAREN f_margs rparen
4576  {
4577  ID tid = internal_id();
4578  arg_var(tid);
4579  /*%%%*/
4580  if (dyna_in_block()) {
4581  $2->nd_value = NEW_DVAR(tid);
4582  }
4583  else {
4584  $2->nd_value = NEW_LVAR(tid);
4585  }
4586  $$ = NEW_ARGS_AUX(tid, 1);
4587  $$->nd_next = $2;
4588  /*%
4589  $$ = dispatch1(mlhs_paren, $2);
4590  %*/
4591  }
4592  ;
4593 
4594 f_arg : f_arg_item
4595  /*%c%*/
4596  /*%c
4597  {
4598  $$ = rb_ary_new3(1, $1);
4599  }
4600  c%*/
4601  | f_arg ',' f_arg_item
4602  {
4603  /*%%%*/
4604  $$ = $1;
4605  $$->nd_plen++;
4606  $$->nd_next = block_append($$->nd_next, $3->nd_next);
4608  /*%
4609  $$ = rb_ary_push($1, $3);
4610  %*/
4611  }
4612  ;
4613 
4614 f_kw : tLABEL arg_value
4615  {
4617  $$ = assignable($1, $2);
4618  /*%%%*/
4619  $$ = NEW_KW_ARG(0, $$);
4620  /*%
4621  $$ = rb_assoc_new($$, $2);
4622  %*/
4623  }
4624  ;
4625 
4626 f_block_kw : tLABEL primary_value
4627  {
4629  $$ = assignable($1, $2);
4630  /*%%%*/
4631  $$ = NEW_KW_ARG(0, $$);
4632  /*%
4633  $$ = rb_assoc_new($$, $2);
4634  %*/
4635  }
4636  ;
4637 
4638 f_block_kwarg : f_block_kw
4639  {
4640  /*%%%*/
4641  $$ = $1;
4642  /*%
4643  $$ = rb_ary_new3(1, $1);
4644  %*/
4645  }
4646  | f_block_kwarg ',' f_block_kw
4647  {
4648  /*%%%*/
4649  NODE *kws = $1;
4650 
4651  while (kws->nd_next) {
4652  kws = kws->nd_next;
4653  }
4654  kws->nd_next = $3;
4655  $$ = $1;
4656  /*%
4657  $$ = rb_ary_push($1, $3);
4658  %*/
4659  }
4660  ;
4661 
4662 
4663 f_kwarg : f_kw
4664  {
4665  /*%%%*/
4666  $$ = $1;
4667  /*%
4668  $$ = rb_ary_new3(1, $1);
4669  %*/
4670  }
4671  | f_kwarg ',' f_kw
4672  {
4673  /*%%%*/
4674  NODE *kws = $1;
4675 
4676  while (kws->nd_next) {
4677  kws = kws->nd_next;
4678  }
4679  kws->nd_next = $3;
4680  $$ = $1;
4681  /*%
4682  $$ = rb_ary_push($1, $3);
4683  %*/
4684  }
4685  ;
4686 
4687 kwrest_mark : tPOW
4688  | tDSTAR
4689  ;
4690 
4691 f_kwrest : kwrest_mark tIDENTIFIER
4692  {
4693  shadowing_lvar(get_id($2));
4694  $$ = $2;
4695  }
4696  | kwrest_mark
4697  {
4698  $$ = internal_id();
4699  }
4700  ;
4701 
4702 f_opt : tIDENTIFIER '=' arg_value
4703  {
4705  $$ = assignable($1, $3);
4706  /*%%%*/
4707  $$ = NEW_OPT_ARG(0, $$);
4708  /*%
4709  $$ = rb_assoc_new($$, $3);
4710  %*/
4711  }
4712  ;
4713 
4714 f_block_opt : tIDENTIFIER '=' primary_value
4715  {
4717  $$ = assignable($1, $3);
4718  /*%%%*/
4719  $$ = NEW_OPT_ARG(0, $$);
4720  /*%
4721  $$ = rb_assoc_new($$, $3);
4722  %*/
4723  }
4724  ;
4725 
4726 f_block_optarg : f_block_opt
4727  {
4728  /*%%%*/
4729  $$ = $1;
4730  /*%
4731  $$ = rb_ary_new3(1, $1);
4732  %*/
4733  }
4734  | f_block_optarg ',' f_block_opt
4735  {
4736  /*%%%*/
4737  NODE *opts = $1;
4738 
4739  while (opts->nd_next) {
4740  opts = opts->nd_next;
4741  }
4742  opts->nd_next = $3;
4743  $$ = $1;
4744  /*%
4745  $$ = rb_ary_push($1, $3);
4746  %*/
4747  }
4748  ;
4749 
4750 f_optarg : f_opt
4751  {
4752  /*%%%*/
4753  $$ = $1;
4754  /*%
4755  $$ = rb_ary_new3(1, $1);
4756  %*/
4757  }
4758  | f_optarg ',' f_opt
4759  {
4760  /*%%%*/
4761  NODE *opts = $1;
4762 
4763  while (opts->nd_next) {
4764  opts = opts->nd_next;
4765  }
4766  opts->nd_next = $3;
4767  $$ = $1;
4768  /*%
4769  $$ = rb_ary_push($1, $3);
4770  %*/
4771  }
4772  ;
4773 
4774 restarg_mark : '*'
4775  | tSTAR
4776  ;
4777 
4778 f_rest_arg : restarg_mark tIDENTIFIER
4779  {
4780  /*%%%*/
4781  if (!is_local_id($2))
4782  yyerror("rest argument must be local variable");
4783  /*% %*/
4785  /*%%%*/
4786  $$ = $2;
4787  /*%
4788  $$ = dispatch1(rest_param, $2);
4789  %*/
4790  }
4791  | restarg_mark
4792  {
4793  /*%%%*/
4794  $$ = internal_id();
4795  arg_var($$);
4796  /*%
4797  $$ = dispatch1(rest_param, Qnil);
4798  %*/
4799  }
4800  ;
4801 
4802 blkarg_mark : '&'
4803  | tAMPER
4804  ;
4805 
4806 f_block_arg : blkarg_mark tIDENTIFIER
4807  {
4808  /*%%%*/
4809  if (!is_local_id($2))
4810  yyerror("block argument must be local variable");
4811  else if (!dyna_in_block() && local_id($2))
4812  yyerror("duplicated block argument name");
4813  /*% %*/
4815  /*%%%*/
4816  $$ = $2;
4817  /*%
4818  $$ = dispatch1(blockarg, $2);
4819  %*/
4820  }
4821  ;
4822 
4823 opt_f_block_arg : ',' f_block_arg
4824  {
4825  $$ = $2;
4826  }
4827  | none
4828  {
4829  /*%%%*/
4830  $$ = 0;
4831  /*%
4832  $$ = Qundef;
4833  %*/
4834  }
4835  ;
4836 
4837 singleton : var_ref
4838  {
4839  /*%%%*/
4840  value_expr($1);
4841  $$ = $1;
4842  if (!$$) $$ = NEW_NIL();
4843  /*%
4844  $$ = $1;
4845  %*/
4846  }
4847  | '(' {lex_state = EXPR_BEG;} expr rparen
4848  {
4849  /*%%%*/
4850  if ($3 == 0) {
4851  yyerror("can't define singleton method for ().");
4852  }
4853  else {
4854  switch (nd_type($3)) {
4855  case NODE_STR:
4856  case NODE_DSTR:
4857  case NODE_XSTR:
4858  case NODE_DXSTR:
4859  case NODE_DREGX:
4860  case NODE_LIT:
4861  case NODE_ARRAY:
4862  case NODE_ZARRAY:
4863  yyerror("can't define singleton method for literals");
4864  default:
4865  value_expr($3);
4866  break;
4867  }
4868  }
4869  $$ = $3;
4870  /*%
4871  $$ = dispatch1(paren, $3);
4872  %*/
4873  }
4874  ;
4875 
4876 assoc_list : none
4877  | assocs trailer
4878  {
4879  /*%%%*/
4880  $$ = $1;
4881  /*%
4882  $$ = dispatch1(assoclist_from_args, $1);
4883  %*/
4884  }
4885  ;
4886 
4887 assocs : assoc
4888  /*%c%*/
4889  /*%c
4890  {
4891  $$ = rb_ary_new3(1, $1);
4892  }
4893  %*/
4894  | assocs ',' assoc
4895  {
4896  /*%%%*/
4897  $$ = list_concat($1, $3);
4898  /*%
4899  $$ = rb_ary_push($1, $3);
4900  %*/
4901  }
4902  ;
4903 
4904 assoc : arg_value tASSOC arg_value
4905  {
4906  /*%%%*/
4907  $$ = list_append(NEW_LIST($1), $3);
4908  /*%
4909  $$ = dispatch2(assoc_new, $1, $3);
4910  %*/
4911  }
4912  | tLABEL arg_value
4913  {
4914  /*%%%*/
4915  $$ = list_append(NEW_LIST(NEW_LIT(ID2SYM($1))), $2);
4916  /*%
4917  $$ = dispatch2(assoc_new, $1, $2);
4918  %*/
4919  }
4920  | tDSTAR arg_value
4921  {
4922  /*%%%*/
4923  $$ = list_append(NEW_LIST(0), $2);
4924  /*%
4925  $$ = dispatch1(assoc_splat, $2);
4926  %*/
4927  }
4928  ;
4929 
4930  ;
4931 
4932 operation : tIDENTIFIER
4933  | tCONSTANT
4934  | tFID
4935  ;
4936 
4937 operation2 : tIDENTIFIER
4938  | tCONSTANT
4939  | tFID
4940  | op
4941  ;
4942 
4943 operation3 : tIDENTIFIER
4944  | tFID
4945  | op
4946  ;
4947 
4948 dot_or_colon : '.'
4949  /*%c%*/
4950  /*%c
4951  { $$ = $<val>1; }
4952  %*/
4953  | tCOLON2
4954  /*%c%*/
4955  /*%c
4956  { $$ = $<val>1; }
4957  %*/
4958  ;
4959 
4960 opt_terms : /* none */
4961  | terms
4962  ;
4963 
4964 opt_nl : /* none */
4965  | '\n'
4966  ;
4967 
4968 rparen : opt_nl ')'
4969  ;
4970 
4971 rbracket : opt_nl ']'
4972  ;
4973 
4974 trailer : /* none */
4975  | '\n'
4976  | ','
4977  ;
4978 
4979 term : ';' {yyerrok;}
4980  | '\n'
4981  ;
4982 
4983 terms : term
4984  | terms ';' {yyerrok;}
4985  ;
4986 
4987 none : /* none */
4988  {
4989  /*%%%*/
4990  $$ = 0;
4991  /*%
4992  $$ = Qundef;
4993  %*/
4994  }
4995  ;
4996 %%
4997 # undef parser
4998 # undef yylex
4999 # undef yylval
5000 # define yylval (*((YYSTYPE*)(parser->parser_yylval)))
5001 
5002 static int parser_regx_options(struct parser_params*);
5003 static int parser_tokadd_string(struct parser_params*,int,int,int,long*,rb_encoding**);
5004 static void parser_tokaddmbc(struct parser_params *parser, int c, rb_encoding *enc);
5005 static int parser_parse_string(struct parser_params*,NODE*);
5006 static int parser_here_document(struct parser_params*,NODE*);
5007 
5008 
5009 # define nextc() parser_nextc(parser)
5010 # define pushback(c) parser_pushback(parser, (c))
5011 # define newtok() parser_newtok(parser)
5012 # define tokspace(n) parser_tokspace(parser, (n))
5013 # define tokadd(c) parser_tokadd(parser, (c))
5014 # define tok_hex(numlen) parser_tok_hex(parser, (numlen))
5015 # define read_escape(flags,e) parser_read_escape(parser, (flags), (e))
5016 # define tokadd_escape(e) parser_tokadd_escape(parser, (e))
5017 # define regx_options() parser_regx_options(parser)
5018 # define tokadd_string(f,t,p,n,e) parser_tokadd_string(parser,(f),(t),(p),(n),(e))
5019 # define parse_string(n) parser_parse_string(parser,(n))
5020 # define tokaddmbc(c, enc) parser_tokaddmbc(parser, (c), (enc))
5021 # define here_document(n) parser_here_document(parser,(n))
5022 # define heredoc_identifier() parser_heredoc_identifier(parser)
5023 # define heredoc_restore(n) parser_heredoc_restore(parser,(n))
5024 # define whole_match_p(e,l,i) parser_whole_match_p(parser,(e),(l),(i))
5025 
5026 #ifndef RIPPER
5027 # define set_yylval_str(x) (yylval.node = NEW_STR(x))
5028 # define set_yylval_num(x) (yylval.num = (x))
5029 # define set_yylval_id(x) (yylval.id = (x))
5030 # define set_yylval_name(x) (yylval.id = (x))
5031 # define set_yylval_literal(x) (yylval.node = NEW_LIT(x))
5032 # define set_yylval_node(x) (yylval.node = (x))
5033 # define yylval_id() (yylval.id)
5034 #else
5035 static inline VALUE
5036 ripper_yylval_id(ID x)
5037 {
5038  return (VALUE)NEW_LASGN(x, ID2SYM(x));
5039 }
5040 # define set_yylval_str(x) (void)(x)
5041 # define set_yylval_num(x) (void)(x)
5042 # define set_yylval_id(x) (void)(x)
5043 # define set_yylval_name(x) (void)(yylval.val = ripper_yylval_id(x))
5044 # define set_yylval_literal(x) (void)(x)
5045 # define set_yylval_node(x) (void)(x)
5046 # define yylval_id() yylval.id
5047 #endif
5048 
5049 #ifndef RIPPER
5050 #define ripper_flush(p) (void)(p)
5051 #else
5052 #define ripper_flush(p) ((p)->tokp = (p)->parser_lex_p)
5053 
5054 #define yylval_rval (*(RB_TYPE_P(yylval.val, T_NODE) ? &yylval.node->nd_rval : &yylval.val))
5055 
5056 static int
5057 ripper_has_scan_event(struct parser_params *parser)
5058 {
5059 
5060  if (lex_p < parser->tokp) rb_raise(rb_eRuntimeError, "lex_p < tokp");
5061  return lex_p > parser->tokp;
5062 }
5063 
5064 static VALUE
5065 ripper_scan_event_val(struct parser_params *parser, int t)
5066 {
5067  VALUE str = STR_NEW(parser->tokp, lex_p - parser->tokp);
5068  VALUE rval = ripper_dispatch1(parser, ripper_token2eventid(t), str);
5069  ripper_flush(parser);
5070  return rval;
5071 }
5072 
5073 static void
5074 ripper_dispatch_scan_event(struct parser_params *parser, int t)
5075 {
5076  if (!ripper_has_scan_event(parser)) return;
5077  yylval_rval = ripper_scan_event_val(parser, t);
5078 }
5079 
5080 static void
5081 ripper_dispatch_ignored_scan_event(struct parser_params *parser, int t)
5082 {
5083  if (!ripper_has_scan_event(parser)) return;
5084  (void)ripper_scan_event_val(parser, t);
5085 }
5086 
5087 static void
5088 ripper_dispatch_delayed_token(struct parser_params *parser, int t)
5089 {
5090  int saved_line = ruby_sourceline;
5091  const char *saved_tokp = parser->tokp;
5092 
5093  ruby_sourceline = parser->delayed_line;
5094  parser->tokp = lex_pbeg + parser->delayed_col;
5095  yylval_rval = ripper_dispatch1(parser, ripper_token2eventid(t), parser->delayed);
5096  parser->delayed = Qnil;
5097  ruby_sourceline = saved_line;
5098  parser->tokp = saved_tokp;
5099 }
5100 #endif /* RIPPER */
5101 
5102 #include "ruby/regex.h"
5103 #include "ruby/util.h"
5104 
5105 /* We remove any previous definition of `SIGN_EXTEND_CHAR',
5106  since ours (we hope) works properly with all combinations of
5107  machines, compilers, `char' and `unsigned char' argument types.
5108  (Per Bothner suggested the basic approach.) */
5109 #undef SIGN_EXTEND_CHAR
5110 #if __STDC__
5111 # define SIGN_EXTEND_CHAR(c) ((signed char)(c))
5112 #else /* not __STDC__ */
5113 /* As in Harbison and Steele. */
5114 # define SIGN_EXTEND_CHAR(c) ((((unsigned char)(c)) ^ 128) - 128)
5115 #endif
5116 
5117 #define parser_encoding_name() (current_enc->name)
5118 #define parser_mbclen() mbclen((lex_p-1),lex_pend,current_enc)
5119 #define parser_precise_mbclen() rb_enc_precise_mbclen((lex_p-1),lex_pend,current_enc)
5120 #define is_identchar(p,e,enc) (rb_enc_isalnum(*(p),(enc)) || (*(p)) == '_' || !ISASCII(*(p)))
5121 #define parser_is_identchar() (!parser->eofp && is_identchar((lex_p-1),lex_pend,current_enc))
5122 
5123 #define parser_isascii() ISASCII(*(lex_p-1))
5124 
5125 #ifndef RIPPER
5126 static int
5127 token_info_get_column(struct parser_params *parser, const char *token)
5128 {
5129  int column = 1;
5130  const char *p, *pend = lex_p - strlen(token);
5131  for (p = lex_pbeg; p < pend; p++) {
5132  if (*p == '\t') {
5133  column = (((column - 1) / 8) + 1) * 8;
5134  }
5135  column++;
5136  }
5137  return column;
5138 }
5139 
5140 static int
5141 token_info_has_nonspaces(struct parser_params *parser, const char *token)
5142 {
5143  const char *p, *pend = lex_p - strlen(token);
5144  for (p = lex_pbeg; p < pend; p++) {
5145  if (*p != ' ' && *p != '\t') {
5146  return 1;
5147  }
5148  }
5149  return 0;
5150 }
5151 
5152 #undef token_info_push
5153 static void
5154 token_info_push(struct parser_params *parser, const char *token)
5155 {
5156  token_info *ptinfo;
5157 
5158  if (!parser->parser_token_info_enabled) return;
5159  ptinfo = ALLOC(token_info);
5160  ptinfo->token = token;
5161  ptinfo->linenum = ruby_sourceline;
5162  ptinfo->column = token_info_get_column(parser, token);
5163  ptinfo->nonspc = token_info_has_nonspaces(parser, token);
5164  ptinfo->next = parser->parser_token_info;
5165 
5166  parser->parser_token_info = ptinfo;
5167 }
5168 
5169 #undef token_info_pop
5170 static void
5171 token_info_pop(struct parser_params *parser, const char *token)
5172 {
5173  int linenum;
5174  token_info *ptinfo = parser->parser_token_info;
5175 
5176  if (!ptinfo) return;
5177  parser->parser_token_info = ptinfo->next;
5178  if (token_info_get_column(parser, token) == ptinfo->column) { /* OK */
5179  goto finish;
5180  }
5181  linenum = ruby_sourceline;
5182  if (linenum == ptinfo->linenum) { /* SKIP */
5183  goto finish;
5184  }
5185  if (token_info_has_nonspaces(parser, token) || ptinfo->nonspc) { /* SKIP */
5186  goto finish;
5187  }
5188  if (parser->parser_token_info_enabled) {
5190  "mismatched indentations at '%s' with '%s' at %d",
5191  token, ptinfo->token, ptinfo->linenum);
5192  }
5193 
5194  finish:
5195  xfree(ptinfo);
5196 }
5197 #endif /* RIPPER */
5198 
5199 static int
5200 parser_yyerror(struct parser_params *parser, const char *msg)
5201 {
5202 #ifndef RIPPER
5203  const int max_line_margin = 30;
5204  const char *p, *pe;
5205  char *buf;
5206  long len;
5207  int i;
5208 
5209  compile_error(PARSER_ARG "%s", msg);
5210  p = lex_p;
5211  while (lex_pbeg <= p) {
5212  if (*p == '\n') break;
5213  p--;
5214  }
5215  p++;
5216 
5217  pe = lex_p;
5218  while (pe < lex_pend) {
5219  if (*pe == '\n') break;
5220  pe++;
5221  }
5222 
5223  len = pe - p;
5224  if (len > 4) {
5225  char *p2;
5226  const char *pre = "", *post = "";
5227 
5228  if (len > max_line_margin * 2 + 10) {
5229  if (lex_p - p > max_line_margin) {
5230  p = rb_enc_prev_char(p, lex_p - max_line_margin, pe, rb_enc_get(lex_lastline));
5231  pre = "...";
5232  }
5233  if (pe - lex_p > max_line_margin) {
5234  pe = rb_enc_prev_char(lex_p, lex_p + max_line_margin, pe, rb_enc_get(lex_lastline));
5235  post = "...";
5236  }
5237  len = pe - p;
5238  }
5239  buf = ALLOCA_N(char, len+2);
5240  MEMCPY(buf, p, char, len);
5241  buf[len] = '\0';
5242  rb_compile_error_append("%s%s%s", pre, buf, post);
5243 
5244  i = (int)(lex_p - p);
5245  p2 = buf; pe = buf + len;
5246 
5247  while (p2 < pe) {
5248  if (*p2 != '\t') *p2 = ' ';
5249  p2++;
5250  }
5251  buf[i] = '^';
5252  buf[i+1] = '\0';
5253  rb_compile_error_append("%s%s", pre, buf);
5254  }
5255 #else
5256  dispatch1(parse_error, STR_NEW2(msg));
5257 #endif /* !RIPPER */
5258  return 0;
5259 }
5260 
5261 static void parser_prepare(struct parser_params *parser);
5262 
5263 #ifndef RIPPER
5264 static VALUE
5265 debug_lines(const char *f)
5266 {
5267  ID script_lines;
5268  CONST_ID(script_lines, "SCRIPT_LINES__");
5269  if (rb_const_defined_at(rb_cObject, script_lines)) {
5270  VALUE hash = rb_const_get_at(rb_cObject, script_lines);
5271  if (RB_TYPE_P(hash, T_HASH)) {
5273  VALUE lines = rb_ary_new();
5274  rb_hash_aset(hash, fname, lines);
5275  return lines;
5276  }
5277  }
5278  return 0;
5279 }
5280 
5281 static VALUE
5282 coverage(const char *f, int n)
5283 {
5284  VALUE coverages = rb_get_coverages();
5285  if (RTEST(coverages) && RBASIC(coverages)->klass == 0) {
5287  VALUE lines = rb_ary_new2(n);
5288  int i;
5289  RBASIC(lines)->klass = 0;
5290  for (i = 0; i < n; i++) RARRAY_PTR(lines)[i] = Qnil;
5291  RARRAY(lines)->as.heap.len = n;
5292  rb_hash_aset(coverages, fname, lines);
5293  return lines;
5294  }
5295  return 0;
5296 }
5297 
5298 static int
5299 e_option_supplied(struct parser_params *parser)
5300 {
5301  return strcmp(ruby_sourcefile, "-e") == 0;
5302 }
5303 
5304 static VALUE
5306 {
5307  int n;
5308  NODE *tree;
5309  struct parser_params *parser = (struct parser_params *)arg;
5310 
5311  if (!compile_for_eval && rb_safe_level() == 0) {
5313  if (ruby_debug_lines && ruby_sourceline > 0) {
5314  VALUE str = STR_NEW0();
5315  n = ruby_sourceline;
5316  do {
5318  } while (--n);
5319  }
5320 
5321  if (!e_option_supplied(parser)) {
5323  }
5324  }
5325 
5326  parser_prepare(parser);
5327  deferred_nodes = 0;
5328 #ifndef RIPPER
5330 #endif
5331 #ifndef RIPPER
5334  parser->parser_ruby_sourceline);
5335  }
5336 #endif
5337  n = yyparse((void*)parser);
5338 #ifndef RIPPER
5341  parser->parser_ruby_sourceline);
5342  }
5343 #endif
5344  ruby_debug_lines = 0;
5345  ruby_coverage = 0;
5346  compile_for_eval = 0;
5347 
5348  lex_strterm = 0;
5349  lex_p = lex_pbeg = lex_pend = 0;
5350  lex_lastline = lex_nextline = 0;
5351  if (parser->nerr) {
5352  return 0;
5353  }
5354  tree = ruby_eval_tree;
5355  if (!tree) {
5356  tree = NEW_NIL();
5357  }
5358  else if (ruby_eval_tree_begin) {
5359  tree->nd_body = NEW_PRELUDE(ruby_eval_tree_begin, tree->nd_body);
5360  }
5361  return (VALUE)tree;
5362 }
5363 
5364 static NODE*
5365 yycompile(struct parser_params *parser, const char *f, int line)
5366 {
5368  ruby_sourceline = line - 1;
5369  return (NODE *)rb_suppress_tracing(yycompile0, (VALUE)parser);
5370 }
5371 #endif /* !RIPPER */
5372 
5373 static rb_encoding *
5375 {
5376  rb_encoding *enc = rb_enc_get(s);
5377  if (!rb_enc_asciicompat(enc)) {
5378  rb_raise(rb_eArgError, "invalid source encoding");
5379  }
5380  return enc;
5381 }
5382 
5383 static VALUE
5384 lex_get_str(struct parser_params *parser, VALUE s)
5385 {
5386  char *beg, *end, *pend;
5388 
5389  beg = RSTRING_PTR(s);
5390  if (lex_gets_ptr) {
5391  if (RSTRING_LEN(s) == lex_gets_ptr) return Qnil;
5392  beg += lex_gets_ptr;
5393  }
5394  pend = RSTRING_PTR(s) + RSTRING_LEN(s);
5395  end = beg;
5396  while (end < pend) {
5397  if (*end++ == '\n') break;
5398  }
5399  lex_gets_ptr = end - RSTRING_PTR(s);
5400  return rb_enc_str_new(beg, end - beg, enc);
5401 }
5402 
5403 static VALUE
5404 lex_getline(struct parser_params *parser)
5405 {
5406  VALUE line = (*parser->parser_lex_gets)(parser, parser->parser_lex_input);
5407  if (NIL_P(line)) return line;
5409 #ifndef RIPPER
5410  if (ruby_debug_lines) {
5413  }
5414  if (ruby_coverage) {
5416  }
5417 #endif
5418  return line;
5419 }
5420 
5421 #ifdef RIPPER
5423 #else
5424 static const rb_data_type_t parser_data_type;
5425 
5426 static NODE*
5427 parser_compile_string(volatile VALUE vparser, const char *f, VALUE s, int line)
5428 {
5429  struct parser_params *parser;
5430  NODE *node;
5431 
5432  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
5434  lex_gets_ptr = 0;
5435  lex_input = s;
5436  lex_pbeg = lex_p = lex_pend = 0;
5438 
5439  node = yycompile(parser, f, line);
5440  RB_GC_GUARD(vparser); /* prohibit tail call optimization */
5441 
5442  return node;
5443 }
5444 
5445 NODE*
5446 rb_compile_string(const char *f, VALUE s, int line)
5447 {
5449  return parser_compile_string(rb_parser_new(), f, s, line);
5450 }
5451 
5452 NODE*
5453 rb_parser_compile_string(volatile VALUE vparser, const char *f, VALUE s, int line)
5454 {
5456  return parser_compile_string(vparser, f, s, line);
5457 }
5458 
5459 NODE*
5460 rb_compile_cstr(const char *f, const char *s, int len, int line)
5461 {
5462  VALUE str = rb_str_new(s, len);
5463  return parser_compile_string(rb_parser_new(), f, str, line);
5464 }
5465 
5466 NODE*
5467 rb_parser_compile_cstr(volatile VALUE vparser, const char *f, const char *s, int len, int line)
5468 {
5469  VALUE str = rb_str_new(s, len);
5470  return parser_compile_string(vparser, f, str, line);
5471 }
5472 
5473 static VALUE
5474 lex_io_gets(struct parser_params *parser, VALUE io)
5475 {
5476  return rb_io_gets(io);
5477 }
5478 
5479 NODE*
5480 rb_compile_file(const char *f, VALUE file, int start)
5481 {
5482  VALUE volatile vparser = rb_parser_new();
5483 
5484  return rb_parser_compile_file(vparser, f, file, start);
5485 }
5486 
5487 NODE*
5488 rb_parser_compile_file(volatile VALUE vparser, const char *f, VALUE file, int start)
5489 {
5490  struct parser_params *parser;
5491  NODE *node;
5492 
5493  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
5495  lex_input = file;
5496  lex_pbeg = lex_p = lex_pend = 0;
5498 
5499  node = yycompile(parser, f, start);
5500  RB_GC_GUARD(vparser); /* prohibit tail call optimization */
5501 
5502  return node;
5503 }
5504 #endif /* !RIPPER */
5505 
5506 #define STR_FUNC_ESCAPE 0x01
5507 #define STR_FUNC_EXPAND 0x02
5508 #define STR_FUNC_REGEXP 0x04
5509 #define STR_FUNC_QWORDS 0x08
5510 #define STR_FUNC_SYMBOL 0x10
5511 #define STR_FUNC_INDENT 0x20
5512 
5513 enum string_type {
5514  str_squote = (0),
5522 };
5523 
5524 static VALUE
5525 parser_str_new(const char *p, long n, rb_encoding *enc, int func, rb_encoding *enc0)
5526 {
5527  VALUE str;
5528 
5529  str = rb_enc_str_new(p, n, enc);
5530  if (!(func & STR_FUNC_REGEXP) && rb_enc_asciicompat(enc)) {
5532  }
5533  else if (enc0 == rb_usascii_encoding() && enc != rb_utf8_encoding()) {
5535  }
5536  }
5537 
5538  return str;
5539 }
5540 
5541 #define lex_goto_eol(parser) ((parser)->parser_lex_p = (parser)->parser_lex_pend)
5542 #define lex_eol_p() (lex_p >= lex_pend)
5543 #define peek(c) peek_n((c), 0)
5544 #define peek_n(c,n) (lex_p+(n) < lex_pend && (c) == (unsigned char)lex_p[n])
5545 
5546 static inline int
5547 parser_nextc(struct parser_params *parser)
5548 {
5549  int c;
5550 
5551  if (lex_p == lex_pend) {
5552  VALUE v = lex_nextline;
5553  lex_nextline = 0;
5554  if (!v) {
5555  if (parser->eofp)
5556  return -1;
5557 
5558  if (!lex_input || NIL_P(v = lex_getline(parser))) {
5559  parser->eofp = Qtrue;
5560  lex_goto_eol(parser);
5561  return -1;
5562  }
5563  }
5564  {
5565 #ifdef RIPPER
5566  if (parser->tokp < lex_pend) {
5567  if (NIL_P(parser->delayed)) {
5568  parser->delayed = rb_str_buf_new(1024);
5569  rb_enc_associate(parser->delayed, current_enc);
5570  rb_str_buf_cat(parser->delayed,
5571  parser->tokp, lex_pend - parser->tokp);
5572  parser->delayed_line = ruby_sourceline;
5573  parser->delayed_col = (int)(parser->tokp - lex_pbeg);
5574  }
5575  else {
5576  rb_str_buf_cat(parser->delayed,
5577  parser->tokp, lex_pend - parser->tokp);
5578  }
5579  }
5580 #endif
5581  if (heredoc_end > 0) {
5583  heredoc_end = 0;
5584  }
5585  ruby_sourceline++;
5586  parser->line_count++;
5587  lex_pbeg = lex_p = RSTRING_PTR(v);
5588  lex_pend = lex_p + RSTRING_LEN(v);
5589  ripper_flush(parser);
5590  lex_lastline = v;
5591  }
5592  }
5593  c = (unsigned char)*lex_p++;
5594  if (c == '\r' && peek('\n')) {
5595  lex_p++;
5596  c = '\n';
5597  }
5598 
5599  return c;
5600 }
5601 
5602 static void
5603 parser_pushback(struct parser_params *parser, int c)
5604 {
5605  if (c == -1) return;
5606  lex_p--;
5607  if (lex_p > lex_pbeg && lex_p[0] == '\n' && lex_p[-1] == '\r') {
5608  lex_p--;
5609  }
5610 }
5611 
5612 #define was_bol() (lex_p == lex_pbeg + 1)
5613 
5614 #define tokfix() (tokenbuf[tokidx]='\0')
5615 #define tok() tokenbuf
5616 #define toklen() tokidx
5617 #define toklast() (tokidx>0?tokenbuf[tokidx-1]:0)
5618 
5619 static char*
5620 parser_newtok(struct parser_params *parser)
5621 {
5622  tokidx = 0;
5624  if (!tokenbuf) {
5625  toksiz = 60;
5626  tokenbuf = ALLOC_N(char, 60);
5627  }
5628  if (toksiz > 4096) {
5629  toksiz = 60;
5630  REALLOC_N(tokenbuf, char, 60);
5631  }
5632  return tokenbuf;
5633 }
5634 
5635 static char *
5636 parser_tokspace(struct parser_params *parser, int n)
5637 {
5638  tokidx += n;
5639 
5640  if (tokidx >= toksiz) {
5641  do {toksiz *= 2;} while (toksiz < tokidx);
5642  REALLOC_N(tokenbuf, char, toksiz);
5643  }
5644  return &tokenbuf[tokidx-n];
5645 }
5646 
5647 static void
5648 parser_tokadd(struct parser_params *parser, int c)
5649 {
5650  tokenbuf[tokidx++] = (char)c;
5651  if (tokidx >= toksiz) {
5652  toksiz *= 2;
5653  REALLOC_N(tokenbuf, char, toksiz);
5654  }
5655 }
5656 
5657 static int
5658 parser_tok_hex(struct parser_params *parser, size_t *numlen)
5659 {
5660  int c;
5661 
5662  c = scan_hex(lex_p, 2, numlen);
5663  if (!*numlen) {
5664  yyerror("invalid hex escape");
5665  return 0;
5666  }
5667  lex_p += *numlen;
5668  return c;
5669 }
5670 
5671 #define tokcopy(n) memcpy(tokspace(n), lex_p - (n), (n))
5672 
5673 /* return value is for ?\u3042 */
5674 static int
5675 parser_tokadd_utf8(struct parser_params *parser, rb_encoding **encp,
5676  int string_literal, int symbol_literal, int regexp_literal)
5677 {
5678  /*
5679  * If string_literal is true, then we allow multiple codepoints
5680  * in \u{}, and add the codepoints to the current token.
5681  * Otherwise we're parsing a character literal and return a single
5682  * codepoint without adding it
5683  */
5684 
5685  int codepoint;
5686  size_t numlen;
5687 
5688  if (regexp_literal) { tokadd('\\'); tokadd('u'); }
5689 
5690  if (peek('{')) { /* handle \u{...} form */
5691  do {
5692  if (regexp_literal) { tokadd(*lex_p); }
5693  nextc();
5694  codepoint = scan_hex(lex_p, 6, &numlen);
5695  if (numlen == 0) {
5696  yyerror("invalid Unicode escape");
5697  return 0;
5698  }
5699  if (codepoint > 0x10ffff) {
5700  yyerror("invalid Unicode codepoint (too large)");
5701  return 0;
5702  }
5703  lex_p += numlen;
5704  if (regexp_literal) {
5705  tokcopy((int)numlen);
5706  }
5707  else if (codepoint >= 0x80) {
5708  *encp = rb_utf8_encoding();
5709  if (string_literal) tokaddmbc(codepoint, *encp);
5710  }
5711  else if (string_literal) {
5712  tokadd(codepoint);
5713  }
5714  } while (string_literal && (peek(' ') || peek('\t')));
5715 
5716  if (!peek('}')) {
5717  yyerror("unterminated Unicode escape");
5718  return 0;
5719  }
5720 
5721  if (regexp_literal) { tokadd('}'); }
5722  nextc();
5723  }
5724  else { /* handle \uxxxx form */
5725  codepoint = scan_hex(lex_p, 4, &numlen);
5726  if (numlen < 4) {
5727  yyerror("invalid Unicode escape");
5728  return 0;
5729  }
5730  lex_p += 4;
5731  if (regexp_literal) {
5732  tokcopy(4);
5733  }
5734  else if (codepoint >= 0x80) {
5735  *encp = rb_utf8_encoding();
5736  if (string_literal) tokaddmbc(codepoint, *encp);
5737  }
5738  else if (string_literal) {
5739  tokadd(codepoint);
5740  }
5741  }
5742 
5743  return codepoint;
5744 }
5745 
5746 #define ESCAPE_CONTROL 1
5747 #define ESCAPE_META 2
5748 
5749 static int
5750 parser_read_escape(struct parser_params *parser, int flags,
5751  rb_encoding **encp)
5752 {
5753  int c;
5754  size_t numlen;
5755 
5756  switch (c = nextc()) {
5757  case '\\': /* Backslash */
5758  return c;
5759 
5760  case 'n': /* newline */
5761  return '\n';
5762 
5763  case 't': /* horizontal tab */
5764  return '\t';
5765 
5766  case 'r': /* carriage-return */
5767  return '\r';
5768 
5769  case 'f': /* form-feed */
5770  return '\f';
5771 
5772  case 'v': /* vertical tab */
5773  return '\13';
5774 
5775  case 'a': /* alarm(bell) */
5776  return '\007';
5777 
5778  case 'e': /* escape */
5779  return 033;
5780 
5781  case '0': case '1': case '2': case '3': /* octal constant */
5782  case '4': case '5': case '6': case '7':
5783  pushback(c);
5784  c = scan_oct(lex_p, 3, &numlen);
5785  lex_p += numlen;
5786  return c;
5787 
5788  case 'x': /* hex constant */
5789  c = tok_hex(&numlen);
5790  if (numlen == 0) return 0;
5791  return c;
5792 
5793  case 'b': /* backspace */
5794  return '\010';
5795 
5796  case 's': /* space */
5797  return ' ';
5798 
5799  case 'M':
5800  if (flags & ESCAPE_META) goto eof;
5801  if ((c = nextc()) != '-') {
5802  pushback(c);
5803  goto eof;
5804  }
5805  if ((c = nextc()) == '\\') {
5806  if (peek('u')) goto eof;
5807  return read_escape(flags|ESCAPE_META, encp) | 0x80;
5808  }
5809  else if (c == -1 || !ISASCII(c)) goto eof;
5810  else {
5811  return ((c & 0xff) | 0x80);
5812  }
5813 
5814  case 'C':
5815  if ((c = nextc()) != '-') {
5816  pushback(c);
5817  goto eof;
5818  }
5819  case 'c':
5820  if (flags & ESCAPE_CONTROL) goto eof;
5821  if ((c = nextc())== '\\') {
5822  if (peek('u')) goto eof;
5823  c = read_escape(flags|ESCAPE_CONTROL, encp);
5824  }
5825  else if (c == '?')
5826  return 0177;
5827  else if (c == -1 || !ISASCII(c)) goto eof;
5828  return c & 0x9f;
5829 
5830  eof:
5831  case -1:
5832  yyerror("Invalid escape character syntax");
5833  return '\0';
5834 
5835  default:
5836  return c;
5837  }
5838 }
5839 
5840 static void
5841 parser_tokaddmbc(struct parser_params *parser, int c, rb_encoding *enc)
5842 {
5843  int len = rb_enc_codelen(c, enc);
5844  rb_enc_mbcput(c, tokspace(len), enc);
5845 }
5846 
5847 static int
5848 parser_tokadd_escape(struct parser_params *parser, rb_encoding **encp)
5849 {
5850  int c;
5851  int flags = 0;
5852  size_t numlen;
5853 
5854  first:
5855  switch (c = nextc()) {
5856  case '\n':
5857  return 0; /* just ignore */
5858 
5859  case '0': case '1': case '2': case '3': /* octal constant */
5860  case '4': case '5': case '6': case '7':
5861  {
5862  ruby_scan_oct(--lex_p, 3, &numlen);
5863  if (numlen == 0) goto eof;
5864  lex_p += numlen;
5865  tokcopy((int)numlen + 1);
5866  }
5867  return 0;
5868 
5869  case 'x': /* hex constant */
5870  {
5871  tok_hex(&numlen);
5872  if (numlen == 0) return -1;
5873  tokcopy((int)numlen + 2);
5874  }
5875  return 0;
5876 
5877  case 'M':
5878  if (flags & ESCAPE_META) goto eof;
5879  if ((c = nextc()) != '-') {
5880  pushback(c);
5881  goto eof;
5882  }
5883  tokcopy(3);
5884  flags |= ESCAPE_META;
5885  goto escaped;
5886 
5887  case 'C':
5888  if (flags & ESCAPE_CONTROL) goto eof;
5889  if ((c = nextc()) != '-') {
5890  pushback(c);
5891  goto eof;
5892  }
5893  tokcopy(3);
5894  goto escaped;
5895 
5896  case 'c':
5897  if (flags & ESCAPE_CONTROL) goto eof;
5898  tokcopy(2);
5899  flags |= ESCAPE_CONTROL;
5900  escaped:
5901  if ((c = nextc()) == '\\') {
5902  goto first;
5903  }
5904  else if (c == -1) goto eof;
5905  tokadd(c);
5906  return 0;
5907 
5908  eof:
5909  case -1:
5910  yyerror("Invalid escape character syntax");
5911  return -1;
5912 
5913  default:
5914  tokadd('\\');
5915  tokadd(c);
5916  }
5917  return 0;
5918 }
5919 
5920 static int
5921 parser_regx_options(struct parser_params *parser)
5922 {
5923  int kcode = 0;
5924  int kopt = 0;
5925  int options = 0;
5926  int c, opt, kc;
5927 
5928  newtok();
5929  while (c = nextc(), ISALPHA(c)) {
5930  if (c == 'o') {
5931  options |= RE_OPTION_ONCE;
5932  }
5933  else if (rb_char_to_option_kcode(c, &opt, &kc)) {
5934  if (kc >= 0) {
5935  if (kc != rb_ascii8bit_encindex()) kcode = c;
5936  kopt = opt;
5937  }
5938  else {
5939  options |= opt;
5940  }
5941  }
5942  else {
5943  tokadd(c);
5944  }
5945  }
5946  options |= kopt;
5947  pushback(c);
5948  if (toklen()) {
5949  tokfix();
5950  compile_error(PARSER_ARG "unknown regexp option%s - %s",
5951  toklen() > 1 ? "s" : "", tok());
5952  }
5953  return options | RE_OPTION_ENCODING(kcode);
5954 }
5955 
5956 static void
5957 dispose_string(VALUE str)
5958 {
5959  rb_str_free(str);
5960  rb_gc_force_recycle(str);
5961 }
5962 
5963 static int
5964 parser_tokadd_mbchar(struct parser_params *parser, int c)
5965 {
5966  int len = parser_precise_mbclen();
5967  if (!MBCLEN_CHARFOUND_P(len)) {
5968  compile_error(PARSER_ARG "invalid multibyte char (%s)", parser_encoding_name());
5969  return -1;
5970  }
5971  tokadd(c);
5972  lex_p += --len;
5973  if (len > 0) tokcopy(len);
5974  return c;
5975 }
5976 
5977 #define tokadd_mbchar(c) parser_tokadd_mbchar(parser, (c))
5978 
5979 static inline int
5980 simple_re_meta(int c)
5981 {
5982  switch (c) {
5983  case '$': case '*': case '+': case '.':
5984  case '?': case '^': case '|':
5985  case ')': case ']': case '}': case '>':
5986  return TRUE;
5987  default:
5988  return FALSE;
5989  }
5990 }
5991 
5992 static int
5993 parser_tokadd_string(struct parser_params *parser,
5994  int func, int term, int paren, long *nest,
5995  rb_encoding **encp)
5996 {
5997  int c;
5998  int has_nonascii = 0;
5999  rb_encoding *enc = *encp;
6000  char *errbuf = 0;
6001  static const char mixed_msg[] = "%s mixed within %s source";
6002 
6003 #define mixed_error(enc1, enc2) if (!errbuf) { \
6004  size_t len = sizeof(mixed_msg) - 4; \
6005  len += strlen(rb_enc_name(enc1)); \
6006  len += strlen(rb_enc_name(enc2)); \
6007  errbuf = ALLOCA_N(char, len); \
6008  snprintf(errbuf, len, mixed_msg, \
6009  rb_enc_name(enc1), \
6010  rb_enc_name(enc2)); \
6011  yyerror(errbuf); \
6012  }
6013 #define mixed_escape(beg, enc1, enc2) do { \
6014  const char *pos = lex_p; \
6015  lex_p = (beg); \
6016  mixed_error((enc1), (enc2)); \
6017  lex_p = pos; \
6018  } while (0)
6019 
6020  while ((c = nextc()) != -1) {
6021  if (paren && c == paren) {
6022  ++*nest;
6023  }
6024  else if (c == term) {
6025  if (!nest || !*nest) {
6026  pushback(c);
6027  break;
6028  }
6029  --*nest;
6030  }
6031  else if ((func & STR_FUNC_EXPAND) && c == '#' && lex_p < lex_pend) {
6032  int c2 = *lex_p;
6033  if (c2 == '$' || c2 == '@' || c2 == '{') {
6034  pushback(c);
6035  break;
6036  }
6037  }
6038  else if (c == '\\') {
6039  const char *beg = lex_p - 1;
6040  c = nextc();
6041  switch (c) {
6042  case '\n':
6043  if (func & STR_FUNC_QWORDS) break;
6044  if (func & STR_FUNC_EXPAND) continue;
6045  tokadd('\\');
6046  break;
6047 
6048  case '\\':
6049  if (func & STR_FUNC_ESCAPE) tokadd(c);
6050  break;
6051 
6052  case 'u':
6053  if ((func & STR_FUNC_EXPAND) == 0) {
6054  tokadd('\\');
6055  break;
6056  }
6057  parser_tokadd_utf8(parser, &enc, 1,
6058  func & STR_FUNC_SYMBOL,
6059  func & STR_FUNC_REGEXP);
6060  if (has_nonascii && enc != *encp) {
6061  mixed_escape(beg, enc, *encp);
6062  }
6063  continue;
6064 
6065  default:
6066  if (c == -1) return -1;
6067  if (!ISASCII(c)) {
6068  if ((func & STR_FUNC_EXPAND) == 0) tokadd('\\');
6069  goto non_ascii;
6070  }
6071  if (func & STR_FUNC_REGEXP) {
6072  if (c == term && !simple_re_meta(c)) {
6073  tokadd(c);
6074  continue;
6075  }
6076  pushback(c);
6077  if ((c = tokadd_escape(&enc)) < 0)
6078  return -1;
6079  if (has_nonascii && enc != *encp) {
6080  mixed_escape(beg, enc, *encp);
6081  }
6082  continue;
6083  }
6084  else if (func & STR_FUNC_EXPAND) {
6085  pushback(c);
6086  if (func & STR_FUNC_ESCAPE) tokadd('\\');
6087  c = read_escape(0, &enc);
6088  }
6089  else if ((func & STR_FUNC_QWORDS) && ISSPACE(c)) {
6090  /* ignore backslashed spaces in %w */
6091  }
6092  else if (c != term && !(paren && c == paren)) {
6093  tokadd('\\');
6094  pushback(c);
6095  continue;
6096  }
6097  }
6098  }
6099  else if (!parser_isascii()) {
6100  non_ascii:
6101  has_nonascii = 1;
6102  if (enc != *encp) {
6103  mixed_error(enc, *encp);
6104  continue;
6105  }
6106  if (tokadd_mbchar(c) == -1) return -1;
6107  continue;
6108  }
6109  else if ((func & STR_FUNC_QWORDS) && ISSPACE(c)) {
6110  pushback(c);
6111  break;
6112  }
6113  if (c & 0x80) {
6114  has_nonascii = 1;
6115  if (enc != *encp) {
6116  mixed_error(enc, *encp);
6117  continue;
6118  }
6119  }
6120  tokadd(c);
6121  }
6122  *encp = enc;
6123  return c;
6124 }
6125 
6126 #define NEW_STRTERM(func, term, paren) \
6127  rb_node_newnode(NODE_STRTERM, (func), (term) | ((paren) << (CHAR_BIT * 2)), 0)
6128 
6129 #ifdef RIPPER
6130 static void
6131 ripper_flush_string_content(struct parser_params *parser, rb_encoding *enc)
6132 {
6133  if (!NIL_P(parser->delayed)) {
6134  ptrdiff_t len = lex_p - parser->tokp;
6135  if (len > 0) {
6136  rb_enc_str_buf_cat(parser->delayed, parser->tokp, len, enc);
6137  }
6138  ripper_dispatch_delayed_token(parser, tSTRING_CONTENT);
6139  parser->tokp = lex_p;
6140  }
6141 }
6142 
6143 #define flush_string_content(enc) ripper_flush_string_content(parser, (enc))
6144 #else
6145 #define flush_string_content(enc) ((void)(enc))
6146 #endif
6147 
6148 RUBY_FUNC_EXPORTED const unsigned int ruby_global_name_punct_bits[(0x7e - 0x20 + 31) / 32];
6149 /* this can be shared with ripper, since it's independent from struct
6150  * parser_params. */
6151 #ifndef RIPPER
6152 #define BIT(c, idx) (((c) / 32 - 1 == idx) ? (1U << ((c) % 32)) : 0)
6153 #define SPECIAL_PUNCT(idx) ( \
6154  BIT('~', idx) | BIT('*', idx) | BIT('$', idx) | BIT('?', idx) | \
6155  BIT('!', idx) | BIT('@', idx) | BIT('/', idx) | BIT('\\', idx) | \
6156  BIT(';', idx) | BIT(',', idx) | BIT('.', idx) | BIT('=', idx) | \
6157  BIT(':', idx) | BIT('<', idx) | BIT('>', idx) | BIT('\"', idx) | \
6158  BIT('&', idx) | BIT('`', idx) | BIT('\'', idx) | BIT('+', idx) | \
6159  BIT('0', idx))
6160 const unsigned int ruby_global_name_punct_bits[] = {
6161  SPECIAL_PUNCT(0),
6162  SPECIAL_PUNCT(1),
6163  SPECIAL_PUNCT(2),
6164 };
6165 #undef BIT
6166 #undef SPECIAL_PUNCT
6167 #endif
6168 
6169 static inline int
6170 is_global_name_punct(const char c)
6171 {
6172  if (c <= 0x20 || 0x7e < c) return 0;
6173  return (ruby_global_name_punct_bits[(c - 0x20) / 32] >> (c % 32)) & 1;
6174 }
6175 
6176 static int
6178 {
6179  int c;
6180  const char *p = lex_p;
6181 
6182  if (p + 1 >= lex_pend) return 0;
6183  c = *p++;
6184  switch (c) {
6185  case '$':
6186  if ((c = *p) == '-') {
6187  if (++p >= lex_pend) return 0;
6188  c = *p;
6189  }
6190  else if (is_global_name_punct(c) || ISDIGIT(c)) {
6191  return tSTRING_DVAR;
6192  }
6193  break;
6194  case '@':
6195  if ((c = *p) == '@') {
6196  if (++p >= lex_pend) return 0;
6197  c = *p;
6198  }
6199  break;
6200  case '{':
6201  lex_p = p;
6202  command_start = TRUE;
6203  return tSTRING_DBEG;
6204  default:
6205  return 0;
6206  }
6207  if (!ISASCII(c) || c == '_' || ISALPHA(c))
6208  return tSTRING_DVAR;
6209  return 0;
6210 }
6211 
6212 static int
6213 parser_parse_string(struct parser_params *parser, NODE *quote)
6214 {
6215  int func = (int)quote->nd_func;
6216  int term = nd_term(quote);
6217  int paren = nd_paren(quote);
6218  int c, space = 0;
6219  rb_encoding *enc = current_enc;
6220 
6221  if (func == -1) return tSTRING_END;
6222  c = nextc();
6223  if ((func & STR_FUNC_QWORDS) && ISSPACE(c)) {
6224  do {c = nextc();} while (ISSPACE(c));
6225  space = 1;
6226  }
6227  if (c == term && !quote->nd_nest) {
6228  if (func & STR_FUNC_QWORDS) {
6229  quote->nd_func = -1;
6230  return ' ';
6231  }
6232  if (!(func & STR_FUNC_REGEXP)) return tSTRING_END;
6234  return tREGEXP_END;
6235  }
6236  if (space) {
6237  pushback(c);
6238  return ' ';
6239  }
6240  newtok();
6241  if ((func & STR_FUNC_EXPAND) && c == '#') {
6242  int t = parser_peek_variable_name(parser);
6243  if (t) return t;
6244  tokadd('#');
6245  c = nextc();
6246  }
6247  pushback(c);
6248  if (tokadd_string(func, term, paren, &quote->nd_nest,
6249  &enc) == -1) {
6250  ruby_sourceline = nd_line(quote);
6251  if (func & STR_FUNC_REGEXP) {
6252  if (parser->eofp)
6253  compile_error(PARSER_ARG "unterminated regexp meets end of file");
6254  return tREGEXP_END;
6255  }
6256  else {
6257  if (parser->eofp)
6258  compile_error(PARSER_ARG "unterminated string meets end of file");
6259  return tSTRING_END;
6260  }
6261  }
6262 
6263  tokfix();
6264  set_yylval_str(STR_NEW3(tok(), toklen(), enc, func));
6265  flush_string_content(enc);
6266 
6267  return tSTRING_CONTENT;
6268 }
6269 
6270 static int
6272 {
6273  int c = nextc(), term, func = 0;
6274  long len;
6275 
6276  if (c == '-') {
6277  c = nextc();
6278  func = STR_FUNC_INDENT;
6279  }
6280  switch (c) {
6281  case '\'':
6282  func |= str_squote; goto quoted;
6283  case '"':
6284  func |= str_dquote; goto quoted;
6285  case '`':
6286  func |= str_xquote;
6287  quoted:
6288  newtok();
6289  tokadd(func);
6290  term = c;
6291  while ((c = nextc()) != -1 && c != term) {
6292  if (tokadd_mbchar(c) == -1) return 0;
6293  }
6294  if (c == -1) {
6295  compile_error(PARSER_ARG "unterminated here document identifier");
6296  return 0;
6297  }
6298  break;
6299 
6300  default:
6301  if (!parser_is_identchar()) {
6302  pushback(c);
6303  if (func & STR_FUNC_INDENT) {
6304  pushback('-');
6305  }
6306  return 0;
6307  }
6308  newtok();
6309  term = '"';
6310  tokadd(func |= str_dquote);
6311  do {
6312  if (tokadd_mbchar(c) == -1) return 0;
6313  } while ((c = nextc()) != -1 && parser_is_identchar());
6314  pushback(c);
6315  break;
6316  }
6317 
6318  tokfix();
6319 #ifdef RIPPER
6320  ripper_dispatch_scan_event(parser, tHEREDOC_BEG);
6321 #endif
6322  len = lex_p - lex_pbeg;
6323  lex_goto_eol(parser);
6325  STR_NEW(tok(), toklen()), /* nd_lit */
6326  len, /* nd_nth */
6327  lex_lastline); /* nd_orig */
6329  ripper_flush(parser);
6330  return term == '`' ? tXSTRING_BEG : tSTRING_BEG;
6331 }
6332 
6333 static void
6334 parser_heredoc_restore(struct parser_params *parser, NODE *here)
6335 {
6336  VALUE line;
6337 
6338  line = here->nd_orig;
6339  lex_lastline = line;
6340  lex_pbeg = RSTRING_PTR(line);
6341  lex_pend = lex_pbeg + RSTRING_LEN(line);
6342  lex_p = lex_pbeg + here->nd_nth;
6344  ruby_sourceline = nd_line(here);
6345  dispose_string(here->nd_lit);
6346  rb_gc_force_recycle((VALUE)here);
6347  ripper_flush(parser);
6348 }
6349 
6350 static int
6351 parser_whole_match_p(struct parser_params *parser,
6352  const char *eos, long len, int indent)
6353 {
6354  const char *p = lex_pbeg;
6355  long n;
6356 
6357  if (indent) {
6358  while (*p && ISSPACE(*p)) p++;
6359  }
6360  n = lex_pend - (p + len);
6361  if (n < 0 || (n > 0 && p[len] != '\n' && p[len] != '\r')) return FALSE;
6362  return strncmp(eos, p, len) == 0;
6363 }
6364 
6365 #ifdef RIPPER
6366 static void
6367 ripper_dispatch_heredoc_end(struct parser_params *parser)
6368 {
6369  if (!NIL_P(parser->delayed))
6370  ripper_dispatch_delayed_token(parser, tSTRING_CONTENT);
6371  lex_goto_eol(parser);
6372  ripper_dispatch_ignored_scan_event(parser, tHEREDOC_END);
6373 }
6374 
6375 #define dispatch_heredoc_end() ripper_dispatch_heredoc_end(parser)
6376 #else
6377 #define dispatch_heredoc_end() ((void)0)
6378 #endif
6379 
6380 static int
6381 parser_here_document(struct parser_params *parser, NODE *here)
6382 {
6383  int c, func, indent = 0;
6384  const char *eos, *p, *pend;
6385  long len;
6386  VALUE str = 0;
6387  rb_encoding *enc = current_enc;
6388 
6389  eos = RSTRING_PTR(here->nd_lit);
6390  len = RSTRING_LEN(here->nd_lit) - 1;
6391  indent = (func = *eos++) & STR_FUNC_INDENT;
6392 
6393  if ((c = nextc()) == -1) {
6394  error:
6395  compile_error(PARSER_ARG "can't find string \"%s\" anywhere before EOF", eos);
6396 #ifdef RIPPER
6397  if (NIL_P(parser->delayed)) {
6398  ripper_dispatch_scan_event(parser, tSTRING_CONTENT);
6399  }
6400  else {
6401  if (str ||
6402  ((len = lex_p - parser->tokp) > 0 &&
6403  (str = STR_NEW3(parser->tokp, len, enc, func), 1))) {
6404  rb_str_append(parser->delayed, str);
6405  }
6406  ripper_dispatch_delayed_token(parser, tSTRING_CONTENT);
6407  }
6408  lex_goto_eol(parser);
6409 #endif
6410  restore:
6412  lex_strterm = 0;
6413  return 0;
6414  }
6415  if (was_bol() && whole_match_p(eos, len, indent)) {
6418  return tSTRING_END;
6419  }
6420 
6421  if (!(func & STR_FUNC_EXPAND)) {
6422  do {
6424  pend = lex_pend;
6425  if (pend > p) {
6426  switch (pend[-1]) {
6427  case '\n':
6428  if (--pend == p || pend[-1] != '\r') {
6429  pend++;
6430  break;
6431  }
6432  case '\r':
6433  --pend;
6434  }
6435  }
6436  if (str)
6437  rb_str_cat(str, p, pend - p);
6438  else
6439  str = STR_NEW(p, pend - p);
6440  if (pend < lex_pend) rb_str_cat(str, "\n", 1);
6441  lex_goto_eol(parser);
6442  if (nextc() == -1) {
6443  if (str) dispose_string(str);
6444  goto error;
6445  }
6446  } while (!whole_match_p(eos, len, indent));
6447  }
6448  else {
6449  /* int mb = ENC_CODERANGE_7BIT, *mbp = &mb;*/
6450  newtok();
6451  if (c == '#') {
6452  int t = parser_peek_variable_name(parser);
6453  if (t) return t;
6454  tokadd('#');
6455  c = nextc();
6456  }
6457  do {
6458  pushback(c);
6459  if ((c = tokadd_string(func, '\n', 0, NULL, &enc)) == -1) {
6460  if (parser->eofp) goto error;
6461  goto restore;
6462  }
6463  if (c != '\n') {
6464  set_yylval_str(STR_NEW3(tok(), toklen(), enc, func));
6465  flush_string_content(enc);
6466  return tSTRING_CONTENT;
6467  }
6468  tokadd(nextc());
6469  /* if (mbp && mb == ENC_CODERANGE_UNKNOWN) mbp = 0;*/
6470  if ((c = nextc()) == -1) goto error;
6471  } while (!whole_match_p(eos, len, indent));
6472  str = STR_NEW3(tok(), toklen(), enc, func);
6473  }
6476  lex_strterm = NEW_STRTERM(-1, 0, 0);
6477  set_yylval_str(str);
6478  return tSTRING_CONTENT;
6479 }
6480 
6481 #include "lex.c"
6482 
6483 static void
6484 arg_ambiguous_gen(struct parser_params *parser)
6485 {
6486 #ifndef RIPPER
6487  rb_warning0("ambiguous first argument; put parentheses or even spaces");
6488 #else
6490 #endif
6491 }
6492 #define arg_ambiguous() (arg_ambiguous_gen(parser), 1)
6493 
6494 static ID
6495 formal_argument_gen(struct parser_params *parser, ID lhs)
6496 {
6497 #ifndef RIPPER
6498  if (!is_local_id(lhs))
6499  yyerror("formal argument must be local variable");
6500 #endif
6501  shadowing_lvar(lhs);
6502  return lhs;
6503 }
6504 
6505 static int
6506 lvar_defined_gen(struct parser_params *parser, ID id)
6507 {
6508  return (dyna_in_block() && dvar_defined_get(id)) || local_id(id);
6509 }
6510 
6511 /* emacsen -*- hack */
6512 static long
6513 parser_encode_length(struct parser_params *parser, const char *name, long len)
6514 {
6515  long nlen;
6516 
6517  if (len > 5 && name[nlen = len - 5] == '-') {
6518  if (rb_memcicmp(name + nlen + 1, "unix", 4) == 0)
6519  return nlen;
6520  }
6521  if (len > 4 && name[nlen = len - 4] == '-') {
6522  if (rb_memcicmp(name + nlen + 1, "dos", 3) == 0)
6523  return nlen;
6524  if (rb_memcicmp(name + nlen + 1, "mac", 3) == 0 &&
6525  !(len == 8 && rb_memcicmp(name, "utf8-mac", len) == 0))
6526  /* exclude UTF8-MAC because the encoding named "UTF8" doesn't exist in Ruby */
6527  return nlen;
6528  }
6529  return len;
6530 }
6531 
6532 static void
6533 parser_set_encode(struct parser_params *parser, const char *name)
6534 {
6535  int idx = rb_enc_find_index(name);
6536  rb_encoding *enc;
6537  VALUE excargs[3];
6538 
6539  if (idx < 0) {
6540  excargs[1] = rb_sprintf("unknown encoding name: %s", name);
6541  error:
6542  excargs[0] = rb_eArgError;
6543  excargs[2] = rb_make_backtrace();
6544  rb_ary_unshift(excargs[2], rb_sprintf("%s:%d", ruby_sourcefile, ruby_sourceline));
6545  rb_exc_raise(rb_make_exception(3, excargs));
6546  }
6547  enc = rb_enc_from_index(idx);
6548  if (!rb_enc_asciicompat(enc)) {
6549  excargs[1] = rb_sprintf("%s is not ASCII compatible", rb_enc_name(enc));
6550  goto error;
6551  }
6552  parser->enc = enc;
6553 #ifndef RIPPER
6554  if (ruby_debug_lines) {
6555  long i, n = RARRAY_LEN(ruby_debug_lines);
6556  const VALUE *p = RARRAY_PTR(ruby_debug_lines);
6557  for (i = 0; i < n; ++i) {
6558  rb_enc_associate_index(*p, idx);
6559  }
6560  }
6561 #endif
6562 }
6563 
6564 static int
6565 comment_at_top(struct parser_params *parser)
6566 {
6567  const char *p = lex_pbeg, *pend = lex_p - 1;
6568  if (parser->line_count != (parser->has_shebang ? 2 : 1)) return 0;
6569  while (p < pend) {
6570  if (!ISSPACE(*p)) return 0;
6571  p++;
6572  }
6573  return 1;
6574 }
6575 
6576 #ifndef RIPPER
6577 typedef long (*rb_magic_comment_length_t)(struct parser_params *parser, const char *name, long len);
6578 typedef void (*rb_magic_comment_setter_t)(struct parser_params *parser, const char *name, const char *val);
6579 
6580 static void
6581 magic_comment_encoding(struct parser_params *parser, const char *name, const char *val)
6582 {
6583  if (!comment_at_top(parser)) {
6584  return;
6585  }
6586  parser_set_encode(parser, val);
6587 }
6588 
6589 static void
6590 parser_set_token_info(struct parser_params *parser, const char *name, const char *val)
6591 {
6592  int *p = &parser->parser_token_info_enabled;
6593 
6594  switch (*val) {
6595  case 't': case 'T':
6596  if (strcasecmp(val, "true") == 0) {
6597  *p = TRUE;
6598  return;
6599  }
6600  break;
6601  case 'f': case 'F':
6602  if (strcasecmp(val, "false") == 0) {
6603  *p = FALSE;
6604  return;
6605  }
6606  break;
6607  }
6608  rb_compile_warning(ruby_sourcefile, ruby_sourceline, "invalid value for %s: %s", name, val);
6609 }
6610 
6611 struct magic_comment {
6612  const char *name;
6615 };
6616 
6617 static const struct magic_comment magic_comments[] = {
6620  {"warn_indent", parser_set_token_info},
6621 };
6622 #endif
6623 
6624 static const char *
6625 magic_comment_marker(const char *str, long len)
6626 {
6627  long i = 2;
6628 
6629  while (i < len) {
6630  switch (str[i]) {
6631  case '-':
6632  if (str[i-1] == '*' && str[i-2] == '-') {
6633  return str + i + 1;
6634  }
6635  i += 2;
6636  break;
6637  case '*':
6638  if (i + 1 >= len) return 0;
6639  if (str[i+1] != '-') {
6640  i += 4;
6641  }
6642  else if (str[i-1] != '-') {
6643  i += 2;
6644  }
6645  else {
6646  return str + i + 2;
6647  }
6648  break;
6649  default:
6650  i += 3;
6651  break;
6652  }
6653  }
6654  return 0;
6655 }
6656 
6657 static int
6658 parser_magic_comment(struct parser_params *parser, const char *str, long len)
6659 {
6660  VALUE name = 0, val = 0;
6661  const char *beg, *end, *vbeg, *vend;
6662 #define str_copy(_s, _p, _n) ((_s) \
6663  ? (void)(rb_str_resize((_s), (_n)), \
6664  MEMCPY(RSTRING_PTR(_s), (_p), char, (_n)), (_s)) \
6665  : (void)((_s) = STR_NEW((_p), (_n))))
6666 
6667  if (len <= 7) return FALSE;
6668  if (!(beg = magic_comment_marker(str, len))) return FALSE;
6669  if (!(end = magic_comment_marker(beg, str + len - beg))) return FALSE;
6670  str = beg;
6671  len = end - beg - 3;
6672 
6673  /* %r"([^\\s\'\":;]+)\\s*:\\s*(\"(?:\\\\.|[^\"])*\"|[^\"\\s;]+)[\\s;]*" */
6674  while (len > 0) {
6675 #ifndef RIPPER
6676  const struct magic_comment *p = magic_comments;
6677 #endif
6678  char *s;
6679  int i;
6680  long n = 0;
6681 
6682  for (; len > 0 && *str; str++, --len) {
6683  switch (*str) {
6684  case '\'': case '"': case ':': case ';':
6685  continue;
6686  }
6687  if (!ISSPACE(*str)) break;
6688  }
6689  for (beg = str; len > 0; str++, --len) {
6690  switch (*str) {
6691  case '\'': case '"': case ':': case ';':
6692  break;
6693  default:
6694  if (ISSPACE(*str)) break;
6695  continue;
6696  }
6697  break;
6698  }
6699  for (end = str; len > 0 && ISSPACE(*str); str++, --len);
6700  if (!len) break;
6701  if (*str != ':') continue;
6702 
6703  do str++; while (--len > 0 && ISSPACE(*str));
6704  if (!len) break;
6705  if (*str == '"') {
6706  for (vbeg = ++str; --len > 0 && *str != '"'; str++) {
6707  if (*str == '\\') {
6708  --len;
6709  ++str;
6710  }
6711  }
6712  vend = str;
6713  if (len) {
6714  --len;
6715  ++str;
6716  }
6717  }
6718  else {
6719  for (vbeg = str; len > 0 && *str != '"' && *str != ';' && !ISSPACE(*str); --len, str++);
6720  vend = str;
6721  }
6722  while (len > 0 && (*str == ';' || ISSPACE(*str))) --len, str++;
6723 
6724  n = end - beg;
6725  str_copy(name, beg, n);
6726  s = RSTRING_PTR(name);
6727  for (i = 0; i < n; ++i) {
6728  if (s[i] == '-') s[i] = '_';
6729  }
6730 #ifndef RIPPER
6731  do {
6732  if (STRNCASECMP(p->name, s, n) == 0) {
6733  n = vend - vbeg;
6734  if (p->length) {
6735  n = (*p->length)(parser, vbeg, n);
6736  }
6737  str_copy(val, vbeg, n);
6738  (*p->func)(parser, s, RSTRING_PTR(val));
6739  break;
6740  }
6741  } while (++p < magic_comments + numberof(magic_comments));
6742 #else
6743  str_copy(val, vbeg, vend - vbeg);
6744  dispatch2(magic_comment, name, val);
6745 #endif
6746  }
6747 
6748  return TRUE;
6749 }
6750 
6751 static void
6752 set_file_encoding(struct parser_params *parser, const char *str, const char *send)
6753 {
6754  int sep = 0;
6755  const char *beg = str;
6756  VALUE s;
6757 
6758  for (;;) {
6759  if (send - str <= 6) return;
6760  switch (str[6]) {
6761  case 'C': case 'c': str += 6; continue;
6762  case 'O': case 'o': str += 5; continue;
6763  case 'D': case 'd': str += 4; continue;
6764  case 'I': case 'i': str += 3; continue;
6765  case 'N': case 'n': str += 2; continue;
6766  case 'G': case 'g': str += 1; continue;
6767  case '=': case ':':
6768  sep = 1;
6769  str += 6;
6770  break;
6771  default:
6772  str += 6;
6773  if (ISSPACE(*str)) break;
6774  continue;
6775  }
6776  if (STRNCASECMP(str-6, "coding", 6) == 0) break;
6777  }
6778  for (;;) {
6779  do {
6780  if (++str >= send) return;
6781  } while (ISSPACE(*str));
6782  if (sep) break;
6783  if (*str != '=' && *str != ':') return;
6784  sep = 1;
6785  str++;
6786  }
6787  beg = str;
6788  while ((*str == '-' || *str == '_' || ISALNUM(*str)) && ++str < send);
6789  s = rb_str_new(beg, parser_encode_length(parser, beg, str - beg));
6790  parser_set_encode(parser, RSTRING_PTR(s));
6791  rb_str_resize(s, 0);
6792 }
6793 
6794 static void
6795 parser_prepare(struct parser_params *parser)
6796 {
6797  int c = nextc();
6798  switch (c) {
6799  case '#':
6800  if (peek('!')) parser->has_shebang = 1;
6801  break;
6802  case 0xef: /* UTF-8 BOM marker */
6803  if (lex_pend - lex_p >= 2 &&
6804  (unsigned char)lex_p[0] == 0xbb &&
6805  (unsigned char)lex_p[1] == 0xbf) {
6806  parser->enc = rb_utf8_encoding();
6807  lex_p += 2;
6808  lex_pbeg = lex_p;
6809  return;
6810  }
6811  break;
6812  case EOF:
6813  return;
6814  }
6815  pushback(c);
6816  parser->enc = rb_enc_get(lex_lastline);
6817 }
6818 
6819 #define IS_ARG() IS_lex_state(EXPR_ARG_ANY)
6820 #define IS_END() IS_lex_state(EXPR_END_ANY)
6821 #define IS_BEG() IS_lex_state(EXPR_BEG_ANY)
6822 #define IS_SPCARG(c) (IS_ARG() && space_seen && !ISSPACE(c))
6823 #define IS_LABEL_POSSIBLE() ((IS_lex_state(EXPR_BEG | EXPR_ENDFN) && !cmd_state) || IS_ARG())
6824 #define IS_LABEL_SUFFIX(n) (peek_n(':',(n)) && !peek_n(':', (n)+1))
6825 #define IS_AFTER_OPERATOR() IS_lex_state(EXPR_FNAME | EXPR_DOT)
6826 
6827 #ifndef RIPPER
6828 #define ambiguous_operator(op, syn) ( \
6829  rb_warning0("`"op"' after local variable is interpreted as binary operator"), \
6830  rb_warning0("even though it seems like "syn""))
6831 #else
6832 #define ambiguous_operator(op, syn) dispatch2(operator_ambiguous, ripper_intern(op), rb_str_new_cstr(syn))
6833 #endif
6834 #define warn_balanced(op, syn) ((void) \
6835  (!IS_lex_state_for(last_state, EXPR_CLASS|EXPR_DOT|EXPR_FNAME|EXPR_ENDFN|EXPR_ENDARG) && \
6836  space_seen && !ISSPACE(c) && \
6837  (ambiguous_operator(op, syn), 0)))
6838 
6839 static int
6840 parser_yylex(struct parser_params *parser)
6841 {
6842  register int c;
6843  int space_seen = 0;
6844  int cmd_state;
6845  enum lex_state_e last_state;
6846  rb_encoding *enc;
6847  int mb;
6848 #ifdef RIPPER
6849  int fallthru = FALSE;
6850 #endif
6851 
6852  if (lex_strterm) {
6853  int token;
6854  if (nd_type(lex_strterm) == NODE_HEREDOC) {
6855  token = here_document(lex_strterm);
6856  if (token == tSTRING_END) {
6857  lex_strterm = 0;
6858  lex_state = EXPR_END;
6859  }
6860  }
6861  else {
6862  token = parse_string(lex_strterm);
6863  if (token == tSTRING_END || token == tREGEXP_END) {
6865  lex_strterm = 0;
6866  lex_state = EXPR_END;
6867  }
6868  }
6869  return token;
6870  }
6871  cmd_state = command_start;
6872  command_start = FALSE;
6873  retry:
6874  last_state = lex_state;
6875  switch (c = nextc()) {
6876  case '\0': /* NUL */
6877  case '\004': /* ^D */
6878  case '\032': /* ^Z */
6879  case -1: /* end of script. */
6880  return 0;
6881 
6882  /* white spaces */
6883  case ' ': case '\t': case '\f': case '\r':
6884  case '\13': /* '\v' */
6885  space_seen = 1;
6886 #ifdef RIPPER
6887  while ((c = nextc())) {
6888  switch (c) {
6889  case ' ': case '\t': case '\f': case '\r':
6890  case '\13': /* '\v' */
6891  break;
6892  default:
6893  goto outofloop;
6894  }
6895  }
6896  outofloop:
6897  pushback(c);
6898  ripper_dispatch_scan_event(parser, tSP);
6899 #endif
6900  goto retry;
6901 
6902  case '#': /* it's a comment */
6903  /* no magic_comment in shebang line */
6904  if (!parser_magic_comment(parser, lex_p, lex_pend - lex_p)) {
6905  if (comment_at_top(parser)) {
6906  set_file_encoding(parser, lex_p, lex_pend);
6907  }
6908  }
6909  lex_p = lex_pend;
6910 #ifdef RIPPER
6911  ripper_dispatch_scan_event(parser, tCOMMENT);
6912  fallthru = TRUE;
6913 #endif
6914  /* fall through */
6915  case '\n':
6916  if (IS_lex_state(EXPR_BEG | EXPR_VALUE | EXPR_CLASS | EXPR_FNAME | EXPR_DOT)) {
6917 #ifdef RIPPER
6918  if (!fallthru) {
6919  ripper_dispatch_scan_event(parser, tIGNORED_NL);
6920  }
6921  fallthru = FALSE;
6922 #endif
6923  goto retry;
6924  }
6925  while ((c = nextc())) {
6926  switch (c) {
6927  case ' ': case '\t': case '\f': case '\r':
6928  case '\13': /* '\v' */
6929  space_seen = 1;
6930  break;
6931  case '.': {
6932  if ((c = nextc()) != '.') {
6933  pushback(c);
6934  pushback('.');
6935  goto retry;
6936  }
6937  }
6938  default:
6939  --ruby_sourceline;
6941  case -1: /* EOF no decrement*/
6942  lex_goto_eol(parser);
6943 #ifdef RIPPER
6944  if (c != -1) {
6945  parser->tokp = lex_p;
6946  }
6947 #endif
6948  goto normal_newline;
6949  }
6950  }
6951  normal_newline:
6952  command_start = TRUE;
6953  lex_state = EXPR_BEG;
6954  return '\n';
6955 
6956  case '*':
6957  if ((c = nextc()) == '*') {
6958  if ((c = nextc()) == '=') {
6960  lex_state = EXPR_BEG;
6961  return tOP_ASGN;
6962  }
6963  pushback(c);
6964  if (IS_SPCARG(c)) {
6965  rb_warning0("`**' interpreted as argument prefix");
6966  c = tDSTAR;
6967  }
6968  else if (IS_BEG()) {
6969  c = tDSTAR;
6970  }
6971  else {
6972  warn_balanced("**", "argument prefix");
6973  c = tPOW;
6974  }
6975  }
6976  else {
6977  if (c == '=') {
6978  set_yylval_id('*');
6979  lex_state = EXPR_BEG;
6980  return tOP_ASGN;
6981  }
6982  pushback(c);
6983  if (IS_SPCARG(c)) {
6984  rb_warning0("`*' interpreted as argument prefix");
6985  c = tSTAR;
6986  }
6987  else if (IS_BEG()) {
6988  c = tSTAR;
6989  }
6990  else {
6991  warn_balanced("*", "argument prefix");
6992  c = '*';
6993  }
6994  }
6995  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
6996  return c;
6997 
6998  case '!':
6999  c = nextc();
7000  if (IS_AFTER_OPERATOR()) {
7001  lex_state = EXPR_ARG;
7002  if (c == '@') {
7003  return '!';
7004  }
7005  }
7006  else {
7007  lex_state = EXPR_BEG;
7008  }
7009  if (c == '=') {
7010  return tNEQ;
7011  }
7012  if (c == '~') {
7013  return tNMATCH;
7014  }
7015  pushback(c);
7016  return '!';
7017 
7018  case '=':
7019  if (was_bol()) {
7020  /* skip embedded rd document */
7021  if (strncmp(lex_p, "begin", 5) == 0 && ISSPACE(lex_p[5])) {
7022 #ifdef RIPPER
7023  int first_p = TRUE;
7024 
7025  lex_goto_eol(parser);
7026  ripper_dispatch_scan_event(parser, tEMBDOC_BEG);
7027 #endif
7028  for (;;) {
7029  lex_goto_eol(parser);
7030 #ifdef RIPPER
7031  if (!first_p) {
7032  ripper_dispatch_scan_event(parser, tEMBDOC);
7033  }
7034  first_p = FALSE;
7035 #endif
7036  c = nextc();
7037  if (c == -1) {
7038  compile_error(PARSER_ARG "embedded document meets end of file");
7039  return 0;
7040  }
7041  if (c != '=') continue;
7042  if (strncmp(lex_p, "end", 3) == 0 &&
7043  (lex_p + 3 == lex_pend || ISSPACE(lex_p[3]))) {
7044  break;
7045  }
7046  }
7047  lex_goto_eol(parser);
7048 #ifdef RIPPER
7049  ripper_dispatch_scan_event(parser, tEMBDOC_END);
7050 #endif
7051  goto retry;
7052  }
7053  }
7054 
7055  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7056  if ((c = nextc()) == '=') {
7057  if ((c = nextc()) == '=') {
7058  return tEQQ;
7059  }
7060  pushback(c);
7061  return tEQ;
7062  }
7063  if (c == '~') {
7064  return tMATCH;
7065  }
7066  else if (c == '>') {
7067  return tASSOC;
7068  }
7069  pushback(c);
7070  return '=';
7071 
7072  case '<':
7073  last_state = lex_state;
7074  c = nextc();
7075  if (c == '<' &&
7076  !IS_lex_state(EXPR_DOT | EXPR_CLASS) &&
7077  !IS_END() &&
7078  (!IS_ARG() || space_seen)) {
7079  int token = heredoc_identifier();
7080  if (token) return token;
7081  }
7082  if (IS_AFTER_OPERATOR()) {
7083  lex_state = EXPR_ARG;
7084  }
7085  else {
7086  if (IS_lex_state(EXPR_CLASS))
7087  command_start = TRUE;
7088  lex_state = EXPR_BEG;
7089  }
7090  if (c == '=') {
7091  if ((c = nextc()) == '>') {
7092  return tCMP;
7093  }
7094  pushback(c);
7095  return tLEQ;
7096  }
7097  if (c == '<') {
7098  if ((c = nextc()) == '=') {
7100  lex_state = EXPR_BEG;
7101  return tOP_ASGN;
7102  }
7103  pushback(c);
7104  warn_balanced("<<", "here document");
7105  return tLSHFT;
7106  }
7107  pushback(c);
7108  return '<';
7109 
7110  case '>':
7111  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7112  if ((c = nextc()) == '=') {
7113  return tGEQ;
7114  }
7115  if (c == '>') {
7116  if ((c = nextc()) == '=') {
7118  lex_state = EXPR_BEG;
7119  return tOP_ASGN;
7120  }
7121  pushback(c);
7122  return tRSHFT;
7123  }
7124  pushback(c);
7125  return '>';
7126 
7127  case '"':
7128  lex_strterm = NEW_STRTERM(str_dquote, '"', 0);
7129  return tSTRING_BEG;
7130 
7131  case '`':
7132  if (IS_lex_state(EXPR_FNAME)) {
7133  lex_state = EXPR_ENDFN;
7134  return c;
7135  }
7136  if (IS_lex_state(EXPR_DOT)) {
7137  if (cmd_state)
7138  lex_state = EXPR_CMDARG;
7139  else
7140  lex_state = EXPR_ARG;
7141  return c;
7142  }
7143  lex_strterm = NEW_STRTERM(str_xquote, '`', 0);
7144  return tXSTRING_BEG;
7145 
7146  case '\'':
7147  lex_strterm = NEW_STRTERM(str_squote, '\'', 0);
7148  return tSTRING_BEG;
7149 
7150  case '?':
7151  if (IS_END()) {
7152  lex_state = EXPR_VALUE;
7153  return '?';
7154  }
7155  c = nextc();
7156  if (c == -1) {
7157  compile_error(PARSER_ARG "incomplete character syntax");
7158  return 0;
7159  }
7160  if (rb_enc_isspace(c, current_enc)) {
7161  if (!IS_ARG()) {
7162  int c2 = 0;
7163  switch (c) {
7164  case ' ':
7165  c2 = 's';
7166  break;
7167  case '\n':
7168  c2 = 'n';
7169  break;
7170  case '\t':
7171  c2 = 't';
7172  break;
7173  case '\v':
7174  c2 = 'v';
7175  break;
7176  case '\r':
7177  c2 = 'r';
7178  break;
7179  case '\f':
7180  c2 = 'f';
7181  break;
7182  }
7183  if (c2) {
7184  rb_warnI("invalid character syntax; use ?\\%c", c2);
7185  }
7186  }
7187  ternary:
7188  pushback(c);
7189  lex_state = EXPR_VALUE;
7190  return '?';
7191  }
7192  newtok();
7193  enc = current_enc;
7194  if (!parser_isascii()) {
7195  if (tokadd_mbchar(c) == -1) return 0;
7196  }
7197  else if ((rb_enc_isalnum(c, current_enc) || c == '_') &&
7199  goto ternary;
7200  }
7201  else if (c == '\\') {
7202  if (peek('u')) {
7203  nextc();
7204  c = parser_tokadd_utf8(parser, &enc, 0, 0, 0);
7205  if (0x80 <= c) {
7206  tokaddmbc(c, enc);
7207  }
7208  else {
7209  tokadd(c);
7210  }
7211  }
7212  else if (!lex_eol_p() && !(c = *lex_p, ISASCII(c))) {
7213  nextc();
7214  if (tokadd_mbchar(c) == -1) return 0;
7215  }
7216  else {
7217  c = read_escape(0, &enc);
7218  tokadd(c);
7219  }
7220  }
7221  else {
7222  tokadd(c);
7223  }
7224  tokfix();
7225  set_yylval_str(STR_NEW3(tok(), toklen(), enc, 0));
7226  lex_state = EXPR_END;
7227  return tCHAR;
7228 
7229  case '&':
7230  if ((c = nextc()) == '&') {
7231  lex_state = EXPR_BEG;
7232  if ((c = nextc()) == '=') {
7234  lex_state = EXPR_BEG;
7235  return tOP_ASGN;
7236  }
7237  pushback(c);
7238  return tANDOP;
7239  }
7240  else if (c == '=') {
7241  set_yylval_id('&');
7242  lex_state = EXPR_BEG;
7243  return tOP_ASGN;
7244  }
7245  pushback(c);
7246  if (IS_SPCARG(c)) {
7247  rb_warning0("`&' interpreted as argument prefix");
7248  c = tAMPER;
7249  }
7250  else if (IS_BEG()) {
7251  c = tAMPER;
7252  }
7253  else {
7254  warn_balanced("&", "argument prefix");
7255  c = '&';
7256  }
7257  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7258  return c;
7259 
7260  case '|':
7261  if ((c = nextc()) == '|') {
7262  lex_state = EXPR_BEG;
7263  if ((c = nextc()) == '=') {
7265  lex_state = EXPR_BEG;
7266  return tOP_ASGN;
7267  }
7268  pushback(c);
7269  return tOROP;
7270  }
7271  if (c == '=') {
7272  set_yylval_id('|');
7273  lex_state = EXPR_BEG;
7274  return tOP_ASGN;
7275  }
7276  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7277  pushback(c);
7278  return '|';
7279 
7280  case '+':
7281  c = nextc();
7282  if (IS_AFTER_OPERATOR()) {
7283  lex_state = EXPR_ARG;
7284  if (c == '@') {
7285  return tUPLUS;
7286  }
7287  pushback(c);
7288  return '+';
7289  }
7290  if (c == '=') {
7291  set_yylval_id('+');
7292  lex_state = EXPR_BEG;
7293  return tOP_ASGN;
7294  }
7295  if (IS_BEG() || (IS_SPCARG(c) && arg_ambiguous())) {
7296  lex_state = EXPR_BEG;
7297  pushback(c);
7298  if (c != -1 && ISDIGIT(c)) {
7299  c = '+';
7300  goto start_num;
7301  }
7302  return tUPLUS;
7303  }
7304  lex_state = EXPR_BEG;
7305  pushback(c);
7306  warn_balanced("+", "unary operator");
7307  return '+';
7308 
7309  case '-':
7310  c = nextc();
7311  if (IS_AFTER_OPERATOR()) {
7312  lex_state = EXPR_ARG;
7313  if (c == '@') {
7314  return tUMINUS;
7315  }
7316  pushback(c);
7317  return '-';
7318  }
7319  if (c == '=') {
7320  set_yylval_id('-');
7321  lex_state = EXPR_BEG;
7322  return tOP_ASGN;
7323  }
7324  if (c == '>') {
7325  lex_state = EXPR_ENDFN;
7326  return tLAMBDA;
7327  }
7328  if (IS_BEG() || (IS_SPCARG(c) && arg_ambiguous())) {
7329  lex_state = EXPR_BEG;
7330  pushback(c);
7331  if (c != -1 && ISDIGIT(c)) {
7332  return tUMINUS_NUM;
7333  }
7334  return tUMINUS;
7335  }
7336  lex_state = EXPR_BEG;
7337  pushback(c);
7338  warn_balanced("-", "unary operator");
7339  return '-';
7340 
7341  case '.':
7342  lex_state = EXPR_BEG;
7343  if ((c = nextc()) == '.') {
7344  if ((c = nextc()) == '.') {
7345  return tDOT3;
7346  }
7347  pushback(c);
7348  return tDOT2;
7349  }
7350  pushback(c);
7351  if (c != -1 && ISDIGIT(c)) {
7352  yyerror("no .<digit> floating literal anymore; put 0 before dot");
7353  }
7354  lex_state = EXPR_DOT;
7355  return '.';
7356 
7357  start_num:
7358  case '0': case '1': case '2': case '3': case '4':
7359  case '5': case '6': case '7': case '8': case '9':
7360  {
7361  int is_float, seen_point, seen_e, nondigit;
7362 
7363  is_float = seen_point = seen_e = nondigit = 0;
7364  lex_state = EXPR_END;
7365  newtok();
7366  if (c == '-' || c == '+') {
7367  tokadd(c);
7368  c = nextc();
7369  }
7370  if (c == '0') {
7371 #define no_digits() do {yyerror("numeric literal without digits"); return 0;} while (0)
7372  int start = toklen();
7373  c = nextc();
7374  if (c == 'x' || c == 'X') {
7375  /* hexadecimal */
7376  c = nextc();
7377  if (c != -1 && ISXDIGIT(c)) {
7378  do {
7379  if (c == '_') {
7380  if (nondigit) break;
7381  nondigit = c;
7382  continue;
7383  }
7384  if (!ISXDIGIT(c)) break;
7385  nondigit = 0;
7386  tokadd(c);
7387  } while ((c = nextc()) != -1);
7388  }
7389  pushback(c);
7390  tokfix();
7391  if (toklen() == start) {
7392  no_digits();
7393  }
7394  else if (nondigit) goto trailing_uc;
7396  return tINTEGER;
7397  }
7398  if (c == 'b' || c == 'B') {
7399  /* binary */
7400  c = nextc();
7401  if (c == '0' || c == '1') {
7402  do {
7403  if (c == '_') {
7404  if (nondigit) break;
7405  nondigit = c;
7406  continue;
7407  }
7408  if (c != '0' && c != '1') break;
7409  nondigit = 0;
7410  tokadd(c);
7411  } while ((c = nextc()) != -1);
7412  }
7413  pushback(c);
7414  tokfix();
7415  if (toklen() == start) {
7416  no_digits();
7417  }
7418  else if (nondigit) goto trailing_uc;
7420  return tINTEGER;
7421  }
7422  if (c == 'd' || c == 'D') {
7423  /* decimal */
7424  c = nextc();
7425  if (c != -1 && ISDIGIT(c)) {
7426  do {
7427  if (c == '_') {
7428  if (nondigit) break;
7429  nondigit = c;
7430  continue;
7431  }
7432  if (!ISDIGIT(c)) break;
7433  nondigit = 0;
7434  tokadd(c);
7435  } while ((c = nextc()) != -1);
7436  }
7437  pushback(c);
7438  tokfix();
7439  if (toklen() == start) {
7440  no_digits();
7441  }
7442  else if (nondigit) goto trailing_uc;
7444  return tINTEGER;
7445  }
7446  if (c == '_') {
7447  /* 0_0 */
7448  goto octal_number;
7449  }
7450  if (c == 'o' || c == 'O') {
7451  /* prefixed octal */
7452  c = nextc();
7453  if (c == -1 || c == '_' || !ISDIGIT(c)) {
7454  no_digits();
7455  }
7456  }
7457  if (c >= '0' && c <= '7') {
7458  /* octal */
7459  octal_number:
7460  do {
7461  if (c == '_') {
7462  if (nondigit) break;
7463  nondigit = c;
7464  continue;
7465  }
7466  if (c < '0' || c > '9') break;
7467  if (c > '7') goto invalid_octal;
7468  nondigit = 0;
7469  tokadd(c);
7470  } while ((c = nextc()) != -1);
7471  if (toklen() > start) {
7472  pushback(c);
7473  tokfix();
7474  if (nondigit) goto trailing_uc;
7476  return tINTEGER;
7477  }
7478  if (nondigit) {
7479  pushback(c);
7480  goto trailing_uc;
7481  }
7482  }
7483  if (c > '7' && c <= '9') {
7484  invalid_octal:
7485  yyerror("Invalid octal digit");
7486  }
7487  else if (c == '.' || c == 'e' || c == 'E') {
7488  tokadd('0');
7489  }
7490  else {
7491  pushback(c);
7493  return tINTEGER;
7494  }
7495  }
7496 
7497  for (;;) {
7498  switch (c) {
7499  case '0': case '1': case '2': case '3': case '4':
7500  case '5': case '6': case '7': case '8': case '9':
7501  nondigit = 0;
7502  tokadd(c);
7503  break;
7504 
7505  case '.':
7506  if (nondigit) goto trailing_uc;
7507  if (seen_point || seen_e) {
7508  goto decode_num;
7509  }
7510  else {
7511  int c0 = nextc();
7512  if (c0 == -1 || !ISDIGIT(c0)) {
7513  pushback(c0);
7514  goto decode_num;
7515  }
7516  c = c0;
7517  }
7518  tokadd('.');
7519  tokadd(c);
7520  is_float++;
7521  seen_point++;
7522  nondigit = 0;
7523  break;
7524 
7525  case 'e':
7526  case 'E':
7527  if (nondigit) {
7528  pushback(c);
7529  c = nondigit;
7530  goto decode_num;
7531  }
7532  if (seen_e) {
7533  goto decode_num;
7534  }
7535  tokadd(c);
7536  seen_e++;
7537  is_float++;
7538  nondigit = c;
7539  c = nextc();
7540  if (c != '-' && c != '+') continue;
7541  tokadd(c);
7542  nondigit = c;
7543  break;
7544 
7545  case '_': /* `_' in number just ignored */
7546  if (nondigit) goto decode_num;
7547  nondigit = c;
7548  break;
7549 
7550  default:
7551  goto decode_num;
7552  }
7553  c = nextc();
7554  }
7555 
7556  decode_num:
7557  pushback(c);
7558  if (nondigit) {
7559  char tmp[30];
7560  trailing_uc:
7561  snprintf(tmp, sizeof(tmp), "trailing `%c' in number", nondigit);
7562  yyerror(tmp);
7563  }
7564  tokfix();
7565  if (is_float) {
7566  double d = strtod(tok(), 0);
7567  if (errno == ERANGE) {
7568  rb_warningS("Float %s out of range", tok());
7569  errno = 0;
7570  }
7572  return tFLOAT;
7573  }
7575  return tINTEGER;
7576  }
7577 
7578  case ')':
7579  case ']':
7581  case '}':
7583  CMDARG_LEXPOP();
7584  if (c == ')')
7585  lex_state = EXPR_ENDFN;
7586  else
7587  lex_state = EXPR_ENDARG;
7588  if (c == '}') {
7589  if (!brace_nest--) c = tSTRING_DEND;
7590  }
7591  return c;
7592 
7593  case ':':
7594  c = nextc();
7595  if (c == ':') {
7596  if (IS_BEG() || IS_lex_state(EXPR_CLASS) || IS_SPCARG(-1)) {
7597  lex_state = EXPR_BEG;
7598  return tCOLON3;
7599  }
7600  lex_state = EXPR_DOT;
7601  return tCOLON2;
7602  }
7603  if (IS_END() || ISSPACE(c)) {
7604  pushback(c);
7605  warn_balanced(":", "symbol literal");
7606  lex_state = EXPR_BEG;
7607  return ':';
7608  }
7609  switch (c) {
7610  case '\'':
7611  lex_strterm = NEW_STRTERM(str_ssym, c, 0);
7612  break;
7613  case '"':
7614  lex_strterm = NEW_STRTERM(str_dsym, c, 0);
7615  break;
7616  default:
7617  pushback(c);
7618  break;
7619  }
7620  lex_state = EXPR_FNAME;
7621  return tSYMBEG;
7622 
7623  case '/':
7624  if (IS_lex_state(EXPR_BEG_ANY)) {
7626  return tREGEXP_BEG;
7627  }
7628  if ((c = nextc()) == '=') {
7629  set_yylval_id('/');
7630  lex_state = EXPR_BEG;
7631  return tOP_ASGN;
7632  }
7633  pushback(c);
7634  if (IS_SPCARG(c)) {
7635  (void)arg_ambiguous();
7636  lex_strterm = NEW_STRTERM(str_regexp, '/', 0);
7637  return tREGEXP_BEG;
7638  }
7639  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7640  warn_balanced("/", "regexp literal");
7641  return '/';
7642 
7643  case '^':
7644  if ((c = nextc()) == '=') {
7646  lex_state = EXPR_BEG;
7647  return tOP_ASGN;
7648  }
7649  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7650  pushback(c);
7651  return '^';
7652 
7653  case ';':
7654  lex_state = EXPR_BEG;
7656  return ';';
7657 
7658  case ',':
7659  lex_state = EXPR_BEG;
7660  return ',';
7661 
7662  case '~':
7663  if (IS_AFTER_OPERATOR()) {
7664  if ((c = nextc()) != '@') {
7665  pushback(c);
7666  }
7667  lex_state = EXPR_ARG;
7668  }
7669  else {
7670  lex_state = EXPR_BEG;
7671  }
7672  return '~';
7673 
7674  case '(':
7675  if (IS_BEG()) {
7676  c = tLPAREN;
7677  }
7678  else if (IS_SPCARG(-1)) {
7679  c = tLPAREN_ARG;
7680  }
7681  paren_nest++;
7682  COND_PUSH(0);
7683  CMDARG_PUSH(0);
7684  lex_state = EXPR_BEG;
7685  return c;
7686 
7687  case '[':
7688  paren_nest++;
7689  if (IS_AFTER_OPERATOR()) {
7690  lex_state = EXPR_ARG;
7691  if ((c = nextc()) == ']') {
7692  if ((c = nextc()) == '=') {
7693  return tASET;
7694  }
7695  pushback(c);
7696  return tAREF;
7697  }
7698  pushback(c);
7699  return '[';
7700  }
7701  else if (IS_BEG()) {
7702  c = tLBRACK;
7703  }
7704  else if (IS_ARG() && space_seen) {
7705  c = tLBRACK;
7706  }
7707  lex_state = EXPR_BEG;
7708  COND_PUSH(0);
7709  CMDARG_PUSH(0);
7710  return c;
7711 
7712  case '{':
7713  ++brace_nest;
7714  if (lpar_beg && lpar_beg == paren_nest) {
7715  lex_state = EXPR_BEG;
7716  lpar_beg = 0;
7717  --paren_nest;
7718  COND_PUSH(0);
7719  CMDARG_PUSH(0);
7720  return tLAMBEG;
7721  }
7722  if (IS_ARG() || IS_lex_state(EXPR_END | EXPR_ENDFN))
7723  c = '{'; /* block (primary) */
7724  else if (IS_lex_state(EXPR_ENDARG))
7725  c = tLBRACE_ARG; /* block (expr) */
7726  else
7727  c = tLBRACE; /* hash */
7728  COND_PUSH(0);
7729  CMDARG_PUSH(0);
7730  lex_state = EXPR_BEG;
7731  if (c != tLBRACE) command_start = TRUE;
7732  return c;
7733 
7734  case '\\':
7735  c = nextc();
7736  if (c == '\n') {
7737  space_seen = 1;
7738 #ifdef RIPPER
7739  ripper_dispatch_scan_event(parser, tSP);
7740 #endif
7741  goto retry; /* skip \\n */
7742  }
7743  pushback(c);
7744  return '\\';
7745 
7746  case '%':
7747  if (IS_lex_state(EXPR_BEG_ANY)) {
7748  int term;
7749  int paren;
7750 
7751  c = nextc();
7752  quotation:
7753  if (c == -1 || !ISALNUM(c)) {
7754  term = c;
7755  c = 'Q';
7756  }
7757  else {
7758  term = nextc();
7759  if (rb_enc_isalnum(term, current_enc) || !parser_isascii()) {
7760  yyerror("unknown type of %string");
7761  return 0;
7762  }
7763  }
7764  if (c == -1 || term == -1) {
7765  compile_error(PARSER_ARG "unterminated quoted string meets end of file");
7766  return 0;
7767  }
7768  paren = term;
7769  if (term == '(') term = ')';
7770  else if (term == '[') term = ']';
7771  else if (term == '{') term = '}';
7772  else if (term == '<') term = '>';
7773  else paren = 0;
7774 
7775  switch (c) {
7776  case 'Q':
7777  lex_strterm = NEW_STRTERM(str_dquote, term, paren);
7778  return tSTRING_BEG;
7779 
7780  case 'q':
7781  lex_strterm = NEW_STRTERM(str_squote, term, paren);
7782  return tSTRING_BEG;
7783 
7784  case 'W':
7785  lex_strterm = NEW_STRTERM(str_dword, term, paren);
7786  do {c = nextc();} while (ISSPACE(c));
7787  pushback(c);
7788  return tWORDS_BEG;
7789 
7790  case 'w':
7791  lex_strterm = NEW_STRTERM(str_sword, term, paren);
7792  do {c = nextc();} while (ISSPACE(c));
7793  pushback(c);
7794  return tQWORDS_BEG;
7795 
7796  case 'I':
7797  lex_strterm = NEW_STRTERM(str_dword, term, paren);
7798  do {c = nextc();} while (ISSPACE(c));
7799  pushback(c);
7800  return tSYMBOLS_BEG;
7801 
7802  case 'i':
7803  lex_strterm = NEW_STRTERM(str_sword, term, paren);
7804  do {c = nextc();} while (ISSPACE(c));
7805  pushback(c);
7806  return tQSYMBOLS_BEG;
7807 
7808  case 'x':
7809  lex_strterm = NEW_STRTERM(str_xquote, term, paren);
7810  return tXSTRING_BEG;
7811 
7812  case 'r':
7813  lex_strterm = NEW_STRTERM(str_regexp, term, paren);
7814  return tREGEXP_BEG;
7815 
7816  case 's':
7817  lex_strterm = NEW_STRTERM(str_ssym, term, paren);
7818  lex_state = EXPR_FNAME;
7819  return tSYMBEG;
7820 
7821  default:
7822  yyerror("unknown type of %string");
7823  return 0;
7824  }
7825  }
7826  if ((c = nextc()) == '=') {
7827  set_yylval_id('%');
7828  lex_state = EXPR_BEG;
7829  return tOP_ASGN;
7830  }
7831  if (IS_SPCARG(c)) {
7832  goto quotation;
7833  }
7834  lex_state = IS_AFTER_OPERATOR() ? EXPR_ARG : EXPR_BEG;
7835  pushback(c);
7836  warn_balanced("%%", "string literal");
7837  return '%';
7838 
7839  case '$':
7840  lex_state = EXPR_END;
7841  newtok();
7842  c = nextc();
7843  switch (c) {
7844  case '_': /* $_: last read line string */
7845  c = nextc();
7846  if (parser_is_identchar()) {
7847  tokadd('$');
7848  tokadd('_');
7849  break;
7850  }
7851  pushback(c);
7852  c = '_';
7853  /* fall through */
7854  case '~': /* $~: match-data */
7855  case '*': /* $*: argv */
7856  case '$': /* $$: pid */
7857  case '?': /* $?: last status */
7858  case '!': /* $!: error string */
7859  case '@': /* $@: error position */
7860  case '/': /* $/: input record separator */
7861  case '\\': /* $\: output record separator */
7862  case ';': /* $;: field separator */
7863  case ',': /* $,: output field separator */
7864  case '.': /* $.: last read line number */
7865  case '=': /* $=: ignorecase */
7866  case ':': /* $:: load path */
7867  case '<': /* $<: reading filename */
7868  case '>': /* $>: default output handle */
7869  case '\"': /* $": already loaded files */
7870  tokadd('$');
7871  tokadd(c);
7872  tokfix();
7874  return tGVAR;
7875 
7876  case '-':
7877  tokadd('$');
7878  tokadd(c);
7879  c = nextc();
7880  if (parser_is_identchar()) {
7881  if (tokadd_mbchar(c) == -1) return 0;
7882  }
7883  else {
7884  pushback(c);
7885  }
7886  gvar:
7887  tokfix();
7889  return tGVAR;
7890 
7891  case '&': /* $&: last match */
7892  case '`': /* $`: string before last match */
7893  case '\'': /* $': string after last match */
7894  case '+': /* $+: string matches last paren. */
7895  if (IS_lex_state_for(last_state, EXPR_FNAME)) {
7896  tokadd('$');
7897  tokadd(c);
7898  goto gvar;
7899  }
7901  return tBACK_REF;
7902 
7903  case '1': case '2': case '3':
7904  case '4': case '5': case '6':
7905  case '7': case '8': case '9':
7906  tokadd('$');
7907  do {
7908  tokadd(c);
7909  c = nextc();
7910  } while (c != -1 && ISDIGIT(c));
7911  pushback(c);
7912  if (IS_lex_state_for(last_state, EXPR_FNAME)) goto gvar;
7913  tokfix();
7914  set_yylval_node(NEW_NTH_REF(atoi(tok()+1)));
7915  return tNTH_REF;
7916 
7917  default:
7918  if (!parser_is_identchar()) {
7919  pushback(c);
7920  compile_error(PARSER_ARG "`$%c' is not allowed as a global variable name", c);
7921  return 0;
7922  }
7923  case '0':
7924  tokadd('$');
7925  }
7926  break;
7927 
7928  case '@':
7929  c = nextc();
7930  newtok();
7931  tokadd('@');
7932  if (c == '@') {
7933  tokadd('@');
7934  c = nextc();
7935  }
7936  if (c != -1 && (ISDIGIT(c) || !parser_is_identchar())) {
7937  pushback(c);
7938  if (tokidx == 1) {
7939  compile_error(PARSER_ARG "`@%c' is not allowed as an instance variable name", c);
7940  }
7941  else {
7942  compile_error(PARSER_ARG "`@@%c' is not allowed as a class variable name", c);
7943  }
7944  return 0;
7945  }
7946  break;
7947 
7948  case '_':
7949  if (was_bol() && whole_match_p("__END__", 7, 0)) {
7950  ruby__end__seen = 1;
7951  parser->eofp = Qtrue;
7952 #ifndef RIPPER
7953  return -1;
7954 #else
7955  lex_goto_eol(parser);
7956  ripper_dispatch_scan_event(parser, k__END__);
7957  return 0;
7958 #endif
7959  }
7960  newtok();
7961  break;
7962 
7963  default:
7964  if (!parser_is_identchar()) {
7965  rb_compile_error(PARSER_ARG "Invalid char `\\x%02X' in expression", c);
7966  goto retry;
7967  }
7968 
7969  newtok();
7970  break;
7971  }
7972 
7973  mb = ENC_CODERANGE_7BIT;
7974  do {
7975  if (!ISASCII(c)) mb = ENC_CODERANGE_UNKNOWN;
7976  if (tokadd_mbchar(c) == -1) return 0;
7977  c = nextc();
7978  } while (parser_is_identchar());
7979  switch (tok()[0]) {
7980  case '@': case '$':
7981  pushback(c);
7982  break;
7983  default:
7984  if ((c == '!' || c == '?') && !peek('=')) {
7985  tokadd(c);
7986  }
7987  else {
7988  pushback(c);
7989  }
7990  }
7991  tokfix();
7992 
7993  {
7994  int result = 0;
7995 
7996  last_state = lex_state;
7997  switch (tok()[0]) {
7998  case '$':
7999  lex_state = EXPR_END;
8000  result = tGVAR;
8001  break;
8002  case '@':
8003  lex_state = EXPR_END;
8004  if (tok()[1] == '@')
8005  result = tCVAR;
8006  else
8007  result = tIVAR;
8008  break;
8009 
8010  default:
8011  if (toklast() == '!' || toklast() == '?') {
8012  result = tFID;
8013  }
8014  else {
8015  if (IS_lex_state(EXPR_FNAME)) {
8016  if ((c = nextc()) == '=' && !peek('~') && !peek('>') &&
8017  (!peek('=') || (peek_n('>', 1)))) {
8018  result = tIDENTIFIER;
8019  tokadd(c);
8020  tokfix();
8021  }
8022  else {
8023  pushback(c);
8024  }
8025  }
8026  if (result == 0 && ISUPPER(tok()[0])) {
8027  result = tCONSTANT;
8028  }
8029  else {
8030  result = tIDENTIFIER;
8031  }
8032  }
8033 
8034  if (IS_LABEL_POSSIBLE()) {
8035  if (IS_LABEL_SUFFIX(0)) {
8036  lex_state = EXPR_BEG;
8037  nextc();
8039  return tLABEL;
8040  }
8041  }
8042  if (mb == ENC_CODERANGE_7BIT && !IS_lex_state(EXPR_DOT)) {
8043  const struct kwtable *kw;
8044 
8045  /* See if it is a reserved word. */
8046  kw = rb_reserved_word(tok(), toklen());
8047  if (kw) {
8048  enum lex_state_e state = lex_state;
8049  lex_state = kw->state;
8050  if (state == EXPR_FNAME) {
8052  return kw->id[0];
8053  }
8054  if (lex_state == EXPR_BEG) {
8055  command_start = TRUE;
8056  }
8057  if (kw->id[0] == keyword_do) {
8058  if (lpar_beg && lpar_beg == paren_nest) {
8059  lpar_beg = 0;
8060  --paren_nest;
8061  return keyword_do_LAMBDA;
8062  }
8063  if (COND_P()) return keyword_do_cond;
8064  if (CMDARG_P() && state != EXPR_CMDARG)
8065  return keyword_do_block;
8066  if (state & (EXPR_BEG | EXPR_ENDARG))
8067  return keyword_do_block;
8068  return keyword_do;
8069  }
8070  if (state & (EXPR_BEG | EXPR_VALUE))
8071  return kw->id[0];
8072  else {
8073  if (kw->id[0] != kw->id[1])
8074  lex_state = EXPR_BEG;
8075  return kw->id[1];
8076  }
8077  }
8078  }
8079 
8080  if (IS_lex_state(EXPR_BEG_ANY | EXPR_ARG_ANY | EXPR_DOT)) {
8081  if (cmd_state) {
8082  lex_state = EXPR_CMDARG;
8083  }
8084  else {
8085  lex_state = EXPR_ARG;
8086  }
8087  }
8088  else if (lex_state == EXPR_FNAME) {
8089  lex_state = EXPR_ENDFN;
8090  }
8091  else {
8092  lex_state = EXPR_END;
8093  }
8094  }
8095  {
8096  ID ident = TOK_INTERN(!ENC_SINGLE(mb));
8097 
8098  set_yylval_name(ident);
8099  if (!IS_lex_state_for(last_state, EXPR_DOT|EXPR_FNAME) &&
8100  is_local_id(ident) && lvar_defined(ident)) {
8101  lex_state = EXPR_END;
8102  }
8103  }
8104  return result;
8105  }
8106 }
8107 
8108 #if YYPURE
8109 static int
8110 yylex(void *lval, void *p)
8111 #else
8112 yylex(void *p)
8113 #endif
8114 {
8115  struct parser_params *parser = (struct parser_params*)p;
8116  int t;
8117 
8118 #if YYPURE
8119  parser->parser_yylval = lval;
8120  parser->parser_yylval->val = Qundef;
8121 #endif
8122  t = parser_yylex(parser);
8123 #ifdef RIPPER
8124  if (!NIL_P(parser->delayed)) {
8125  ripper_dispatch_delayed_token(parser, t);
8126  return t;
8127  }
8128  if (t != 0)
8129  ripper_dispatch_scan_event(parser, t);
8130 #endif
8131 
8132  return t;
8133 }
8134 
8135 #ifndef RIPPER
8136 static NODE*
8137 node_newnode(struct parser_params *parser, enum node_type type, VALUE a0, VALUE a1, VALUE a2)
8138 {
8139  NODE *n = (rb_node_newnode)(type, a0, a1, a2);
8141  return n;
8142 }
8143 
8144 static enum node_type
8145 nodetype(NODE *node) /* for debug */
8146 {
8147  return (enum node_type)nd_type(node);
8148 }
8149 
8150 static int
8151 nodeline(NODE *node)
8152 {
8153  return nd_line(node);
8154 }
8155 
8156 static NODE*
8157 newline_node(NODE *node)
8158 {
8159  if (node) {
8160  node = remove_begin(node);
8161  node->flags |= NODE_FL_NEWLINE;
8162  }
8163  return node;
8164 }
8165 
8166 static void
8167 fixpos(NODE *node, NODE *orig)
8168 {
8169  if (!node) return;
8170  if (!orig) return;
8171  if (orig == (NODE*)1) return;
8172  nd_set_line(node, nd_line(orig));
8173 }
8174 
8175 static void
8176 parser_warning(struct parser_params *parser, NODE *node, const char *mesg)
8177 {
8178  rb_compile_warning(ruby_sourcefile, nd_line(node), "%s", mesg);
8179 }
8180 #define parser_warning(node, mesg) parser_warning(parser, (node), (mesg))
8181 
8182 static void
8183 parser_warn(struct parser_params *parser, NODE *node, const char *mesg)
8184 {
8185  rb_compile_warn(ruby_sourcefile, nd_line(node), "%s", mesg);
8186 }
8187 #define parser_warn(node, mesg) parser_warn(parser, (node), (mesg))
8188 
8189 static NODE*
8190 block_append_gen(struct parser_params *parser, NODE *head, NODE *tail)
8191 {
8192  NODE *end, *h = head, *nd;
8193 
8194  if (tail == 0) return head;
8195 
8196  if (h == 0) return tail;
8197  switch (nd_type(h)) {
8198  case NODE_LIT:
8199  case NODE_STR:
8200  case NODE_SELF:
8201  case NODE_TRUE:
8202  case NODE_FALSE:
8203  case NODE_NIL:
8204  parser_warning(h, "unused literal ignored");
8205  return tail;
8206  default:
8207  h = end = NEW_BLOCK(head);
8208  end->nd_end = end;
8209  fixpos(end, head);
8210  head = end;
8211  break;
8212  case NODE_BLOCK:
8213  end = h->nd_end;
8214  break;
8215  }
8216 
8217  nd = end->nd_head;
8218  switch (nd_type(nd)) {
8219  case NODE_RETURN:
8220  case NODE_BREAK:
8221  case NODE_NEXT:
8222  case NODE_REDO:
8223  case NODE_RETRY:
8224  if (RTEST(ruby_verbose)) {
8225  parser_warning(tail, "statement not reached");
8226  }
8227  break;
8228 
8229  default:
8230  break;
8231  }
8232 
8233  if (nd_type(tail) != NODE_BLOCK) {
8234  tail = NEW_BLOCK(tail);
8235  tail->nd_end = tail;
8236  }
8237  end->nd_next = tail;
8238  h->nd_end = tail->nd_end;
8239  return head;
8240 }
8241 
8242 /* append item to the list */
8243 static NODE*
8244 list_append_gen(struct parser_params *parser, NODE *list, NODE *item)
8245 {
8246  NODE *last;
8247 
8248  if (list == 0) return NEW_LIST(item);
8249  if (list->nd_next) {
8250  last = list->nd_next->nd_end;
8251  }
8252  else {
8253  last = list;
8254  }
8255 
8256  list->nd_alen += 1;
8257  last->nd_next = NEW_LIST(item);
8258  list->nd_next->nd_end = last->nd_next;
8259  return list;
8260 }
8261 
8262 /* concat two lists */
8263 static NODE*
8264 list_concat_gen(struct parser_params *parser, NODE *head, NODE *tail)
8265 {
8266  NODE *last;
8267 
8268  if (head->nd_next) {
8269  last = head->nd_next->nd_end;
8270  }
8271  else {
8272  last = head;
8273  }
8274 
8275  head->nd_alen += tail->nd_alen;
8276  last->nd_next = tail;
8277  if (tail->nd_next) {
8278  head->nd_next->nd_end = tail->nd_next->nd_end;
8279  }
8280  else {
8281  head->nd_next->nd_end = tail;
8282  }
8283 
8284  return head;
8285 }
8286 
8287 static int
8288 literal_concat0(struct parser_params *parser, VALUE head, VALUE tail)
8289 {
8290  if (NIL_P(tail)) return 1;
8291  if (!rb_enc_compatible(head, tail)) {
8292  compile_error(PARSER_ARG "string literal encodings differ (%s / %s)",
8293  rb_enc_name(rb_enc_get(head)),
8294  rb_enc_name(rb_enc_get(tail)));
8295  rb_str_resize(head, 0);
8296  rb_str_resize(tail, 0);
8297  return 0;
8298  }
8299  rb_str_buf_append(head, tail);
8300  return 1;
8301 }
8302 
8303 /* concat two string literals */
8304 static NODE *
8305 literal_concat_gen(struct parser_params *parser, NODE *head, NODE *tail)
8306 {
8307  enum node_type htype;
8308  NODE *headlast;
8309  VALUE lit;
8310 
8311  if (!head) return tail;
8312  if (!tail) return head;
8313 
8314  htype = nd_type(head);
8315  if (htype == NODE_EVSTR) {
8316  NODE *node = NEW_DSTR(Qnil);
8317  head = list_append(node, head);
8318  htype = NODE_DSTR;
8319  }
8320  switch (nd_type(tail)) {
8321  case NODE_STR:
8322  if (htype == NODE_DSTR && (headlast = head->nd_next->nd_end->nd_head) &&
8323  nd_type(headlast) == NODE_STR) {
8324  htype = NODE_STR;
8325  lit = headlast->nd_lit;
8326  }
8327  else {
8328  lit = head->nd_lit;
8329  }
8330  if (htype == NODE_STR) {
8331  if (!literal_concat0(parser, lit, tail->nd_lit)) {
8332  error:
8333  rb_gc_force_recycle((VALUE)head);
8334  rb_gc_force_recycle((VALUE)tail);
8335  return 0;
8336  }
8337  rb_gc_force_recycle((VALUE)tail);
8338  }
8339  else {
8340  list_append(head, tail);
8341  }
8342  break;
8343 
8344  case NODE_DSTR:
8345  if (htype == NODE_STR) {
8346  if (!literal_concat0(parser, head->nd_lit, tail->nd_lit))
8347  goto error;
8348  tail->nd_lit = head->nd_lit;
8349  rb_gc_force_recycle((VALUE)head);
8350  head = tail;
8351  }
8352  else if (NIL_P(tail->nd_lit)) {
8353  append:
8354  head->nd_alen += tail->nd_alen - 1;
8355  head->nd_next->nd_end->nd_next = tail->nd_next;
8356  head->nd_next->nd_end = tail->nd_next->nd_end;
8357  rb_gc_force_recycle((VALUE)tail);
8358  }
8359  else if (htype == NODE_DSTR && (headlast = head->nd_next->nd_end->nd_head) &&
8360  nd_type(headlast) == NODE_STR) {
8361  lit = headlast->nd_lit;
8362  if (!literal_concat0(parser, lit, tail->nd_lit))
8363  goto error;
8364  tail->nd_lit = Qnil;
8365  goto append;
8366  }
8367  else {
8368  nd_set_type(tail, NODE_ARRAY);
8369  tail->nd_head = NEW_STR(tail->nd_lit);
8370  list_concat(head, tail);
8371  }
8372  break;
8373 
8374  case NODE_EVSTR:
8375  if (htype == NODE_STR) {
8376  nd_set_type(head, NODE_DSTR);
8377  head->nd_alen = 1;
8378  }
8379  list_append(head, tail);
8380  break;
8381  }
8382  return head;
8383 }
8384 
8385 static NODE *
8386 evstr2dstr_gen(struct parser_params *parser, NODE *node)
8387 {
8388  if (nd_type(node) == NODE_EVSTR) {
8389  node = list_append(NEW_DSTR(Qnil), node);
8390  }
8391  return node;
8392 }
8393 
8394 static NODE *
8395 new_evstr_gen(struct parser_params *parser, NODE *node)
8396 {
8397  NODE *head = node;
8398 
8399  if (node) {
8400  switch (nd_type(node)) {
8401  case NODE_STR: case NODE_DSTR: case NODE_EVSTR:
8402  return node;
8403  }
8404  }
8405  return NEW_EVSTR(head);
8406 }
8407 
8408 static NODE *
8409 call_bin_op_gen(struct parser_params *parser, NODE *recv, ID id, NODE *arg1)
8410 {
8411  value_expr(recv);
8412  value_expr(arg1);
8413  return NEW_CALL(recv, id, NEW_LIST(arg1));
8414 }
8415 
8416 static NODE *
8417 call_uni_op_gen(struct parser_params *parser, NODE *recv, ID id)
8418 {
8419  value_expr(recv);
8420  return NEW_CALL(recv, id, 0);
8421 }
8422 
8423 static NODE*
8424 match_op_gen(struct parser_params *parser, NODE *node1, NODE *node2)
8425 {
8426  value_expr(node1);
8427  value_expr(node2);
8428  if (node1) {
8429  switch (nd_type(node1)) {
8430  case NODE_DREGX:
8431  case NODE_DREGX_ONCE:
8432  return NEW_MATCH2(node1, node2);
8433 
8434  case NODE_LIT:
8435  if (RB_TYPE_P(node1->nd_lit, T_REGEXP)) {
8436  return NEW_MATCH2(node1, node2);
8437  }
8438  }
8439  }
8440 
8441  if (node2) {
8442  switch (nd_type(node2)) {
8443  case NODE_DREGX:
8444  case NODE_DREGX_ONCE:
8445  return NEW_MATCH3(node2, node1);
8446 
8447  case NODE_LIT:
8448  if (RB_TYPE_P(node2->nd_lit, T_REGEXP)) {
8449  return NEW_MATCH3(node2, node1);
8450  }
8451  }
8452  }
8453 
8454  return NEW_CALL(node1, tMATCH, NEW_LIST(node2));
8455 }
8456 
8457 static NODE*
8458 gettable_gen(struct parser_params *parser, ID id)
8459 {
8460  switch (id) {
8461  case keyword_self:
8462  return NEW_SELF();
8463  case keyword_nil:
8464  return NEW_NIL();
8465  case keyword_true:
8466  return NEW_TRUE();
8467  case keyword_false:
8468  return NEW_FALSE();
8469  case keyword__FILE__:
8472  case keyword__LINE__:
8473  return NEW_LIT(INT2FIX(tokline));
8474  case keyword__ENCODING__:
8476  }
8477  switch (id_type(id)) {
8478  case ID_LOCAL:
8479  if (dyna_in_block() && dvar_defined(id)) return NEW_DVAR(id);
8480  if (local_id(id)) return NEW_LVAR(id);
8481  /* method call without arguments */
8482  return NEW_VCALL(id);
8483  case ID_GLOBAL:
8484  return NEW_GVAR(id);
8485  case ID_INSTANCE:
8486  return NEW_IVAR(id);
8487  case ID_CONST:
8488  return NEW_CONST(id);
8489  case ID_CLASS:
8490  return NEW_CVAR(id);
8491  }
8492  compile_error(PARSER_ARG "identifier %s is not valid to get", rb_id2name(id));
8493  return 0;
8494 }
8495 #else /* !RIPPER */
8496 static int
8497 id_is_var_gen(struct parser_params *parser, ID id)
8498 {
8499  if (is_notop_id(id)) {
8500  switch (id & ID_SCOPE_MASK) {
8501  case ID_GLOBAL: case ID_INSTANCE: case ID_CONST: case ID_CLASS:
8502  return 1;
8503  case ID_LOCAL:
8504  if (dyna_in_block() && dvar_defined(id)) return 1;
8505  if (local_id(id)) return 1;
8506  /* method call without arguments */
8507  return 0;
8508  }
8509  }
8510  compile_error(PARSER_ARG "identifier %s is not valid to get", rb_id2name(id));
8511  return 0;
8512 }
8513 #endif /* !RIPPER */
8514 
8515 #if PARSER_DEBUG
8516 static const char *
8517 lex_state_name(enum lex_state_e state)
8518 {
8519  static const char names[][12] = {
8520  "EXPR_BEG", "EXPR_END", "EXPR_ENDARG", "EXPR_ENDFN", "EXPR_ARG",
8521  "EXPR_CMDARG", "EXPR_MID", "EXPR_FNAME", "EXPR_DOT", "EXPR_CLASS",
8522  "EXPR_VALUE",
8523  };
8524 
8525  if ((unsigned)state & ~(~0u << EXPR_MAX_STATE))
8526  return names[ffs(state)];
8527  return NULL;
8528 }
8529 #endif
8530 
8531 #ifdef RIPPER
8532 static VALUE
8533 assignable_gen(struct parser_params *parser, VALUE lhs)
8534 #else
8535 static NODE*
8536 assignable_gen(struct parser_params *parser, ID id, NODE *val)
8537 #endif
8538 {
8539 #ifdef RIPPER
8540  ID id = get_id(lhs);
8541 # define assignable_result(x) get_value(lhs)
8542 # define parser_yyerror(parser, x) dispatch1(assign_error, lhs)
8543 #else
8544 # define assignable_result(x) (x)
8545 #endif
8546  if (!id) return assignable_result(0);
8547  switch (id) {
8548  case keyword_self:
8549  yyerror("Can't change the value of self");
8550  goto error;
8551  case keyword_nil:
8552  yyerror("Can't assign to nil");
8553  goto error;
8554  case keyword_true:
8555  yyerror("Can't assign to true");
8556  goto error;
8557  case keyword_false:
8558  yyerror("Can't assign to false");
8559  goto error;
8560  case keyword__FILE__:
8561  yyerror("Can't assign to __FILE__");
8562  goto error;
8563  case keyword__LINE__:
8564  yyerror("Can't assign to __LINE__");
8565  goto error;
8566  case keyword__ENCODING__:
8567  yyerror("Can't assign to __ENCODING__");
8568  goto error;
8569  }
8570  switch (id_type(id)) {
8571  case ID_LOCAL:
8572  if (dyna_in_block()) {
8573  if (dvar_curr(id)) {
8574  return assignable_result(NEW_DASGN_CURR(id, val));
8575  }
8576  else if (dvar_defined(id)) {
8577  return assignable_result(NEW_DASGN(id, val));
8578  }
8579  else if (local_id(id)) {
8580  return assignable_result(NEW_LASGN(id, val));
8581  }
8582  else {
8583  dyna_var(id);
8584  return assignable_result(NEW_DASGN_CURR(id, val));
8585  }
8586  }
8587  else {
8588  if (!local_id(id)) {
8589  local_var(id);
8590  }
8591  return assignable_result(NEW_LASGN(id, val));
8592  }
8593  break;
8594  case ID_GLOBAL:
8595  return assignable_result(NEW_GASGN(id, val));
8596  case ID_INSTANCE:
8597  return assignable_result(NEW_IASGN(id, val));
8598  case ID_CONST:
8599  if (!in_def && !in_single)
8600  return assignable_result(NEW_CDECL(id, val, 0));
8601  yyerror("dynamic constant assignment");
8602  break;
8603  case ID_CLASS:
8604  return assignable_result(NEW_CVASGN(id, val));
8605  default:
8606  compile_error(PARSER_ARG "identifier %s is not valid to set", rb_id2name(id));
8607  }
8608  error:
8609  return assignable_result(0);
8610 #undef assignable_result
8611 #undef parser_yyerror
8612 }
8613 
8614 static int
8615 is_private_local_id(ID name)
8616 {
8617  VALUE s;
8618  if (name == idUScore) return 1;
8619  if (!is_local_id(name)) return 0;
8620  s = rb_id2str(name);
8621  if (!s) return 0;
8622  return RSTRING_PTR(s)[0] == '_';
8623 }
8624 
8625 #define LVAR_USED ((ID)1 << (sizeof(ID) * CHAR_BIT - 1))
8626 
8627 static ID
8628 shadowing_lvar_gen(struct parser_params *parser, ID name)
8629 {
8630  if (is_private_local_id(name)) return name;
8631  if (dyna_in_block()) {
8632  if (dvar_curr(name)) {
8633  yyerror("duplicated argument name");
8634  }
8635  else if (dvar_defined_get(name) || local_id(name)) {
8636  rb_warningS("shadowing outer local variable - %s", rb_id2name(name));
8637  vtable_add(lvtbl->vars, name);
8638  if (lvtbl->used) {
8640  }
8641  }
8642  }
8643  else {
8644  if (local_id(name)) {
8645  yyerror("duplicated argument name");
8646  }
8647  }
8648  return name;
8649 }
8650 
8651 static void
8652 new_bv_gen(struct parser_params *parser, ID name)
8653 {
8654  if (!name) return;
8655  if (!is_local_id(name)) {
8656  compile_error(PARSER_ARG "invalid local variable - %s",
8657  rb_id2name(name));
8658  return;
8659  }
8660  shadowing_lvar(name);
8661  dyna_var(name);
8662 }
8663 
8664 #ifndef RIPPER
8665 static NODE *
8666 aryset_gen(struct parser_params *parser, NODE *recv, NODE *idx)
8667 {
8668  if (recv && nd_type(recv) == NODE_SELF)
8669  recv = (NODE *)1;
8670  return NEW_ATTRASGN(recv, tASET, idx);
8671 }
8672 
8673 static void
8674 block_dup_check_gen(struct parser_params *parser, NODE *node1, NODE *node2)
8675 {
8676  if (node2 && node1 && nd_type(node1) == NODE_BLOCK_PASS) {
8677  compile_error(PARSER_ARG "both block arg and actual block given");
8678  }
8679 }
8680 
8681 static const char id_type_names[][9] = {
8682  "LOCAL",
8683  "INSTANCE",
8684  "", /* INSTANCE2 */
8685  "GLOBAL",
8686  "ATTRSET",
8687  "CONST",
8688  "CLASS",
8689  "JUNK",
8690 };
8691 
8692 ID
8693 rb_id_attrset(ID id)
8694 {
8695  if (!is_notop_id(id)) {
8696  switch (id) {
8697  case tAREF: case tASET:
8698  return tASET; /* only exception */
8699  }
8700  rb_name_error(id, "cannot make operator ID :%s attrset", rb_id2name(id));
8701  }
8702  else {
8703  int scope = (int)(id & ID_SCOPE_MASK);
8704  switch (scope) {
8705  case ID_LOCAL: case ID_INSTANCE: case ID_GLOBAL:
8706  case ID_CONST: case ID_CLASS: case ID_JUNK:
8707  break;
8708  case ID_ATTRSET:
8709  return id;
8710  default:
8711  rb_name_error(id, "cannot make %s ID %+"PRIsVALUE" attrset",
8712  id_type_names[scope], ID2SYM(id));
8713 
8714  }
8715  }
8716  id &= ~ID_SCOPE_MASK;
8717  id |= ID_ATTRSET;
8718  return id;
8719 }
8720 
8721 static NODE *
8722 attrset_gen(struct parser_params *parser, NODE *recv, ID id)
8723 {
8724  if (recv && nd_type(recv) == NODE_SELF)
8725  recv = (NODE *)1;
8726  return NEW_ATTRASGN(recv, rb_id_attrset(id), 0);
8727 }
8728 
8729 static void
8730 rb_backref_error_gen(struct parser_params *parser, NODE *node)
8731 {
8732  switch (nd_type(node)) {
8733  case NODE_NTH_REF:
8734  compile_error(PARSER_ARG "Can't set variable $%ld", node->nd_nth);
8735  break;
8736  case NODE_BACK_REF:
8737  compile_error(PARSER_ARG "Can't set variable $%c", (int)node->nd_nth);
8738  break;
8739  }
8740 }
8741 
8742 static NODE *
8743 arg_concat_gen(struct parser_params *parser, NODE *node1, NODE *node2)
8744 {
8745  if (!node2) return node1;
8746  switch (nd_type(node1)) {
8747  case NODE_BLOCK_PASS:
8748  if (node1->nd_head)
8749  node1->nd_head = arg_concat(node1->nd_head, node2);
8750  else
8751  node1->nd_head = NEW_LIST(node2);
8752  return node1;
8753  case NODE_ARGSPUSH:
8754  if (nd_type(node2) != NODE_ARRAY) break;
8755  node1->nd_body = list_concat(NEW_LIST(node1->nd_body), node2);
8756  nd_set_type(node1, NODE_ARGSCAT);
8757  return node1;
8758  case NODE_ARGSCAT:
8759  if (nd_type(node2) != NODE_ARRAY ||
8760  nd_type(node1->nd_body) != NODE_ARRAY) break;
8761  node1->nd_body = list_concat(node1->nd_body, node2);
8762  return node1;
8763  }
8764  return NEW_ARGSCAT(node1, node2);
8765 }
8766 
8767 static NODE *
8768 arg_append_gen(struct parser_params *parser, NODE *node1, NODE *node2)
8769 {
8770  if (!node1) return NEW_LIST(node2);
8771  switch (nd_type(node1)) {
8772  case NODE_ARRAY:
8773  return list_append(node1, node2);
8774  case NODE_BLOCK_PASS:
8775  node1->nd_head = arg_append(node1->nd_head, node2);
8776  return node1;
8777  case NODE_ARGSPUSH:
8778  node1->nd_body = list_append(NEW_LIST(node1->nd_body), node2);
8779  nd_set_type(node1, NODE_ARGSCAT);
8780  return node1;
8781  }
8782  return NEW_ARGSPUSH(node1, node2);
8783 }
8784 
8785 static NODE *
8786 splat_array(NODE* node)
8787 {
8788  if (nd_type(node) == NODE_SPLAT) node = node->nd_head;
8789  if (nd_type(node) == NODE_ARRAY) return node;
8790  return 0;
8791 }
8792 
8793 static NODE *
8794 node_assign_gen(struct parser_params *parser, NODE *lhs, NODE *rhs)
8795 {
8796  if (!lhs) return 0;
8797 
8798  switch (nd_type(lhs)) {
8799  case NODE_GASGN:
8800  case NODE_IASGN:
8801  case NODE_IASGN2:
8802  case NODE_LASGN:
8803  case NODE_DASGN:
8804  case NODE_DASGN_CURR:
8805  case NODE_MASGN:
8806  case NODE_CDECL:
8807  case NODE_CVASGN:
8808  lhs->nd_value = rhs;
8809  break;
8810 
8811  case NODE_ATTRASGN:
8812  case NODE_CALL:
8813  lhs->nd_args = arg_append(lhs->nd_args, rhs);
8814  break;
8815 
8816  default:
8817  /* should not happen */
8818  break;
8819  }
8820 
8821  return lhs;
8822 }
8823 
8824 static int
8825 value_expr_gen(struct parser_params *parser, NODE *node)
8826 {
8827  int cond = 0;
8828 
8829  if (!node) {
8830  rb_warning0("empty expression");
8831  }
8832  while (node) {
8833  switch (nd_type(node)) {
8834  case NODE_DEFN:
8835  case NODE_DEFS:
8836  parser_warning(node, "void value expression");
8837  return FALSE;
8838 
8839  case NODE_RETURN:
8840  case NODE_BREAK:
8841  case NODE_NEXT:
8842  case NODE_REDO:
8843  case NODE_RETRY:
8844  if (!cond) yyerror("void value expression");
8845  /* or "control never reach"? */
8846  return FALSE;
8847 
8848  case NODE_BLOCK:
8849  while (node->nd_next) {
8850  node = node->nd_next;
8851  }
8852  node = node->nd_head;
8853  break;
8854 
8855  case NODE_BEGIN:
8856  node = node->nd_body;
8857  break;
8858 
8859  case NODE_IF:
8860  if (!node->nd_body) {
8861  node = node->nd_else;
8862  break;
8863  }
8864  else if (!node->nd_else) {
8865  node = node->nd_body;
8866  break;
8867  }
8868  if (!value_expr(node->nd_body)) return FALSE;
8869  node = node->nd_else;
8870  break;
8871 
8872  case NODE_AND:
8873  case NODE_OR:
8874  cond = 1;
8875  node = node->nd_2nd;
8876  break;
8877 
8878  default:
8879  return TRUE;
8880  }
8881  }
8882 
8883  return TRUE;
8884 }
8885 
8886 static void
8887 void_expr_gen(struct parser_params *parser, NODE *node)
8888 {
8889  const char *useless = 0;
8890 
8891  if (!RTEST(ruby_verbose)) return;
8892 
8893  if (!node) return;
8894  switch (nd_type(node)) {
8895  case NODE_CALL:
8896  switch (node->nd_mid) {
8897  case '+':
8898  case '-':
8899  case '*':
8900  case '/':
8901  case '%':
8902  case tPOW:
8903  case tUPLUS:
8904  case tUMINUS:
8905  case '|':
8906  case '^':
8907  case '&':
8908  case tCMP:
8909  case '>':
8910  case tGEQ:
8911  case '<':
8912  case tLEQ:
8913  case tEQ:
8914  case tNEQ:
8915  useless = rb_id2name(node->nd_mid);
8916  break;
8917  }
8918  break;
8919 
8920  case NODE_LVAR:
8921  case NODE_DVAR:
8922  case NODE_GVAR:
8923  case NODE_IVAR:
8924  case NODE_CVAR:
8925  case NODE_NTH_REF:
8926  case NODE_BACK_REF:
8927  useless = "a variable";
8928  break;
8929  case NODE_CONST:
8930  useless = "a constant";
8931  break;
8932  case NODE_LIT:
8933  case NODE_STR:
8934  case NODE_DSTR:
8935  case NODE_DREGX:
8936  case NODE_DREGX_ONCE:
8937  useless = "a literal";
8938  break;
8939  case NODE_COLON2:
8940  case NODE_COLON3:
8941  useless = "::";
8942  break;
8943  case NODE_DOT2:
8944  useless = "..";
8945  break;
8946  case NODE_DOT3:
8947  useless = "...";
8948  break;
8949  case NODE_SELF:
8950  useless = "self";
8951  break;
8952  case NODE_NIL:
8953  useless = "nil";
8954  break;
8955  case NODE_TRUE:
8956  useless = "true";
8957  break;
8958  case NODE_FALSE:
8959  useless = "false";
8960  break;
8961  case NODE_DEFINED:
8962  useless = "defined?";
8963  break;
8964  }
8965 
8966  if (useless) {
8967  int line = ruby_sourceline;
8968 
8969  ruby_sourceline = nd_line(node);
8970  rb_warnS("possibly useless use of %s in void context", useless);
8971  ruby_sourceline = line;
8972  }
8973 }
8974 
8975 static void
8976 void_stmts_gen(struct parser_params *parser, NODE *node)
8977 {
8978  if (!RTEST(ruby_verbose)) return;
8979  if (!node) return;
8980  if (nd_type(node) != NODE_BLOCK) return;
8981 
8982  for (;;) {
8983  if (!node->nd_next) return;
8984  void_expr0(node->nd_head);
8985  node = node->nd_next;
8986  }
8987 }
8988 
8989 static NODE *
8990 remove_begin(NODE *node)
8991 {
8992  NODE **n = &node, *n1 = node;
8993  while (n1 && nd_type(n1) == NODE_BEGIN && n1->nd_body) {
8994  *n = n1 = n1->nd_body;
8995  }
8996  return node;
8997 }
8998 
8999 static void
9000 reduce_nodes_gen(struct parser_params *parser, NODE **body)
9001 {
9002  NODE *node = *body;
9003 
9004  if (!node) {
9005  *body = NEW_NIL();
9006  return;
9007  }
9008 #define subnodes(n1, n2) \
9009  ((!node->n1) ? (node->n2 ? (body = &node->n2, 1) : 0) : \
9010  (!node->n2) ? (body = &node->n1, 1) : \
9011  (reduce_nodes(&node->n1), body = &node->n2, 1))
9012 
9013  while (node) {
9014  int newline = (int)(node->flags & NODE_FL_NEWLINE);
9015  switch (nd_type(node)) {
9016  end:
9017  case NODE_NIL:
9018  *body = 0;
9019  return;
9020  case NODE_RETURN:
9021  *body = node = node->nd_stts;
9022  if (newline && node) node->flags |= NODE_FL_NEWLINE;
9023  continue;
9024  case NODE_BEGIN:
9025  *body = node = node->nd_body;
9026  if (newline && node) node->flags |= NODE_FL_NEWLINE;
9027  continue;
9028  case NODE_BLOCK:
9029  body = &node->nd_end->nd_head;
9030  break;
9031  case NODE_IF:
9032  if (subnodes(nd_body, nd_else)) break;
9033  return;
9034  case NODE_CASE:
9035  body = &node->nd_body;
9036  break;
9037  case NODE_WHEN:
9038  if (!subnodes(nd_body, nd_next)) goto end;
9039  break;
9040  case NODE_ENSURE:
9041  if (!subnodes(nd_head, nd_resq)) goto end;
9042  break;
9043  case NODE_RESCUE:
9044  if (node->nd_else) {
9045  body = &node->nd_resq;
9046  break;
9047  }
9048  if (!subnodes(nd_head, nd_resq)) goto end;
9049  break;
9050  default:
9051  return;
9052  }
9053  node = *body;
9054  if (newline && node) node->flags |= NODE_FL_NEWLINE;
9055  }
9056 
9057 #undef subnodes
9058 }
9059 
9060 static int
9061 is_static_content(NODE *node)
9062 {
9063  if (!node) return 1;
9064  switch (nd_type(node)) {
9065  case NODE_HASH:
9066  if (!(node = node->nd_head)) break;
9067  case NODE_ARRAY:
9068  do {
9069  if (!is_static_content(node->nd_head)) return 0;
9070  } while ((node = node->nd_next) != 0);
9071  case NODE_LIT:
9072  case NODE_STR:
9073  case NODE_NIL:
9074  case NODE_TRUE:
9075  case NODE_FALSE:
9076  case NODE_ZARRAY:
9077  break;
9078  default:
9079  return 0;
9080  }
9081  return 1;
9082 }
9083 
9084 static int
9085 assign_in_cond(struct parser_params *parser, NODE *node)
9086 {
9087  switch (nd_type(node)) {
9088  case NODE_MASGN:
9089  yyerror("multiple assignment in conditional");
9090  return 1;
9091 
9092  case NODE_LASGN:
9093  case NODE_DASGN:
9094  case NODE_DASGN_CURR:
9095  case NODE_GASGN:
9096  case NODE_IASGN:
9097  break;
9098 
9099  default:
9100  return 0;
9101  }
9102 
9103  if (!node->nd_value) return 1;
9104  if (is_static_content(node->nd_value)) {
9105  /* reports always */
9106  parser_warn(node->nd_value, "found = in conditional, should be ==");
9107  }
9108  return 1;
9109 }
9110 
9111 static void
9112 warn_unless_e_option(struct parser_params *parser, NODE *node, const char *str)
9113 {
9114  if (!e_option_supplied(parser)) parser_warn(node, str);
9115 }
9116 
9117 static void
9118 warning_unless_e_option(struct parser_params *parser, NODE *node, const char *str)
9119 {
9120  if (!e_option_supplied(parser)) parser_warning(node, str);
9121 }
9122 
9123 static void
9124 fixup_nodes(NODE **rootnode)
9125 {
9126  NODE *node, *next, *head;
9127 
9128  for (node = *rootnode; node; node = next) {
9129  enum node_type type;
9130  VALUE val;
9131 
9132  next = node->nd_next;
9133  head = node->nd_head;
9134  rb_gc_force_recycle((VALUE)node);
9135  *rootnode = next;
9136  switch (type = nd_type(head)) {
9137  case NODE_DOT2:
9138  case NODE_DOT3:
9139  val = rb_range_new(head->nd_beg->nd_lit, head->nd_end->nd_lit,
9140  type == NODE_DOT3);
9141  rb_gc_force_recycle((VALUE)head->nd_beg);
9142  rb_gc_force_recycle((VALUE)head->nd_end);
9143  nd_set_type(head, NODE_LIT);
9144  head->nd_lit = val;
9145  break;
9146  default:
9147  break;
9148  }
9149  }
9150 }
9151 
9152 static NODE *cond0(struct parser_params*,NODE*);
9153 
9154 static NODE*
9155 range_op(struct parser_params *parser, NODE *node)
9156 {
9157  enum node_type type;
9158 
9159  if (node == 0) return 0;
9160 
9161  type = nd_type(node);
9162  value_expr(node);
9163  if (type == NODE_LIT && FIXNUM_P(node->nd_lit)) {
9164  warn_unless_e_option(parser, node, "integer literal in conditional range");
9165  return NEW_CALL(node, tEQ, NEW_LIST(NEW_GVAR(rb_intern("$."))));
9166  }
9167  return cond0(parser, node);
9168 }
9169 
9170 static int
9171 literal_node(NODE *node)
9172 {
9173  if (!node) return 1; /* same as NODE_NIL */
9174  switch (nd_type(node)) {
9175  case NODE_LIT:
9176  case NODE_STR:
9177  case NODE_DSTR:
9178  case NODE_EVSTR:
9179  case NODE_DREGX:
9180  case NODE_DREGX_ONCE:
9181  case NODE_DSYM:
9182  return 2;
9183  case NODE_TRUE:
9184  case NODE_FALSE:
9185  case NODE_NIL:
9186  return 1;
9187  }
9188  return 0;
9189 }
9190 
9191 static NODE*
9192 cond0(struct parser_params *parser, NODE *node)
9193 {
9194  if (node == 0) return 0;
9195  assign_in_cond(parser, node);
9196 
9197  switch (nd_type(node)) {
9198  case NODE_DSTR:
9199  case NODE_EVSTR:
9200  case NODE_STR:
9201  rb_warn0("string literal in condition");
9202  break;
9203 
9204  case NODE_DREGX:
9205  case NODE_DREGX_ONCE:
9206  warning_unless_e_option(parser, node, "regex literal in condition");
9207  return NEW_MATCH2(node, NEW_GVAR(rb_intern("$_")));
9208 
9209  case NODE_AND:
9210  case NODE_OR:
9211  node->nd_1st = cond0(parser, node->nd_1st);
9212  node->nd_2nd = cond0(parser, node->nd_2nd);
9213  break;
9214 
9215  case NODE_DOT2:
9216  case NODE_DOT3:
9217  node->nd_beg = range_op(parser, node->nd_beg);
9218  node->nd_end = range_op(parser, node->nd_end);
9219  if (nd_type(node) == NODE_DOT2) nd_set_type(node,NODE_FLIP2);
9220  else if (nd_type(node) == NODE_DOT3) nd_set_type(node, NODE_FLIP3);
9221  if (!e_option_supplied(parser)) {
9222  int b = literal_node(node->nd_beg);
9223  int e = literal_node(node->nd_end);
9224  if ((b == 1 && e == 1) || (b + e >= 2 && RTEST(ruby_verbose))) {
9225  parser_warn(node, "range literal in condition");
9226  }
9227  }
9228  break;
9229 
9230  case NODE_DSYM:
9231  parser_warning(node, "literal in condition");
9232  break;
9233 
9234  case NODE_LIT:
9235  if (RB_TYPE_P(node->nd_lit, T_REGEXP)) {
9236  warn_unless_e_option(parser, node, "regex literal in condition");
9237  nd_set_type(node, NODE_MATCH);
9238  }
9239  else {
9240  parser_warning(node, "literal in condition");
9241  }
9242  default:
9243  break;
9244  }
9245  return node;
9246 }
9247 
9248 static NODE*
9249 cond_gen(struct parser_params *parser, NODE *node)
9250 {
9251  if (node == 0) return 0;
9252  return cond0(parser, node);
9253 }
9254 
9255 static NODE*
9256 logop_gen(struct parser_params *parser, enum node_type type, NODE *left, NODE *right)
9257 {
9258  value_expr(left);
9259  if (left && (enum node_type)nd_type(left) == type) {
9260  NODE *node = left, *second;
9261  while ((second = node->nd_2nd) != 0 && (enum node_type)nd_type(second) == type) {
9262  node = second;
9263  }
9264  node->nd_2nd = NEW_NODE(type, second, right, 0);
9265  return left;
9266  }
9267  return NEW_NODE(type, left, right, 0);
9268 }
9269 
9270 static void
9271 no_blockarg(struct parser_params *parser, NODE *node)
9272 {
9273  if (node && nd_type(node) == NODE_BLOCK_PASS) {
9274  compile_error(PARSER_ARG "block argument should not be given");
9275  }
9276 }
9277 
9278 static NODE *
9279 ret_args_gen(struct parser_params *parser, NODE *node)
9280 {
9281  if (node) {
9282  no_blockarg(parser, node);
9283  if (nd_type(node) == NODE_ARRAY) {
9284  if (node->nd_next == 0) {
9285  node = node->nd_head;
9286  }
9287  else {
9288  nd_set_type(node, NODE_VALUES);
9289  }
9290  }
9291  }
9292  return node;
9293 }
9294 
9295 static NODE *
9296 new_yield_gen(struct parser_params *parser, NODE *node)
9297 {
9298  if (node) no_blockarg(parser, node);
9299 
9300  return NEW_YIELD(node);
9301 }
9302 
9303 static NODE*
9304 negate_lit(NODE *node)
9305 {
9306  switch (TYPE(node->nd_lit)) {
9307  case T_FIXNUM:
9308  node->nd_lit = LONG2FIX(-FIX2LONG(node->nd_lit));
9309  break;
9310  case T_BIGNUM:
9311  node->nd_lit = rb_funcall(node->nd_lit,tUMINUS,0,0);
9312  break;
9313  case T_FLOAT:
9314 #if USE_FLONUM
9315  if (FLONUM_P(node->nd_lit)) {
9316  node->nd_lit = DBL2NUM(-RFLOAT_VALUE(node->nd_lit));
9317  }
9318  else {
9319  RFLOAT(node->nd_lit)->float_value = -RFLOAT_VALUE(node->nd_lit);
9320  }
9321 #else
9322  RFLOAT(node->nd_lit)->float_value = -RFLOAT_VALUE(node->nd_lit);
9323 #endif
9324  break;
9325  default:
9326  break;
9327  }
9328  return node;
9329 }
9330 
9331 static NODE *
9332 arg_blk_pass(NODE *node1, NODE *node2)
9333 {
9334  if (node2) {
9335  node2->nd_head = node1;
9336  return node2;
9337  }
9338  return node1;
9339 }
9340 
9341 
9342 static NODE*
9343 new_args_gen(struct parser_params *parser, NODE *m, NODE *o, ID r, NODE *p, NODE *tail)
9344 {
9345  int saved_line = ruby_sourceline;
9346  struct rb_args_info *args = tail->nd_ainfo;
9347 
9348  args->pre_args_num = m ? rb_long2int(m->nd_plen) : 0;
9349  args->pre_init = m ? m->nd_next : 0;
9350 
9351  args->post_args_num = p ? rb_long2int(p->nd_plen) : 0;
9352  args->post_init = p ? p->nd_next : 0;
9353  args->first_post_arg = p ? p->nd_pid : 0;
9354 
9355  args->rest_arg = r;
9356 
9357  args->opt_args = o;
9358 
9359  ruby_sourceline = saved_line;
9360 
9361  return tail;
9362 }
9363 
9364 static NODE*
9365 new_args_tail_gen(struct parser_params *parser, NODE *k, ID kr, ID b)
9366 {
9367  int saved_line = ruby_sourceline;
9368  struct rb_args_info *args;
9369  NODE *kw_rest_arg = 0;
9370  NODE *node;
9371 
9372  args = ALLOC(struct rb_args_info);
9373  MEMZERO(args, struct rb_args_info, 1);
9374  node = NEW_NODE(NODE_ARGS, 0, 0, args);
9375 
9376  args->block_arg = b;
9377  args->kw_args = k;
9378  if (k && !kr) kr = internal_id();
9379  if (kr) {
9380  arg_var(kr);
9381  kw_rest_arg = NEW_DVAR(kr);
9382  }
9383  args->kw_rest_arg = kw_rest_arg;
9384 
9385  ruby_sourceline = saved_line;
9386  return node;
9387 }
9388 
9389 static NODE*
9390 dsym_node_gen(struct parser_params *parser, NODE *node)
9391 {
9392  VALUE lit;
9393 
9394  if (!node) {
9395  return NEW_LIT(ID2SYM(idNULL));
9396  }
9397 
9398  switch (nd_type(node)) {
9399  case NODE_DSTR:
9400  nd_set_type(node, NODE_DSYM);
9401  break;
9402  case NODE_STR:
9403  lit = node->nd_lit;
9404  node->nd_lit = ID2SYM(rb_intern_str(lit));
9405  nd_set_type(node, NODE_LIT);
9406  break;
9407  default:
9408  node = NEW_NODE(NODE_DSYM, Qnil, 1, NEW_LIST(node));
9409  break;
9410  }
9411  return node;
9412 }
9413 #endif /* !RIPPER */
9414 
9415 #ifndef RIPPER
9416 static NODE *
9417 new_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs)
9418 {
9419  NODE *asgn;
9420 
9421  if (lhs) {
9422  ID vid = lhs->nd_vid;
9423  if (op == tOROP) {
9424  lhs->nd_value = rhs;
9425  asgn = NEW_OP_ASGN_OR(gettable(vid), lhs);
9426  if (is_asgn_or_id(vid)) {
9427  asgn->nd_aid = vid;
9428  }
9429  }
9430  else if (op == tANDOP) {
9431  lhs->nd_value = rhs;
9432  asgn = NEW_OP_ASGN_AND(gettable(vid), lhs);
9433  }
9434  else {
9435  asgn = lhs;
9436  asgn->nd_value = NEW_CALL(gettable(vid), op, NEW_LIST(rhs));
9437  }
9438  }
9439  else {
9440  asgn = NEW_BEGIN(0);
9441  }
9442  return asgn;
9443 }
9444 
9445 static NODE *
9446 new_attr_op_assign_gen(struct parser_params *parser, NODE *lhs, ID attr, ID op, NODE *rhs)
9447 {
9448  NODE *asgn;
9449 
9450  if (op == tOROP) {
9451  op = 0;
9452  }
9453  else if (op == tANDOP) {
9454  op = 1;
9455  }
9456  asgn = NEW_OP_ASGN2(lhs, attr, op, rhs);
9457  fixpos(asgn, lhs);
9458  return asgn;
9459 }
9460 
9461 static NODE *
9462 new_const_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs)
9463 {
9464  NODE *asgn;
9465 
9466  if (op == tOROP) {
9467  op = 0;
9468  }
9469  else if (op == tANDOP) {
9470  op = 1;
9471  }
9472  if (lhs) {
9473  asgn = NEW_OP_CDECL(lhs, op, rhs);
9474  }
9475  else {
9476  asgn = NEW_BEGIN(0);
9477  }
9478  fixpos(asgn, lhs);
9479  return asgn;
9480 }
9481 #else
9482 static VALUE
9483 new_op_assign_gen(struct parser_params *parser, VALUE lhs, VALUE op, VALUE rhs)
9484 {
9485  return dispatch3(opassign, lhs, op, rhs);
9486 }
9487 
9488 static VALUE
9489 new_attr_op_assign_gen(struct parser_params *parser, VALUE lhs, VALUE type, VALUE attr, VALUE op, VALUE rhs)
9490 {
9491  VALUE recv = dispatch3(field, lhs, type, attr);
9492  return dispatch3(opassign, recv, op, rhs);
9493 }
9494 #endif
9495 
9496 static void
9497 warn_unused_var(struct parser_params *parser, struct local_vars *local)
9498 {
9499  int i, cnt;
9500  ID *v, *u;
9501 
9502  if (!local->used) return;
9503  v = local->vars->tbl;
9504  u = local->used->tbl;
9505  cnt = local->used->pos;
9506  if (cnt != local->vars->pos) {
9507  rb_bug("local->used->pos != local->vars->pos");
9508  }
9509  for (i = 0; i < cnt; ++i) {
9510  if (!v[i] || (u[i] & LVAR_USED)) continue;
9511  if (is_private_local_id(v[i])) continue;
9512  rb_warn4S(ruby_sourcefile, (int)u[i], "assigned but unused variable - %s", rb_id2name(v[i]));
9513  }
9514 }
9515 
9516 static void
9517 local_push_gen(struct parser_params *parser, int inherit_dvars)
9518 {
9519  struct local_vars *local;
9520 
9521  local = ALLOC(struct local_vars);
9522  local->prev = lvtbl;
9523  local->args = vtable_alloc(0);
9524  local->vars = vtable_alloc(inherit_dvars ? DVARS_INHERIT : DVARS_TOPSCOPE);
9525  local->used = !(inherit_dvars &&
9527  RTEST(ruby_verbose) ? vtable_alloc(0) : 0;
9528  local->cmdargs = cmdarg_stack;
9529  cmdarg_stack = 0;
9530  lvtbl = local;
9531 }
9532 
9533 static void
9534 local_pop_gen(struct parser_params *parser)
9535 {
9536  struct local_vars *local = lvtbl->prev;
9537  if (lvtbl->used) {
9538  warn_unused_var(parser, lvtbl);
9539  vtable_free(lvtbl->used);
9540  }
9541  vtable_free(lvtbl->args);
9542  vtable_free(lvtbl->vars);
9543  cmdarg_stack = lvtbl->cmdargs;
9544  xfree(lvtbl);
9545  lvtbl = local;
9546 }
9547 
9548 #ifndef RIPPER
9549 static ID*
9550 vtable_tblcpy(ID *buf, const struct vtable *src)
9551 {
9552  int i, cnt = vtable_size(src);
9553 
9554  if (cnt > 0) {
9555  buf[0] = cnt;
9556  for (i = 0; i < cnt; i++) {
9557  buf[i] = src->tbl[i];
9558  }
9559  return buf;
9560  }
9561  return 0;
9562 }
9563 
9564 static ID*
9565 local_tbl_gen(struct parser_params *parser)
9566 {
9567  int cnt = vtable_size(lvtbl->args) + vtable_size(lvtbl->vars);
9568  ID *buf;
9569 
9570  if (cnt <= 0) return 0;
9571  buf = ALLOC_N(ID, cnt + 1);
9572  vtable_tblcpy(buf+1, lvtbl->args);
9573  vtable_tblcpy(buf+vtable_size(lvtbl->args)+1, lvtbl->vars);
9574  buf[0] = cnt;
9575  return buf;
9576 }
9577 #endif
9578 
9579 static int
9580 arg_var_gen(struct parser_params *parser, ID id)
9581 {
9582  vtable_add(lvtbl->args, id);
9583  return vtable_size(lvtbl->args) - 1;
9584 }
9585 
9586 static int
9587 local_var_gen(struct parser_params *parser, ID id)
9588 {
9589  vtable_add(lvtbl->vars, id);
9590  if (lvtbl->used) {
9592  }
9593  return vtable_size(lvtbl->vars) - 1;
9594 }
9595 
9596 static int
9597 local_id_gen(struct parser_params *parser, ID id)
9598 {
9599  struct vtable *vars, *args, *used;
9600 
9601  vars = lvtbl->vars;
9602  args = lvtbl->args;
9603  used = lvtbl->used;
9604 
9605  while (vars && POINTER_P(vars->prev)) {
9606  vars = vars->prev;
9607  args = args->prev;
9608  if (used) used = used->prev;
9609  }
9610 
9611  if (vars && vars->prev == DVARS_INHERIT) {
9612  return rb_local_defined(id);
9613  }
9614  else if (vtable_included(args, id)) {
9615  return 1;
9616  }
9617  else {
9618  int i = vtable_included(vars, id);
9619  if (i && used) used->tbl[i-1] |= LVAR_USED;
9620  return i != 0;
9621  }
9622 }
9623 
9624 static const struct vtable *
9625 dyna_push_gen(struct parser_params *parser)
9626 {
9627  lvtbl->args = vtable_alloc(lvtbl->args);
9628  lvtbl->vars = vtable_alloc(lvtbl->vars);
9629  if (lvtbl->used) {
9630  lvtbl->used = vtable_alloc(lvtbl->used);
9631  }
9632  return lvtbl->args;
9633 }
9634 
9635 static void
9636 dyna_pop_1(struct parser_params *parser)
9637 {
9638  struct vtable *tmp;
9639 
9640  if ((tmp = lvtbl->used) != 0) {
9641  warn_unused_var(parser, lvtbl);
9642  lvtbl->used = lvtbl->used->prev;
9643  vtable_free(tmp);
9644  }
9645  tmp = lvtbl->args;
9646  lvtbl->args = lvtbl->args->prev;
9647  vtable_free(tmp);
9648  tmp = lvtbl->vars;
9649  lvtbl->vars = lvtbl->vars->prev;
9650  vtable_free(tmp);
9651 }
9652 
9653 static void
9654 dyna_pop_gen(struct parser_params *parser, const struct vtable *lvargs)
9655 {
9656  while (lvtbl->args != lvargs) {
9657  dyna_pop_1(parser);
9658  if (!lvtbl->args) {
9659  struct local_vars *local = lvtbl->prev;
9660  xfree(lvtbl);
9661  lvtbl = local;
9662  }
9663  }
9664  dyna_pop_1(parser);
9665 }
9666 
9667 static int
9668 dyna_in_block_gen(struct parser_params *parser)
9669 {
9670  return POINTER_P(lvtbl->vars) && lvtbl->vars->prev != DVARS_TOPSCOPE;
9671 }
9672 
9673 static int
9674 dvar_defined_gen(struct parser_params *parser, ID id, int get)
9675 {
9676  struct vtable *vars, *args, *used;
9677  int i;
9678 
9679  args = lvtbl->args;
9680  vars = lvtbl->vars;
9681  used = lvtbl->used;
9682 
9683  while (POINTER_P(vars)) {
9684  if (vtable_included(args, id)) {
9685  return 1;
9686  }
9687  if ((i = vtable_included(vars, id)) != 0) {
9688  if (used) used->tbl[i-1] |= LVAR_USED;
9689  return 1;
9690  }
9691  args = args->prev;
9692  vars = vars->prev;
9693  if (get) used = 0;
9694  if (used) used = used->prev;
9695  }
9696 
9697  if (vars == DVARS_INHERIT) {
9698  return rb_dvar_defined(id);
9699  }
9700 
9701  return 0;
9702 }
9703 
9704 static int
9705 dvar_curr_gen(struct parser_params *parser, ID id)
9706 {
9707  return (vtable_included(lvtbl->args, id) ||
9708  vtable_included(lvtbl->vars, id));
9709 }
9710 
9711 #ifndef RIPPER
9712 static void
9713 reg_fragment_setenc_gen(struct parser_params* parser, VALUE str, int options)
9714 {
9715  int c = RE_OPTION_ENCODING_IDX(options);
9716 
9717  if (c) {
9718  int opt, idx;
9719  rb_char_to_option_kcode(c, &opt, &idx);
9720  if (idx != ENCODING_GET(str) &&
9722  goto error;
9723  }
9724  ENCODING_SET(str, idx);
9725  }
9726  else if (RE_OPTION_ENCODING_NONE(options)) {
9727  if (!ENCODING_IS_ASCII8BIT(str) &&
9729  c = 'n';
9730  goto error;
9731  }
9733  }
9734  else if (current_enc == rb_usascii_encoding()) {
9736  /* raise in re.c */
9738  }
9739  else {
9741  }
9742  }
9743  return;
9744 
9745  error:
9747  "regexp encoding option '%c' differs from source encoding '%s'",
9748  c, rb_enc_name(rb_enc_get(str)));
9749 }
9750 
9751 static int
9752 reg_fragment_check_gen(struct parser_params* parser, VALUE str, int options)
9753 {
9754  VALUE err;
9755  reg_fragment_setenc(str, options);
9756  err = rb_reg_check_preprocess(str);
9757  if (err != Qnil) {
9758  err = rb_obj_as_string(err);
9759  compile_error(PARSER_ARG "%s", RSTRING_PTR(err));
9760  RB_GC_GUARD(err);
9761  return 0;
9762  }
9763  return 1;
9764 }
9765 
9766 typedef struct {
9767  struct parser_params* parser;
9768  rb_encoding *enc;
9769  NODE *succ_block;
9770  NODE *fail_block;
9771  int num;
9773 
9774 static int
9775 reg_named_capture_assign_iter(const OnigUChar *name, const OnigUChar *name_end,
9776  int back_num, int *back_refs, OnigRegex regex, void *arg0)
9777 {
9779  struct parser_params* parser = arg->parser;
9780  rb_encoding *enc = arg->enc;
9781  long len = name_end - name;
9782  const char *s = (const char *)name;
9783  ID var;
9784 
9785  arg->num++;
9786 
9787  if (arg->succ_block == 0) {
9788  arg->succ_block = NEW_BEGIN(0);
9789  arg->fail_block = NEW_BEGIN(0);
9790  }
9791 
9792  if (!len || (*name != '_' && ISASCII(*name) && !rb_enc_islower(*name, enc)) ||
9793  (len < MAX_WORD_LENGTH && rb_reserved_word(s, (int)len)) ||
9794  !rb_enc_symname2_p(s, len, enc)) {
9795  return ST_CONTINUE;
9796  }
9797  var = rb_intern3(s, len, enc);
9798  if (dvar_defined(var) || local_id(var)) {
9799  rb_warningS("named capture conflicts a local variable - %s",
9800  rb_id2name(var));
9801  }
9802  arg->succ_block = block_append(arg->succ_block,
9804  NEW_CALL(
9805  gettable(rb_intern("$~")),
9806  idAREF,
9807  NEW_LIST(NEW_LIT(ID2SYM(var))))
9808  )));
9809  arg->fail_block = block_append(arg->fail_block,
9811  return ST_CONTINUE;
9812 }
9813 
9814 static NODE *
9815 reg_named_capture_assign_gen(struct parser_params* parser, VALUE regexp, NODE *match)
9816 {
9818 
9819  arg.parser = parser;
9820  arg.enc = rb_enc_get(regexp);
9821  arg.succ_block = 0;
9822  arg.fail_block = 0;
9823  arg.num = 0;
9824  onig_foreach_name(RREGEXP(regexp)->ptr, reg_named_capture_assign_iter, (void*)&arg);
9825 
9826  if (arg.num == 0)
9827  return match;
9828 
9829  return
9830  block_append(
9831  newline_node(match),
9832  NEW_IF(gettable(rb_intern("$~")),
9833  block_append(
9834  newline_node(arg.succ_block),
9835  newline_node(
9836  NEW_CALL(
9837  gettable(rb_intern("$~")),
9838  rb_intern("begin"),
9839  NEW_LIST(NEW_LIT(INT2FIX(0)))))),
9840  block_append(
9841  newline_node(arg.fail_block),
9842  newline_node(
9843  NEW_LIT(Qnil)))));
9844 }
9845 
9846 static VALUE
9847 reg_compile_gen(struct parser_params* parser, VALUE str, int options)
9848 {
9849  VALUE re;
9850  VALUE err;
9851 
9852  reg_fragment_setenc(str, options);
9853  err = rb_errinfo();
9854  re = rb_reg_compile(str, options & RE_OPTION_MASK, ruby_sourcefile, ruby_sourceline);
9855  if (NIL_P(re)) {
9856  ID mesg = rb_intern("mesg");
9857  VALUE m = rb_attr_get(rb_errinfo(), mesg);
9858  rb_set_errinfo(err);
9859  if (!NIL_P(err)) {
9860  rb_str_append(rb_str_cat(rb_attr_get(err, mesg), "\n", 1), m);
9861  }
9862  else {
9864  }
9865  return Qnil;
9866  }
9867  return re;
9868 }
9869 
9870 void
9871 rb_gc_mark_parser(void)
9872 {
9873 }
9874 
9875 NODE*
9876 rb_parser_append_print(VALUE vparser, NODE *node)
9877 {
9878  NODE *prelude = 0;
9879  NODE *scope = node;
9880  struct parser_params *parser;
9881 
9882  if (!node) return node;
9883 
9884  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
9885 
9886  node = node->nd_body;
9887 
9888  if (nd_type(node) == NODE_PRELUDE) {
9889  prelude = node;
9890  node = node->nd_body;
9891  }
9892 
9893  node = block_append(node,
9894  NEW_FCALL(rb_intern("print"),
9895  NEW_ARRAY(NEW_GVAR(rb_intern("$_")))));
9896  if (prelude) {
9897  prelude->nd_body = node;
9898  scope->nd_body = prelude;
9899  }
9900  else {
9901  scope->nd_body = node;
9902  }
9903 
9904  return scope;
9905 }
9906 
9907 NODE *
9908 rb_parser_while_loop(VALUE vparser, NODE *node, int chop, int split)
9909 {
9910  NODE *prelude = 0;
9911  NODE *scope = node;
9912  struct parser_params *parser;
9913 
9914  if (!node) return node;
9915 
9916  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
9917 
9918  node = node->nd_body;
9919 
9920  if (nd_type(node) == NODE_PRELUDE) {
9921  prelude = node;
9922  node = node->nd_body;
9923  }
9924  if (split) {
9925  node = block_append(NEW_GASGN(rb_intern("$F"),
9926  NEW_CALL(NEW_GVAR(rb_intern("$_")),
9927  rb_intern("split"), 0)),
9928  node);
9929  }
9930  if (chop) {
9931  node = block_append(NEW_CALL(NEW_GVAR(rb_intern("$_")),
9932  rb_intern("chop!"), 0), node);
9933  }
9934 
9935  node = NEW_OPT_N(node);
9936 
9937  if (prelude) {
9938  prelude->nd_body = node;
9939  scope->nd_body = prelude;
9940  }
9941  else {
9942  scope->nd_body = node;
9943  }
9944 
9945  return scope;
9946 }
9947 
9948 static const struct {
9949  ID token;
9950  const char *name;
9951 } op_tbl[] = {
9952  {tDOT2, ".."},
9953  {tDOT3, "..."},
9954  {tPOW, "**"},
9955  {tDSTAR, "**"},
9956  {tUPLUS, "+@"},
9957  {tUMINUS, "-@"},
9958  {tCMP, "<=>"},
9959  {tGEQ, ">="},
9960  {tLEQ, "<="},
9961  {tEQ, "=="},
9962  {tEQQ, "==="},
9963  {tNEQ, "!="},
9964  {tMATCH, "=~"},
9965  {tNMATCH, "!~"},
9966  {tAREF, "[]"},
9967  {tASET, "[]="},
9968  {tLSHFT, "<<"},
9969  {tRSHFT, ">>"},
9970  {tCOLON2, "::"},
9971 };
9972 
9973 #define op_tbl_count numberof(op_tbl)
9974 
9975 #ifndef ENABLE_SELECTOR_NAMESPACE
9976 #define ENABLE_SELECTOR_NAMESPACE 0
9977 #endif
9978 
9979 static struct symbols {
9980  ID last_id;
9981  st_table *sym_id;
9982  st_table *id_str;
9983 #if ENABLE_SELECTOR_NAMESPACE
9984  st_table *ivar2_id;
9985  st_table *id_ivar2;
9986 #endif
9989 
9990 static const struct st_hash_type symhash = {
9992  rb_str_hash,
9993 };
9994 
9995 #if ENABLE_SELECTOR_NAMESPACE
9996 struct ivar2_key {
9997  ID id;
9998  VALUE klass;
9999 };
10000 
10001 static int
10002 ivar2_cmp(struct ivar2_key *key1, struct ivar2_key *key2)
10003 {
10004  if (key1->id == key2->id && key1->klass == key2->klass) {
10005  return 0;
10006  }
10007  return 1;
10008 }
10009 
10010 static int
10011 ivar2_hash(struct ivar2_key *key)
10012 {
10013  return (key->id << 8) ^ (key->klass >> 2);
10014 }
10015 
10016 static const struct st_hash_type ivar2_hash_type = {
10017  ivar2_cmp,
10018  ivar2_hash,
10019 };
10020 #endif
10021 
10022 void
10023 Init_sym(void)
10024 {
10025  global_symbols.sym_id = st_init_table_with_size(&symhash, 1000);
10027 #if ENABLE_SELECTOR_NAMESPACE
10028  global_symbols.ivar2_id = st_init_table_with_size(&ivar2_hash_type, 1000);
10029  global_symbols.id_ivar2 = st_init_numtable_with_size(1000);
10030 #endif
10031 
10032  (void)nodetype;
10033  (void)nodeline;
10034 #if PARSER_DEBUG
10035  (void)lex_state_name(-1);
10036 #endif
10037 
10038  Init_id();
10039 }
10040 
10041 void
10042 rb_gc_mark_symbols(void)
10043 {
10047 }
10048 #endif /* !RIPPER */
10049 
10050 static ID
10051 internal_id_gen(struct parser_params *parser)
10052 {
10053  ID id = (ID)vtable_size(lvtbl->args) + (ID)vtable_size(lvtbl->vars);
10054  id += ((tLAST_TOKEN - ID_INTERNAL) >> ID_SCOPE_SHIFT) + 1;
10055  return ID_INTERNAL | (id << ID_SCOPE_SHIFT);
10056 }
10057 
10058 #ifndef RIPPER
10059 static int
10060 is_special_global_name(const char *m, const char *e, rb_encoding *enc)
10061 {
10062  int mb = 0;
10063 
10064  if (m >= e) return 0;
10065  if (is_global_name_punct(*m)) {
10066  ++m;
10067  }
10068  else if (*m == '-') {
10069  ++m;
10070  if (m < e && is_identchar(m, e, enc)) {
10071  if (!ISASCII(*m)) mb = 1;
10072  m += rb_enc_mbclen(m, e, enc);
10073  }
10074  }
10075  else {
10076  if (!rb_enc_isdigit(*m, enc)) return 0;
10077  do {
10078  if (!ISASCII(*m)) mb = 1;
10079  ++m;
10080  } while (m < e && rb_enc_isdigit(*m, enc));
10081  }
10082  return m == e ? mb + 1 : 0;
10083 }
10084 
10085 int
10086 rb_symname_p(const char *name)
10087 {
10088  return rb_enc_symname_p(name, rb_ascii8bit_encoding());
10089 }
10090 
10091 int
10092 rb_enc_symname_p(const char *name, rb_encoding *enc)
10093 {
10094  return rb_enc_symname2_p(name, strlen(name), enc);
10095 }
10096 
10097 #define IDSET_ATTRSET_FOR_SYNTAX ((1U<<ID_LOCAL)|(1U<<ID_CONST))
10098 #define IDSET_ATTRSET_FOR_INTERN (~(~0U<<(1<<ID_SCOPE_SHIFT)) & ~(1U<<ID_ATTRSET))
10099 
10100 static int
10101 rb_enc_symname_type(const char *name, long len, rb_encoding *enc, unsigned int allowed_atttset)
10102 {
10103  const char *m = name;
10104  const char *e = m + len;
10105  int type = ID_JUNK;
10106 
10107  if (!m || len <= 0) return -1;
10108  switch (*m) {
10109  case '\0':
10110  return -1;
10111 
10112  case '$':
10113  type = ID_GLOBAL;
10114  if (is_special_global_name(++m, e, enc)) return type;
10115  goto id;
10116 
10117  case '@':
10118  type = ID_INSTANCE;
10119  if (*++m == '@') {
10120  ++m;
10121  type = ID_CLASS;
10122  }
10123  goto id;
10124 
10125  case '<':
10126  switch (*++m) {
10127  case '<': ++m; break;
10128  case '=': if (*++m == '>') ++m; break;
10129  default: break;
10130  }
10131  break;
10132 
10133  case '>':
10134  switch (*++m) {
10135  case '>': case '=': ++m; break;
10136  }
10137  break;
10138 
10139  case '=':
10140  switch (*++m) {
10141  case '~': ++m; break;
10142  case '=': if (*++m == '=') ++m; break;
10143  default: return -1;
10144  }
10145  break;
10146 
10147  case '*':
10148  if (*++m == '*') ++m;
10149  break;
10150 
10151  case '+': case '-':
10152  if (*++m == '@') ++m;
10153  break;
10154 
10155  case '|': case '^': case '&': case '/': case '%': case '~': case '`':
10156  ++m;
10157  break;
10158 
10159  case '[':
10160  if (*++m != ']') return -1;
10161  if (*++m == '=') ++m;
10162  break;
10163 
10164  case '!':
10165  if (len == 1) return ID_JUNK;
10166  switch (*++m) {
10167  case '=': case '~': ++m; break;
10168  default: return -1;
10169  }
10170  break;
10171 
10172  default:
10173  type = rb_enc_isupper(*m, enc) ? ID_CONST : ID_LOCAL;
10174  id:
10175  if (m >= e || (*m != '_' && !rb_enc_isalpha(*m, enc) && ISASCII(*m)))
10176  return -1;
10177  while (m < e && is_identchar(m, e, enc)) m += rb_enc_mbclen(m, e, enc);
10178  if (m >= e) break;
10179  switch (*m) {
10180  case '!': case '?':
10181  if (type == ID_GLOBAL || type == ID_CLASS || type == ID_INSTANCE) return -1;
10182  type = ID_JUNK;
10183  ++m;
10184  if (m + 1 < e || *m != '=') break;
10185  /* fall through */
10186  case '=':
10187  if (!(allowed_atttset & (1U << type))) return -1;
10188  type = ID_ATTRSET;
10189  ++m;
10190  break;
10191  }
10192  break;
10193  }
10194  return m == e ? type : -1;
10195 }
10196 
10197 int
10198 rb_enc_symname2_p(const char *name, long len, rb_encoding *enc)
10199 {
10200  return rb_enc_symname_type(name, len, enc, IDSET_ATTRSET_FOR_SYNTAX) != -1;
10201 }
10202 
10203 static int
10204 rb_str_symname_type(VALUE name, unsigned int allowed_atttset)
10205 {
10206  const char *ptr = StringValuePtr(name);
10207  long len = RSTRING_LEN(name);
10208  int type = rb_enc_symname_type(ptr, len, rb_enc_get(name), allowed_atttset);
10209  RB_GC_GUARD(name);
10210  return type;
10211 }
10212 
10213 static ID
10214 register_symid(ID id, const char *name, long len, rb_encoding *enc)
10215 {
10216  VALUE str = rb_enc_str_new(name, len, enc);
10217  return register_symid_str(id, str);
10218 }
10219 
10220 static ID
10221 register_symid_str(ID id, VALUE str)
10222 {
10223  OBJ_FREEZE(str);
10226  return id;
10227 }
10228 
10229 static int
10231 {
10232  if (!rb_enc_asciicompat(rb_enc_get(str))) return FALSE;
10233  switch (rb_enc_str_coderange(str)) {
10234  case ENC_CODERANGE_BROKEN:
10235  rb_raise(rb_eEncodingError, "invalid encoding symbol");
10236  case ENC_CODERANGE_7BIT:
10237  return TRUE;
10238  }
10239  return FALSE;
10240 }
10241 
10242 /*
10243  * _str_ itself will be registered at the global symbol table. _str_
10244  * can be modified before the registration, since the encoding will be
10245  * set to ASCII-8BIT if it is a special global name.
10246  */
10247 static ID intern_str(VALUE str);
10248 
10249 ID
10250 rb_intern3(const char *name, long len, rb_encoding *enc)
10251 {
10252  VALUE str;
10253  st_data_t data;
10254  struct RString fake_str;
10255  fake_str.basic.flags = T_STRING|RSTRING_NOEMBED;
10256  fake_str.basic.klass = rb_cString;
10257  fake_str.as.heap.len = len;
10258  fake_str.as.heap.ptr = (char *)name;
10259  fake_str.as.heap.aux.capa = len;
10260  str = (VALUE)&fake_str;
10261  rb_enc_associate(str, enc);
10262  OBJ_FREEZE(str);
10263 
10264  if (st_lookup(global_symbols.sym_id, str, &data))
10265  return (ID)data;
10266 
10267  str = rb_enc_str_new(name, len, enc); /* make true string */
10268  return intern_str(str);
10269 }
10270 
10271 static ID
10272 intern_str(VALUE str)
10273 {
10274  const char *name, *m, *e;
10275  long len, last;
10276  rb_encoding *enc, *symenc;
10277  unsigned char c;
10278  ID id;
10279  int mb;
10280 
10281  RSTRING_GETMEM(str, name, len);
10282  m = name;
10283  e = m + len;
10284  enc = rb_enc_get(str);
10285  symenc = enc;
10286 
10287  if (!len || (rb_cString && !rb_enc_asciicompat(enc))) {
10288  junk:
10289  id = ID_JUNK;
10290  goto new_id;
10291  }
10292  last = len-1;
10293  id = 0;
10294  switch (*m) {
10295  case '$':
10296  if (len < 2) goto junk;
10297  id |= ID_GLOBAL;
10298  if ((mb = is_special_global_name(++m, e, enc)) != 0) {
10299  if (!--mb) symenc = rb_usascii_encoding();
10300  goto new_id;
10301  }
10302  break;
10303  case '@':
10304  if (m[1] == '@') {
10305  if (len < 3) goto junk;
10306  m++;
10307  id |= ID_CLASS;
10308  }
10309  else {
10310  if (len < 2) goto junk;
10311  id |= ID_INSTANCE;
10312  }
10313  m++;
10314  break;
10315  default:
10316  c = m[0];
10317  if (c != '_' && rb_enc_isascii(c, enc) && rb_enc_ispunct(c, enc)) {
10318  /* operators */
10319  int i;
10320 
10321  if (len == 1) {
10322  id = c;
10323  goto id_register;
10324  }
10325  for (i = 0; i < op_tbl_count; i++) {
10326  if (*op_tbl[i].name == *m &&
10327  strcmp(op_tbl[i].name, m) == 0) {
10328  id = op_tbl[i].token;
10329  goto id_register;
10330  }
10331  }
10332  }
10333  break;
10334  }
10335  if (name[last] == '=') {
10336  /* attribute assignment */
10337  if (last > 1 && name[last-1] == '=')
10338  goto junk;
10339  id = rb_intern3(name, last, enc);
10340  if (id > tLAST_OP_ID && !is_attrset_id(id)) {
10341  enc = rb_enc_get(rb_id2str(id));
10342  id = rb_id_attrset(id);
10343  goto id_register;
10344  }
10345  id = ID_ATTRSET;
10346  }
10347  else if (id == 0) {
10348  if (rb_enc_isupper(m[0], enc)) {
10349  id = ID_CONST;
10350  }
10351  else {
10352  id = ID_LOCAL;
10353  }
10354  }
10355  if (!rb_enc_isdigit(*m, enc)) {
10356  while (m <= name + last && is_identchar(m, e, enc)) {
10357  if (ISASCII(*m)) {
10358  m++;
10359  }
10360  else {
10361  m += rb_enc_mbclen(m, e, enc);
10362  }
10363  }
10364  }
10365  if (id != ID_ATTRSET && m - name < len) id = ID_JUNK;
10366  if (sym_check_asciionly(str)) symenc = rb_usascii_encoding();
10367  new_id:
10368  if (symenc != enc) rb_enc_associate(str, symenc);
10370  if (len > 20) {
10371  rb_raise(rb_eRuntimeError, "symbol table overflow (symbol %.20s...)",
10372  name);
10373  }
10374  else {
10375  rb_raise(rb_eRuntimeError, "symbol table overflow (symbol %.*s)",
10376  (int)len, name);
10377  }
10378  }
10380  id_register:
10381  return register_symid_str(id, str);
10382 }
10383 
10384 ID
10385 rb_intern2(const char *name, long len)
10386 {
10387  return rb_intern3(name, len, rb_usascii_encoding());
10388 }
10389 
10390 #undef rb_intern
10391 ID
10392 rb_intern(const char *name)
10393 {
10394  return rb_intern2(name, strlen(name));
10395 }
10396 
10397 ID
10398 rb_intern_str(VALUE str)
10399 {
10400  st_data_t id;
10401 
10402  if (st_lookup(global_symbols.sym_id, str, &id))
10403  return (ID)id;
10404  return intern_str(rb_str_dup(str));
10405 }
10406 
10407 VALUE
10408 rb_id2str(ID id)
10409 {
10410  st_data_t data;
10411 
10412  if (id < tLAST_TOKEN) {
10413  int i = 0;
10414 
10415  if (id < INT_MAX && rb_ispunct((int)id)) {
10416  VALUE str = global_symbols.op_sym[i = (int)id];
10417  if (!str) {
10418  char name[2];
10419  name[0] = (char)id;
10420  name[1] = 0;
10421  str = rb_usascii_str_new(name, 1);
10422  OBJ_FREEZE(str);
10423  global_symbols.op_sym[i] = str;
10424  }
10425  return str;
10426  }
10427  for (i = 0; i < op_tbl_count; i++) {
10428  if (op_tbl[i].token == id) {
10429  VALUE str = global_symbols.op_sym[i];
10430  if (!str) {
10431  str = rb_usascii_str_new2(op_tbl[i].name);
10432  OBJ_FREEZE(str);
10433  global_symbols.op_sym[i] = str;
10434  }
10435  return str;
10436  }
10437  }
10438  }
10439 
10440  if (st_lookup(global_symbols.id_str, id, &data)) {
10441  VALUE str = (VALUE)data;
10442  if (RBASIC(str)->klass == 0)
10443  RBASIC(str)->klass = rb_cString;
10444  return str;
10445  }
10446 
10447  if (is_attrset_id(id)) {
10448  ID id_stem = (id & ~ID_SCOPE_MASK);
10449  VALUE str;
10450 
10451  do {
10452  if (!!(str = rb_id2str(id_stem | ID_LOCAL))) break;
10453  if (!!(str = rb_id2str(id_stem | ID_CONST))) break;
10454  if (!!(str = rb_id2str(id_stem | ID_INSTANCE))) break;
10455  if (!!(str = rb_id2str(id_stem | ID_GLOBAL))) break;
10456  if (!!(str = rb_id2str(id_stem | ID_CLASS))) break;
10457  if (!!(str = rb_id2str(id_stem | ID_JUNK))) break;
10458  return 0;
10459  } while (0);
10460  str = rb_str_dup(str);
10461  rb_str_cat(str, "=", 1);
10462  register_symid_str(id, str);
10463  if (st_lookup(global_symbols.id_str, id, &data)) {
10464  VALUE str = (VALUE)data;
10465  if (RBASIC(str)->klass == 0)
10466  RBASIC(str)->klass = rb_cString;
10467  return str;
10468  }
10469  }
10470  return 0;
10471 }
10472 
10473 const char *
10474 rb_id2name(ID id)
10475 {
10476  VALUE str = rb_id2str(id);
10477 
10478  if (!str) return 0;
10479  return RSTRING_PTR(str);
10480 }
10481 
10482 static int
10483 symbols_i(VALUE sym, ID value, VALUE ary)
10484 {
10485  rb_ary_push(ary, ID2SYM(value));
10486  return ST_CONTINUE;
10487 }
10488 
10489 /*
10490  * call-seq:
10491  * Symbol.all_symbols => array
10492  *
10493  * Returns an array of all the symbols currently in Ruby's symbol
10494  * table.
10495  *
10496  * Symbol.all_symbols.size #=> 903
10497  * Symbol.all_symbols[1,20] #=> [:floor, :ARGV, :Binding, :symlink,
10498  * :chown, :EOFError, :$;, :String,
10499  * :LOCK_SH, :"setuid?", :$<,
10500  * :default_proc, :compact, :extend,
10501  * :Tms, :getwd, :$=, :ThreadGroup,
10502  * :wait2, :$>]
10503  */
10504 
10505 VALUE
10506 rb_sym_all_symbols(void)
10507 {
10509 
10511  return ary;
10512 }
10513 
10514 int
10515 rb_is_const_id(ID id)
10516 {
10517  return is_const_id(id);
10518 }
10519 
10520 int
10521 rb_is_class_id(ID id)
10522 {
10523  return is_class_id(id);
10524 }
10525 
10526 int
10527 rb_is_global_id(ID id)
10528 {
10529  return is_global_id(id);
10530 }
10531 
10532 int
10534 {
10535  return is_instance_id(id);
10536 }
10537 
10538 int
10539 rb_is_attrset_id(ID id)
10540 {
10541  return is_attrset_id(id);
10542 }
10543 
10544 int
10545 rb_is_local_id(ID id)
10546 {
10547  return is_local_id(id);
10548 }
10549 
10550 int
10551 rb_is_junk_id(ID id)
10552 {
10553  return is_junk_id(id);
10554 }
10555 
10567 ID
10568 rb_check_id(volatile VALUE *namep)
10569 {
10570  st_data_t id;
10571  VALUE tmp;
10572  VALUE name = *namep;
10573 
10574  if (SYMBOL_P(name)) {
10575  return SYM2ID(name);
10576  }
10577  else if (!RB_TYPE_P(name, T_STRING)) {
10578  tmp = rb_check_string_type(name);
10579  if (NIL_P(tmp)) {
10580  tmp = rb_inspect(name);
10581  rb_raise(rb_eTypeError, "%s is not a symbol",
10582  RSTRING_PTR(tmp));
10583  }
10584  name = tmp;
10585  *namep = name;
10586  }
10587 
10588  sym_check_asciionly(name);
10589 
10590  if (st_lookup(global_symbols.sym_id, (st_data_t)name, &id))
10591  return (ID)id;
10592 
10593  if (rb_is_attrset_name(name)) {
10594  struct RString fake_str;
10595  const VALUE localname = (VALUE)&fake_str;
10596  /* make local name by chopping '=' */
10597  fake_str.basic.flags = T_STRING|RSTRING_NOEMBED;
10598  fake_str.basic.klass = rb_cString;
10599  fake_str.as.heap.len = RSTRING_LEN(name) - 1;
10600  fake_str.as.heap.ptr = RSTRING_PTR(name);
10601  fake_str.as.heap.aux.capa = fake_str.as.heap.len;
10602  rb_enc_copy(localname, name);
10603  OBJ_FREEZE(localname);
10604 
10605  if (st_lookup(global_symbols.sym_id, (st_data_t)localname, &id)) {
10606  return rb_id_attrset((ID)id);
10607  }
10608  RB_GC_GUARD(name);
10609  }
10610 
10611  return (ID)0;
10612 }
10613 
10614 ID
10615 rb_check_id_cstr(const char *ptr, long len, rb_encoding *enc)
10616 {
10617  st_data_t id;
10618  struct RString fake_str;
10619  const VALUE name = (VALUE)&fake_str;
10620  fake_str.basic.flags = T_STRING|RSTRING_NOEMBED;
10621  fake_str.basic.klass = rb_cString;
10622  fake_str.as.heap.len = len;
10623  fake_str.as.heap.ptr = (char *)ptr;
10624  fake_str.as.heap.aux.capa = len;
10625  rb_enc_associate(name, enc);
10626 
10627  sym_check_asciionly(name);
10628 
10629  if (st_lookup(global_symbols.sym_id, (st_data_t)name, &id))
10630  return (ID)id;
10631 
10632  if (rb_is_attrset_name(name)) {
10633  fake_str.as.heap.len = len - 1;
10634  if (st_lookup(global_symbols.sym_id, (st_data_t)name, &id)) {
10635  return rb_id_attrset((ID)id);
10636  }
10637  }
10638 
10639  return (ID)0;
10640 }
10641 
10642 int
10643 rb_is_const_name(VALUE name)
10644 {
10645  return rb_str_symname_type(name, 0) == ID_CONST;
10646 }
10647 
10648 int
10649 rb_is_class_name(VALUE name)
10650 {
10651  return rb_str_symname_type(name, 0) == ID_CLASS;
10652 }
10653 
10654 int
10656 {
10657  return rb_str_symname_type(name, 0) == ID_GLOBAL;
10658 }
10659 
10660 int
10662 {
10663  return rb_str_symname_type(name, 0) == ID_INSTANCE;
10664 }
10665 
10666 int
10668 {
10670 }
10671 
10672 int
10673 rb_is_local_name(VALUE name)
10674 {
10675  return rb_str_symname_type(name, 0) == ID_LOCAL;
10676 }
10677 
10678 int
10680 {
10681  switch (rb_str_symname_type(name, 0)) {
10682  case ID_LOCAL: case ID_ATTRSET: case ID_JUNK:
10683  return TRUE;
10684  }
10685  return FALSE;
10686 }
10687 
10688 int
10689 rb_is_junk_name(VALUE name)
10690 {
10691  return rb_str_symname_type(name, IDSET_ATTRSET_FOR_SYNTAX) == -1;
10692 }
10693 
10694 #endif /* !RIPPER */
10695 
10696 static void
10697 parser_initialize(struct parser_params *parser)
10698 {
10699  parser->eofp = Qfalse;
10700 
10701  parser->parser_lex_strterm = 0;
10702  parser->parser_cond_stack = 0;
10703  parser->parser_cmdarg_stack = 0;
10704  parser->parser_class_nest = 0;
10705  parser->parser_paren_nest = 0;
10706  parser->parser_lpar_beg = 0;
10707  parser->parser_brace_nest = 0;
10708  parser->parser_in_single = 0;
10709  parser->parser_in_def = 0;
10710  parser->parser_in_defined = 0;
10711  parser->parser_compile_for_eval = 0;
10712  parser->parser_cur_mid = 0;
10713  parser->parser_tokenbuf = NULL;
10714  parser->parser_tokidx = 0;
10715  parser->parser_toksiz = 0;
10716  parser->parser_heredoc_end = 0;
10717  parser->parser_command_start = TRUE;
10718  parser->parser_deferred_nodes = 0;
10719  parser->parser_lex_pbeg = 0;
10720  parser->parser_lex_p = 0;
10721  parser->parser_lex_pend = 0;
10722  parser->parser_lvtbl = 0;
10723  parser->parser_ruby__end__seen = 0;
10724  parser->parser_ruby_sourcefile = 0;
10725 #ifndef RIPPER
10726  parser->is_ripper = 0;
10727  parser->parser_eval_tree_begin = 0;
10728  parser->parser_eval_tree = 0;
10729 #else
10730  parser->is_ripper = 1;
10731  parser->parser_ruby_sourcefile_string = Qnil;
10732  parser->delayed = Qnil;
10733 
10734  parser->result = Qnil;
10735  parser->parsing_thread = Qnil;
10736  parser->toplevel_p = TRUE;
10737 #endif
10738 #ifdef YYMALLOC
10739  parser->heap = NULL;
10740 #endif
10741  parser->enc = rb_utf8_encoding();
10742 }
10743 
10744 #ifdef RIPPER
10745 #define parser_mark ripper_parser_mark
10746 #define parser_free ripper_parser_free
10747 #endif
10748 
10749 static void
10750 parser_mark(void *ptr)
10751 {
10752  struct parser_params *p = (struct parser_params*)ptr;
10753 
10759 #ifndef RIPPER
10762  rb_gc_mark(p->debug_lines);
10763 #else
10764  rb_gc_mark(p->parser_ruby_sourcefile_string);
10765  rb_gc_mark(p->delayed);
10766  rb_gc_mark(p->value);
10767  rb_gc_mark(p->result);
10768  rb_gc_mark(p->parsing_thread);
10769 #endif
10770 #ifdef YYMALLOC
10771  rb_gc_mark((VALUE)p->heap);
10772 #endif
10773 }
10774 
10775 static void
10776 parser_free(void *ptr)
10777 {
10778  struct parser_params *p = (struct parser_params*)ptr;
10779  struct local_vars *local, *prev;
10780 
10781  if (p->parser_tokenbuf) {
10782  xfree(p->parser_tokenbuf);
10783  }
10784  for (local = p->parser_lvtbl; local; local = prev) {
10785  if (local->vars) xfree(local->vars);
10786  prev = local->prev;
10787  xfree(local);
10788  }
10789 #ifndef RIPPER
10791 #endif
10792  xfree(p);
10793 }
10794 
10795 static size_t
10796 parser_memsize(const void *ptr)
10797 {
10798  struct parser_params *p = (struct parser_params*)ptr;
10799  struct local_vars *local;
10800  size_t size = sizeof(*p);
10801 
10802  if (!ptr) return 0;
10803  size += p->parser_toksiz;
10804  for (local = p->parser_lvtbl; local; local = local->prev) {
10805  size += sizeof(*local);
10806  if (local->vars) size += local->vars->capa * sizeof(ID);
10807  }
10808 #ifndef RIPPER
10809  if (p->parser_ruby_sourcefile) {
10810  size += strlen(p->parser_ruby_sourcefile) + 1;
10811  }
10812 #endif
10813  return size;
10814 }
10815 
10816 static
10817 #ifndef RIPPER
10818 const
10819 #endif
10820 rb_data_type_t parser_data_type = {
10821  "parser",
10822  {
10823  parser_mark,
10824  parser_free,
10826  },
10827 };
10828 
10829 #ifndef RIPPER
10830 #undef rb_reserved_word
10831 
10832 const struct kwtable *
10833 rb_reserved_word(const char *str, unsigned int len)
10834 {
10835  return reserved_word(str, len);
10836 }
10837 
10838 static struct parser_params *
10839 parser_new(void)
10840 {
10841  struct parser_params *p;
10842 
10843  p = ALLOC_N(struct parser_params, 1);
10844  MEMZERO(p, struct parser_params, 1);
10845  parser_initialize(p);
10846  return p;
10847 }
10848 
10849 VALUE
10850 rb_parser_new(void)
10851 {
10852  struct parser_params *p = parser_new();
10853 
10854  return TypedData_Wrap_Struct(0, &parser_data_type, p);
10855 }
10856 
10857 /*
10858  * call-seq:
10859  * ripper#end_seen? -> Boolean
10860  *
10861  * Return true if parsed source ended by +\_\_END\_\_+.
10862  */
10863 VALUE
10864 rb_parser_end_seen_p(VALUE vparser)
10865 {
10866  struct parser_params *parser;
10867 
10868  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
10869  return ruby__end__seen ? Qtrue : Qfalse;
10870 }
10871 
10872 /*
10873  * call-seq:
10874  * ripper#encoding -> encoding
10875  *
10876  * Return encoding of the source.
10877  */
10878 VALUE
10879 rb_parser_encoding(VALUE vparser)
10880 {
10881  struct parser_params *parser;
10882 
10883  TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, parser);
10885 }
10886 
10887 /*
10888  * call-seq:
10889  * ripper.yydebug -> true or false
10890  *
10891  * Get yydebug.
10892  */
10893 VALUE
10895 {
10896  struct parser_params *parser;
10897 
10898  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
10899  return yydebug ? Qtrue : Qfalse;
10900 }
10901 
10902 /*
10903  * call-seq:
10904  * ripper.yydebug = flag
10905  *
10906  * Set yydebug.
10907  */
10908 VALUE
10909 rb_parser_set_yydebug(VALUE self, VALUE flag)
10910 {
10911  struct parser_params *parser;
10912 
10913  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
10914  yydebug = RTEST(flag);
10915  return flag;
10916 }
10917 
10918 #ifdef YYMALLOC
10919 #define HEAPCNT(n, size) ((n) * (size) / sizeof(YYSTYPE))
10920 #define NEWHEAP() rb_node_newnode(NODE_ALLOCA, 0, (VALUE)parser->heap, 0)
10921 #define ADD2HEAP(n, c, p) ((parser->heap = (n))->u1.node = (p), \
10922  (n)->u3.cnt = (c), (p))
10923 
10924 void *
10925 rb_parser_malloc(struct parser_params *parser, size_t size)
10926 {
10927  size_t cnt = HEAPCNT(1, size);
10928  NODE *n = NEWHEAP();
10929  void *ptr = xmalloc(size);
10930 
10931  return ADD2HEAP(n, cnt, ptr);
10932 }
10933 
10934 void *
10935 rb_parser_calloc(struct parser_params *parser, size_t nelem, size_t size)
10936 {
10937  size_t cnt = HEAPCNT(nelem, size);
10938  NODE *n = NEWHEAP();
10939  void *ptr = xcalloc(nelem, size);
10940 
10941  return ADD2HEAP(n, cnt, ptr);
10942 }
10943 
10944 void *
10945 rb_parser_realloc(struct parser_params *parser, void *ptr, size_t size)
10946 {
10947  NODE *n;
10948  size_t cnt = HEAPCNT(1, size);
10949 
10950  if (ptr && (n = parser->heap) != NULL) {
10951  do {
10952  if (n->u1.node == ptr) {
10953  n->u1.node = ptr = xrealloc(ptr, size);
10954  if (n->u3.cnt) n->u3.cnt = cnt;
10955  return ptr;
10956  }
10957  } while ((n = n->u2.node) != NULL);
10958  }
10959  n = NEWHEAP();
10960  ptr = xrealloc(ptr, size);
10961  return ADD2HEAP(n, cnt, ptr);
10962 }
10963 
10964 void
10965 rb_parser_free(struct parser_params *parser, void *ptr)
10966 {
10967  NODE **prev = &parser->heap, *n;
10968 
10969  while ((n = *prev) != NULL) {
10970  if (n->u1.node == ptr) {
10971  *prev = n->u2.node;
10973  break;
10974  }
10975  prev = &n->u2.node;
10976  }
10977  xfree(ptr);
10978 }
10979 #endif
10980 #endif
10981 
10982 #ifdef RIPPER
10983 #ifdef RIPPER_DEBUG
10984 extern int rb_is_pointer_to_heap(VALUE);
10985 
10986 /* :nodoc: */
10987 static VALUE
10988 ripper_validate_object(VALUE self, VALUE x)
10989 {
10990  if (x == Qfalse) return x;
10991  if (x == Qtrue) return x;
10992  if (x == Qnil) return x;
10993  if (x == Qundef)
10994  rb_raise(rb_eArgError, "Qundef given");
10995  if (FIXNUM_P(x)) return x;
10996  if (SYMBOL_P(x)) return x;
10997  if (!rb_is_pointer_to_heap(x))
10998  rb_raise(rb_eArgError, "invalid pointer: %p", x);
10999  switch (TYPE(x)) {
11000  case T_STRING:
11001  case T_OBJECT:
11002  case T_ARRAY:
11003  case T_BIGNUM:
11004  case T_FLOAT:
11005  return x;
11006  case T_NODE:
11007  if (nd_type(x) != NODE_LASGN) {
11008  rb_raise(rb_eArgError, "NODE given: %p", x);
11009  }
11010  return ((NODE *)x)->nd_rval;
11011  default:
11012  rb_raise(rb_eArgError, "wrong type of ruby object: %p (%s)",
11013  x, rb_obj_classname(x));
11014  }
11015  return x;
11016 }
11017 #endif
11018 
11019 #define validate(x) ((x) = get_value(x))
11020 
11021 static VALUE
11022 ripper_dispatch0(struct parser_params *parser, ID mid)
11023 {
11024  return rb_funcall(parser->value, mid, 0);
11025 }
11026 
11027 static VALUE
11028 ripper_dispatch1(struct parser_params *parser, ID mid, VALUE a)
11029 {
11030  validate(a);
11031  return rb_funcall(parser->value, mid, 1, a);
11032 }
11033 
11034 static VALUE
11035 ripper_dispatch2(struct parser_params *parser, ID mid, VALUE a, VALUE b)
11036 {
11037  validate(a);
11038  validate(b);
11039  return rb_funcall(parser->value, mid, 2, a, b);
11040 }
11041 
11042 static VALUE
11043 ripper_dispatch3(struct parser_params *parser, ID mid, VALUE a, VALUE b, VALUE c)
11044 {
11045  validate(a);
11046  validate(b);
11047  validate(c);
11048  return rb_funcall(parser->value, mid, 3, a, b, c);
11049 }
11050 
11051 static VALUE
11052 ripper_dispatch4(struct parser_params *parser, ID mid, VALUE a, VALUE b, VALUE c, VALUE d)
11053 {
11054  validate(a);
11055  validate(b);
11056  validate(c);
11057  validate(d);
11058  return rb_funcall(parser->value, mid, 4, a, b, c, d);
11059 }
11060 
11061 static VALUE
11062 ripper_dispatch5(struct parser_params *parser, ID mid, VALUE a, VALUE b, VALUE c, VALUE d, VALUE e)
11063 {
11064  validate(a);
11065  validate(b);
11066  validate(c);
11067  validate(d);
11068  validate(e);
11069  return rb_funcall(parser->value, mid, 5, a, b, c, d, e);
11070 }
11071 
11072 static VALUE
11073 ripper_dispatch7(struct parser_params *parser, ID mid, VALUE a, VALUE b, VALUE c, VALUE d, VALUE e, VALUE f, VALUE g)
11074 {
11075  validate(a);
11076  validate(b);
11077  validate(c);
11078  validate(d);
11079  validate(e);
11080  validate(f);
11081  validate(g);
11082  return rb_funcall(parser->value, mid, 7, a, b, c, d, e, f, g);
11083 }
11084 
11085 static const struct kw_assoc {
11086  ID id;
11087  const char *name;
11088 } keyword_to_name[] = {
11089  {keyword_class, "class"},
11090  {keyword_module, "module"},
11091  {keyword_def, "def"},
11092  {keyword_undef, "undef"},
11093  {keyword_begin, "begin"},
11094  {keyword_rescue, "rescue"},
11095  {keyword_ensure, "ensure"},
11096  {keyword_end, "end"},
11097  {keyword_if, "if"},
11098  {keyword_unless, "unless"},
11099  {keyword_then, "then"},
11100  {keyword_elsif, "elsif"},
11101  {keyword_else, "else"},
11102  {keyword_case, "case"},
11103  {keyword_when, "when"},
11104  {keyword_while, "while"},
11105  {keyword_until, "until"},
11106  {keyword_for, "for"},
11107  {keyword_break, "break"},
11108  {keyword_next, "next"},
11109  {keyword_redo, "redo"},
11110  {keyword_retry, "retry"},
11111  {keyword_in, "in"},
11112  {keyword_do, "do"},
11113  {keyword_do_cond, "do"},
11114  {keyword_do_block, "do"},
11115  {keyword_return, "return"},
11116  {keyword_yield, "yield"},
11117  {keyword_super, "super"},
11118  {keyword_self, "self"},
11119  {keyword_nil, "nil"},
11120  {keyword_true, "true"},
11121  {keyword_false, "false"},
11122  {keyword_and, "and"},
11123  {keyword_or, "or"},
11124  {keyword_not, "not"},
11125  {modifier_if, "if"},
11126  {modifier_unless, "unless"},
11127  {modifier_while, "while"},
11128  {modifier_until, "until"},
11129  {modifier_rescue, "rescue"},
11130  {keyword_alias, "alias"},
11131  {keyword_defined, "defined?"},
11132  {keyword_BEGIN, "BEGIN"},
11133  {keyword_END, "END"},
11134  {keyword__LINE__, "__LINE__"},
11135  {keyword__FILE__, "__FILE__"},
11136  {keyword__ENCODING__, "__ENCODING__"},
11137  {0, NULL}
11138 };
11139 
11140 static const char*
11141 keyword_id_to_str(ID id)
11142 {
11143  const struct kw_assoc *a;
11144 
11145  for (a = keyword_to_name; a->id; a++) {
11146  if (a->id == id)
11147  return a->name;
11148  }
11149  return NULL;
11150 }
11151 
11152 #undef ripper_id2sym
11153 static VALUE
11154 ripper_id2sym(ID id)
11155 {
11156  const char *name;
11157  char buf[8];
11158 
11159  if (id <= 256) {
11160  buf[0] = (char)id;
11161  buf[1] = '\0';
11162  return ID2SYM(rb_intern2(buf, 1));
11163  }
11164  if ((name = keyword_id_to_str(id))) {
11165  return ID2SYM(rb_intern(name));
11166  }
11167  switch (id) {
11168  case tOROP:
11169  name = "||";
11170  break;
11171  case tANDOP:
11172  name = "&&";
11173  break;
11174  default:
11175  name = rb_id2name(id);
11176  if (!name) {
11177  rb_bug("cannot convert ID to string: %ld", (unsigned long)id);
11178  }
11179  return ID2SYM(id);
11180  }
11181  return ID2SYM(rb_intern(name));
11182 }
11183 
11184 static ID
11185 ripper_get_id(VALUE v)
11186 {
11187  NODE *nd;
11188  if (!RB_TYPE_P(v, T_NODE)) return 0;
11189  nd = (NODE *)v;
11190  if (nd_type(nd) != NODE_LASGN) return 0;
11191  return nd->nd_vid;
11192 }
11193 
11194 static VALUE
11195 ripper_get_value(VALUE v)
11196 {
11197  NODE *nd;
11198  if (v == Qundef) return Qnil;
11199  if (!RB_TYPE_P(v, T_NODE)) return v;
11200  nd = (NODE *)v;
11201  if (nd_type(nd) != NODE_LASGN) return Qnil;
11202  return nd->nd_rval;
11203 }
11204 
11205 static void
11206 ripper_compile_error(struct parser_params *parser, const char *fmt, ...)
11207 {
11208  VALUE str;
11209  va_list args;
11210 
11211  va_start(args, fmt);
11212  str = rb_vsprintf(fmt, args);
11213  va_end(args);
11214  rb_funcall(parser->value, rb_intern("compile_error"), 1, str);
11215 }
11216 
11217 static void
11218 ripper_warn0(struct parser_params *parser, const char *fmt)
11219 {
11220  rb_funcall(parser->value, rb_intern("warn"), 1, STR_NEW2(fmt));
11221 }
11222 
11223 static void
11224 ripper_warnI(struct parser_params *parser, const char *fmt, int a)
11225 {
11226  rb_funcall(parser->value, rb_intern("warn"), 2,
11227  STR_NEW2(fmt), INT2NUM(a));
11228 }
11229 
11230 static void
11231 ripper_warnS(struct parser_params *parser, const char *fmt, const char *str)
11232 {
11233  rb_funcall(parser->value, rb_intern("warn"), 2,
11234  STR_NEW2(fmt), STR_NEW2(str));
11235 }
11236 
11237 static void
11238 ripper_warning0(struct parser_params *parser, const char *fmt)
11239 {
11240  rb_funcall(parser->value, rb_intern("warning"), 1, STR_NEW2(fmt));
11241 }
11242 
11243 static void
11244 ripper_warningS(struct parser_params *parser, const char *fmt, const char *str)
11245 {
11246  rb_funcall(parser->value, rb_intern("warning"), 2,
11247  STR_NEW2(fmt), STR_NEW2(str));
11248 }
11249 
11250 static VALUE
11251 ripper_lex_get_generic(struct parser_params *parser, VALUE src)
11252 {
11253  return rb_io_gets(src);
11254 }
11255 
11256 static VALUE
11257 ripper_s_allocate(VALUE klass)
11258 {
11259  struct parser_params *p;
11260  VALUE self;
11261 
11262  p = ALLOC_N(struct parser_params, 1);
11263  MEMZERO(p, struct parser_params, 1);
11264  self = TypedData_Wrap_Struct(klass, &parser_data_type, p);
11265  p->value = self;
11266  return self;
11267 }
11268 
11269 #define ripper_initialized_p(r) ((r)->parser_lex_input != 0)
11270 
11271 /*
11272  * call-seq:
11273  * Ripper.new(src, filename="(ripper)", lineno=1) -> ripper
11274  *
11275  * Create a new Ripper object.
11276  * _src_ must be a String, an IO, or an Object which has #gets method.
11277  *
11278  * This method does not starts parsing.
11279  * See also Ripper#parse and Ripper.parse.
11280  */
11281 static VALUE
11282 ripper_initialize(int argc, VALUE *argv, VALUE self)
11283 {
11284  struct parser_params *parser;
11285  VALUE src, fname, lineno;
11286 
11287  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
11288  rb_scan_args(argc, argv, "12", &src, &fname, &lineno);
11289  if (RB_TYPE_P(src, T_FILE)) {
11290  parser->parser_lex_gets = ripper_lex_get_generic;
11291  }
11292  else {
11293  StringValue(src);
11294  parser->parser_lex_gets = lex_get_str;
11295  }
11296  parser->parser_lex_input = src;
11297  parser->eofp = Qfalse;
11298  if (NIL_P(fname)) {
11299  fname = STR_NEW2("(ripper)");
11300  }
11301  else {
11302  StringValue(fname);
11303  }
11304  parser_initialize(parser);
11305 
11306  parser->parser_ruby_sourcefile_string = fname;
11307  parser->parser_ruby_sourcefile = RSTRING_PTR(fname);
11308  parser->parser_ruby_sourceline = NIL_P(lineno) ? 0 : NUM2INT(lineno) - 1;
11309 
11310  return Qnil;
11311 }
11312 
11313 struct ripper_args {
11314  struct parser_params *parser;
11315  int argc;
11316  VALUE *argv;
11317 };
11318 
11319 static VALUE
11320 ripper_parse0(VALUE parser_v)
11321 {
11322  struct parser_params *parser;
11323 
11324  TypedData_Get_Struct(parser_v, struct parser_params, &parser_data_type, parser);
11325  parser_prepare(parser);
11326  ripper_yyparse((void*)parser);
11327  return parser->result;
11328 }
11329 
11330 static VALUE
11331 ripper_ensure(VALUE parser_v)
11332 {
11333  struct parser_params *parser;
11334 
11335  TypedData_Get_Struct(parser_v, struct parser_params, &parser_data_type, parser);
11336  parser->parsing_thread = Qnil;
11337  return Qnil;
11338 }
11339 
11340 /*
11341  * call-seq:
11342  * ripper#parse
11343  *
11344  * Start parsing and returns the value of the root action.
11345  */
11346 static VALUE
11347 ripper_parse(VALUE self)
11348 {
11349  struct parser_params *parser;
11350 
11351  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
11352  if (!ripper_initialized_p(parser)) {
11353  rb_raise(rb_eArgError, "method called for uninitialized object");
11354  }
11355  if (!NIL_P(parser->parsing_thread)) {
11356  if (parser->parsing_thread == rb_thread_current())
11357  rb_raise(rb_eArgError, "Ripper#parse is not reentrant");
11358  else
11359  rb_raise(rb_eArgError, "Ripper#parse is not multithread-safe");
11360  }
11361  parser->parsing_thread = rb_thread_current();
11362  rb_ensure(ripper_parse0, self, ripper_ensure, self);
11363 
11364  return parser->result;
11365 }
11366 
11367 /*
11368  * call-seq:
11369  * ripper#column -> Integer
11370  *
11371  * Return column number of current parsing line.
11372  * This number starts from 0.
11373  */
11374 static VALUE
11375 ripper_column(VALUE self)
11376 {
11377  struct parser_params *parser;
11378  long col;
11379 
11380  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
11381  if (!ripper_initialized_p(parser)) {
11382  rb_raise(rb_eArgError, "method called for uninitialized object");
11383  }
11384  if (NIL_P(parser->parsing_thread)) return Qnil;
11385  col = parser->tokp - parser->parser_lex_pbeg;
11386  return LONG2NUM(col);
11387 }
11388 
11389 /*
11390  * call-seq:
11391  * ripper#filename -> String
11392  *
11393  * Return current parsing filename.
11394  */
11395 static VALUE
11396 ripper_filename(VALUE self)
11397 {
11398  struct parser_params *parser;
11399 
11400  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
11401  if (!ripper_initialized_p(parser)) {
11402  rb_raise(rb_eArgError, "method called for uninitialized object");
11403  }
11404  return parser->parser_ruby_sourcefile_string;
11405 }
11406 
11407 /*
11408  * call-seq:
11409  * ripper#lineno -> Integer
11410  *
11411  * Return line number of current parsing line.
11412  * This number starts from 1.
11413  */
11414 static VALUE
11415 ripper_lineno(VALUE self)
11416 {
11417  struct parser_params *parser;
11418 
11419  TypedData_Get_Struct(self, struct parser_params, &parser_data_type, parser);
11420  if (!ripper_initialized_p(parser)) {
11421  rb_raise(rb_eArgError, "method called for uninitialized object");
11422  }
11423  if (NIL_P(parser->parsing_thread)) return Qnil;
11424  return INT2NUM(parser->parser_ruby_sourceline);
11425 }
11426 
11427 #ifdef RIPPER_DEBUG
11428 /* :nodoc: */
11429 static VALUE
11430 ripper_assert_Qundef(VALUE self, VALUE obj, VALUE msg)
11431 {
11432  StringValue(msg);
11433  if (obj == Qundef) {
11434  rb_raise(rb_eArgError, "%s", RSTRING_PTR(msg));
11435  }
11436  return Qnil;
11437 }
11438 
11439 /* :nodoc: */
11440 static VALUE
11441 ripper_value(VALUE self, VALUE obj)
11442 {
11443  return ULONG2NUM(obj);
11444 }
11445 #endif
11446 
11447 
11448 void
11449 Init_ripper(void)
11450 {
11451  parser_data_type.parent = RTYPEDDATA_TYPE(rb_parser_new());
11452 
11455  /* ensure existing in symbol table */
11456  (void)rb_intern("||");
11457  (void)rb_intern("&&");
11458 
11459  InitVM(ripper);
11460 }
11461 
11462 void
11463 InitVM_ripper(void)
11464 {
11465  VALUE Ripper;
11466 
11467  Ripper = rb_define_class("Ripper", rb_cObject);
11468  rb_define_const(Ripper, "Version", rb_usascii_str_new2(RIPPER_VERSION));
11469  rb_define_alloc_func(Ripper, ripper_s_allocate);
11470  rb_define_method(Ripper, "initialize", ripper_initialize, -1);
11471  rb_define_method(Ripper, "parse", ripper_parse, 0);
11472  rb_define_method(Ripper, "column", ripper_column, 0);
11473  rb_define_method(Ripper, "filename", ripper_filename, 0);
11474  rb_define_method(Ripper, "lineno", ripper_lineno, 0);
11475  rb_define_method(Ripper, "end_seen?", rb_parser_end_seen_p, 0);
11476  rb_define_method(Ripper, "encoding", rb_parser_encoding, 0);
11477  rb_define_method(Ripper, "yydebug", rb_parser_get_yydebug, 0);
11478  rb_define_method(Ripper, "yydebug=", rb_parser_set_yydebug, 1);
11479 #ifdef RIPPER_DEBUG
11480  rb_define_method(rb_mKernel, "assert_Qundef", ripper_assert_Qundef, 2);
11481  rb_define_method(rb_mKernel, "rawVALUE", ripper_value, 1);
11482  rb_define_method(rb_mKernel, "validate_object", ripper_validate_object, 1);
11483 #endif
11484 
11487 
11488 # if 0
11489  /* Hack to let RDoc document SCRIPT_LINES__ */
11490 
11491  /*
11492  * When a Hash is assigned to +SCRIPT_LINES__+ the contents of files loaded
11493  * after the assignment will be added as an Array of lines with the file
11494  * name as the key.
11495  */
11496  rb_define_global_const("SCRIPT_LINES__", Qnil);
11497 #endif
11498 
11499 }
11500 #endif /* RIPPER */
static const struct @60 op_tbl[]
#define tokline
Definition: parse.y:326
#define rb_enc_islower(c, enc)
static int yylex(void *)
char * parser_ruby_sourcefile
Definition: ripper.c:327
#define RB_TYPE_P(obj, type)
VALUE val
Definition: parse.h:164
#define nd_next
#define command_start
Definition: parse.y:334
#define nd_type(n)
#define NEW_ARGSCAT(a, b)
#define NODE_DREGX_ONCE
VALUE rb_const_get_at(VALUE, ID)
Definition: variable.c:1882
#define lex_eol_p()
stack_type cmdargs
Definition: ripper.c:193
#define ALLOC(type)
#define NEW_FALSE()
#define COND_PUSH(n)
Definition: parse.y:113
enum lex_state_e state
Definition: lex.c:33
struct local_vars * parser_lvtbl
Definition: ripper.c:323
#define NODE_IF
#define lex_p
Definition: parse.y:331
VALUE rb_ary_unshift(VALUE ary, VALUE item)
Definition: array.c:1084
static ID ripper_token2eventid(int tok)
Definition: eventids2.c:273
#define NODE_RESCUE
Definition: lex.c:33
#define rb_warn4S(file, line, fmt, a)
Definition: parse.y:638
static NODE * match_op_gen(struct parser_params *, NODE *, NODE *)
int rb_is_attrset_id(ID id)
Definition: ripper.c:17123
int rb_enc_codelen(int c, rb_encoding *enc)
Definition: encoding.c:954
#define NODE_RETRY
Definition: ripper.y:119
#define NODE_DEFN
static double zero(void)
Definition: isinf.c:51
#define gettable(id)
Definition: parse.y:424
#define RE_OPTION_ENCODING(e)
Definition: parse.y:525
#define NODE_FALSE
#define NEW_DOT3(b, e)
static struct parser_params * parser_new(void)
Definition: ripper.c:17423
#define DVARS_TOPSCOPE
Definition: parse.y:139
#define FLONUM_P(x)
#define NODE_OR
int onig_foreach_name(regex_t *reg, int(*func)(const UChar *, const UChar *, int, int *, regex_t *, void *), void *arg)
Definition: regparse.c:537
st_table * st_init_table_with_size(const struct st_hash_type *, st_index_t)
Definition: st.c:229
#define NEW_IASGN(v, val)
VALUE rb_get_coverages(void)
Definition: thread.c:5182
#define dvar_defined_get(id)
Definition: parse.y:516
#define RE_OPTION_ENCODING_IDX(o)
Definition: parse.y:526
#define NEW_NTH_REF(n)
#define IDSET_ATTRSET_FOR_SYNTAX
Definition: ripper.y:115
#define STR_NEW3(p, n, e, func)
Definition: parse.y:303
void rb_bug(const char *fmt,...)
Definition: error.c:290
#define NEW_DASGN_CURR(v, val)
static NODE * reg_named_capture_assign_gen(struct parser_params *parser, VALUE regexp, NODE *match)
#define IS_BEG()
#define ADD2HEAP(n, c, p)
struct token_info * next
Definition: ripper.c:275
< num > opt_block_param compstmt
Definition: parse.y:1357
void rb_enc_copy(VALUE obj1, VALUE obj2)
Definition: encoding.c:856
#define FALSE
Definition: nkf.h:174
#define attrset(node, id)
Definition: parse.y:431
static const struct kwtable * reserved_word(const char *, unsigned int)
#define tail
Definition: st.c:108
Definition: ripper.y:108
void rb_mark_tbl(struct st_table *)
Definition: gc.c:2543
int rb_is_class_name(VALUE name)
Definition: ripper.c:17233
struct vtable * used
Definition: ripper.c:191
#define tHEREDOC_BEG
Definition: eventids2.c:7
NODE * rb_parser_compile_file(volatile VALUE vparser, const char *f, VALUE file, int start)
Definition: ripper.c:12072
static int comment_at_top(struct parser_params *parser)
Definition: ripper.c:13149
#define new_args(f, o, r, p, t)
Definition: parse.y:410
#define rb_gc_mark_locations(start, end)
Definition: gc.c:2348
size_t strlen(const char *)
int i
Definition: win32ole.c:784
static size_t parser_memsize(const void *ptr)
Definition: ripper.c:17380
VALUE parser_lex_nextline
Definition: ripper.c:314
VALUE rb_make_exception(int argc, VALUE *argv)
Definition: eval.c:642
#define whole_match_p(e, l, i)
#define scan_oct(s, l, e)
Definition: util.h:52
unsigned long VALUE
Definition: ripper.y:104
#define is_class_id(id)
Definition: parse.y:58
#define HEAPCNT(n, size)
const char * rb_obj_classname(VALUE)
Definition: variable.c:396
#define cond_stack
Definition: parse.y:312
case return tREGEXP_BEG
Definition: parse.y:7625
static void local_push_gen(struct parser_params *, int)
static NODE * node_assign_gen(struct parser_params *, NODE *, NODE *)
VALUE rb_id2str(ID id)
Definition: ripper.c:16992
#define new_yield(node)
Definition: parse.y:419
#define list_concat(h, t)
Definition: parse.y:390
int parser_ruby__end__seen
Definition: ripper.c:324
#define NODE_DSYM
int parser_command_start
Definition: ripper.c:319
#define dyna_var(id)
Definition: parse.y:513
static int local_var_gen(struct parser_params *, ID)
#define NODE_DEFS
#define lvar_defined(id)
Definition: parse.y:521
static int parser_yyerror(struct parser_params *, const char *)
#define NEW_CALL(r, m, a)
int st_lookup(st_table *, st_data_t, st_data_t *)
void st_add_direct(st_table *, st_data_t, st_data_t)
Definition: st.c:624
#define nd_body
#define COND_LEXPOP()
Definition: parse.y:115
VALUE rb_str_buf_append(VALUE, VALUE)
Definition: string.c:2106
#define NODE_HASH
#define get_id(id)
Definition: parse.y:461
#define TOK_INTERN(mb)
Definition: parse.y:305
#define NODE_DOT3
#define local_var(id)
Definition: parse.y:499
const char * name
Definition: lex.c:33
#define tEMBDOC_BEG
Definition: eventids2.c:3
Definition: ripper.y:118
static int parser_tokadd_utf8(struct parser_params *parser, rb_encoding **encp, int string_literal, int symbol_literal, int regexp_literal)
Definition: ripper.c:12259
int parser_compile_for_eval
Definition: ripper.c:305
int parser_token_info_enabled
Definition: ripper.c:341
#define NEW_ALIAS(n, o)
static NODE * node_newnode(struct parser_params *, enum node_type, VALUE, VALUE, VALUE)
#define NEW_OP_CDECL(v, op, val)
int parser_brace_nest
Definition: ripper.c:304
#define IS_LABEL_SUFFIX(n)
Definition: ripper.y:105
#define paren_nest
Definition: parse.y:315
static void parser_heredoc_restore(struct parser_params *parser, NODE *here)
Definition: ripper.c:12918
#define rb_usascii_str_new2
#define NEW_TRUE()
#define call_uni_op(recv, id)
Definition: parse.y:407
#define nd_resq
#define NODE_NTH_REF
void rb_define_global_const(const char *, VALUE)
Definition: variable.c:2216
void rb_gc_force_recycle(VALUE)
Definition: gc.c:2963
#define NODE_TRUE
#define T_NODE
static struct symbols global_symbols
#define rb_enc_name(enc)
VALUE rb_parser_end_seen_p(VALUE vparser)
Definition: ripper.c:17448
#define lex_lastline
Definition: parse.y:328
#define ruby_sourceline
Definition: parse.y:340
const int id
Definition: nkf.c:209
static void fixpos(NODE *, NODE *)
int line_count
Definition: ripper.c:325
#define NEW_EVSTR(n)
#define NODE_ARGS
#define NEW_NEXT(s)
#define literal_concat(h, t)
Definition: parse.y:396
stack_type parser_cmdarg_stack
Definition: ripper.c:298
#define RFLOAT_VALUE(v)
#define IS_END()
#define tokspace(n)
#define strcasecmp
Definition: win32.h:200
#define new_op_assign(lhs, op, rhs)
Definition: parse.y:485
#define is_const_id(id)
Definition: parse.y:57
VALUE rb_enc_from_encoding(rb_encoding *encoding)
Definition: encoding.c:103
#define NEW_NIL()
static VALUE debug_lines(const char *f)
Definition: ripper.c:11849
#define NODE_ENSURE
VALUE rb_eTypeError
Definition: error.c:511
#define rb_enc_isalnum(c, enc)
static int parser_here_document(struct parser_params *, NODE *)
Definition: ripper.c:12965
static NODE * arg_append_gen(struct parser_params *, NODE *, NODE *)
#define OBJ_FREEZE(x)
static NODE * new_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs)
Definition: ripper.y:120
void rb_define_alloc_func(VALUE, rb_alloc_func_t)
long(* rb_magic_comment_length_t)(struct parser_params *parser, const char *name, long len)
Definition: ripper.c:13161
#define NEW_ZARRAY()
st_table * names
Definition: encoding.c:53
#define rb_enc_prev_char(s, p, e, enc)
#define lex_pbeg
Definition: parse.y:330
VALUE rb_ary_push(VALUE ary, VALUE item)
Definition: array.c:822
NODE * kw_args
Definition: ripper.y:517
Definition: ripper.y:99
#define subnodes(n1, n2)
#define MAX_WORD_LENGTH
Definition: lex.c:43
#define local_pop()
Definition: parse.y:497
VALUE rb_eEncodingError
Definition: error.c:517
static int reg_named_capture_assign_iter(const OnigUChar *name, const OnigUChar *name_end, int back_num, int *back_refs, OnigRegex regex, void *arg0)
Definition: ripper.c:16359
static void warn_unused_var(struct parser_params *parser, struct local_vars *local)
Definition: ripper.c:16081
#define new_args_tail(k, kr, b)
Definition: parse.y:412
static NODE * new_args_tail_gen(struct parser_params *, NODE *, ID, ID)
#define TYPE(x)
struct RBasic basic
Definition: ripper.y:843
#define nd_else
rb_encoding * rb_enc_compatible(VALUE str1, VALUE str2)
Definition: encoding.c:789
#define newtok()
#define NODE_PRELUDE
#define nd_term(node)
Definition: parse.y:538
mlhs_head tSTAR mlhs_node
Definition: parse.y:1525
#define RSTRING_PTR(str)
#define void_stmts(node)
Definition: parse.y:379
#define NEW_MATCH2(n1, n2)
VALUE op_sym[tLAST_OP_ID]
Definition: ripper.c:16571
VALUE rb_reg_compile(VALUE str, int options, const char *sourcefile, int sourceline)
Definition: re.c:2530
#define CMDARG_LEXPOP()
Definition: parse.y:120
#define T_ARRAY
VALUE debug_lines
Definition: ripper.c:337
VALUE rb_enc_str_new(const char *, long, rb_encoding *)
Definition: string.c:439
mlhs_node keyword_variable
Definition: parse.y:1646
#define parser_precise_mbclen()
#define NEW_LAMBDA(a, b)
#define shadowing_lvar(name)
Definition: parse.y:490
#define is_identchar(p, e, enc)
static NODE * arg_blk_pass(NODE *, NODE *)
#define NEW_POSTEXE(b)
#define NEW_STR(s)
#define yyerrok
Definition: ripper.c:4378
#define NODE_EVSTR
#define xfree
static void reg_fragment_setenc_gen(struct parser_params *, VALUE, int)
VALUE rb_funcall(VALUE, ID, int,...)
Calls a method.
Definition: vm_eval.c:773
#define Qnil
return tOP_ASGN
Definition: parse.y:7647
#define mixed_error(enc1, enc2)
#define NODE_DXSTR
static void ripper_init_eventids1_table(VALUE self)
Definition: eventids1.c:270
#define NODE_CASE
void rb_raise(VALUE exc, const char *fmt,...)
Definition: error.c:1780
#define STR_FUNC_INDENT
#define T_HASH
Definition: ripper.y:109
#define mixed_escape(beg, enc1, enc2)
VALUE rb_enc_associate(VALUE obj, rb_encoding *enc)
Definition: encoding.c:766
ID * tbl
Definition: ripper.c:182
#define yyparse
Definition: parse.y:359
#define warn_balanced(op, syn)
void rb_compile_warn(const char *file, int line, const char *fmt,...)
Definition: error.c:172
#define peek_n(c, n)
static NODE * range_op(struct parser_params *parser, NODE *node)
Definition: ripper.c:15739
#define T_FILE
int pre_args_num
Definition: ripper.y:509
#define NEW_CONST(v)
int parser_toksiz
Definition: ripper.c:310
#define set_yylval_node(x)
static NODE * new_yield_gen(struct parser_params *, NODE *)
int rb_enc_mbclen(const char *p, const char *e, rb_encoding *enc)
Definition: encoding.c:886
expr expr keyword_or expr
Definition: parse.y:1292
static void parser_pushback(struct parser_params *parser, int c)
Definition: ripper.c:12187
NODE * kw_rest_arg
Definition: ripper.y:518
#define NODE_STR
ID last_id
Definition: ripper.c:16564
nd_set_line($$,$< num >2)
#define RFLOAT(obj)
#define NODE_REDO
#define is_attrset_id(id)
Definition: parse.y:56
#define NODE_NEXT
#define formal_argument(id)
Definition: parse.y:488
Definition: ripper.y:112
#define NEW_DVAR(v)
void(* rb_magic_comment_setter_t)(struct parser_params *parser, const char *name, const char *val)
Definition: ripper.c:13162
#define heredoc_restore(n)
static void reduce_nodes_gen(struct parser_params *, NODE **)
#define rb_warningS(fmt, a)
Definition: parse.y:640
#define ID_LOCAL
Definition: ripper.y:82
#define NODE_XSTR
#define cmdarg_stack
Definition: parse.y:313
Definition: ripper.y:107
#define NEW_CVASGN(v, val)
static int parser_whole_match_p(struct parser_params *parser, const char *eos, long len, int indent)
Definition: ripper.c:12935
#define NODE_BLOCK_PASS
#define ISDIGIT(c)
mlhs_item mlhs_head
Definition: ripper.y:1589
#define reg_compile(str, options)
Definition: parse.y:453
#define NEW_BREAK(s)
unsigned int last
Definition: nkf.c:4310
#define NEW_OP_ASGN_OR(i, val)
static void parser_initialize(struct parser_params *parser)
Definition: ripper.c:17281
#define NEW_MASGN(l, r)
ID block_arg
Definition: ripper.y:515
#define ENCODING_IS_ASCII8BIT(obj)
static VALUE parse(int argc, VALUE *argv, VALUE self)
Definition: psych_parser.c:229
#define InitVM(ext)
ID rb_check_id(volatile VALUE *namep)
Returns ID for the given name if it is interned already, or 0.
Definition: ripper.c:17152
ID rb_check_id_cstr(const char *ptr, long len, rb_encoding *enc)
Definition: ripper.c:17199
static NODE * yycompile(struct parser_params *parser, const char *f, int line)
Definition: ripper.c:11949
struct RNode * node
Definition: ripper.y:244
#define ruby_debug_lines
Definition: parse.y:348
keyword_super command_args
Definition: parse.y:1443
static ID * vtable_tblcpy(ID *buf, const struct vtable *src)
Definition: ripper.c:16134
#define token_info_pop(token)
Definition: parse.y:679
#define current_enc
Definition: parse.y:342
rb_encoding * rb_utf8_encoding(void)
Definition: encoding.c:1168
#define ID2SYM(x)
VALUE parser_lex_input
Definition: ripper.c:312
static long parser_encode_length(struct parser_params *parser, const char *name, long len)
Definition: ripper.c:13097
#define T_FLOAT
#define NEW_LVAR(v)
#define yydebug
Definition: parse.y:343
#define STR_FUNC_REGEXP
#define rb_enc_isdigit(c, enc)
#define T_OBJECT
static enum node_type nodetype(NODE *node)
Definition: ripper.c:14729
#define ENC_CODERANGE_BROKEN
VALUE rb_sym_all_symbols(void)
Definition: ripper.c:17090
static VALUE lex_getline(struct parser_params *parser)
Definition: ripper.c:11988
static NODE * call_uni_op_gen(struct parser_params *, NODE *, ID)
Definition: ripper.y:114
#define ID_INTERNAL
#define LONG2NUM(x)
VALUE rb_str_append(VALUE, VALUE)
Definition: string.c:2122
#define RUBY_DTRACE_PARSE_BEGIN(arg0, arg1)
Definition: probes.h:68
Definition: ripper.y:96
#define assignable_result(x)
int pos
Definition: ripper.c:183
#define NEW_FOR(v, i, b)
#define NEW_CLASS(n, b, s)
static int literal_concat0(struct parser_params *, VALUE, VALUE)
static NODE * assignable_gen(struct parser_params *, ID, NODE *)
#define tokidx
Definition: parse.y:324
#define NODE_GASGN
#define LVAR_USED
#define list_append(l, i)
Definition: parse.y:388
int rb_enc_symname2_p(const char *name, long len, rb_encoding *enc)
Definition: ripper.c:16782
#define NEW_SPLAT(a)
#define ID_SCOPE_SHIFT
VALUE rb_parser_set_yydebug(VALUE self, VALUE flag)
Definition: ripper.c:17493
#define NEW_PRELUDE(p, b)
#define block_dup_check(n1, n2)
Definition: parse.y:383
static NODE * evstr2dstr_gen(struct parser_params *, NODE *)
#define NEW_ITER(a, b)
#define head
Definition: st.c:107
pure parser lex param
Definition: parse.y:687
#define match_op(node1, node2)
Definition: parse.y:445
#define ENCODING_GET(obj)
int parser_yydebug
Definition: ripper.c:331
st_table * id_str
Definition: ripper.c:16566
NODE * parser_eval_tree
Definition: ripper.c:336
return tSYMBEG
Definition: parse.y:7621
#define set_yylval_num(x)
NODE * parser_deferred_nodes
Definition: ripper.c:320
#define sym(x)
Definition: date_core.c:3715
static int simple_re_meta(int c)
Definition: ripper.c:12564
#define NEW_GVAR(v)
void rb_name_error(ID id, const char *fmt,...)
Definition: error.c:899
Definition: ripper.y:240
static int e_option_supplied(struct parser_params *parser)
Definition: ripper.c:11883
return c
Definition: parse.y:7591
Definition: parse.h:159
int has_shebang
Definition: ripper.c:326
nd_args
Definition: parse.y:1382
#define NEW_DSTR(s)
Win32OLEIDispatch * p
Definition: win32ole.c:786
#define nd_set_type(n, t)
static NODE * list_append_gen(struct parser_params *, NODE *, NODE *)
#define toklen()
static int assign_in_cond(struct parser_params *parser, NODE *node)
Definition: ripper.c:15669
mlhs_head tSTAR mlhs_post
Definition: parse.y:1533
#define ISALPHA(c)
Definition: ruby.h:1636
#define MEMZERO(p, type, n)
void rb_exc_raise(VALUE mesg)
Definition: eval.c:527
#define NEWHEAP()
#define rb_compile_error
Definition: parse.y:661
#define NEW_UNLESS(c, t, e)
#define NEW_MODULE(n, b)
int args
Definition: win32ole.c:785
unsigned long st_data_t
Definition: ripper.y:35
#define strtod(s, e)
Definition: util.h:76
VALUE rb_usascii_str_new(const char *, long)
Definition: string.c:431
static rb_encoding * must_be_ascii_compatible(VALUE s)
Definition: ripper.c:11958
struct vtable * prev
Definition: ripper.c:185
int rb_is_const_id(ID id)
Definition: ripper.c:17099
int rb_is_instance_id(ID id)
Definition: ripper.c:17117
#define RUBY_DTRACE_PARSE_END(arg0, arg1)
Definition: probes.h:72
static int parser_tokadd_string(struct parser_params *, int, int, int, long *, rb_encoding **)
Definition: ripper.c:12577
static NODE * remove_begin(NODE *)
#define nd_paren(node)
Definition: parse.y:540
int rb_is_method_name(VALUE name)
Definition: ripper.c:17263
Definition: ripper.y:110
Definition: ripper.y:97
#define NEW_OP_ASGN_AND(i, val)
rb_encoding * enc
Definition: ripper.c:329
static NODE * gettable_gen(struct parser_params *, ID)
static NODE * dsym_node_gen(struct parser_params *, NODE *)
#define NODE_LVAR
static int parser_regx_options(struct parser_params *)
Definition: ripper.c:12505
enum lex_state_e parser_lex_state
Definition: ripper.c:296
#define NODE_LASGN
int capa
Definition: ripper.c:184
VALUE parser_lex_lastline
Definition: ripper.c:313
#define NEW_OPT_N(b)
Definition: ripper.y:113
static NODE * newline_node(NODE *)
NODE * rb_parser_compile_string(volatile VALUE vparser, const char *f, VALUE s, int line)
Definition: ripper.c:12037
#define NEW_KW_ARG(i, v)
static int parser_yylex(struct parser_params *parser)
Definition: ripper.c:13424
static VALUE parser_str_new(const char *p, long n, rb_encoding *enc, int func, rb_encoding *enc0)
Definition: ripper.c:12109
#define scan_hex(s, l, e)
Definition: util.h:54
#define FIXNUM_P(f)
#define rb_intern_str(string)
Definition: generator.h:17
int rb_char_to_option_kcode(int c, int *option, int *kcode)
Definition: re.c:301
static char * parser_tokspace(struct parser_params *parser, int n)
Definition: ripper.c:12220
static NODE * cond_gen(struct parser_params *, NODE *)
#define arg_append(h, t)
Definition: parse.y:392
#define local_id(id)
Definition: parse.y:503
#define op_tbl_count
#define TypedData_Get_Struct(obj, type, data_type, sval)
void rb_compile_error_append(const char *fmt,...)
Definition: error.c:150
#define RARRAY_LEN(a)
static void parser_free(void *ptr)
Definition: ripper.c:17360
#define nextc()
#define NODE_WHEN
#define StringValuePtr(v)
#define parser_warning(node, mesg)
#define val
#define RE_OPTION_ONCE
Definition: parse.y:523
int rb_ispunct(int c)
Definition: encoding.c:1892
static void vtable_add(struct vtable *tbl, ID id)
Definition: parse.y:181
VALUE rb_eRuntimeError
Definition: error.c:510
#define Qtrue
static int symbols_i(VALUE sym, ID value, VALUE ary)
Definition: ripper.c:17067
const rb_data_type_t * parent
Definition: ripper.y:969
#define NEW_RESCUE(b, res, e)
#define RARRAY(obj)
static int parser_tokadd_escape(struct parser_params *parser, rb_encoding **encp)
Definition: ripper.c:12432
VALUE rb_parser_encoding(VALUE vparser)
Definition: ripper.c:17463
union RNode::@81 u2
struct parser_params * parser
Definition: ripper.c:16351
#define NODE_YIELD
#define NEW_NODE(t, a0, a1, a2)
#define NEW_LIST(a)
#define NEW_ENSURE(b, en)
RUBY_EXTERN VALUE rb_mKernel
Definition: ripper.y:1414
#define NODE_FLIP2
char * ruby_strdup(const char *)
Definition: util.c:456
#define NODE_BLOCK
#define ID_INSTANCE
static NODE * attrset_gen(struct parser_params *, NODE *, ID)
NODE * rb_compile_string(const char *f, VALUE s, int line)
Definition: ripper.c:12030
#define NEW_BLOCK(a)
#define NODE_DASGN_CURR
#define NODE_HEREDOC
Definition: parse.y:532
int parser_paren_nest
Definition: ripper.c:300
static int dvar_curr_gen(struct parser_params *, ID)
VALUE rb_ary_new(void)
Definition: array.c:424
#define NODE_AND
#define local_push(top)
Definition: parse.y:495
int rb_ascii8bit_encindex(void)
Definition: encoding.c:1162
unsigned long ID
Definition: ripper.y:105
static int is_global_name_punct(const char c)
Definition: ripper.c:12754
#define NEW_UNDEF(i)
#define ID_JUNK
#define dispatch_heredoc_end()
void rb_gc_mark(VALUE)
Definition: gc.c:2600
#define ID_GLOBAL
static char * parser_newtok(struct parser_params *parser)
Definition: ripper.c:12204
top_stmt bodystmt
Definition: parse.y:942
#define lex_pend
Definition: parse.y:332
lhs
Definition: parse.y:1270
#define heredoc_identifier()
void rb_define_const(VALUE, const char *, VALUE)
Definition: variable.c:2202
#define SPECIAL_PUNCT(idx)
RUBY_EXTERN int ffs(int)
Definition: ffs.c:6
#define NEW_WHEN(c, t, e)
top_stmt escape_Qundef($1)
#define ISASCII(c)
Definition: ruby.h:1629
#define IS_ARG()
VALUE rb_define_class(const char *name, VALUE super)
Defines a top-level class.
Definition: class.c:499
static char msg[50]
Definition: strerror.c:8
#define RSTRING_LEN(str)
static void parser_set_token_info(struct parser_params *parser, const char *name, const char *val)
Definition: ripper.c:13174
#define INT2FIX(i)
#define toksiz
Definition: parse.y:325
#define Qfalse
#define call_bin_op(recv, id, arg1)
Definition: parse.y:405
Definition: ripper.y:135
VALUE value
Definition: ripper.y:246
static NODE * call_bin_op_gen(struct parser_params *, NODE *, ID, NODE *)
static void parser_tokadd(struct parser_params *parser, int c)
Definition: ripper.c:12232
#define FIX2LONG(x)
#define k__END__
Definition: eventids2.c:9
#define ruby_eval_tree_begin
Definition: parse.y:347
static void parser_mark(void *ptr)
Definition: ripper.c:17334
#define MATCH(s, p, c)
Definition: date_parse.c:267
#define ISALNUM(c)
Definition: ruby.h:1635
rb_atomic_t cnt[RUBY_NSIG]
Definition: signal.c:432
#define T_STRING
#define MBCLEN_CHARFOUND_P(ret)
static double one(void)
Definition: isinf.c:52
#define evstr2dstr(n)
Definition: parse.y:401
unsigned char OnigUChar
Definition: ripper.y:114
#define NODE_ARGSCAT
#define NODE_COLON2
NODE * rb_parser_append_print(VALUE vparser, NODE *node)
Definition: ripper.c:16460
keyword_BEGIN
Definition: parse.y:1029
#define RE_OPTION_ENCODING_NONE(o)
Definition: parse.y:527
#define xmalloc
#define xrealloc
static void ripper_init_eventids1(void)
Definition: eventids1.c:134
int argc
Definition: ruby.c:130
#define NIL_P(v)
char ary[RSTRING_EMBED_LEN_MAX+1]
Definition: ripper.y:853
static NODE * parser_compile_string(volatile VALUE vparser, const char *f, VALUE s, int line)
Definition: ripper.c:12011
#define NEW_ARGS_AUX(r, b)
static const struct vtable * dyna_push_gen(struct parser_params *)
#define TypedData_Wrap_Struct(klass, data_type, sval)
#define RSTRING_NOEMBED
static VALUE coverage(const char *f, int n)
Definition: ripper.c:11866
static VALUE lex_get_str(struct parser_params *parser, VALUE s)
Definition: ripper.c:11968
static int rb_enc_symname_type(const char *name, long len, rb_encoding *enc, unsigned int allowed_atttset)
Definition: ripper.c:16685
#define ISUPPER(c)
Definition: ruby.h:1633
#define RUBY_FUNC_EXPORTED
Definition: defines.h:184
VALUE rb_suppress_tracing(VALUE(*func)(VALUE), VALUE arg)
Definition: vm_trace.c:345
#define rb_warn0(fmt)
Definition: parse.y:635
static NODE * block_append_gen(struct parser_params *, NODE *, NODE *)
VALUE rb_enc_associate_index(VALUE obj, int idx)
Definition: encoding.c:748
int rb_parse_in_main(void)
Definition: compile.c:5882
static int parser_nextc(struct parser_params *parser)
Definition: ripper.c:12131
int err
Definition: win32.c:87
#define ESCAPE_CONTROL
#define dyna_in_block()
Definition: parse.y:512
const char * parser_lex_pend
Definition: ripper.c:317
#define NEW_DEFINED(e)
#define DBL2NUM(dbl)
#define RE_OPTION_MASK
Definition: parse.y:528
#define in_defined
Definition: parse.y:322
static void block_dup_check_gen(struct parser_params *, NODE *, NODE *)
#define ALLOCA_N(type, n)
static int local_id_gen(struct parser_params *, ID)
#define rb_backref_error(n)
Definition: parse.y:434
#define ENC_CODERANGE_UNKNOWN
void rb_gc_mark_symbols(void)
Definition: ripper.c:16626
long cnt
Definition: ripper.y:262
ID token
Definition: ripper.c:16533
static ID intern_str(VALUE str)
Definition: ripper.c:16856
Definition: ripper.y:116
NODE * rb_parser_while_loop(VALUE vparser, NODE *node, int chop, int split)
Definition: ripper.c:16492
primary_value operation2 command_args prec tLOWEST
Definition: parse.y:1401
Definition: util.c:791
#define token_info_push(token)
Definition: parse.y:678
static void rb_backref_error_gen(struct parser_params *, NODE *)
NODE * rb_compile_cstr(const char *f, const char *s, int len, int line)
Definition: ripper.c:12044
token_info * parser_token_info
Definition: ripper.c:342
Definition: ripper.y:123
static int lvar_defined_gen(struct parser_params *, ID)
static void magic_comment_encoding(struct parser_params *parser, const char *name, const char *val)
Definition: ripper.c:13165
int column
Definition: ripper.c:273
#define parser_is_identchar()
#define END(no)
Definition: re.c:26
#define lex_state
Definition: parse.y:311
#define EOF
Definition: vsnprintf.c:207
VALUE rb_str_buf_cat(VALUE, const char *, long)
Definition: string.c:1948
#define ruby_verbose
void * rb_parser_malloc(struct parser_params *parser, size_t size)
Definition: ripper.c:17509
VALUE rb_str_dup(VALUE)
Definition: string.c:946
mlhs_head tSTAR
Definition: parse.y:1542
static NODE * new_attr_op_assign_gen(struct parser_params *parser, NODE *lhs, ID attr, ID op, NODE *rhs)
#define tHEREDOC_END
Definition: eventids2.c:8
#define rb_long2int(n)
#define ID_CLASS
static int parser_peek_variable_name(struct parser_params *parser)
Definition: ripper.c:12761
#define NEW_LASGN(v, val)
node_type
Definition: ripper.y:23
static VALUE yycompile0(VALUE arg)
Definition: ripper.c:11889
VALUE rb_obj_as_string(VALUE)
Definition: string.c:895
#define NODE_MEMO
#define NEW_OPT_ARG(i, v)
VALUE rb_hash_aset(VALUE, VALUE, VALUE)
string_type
Definition: ripper.c:12097
mlhs_inner mlhs_basic
Definition: parse.y:1495
int rb_dvar_defined(ID id)
Definition: compile.c:5832
#define lex_gets
Definition: parse.y:337
static int arg_var_gen(struct parser_params *, ID)
static void dispose_string(VALUE str)
Definition: ripper.c:12541
#define IS_SPCARG(c)
#define arg_ambiguous()
VALUE rb_str_resize(VALUE, long)
Definition: string.c:1854
static int reg_fragment_check_gen(struct parser_params *, VALUE, int)
int parser_in_single
Definition: ripper.c:302
#define RTEST(v)
lex_state_bits
Definition: ripper.c:125
int st_foreach(st_table *, int(*)(ANYARGS), st_data_t)
Definition: st.c:1000
#define NEW_SCLASS(r, b)
#define RUBY_DTRACE_PARSE_END_ENABLED()
Definition: probes.h:71
#define void_expr(node)
Definition: parse.y:377
ID rest_arg
Definition: ripper.y:514
#define node_assign(node1, node2)
Definition: parse.y:436
#define ret_args(node)
Definition: parse.y:416
SSL_METHOD *(* func)(void)
Definition: ossl_ssl.c:108
#define set_yylval_name(x)
int errno
#define TRUE
Definition: nkf.h:175
int rb_symname_p(const char *name)
Definition: ripper.c:16670
#define NODE_NIL
VALUE rb_thread_current(void)
Definition: thread.c:2352
#define tok()
#define NODE_ATTRASGN
VALUE rb_range_new(VALUE, VALUE, int)
Definition: range.c:67
VALUE rb_sprintf(const char *format,...)
Definition: sprintf.c:1270
#define NODE_COLON3
#define StringValue(v)
#define NODE_DEFINED
#define rb_enc_mbcput(c, buf, enc)
#define in_def
Definition: parse.y:319
static ID formal_argument_gen(struct parser_params *, ID)
#define lex_strterm
Definition: parse.y:310
static void set_file_encoding(struct parser_params *parser, const char *str, const char *send)
Definition: ripper.c:13336
#define NEW_DOT2(b, e)
static NODE * ret_args_gen(struct parser_params *, NODE *)
#define NODE_MASGN
#define T_REGEXP
#define nd_nth
static NODE * new_const_op_assign_gen(struct parser_params *parser, NODE *lhs, ID op, NODE *rhs)
int rb_is_attrset_name(VALUE name)
Definition: ripper.c:17251
#define rb_warnS(fmt, a)
Definition: parse.y:637
#define NEW_DASGN(v, val)
#define NEW_VALIAS(n, o)
#define read_escape(flags, e)
#define parser_isascii()
int rb_enc_symname_p(const char *name, rb_encoding *enc)
Definition: ripper.c:16676
#define NEW_POSTARG(i, v)
#define here_document(n)
#define CONST_ID(var, str)
#define NEW_ERRINFO()
#define tok_hex(numlen)
static const struct magic_comment magic_comments[]
Definition: ripper.c:13201
void Init_sym(void)
Definition: ripper.c:16607
static void local_pop_gen(struct parser_params *)
#define NODE_CONST
static int parser_parse_string(struct parser_params *, NODE *)
Definition: ripper.c:12797
#define heredoc_end
Definition: parse.y:333
static NODE * literal_concat_gen(struct parser_params *, NODE *, NODE *)
#define IS_lex_state(ls)
Definition: parse.y:100
static void void_expr_gen(struct parser_params *, NODE *)
int rb_is_local_id(ID id)
Definition: ripper.c:17129
rb_magic_comment_length_t length
Definition: ripper.c:13198
int parser_in_def
Definition: ripper.c:303
static NODE * negate_lit(NODE *)
int rb_scan_args(int argc, const VALUE *argv, const char *fmt,...)
Definition: class.c:1570
#define NEW_SUPER(a)
#define no_digits()
mlhs mlhs_inner
Definition: ripper.y:1484
#define NEW_COLON2(c, i)
static int dyna_in_block_gen(struct parser_params *)
static void fixup_nodes(NODE **)
VALUE parser_cur_mid
Definition: ripper.c:306
unsigned char buf[MIME_BUF_SIZE]
Definition: nkf.c:4308
#define NEW_STRTERM(func, term, paren)
VALUE rb_io_gets(VALUE)
Definition: io.c:3110
static void Init_id(void)
Definition: ripper.y:15
#define is_junk_id(id)
Definition: parse.y:59
long parser_lex_gets_ptr
Definition: ripper.c:321
#define NODE_GVAR
#define NODE_CDECL
#define CMDARG_PUSH(n)
Definition: parse.y:118
rb_encoding * rb_usascii_encoding(void)
Definition: encoding.c:1183
#define NEW_HASH(a)
#define reg_named_capture_assign(regexp, match)
Definition: parse.y:459
#define arg_concat(h, t)
Definition: parse.y:394
Definition: ripper.y:94
#define RARRAY_PTR(a)
union RNode::@82 u3
static void arg_ambiguous_gen(struct parser_params *parser)
Definition: ripper.c:13068
static void parser_prepare(struct parser_params *parser)
Definition: ripper.c:13379
#define RB_GC_GUARD(v)
#define set_yylval_id(x)
#define NODE_LIT
#define rb_reserved_word(str, len)
Definition: lex.c:37
int type
Definition: tcltklib.c:111
int id[2]
Definition: lex.c:33
static int options(unsigned char *cp)
Definition: nkf.c:6355
#define NEW_UNTIL(c, b, n)
stmt_or_begin
Definition: parse.y:1003
#define T_FIXNUM
#define NEW_MATCH3(r, n2)
VALUE rb_str_buf_new(long)
Definition: string.c:777
stack_type parser_cond_stack
Definition: ripper.c:297
#define ESCAPE_META
static VALUE result
Definition: nkf.c:40
NODE * post_init
Definition: ripper.y:507
static void ripper_init_eventids2(void)
Definition: eventids2.c:64
int rb_const_defined_at(VALUE, ID)
Definition: variable.c:2109
int rb_is_junk_id(ID id)
Definition: ripper.c:17135
static void dyna_pop_1(struct parser_params *parser)
Definition: ripper.c:16220
static int parser_read_escape(struct parser_params *parser, int flags, rb_encoding **encp)
Definition: ripper.c:12334
int parser_heredoc_end
Definition: ripper.c:318
static void new_bv_gen(struct parser_params *, ID)
static int parser_heredoc_identifier(struct parser_params *parser)
Definition: ripper.c:12855
Definition: ripper.y:101
#define str_copy(_s, _p, _n)
ID rb_id_attrset(ID id)
Definition: ripper.c:15277
Definition: ripper.y:72
int post_args_num
Definition: ripper.y:510
#define regx_options()
int rb_is_global_id(ID id)
Definition: ripper.c:17111
#define rb_node_newnode(type, a1, a2, a3)
Definition: parse.y:362
#define NEW_SELF()
VALUE rb_attr_get(VALUE, ID)
Definition: variable.c:1122
#define rb_enc_ispunct(c, enc)
VALUE rb_ensure(VALUE(*b_proc)(ANYARGS), VALUE data1, VALUE(*e_proc)(ANYARGS), VALUE data2)
Definition: eval.c:804
VALUE flags
Definition: ripper.y:700
#define NEW_RESBODY(a, ex, n)
#define NEW_RETURN(s)
#define NODE_ARGSPUSH
#define NODE_BACK_REF
#define NODE_MATCH
#define is_instance_id(id)
Definition: parse.y:55
#define tokadd(c)
#define set_yylval_str(x)
#define AREF(s, idx)
Definition: cparse.c:93
VALUE rb_reg_check_preprocess(VALUE)
Definition: re.c:2304
#define lvtbl
Definition: parse.y:338
VALUE flags
Definition: ripper.y:241
expr ripper_intern("and")
static int is_static_content(NODE *node)
Definition: ripper.c:15645
static ID shadowing_lvar_gen(struct parser_params *, ID)
const char * token
Definition: ripper.c:271
static NODE * arg_concat_gen(struct parser_params *, NODE *, NODE *)
RUBY_EXTERN VALUE rb_cString
Definition: ripper.y:1456
#define NEW_COLON3(i)
#define RUBY_DTRACE_PARSE_BEGIN_ENABLED()
Definition: probes.h:67
#define NEW_CASE(h, b)
top_stmt
Definition: parse.y:906
#define value_expr(node)
Definition: parse.y:375
#define NODE_DASGN
int parser_in_defined
Definition: ripper.c:307
#define reg_fragment_setenc(str, options)
Definition: parse.y:455
#define NEW_BACK_REF(n)
VALUE rb_vsprintf(const char *, va_list)
Definition: sprintf.c:1264
#define new_bv(id)
Definition: parse.y:492
int parser_class_nest
Definition: ripper.c:299
#define T_BIGNUM
#define DVARS_INHERIT
Definition: parse.y:138
#define MEMCPY(p1, p2, type, n)
#define ruby_eval_tree
Definition: parse.y:346
block_command cmd_brace_block
Definition: parse.y:1338
#define ruby__end__seen
Definition: parse.y:339
#define dvar_curr(id)
Definition: parse.y:518
Definition: ripper.y:122
static void vtable_free(struct vtable *tbl)
Definition: parse.y:169
#define NEW_IF(c, t, e)
#define dyna_pop(node)
Definition: parse.y:510
arg
Definition: parse.y:1316
#define logop(type, node1, node2)
Definition: parse.y:367
#define NEW_GASGN(v, val)
VALUE stack_type
Definition: parse.y:106
#define PARSER_ARG
Definition: parse.y:663
static void warning_unless_e_option(struct parser_params *parser, NODE *node, const char *str)
Definition: ripper.c:15702
#define NEW_ARGSPUSH(a, b)
int rb_is_const_name(VALUE name)
Definition: ripper.c:17227
static void parser_tokaddmbc(struct parser_params *parser, int c, rb_encoding *enc)
Definition: ripper.c:12425
int rb_is_local_name(VALUE name)
Definition: ripper.c:17257
static NODE * logop_gen(struct parser_params *, enum node_type, NODE *, NODE *)
#define assignable(id, node)
Definition: parse.y:426
VALUE rb_str_cat(VALUE, const char *, long)
Definition: string.c:1964
#define NEW_XSTR(s)
Definition: ripper.y:111
#define ENC_CODERANGE_7BIT
rb_encoding * rb_enc_get(VALUE obj)
Definition: encoding.c:772
#define NEW_WHILE(c, b, n)
#define NEW_DEFS(r, i, a, d)
void rb_gc_mark_parser(void)
Definition: ripper.c:16455
int nonspc
Definition: ripper.c:274
int size
Definition: encoding.c:52
#define f
#define deferred_nodes
Definition: parse.y:335
static int is_private_local_id(ID name)
Definition: ripper.c:15199
#define SYMBOL_P(x)
#define IS_lex_state_for(x, ls)
Definition: parse.y:99
static void no_blockarg(struct parser_params *parser, NODE *node)
Definition: ripper.c:15855
#define NODE_FLIP3
#define POINTER_P(val)
Definition: parse.y:141
void rb_parser_free(struct parser_params *parser, void *ptr)
Definition: ripper.c:17549
#define Qundef
int parser_tokidx
Definition: ripper.c:309
#define ruby_coverage
Definition: parse.y:349
#define NODE_DVAR
#define is_local_id(id)
Definition: parse.y:53
Definition: ripper.y:92
Definition: ripper.y:127
VALUE coverage
Definition: ripper.c:338
#define COND_POP()
Definition: parse.y:114
VALUE rb_external_str_new_with_enc(const char *ptr, long len, rb_encoding *)
Definition: string.c:569
void rb_set_errinfo(VALUE err)
Definition: eval.c:1436
#define rb_enc_isspace(c, enc)
static ID register_symid_str(ID, VALUE)
NODE * parser_lex_strterm
Definition: ripper.c:295
const char * name
Definition: ripper.c:13196
#define NEW_IVAR(v)
top_stmts dispatch0(stmts_new)
#define tSP
Definition: eventids2.c:6
#define COND_P()
Definition: parse.y:116
#define NEW_ATTRASGN(r, m, a)
#define aryset(node1, node2)
Definition: parse.y:429
#define NODE_ZARRAY
#define ruby_sourcefile
Definition: parse.y:341
static int token_info_get_column(struct parser_params *parser, const char *token)
Definition: ripper.c:11711
static const struct st_hash_type symhash
Definition: ripper.c:16574
#define new_const_op_assign(lhs, op, rhs)
Definition: parse.y:442
static NODE * new_evstr_gen(struct parser_params *, NODE *)
#define arg_var(id)
Definition: parse.y:501
#define STR_FUNC_SYMBOL
#define NEW_BEGIN(b)
NODE * pre_init
Definition: ripper.y:506
#define NEW_FCALL(m, a)
#define NODE_CVAR
#define NEW_SCOPE(a, b)
static int token_info_has_nonspaces(struct parser_params *parser, const char *token)
Definition: ripper.c:11725
st_index_t rb_str_hash(VALUE)
Definition: string.c:2245
#define NEW_OP_ASGN2(r, i, o, val)
#define NODE_BREAK
static const rb_data_type_t parser_data_type
Definition: ripper.c:12008
rb_magic_comment_setter_t func
Definition: ripper.c:13197
static int value_expr_gen(struct parser_params *, NODE *)
int parser_lpar_beg
Definition: ripper.c:301
void rb_compile_warning(const char *file, int line, const char *fmt,...)
Definition: error.c:185
#define STR_FUNC_QWORDS
st_table * sym_id
Definition: ripper.c:16565
RUBY_EXTERN VALUE rb_cObject
Definition: ripper.y:1426
#define ALLOC_N(type, n)
#define cur_mid
Definition: parse.y:321
uint8_t key[16]
Definition: random.c:1370
#define LONG2FIX(i)
#define NODE_FL_NEWLINE
#define rb_intern(str)
#define dvar_defined(id)
Definition: parse.y:515
#define CMDARG_P()
Definition: parse.y:121
#define RBASIC(obj)
struct local_vars * prev
Definition: ripper.c:192
#define NEW_VCALL(m)
#define ifndef_ripper(x)
Definition: parse.y:628
static int vtable_included(const struct vtable *tbl, ID id)
Definition: parse.y:196
struct vtable * vars
Definition: ripper.c:190
#define DEF_EXPR(n)
Definition: parse.y:83
static VALUE lex_io_gets(struct parser_params *parser, VALUE io)
Definition: ripper.c:12058
static NODE * splat_array(NODE *)
#define INT2NUM(x)
#define NODE_DSTR
#define STR_NEW0()
Definition: parse.y:301
struct rb_encoding_entry * list
Definition: encoding.c:50
#define NEW_RETRY()
void * rb_parser_calloc(struct parser_params *parser, size_t nelem, size_t size)
Definition: ripper.c:17519
#define STRNCASECMP(s1, s2, n)
rb_encoding * rb_filesystem_encoding(void)
Definition: encoding.c:1248
VALUE rb_make_backtrace(void)
Definition: vm_backtrace.c:772
#define STR_FUNC_EXPAND
v
Definition: win32ole.c:798
mlhs_inner mlhs_head mlhs_item
Definition: parse.y:1517
#define flush_string_content(enc)
#define STR_FUNC_ESCAPE
int linenum
Definition: ripper.c:272
#define NEW_CVAR(v)
#define dsym_node(node)
Definition: parse.y:421
static NODE * aryset_gen(struct parser_params *, NODE *, NODE *)
#define RUBY_TOKEN(t)
#define tEMBDOC
Definition: eventids2.c:4
Definition: ripper.y:121
#define NODE_BEGIN
static int dvar_defined_gen(struct parser_params *, ID, int)
#define block_append(h, t)
Definition: parse.y:386
char * parser_tokenbuf
Definition: ripper.c:308
VALUE rb_cArray
Definition: array.c:29
static const char * magic_comment_marker(const char *str, long len)
Definition: ripper.c:13209
#define BEG(no)
Definition: re.c:25
#define NEW_OP_ASGN1(p, id, a)
static unsigned int hash(const char *str, unsigned int len)
Definition: lex.c:56
#define tokadd_mbchar(c)
#define is_asgn_or_id(id)
Definition: parse.y:62
static int parser_magic_comment(struct parser_params *parser, const char *str, long len)
Definition: ripper.c:13242
int parser_tokline
Definition: ripper.c:311
Definition: ripper.y:79
#define ripper_flush(p)
VALUE rb_ary_new2(long capa)
Definition: array.c:417
#define lpar_beg
Definition: parse.y:316
static const char id_type_names[][9]
Definition: ripper.c:15265
VALUE rb_str_new(const char *, long)
Definition: string.c:425
union RNode::@80 u1
const char * parser_lex_pbeg
Definition: ripper.c:315
int rb_is_class_id(ID id)
Definition: ripper.c:17105
#define cond(node)
Definition: parse.y:365
#define rb_safe_level()
Definition: tcltklib.c:94
VALUE rb_parser_new(void)
Definition: ripper.c:17434
#define NODE_CVASGN
Definition: ripper.c:181
static VALUE reg_compile_gen(struct parser_params *, VALUE, int)
static void parser_set_encode(struct parser_params *parser, const char *name)
Definition: ripper.c:13117
#define NEW_CDECL(v, val, path)
static int literal_node(NODE *node)
Definition: ripper.c:15755
#define lex_gets_ptr
Definition: parse.y:336
const char * parser_lex_p
Definition: ripper.c:316
const char * name
Definition: nkf.c:208
#define tokenbuf
Definition: parse.y:323
#define nd_lit
static int parser_tok_hex(struct parser_params *parser, size_t *numlen)
Definition: ripper.c:12242
#define is_global_id(id)
Definition: parse.y:54
#define rb_enc_asciicompat(enc)
lex_state_e
Definition: ripper.c:140
#define NUM2INT(x)
#define nd_head
int rb_is_instance_name(VALUE name)
Definition: ripper.c:17245
int parser_ruby_sourceline
Definition: ripper.c:328
const char * rb_id2name(ID id)
Definition: ripper.c:17058
#define NODE_CALL
#define lex_goto_eol(parser)
#define rb_errinfo()
Definition: tcltklib.c:89
#define rb_enc_isupper(c, enc)
#define PRIsVALUE
static int nodeline(NODE *node)
Definition: ripper.c:14735
YYSTYPE * parser_yylval
Definition: ripper.c:292
#define new_attr_op_assign(lhs, type, attr, op, rhs)
Definition: parse.y:440
#define xcalloc
#define lex_input
Definition: parse.y:327
#define NEW_LIT(l)
#define rb_enc_isascii(c, enc)
int rb_str_hash_cmp(VALUE, VALUE)
Definition: string.c:2255
#define tokaddmbc(c, enc)
#define dyna_push()
Definition: parse.y:508
#define in_single
Definition: parse.y:318
int is_ripper
Definition: ripper.c:289
static NODE * cond0(struct parser_params *, NODE *)
Definition: ripper.c:15776
rb_encoding * rb_ascii8bit_encoding(void)
Definition: encoding.c:1153
int rb_is_junk_name(VALUE name)
Definition: ripper.c:17273
#define NODE_IVAR
#define RREGEXP(obj)
int rb_enc_find_index(const char *name)
Definition: encoding.c:635
VALUE eofp
Definition: ripper.c:293
RUBY_FUNC_EXPORTED const unsigned int ruby_global_name_punct_bits[(0x7e-0x20+31)/32]
Definition: ripper.c:12732
#define reduce_nodes(n)
Definition: parse.y:381
#define pushback(c)
long len
Definition: ripper.y:846
NODE * heap
Definition: ripper.c:290
#define RSTRING_GETMEM(str, ptrvar, lenvar)
#define STR_NEW(p, n)
Definition: parse.y:300
ID rb_intern3(const char *name, long len, rb_encoding *enc)
Definition: ripper.c:16834
#define NODE_DOT2
#define compile_error
Definition: parse.y:662
#define tokfix()
#define void_expr0(node)
Definition: parse.y:376
#define rb_warnI(fmt, a)
Definition: parse.y:636
#define ID_SCOPE_MASK
#define peek(c)
static ID register_symid(ID, const char *, long, rb_encoding *)
Definition: ripper.c:16798
#define NODE_DREGX
#define NODE_IASGN
#define NEW_DEFN(i, a, d, p)
#define ENC_SINGLE(cr)
Definition: parse.y:304
static NODE * new_args_gen(struct parser_params *, NODE *, NODE *, ID, NODE *, NODE *)
#define NODE_RETURN
#define snprintf
#define toklast()
ID first_post_arg
Definition: ripper.y:512
void * rb_parser_realloc(struct parser_params *parser, void *ptr, size_t size)
Definition: ripper.c:17529
#define NEW_REDO()
st_table * st_init_numtable_with_size(st_index_t)
Definition: st.c:278
VALUE rb_cstr_to_inum(const char *str, int base, int badcheck)
Definition: bignum.c:579
#define new_evstr(n)
Definition: parse.y:399
#define NODE_ARRAY
#define NODE_SPLAT
int rb_parse_in_eval(void)
Definition: compile.c:5876
#define ENCODING_SET(obj, i)
#define internal_id()
Definition: parse.y:505
int rb_memcicmp(const void *, const void *, long)
Definition: re.c:80
static NODE * list_concat_gen(struct parser_params *, NODE *, NODE *)
#define tCOMMENT
Definition: eventids2.c:2
#define NEW_ZSUPER()
ID rb_intern2(const char *name, long len)
Definition: ripper.c:16969
#define tokadd_string(f, t, p, n, e)
NODE * rb_compile_file(const char *f, VALUE file, int start)
Definition: ripper.c:12064
static int is_special_global_name(const char *m, const char *e, rb_encoding *enc)
Definition: ripper.c:16644
#define lex_nextline
Definition: parse.y:329
#define nd_line(n)
VALUE rb_parser_get_yydebug(VALUE self)
Definition: ripper.c:17478
static ID internal_id_gen(struct parser_params *)
VALUE(* parser_lex_gets)(struct parser_params *, VALUE)
Definition: ripper.c:322
#define NULL
Definition: _sdbm.c:103
#define IS_LABEL_POSSIBLE()
#define rb_enc_isalpha(c, enc)
#define tIGNORED_NL
Definition: eventids2.c:1
NODE * rb_parser_compile_cstr(volatile VALUE vparser, const char *f, const char *s, int len, int line)
Definition: ripper.c:12051
#define compile_for_eval
Definition: parse.y:320
#define id_type(id)
Definition: parse.y:60
static int rb_str_symname_type(VALUE name, unsigned int allowed_atttset)
Definition: ripper.c:16788
struct token_info token_info
VALUE rb_check_string_type(VALUE)
Definition: string.c:1509
#define Qnone
Definition: parse.y:627
#define REALLOC_N(var, type, n)
#define NODE_SCOPE
command_call
Definition: parse.y:1308
error stmt
Definition: parse.y:1019
int rb_enc_str_coderange(VALUE)
Definition: string.c:327
#define ISXDIGIT(c)
Definition: ruby.h:1638
#define set_yylval_literal(x)
int rb_local_defined(ID id)
Definition: compile.c:5857
st_index_t num_entries
Definition: ripper.y:93
NODE * parser_eval_tree_begin
Definition: ripper.c:335
static int match(VALUE str, VALUE pat, VALUE hash, int(*cb)(VALUE, VALUE))
Definition: date_parse.c:273
void rb_define_method(VALUE klass, const char *name, VALUE(*func)(ANYARGS), int argc)
Definition: class.c:1344
static void dyna_pop_gen(struct parser_params *, const struct vtable *)
static void warn_unless_e_option(struct parser_params *parser, NODE *node, const char *str)
Definition: ripper.c:15696
#define NODE_IASGN2
#define ULONG2NUM(x)
#define NODE_SELF
#define rb_warning0(fmt)
Definition: parse.y:639
#define SYM2ID(x)
#define ID_CONST
#define tokadd_escape(e)
VALUE rb_eArgError
Definition: error.c:512
static struct vtable * vtable_alloc(struct vtable *prev)
Definition: parse.y:157
#define NEW_ARRAY(a)
Definition: ripper.y:93
void rb_str_free(VALUE)
Definition: string.c:830
static ID * local_tbl_gen(struct parser_params *)
#define VTBL_DEBUG
Definition: parse.y:154
#define IS_AFTER_OPERATOR()
#define RTYPEDDATA_TYPE(v)
unsigned long ruby_scan_oct(const char *, size_t, size_t *)
Definition: util.c:28
#define NODE_VALUES
#define ID_ATTRSET
struct vtable * args
Definition: ripper.c:189
#define was_bol()
Definition: ripper.y:136
#define IDSET_ATTRSET_FOR_INTERN
#define parser_warn(node, mesg)
char ** argv
Definition: ruby.c:131
#define tEMBDOC_END
Definition: eventids2.c:5
#define STR_NEW2(p)
Definition: parse.y:302
keyword_return call_args
Definition: parse.y:1461
static void ripper_init_eventids2_table(VALUE self)
Definition: eventids2table.c:2
#define reg_fragment_check(str, options)
Definition: parse.y:457
static int vtable_size(const struct vtable *tbl)
Definition: parse.y:144
#define NEW_YIELD(a)
#define ISSPACE(c)
Definition: ruby.h:1632
#define parser_encoding_name()
VALUE rb_enc_str_buf_cat(VALUE str, const char *ptr, long len, rb_encoding *enc)
Definition: string.c:2075
VALUE rb_inspect(VALUE)
Definition: object.c:402
static int sym_check_asciionly(VALUE str)
Definition: ripper.c:16814
static void void_stmts_gen(struct parser_params *, NODE *)
#define is_notop_id(id)
Definition: parse.y:52
rb_encoding * rb_enc_from_index(int index)
Definition: encoding.c:548
#define brace_nest
Definition: parse.y:317
#define yyerror(msg)
Definition: parse.y:308
#define NEW_BLOCK_PASS(b)
NODE * opt_args
Definition: ripper.y:520
#define tokcopy(n)
#define numberof(array)
#define parse_string(n)
int rb_is_global_name(VALUE name)
Definition: ripper.c:17239
static int parser_tokadd_mbchar(struct parser_params *parser, int c)
Definition: ripper.c:12548