11#include "ruby/ruby.h"
22#include "ruby/thread.h"
3+ #include "ruby/io.h"
34#include "ruby/fiber/scheduler.h"
45
56/*
2425 */
2526
2627struct blocking_state {
28+ int notify_descriptor ;
2729 volatile int interrupted ;
2830};
2931
@@ -39,14 +41,14 @@ blocking_operation(void *argument)
3941{
4042 struct blocking_state * blocking_state = (struct blocking_state * )argument ;
4143
42- while (true) {
43- struct timeval tv = {1 , 0 }; // 1 second timeout.
44+ write (blocking_state -> notify_descriptor , "x" , 1 );
4445
46+ while (!blocking_state -> interrupted ) {
47+ struct timeval tv = {1 , 0 }; // 1 second timeout.
4548 int result = select (0 , NULL , NULL , NULL , & tv );
4649
4750 if (result == -1 && errno == EINTR ) {
4851 blocking_state -> interrupted = 1 ;
49- return NULL ;
5052 }
5153
5254 // Otherwise, timeout -> loop again.
@@ -56,9 +58,10 @@ blocking_operation(void *argument)
5658}
5759
5860static VALUE
59- scheduler_blocking_loop (VALUE self )
61+ scheduler_blocking_loop (VALUE self , VALUE notify )
6062{
6163 struct blocking_state blocking_state = {
64+ .notify_descriptor = rb_io_descriptor (notify ),
6265 .interrupted = 0 ,
6366 };
6467
@@ -84,5 +87,5 @@ Init_scheduler(void)
8487 VALUE mBug = rb_define_module ("Bug" );
8588 VALUE mScheduler = rb_define_module_under (mBug , "Scheduler" );
8689
87- rb_define_module_function (mScheduler , "blocking_loop" , scheduler_blocking_loop , 0 );
90+ rb_define_module_function (mScheduler , "blocking_loop" , scheduler_blocking_loop , 1 );
8891}
0 commit comments