nio4r 2.5.4 → 2.5.5

Sign up to get free protection for your applications and to get access to all the features.
data/ext/libev/ev_vars.h CHANGED
@@ -118,6 +118,35 @@ VARx(int, linuxaio_submitmax)
118
118
  VARx(ev_io, linuxaio_epoll_w)
119
119
  #endif
120
120
 
121
+ #if EV_USE_IOURING || EV_GENWRAP
122
+ VARx(int, iouring_fd)
123
+ VARx(unsigned, iouring_to_submit);
124
+ VARx(int, iouring_entries)
125
+ VARx(int, iouring_max_entries)
126
+ VARx(void *, iouring_sq_ring)
127
+ VARx(void *, iouring_cq_ring)
128
+ VARx(void *, iouring_sqes)
129
+ VARx(uint32_t, iouring_sq_ring_size)
130
+ VARx(uint32_t, iouring_cq_ring_size)
131
+ VARx(uint32_t, iouring_sqes_size)
132
+ VARx(uint32_t, iouring_sq_head)
133
+ VARx(uint32_t, iouring_sq_tail)
134
+ VARx(uint32_t, iouring_sq_ring_mask)
135
+ VARx(uint32_t, iouring_sq_ring_entries)
136
+ VARx(uint32_t, iouring_sq_flags)
137
+ VARx(uint32_t, iouring_sq_dropped)
138
+ VARx(uint32_t, iouring_sq_array)
139
+ VARx(uint32_t, iouring_cq_head)
140
+ VARx(uint32_t, iouring_cq_tail)
141
+ VARx(uint32_t, iouring_cq_ring_mask)
142
+ VARx(uint32_t, iouring_cq_ring_entries)
143
+ VARx(uint32_t, iouring_cq_overflow)
144
+ VARx(uint32_t, iouring_cq_cqes)
145
+ VARx(ev_tstamp, iouring_tfd_to)
146
+ VARx(int, iouring_tfd)
147
+ VARx(ev_io, iouring_tfd_w)
148
+ #endif
149
+
121
150
  #if EV_USE_KQUEUE || EV_GENWRAP
122
151
  VARx(pid_t, kqueue_fd_pid)
123
152
  VARx(struct kevent *, kqueue_changes)
@@ -198,6 +227,11 @@ VARx(ev_io, sigfd_w)
198
227
  VARx(sigset_t, sigfd_set)
199
228
  #endif
200
229
 
230
+ #if EV_USE_TIMERFD || EV_GENWRAP
231
+ VARx(int, timerfd) /* timerfd for time jump detection */
232
+ VARx(ev_io, timerfd_w)
233
+ #endif
234
+
201
235
  VARx(unsigned int, origflags) /* original loop flags */
202
236
 
203
237
  #if EV_FEATURE_API || EV_GENWRAP
data/ext/libev/ev_win32.c CHANGED
@@ -154,8 +154,8 @@ ev_time (void)
154
154
  ui.u.LowPart = ft.dwLowDateTime;
155
155
  ui.u.HighPart = ft.dwHighDateTime;
156
156
 
157
- /* msvc cannot convert ulonglong to double... yes, it is that sucky */
158
- return (LONGLONG)(ui.QuadPart - 116444736000000000) * 1e-7;
157
+ /* also, msvc cannot convert ulonglong to double... yes, it is that sucky */
158
+ return EV_TS_FROM_USEC (((LONGLONG)(ui.QuadPart - 116444736000000000) * 1e-1));
159
159
  }
160
160
 
161
161
  #endif
data/ext/libev/ev_wrap.h CHANGED
@@ -44,6 +44,32 @@
44
44
  #define invoke_cb ((loop)->invoke_cb)
45
45
  #define io_blocktime ((loop)->io_blocktime)
46
46
  #define iocp ((loop)->iocp)
47
+ #define iouring_cq_cqes ((loop)->iouring_cq_cqes)
48
+ #define iouring_cq_head ((loop)->iouring_cq_head)
49
+ #define iouring_cq_overflow ((loop)->iouring_cq_overflow)
50
+ #define iouring_cq_ring ((loop)->iouring_cq_ring)
51
+ #define iouring_cq_ring_entries ((loop)->iouring_cq_ring_entries)
52
+ #define iouring_cq_ring_mask ((loop)->iouring_cq_ring_mask)
53
+ #define iouring_cq_ring_size ((loop)->iouring_cq_ring_size)
54
+ #define iouring_cq_tail ((loop)->iouring_cq_tail)
55
+ #define iouring_entries ((loop)->iouring_entries)
56
+ #define iouring_fd ((loop)->iouring_fd)
57
+ #define iouring_max_entries ((loop)->iouring_max_entries)
58
+ #define iouring_sq_array ((loop)->iouring_sq_array)
59
+ #define iouring_sq_dropped ((loop)->iouring_sq_dropped)
60
+ #define iouring_sq_flags ((loop)->iouring_sq_flags)
61
+ #define iouring_sq_head ((loop)->iouring_sq_head)
62
+ #define iouring_sq_ring ((loop)->iouring_sq_ring)
63
+ #define iouring_sq_ring_entries ((loop)->iouring_sq_ring_entries)
64
+ #define iouring_sq_ring_mask ((loop)->iouring_sq_ring_mask)
65
+ #define iouring_sq_ring_size ((loop)->iouring_sq_ring_size)
66
+ #define iouring_sq_tail ((loop)->iouring_sq_tail)
67
+ #define iouring_sqes ((loop)->iouring_sqes)
68
+ #define iouring_sqes_size ((loop)->iouring_sqes_size)
69
+ #define iouring_tfd ((loop)->iouring_tfd)
70
+ #define iouring_tfd_to ((loop)->iouring_tfd_to)
71
+ #define iouring_tfd_w ((loop)->iouring_tfd_w)
72
+ #define iouring_to_submit ((loop)->iouring_to_submit)
47
73
  #define kqueue_changecnt ((loop)->kqueue_changecnt)
48
74
  #define kqueue_changemax ((loop)->kqueue_changemax)
49
75
  #define kqueue_changes ((loop)->kqueue_changes)
@@ -97,6 +123,8 @@
97
123
  #define sigfd_w ((loop)->sigfd_w)
98
124
  #define timeout_blocktime ((loop)->timeout_blocktime)
99
125
  #define timercnt ((loop)->timercnt)
126
+ #define timerfd ((loop)->timerfd)
127
+ #define timerfd_w ((loop)->timerfd_w)
100
128
  #define timermax ((loop)->timermax)
101
129
  #define timers ((loop)->timers)
102
130
  #define userdata ((loop)->userdata)
@@ -151,6 +179,32 @@
151
179
  #undef invoke_cb
152
180
  #undef io_blocktime
153
181
  #undef iocp
182
+ #undef iouring_cq_cqes
183
+ #undef iouring_cq_head
184
+ #undef iouring_cq_overflow
185
+ #undef iouring_cq_ring
186
+ #undef iouring_cq_ring_entries
187
+ #undef iouring_cq_ring_mask
188
+ #undef iouring_cq_ring_size
189
+ #undef iouring_cq_tail
190
+ #undef iouring_entries
191
+ #undef iouring_fd
192
+ #undef iouring_max_entries
193
+ #undef iouring_sq_array
194
+ #undef iouring_sq_dropped
195
+ #undef iouring_sq_flags
196
+ #undef iouring_sq_head
197
+ #undef iouring_sq_ring
198
+ #undef iouring_sq_ring_entries
199
+ #undef iouring_sq_ring_mask
200
+ #undef iouring_sq_ring_size
201
+ #undef iouring_sq_tail
202
+ #undef iouring_sqes
203
+ #undef iouring_sqes_size
204
+ #undef iouring_tfd
205
+ #undef iouring_tfd_to
206
+ #undef iouring_tfd_w
207
+ #undef iouring_to_submit
154
208
  #undef kqueue_changecnt
155
209
  #undef kqueue_changemax
156
210
  #undef kqueue_changes
@@ -204,6 +258,8 @@
204
258
  #undef sigfd_w
205
259
  #undef timeout_blocktime
206
260
  #undef timercnt
261
+ #undef timerfd
262
+ #undef timerfd_w
207
263
  #undef timermax
208
264
  #undef timers
209
265
  #undef userdata
data/ext/nio4r/extconf.rb CHANGED
@@ -15,6 +15,7 @@ require "mkmf"
15
15
  have_header("unistd.h")
16
16
 
17
17
  $defs << "-DEV_USE_LINUXAIO" if have_header("linux/aio_abi.h")
18
+ $defs << "-DEV_USE_IOURING" if have_header("linux/io_uring.h")
18
19
  $defs << "-DEV_USE_SELECT" if have_header("sys/select.h")
19
20
  $defs << "-DEV_USE_POLL" if have_type("port_event_t", "poll.h")
20
21
  $defs << "-DEV_USE_EPOLL" if have_header("sys/epoll.h")
@@ -1,6 +1,7 @@
1
1
  package org.nio4r;
2
2
 
3
3
  import java.io.IOException;
4
+ import java.io.Serializable;
4
5
  import java.nio.channels.Channel;
5
6
  import java.nio.channels.SelectableChannel;
6
7
  import java.nio.channels.ReadableByteChannel;
@@ -25,6 +26,7 @@ import org.jruby.runtime.Block;
25
26
  created by Upekshej
26
27
  */
27
28
  public class ByteBuffer extends RubyObject {
29
+ private static final long serialVersionUID = -6903439483039149324L;
28
30
  private java.nio.ByteBuffer byteBuffer;
29
31
 
30
32
  public static RaiseException newOverflowError(ThreadContext context, String message) {
@@ -13,6 +13,7 @@ import org.jruby.runtime.ThreadContext;
13
13
  import org.jruby.runtime.builtin.IRubyObject;
14
14
 
15
15
  public class Monitor extends RubyObject {
16
+ private static final long serialVersionUID = -3733782997115074794L;
16
17
  private SelectionKey key;
17
18
  private RubyIO io;
18
19
  private IRubyObject interests, selector, value, closed;
@@ -7,7 +7,6 @@ import java.io.IOException;
7
7
  import java.nio.channels.Channel;
8
8
  import java.nio.channels.SelectableChannel;
9
9
  import java.nio.channels.SelectionKey;
10
- import java.nio.channels.CancelledKeyException;
11
10
 
12
11
  import org.jruby.Ruby;
13
12
  import org.jruby.RubyArray;
@@ -21,9 +20,8 @@ import org.jruby.runtime.ThreadContext;
21
20
  import org.jruby.runtime.builtin.IRubyObject;
22
21
  import org.jruby.util.io.OpenFile;
23
22
 
24
- import org.nio4r.Monitor;
25
-
26
23
  public class Selector extends RubyObject {
24
+ private static final long serialVersionUID = -14562818539414873L;
27
25
  private java.nio.channels.Selector selector;
28
26
  private HashMap<SelectableChannel,SelectionKey> cancelledKeys;
29
27
  private volatile boolean wakeupFired;
@@ -45,7 +43,7 @@ public class Selector extends RubyObject {
45
43
 
46
44
  @JRubyMethod
47
45
  public IRubyObject initialize(ThreadContext context, IRubyObject backend) {
48
- if(backend != context.runtime.newSymbol("java")) {
46
+ if(backend != context.runtime.newSymbol("java") && !backend.isNil()) {
49
47
  throw context.runtime.newArgumentError(":java is the only supported backend");
50
48
  }
51
49
 
@@ -203,15 +201,15 @@ public class Selector extends RubyObject {
203
201
  return context.nil;
204
202
  }
205
203
 
206
- RubyArray array = null;
204
+ RubyArray<?> array = null;
207
205
 
208
206
  if(!block.isGiven()) {
209
207
  array = runtime.newArray(this.selector.selectedKeys().size());
210
208
  }
211
209
 
212
- Iterator selectedKeys = this.selector.selectedKeys().iterator();
210
+ Iterator<SelectionKey> selectedKeys = this.selector.selectedKeys().iterator();
213
211
  while(selectedKeys.hasNext()) {
214
- SelectionKey key = (SelectionKey)selectedKeys.next();
212
+ SelectionKey key = selectedKeys.next();
215
213
  processKey(key);
216
214
 
217
215
  selectedKeys.remove();
@@ -263,10 +261,10 @@ public class Selector extends RubyObject {
263
261
 
264
262
  /* Flush our internal buffer of cancelled keys */
265
263
  private void cancelKeys() {
266
- Iterator cancelledKeys = this.cancelledKeys.entrySet().iterator();
264
+ Iterator<Map.Entry<SelectableChannel, SelectionKey>> cancelledKeys = this.cancelledKeys.entrySet().iterator();
267
265
  while(cancelledKeys.hasNext()) {
268
- Map.Entry entry = (Map.Entry)cancelledKeys.next();
269
- SelectionKey key = (SelectionKey)entry.getValue();
266
+ Map.Entry<SelectableChannel, SelectionKey> entry = cancelledKeys.next();
267
+ SelectionKey key = entry.getValue();
270
268
  key.cancel();
271
269
  cancelledKeys.remove();
272
270
  }
data/ext/nio4r/selector.c CHANGED
@@ -183,6 +183,14 @@ static VALUE NIO_Selector_supported_backends(VALUE klass)
183
183
  rb_ary_push(result, ID2SYM(rb_intern("port")));
184
184
  }
185
185
 
186
+ if (backends & EVBACKEND_LINUXAIO) {
187
+ rb_ary_push(result, ID2SYM(rb_intern("linuxaio")));
188
+ }
189
+
190
+ if (backends & EVBACKEND_IOURING) {
191
+ rb_ary_push(result, ID2SYM(rb_intern("io_uring")));
192
+ }
193
+
186
194
  return result;
187
195
  }
188
196
 
@@ -218,6 +226,10 @@ static VALUE NIO_Selector_initialize(int argc, VALUE *argv, VALUE self)
218
226
  flags = EVBACKEND_SELECT;
219
227
  } else if (backend_id == rb_intern("port")) {
220
228
  flags = EVBACKEND_PORT;
229
+ } else if (backend_id == rb_intern("linuxaio")) {
230
+ flags = EVBACKEND_LINUXAIO;
231
+ } else if (backend_id == rb_intern("io_uring")) {
232
+ flags = EVBACKEND_IOURING;
221
233
  } else {
222
234
  rb_raise(rb_eArgError, "unsupported backend: %s", RSTRING_PTR(rb_funcall(backend, rb_intern("inspect"), 0)));
223
235
  }
@@ -263,6 +275,10 @@ static VALUE NIO_Selector_backend(VALUE self)
263
275
  return ID2SYM(rb_intern("select"));
264
276
  case EVBACKEND_PORT:
265
277
  return ID2SYM(rb_intern("port"));
278
+ case EVBACKEND_LINUXAIO:
279
+ return ID2SYM(rb_intern("linuxaio"));
280
+ case EVBACKEND_IOURING:
281
+ return ID2SYM(rb_intern("io_uring"));
266
282
  }
267
283
 
268
284
  return ID2SYM(rb_intern("unknown"));
data/lib/nio.rb CHANGED
@@ -12,9 +12,28 @@ module NIO
12
12
  def self.engine
13
13
  ENGINE
14
14
  end
15
+
16
+ def self.pure?(env = ENV)
17
+ # The user has explicitly opted in to non-native implementation:
18
+ if env["NIO4R_PURE"] == "true"
19
+ return true
20
+ end
21
+
22
+ # Native Ruby on Windows is not supported:
23
+ if (Gem.win_platform? && !defined?(JRUBY_VERSION))
24
+ return true
25
+ end
26
+
27
+ # M1 native extension is crashing on M1 (arm64):
28
+ if RUBY_PLATFORM =~ /darwin/ && RUBY_PLATFORM =~ /arm64/
29
+ return true
30
+ end
31
+
32
+ return false
33
+ end
15
34
  end
16
35
 
17
- if ENV["NIO4R_PURE"] == "true" || (Gem.win_platform? && !defined?(JRUBY_VERSION))
36
+ if NIO.pure?
18
37
  require "nio/monitor"
19
38
  require "nio/selector"
20
39
  require "nio/bytebuffer"
data/lib/nio/selector.rb CHANGED
@@ -14,7 +14,7 @@ module NIO
14
14
 
15
15
  # Create a new NIO::Selector
16
16
  def initialize(backend = :ruby)
17
- raise ArgumentError, "unsupported backend: #{backend}" unless backend == :ruby
17
+ raise ArgumentError, "unsupported backend: #{backend}" unless [:ruby, nil].include?(backend)
18
18
 
19
19
  @selectables = {}
20
20
  @lock = Mutex.new
@@ -26,14 +26,16 @@ module NIO
26
26
 
27
27
  # Return a symbol representing the backend I/O multiplexing mechanism used.
28
28
  # Supported backends are:
29
- # * :ruby - pure Ruby (i.e IO.select)
30
- # * :java - Java NIO on JRuby
31
- # * :epoll - libev w\ Linux epoll
32
- # * :poll - libev w\ POSIX poll
33
- # * :kqueue - libev w\ BSD kqueue
34
- # * :select - libev w\ SysV select
35
- # * :port - libev w\ I/O completion ports
36
- # * :unknown - libev w\ unknown backend
29
+ # * :ruby - pure Ruby (i.e IO.select)
30
+ # * :java - Java NIO on JRuby
31
+ # * :epoll - libev w\ Linux epoll
32
+ # * :poll - libev w\ POSIX poll
33
+ # * :kqueue - libev w\ BSD kqueue
34
+ # * :select - libev w\ SysV select
35
+ # * :port - libev w\ I/O completion ports
36
+ # * :linuxaio - libev w\ Linux AIO io_submit (experimental)
37
+ # * :io_uring - libev w\ Linux io_uring (experimental)
38
+ # * :unknown - libev w\ unknown backend
37
39
  def backend
38
40
  :ruby
39
41
  end
data/lib/nio/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module NIO
4
- VERSION = "2.5.4"
4
+ VERSION = "2.5.5"
5
5
  end
@@ -24,6 +24,10 @@ RSpec.describe NIO::Selector do
24
24
  example.reporter.message "Supported backends: #{described_class.backends}"
25
25
  end
26
26
 
27
+ it "automatically selects a backend if none or nil is specified" do
28
+ expect(described_class.new.backend).to eq described_class.new(nil).backend
29
+ end
30
+
27
31
  it "raises ArgumentError if given an invalid backend" do
28
32
  expect { described_class.new(:derp) }.to raise_error ArgumentError
29
33
  end
data/spec/spec_helper.rb CHANGED
@@ -12,6 +12,8 @@ RSpec.configure do |config|
12
12
  # Enable flags like --only-failures and --next-failure
13
13
  config.example_status_persistence_file_path = ".rspec_status"
14
14
 
15
+ config.filter_run_when_matching :focus
16
+
15
17
  config.expect_with :rspec do |c|
16
18
  c.syntax = :expect
17
19
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: nio4r
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.5.4
4
+ version: 2.5.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tony Arcieri
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-09-15 00:00:00.000000000 Z
11
+ date: 2021-02-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -62,6 +62,7 @@ files:
62
62
  - ext/libev/ev.c
63
63
  - ext/libev/ev.h
64
64
  - ext/libev/ev_epoll.c
65
+ - ext/libev/ev_iouring.c
65
66
  - ext/libev/ev_kqueue.c
66
67
  - ext/libev/ev_linuxaio.c
67
68
  - ext/libev/ev_poll.c
@@ -108,8 +109,8 @@ licenses:
108
109
  metadata:
109
110
  bug_tracker_uri: https://github.com/socketry/nio4r/issues
110
111
  changelog_uri: https://github.com/socketry/nio4r/blob/master/CHANGES.md
111
- documentation_uri: https://www.rubydoc.info/gems/nio4r/2.5.4
112
- source_code_uri: https://github.com/socketry/nio4r/tree/v2.5.4
112
+ documentation_uri: https://www.rubydoc.info/gems/nio4r/2.5.5
113
+ source_code_uri: https://github.com/socketry/nio4r/tree/v2.5.5
113
114
  wiki_uri: https://github.com/socketry/nio4r/wiki
114
115
  post_install_message:
115
116
  rdoc_options: []