summaryrefslogtreecommitdiff
path: root/compile.c
diff options
context:
space:
mode:
authorJeremy Evans <code@jeremyevans.net>2022-07-20 15:09:20 -0700
committerJeremy Evans <code@jeremyevans.net>2022-08-09 22:19:46 -0700
commit9363b0423a0269272eff2e243d4b55bc8d135430 (patch)
treeaee5131097d7b12dd4e811acfd9cc0402e20f3f8 /compile.c
parentfc4b4f2e8db3d68b80b9c7580c40a0165736006c (diff)
downloadruby-9363b0423a0269272eff2e243d4b55bc8d135430.tar.gz
Optimize duparray/expandarray -> putobject/expandarray
There's no point in making a copy of an array just to expand it. Saves an unnecessary array allocation in the multiple assignment case, with a 35-84% improvement in affected cases in benchmark/masgn.yml.
Diffstat (limited to 'compile.c')
-rw-r--r--compile.c14
1 files changed, 14 insertions, 0 deletions
diff --git a/compile.c b/compile.c
index 8879e661fe..484399abc6 100644
--- a/compile.c
+++ b/compile.c
@@ -3396,6 +3396,20 @@ iseq_peephole_optimize(rb_iseq_t *iseq, LINK_ELEMENT *list, const int do_tailcal
}
}
+ if (IS_INSN_ID(iobj, duparray)) {
+ LINK_ELEMENT *next = iobj->link.next;
+ /*
+ * duparray obj
+ * expandarray X, 0
+ * =>
+ * putobject obj
+ * expandarray X, 0
+ */
+ if (IS_INSN(next) && IS_INSN_ID(next, expandarray)) {
+ INSN_OF(iobj) = BIN(putobject);
+ }
+ }
+
if (IS_INSN_ID(iobj, anytostring)) {
LINK_ELEMENT *next = iobj->link.next;
/*