Bug #16442

Segmentation fault when calling a method with array splat and empty kwargs splat

Added by tompng (tomoya ishida) 3 months ago. Updated 3 months ago.

Target version:
ruby -v:
ruby 2.7.0preview3 (2019-11-23 master b563439274) [x86_64-darwin19] 〜 ruby 2.7.0dev (2019-12-21T14:08:52Z master 85a337f986) [x86_64-linux]


a=[1];b(*a, 2, **{})

$ ruby -e "a=[1];b(*a, 2, **{})" 
-e:1: [BUG] Segmentation fault at 0x0000000000000005
ruby 2.7.0preview3 (2019-11-23 master b563439274) [x86_64-darwin19]
$ ./miniruby -e "a=[1];b(*a, 2, **{})" 
-e:1: [BUG] Segmentation fault at 0x0000000000000005
ruby 2.7.0dev (2019-12-14T15:21:19Z trunk db2ea9b0c5) [x86_64-darwin19]
$ ruby -ve "a=[nil];{}.instance_exec(*a, nil, **{}, &->(a,b){})" 
ruby 2.7.0dev (2019-12-21T14:08:52Z master 85a337f986) [x86_64-linux]
-e:1: [BUG] Segmentation fault at 0x0000000000000008
ruby 2.7.0dev (2019-12-21T14:08:52Z master 85a337f986) [x86_64-linux]

Updated by ko1 (Koichi Sasada) 3 months ago

same as: p(*nil, nil, **{})

(gdb) bt
#0  0x00005555557d6de0 in CALLER_REMOVE_EMPTY_KW_SPLAT (cfp=0x7ffff6bc4fa0, calling=<optimized out>, calling=<optimized out>, ci=0x555555c4e6e0)
    at /home/ko1/src/ruby/trunk/vm_insnhelper.c:1996
#1  vm_call_cfunc (ec=0x555555b14510, reg_cfp=0x7ffff6bc4fa0, calling=0x7fffffffe650, cd=0x555555c4e6a0) at /home/ko1/src/ruby/trunk/vm_insnhelper.c:2535
#2  0x00005555557eb3cc in vm_call_method_each_type (ec=0x555555b14510, cfp=0x7ffff6bc4fa0, calling=0x7fffffffe650, cd=0x555555c4e6a0)
    at /home/ko1/src/ruby/trunk/vm_insnhelper.c:2925
#3  0x00005555557ebb1e in vm_call_method (ec=0x555555b14510, cfp=0x7ffff6bc4fa0, calling=<optimized out>, cd=<optimized out>)
    at /home/ko1/src/ruby/trunk/vm_insnhelper.c:3053
#4  0x00005555557dab1e in vm_sendish (block_handler=<optimized out>, method_explorer=<optimized out>, cd=<optimized out>, reg_cfp=<optimized out>,
    ec=<optimized out>) at /home/ko1/src/ruby/trunk/vm_insnhelper.c:4023
#5  vm_exec_core (ec=0x1, initial=140737331875920) at ../../../src/ruby/trunk/insns.def:801
#6  0x00005555557e129b in rb_vm_exec (ec=0x555555b14510, mjit_enable_p=1) at /home/ko1/src/ruby/trunk/vm.c:1920
#7  0x00005555556192ba in rb_ec_exec_node (ec=ec@entry=0x555555b14510, n=n@entry=0x555555b24990) at /home/ko1/src/ruby/trunk/eval.c:277
#8  0x000055555561fcb9 in ruby_run_node (n=0x555555b24990) at /home/ko1/src/ruby/trunk/eval.c:335
#9  0x000055555557c2ff in main (argc=<optimized out>, argv=<optimized out>) at /home/ko1/src/ruby/trunk/main.c:50

Updated by mame (Yusuke Endoh) 3 months ago

  • Status changed from Open to Closed

Applied in changeset git|75acbd5f0076970d48bc423c2b058adbdb5da9e8.

compile.c: avoid newarraykwsplat for arguments

foo(*rest, post, **empty_kw) is compiled like
foo(*rest + [post, **empty_kw]), and **empty_kw is removed by
"newarraykwsplat" instruction.
However, the method call still has a flag of KW_SPLAT, so "post" is
considered as a keyword hash, which caused a segfault.
Note that the flag cannot be removed if "empty_kw" is not always empty.

This change fixes the issue by compiling arguments with "newarray"
instead of "newarraykwsplat".

[Bug #16442]

Also available in: Atom PDF