io-event 0.3.3 → 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 889604c87afea8f1d84e1ee40ada077792e84cfa77d074d695bf6cc1f27b69e1
4
- data.tar.gz: c46aada520c6a8ba41918c7c3f794922befc5012fc9fe5954be6a4b15b920a20
3
+ metadata.gz: 92c441dcc5d0c1c052d12cca378cb86ed81ce156bbff09b8d699699424acb3e6
4
+ data.tar.gz: bd971d884cd6decd4b6e2b0de10248255d17161acb556a709f24aa732594eb32
5
5
  SHA512:
6
- metadata.gz: 98050d505cf276b82824ab4c4371f632609c24fa06249feffbce10eeb8a3d8f45760c4472d4046b473a3da61ab75c60ddbbe93f0e9671d9bd5411abc705558a9
7
- data.tar.gz: dc127c772d0f48fd2710e399aa5f59150724c37f5599b63c2aaba45804fdf1d68075b7808c679158ff7579fc85f5d7e987f7ee92e02493342dd7d2f29b2f5cb8
6
+ metadata.gz: b296a4cabf9c7db248139f23821bd9f43894269494c9f831dd0e56a67ab4b89e7346dcb7bb20c510a5067a2309e0372a743a862c548a7f781c84e3f6a51e4287
7
+ data.tar.gz: fd8df36184a53e494ec16e378721f0d35305c97b561e393821eae88d0c7b8775f04f9f883821530f07a2584525978a4c1c14912dba4f35cfe366638f396a82db
data/ext/IO_Event.bundle CHANGED
Binary file
data/ext/event.o CHANGED
Binary file
data/ext/interrupt.o CHANGED
Binary file
@@ -299,6 +299,11 @@ VALUE io_wait_transfer(VALUE _arguments) {
299
299
 
300
300
  VALUE result = IO_Event_Selector_fiber_transfer(arguments->data->backend.loop, 0, NULL);
301
301
 
302
+ // If the fiber is being cancelled, it might be resumed with nil:
303
+ if (!RTEST(result)) {
304
+ return Qfalse;
305
+ }
306
+
302
307
  return INT2NUM(events_from_epoll_flags(NUM2INT(result)));
303
308
  };
304
309
 
@@ -365,7 +370,7 @@ VALUE io_read_loop(VALUE _arguments) {
365
370
 
366
371
  void *base;
367
372
  size_t size;
368
- rb_io_buffer_get_mutable(arguments->buffer, &base, &size);
373
+ rb_io_buffer_get_bytes_for_writing(arguments->buffer, &base, &size);
369
374
 
370
375
  size_t offset = 0;
371
376
  size_t length = arguments->length;
@@ -437,7 +442,7 @@ VALUE io_write_loop(VALUE _arguments) {
437
442
 
438
443
  const void *base;
439
444
  size_t size;
440
- rb_io_buffer_get_immutable(arguments->buffer, &base, &size);
445
+ rb_io_buffer_get_bytes_for_reading(arguments->buffer, &base, &size);
441
446
 
442
447
  size_t offset = 0;
443
448
  size_t length = arguments->length;
@@ -540,7 +545,11 @@ void select_internal_without_gvl(struct select_arguments *arguments) {
540
545
  arguments->data->blocked = 0;
541
546
 
542
547
  if (arguments->count == -1) {
543
- rb_sys_fail("select_internal_without_gvl:epoll_wait");
548
+ if (errno != EINTR) {
549
+ rb_sys_fail("select_internal_without_gvl:epoll_wait");
550
+ } else {
551
+ arguments->count = 0;
552
+ }
544
553
  }
545
554
  }
546
555
 
@@ -549,7 +558,11 @@ void select_internal_with_gvl(struct select_arguments *arguments) {
549
558
  select_internal((void *)arguments);
550
559
 
551
560
  if (arguments->count == -1) {
552
- rb_sys_fail("select_internal_with_gvl:epoll_wait");
561
+ if (errno != EINTR) {
562
+ rb_sys_fail("select_internal_with_gvl:epoll_wait");
563
+ } else {
564
+ arguments->count = 0;
565
+ }
553
566
  }
554
567
  }
555
568
 
@@ -355,6 +355,11 @@ VALUE io_wait_transfer(VALUE _arguments) {
355
355
 
356
356
  VALUE result = IO_Event_Selector_fiber_transfer(arguments->data->backend.loop, 0, NULL);
357
357
 
358
+ // If the fiber is being cancelled, it might be resumed with nil:
359
+ if (!RTEST(result)) {
360
+ return Qfalse;
361
+ }
362
+
358
363
  return INT2NUM(events_from_kqueue_filter(RB_NUM2INT(result)));
359
364
  }
360
365
 
@@ -396,7 +401,7 @@ VALUE io_read_loop(VALUE _arguments) {
396
401
 
397
402
  void *base;
398
403
  size_t size;
399
- rb_io_buffer_get_mutable(arguments->buffer, &base, &size);
404
+ rb_io_buffer_get_bytes_for_writing(arguments->buffer, &base, &size);
400
405
 
401
406
  size_t offset = 0;
402
407
  size_t length = arguments->length;
@@ -478,7 +483,7 @@ VALUE io_write_loop(VALUE _arguments) {
478
483
 
479
484
  const void *base;
480
485
  size_t size;
481
- rb_io_buffer_get_immutable(arguments->buffer, &base, &size);
486
+ rb_io_buffer_get_bytes_for_reading(arguments->buffer, &base, &size);
482
487
 
483
488
  size_t offset = 0;
484
489
  size_t length = arguments->length;
@@ -605,7 +610,11 @@ void select_internal_without_gvl(struct select_arguments *arguments) {
605
610
  arguments->data->blocked = 0;
606
611
 
607
612
  if (arguments->count == -1) {
608
- rb_sys_fail("select_internal_without_gvl:kevent");
613
+ if (errno != EINTR) {
614
+ rb_sys_fail("select_internal_without_gvl:kevent");
615
+ } else {
616
+ arguments->count = 0;
617
+ }
609
618
  }
610
619
  }
611
620
 
@@ -614,7 +623,11 @@ void select_internal_with_gvl(struct select_arguments *arguments) {
614
623
  select_internal((void *)arguments);
615
624
 
616
625
  if (arguments->count == -1) {
617
- rb_sys_fail("select_internal_with_gvl:kevent");
626
+ if (errno != EINTR) {
627
+ rb_sys_fail("select_internal_with_gvl:kevent");
628
+ } else {
629
+ arguments->count = 0;
630
+ }
618
631
  }
619
632
  }
620
633
 
@@ -27,6 +27,8 @@
27
27
 
28
28
  #include "pidfd.c"
29
29
 
30
+ #include <linux/version.h>
31
+
30
32
  enum {
31
33
  DEBUG = 0,
32
34
  DEBUG_IO_READ = 0,
@@ -336,6 +338,10 @@ VALUE io_wait_transfer(VALUE _arguments) {
336
338
  VALUE result = IO_Event_Selector_fiber_transfer(data->backend.loop, 0, NULL);
337
339
  if (DEBUG) fprintf(stderr, "io_wait:IO_Event_Selector_fiber_transfer -> %d\n", RB_NUM2INT(result));
338
340
 
341
+ if (!RTEST(result)) {
342
+ return Qfalse;
343
+ }
344
+
339
345
  // We explicitly filter the resulting events based on the requested events.
340
346
  // In some cases, poll will report events we didn't ask for.
341
347
  short flags = arguments->flags & NUM2INT(result);
@@ -371,12 +377,28 @@ VALUE IO_Event_Selector_URing_io_wait(VALUE self, VALUE fiber, VALUE io, VALUE e
371
377
 
372
378
  #ifdef HAVE_RUBY_IO_BUFFER_H
373
379
 
380
+ #if LINUX_VERSION_CODE >= KERNEL_VERSION(5,16,0)
381
+ static inline off_t io_seekable(int descriptor) {
382
+ return -1;
383
+ }
384
+ #else
385
+ #warning Upgrade your kernel to 5.16! io_uring bugs prevent efficient io_read/io_write hooks.
386
+ static inline off_t io_seekable(int descriptor)
387
+ {
388
+ if (lseek(descriptor, 0, SEEK_CUR) == -1) {
389
+ return 0;
390
+ } else {
391
+ return -1;
392
+ }
393
+ }
394
+ #endif
395
+
374
396
  static int io_read(struct IO_Event_Selector_URing *data, VALUE fiber, int descriptor, char *buffer, size_t length) {
375
397
  struct io_uring_sqe *sqe = io_get_sqe(data);
376
398
 
377
399
  if (DEBUG) fprintf(stderr, "io_read:io_uring_prep_read(fiber=%p)\n", (void*)fiber);
378
400
 
379
- io_uring_prep_read(sqe, descriptor, buffer, length, -1);
401
+ io_uring_prep_read(sqe, descriptor, buffer, length, io_seekable(descriptor));
380
402
  io_uring_sqe_set_data(sqe, (void*)fiber);
381
403
  io_uring_submit_now(data);
382
404
 
@@ -394,7 +416,7 @@ VALUE IO_Event_Selector_URing_io_read(VALUE self, VALUE fiber, VALUE io, VALUE b
394
416
 
395
417
  void *base;
396
418
  size_t size;
397
- rb_io_buffer_get_mutable(buffer, &base, &size);
419
+ rb_io_buffer_get_bytes_for_writing(buffer, &base, &size);
398
420
 
399
421
  size_t offset = 0;
400
422
  size_t length = NUM2SIZET(_length);
@@ -427,7 +449,7 @@ int io_write(struct IO_Event_Selector_URing *data, VALUE fiber, int descriptor,
427
449
 
428
450
  if (DEBUG) fprintf(stderr, "io_write:io_uring_prep_write(fiber=%p)\n", (void*)fiber);
429
451
 
430
- io_uring_prep_write(sqe, descriptor, buffer, length, -1);
452
+ io_uring_prep_write(sqe, descriptor, buffer, length, io_seekable(descriptor));
431
453
  io_uring_sqe_set_data(sqe, (void*)fiber);
432
454
  io_uring_submit_pending(data);
433
455
 
@@ -445,7 +467,7 @@ VALUE IO_Event_Selector_URing_io_write(VALUE self, VALUE fiber, VALUE io, VALUE
445
467
 
446
468
  const void *base;
447
469
  size_t size;
448
- rb_io_buffer_get_immutable(buffer, &base, &size);
470
+ rb_io_buffer_get_bytes_for_reading(buffer, &base, &size);
449
471
 
450
472
  size_t offset = 0;
451
473
  size_t length = NUM2SIZET(_length);
@@ -558,6 +580,8 @@ int select_internal_without_gvl(struct select_arguments *arguments) {
558
580
 
559
581
  if (arguments->result == -ETIME) {
560
582
  arguments->result = 0;
583
+ } else if (arguments->result == -EINTR) {
584
+ arguments->result = 0;
561
585
  } else if (arguments->result < 0) {
562
586
  rb_syserr_fail(-arguments->result, "select_internal_without_gvl:io_uring_wait_cqe_timeout");
563
587
  } else {
@@ -568,8 +592,6 @@ int select_internal_without_gvl(struct select_arguments *arguments) {
568
592
  return arguments->result;
569
593
  }
570
594
 
571
- // #define IO_EVENT_SELECTOR_URING_UDATA_INTERRUPT ((__u64) -2)
572
-
573
595
  static inline
574
596
  unsigned select_process_completions(struct io_uring *ring) {
575
597
  unsigned completed = 0;
@@ -585,10 +607,6 @@ unsigned select_process_completions(struct io_uring *ring) {
585
607
  continue;
586
608
  }
587
609
 
588
- // if (cqe->user_data == IO_EVENT_SELECTOR_URING_UDATA_INTERRUPT) {
589
- // io_uring_cq_advance(ring, 1);
590
- // }
591
-
592
610
  VALUE fiber = (VALUE)cqe->user_data;
593
611
  VALUE result = RB_INT2NUM(cqe->res);
594
612
 
data/ext/kqueue.o CHANGED
Binary file
data/ext/selector.o CHANGED
Binary file
@@ -158,7 +158,7 @@ module IO::Event
158
158
  else
159
159
  break unless result
160
160
 
161
- buffer.copy(result, offset)
161
+ buffer.set_string(result, offset)
162
162
 
163
163
  size = result.bytesize
164
164
  offset += size
@@ -176,7 +176,7 @@ module IO::Event
176
176
  while true
177
177
  maximum_size = buffer.size - offset
178
178
 
179
- chunk = buffer.to_str(offset, maximum_size)
179
+ chunk = buffer.get_string(offset, maximum_size)
180
180
  case result = blocking{io.write_nonblock(chunk, exception: false)}
181
181
  when :wait_readable
182
182
  if length > 0
@@ -31,12 +31,10 @@ module IO::Event
31
31
  end
32
32
  end
33
33
 
34
- if self.const_defined?(:URing)
35
- return URing
34
+ if self.const_defined?(:EPoll)
35
+ return EPoll
36
36
  elsif self.const_defined?(:KQueue)
37
37
  return KQueue
38
- elsif self.const_defined?(:EPoll)
39
- return EPoll
40
38
  else
41
39
  return Select
42
40
  end
@@ -19,5 +19,5 @@
19
19
  # THE SOFTWARE.
20
20
 
21
21
  module IO::Event
22
- VERSION = "0.3.3"
22
+ VERSION = "1.0.1"
23
23
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: io-event
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.3
4
+ version: 1.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Samuel Williams
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-12-18 00:00:00.000000000 Z
11
+ date: 2021-12-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bake
@@ -113,14 +113,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
113
113
  requirements:
114
114
  - - ">="
115
115
  - !ruby/object:Gem::Version
116
- version: '0'
116
+ version: '3.0'
117
117
  required_rubygems_version: !ruby/object:Gem::Requirement
118
118
  requirements:
119
119
  - - ">="
120
120
  - !ruby/object:Gem::Version
121
121
  version: '0'
122
122
  requirements: []
123
- rubygems_version: 3.3.0.dev
123
+ rubygems_version: 3.3.2
124
124
  signing_key:
125
125
  specification_version: 4
126
126
  summary: An event loop.