nio4r 2.3.1-java → 2.5.3-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (49) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/workflow.yml +43 -0
  3. data/.gitignore +1 -0
  4. data/.rubocop.yml +37 -11
  5. data/CHANGES.md +40 -0
  6. data/Gemfile +5 -6
  7. data/README.md +53 -7
  8. data/Rakefile +0 -2
  9. data/examples/echo_server.rb +2 -2
  10. data/ext/libev/Changes +35 -0
  11. data/ext/libev/README +2 -1
  12. data/ext/libev/ev.c +213 -151
  13. data/ext/libev/ev.h +95 -88
  14. data/ext/libev/ev_epoll.c +26 -15
  15. data/ext/libev/ev_kqueue.c +11 -5
  16. data/ext/libev/ev_linuxaio.c +642 -0
  17. data/ext/libev/ev_poll.c +13 -8
  18. data/ext/libev/ev_port.c +5 -2
  19. data/ext/libev/ev_vars.h +14 -3
  20. data/ext/libev/ev_wrap.h +16 -0
  21. data/ext/nio4r/extconf.rb +2 -0
  22. data/ext/nio4r/monitor.c +1 -0
  23. data/ext/nio4r/nio4r.h +1 -1
  24. data/ext/nio4r/org/nio4r/Selector.java +5 -1
  25. data/ext/nio4r/selector.c +5 -5
  26. data/lib/nio.rb +3 -3
  27. data/lib/nio/bytebuffer.rb +4 -0
  28. data/lib/nio/monitor.rb +10 -8
  29. data/lib/nio/selector.rb +3 -1
  30. data/lib/nio/version.rb +1 -1
  31. data/nio4r.gemspec +10 -2
  32. data/{tasks → rakelib}/extension.rake +2 -0
  33. data/{tasks → rakelib}/rspec.rake +0 -0
  34. data/{tasks → rakelib}/rubocop.rake +0 -0
  35. data/spec/nio/acceptables_spec.rb +3 -5
  36. data/spec/nio/bytebuffer_spec.rb +2 -4
  37. data/spec/nio/monitor_spec.rb +2 -2
  38. data/spec/nio/selectables/ssl_socket_spec.rb +50 -20
  39. data/spec/nio/selectables/tcp_socket_spec.rb +23 -17
  40. data/spec/nio/selectables/udp_socket_spec.rb +13 -8
  41. data/spec/nio/selector_spec.rb +34 -16
  42. data/spec/spec_helper.rb +4 -16
  43. data/spec/support/selectable_examples.rb +37 -17
  44. metadata +28 -17
  45. data/.travis.yml +0 -36
  46. data/LICENSE.txt +0 -20
  47. data/appveyor.yml +0 -27
  48. data/ext/libev/README.embed +0 -3
  49. data/ext/libev/test_libev_win32.c +0 -123
@@ -4,19 +4,22 @@ require "spec_helper"
4
4
 
5
5
  RSpec.describe TCPSocket do
6
6
  let(:addr) { "127.0.0.1" }
7
- let(:port) { next_available_tcp_port }
8
7
 
9
8
  let :readable_subject do
10
- server = TCPServer.new(addr, port)
11
- sock = TCPSocket.new(addr, port)
9
+ server = TCPServer.new(addr, 0)
10
+ sock = TCPSocket.new(addr, server.local_address.ip_port)
12
11
  peer = server.accept
13
- peer << "data"
12
+
13
+ peer << "Xdata"
14
+ peer.flush
15
+ sock.read(1)
16
+
14
17
  sock
15
18
  end
16
19
 
17
20
  let :unreadable_subject do
18
- TCPServer.new(addr, port)
19
- sock = TCPSocket.new(addr, port)
21
+ server = TCPServer.new(addr, 0)
22
+ sock = TCPSocket.new(addr, server.local_address.ip_port)
20
23
 
21
24
  # Sanity check to make sure we actually produced an unreadable socket
22
25
  pending "Failed to produce an unreadable socket" if select([sock], [], [], 0)
@@ -25,13 +28,13 @@ RSpec.describe TCPSocket do
25
28
  end
26
29
 
27
30
  let :writable_subject do
28
- TCPServer.new(addr, port)
29
- TCPSocket.new(addr, port)
31
+ server = TCPServer.new(addr, 0)
32
+ TCPSocket.new(addr, server.local_address.ip_port)
30
33
  end
31
34
 
32
35
  let :unwritable_subject do
33
- server = TCPServer.new(addr, port)
34
- sock = TCPSocket.new(addr, port)
36
+ server = TCPServer.new(addr, 0)
37
+ sock = TCPSocket.new(addr, server.local_address.ip_port)
35
38
 
36
39
  # TODO: close this socket
37
40
  _peer = server.accept
@@ -61,8 +64,8 @@ RSpec.describe TCPSocket do
61
64
  end
62
65
 
63
66
  let :pair do
64
- server = TCPServer.new(addr, port)
65
- client = TCPSocket.new(addr, port)
67
+ server = TCPServer.new(addr, 0)
68
+ client = TCPSocket.new(addr, server.local_address.ip_port)
66
69
  [client, server.accept]
67
70
  end
68
71
 
@@ -71,19 +74,22 @@ RSpec.describe TCPSocket do
71
74
  it_behaves_like "an NIO bidirectional stream"
72
75
 
73
76
  context :connect do
74
- it "selects writable when connected", retry: 5 do # retry: Flaky on OS X
77
+ include_context NIO::Selector
78
+
79
+ it "selects writable when connected" do
75
80
  begin
76
- server = TCPServer.new(addr, port)
77
- selector = NIO::Selector.new
81
+ server = TCPServer.new(addr, 0)
78
82
 
79
83
  client = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
80
84
  monitor = selector.register(client, :w)
81
85
 
82
86
  expect do
83
- client.connect_nonblock Socket.sockaddr_in(port, addr)
87
+ client.connect_nonblock server.local_address
84
88
  end.to raise_exception Errno::EINPROGRESS
85
89
 
86
- expect(selector.select(0.001)).to include monitor
90
+ ready = selector.select(1)
91
+
92
+ expect(ready).to include monitor
87
93
  result = client.getsockopt(::Socket::SOL_SOCKET, ::Socket::SO_ERROR)
88
94
  expect(result.unpack("i").first).to be_zero
89
95
  ensure
@@ -6,32 +6,37 @@ RSpec.describe UDPSocket, if: !defined?(JRUBY_VERSION) do
6
6
  let(:udp_port) { 23_456 }
7
7
 
8
8
  let :readable_subject do
9
- sock = UDPSocket.new
10
- sock.bind("127.0.0.1", udp_port)
9
+ server = UDPSocket.new
10
+ server.bind("127.0.0.1", 0)
11
11
 
12
12
  peer = UDPSocket.new
13
- peer.send("hi there", 0, "127.0.0.1", udp_port)
13
+ peer.send("hi there", 0, "127.0.0.1", server.local_address.ip_port)
14
14
 
15
- sock
15
+ server
16
16
  end
17
17
 
18
18
  let :unreadable_subject do
19
19
  sock = UDPSocket.new
20
- sock.bind("127.0.0.1", udp_port + 1)
20
+ sock.bind("127.0.0.1", 0)
21
21
  sock
22
22
  end
23
23
 
24
24
  let :writable_subject do
25
+ server = UDPSocket.new
26
+ server.bind("127.0.0.1", 0)
27
+
25
28
  peer = UDPSocket.new
26
- peer.connect "127.0.0.1", udp_port
29
+ peer.connect("127.0.0.1", server.local_address.ip_port)
30
+
27
31
  cntr = 0
28
32
  begin
29
33
  peer.send("X" * 1024, 0)
30
34
  cntr += 1
31
35
  t = select [], [peer], [], 0
32
- rescue Errno::ECONNREFUSED => ex
33
- skip "Couln't make writable UDPSocket subject: #{ex.class}: #{ex}"
36
+ rescue Errno::ECONNREFUSED => e
37
+ skip "Couldn't make writable UDPSocket subject: #{e.class}: #{e}"
34
38
  end while t && t[1].include?(peer) && cntr < 5
39
+
35
40
  peer
36
41
  end
37
42
 
@@ -3,12 +3,6 @@
3
3
  require "spec_helper"
4
4
  require "timeout"
5
5
 
6
- # Timeouts should be at least this precise (in seconds) to pass the tests
7
- # Typical precision should be better than this, but if it's worse it will fail
8
- # the tests
9
- TIMEOUT_PRECISION = 0.1
10
-
11
- # rubocop:disable Metrics/BlockLength
12
6
  RSpec.describe NIO::Selector do
13
7
  let(:pair) { IO.pipe }
14
8
  let(:reader) { pair.first }
@@ -22,10 +16,12 @@ RSpec.describe NIO::Selector do
22
16
  end
23
17
 
24
18
  context "#initialize" do
25
- it "allows explicitly specifying a backend" do
19
+ it "allows explicitly specifying a backend" do |example|
26
20
  backend = described_class.backends.first
27
21
  selector = described_class.new(backend)
28
22
  expect(selector.backend).to eq backend
23
+
24
+ example.reporter.message "Supported backends: #{described_class.backends}"
29
25
  end
30
26
 
31
27
  it "raises ArgumentError if given an invalid backend" do
@@ -38,8 +34,10 @@ RSpec.describe NIO::Selector do
38
34
  end
39
35
 
40
36
  context "backend" do
41
- it "knows its backend" do
37
+ it "knows its backend" do |example|
42
38
  expect(subject.backend).to be_a Symbol
39
+
40
+ example.reporter.message "Current backend: #{subject.backend}"
43
41
  end
44
42
  end
45
43
 
@@ -73,6 +71,15 @@ RSpec.describe NIO::Selector do
73
71
  expect(monitor).to be_closed
74
72
  end
75
73
 
74
+ it "allows deregistering closed IO objects" do
75
+ subject.register(reader, :r)
76
+ reader.close
77
+
78
+ expect do
79
+ subject.deregister(reader)
80
+ end.not_to raise_error
81
+ end
82
+
76
83
  it "reports if it is empty" do
77
84
  expect(subject).to be_empty
78
85
  subject.register(reader, :r)
@@ -96,31 +103,43 @@ RSpec.describe NIO::Selector do
96
103
  end
97
104
 
98
105
  context "timeouts" do
99
- it "waits for a timeout when selecting" do
106
+ let(:select_precision) {0.2}
107
+ let(:timeout) {2.0}
108
+ let(:payload) {"hi there"}
109
+
110
+ it "waits for timeout when selecting from empty selector" do
111
+ started_at = Time.now
112
+ expect(subject.select(timeout)).to be_nil
113
+ expect(Time.now - started_at).to be_within(select_precision).of(timeout)
114
+ end
115
+
116
+ it "waits for a timeout when selecting with reader" do
100
117
  monitor = subject.register(reader, :r)
101
118
 
102
- payload = "hi there"
103
119
  writer << payload
104
120
 
105
- timeout = 0.5
106
121
  started_at = Time.now
107
122
  expect(subject.select(timeout)).to include monitor
108
- expect(Time.now - started_at).to be_within(TIMEOUT_PRECISION).of(0)
123
+ expect(Time.now - started_at).to be_within(select_precision).of(0)
109
124
  reader.read_nonblock(payload.size)
110
125
 
111
126
  started_at = Time.now
112
127
  expect(subject.select(timeout)).to be_nil
113
- expect(Time.now - started_at).to be_within(TIMEOUT_PRECISION).of(timeout)
128
+ expect(Time.now - started_at).to be_within(select_precision).of(timeout)
114
129
  end
115
130
 
116
131
  it "raises ArgumentError if given a negative timeout" do
117
132
  subject.register(reader, :r)
118
133
 
119
- expect { subject.select(-1) }.to raise_exception(ArgumentError)
134
+ expect do
135
+ subject.select(-1)
136
+ end.to raise_exception(ArgumentError)
120
137
  end
121
138
  end
122
139
 
123
140
  context "wakeup" do
141
+ let(:select_precision) {0.2}
142
+
124
143
  it "wakes up if signaled to from another thread" do
125
144
  subject.register(reader, :r)
126
145
 
@@ -134,7 +153,7 @@ RSpec.describe NIO::Selector do
134
153
  sleep timeout
135
154
  subject.wakeup
136
155
 
137
- expect(thread.value).to be_within(TIMEOUT_PRECISION).of(timeout)
156
+ expect(thread.value).to be_within(select_precision).of(timeout)
138
157
  end
139
158
 
140
159
  it "raises IOError if asked to wake up a closed selector" do
@@ -215,4 +234,3 @@ RSpec.describe NIO::Selector do
215
234
  expect(subject).to be_closed
216
235
  end
217
236
  end
218
- # rubocop:enable Metrics/BlockLength
@@ -5,26 +5,14 @@ Coveralls.wear!
5
5
 
6
6
  require "nio"
7
7
  require "support/selectable_examples"
8
- require "rspec/retry"
9
8
 
10
9
  RSpec.configure do |config|
11
10
  config.disable_monkey_patching!
12
- config.verbose_retry = true
13
- config.display_try_failure_messages = true
14
- end
15
-
16
- $current_tcp_port = 10_000
17
-
18
- def next_available_tcp_port
19
- loop do
20
- $current_tcp_port += 1
21
11
 
22
- begin
23
- sock = Timeout.timeout(0.5) { TCPSocket.new("127.0.0.1", $current_tcp_port) }
24
- rescue Errno::ECONNREFUSED, Timeout::Error
25
- break $current_tcp_port
26
- end
12
+ # Enable flags like --only-failures and --next-failure
13
+ config.example_status_persistence_file_path = ".rspec_status"
27
14
 
28
- sock.close
15
+ config.expect_with :rspec do |c|
16
+ c.syntax = :expect
29
17
  end
30
18
  end
@@ -1,11 +1,21 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ RSpec.shared_context NIO::Selector do
4
+ let(:selector) {@selector = NIO::Selector.new}
5
+
6
+ after(:each) do
7
+ if defined?(@selector)
8
+ @selector.close
9
+ end
10
+ end
11
+ end
12
+
3
13
  RSpec.shared_context "an NIO selectable" do
4
- let(:selector) { NIO::Selector.new }
14
+ include_context NIO::Selector
5
15
 
6
- it "selects readable objects", retry: 5 do # retry: Flaky on OS X
16
+ it "selects readable objects" do
7
17
  monitor = selector.register(readable_subject, :r)
8
- ready = selector.select(0)
18
+ ready = selector.select(1)
9
19
  expect(ready).to be_an Enumerable
10
20
  expect(ready).to include monitor
11
21
  end
@@ -17,25 +27,29 @@ RSpec.shared_context "an NIO selectable" do
17
27
 
18
28
  it "selects writable objects" do
19
29
  monitor = selector.register(writable_subject, :w)
20
- ready = selector.select(0)
30
+ ready = selector.select(1)
21
31
  expect(ready).to be_an Enumerable
22
32
  expect(ready).to include monitor
23
33
  end
24
34
 
25
35
  it "does not select unwritable objects" do
26
36
  selector.register(unwritable_subject, :w)
27
- expect(selector.select(0)).to be_nil
37
+ ready = selector.select(0)
38
+ expect(ready).to be_nil
28
39
  end
29
40
  end
30
41
 
31
- RSpec.shared_context "an NIO selectable stream" do
32
- let(:selector) { NIO::Selector.new }
42
+ RSpec.shared_context "an NIO selectable stream" do |is_tls13|
43
+ include_context NIO::Selector
44
+
33
45
  let(:stream) { pair.first }
34
46
  let(:peer) { pair.last }
35
47
 
36
48
  it "selects readable when the other end closes" do
37
49
  monitor = selector.register(stream, :r)
38
- expect(selector.select(0)).to be_nil
50
+ unless is_tls13
51
+ expect(selector.select(1)).to be_nil
52
+ end
39
53
 
40
54
  peer.close
41
55
  # Wait and give the TCP session time to close
@@ -44,22 +58,28 @@ RSpec.shared_context "an NIO selectable stream" do
44
58
  end
45
59
 
46
60
  RSpec.shared_context "an NIO bidirectional stream" do
47
- let(:selector) { NIO::Selector.new }
48
- let(:stream) { pair.first }
49
- let(:peer) { pair.last }
61
+ include_context NIO::Selector
62
+
63
+ let(:stream) {pair.first}
64
+ let(:peer) {pair.last}
50
65
 
51
- it "selects readable and writable", retry: 5 do # retry: Flaky on OS X
66
+ it "selects readable and writable" do
52
67
  selector.register(readable_subject, :rw)
53
- selector.select(0) do |m|
54
- expect(m.readiness).to eq(:rw)
68
+
69
+ selector.select(1) do |monitor|
70
+ expect(monitor.readiness).to eq(:rw)
55
71
  end
72
+
73
+ readable_subject.close
56
74
  end
75
+
57
76
  it "keeps readiness after the selectable has been closed" do
58
77
  selector.register(readable_subject, :rw)
59
- selector.select(0) do |m|
60
- expect(m.readiness).to eq(:rw)
78
+
79
+ selector.select(1) do |monitor|
80
+ expect(monitor.readiness).to eq(:rw)
61
81
  readable_subject.close
62
- expect(m.readiness).to eq(:rw)
82
+ expect(monitor.readiness).to eq(:rw)
63
83
  end
64
84
  end
65
85
  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.3.1
4
+ version: 2.5.3
5
5
  platform: java
6
6
  authors:
7
7
  - Tony Arcieri
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-05-02 00:00:00.000000000 Z
11
+ date: 2020-09-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement
@@ -17,8 +17,8 @@ dependencies:
17
17
  - !ruby/object:Gem::Version
18
18
  version: '0'
19
19
  name: bundler
20
- prerelease: false
21
20
  type: :development
21
+ prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - ">="
@@ -31,8 +31,8 @@ dependencies:
31
31
  - !ruby/object:Gem::Version
32
32
  version: '0'
33
33
  name: rake
34
- prerelease: false
35
34
  type: :development
35
+ prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - ">="
@@ -46,33 +46,30 @@ executables: []
46
46
  extensions: []
47
47
  extra_rdoc_files: []
48
48
  files:
49
+ - ".github/workflows/workflow.yml"
49
50
  - ".gitignore"
50
51
  - ".rspec"
51
52
  - ".rubocop.yml"
52
- - ".travis.yml"
53
53
  - CHANGES.md
54
54
  - Gemfile
55
55
  - Guardfile
56
- - LICENSE.txt
57
56
  - README.md
58
57
  - Rakefile
59
- - appveyor.yml
60
58
  - examples/echo_server.rb
61
59
  - ext/libev/Changes
62
60
  - ext/libev/LICENSE
63
61
  - ext/libev/README
64
- - ext/libev/README.embed
65
62
  - ext/libev/ev.c
66
63
  - ext/libev/ev.h
67
64
  - ext/libev/ev_epoll.c
68
65
  - ext/libev/ev_kqueue.c
66
+ - ext/libev/ev_linuxaio.c
69
67
  - ext/libev/ev_poll.c
70
68
  - ext/libev/ev_port.c
71
69
  - ext/libev/ev_select.c
72
70
  - ext/libev/ev_vars.h
73
71
  - ext/libev/ev_win32.c
74
72
  - ext/libev/ev_wrap.h
75
- - ext/libev/test_libev_win32.c
76
73
  - ext/nio4r/bytebuffer.c
77
74
  - ext/nio4r/extconf.rb
78
75
  - ext/nio4r/libev.h
@@ -92,6 +89,9 @@ files:
92
89
  - lib/nio4r_ext.jar
93
90
  - logo.png
94
91
  - nio4r.gemspec
92
+ - rakelib/extension.rake
93
+ - rakelib/rspec.rake
94
+ - rakelib/rubocop.rake
95
95
  - spec/nio/acceptables_spec.rb
96
96
  - spec/nio/bytebuffer_spec.rb
97
97
  - spec/nio/monitor_spec.rb
@@ -102,13 +102,15 @@ files:
102
102
  - spec/nio/selector_spec.rb
103
103
  - spec/spec_helper.rb
104
104
  - spec/support/selectable_examples.rb
105
- - tasks/extension.rake
106
- - tasks/rspec.rake
107
- - tasks/rubocop.rake
108
105
  homepage: https://github.com/socketry/nio4r
109
106
  licenses:
110
107
  - MIT
111
- metadata: {}
108
+ metadata:
109
+ bug_tracker_uri: https://github.com/socketry/nio4r/issues
110
+ changelog_uri: https://github.com/socketry/nio4r/blob/master/CHANGES.md
111
+ documentation_uri: https://www.rubydoc.info/gems/nio4r/2.5.3
112
+ source_code_uri: https://github.com/socketry/nio4r/tree/v2.5.3
113
+ wiki_uri: https://github.com/socketry/nio4r/wiki
112
114
  post_install_message:
113
115
  rdoc_options: []
114
116
  require_paths:
@@ -117,16 +119,25 @@ required_ruby_version: !ruby/object:Gem::Requirement
117
119
  requirements:
118
120
  - - ">="
119
121
  - !ruby/object:Gem::Version
120
- version: 2.2.2
122
+ version: '2.4'
121
123
  required_rubygems_version: !ruby/object:Gem::Requirement
122
124
  requirements:
123
125
  - - ">="
124
126
  - !ruby/object:Gem::Version
125
127
  version: '0'
126
128
  requirements: []
127
- rubyforge_project:
128
- rubygems_version: 2.7.4
129
+ rubygems_version: 3.0.6
129
130
  signing_key:
130
131
  specification_version: 4
131
132
  summary: New IO for Ruby
132
- test_files: []
133
+ test_files:
134
+ - spec/nio/acceptables_spec.rb
135
+ - spec/nio/bytebuffer_spec.rb
136
+ - spec/nio/monitor_spec.rb
137
+ - spec/nio/selectables/pipe_spec.rb
138
+ - spec/nio/selectables/ssl_socket_spec.rb
139
+ - spec/nio/selectables/tcp_socket_spec.rb
140
+ - spec/nio/selectables/udp_socket_spec.rb
141
+ - spec/nio/selector_spec.rb
142
+ - spec/spec_helper.rb
143
+ - spec/support/selectable_examples.rb