eventmachine 1.0.3-x86-mingw32 → 1.2.0.dev.2-x86-mingw32
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CHANGELOG.md +84 -1
- data/README.md +6 -7
- data/ext/binder.cpp +10 -10
- data/ext/binder.h +5 -5
- data/ext/cmain.cpp +173 -61
- data/ext/ed.cpp +262 -127
- data/ext/ed.h +50 -30
- data/ext/em.cpp +491 -445
- data/ext/em.h +101 -36
- data/ext/eventmachine.h +67 -51
- data/ext/extconf.rb +124 -31
- data/ext/fastfilereader/extconf.rb +9 -2
- data/ext/fastfilereader/mapper.cpp +3 -1
- data/ext/fastfilereader/rubymain.cpp +7 -7
- data/ext/kb.cpp +1 -1
- data/ext/pipe.cpp +11 -4
- data/ext/project.h +26 -6
- data/ext/rubymain.cpp +408 -201
- data/ext/ssl.cpp +167 -20
- data/ext/ssl.h +11 -2
- data/java/src/com/rubyeventmachine/EmReactor.java +16 -0
- data/java/src/com/rubyeventmachine/EventableChannel.java +2 -0
- data/java/src/com/rubyeventmachine/EventableDatagramChannel.java +6 -0
- data/java/src/com/rubyeventmachine/EventableSocketChannel.java +55 -10
- data/lib/1.9/fastfilereaderext.so +0 -0
- data/lib/1.9/rubyeventmachine.so +0 -0
- data/lib/2.0/fastfilereaderext.so +0 -0
- data/lib/2.0/rubyeventmachine.so +0 -0
- data/lib/2.1/fastfilereaderext.so +0 -0
- data/lib/2.1/rubyeventmachine.so +0 -0
- data/lib/2.2/fastfilereaderext.so +0 -0
- data/lib/2.2/rubyeventmachine.so +0 -0
- data/lib/2.3/fastfilereaderext.so +0 -0
- data/lib/2.3/rubyeventmachine.so +0 -0
- data/lib/em/buftok.rb +34 -85
- data/lib/em/channel.rb +5 -0
- data/lib/em/completion.rb +2 -2
- data/lib/em/connection.rb +62 -4
- data/lib/em/iterator.rb +30 -48
- data/lib/em/pool.rb +1 -1
- data/lib/em/protocols/httpclient.rb +31 -11
- data/lib/em/protocols/line_and_text.rb +4 -4
- data/lib/em/protocols/linetext2.rb +44 -39
- data/lib/em/protocols/smtpclient.rb +60 -31
- data/lib/em/protocols/smtpserver.rb +32 -9
- data/lib/em/pure_ruby.rb +8 -3
- data/lib/em/queue.rb +16 -7
- data/lib/em/resolver.rb +64 -24
- data/lib/em/threaded_resource.rb +2 -2
- data/lib/em/tick_loop.rb +19 -19
- data/lib/em/version.rb +1 -1
- data/lib/eventmachine.rb +96 -49
- data/lib/jeventmachine.rb +17 -0
- data/rakelib/package.rake +31 -4
- data/tests/dhparam.pem +13 -0
- data/tests/em_test_helper.rb +87 -0
- data/tests/test_attach.rb +25 -0
- data/tests/test_basic.rb +27 -38
- data/tests/test_channel.rb +14 -1
- data/tests/test_completion.rb +1 -0
- data/tests/test_connection_count.rb +22 -1
- data/tests/test_connection_write.rb +35 -0
- data/tests/test_defer.rb +17 -0
- data/tests/test_epoll.rb +26 -14
- data/tests/test_file_watch.rb +1 -0
- data/tests/test_fork.rb +75 -0
- data/tests/test_httpclient.rb +43 -0
- data/tests/test_idle_connection.rb +6 -4
- data/tests/test_ipv4.rb +125 -0
- data/tests/test_ipv6.rb +131 -0
- data/tests/test_iterator.rb +115 -0
- data/tests/test_kb.rb +19 -25
- data/tests/test_ltp2.rb +20 -0
- data/tests/test_many_fds.rb +22 -0
- data/tests/test_pause.rb +29 -0
- data/tests/test_pool.rb +2 -0
- data/tests/test_process_watch.rb +2 -0
- data/tests/test_processes.rb +7 -7
- data/tests/test_queue.rb +14 -0
- data/tests/test_resolver.rb +56 -7
- data/tests/test_set_sock_opt.rb +2 -0
- data/tests/test_smtpclient.rb +20 -0
- data/tests/test_ssl_args.rb +2 -2
- data/tests/test_ssl_dhparam.rb +83 -0
- data/tests/test_ssl_ecdh_curve.rb +79 -0
- data/tests/test_ssl_extensions.rb +49 -0
- data/tests/test_ssl_methods.rb +22 -5
- data/tests/test_ssl_protocols.rb +246 -0
- data/tests/test_ssl_verify.rb +103 -59
- data/tests/test_system.rb +4 -0
- data/tests/test_threaded_resource.rb +8 -0
- data/tests/test_unbind_reason.rb +5 -1
- metadata +173 -107
- data/.gitignore +0 -21
- data/.travis.yml +0 -12
- data/.yardopts +0 -7
- data/Gemfile +0 -2
- data/Rakefile +0 -20
- data/eventmachine.gemspec +0 -36
- data/rakelib/cpp.rake_example +0 -77
data/lib/jeventmachine.rb
CHANGED
@@ -268,6 +268,20 @@ module EventMachine
|
|
268
268
|
@em.getConnectionCount
|
269
269
|
end
|
270
270
|
|
271
|
+
def self.pause_connection(sig)
|
272
|
+
@em.pauseConnection(sig)
|
273
|
+
end
|
274
|
+
def self.resume_connection(sig)
|
275
|
+
@em.resumeConnection(sig)
|
276
|
+
end
|
277
|
+
def self.connection_paused?(sig)
|
278
|
+
@em.isConnectionPaused(sig)
|
279
|
+
end
|
280
|
+
def self._get_outbound_data_size(sig)
|
281
|
+
@em.getOutboundDataSize(sig)
|
282
|
+
end
|
283
|
+
|
284
|
+
|
271
285
|
def self.set_tls_parms(sig, params)
|
272
286
|
end
|
273
287
|
def self.start_tls(sig)
|
@@ -279,6 +293,9 @@ module EventMachine
|
|
279
293
|
def associate_callback_target sig
|
280
294
|
# No-op for the time being
|
281
295
|
end
|
296
|
+
def get_outbound_data_size
|
297
|
+
EM._get_outbound_data_size @signature
|
298
|
+
end
|
282
299
|
end
|
283
300
|
end
|
284
301
|
|
data/rakelib/package.rake
CHANGED
@@ -25,14 +25,19 @@ else
|
|
25
25
|
def setup_cross_compilation(ext)
|
26
26
|
unless RUBY_PLATFORM =~ /mswin|mingw/
|
27
27
|
ext.cross_compile = true
|
28
|
-
ext.cross_platform = ['x86-mingw32', '
|
28
|
+
ext.cross_platform = ['x86-mingw32', 'x64-mingw32']
|
29
29
|
end
|
30
30
|
end
|
31
31
|
def hack_cross_compilation(ext)
|
32
32
|
# inject 1.8/1.9 pure-ruby entry point
|
33
33
|
# HACK: add these dependencies to the task instead of using cross_compiling
|
34
|
-
ext.cross_platform.
|
35
|
-
|
34
|
+
if ext.cross_platform.is_a?(Array)
|
35
|
+
ext.cross_platform.each do |platform|
|
36
|
+
task = "native:#{GEMSPEC.name}:#{platform}"
|
37
|
+
if Rake::Task.task_defined?(task)
|
38
|
+
Rake::Task[task].prerequisites.unshift "lib/#{ext.name}.rb"
|
39
|
+
end
|
40
|
+
end
|
36
41
|
end
|
37
42
|
end
|
38
43
|
|
@@ -60,7 +65,7 @@ end
|
|
60
65
|
require "\#{$1}/#{File.basename(t.name, '.rb')}"
|
61
66
|
eoruby
|
62
67
|
end
|
63
|
-
at_exit{ FileUtils.rm t.name if File.
|
68
|
+
at_exit{ FileUtils.rm t.name if File.exist?(t.name) }
|
64
69
|
end
|
65
70
|
end
|
66
71
|
|
@@ -91,3 +96,25 @@ def gem_cmd(action, name, *args)
|
|
91
96
|
end
|
92
97
|
|
93
98
|
Rake::Task[:clean].enhance [:clobber_package]
|
99
|
+
|
100
|
+
# DevKit task following the example of Luis Lavena's test-ruby-c-extension
|
101
|
+
task :devkit do
|
102
|
+
begin
|
103
|
+
require "devkit"
|
104
|
+
rescue LoadError => e
|
105
|
+
abort "Failed to activate RubyInstaller's DevKit required for compilation."
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
if RUBY_PLATFORM =~ /mingw|mswin/
|
110
|
+
Rake::Task['compile'].prerequisites.unshift 'devkit'
|
111
|
+
end
|
112
|
+
|
113
|
+
desc "Build binary gems for Windows with rake-compiler-dock"
|
114
|
+
task 'gem:windows' do
|
115
|
+
require 'rake_compiler_dock'
|
116
|
+
RakeCompilerDock.sh <<-EOT
|
117
|
+
RUBY_CC_VERSION="${RUBY_CC_VERSION//1.8.7/}"
|
118
|
+
bundle && rake cross native gem
|
119
|
+
EOT
|
120
|
+
end
|
data/tests/dhparam.pem
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
-----BEGIN DH PARAMETERS-----
|
2
|
+
MIICCAKCAgEAikiatXa5aAteOtd6hOO33npjCvJByD3dwuM8rWzz0DFZdUH9nFJi
|
3
|
+
b0VvTVweVECb6XZBsrDNLqGQykCrm43swSk5D9XQCGJLxFERD6yk3b90xaeCm3/a
|
4
|
+
b0Ek5ZVvV73Cc/YbVmpBiOHoTFpUFJLZ7pLMQUSn8y3qUlNcY9/88HuwFi1s1lRM
|
5
|
+
ovihSRyZMYAuYWOD4yuOuIcroKVjD6gWFrsW9XrALWny6vUXQrhk8Q3rj+wM6ZtE
|
6
|
+
5afcB0b6ZJtphrDfk3dFjOVG/zVT37VWgrY8GABrpo2ey0W0WIQJ7rDKLaPaI4kc
|
7
|
+
voOgC2K8Z3kSARZK+jULnwmBeYECz4EH/FF6FEp3GOKtkL4mqEkvh1n5EAesDOGl
|
8
|
+
iiX+RZXcUrZliSeifSXBTMJWWFVC0fkGIMb9PTZfZHyAC54lpuxzVki0HIyQG9Fs
|
9
|
+
41zBJ5e8eEoXXlfUYtduUC35YGy2IxSzYLAJE76rctAZSWghha9xLOCDFoLjMr8h
|
10
|
+
FosKeHKJcBQ0bc8ymOpRIfrYLWhc0Pz2zkpJ/4eYw9t7NYg7S+jP19IE0gUnuM9v
|
11
|
+
SpoYMtS28tP9nEdokdwuBKD0D3bJEBBefDlHgfXoMgvy9Hivc9PBGGNTNpyFPpwF
|
12
|
+
sWVAkfhoNMJMC5V7LZsze+lftiDtzVoLSPDa9bO4BK7b/MgwCxfOhGsCAQI=
|
13
|
+
-----END DH PARAMETERS-----
|
data/tests/em_test_helper.rb
CHANGED
@@ -31,6 +31,61 @@ class Test::Unit::TestCase
|
|
31
31
|
@@port
|
32
32
|
end
|
33
33
|
|
34
|
+
# Returns true if the host have a localhost 127.0.0.1 IPv4.
|
35
|
+
def self.local_ipv4?
|
36
|
+
return @@has_local_ipv4 if defined?(@@has_local_ipv4)
|
37
|
+
begin
|
38
|
+
get_my_ipv4_address "127.0.0.1"
|
39
|
+
@@has_local_ipv4 = true
|
40
|
+
rescue
|
41
|
+
@@has_local_ipv4 = false
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
# Returns true if the host have a public IPv4 and stores it in
|
46
|
+
# @@public_ipv4.
|
47
|
+
def self.public_ipv4?
|
48
|
+
return @@has_public_ipv4 if defined?(@@has_public_ipv4)
|
49
|
+
begin
|
50
|
+
@@public_ipv4 = get_my_ipv4_address "1.2.3.4"
|
51
|
+
@@has_public_ipv4 = true
|
52
|
+
rescue
|
53
|
+
@@has_public_ipv4 = false
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
# Returns true if the host have a localhost ::1 IPv6.
|
58
|
+
def self.local_ipv6?
|
59
|
+
return @@has_local_ipv6 if defined?(@@has_local_ipv6)
|
60
|
+
begin
|
61
|
+
get_my_ipv6_address "::1"
|
62
|
+
@@has_local_ipv6 = true
|
63
|
+
rescue
|
64
|
+
@@has_local_ipv6 = false
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
# Returns true if the host have a public IPv6 and stores it in
|
69
|
+
# @@public_ipv6.
|
70
|
+
def self.public_ipv6?
|
71
|
+
return @@has_public_ipv6 if defined?(@@has_public_ipv6)
|
72
|
+
begin
|
73
|
+
@@public_ipv6 = get_my_ipv6_address "2001::1"
|
74
|
+
@@has_public_ipv6 = true
|
75
|
+
rescue
|
76
|
+
@@has_public_ipv6 = false
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
# Returns an array with the localhost addresses (IPv4 and/or IPv6).
|
81
|
+
def local_ips
|
82
|
+
return @@local_ips if defined?(@@local_ips)
|
83
|
+
@@local_ips = []
|
84
|
+
@@local_ips << "127.0.0.1" if self.class.local_ipv4?
|
85
|
+
@@local_ips << "::1" if self.class.local_ipv6?
|
86
|
+
@@local_ips
|
87
|
+
end
|
88
|
+
|
34
89
|
def exception_class
|
35
90
|
jruby? ? NativeException : RuntimeError
|
36
91
|
end
|
@@ -41,10 +96,18 @@ class Test::Unit::TestCase
|
|
41
96
|
RbConfig::CONFIG['host_os'] =~ /mswin|mingw/
|
42
97
|
end
|
43
98
|
|
99
|
+
def solaris?
|
100
|
+
RUBY_PLATFORM =~ /solaris/
|
101
|
+
end
|
102
|
+
|
44
103
|
# http://stackoverflow.com/questions/1342535/how-can-i-tell-if-im-running-from-jruby-vs-ruby/1685970#1685970
|
45
104
|
def jruby?
|
46
105
|
defined? JRUBY_VERSION
|
47
106
|
end
|
107
|
+
|
108
|
+
def rbx?
|
109
|
+
defined?(RUBY_ENGINE) && RUBY_ENGINE == 'rbx'
|
110
|
+
end
|
48
111
|
end
|
49
112
|
|
50
113
|
include PlatformHelper
|
@@ -61,4 +124,28 @@ class Test::Unit::TestCase
|
|
61
124
|
$VERBOSE = backup
|
62
125
|
end
|
63
126
|
end
|
127
|
+
|
128
|
+
|
129
|
+
private
|
130
|
+
|
131
|
+
def self.get_my_ipv4_address ip
|
132
|
+
orig, Socket.do_not_reverse_lookup = Socket.do_not_reverse_lookup, true # turn off reverse DNS resolution temporarily
|
133
|
+
UDPSocket.open(Socket::AF_INET) do |s|
|
134
|
+
s.connect ip, 1
|
135
|
+
s.addr.last
|
136
|
+
end
|
137
|
+
ensure
|
138
|
+
Socket.do_not_reverse_lookup = orig
|
139
|
+
end
|
140
|
+
|
141
|
+
def self.get_my_ipv6_address ip
|
142
|
+
orig, Socket.do_not_reverse_lookup = Socket.do_not_reverse_lookup, true # turn off reverse DNS resolution temporarily
|
143
|
+
UDPSocket.open(Socket::AF_INET6) do |s|
|
144
|
+
s.connect ip, 1
|
145
|
+
s.addr.last
|
146
|
+
end
|
147
|
+
ensure
|
148
|
+
Socket.do_not_reverse_lookup = orig
|
149
|
+
end
|
150
|
+
|
64
151
|
end
|
data/tests/test_attach.rb
CHANGED
@@ -4,6 +4,7 @@ require 'socket'
|
|
4
4
|
class TestAttach < Test::Unit::TestCase
|
5
5
|
class EchoServer < EM::Connection
|
6
6
|
def receive_data data
|
7
|
+
$received_data << data
|
7
8
|
send_data data
|
8
9
|
end
|
9
10
|
end
|
@@ -31,12 +32,14 @@ class TestAttach < Test::Unit::TestCase
|
|
31
32
|
def setup
|
32
33
|
@port = next_port
|
33
34
|
$read, $r, $w, $fd = nil
|
35
|
+
$received_data = ""
|
34
36
|
end
|
35
37
|
|
36
38
|
def teardown
|
37
39
|
[$r, $w].each do |io|
|
38
40
|
io.close rescue nil
|
39
41
|
end
|
42
|
+
$received_data = nil
|
40
43
|
end
|
41
44
|
|
42
45
|
def test_attach
|
@@ -63,6 +66,28 @@ class TestAttach < Test::Unit::TestCase
|
|
63
66
|
end
|
64
67
|
end
|
65
68
|
|
69
|
+
def test_attach_server
|
70
|
+
omit_if(jruby?)
|
71
|
+
$before = TCPServer.new("127.0.0.1", @port)
|
72
|
+
sig = nil
|
73
|
+
EM.run {
|
74
|
+
sig = EM.attach_server $before, EchoServer
|
75
|
+
|
76
|
+
handler = Class.new(EM::Connection) do
|
77
|
+
def initialize
|
78
|
+
send_data "hello world"
|
79
|
+
close_connection_after_writing
|
80
|
+
EM.add_timer(0.1) { EM.stop }
|
81
|
+
end
|
82
|
+
end
|
83
|
+
EM.connect("127.0.0.1", @port, handler)
|
84
|
+
}
|
85
|
+
|
86
|
+
assert_equal false, $before.closed?
|
87
|
+
assert_equal "hello world", $received_data
|
88
|
+
assert sig.is_a?(Integer)
|
89
|
+
end
|
90
|
+
|
66
91
|
def test_attach_pipe
|
67
92
|
EM.run{
|
68
93
|
$r, $w = IO.pipe
|
data/tests/test_basic.rb
CHANGED
@@ -93,15 +93,28 @@ class TestBasic < Test::Unit::TestCase
|
|
93
93
|
end
|
94
94
|
end
|
95
95
|
|
96
|
-
def
|
96
|
+
def test_unbind_error_during_stop
|
97
97
|
assert_raises( UnbindError::ERR ) {
|
98
98
|
EM.run {
|
99
99
|
EM.start_server "127.0.0.1", @port
|
100
|
-
EM.connect "127.0.0.1", @port, UnbindError
|
100
|
+
EM.connect "127.0.0.1", @port, UnbindError do
|
101
|
+
EM.stop
|
102
|
+
end
|
101
103
|
}
|
102
104
|
}
|
103
105
|
end
|
104
106
|
|
107
|
+
def test_unbind_error
|
108
|
+
EM.run {
|
109
|
+
EM.error_handler do |e|
|
110
|
+
assert(e.is_a?(UnbindError::ERR))
|
111
|
+
EM.stop
|
112
|
+
end
|
113
|
+
EM.start_server "127.0.0.1", @port
|
114
|
+
EM.connect "127.0.0.1", @port, UnbindError
|
115
|
+
}
|
116
|
+
end
|
117
|
+
|
105
118
|
module BrsTestSrv
|
106
119
|
def receive_data data
|
107
120
|
$received << data
|
@@ -131,6 +144,8 @@ class TestBasic < Test::Unit::TestCase
|
|
131
144
|
end
|
132
145
|
|
133
146
|
def test_bind_connect
|
147
|
+
pend('FIXME: this test is broken on Windows') if windows?
|
148
|
+
|
134
149
|
local_ip = UDPSocket.open {|s| s.connect('google.com', 80); s.addr.last }
|
135
150
|
|
136
151
|
bind_port = next_port
|
@@ -179,18 +194,15 @@ class TestBasic < Test::Unit::TestCase
|
|
179
194
|
assert x
|
180
195
|
end
|
181
196
|
|
182
|
-
|
183
|
-
|
184
|
-
|
185
|
-
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
end
|
192
|
-
else
|
193
|
-
warn "EM.set_heartbeat_interval not implemented, skipping a test in #{__FILE__}"
|
197
|
+
def test_set_heartbeat_interval
|
198
|
+
omit_if(jruby?)
|
199
|
+
interval = 0.5
|
200
|
+
EM.run {
|
201
|
+
EM.set_heartbeat_interval interval
|
202
|
+
$interval = EM.get_heartbeat_interval
|
203
|
+
EM.stop
|
204
|
+
}
|
205
|
+
assert_equal(interval, $interval)
|
194
206
|
end
|
195
207
|
|
196
208
|
module PostInitRaiser
|
@@ -226,6 +238,7 @@ class TestBasic < Test::Unit::TestCase
|
|
226
238
|
end
|
227
239
|
|
228
240
|
def test_schedule_close
|
241
|
+
omit_if(jruby?)
|
229
242
|
localhost, port = '127.0.0.1', 9000
|
230
243
|
timer_ran = false
|
231
244
|
num_close_scheduled = nil
|
@@ -246,30 +259,6 @@ class TestBasic < Test::Unit::TestCase
|
|
246
259
|
assert_equal 1, num_close_scheduled
|
247
260
|
end
|
248
261
|
|
249
|
-
def test_fork_safe
|
250
|
-
return unless cpid = fork { exit! } rescue false
|
251
|
-
|
252
|
-
read, write = IO.pipe
|
253
|
-
EM.run do
|
254
|
-
cpid = fork do
|
255
|
-
write.puts "forked"
|
256
|
-
EM.run do
|
257
|
-
EM.next_tick do
|
258
|
-
write.puts "EM ran"
|
259
|
-
exit!
|
260
|
-
end
|
261
|
-
end
|
262
|
-
end
|
263
|
-
EM.stop
|
264
|
-
end
|
265
|
-
Process.waitall
|
266
|
-
assert_equal "forked\n", read.readline
|
267
|
-
assert_equal "EM ran\n", read.readline
|
268
|
-
ensure
|
269
|
-
read.close rescue nil
|
270
|
-
write.close rescue nil
|
271
|
-
end
|
272
|
-
|
273
262
|
def test_error_handler_idempotent # issue 185
|
274
263
|
errors = []
|
275
264
|
ticks = []
|
data/tests/test_channel.rb
CHANGED
@@ -59,4 +59,17 @@ class TestEMChannel < Test::Unit::TestCase
|
|
59
59
|
|
60
60
|
assert_equal [1,2,3], out
|
61
61
|
end
|
62
|
-
|
62
|
+
|
63
|
+
def test_channel_num_subscribers
|
64
|
+
subs = 0
|
65
|
+
EM.run do
|
66
|
+
c = EM::Channel.new
|
67
|
+
c.subscribe { |v| s = v }
|
68
|
+
c.subscribe { |v| s = v }
|
69
|
+
EM.next_tick { EM.stop }
|
70
|
+
subs = c.num_subscribers
|
71
|
+
end
|
72
|
+
|
73
|
+
assert_equal subs, 2
|
74
|
+
end
|
75
|
+
end
|
data/tests/test_completion.rb
CHANGED
@@ -30,4 +30,25 @@ class TestConnectionCount < Test::Unit::TestCase
|
|
30
30
|
assert_equal(1, $server_conns)
|
31
31
|
assert_equal(4, $client_conns + $server_conns)
|
32
32
|
end
|
33
|
-
|
33
|
+
|
34
|
+
module DoubleCloseClient
|
35
|
+
def unbind
|
36
|
+
close_connection
|
37
|
+
$num_close_scheduled_1 = EM.num_close_scheduled
|
38
|
+
EM.next_tick do
|
39
|
+
$num_close_scheduled_2 = EM.num_close_scheduled
|
40
|
+
EM.stop
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def test_num_close_scheduled
|
46
|
+
omit_if(jruby?)
|
47
|
+
EM.run {
|
48
|
+
assert_equal(0, EM.num_close_scheduled)
|
49
|
+
EM.connect("127.0.0.1", 9999, DoubleCloseClient) # nothing listening on 9999
|
50
|
+
}
|
51
|
+
assert_equal(1, $num_close_scheduled_1)
|
52
|
+
assert_equal(0, $num_close_scheduled_2)
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'em_test_helper'
|
2
|
+
|
3
|
+
class TestConnectionWrite < Test::Unit::TestCase
|
4
|
+
|
5
|
+
# This test takes advantage of the fact that EM::_RunSelectOnce iterates over the connections twice:
|
6
|
+
# - once to determine which ones to call Write() on
|
7
|
+
# - and once to call Write() on each of them.
|
8
|
+
#
|
9
|
+
# But state may change in the meantime before Write() is finally called.
|
10
|
+
# And that is what we try to exploit to get Write() to be called when bWatchOnly is true, and bNotifyWritable is false,
|
11
|
+
# to cause an assertion failure.
|
12
|
+
|
13
|
+
module SimpleClient
|
14
|
+
def notify_writable
|
15
|
+
$conn2.notify_writable = false # Being naughty in callback
|
16
|
+
# If this doesn't crash anything, the test passed!
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
def test_with_naughty_callback
|
21
|
+
EM.run do
|
22
|
+
r1, _ = IO.pipe
|
23
|
+
r2, _ = IO.pipe
|
24
|
+
|
25
|
+
# Adding EM.watches
|
26
|
+
$conn1 = EM.watch(r1, SimpleClient)
|
27
|
+
$conn2 = EM.watch(r2, SimpleClient)
|
28
|
+
|
29
|
+
$conn1.notify_writable = true
|
30
|
+
$conn2.notify_writable = true
|
31
|
+
|
32
|
+
EM.stop
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|