From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on dcvr.yhbt.net X-Spam-Level: X-Spam-ASN: X-Spam-Status: No, score=-4.0 required=3.0 tests=ALL_TRUSTED,AWL,BAYES_00 shortcircuit=no autolearn=ham autolearn_force=no version=3.4.2 Received: from localhost (dcvr.yhbt.net [127.0.0.1]) by dcvr.yhbt.net (Postfix) with ESMTP id CBEB6211B4 for ; Sat, 1 Dec 2018 06:38:52 +0000 (UTC) From: Eric Wong To: spew@80x24.org Subject: [PATCH] vm.c: alternative fix for [Bug #15362] UNVERIFIED DO NOT COMMIT Date: Sat, 1 Dec 2018 06:38:52 +0000 Message-Id: <20181201063852.30438-1-e@80x24.org> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit List-Id: UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT This is my hypothesis for [ruby-core:90203]. However, I cannot reproduce the original problem on GNU/Linux or FreeBSD (I don't use OSX where this problem manifests), so I cannot verify that it is correct. I also do not like this patch because it adds extra branches to a function for all platforms. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT. UNVERIFIED DO NOT COMMIT --- vm.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/vm.c b/vm.c index e86f4650f0..b3034a62e3 100644 --- a/vm.c +++ b/vm.c @@ -2432,6 +2432,17 @@ rb_thread_recycle_stack_release(VALUE *stack) ruby_xfree(stack); } +static int +ec_owner_alive_p(const rb_execution_context_t *ec) +{ + rb_thread_t *th = rb_ec_thread_ptr(ec); + + if (!th) return FALSE; + if (th == th->vm->main_thread) return TRUE; + + return th->status != THREAD_KILLED; +} + void rb_execution_context_mark(const rb_execution_context_t *ec) { @@ -2470,6 +2481,7 @@ rb_execution_context_mark(const rb_execution_context_t *ec) /* mark machine stack */ if (ec->machine.stack_start && ec->machine.stack_end && ec != GET_EC() /* marked for current ec at the first stage of marking */ + && ec_owner_alive_p(ec) ) { rb_gc_mark_machine_stack(ec); rb_gc_mark_locations((VALUE *)&ec->machine.regs, -- EW