mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
thread.c: interrupt queue on uninitialized thread
* thread.c (rb_thread_pending_interrupt_p): no pending interrupt before initialization. * thread.c (thread_raise_m, rb_thread_kill): uninitialized thread cannot interrupt. [ruby-core:72732] [Bug #11959] git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@53449 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
b032d111ab
commit
557a00f1aa
3 changed files with 38 additions and 2 deletions
|
@ -1,3 +1,11 @@
|
||||||
|
Thu Jan 7 14:49:12 2016 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
|
* thread.c (rb_thread_pending_interrupt_p): no pending interrupt
|
||||||
|
before initialization.
|
||||||
|
|
||||||
|
* thread.c (thread_raise_m, rb_thread_kill): uninitialized thread
|
||||||
|
cannot interrupt. [ruby-core:72732] [Bug #11959]
|
||||||
|
|
||||||
Thu Jan 7 11:34:14 2016 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
Thu Jan 7 11:34:14 2016 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
* include/ruby/backward.h (ruby_show_copyright_to_die): for source
|
* include/ruby/backward.h (ruby_show_copyright_to_die): for source
|
||||||
|
|
|
@ -748,9 +748,24 @@ _eom
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_uninitialized
|
def test_uninitialized
|
||||||
c = Class.new(Thread)
|
c = Class.new(Thread) {def initialize; end}
|
||||||
c.class_eval { def initialize; end }
|
|
||||||
assert_raise(ThreadError) { c.new.start }
|
assert_raise(ThreadError) { c.new.start }
|
||||||
|
|
||||||
|
bug11959 = '[ruby-core:72732] [Bug #11959]'
|
||||||
|
|
||||||
|
c = Class.new(Thread) {def initialize; exit; end}
|
||||||
|
assert_raise(ThreadError, bug11959) { c.new }
|
||||||
|
|
||||||
|
c = Class.new(Thread) {def initialize; raise; end}
|
||||||
|
assert_raise(ThreadError, bug11959) { c.new }
|
||||||
|
|
||||||
|
c = Class.new(Thread) {
|
||||||
|
def initialize
|
||||||
|
pending = pending_interrupt?
|
||||||
|
super {pending}
|
||||||
|
end
|
||||||
|
}
|
||||||
|
assert_equal(false, c.new.value, bug11959)
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_backtrace
|
def test_backtrace
|
||||||
|
|
13
thread.c
13
thread.c
|
@ -1559,6 +1559,14 @@ rb_threadptr_pending_interrupt_enque(rb_thread_t *th, VALUE v)
|
||||||
th->pending_interrupt_queue_checked = 0;
|
th->pending_interrupt_queue_checked = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
threadptr_check_pending_interrupt_queue(rb_thread_t *th)
|
||||||
|
{
|
||||||
|
if (!th->pending_interrupt_queue) {
|
||||||
|
rb_raise(rb_eThreadError, "uninitialized thread");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
enum handle_interrupt_timing {
|
enum handle_interrupt_timing {
|
||||||
INTERRUPT_NONE,
|
INTERRUPT_NONE,
|
||||||
INTERRUPT_IMMEDIATE,
|
INTERRUPT_IMMEDIATE,
|
||||||
|
@ -1866,6 +1874,9 @@ rb_thread_pending_interrupt_p(int argc, VALUE *argv, VALUE target_thread)
|
||||||
|
|
||||||
GetThreadPtr(target_thread, target_th);
|
GetThreadPtr(target_thread, target_th);
|
||||||
|
|
||||||
|
if (!target_th->pending_interrupt_queue) {
|
||||||
|
return Qfalse;
|
||||||
|
}
|
||||||
if (rb_threadptr_pending_interrupt_empty_p(target_th)) {
|
if (rb_threadptr_pending_interrupt_empty_p(target_th)) {
|
||||||
return Qfalse;
|
return Qfalse;
|
||||||
}
|
}
|
||||||
|
@ -2179,6 +2190,7 @@ thread_raise_m(int argc, VALUE *argv, VALUE self)
|
||||||
rb_thread_t *target_th;
|
rb_thread_t *target_th;
|
||||||
rb_thread_t *th = GET_THREAD();
|
rb_thread_t *th = GET_THREAD();
|
||||||
GetThreadPtr(self, target_th);
|
GetThreadPtr(self, target_th);
|
||||||
|
threadptr_check_pending_interrupt_queue(target_th);
|
||||||
rb_threadptr_raise(target_th, argc, argv);
|
rb_threadptr_raise(target_th, argc, argv);
|
||||||
|
|
||||||
/* To perform Thread.current.raise as Kernel.raise */
|
/* To perform Thread.current.raise as Kernel.raise */
|
||||||
|
@ -2223,6 +2235,7 @@ rb_thread_kill(VALUE thread)
|
||||||
rb_threadptr_to_kill(th);
|
rb_threadptr_to_kill(th);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
threadptr_check_pending_interrupt_queue(th);
|
||||||
rb_threadptr_pending_interrupt_enque(th, eKillSignal);
|
rb_threadptr_pending_interrupt_enque(th, eKillSignal);
|
||||||
rb_threadptr_interrupt(th);
|
rb_threadptr_interrupt(th);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue