ruby-changes:65566
From: Aaron <ko1@a...>
Date: Thu, 18 Mar 2021 02:55:55 +0900 (JST)
Subject: [ruby-changes:65566] 17bf478de1 (master): Store strings for `defined` in the iseqs
https://git.ruby-lang.org/ruby.git/commit/?id=17bf478de1 From 17bf478de14d0dd9098df65282f7f419cd792599 Mon Sep 17 00:00:00 2001 From: Aaron Patterson <tenderlove@r...> Date: Tue, 16 Mar 2021 15:12:37 -0700 Subject: Store strings for `defined` in the iseqs We can know the string used for "defined" calls at compile time, then store the string in the instruction sequences --- compile.c | 36 +++++++++++++++++++++--------------- insns.def | 7 ++++++- iseq.c | 2 +- 3 files changed, 28 insertions(+), 17 deletions(-) diff --git a/compile.c b/compile.c index 3193be8..78870ee 100644 --- a/compile.c +++ b/compile.c @@ -4935,28 +4935,29 @@ defined_expr0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, https://github.com/ruby/ruby/blob/trunk/compile.c#L4935 expr_type = DEFINED_LVAR; break; +#define PUSH_VAL(type) (needstr == Qfalse ? Qtrue : rb_iseq_defined_string(type)) case NODE_IVAR: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_IVAR), - ID2SYM(node->nd_vid), needstr); + ID2SYM(node->nd_vid), PUSH_VAL(DEFINED_IVAR)); return; case NODE_GVAR: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_GVAR), - ID2SYM(node->nd_entry), needstr); + ID2SYM(node->nd_entry), PUSH_VAL(DEFINED_GVAR)); return; case NODE_CVAR: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_CVAR), - ID2SYM(node->nd_vid), needstr); + ID2SYM(node->nd_vid), PUSH_VAL(DEFINED_CVAR)); return; case NODE_CONST: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_CONST), - ID2SYM(node->nd_vid), needstr); + ID2SYM(node->nd_vid), PUSH_VAL(DEFINED_CONST)); return; case NODE_COLON2: if (!lfinish[1]) { @@ -4966,15 +4967,19 @@ defined_expr0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, https://github.com/ruby/ruby/blob/trunk/compile.c#L4967 ADD_INSNL(ret, line, branchunless, lfinish[1]); NO_CHECK(COMPILE(ret, "defined/colon2#nd_head", node->nd_head)); - ADD_INSN3(ret, line, defined, - (rb_is_const_id(node->nd_mid) ? - INT2FIX(DEFINED_CONST_FROM) : INT2FIX(DEFINED_METHOD)), - ID2SYM(node->nd_mid), needstr); + if (rb_is_const_id(node->nd_mid)) { + ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_CONST_FROM), + ID2SYM(node->nd_mid), PUSH_VAL(DEFINED_CONST)); + } + else { + ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_METHOD), + ID2SYM(node->nd_mid), PUSH_VAL(DEFINED_METHOD)); + } return; case NODE_COLON3: ADD_INSN1(ret, line, putobject, rb_cObject); ADD_INSN3(ret, line, defined, - INT2FIX(DEFINED_CONST_FROM), ID2SYM(node->nd_mid), needstr); + INT2FIX(DEFINED_CONST_FROM), ID2SYM(node->nd_mid), PUSH_VAL(DEFINED_CONST)); return; /* method dispatch */ @@ -4999,12 +5004,12 @@ defined_expr0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, https://github.com/ruby/ruby/blob/trunk/compile.c#L5004 ADD_INSNL(ret, line, branchunless, lfinish[1]); NO_CHECK(COMPILE(ret, "defined/recv", node->nd_recv)); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_METHOD), - ID2SYM(node->nd_mid), needstr); + ID2SYM(node->nd_mid), PUSH_VAL(DEFINED_METHOD)); } else { ADD_INSN(ret, line, putself); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_FUNC), - ID2SYM(node->nd_mid), needstr); + ID2SYM(node->nd_mid), PUSH_VAL(DEFINED_METHOD)); } return; } @@ -5012,7 +5017,7 @@ defined_expr0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, https://github.com/ruby/ruby/blob/trunk/compile.c#L5017 case NODE_YIELD: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_YIELD), 0, - needstr); + PUSH_VAL(DEFINED_YIELD)); return; case NODE_BACK_REF: @@ -5020,16 +5025,17 @@ defined_expr0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, https://github.com/ruby/ruby/blob/trunk/compile.c#L5025 ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_REF), INT2FIX((node->nd_nth << 1) | (type == NODE_BACK_REF)), - needstr); + PUSH_VAL(DEFINED_GVAR)); return; case NODE_SUPER: case NODE_ZSUPER: ADD_INSN(ret, line, putnil); ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_ZSUPER), 0, - needstr); + PUSH_VAL(DEFINED_ZSUPER)); return; +#undef PUSH_VAL case NODE_OP_ASGN1: case NODE_OP_ASGN2: case NODE_OP_ASGN_OR: @@ -8050,7 +8056,7 @@ iseq_compile_each0(rb_iseq_t *iseq, LINK_ANCHOR *const ret, const NODE *node, in https://github.com/ruby/ruby/blob/trunk/compile.c#L8056 lassign = NEW_LABEL(line); ADD_INSN(ret, line, dup); /* cref cref */ ADD_INSN3(ret, line, defined, INT2FIX(DEFINED_CONST_FROM), - ID2SYM(mid), Qfalse); /* cref bool */ + ID2SYM(mid), Qtrue); /* cref bool */ ADD_INSNL(ret, line, branchunless, lassign); /* cref */ } ADD_INSN(ret, line, dup); /* cref cref */ diff --git a/insns.def b/insns.def index e3c7ad5..55564c4 100644 --- a/insns.def +++ b/insns.def @@ -667,7 +667,12 @@ defined https://github.com/ruby/ruby/blob/trunk/insns.def#L667 (VALUE val) // attr bool leaf = leafness_of_defined(op_type); { - val = vm_defined(ec, GET_CFP(), op_type, obj, needstr, v); + if (vm_defined(ec, GET_CFP(), op_type, obj, Qfalse, v)) { + val = needstr; + } + else { + val = Qnil; + } } /* check `target' matches `pattern'. diff --git a/iseq.c b/iseq.c index 2d83bc3..f696df9 100644 --- a/iseq.c +++ b/iseq.c @@ -3105,7 +3105,7 @@ rb_iseq_defined_string(enum defined_type type) https://github.com/ruby/ruby/blob/trunk/iseq.c#L3105 const char *estr; VALUE *defs, str; - if ((unsigned)(type - 1) >= (unsigned)numberof(expr_names)) return 0; + if ((unsigned)(type - 1) >= (unsigned)numberof(expr_names)) rb_bug("unknown defined type %d", type); estr = expr_names[type - 1]; if (!estr[0]) return 0; defs = GET_VM()->defined_strings; -- cgit v1.1 -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/