summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Zhu <[email protected]>2024-01-11 12:27:50 -0500
committerPeter Zhu <[email protected]>2024-01-11 14:58:24 -0500
commit45dd8edf82d2648fed51b0e65f6fc1cf4473038d (patch)
tree619540f524d1ef751bfd375c35a64856421d080c
parentf2149dc094a92bd1aa29622f9585247d491f7a08 (diff)
[PRISM] Fix splat inside of aset
Fixes ruby/prism#2146.
-rw-r--r--prism_compile.c10
-rw-r--r--test/ruby/test_compile_prism.rb7
2 files changed, 16 insertions, 1 deletions
diff --git a/prism_compile.c b/prism_compile.c
index 9594be7065..cbae85b9f4 100644
--- a/prism_compile.c
+++ b/prism_compile.c
@@ -2645,9 +2645,17 @@ pm_compile_call(rb_iseq_t *iseq, const pm_call_node_t *call_node, LINK_ANCHOR *c
}
if (pm_node->flags & PM_CALL_NODE_FLAGS_ATTRIBUTE_WRITE) {
- if (!popped) {
+ if (flags & VM_CALL_ARGS_SPLAT) {
+ ADD_INSN(ret, &dummy_line_node, dup);
+ ADD_INSN1(ret, &dummy_line_node, putobject, INT2FIX(-1));
+ ADD_SEND_WITH_FLAG(ret, &dummy_line_node, idAREF, INT2FIX(1), INT2FIX(0));
+ ADD_INSN1(ret, &dummy_line_node, setn, INT2FIX(orig_argc + 2));
+ ADD_INSN (ret, &dummy_line_node, pop);
+ }
+ else if (!popped) {
ADD_INSN1(ret, &dummy_line_node, setn, INT2FIX(orig_argc + 1));
}
+
ADD_SEND_R(ret, &dummy_line_node, method_id, INT2FIX(orig_argc), block_iseq, INT2FIX(flags), kw_arg);
PM_POP_UNLESS_POPPED;
}
diff --git a/test/ruby/test_compile_prism.rb b/test/ruby/test_compile_prism.rb
index 835b3b819b..7115597903 100644
--- a/test/ruby/test_compile_prism.rb
+++ b/test/ruby/test_compile_prism.rb
@@ -1484,6 +1484,13 @@ module Prism
foo.[]=(1,2)
CODE
+ # With splat inside of []=
+ assert_prism_eval(<<~RUBY)
+ obj = Object.new
+ def obj.[]=(a, b); 10; end
+ obj[*[1]] = 3
+ RUBY
+
assert_prism_eval(<<-CODE)
def self.prism_opt_var_trail_hash(a = nil, *b, c, **d); end
prism_opt_var_trail_hash("a")