io-wait 0.1.0 → 0.2.2.pre1

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: 5ea39ff5c3815f098f8c15eb5b493e27408afda30a88d11cd00564ab85438639
4
- data.tar.gz: 1a9ba20f028fe3259153bac2aa27b70870ef8e103d00c20cb6f7a267da94a6b5
3
+ metadata.gz: 3cdf9086254a2bafdcebba616ff05a5b024389e554861fcea442fc27882bd73a
4
+ data.tar.gz: 51740df7f2f5b67161a3c6e336698de3a345f38ed331e4e701af28f3990875b8
5
5
  SHA512:
6
- metadata.gz: bebdf7aba83d894c28fa9763b0048047c437c67962a939e3d29a6b4cbefe1ac690afd8ef8ed372d013204b1298f7fab0f01cd45c35ced0bb4d62e4234818f0ae
7
- data.tar.gz: 0f9635692758b787c4dc873e449e0a3e893dee5427f122fbda17f9458d4f33916bd32c333bf76023a73285177ac70b4b576025504130423089467fdb703266b5
6
+ metadata.gz: 55eb2c59c806b21fb6d038c7ccc58ec59f1a7e7a5a4e5bc2991b893b19f2a8265624e666daed915a4b58c0981619bb3459d80aa7856be6a8c9ba1277449f1b83
7
+ data.tar.gz: ecc6d22a99dbb5ac2c911f187c0253a30c3764e398997cde8d57efd54d278a317cfbc6149ab8d2a1695b71119ab04c0498c122111d37b8eeb544a74372ce3937
data/Gemfile CHANGED
@@ -1,4 +1,11 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
- # Specify your gem's dependencies in etc.gemspec
3
+ # Specify your gem's dependencies in io-wait.gemspec
4
4
  gemspec
5
+
6
+ group :development do
7
+ gem "rake"
8
+ gem "rake-compiler"
9
+ gem "test-unit"
10
+ gem 'ruby-maven', :platforms => :jruby
11
+ end
data/ext/io/wait/depend CHANGED
@@ -2,7 +2,7 @@
2
2
  wait.o: $(RUBY_EXTCONF_H)
3
3
  wait.o: $(arch_hdrdir)/ruby/config.h
4
4
  wait.o: $(hdrdir)/ruby.h
5
- wait.o: $(hdrdir)/ruby/assert.h
5
+ # wait.o: $(hdrdir)/ruby/assert.h # not in 2.6
6
6
  wait.o: $(hdrdir)/ruby/backward.h
7
7
  wait.o: $(hdrdir)/ruby/defines.h
8
8
  wait.o: $(hdrdir)/ruby/encoding.h
@@ -1,19 +1,24 @@
1
1
  # frozen_string_literal: false
2
2
  require 'mkmf'
3
- target = "io/wait"
4
3
 
5
- unless macro_defined?("DOSISH", "#include <ruby.h>")
6
- have_header(ioctl_h = "sys/ioctl.h") or ioctl_h = nil
7
- fionread = %w[sys/ioctl.h sys/filio.h sys/socket.h].find do |h|
8
- have_macro("FIONREAD", [h, ioctl_h].compact)
9
- end
10
- if fionread
11
- $defs << "-DFIONREAD_HEADER=\"<#{fionread}>\""
12
- create_makefile(target)
13
- end
4
+ if RUBY_VERSION < "2.6"
5
+ File.write("Makefile", dummy_makefile($srcdir).join(""))
14
6
  else
15
- if have_func("rb_w32_ioctlsocket", "ruby.h")
16
- have_func("rb_w32_is_socket", "ruby.h")
17
- create_makefile(target)
7
+ target = "io/wait"
8
+ have_func("rb_io_wait")
9
+ unless macro_defined?("DOSISH", "#include <ruby.h>")
10
+ have_header(ioctl_h = "sys/ioctl.h") or ioctl_h = nil
11
+ fionread = %w[sys/ioctl.h sys/filio.h sys/socket.h].find do |h|
12
+ have_macro("FIONREAD", [h, ioctl_h].compact)
13
+ end
14
+ if fionread
15
+ $defs << "-DFIONREAD_HEADER=\"<#{fionread}>\""
16
+ create_makefile(target)
17
+ end
18
+ else
19
+ if have_func("rb_w32_ioctlsocket", "ruby.h")
20
+ have_func("rb_w32_is_socket", "ruby.h")
21
+ create_makefile(target)
22
+ end
18
23
  end
19
24
  end
data/ext/io/wait/wait.c CHANGED
@@ -1,3 +1,4 @@
1
+ /* -*- c-file-style: "ruby"; indent-tabs-mode: t -*- */
1
2
  /**********************************************************************
2
3
 
3
4
  io/wait.c -
@@ -39,6 +40,7 @@
39
40
  #define FIONREAD_POSSIBLE_P(fd) ((void)(fd),Qtrue)
40
41
  #endif
41
42
 
43
+ #ifndef HAVE_RB_IO_WAIT
42
44
  static VALUE io_ready_p _((VALUE io));
43
45
  static VALUE io_wait_readable _((int argc, VALUE *argv, VALUE io));
44
46
  static VALUE io_wait_writable _((int argc, VALUE *argv, VALUE io));
@@ -67,6 +69,7 @@ wait_for_single_fd(rb_io_t *fptr, int events, struct timeval *tv)
67
69
  rb_io_check_closed(fptr);
68
70
  return (i & events);
69
71
  }
72
+ #endif
70
73
 
71
74
  /*
72
75
  * call-seq:
@@ -74,6 +77,8 @@ wait_for_single_fd(rb_io_t *fptr, int events, struct timeval *tv)
74
77
  *
75
78
  * Returns number of bytes that can be read without blocking.
76
79
  * Returns zero if no information available.
80
+ *
81
+ * You must require 'io/wait' to use this method.
77
82
  */
78
83
 
79
84
  static VALUE
@@ -93,77 +98,164 @@ io_nread(VALUE io)
93
98
  return INT2FIX(0);
94
99
  }
95
100
 
101
+ #ifdef HAVE_RB_IO_WAIT
102
+ static VALUE
103
+ io_wait_event(VALUE io, int event, VALUE timeout)
104
+ {
105
+ VALUE result = rb_io_wait(io, RB_INT2NUM(event), timeout);
106
+
107
+ if (!RB_TEST(result)) {
108
+ return Qnil;
109
+ }
110
+
111
+ int mask = RB_NUM2INT(result);
112
+
113
+ if (mask & event) {
114
+ return io;
115
+ }
116
+ else {
117
+ return Qfalse;
118
+ }
119
+ }
120
+ #endif
121
+
96
122
  /*
97
123
  * call-seq:
98
- * io.ready? -> true or false
124
+ * io.ready? -> truthy or falsy
99
125
  *
100
- * Returns true if input available without blocking, or false.
126
+ * Returns a truthy value if input available without blocking, or a
127
+ * falsy value.
128
+ *
129
+ * You must require 'io/wait' to use this method.
101
130
  */
102
131
 
103
132
  static VALUE
104
133
  io_ready_p(VALUE io)
105
134
  {
106
135
  rb_io_t *fptr;
136
+ #ifndef HAVE_RB_IO_WAIT
107
137
  struct timeval tv = {0, 0};
138
+ #endif
108
139
 
109
140
  GetOpenFile(io, fptr);
110
141
  rb_io_check_readable(fptr);
111
142
  if (rb_io_read_pending(fptr)) return Qtrue;
143
+
144
+ #ifndef HAVE_RB_IO_WAIT
112
145
  if (wait_for_single_fd(fptr, RB_WAITFD_IN, &tv))
113
146
  return Qtrue;
147
+ #else
148
+ if (RTEST(io_wait_event(io, RUBY_IO_READABLE, RB_INT2NUM(0))))
149
+ return Qtrue;
150
+ #endif
114
151
  return Qfalse;
115
152
  }
116
153
 
117
154
  /*
118
155
  * call-seq:
119
- * io.wait_readable -> IO, true or nil
120
- * io.wait_readable(timeout) -> IO, true or nil
156
+ * io.wait_readable -> truthy or falsy
157
+ * io.wait_readable(timeout) -> truthy or falsy
158
+ *
159
+ * Waits until IO is readable and returns a truthy value, or a falsy
160
+ * value when times out. Returns a truthy value immediately when
161
+ * buffered data is available.
121
162
  *
122
- * Waits until IO is readable without blocking and returns +self+, or
123
- * +nil+ when times out.
124
- * Returns +true+ immediately when buffered data is available.
163
+ * You must require 'io/wait' to use this method.
125
164
  */
126
165
 
127
166
  static VALUE
128
167
  io_wait_readable(int argc, VALUE *argv, VALUE io)
129
168
  {
130
169
  rb_io_t *fptr;
170
+ #ifndef HAVE_RB_IO_WAIT
131
171
  struct timeval timerec;
132
172
  struct timeval *tv;
173
+ #endif
133
174
 
134
175
  GetOpenFile(io, fptr);
135
176
  rb_io_check_readable(fptr);
177
+
178
+ #ifndef HAVE_RB_IO_WAIT
136
179
  tv = get_timeout(argc, argv, &timerec);
180
+ #endif
137
181
  if (rb_io_read_pending(fptr)) return Qtrue;
182
+
183
+ #ifndef HAVE_RB_IO_WAIT
138
184
  if (wait_for_single_fd(fptr, RB_WAITFD_IN, tv)) {
139
185
  return io;
140
186
  }
141
187
  return Qnil;
188
+ #else
189
+ rb_check_arity(argc, 0, 1);
190
+ VALUE timeout = (argc == 1 ? argv[0] : Qnil);
191
+
192
+ return io_wait_event(io, RUBY_IO_READABLE, timeout);
193
+ #endif
142
194
  }
143
195
 
144
196
  /*
145
197
  * call-seq:
146
- * io.wait_writable -> IO
147
- * io.wait_writable(timeout) -> IO or nil
198
+ * io.wait_writable -> truthy or falsy
199
+ * io.wait_writable(timeout) -> truthy or falsy
200
+ *
201
+ * Waits until IO is writable and returns a truthy value or a falsy
202
+ * value when times out.
148
203
  *
149
- * Waits until IO is writable without blocking and returns +self+ or
150
- * +nil+ when times out.
204
+ * You must require 'io/wait' to use this method.
151
205
  */
152
206
  static VALUE
153
207
  io_wait_writable(int argc, VALUE *argv, VALUE io)
154
208
  {
155
209
  rb_io_t *fptr;
210
+ #ifndef HAVE_RB_IO_WAIT
156
211
  struct timeval timerec;
157
212
  struct timeval *tv;
213
+ #endif
158
214
 
159
215
  GetOpenFile(io, fptr);
160
216
  rb_io_check_writable(fptr);
217
+
218
+ #ifndef HAVE_RB_IO_WAIT
161
219
  tv = get_timeout(argc, argv, &timerec);
162
220
  if (wait_for_single_fd(fptr, RB_WAITFD_OUT, tv)) {
163
221
  return io;
164
222
  }
165
223
  return Qnil;
224
+ #else
225
+ rb_check_arity(argc, 0, 1);
226
+ VALUE timeout = (argc == 1 ? argv[0] : Qnil);
227
+
228
+ return io_wait_event(io, RUBY_IO_WRITABLE, timeout);
229
+ #endif
230
+ }
231
+
232
+ #ifdef HAVE_RB_IO_WAIT
233
+ /*
234
+ * call-seq:
235
+ * io.wait_priority -> truthy or falsy
236
+ * io.wait_priority(timeout) -> truthy or falsy
237
+ *
238
+ * Waits until IO is priority and returns a truthy value or a falsy
239
+ * value when times out.
240
+ *
241
+ * You must require 'io/wait' to use this method.
242
+ */
243
+ static VALUE
244
+ io_wait_priority(int argc, VALUE *argv, VALUE io)
245
+ {
246
+ rb_io_t *fptr = NULL;
247
+
248
+ RB_IO_POINTER(io, fptr);
249
+ rb_io_check_readable(fptr);
250
+
251
+ if (rb_io_read_pending(fptr)) return Qtrue;
252
+
253
+ rb_check_arity(argc, 0, 1);
254
+ VALUE timeout = argc == 1 ? argv[0] : Qnil;
255
+
256
+ return io_wait_event(io, RUBY_IO_PRIORITY, timeout);
166
257
  }
258
+ #endif
167
259
 
168
260
  static int
169
261
  wait_mode_sym(VALUE mode)
@@ -201,18 +293,27 @@ wait_mode_sym(VALUE mode)
201
293
 
202
294
  /*
203
295
  * call-seq:
204
- * io.wait(timeout = nil, mode = :read) -> IO, true or nil
296
+ * io.wait(events, timeout) -> truthy or falsy
297
+ * io.wait(timeout = nil, mode = :read) -> truthy or falsy.
298
+ *
299
+ * Waits until the IO becomes ready for the specified events and returns the
300
+ * subset of events that become ready, or a falsy value when times out.
301
+ *
302
+ * The events can be a bit mask of +IO::READABLE+, +IO::WRITABLE+ or
303
+ * +IO::PRIORITY+.
304
+ *
305
+ * Returns a truthy value immediately when buffered data is available.
205
306
  *
206
- * Waits until IO is readable or writable without blocking and returns
207
- * +self+, or +nil+ when times out.
208
- * Returns +true+ immediately when buffered data is available.
209
307
  * Optional parameter +mode+ is one of +:read+, +:write+, or
210
308
  * +:read_write+.
309
+ *
310
+ * You must require 'io/wait' to use this method.
211
311
  */
212
312
 
213
313
  static VALUE
214
- io_wait_readwrite(int argc, VALUE *argv, VALUE io)
314
+ io_wait(int argc, VALUE *argv, VALUE io)
215
315
  {
316
+ #ifndef HAVE_RB_IO_WAIT
216
317
  rb_io_t *fptr;
217
318
  struct timeval timerec;
218
319
  struct timeval *tv = NULL;
@@ -236,6 +337,44 @@ io_wait_readwrite(int argc, VALUE *argv, VALUE io)
236
337
  if (wait_for_single_fd(fptr, event, tv))
237
338
  return io;
238
339
  return Qnil;
340
+ #else
341
+ VALUE timeout = Qundef;
342
+ rb_io_event_t events = 0;
343
+
344
+ if (argc != 2 || (RB_SYMBOL_P(argv[0]) || RB_SYMBOL_P(argv[1]))) {
345
+ for (int i = 0; i < argc; i += 1) {
346
+ if (RB_SYMBOL_P(argv[i])) {
347
+ events |= wait_mode_sym(argv[i]);
348
+ }
349
+ else if (timeout == Qundef) {
350
+ rb_time_interval(timeout = argv[i]);
351
+ }
352
+ else {
353
+ rb_raise(rb_eArgError, "timeout given more than once");
354
+ }
355
+ }
356
+ if (timeout == Qundef) timeout = Qnil;
357
+ }
358
+ else /* argc == 2 */ {
359
+ events = RB_NUM2UINT(argv[0]);
360
+ timeout = argv[1];
361
+ }
362
+
363
+ if (events == 0) {
364
+ events = RUBY_IO_READABLE;
365
+ }
366
+
367
+ if (events & RUBY_IO_READABLE) {
368
+ rb_io_t *fptr = NULL;
369
+ RB_IO_POINTER(io, fptr);
370
+
371
+ if (rb_io_read_pending(fptr)) {
372
+ return Qtrue;
373
+ }
374
+ }
375
+
376
+ return io_wait_event(io, events, timeout);
377
+ #endif
239
378
  }
240
379
 
241
380
  /*
@@ -245,9 +384,18 @@ io_wait_readwrite(int argc, VALUE *argv, VALUE io)
245
384
  void
246
385
  Init_wait(void)
247
386
  {
387
+ #ifdef HAVE_RB_EXT_RACTOR_SAFE
388
+ RB_EXT_RACTOR_SAFE(true);
389
+ #endif
390
+
248
391
  rb_define_method(rb_cIO, "nread", io_nread, 0);
249
392
  rb_define_method(rb_cIO, "ready?", io_ready_p, 0);
250
- rb_define_method(rb_cIO, "wait", io_wait_readwrite, -1);
393
+
394
+ rb_define_method(rb_cIO, "wait", io_wait, -1);
395
+
251
396
  rb_define_method(rb_cIO, "wait_readable", io_wait_readable, -1);
252
397
  rb_define_method(rb_cIO, "wait_writable", io_wait_writable, -1);
398
+ #ifdef HAVE_RB_IO_WAIT
399
+ rb_define_method(rb_cIO, "wait_priority", io_wait_priority, -1);
400
+ #endif
253
401
  }
metadata CHANGED
@@ -1,34 +1,31 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: io-wait
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.2.pre1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nobu Nakada
8
+ - Charles Oliver Nutter
8
9
  autorequire:
9
10
  bindir: exe
10
11
  cert_chain: []
11
- date: 2020-09-18 00:00:00.000000000 Z
12
+ date: 2022-03-10 00:00:00.000000000 Z
12
13
  dependencies: []
13
14
  description: Waits until IO is readable or writable without blocking.
14
15
  email:
15
16
  - nobu@ruby-lang.org
17
+ - headius@headius.com
16
18
  executables: []
17
- extensions: []
19
+ extensions:
20
+ - ext/io/wait/extconf.rb
18
21
  extra_rdoc_files: []
19
22
  files:
20
- - ".gitignore"
21
- - ".travis.yml"
22
23
  - COPYING
23
24
  - Gemfile
24
25
  - README.md
25
- - Rakefile
26
- - bin/console
27
- - bin/setup
28
26
  - ext/io/wait/depend
29
27
  - ext/io/wait/extconf.rb
30
28
  - ext/io/wait/wait.c
31
- - io-wait.gemspec
32
29
  homepage: https://github.com/ruby/io-wait
33
30
  licenses:
34
31
  - Ruby
@@ -44,14 +41,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
44
41
  requirements:
45
42
  - - ">="
46
43
  - !ruby/object:Gem::Version
47
- version: 2.3.0
44
+ version: '0'
48
45
  required_rubygems_version: !ruby/object:Gem::Requirement
49
46
  requirements:
50
- - - ">="
47
+ - - ">"
51
48
  - !ruby/object:Gem::Version
52
- version: '0'
49
+ version: 1.3.1
53
50
  requirements: []
54
- rubygems_version: 3.2.0.rc.1
51
+ rubygems_version: 3.4.0.dev
55
52
  signing_key:
56
53
  specification_version: 4
57
54
  summary: Waits until IO is readable or writable without blocking.
data/.gitignore DELETED
@@ -1,11 +0,0 @@
1
- /.bundle/
2
- /.yardoc
3
- /_yardoc/
4
- /coverage/
5
- /doc/
6
- /pkg/
7
- /spec/reports/
8
- /tmp/
9
- *.bundle
10
- *.dll
11
- *.so
data/.travis.yml DELETED
@@ -1,6 +0,0 @@
1
- ---
2
- language: ruby
3
- cache: bundler
4
- rvm:
5
- - 2.8.0
6
- before_install: gem install bundler -v 2.1.4
data/Rakefile DELETED
@@ -1,12 +0,0 @@
1
- require "bundler/gem_tasks"
2
- require "rake/testtask"
3
-
4
- Rake::TestTask.new(:test) do |t|
5
- t.libs << "test/lib"
6
- t.ruby_opts << "-rhelper"
7
- t.test_files = FileList["test/**/test_*.rb"]
8
- end
9
-
10
- require 'rake/extensiontask'
11
- Rake::ExtensionTask.new("io/wait")
12
- task :default => :test
data/bin/console DELETED
@@ -1,14 +0,0 @@
1
- #!/usr/bin/env ruby
2
-
3
- require "bundler/setup"
4
- require "io/wait"
5
-
6
- # You can add fixtures and/or initialization code here to make experimenting
7
- # with your gem easier. You can also use a different console, if you like.
8
-
9
- # (If you use this, don't forget to add pry to your Gemfile!)
10
- # require "pry"
11
- # Pry.start
12
-
13
- require "irb"
14
- IRB.start(__FILE__)
data/bin/setup DELETED
@@ -1,8 +0,0 @@
1
- #!/usr/bin/env bash
2
- set -euo pipefail
3
- IFS=$'\n\t'
4
- set -vx
5
-
6
- bundle install
7
-
8
- # Do any other automated setup that you need to do here
data/io-wait.gemspec DELETED
@@ -1,22 +0,0 @@
1
- Gem::Specification.new do |spec|
2
- spec.name = "io-wait"
3
- spec.version = "0.1.0"
4
- spec.authors = ["Nobu Nakada"]
5
- spec.email = ["nobu@ruby-lang.org"]
6
-
7
- spec.summary = %q{Waits until IO is readable or writable without blocking.}
8
- spec.description = %q{Waits until IO is readable or writable without blocking.}
9
- spec.homepage = "https://github.com/ruby/io-wait"
10
- spec.licenses = ["Ruby", "BSD-2-Clause"]
11
- spec.required_ruby_version = Gem::Requirement.new(">= 2.3.0")
12
-
13
- spec.metadata["homepage_uri"] = spec.homepage
14
- spec.metadata["source_code_uri"] = spec.homepage
15
-
16
- spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
17
- `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
18
- end
19
- spec.bindir = "exe"
20
- spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
21
- spec.require_paths = ["lib"]
22
- end