diff options
| -rw-r--r-- | mrbgems/mruby-compiler/core/codegen.c | 20 | ||||
| -rw-r--r-- | mrbgems/mruby-compiler/core/parse.y | 22 |
2 files changed, 33 insertions, 9 deletions
diff --git a/mrbgems/mruby-compiler/core/codegen.c b/mrbgems/mruby-compiler/core/codegen.c index 3853814ec..f2bbf3497 100644 --- a/mrbgems/mruby-compiler/core/codegen.c +++ b/mrbgems/mruby-compiler/core/codegen.c @@ -2216,7 +2216,8 @@ codegen(codegen_scope *s, node *tree, int val) case NODE_REGX: if (val) { char *p1 = (char*)tree->car; - char *p2 = (char*)tree->cdr; + char *p2 = (char*)tree->cdr->car; + char *p3 = (char*)tree->cdr->cdr; int ai = mrb_gc_arena_save(s->mrb); int sym = new_sym(s, mrb_intern_lit(s->mrb, REGEXP_CLASS)); int off = new_lit(s, mrb_str_new_cstr(s->mrb, p1)); @@ -2226,11 +2227,22 @@ codegen(codegen_scope *s, node *tree, int val) genop(s, MKOP_ABx(OP_GETMCNST, cursp(), sym)); push(); genop(s, MKOP_ABx(OP_STRING, cursp(), off)); - if (p2) { + if (p2 || p3) { push(); - off = new_lit(s, mrb_str_new_cstr(s->mrb, p2)); - genop(s, MKOP_ABx(OP_STRING, cursp(), off)); + if (p2) { + off = new_lit(s, mrb_str_new_cstr(s->mrb, p2)); + genop(s, MKOP_ABx(OP_STRING, cursp(), off)); + } else { + genop(s, MKOP_A(OP_LOADNIL, cursp())); + } argc++; + if (p3) { + push(); + off = new_lit(s, mrb_str_new(s->mrb, p3, 1)); + genop(s, MKOP_ABx(OP_STRING, cursp(), off)); + argc++; + pop(); + } pop(); } pop(); diff --git a/mrbgems/mruby-compiler/core/parse.y b/mrbgems/mruby-compiler/core/parse.y index 097d63ac4..2b0591769 100644 --- a/mrbgems/mruby-compiler/core/parse.y +++ b/mrbgems/mruby-compiler/core/parse.y @@ -761,9 +761,9 @@ new_dsym(parser_state *p, node *a) /* (:str . (a . a)) */ static node* -new_regx(parser_state *p, const char *p1, const char* p2) +new_regx(parser_state *p, const char *p1, const char* p2, const char* p3) { - return cons((node*)NODE_REGX, cons((node*)p1, (node*)p2)); + return cons((node*)NODE_REGX, cons((node*)p1, cons((node*)p2, (node*)p3))); } /* (:dregx . a) */ @@ -3986,6 +3986,8 @@ parse_string(parser_state *p) char *s = strndup(tok(p), toklen(p)); char flags[3]; char *flag = flags; + char enc = '\0'; + char *encp; char *dup; newtok(p); @@ -3994,6 +3996,8 @@ parse_string(parser_state *p) case 'i': f |= 1; break; case 'x': f |= 2; break; case 'm': f |= 4; break; + case 'u': f |= 16; break; + case 'n': f |= 32; break; default: tokadd(p, re_opt); break; } } @@ -4009,12 +4013,20 @@ parse_string(parser_state *p) if (f & 1) *flag++ = 'i'; if (f & 2) *flag++ = 'x'; if (f & 4) *flag++ = 'm'; - dup = strndup(flags, (size_t)(flag - flags)); + if (f & 16) enc = 'u'; + if (f & 32) enc = 'n'; } - else { + if (flag > flags) { + dup = strndup(flags, (size_t)(flag - flags)); + } else { dup = NULL; } - yylval.nd = new_regx(p, s, dup); + if (enc) { + encp = strndup(&enc, 1); + } else { + encp = NULL; + } + yylval.nd = new_regx(p, s, dup, encp); return tREGEXP; } |
