Feature #9502 ยป remove-deprecates.diff
bignum.c (working copy) | ||
---|---|---|
3686 | 3686 |
return bignorm(val); |
3687 | 3687 |
} |
3688 | 3688 | |
3689 |
#define QUAD_SIZE 8 |
|
3690 | ||
3691 |
void |
|
3692 |
rb_quad_pack(char *buf, VALUE val) |
|
3693 |
{ |
|
3694 |
rb_integer_pack(val, buf, 1, QUAD_SIZE, 0, |
|
3695 |
INTEGER_PACK_NATIVE_BYTE_ORDER| |
|
3696 |
INTEGER_PACK_2COMP); |
|
3697 |
} |
|
3698 | ||
3699 |
VALUE |
|
3700 |
rb_quad_unpack(const char *buf, int signed_p) |
|
3701 |
{ |
|
3702 |
return rb_integer_unpack(buf, 1, QUAD_SIZE, 0, |
|
3703 |
INTEGER_PACK_NATIVE_BYTE_ORDER| |
|
3704 |
(signed_p ? INTEGER_PACK_2COMP : 0)); |
|
3705 |
} |
|
3706 | ||
3707 | 3689 |
#define conv_digit(c) (ruby_digit36_to_number_table[(unsigned char)(c)]) |
3708 | 3690 | |
3709 | 3691 |
static void |
... | ... | |
4540 | 4522 |
return base36_power_cache[base - 2][power_level]; |
4541 | 4523 |
} |
4542 | 4524 | |
4543 |
/* |
|
4544 |
* deprecated. (used only from deprecated rb_big2str0) |
|
4545 |
* |
|
4546 |
* big2str_muraken_find_n1 |
|
4547 |
* |
|
4548 |
* Let a natural number x is given by: |
|
4549 |
* x = 2^0 * x_0 + 2^1 * x_1 + ... + 2^(B*n_0 - 1) * x_{B*n_0 - 1}, |
|
4550 |
* where B is BITSPERDIG (i.e. BDIGITS*CHAR_BIT) and n_0 is |
|
4551 |
* RBIGNUM_LEN(x). |
|
4552 |
* |
|
4553 |
* Now, we assume n_1 = min_n \{ n | 2^(B*n_0/2) <= b_1^(n_1) \}, so |
|
4554 |
* it is realized that 2^(B*n_0) <= {b_1}^{2*n_1}, where b_1 is a |
|
4555 |
* given radix number. And then, we have n_1 <= (B*n_0) / |
|
4556 |
* (2*log_2(b_1)), therefore n_1 is given by ceil((B*n_0) / |
|
4557 |
* (2*log_2(b_1))). |
|
4558 |
*/ |
|
4559 |
static long |
|
4560 |
big2str_find_n1(VALUE x, int base) |
|
4561 |
{ |
|
4562 |
static const double log_2[] = { |
|
4563 |
1.0, 1.58496250072116, 2.0, |
|
4564 |
2.32192809488736, 2.58496250072116, 2.8073549220576, |
|
4565 |
3.0, 3.16992500144231, 3.32192809488736, |
|
4566 |
3.4594316186373, 3.58496250072116, 3.70043971814109, |
|
4567 |
3.8073549220576, 3.90689059560852, 4.0, |
|
4568 |
4.08746284125034, 4.16992500144231, 4.24792751344359, |
|
4569 |
4.32192809488736, 4.39231742277876, 4.4594316186373, |
|
4570 |
4.52356195605701, 4.58496250072116, 4.64385618977472, |
|
4571 |
4.70043971814109, 4.75488750216347, 4.8073549220576, |
|
4572 |
4.85798099512757, 4.90689059560852, 4.95419631038688, |
|
4573 |
5.0, 5.04439411935845, 5.08746284125034, |
|
4574 |
5.12928301694497, 5.16992500144231 |
|
4575 |
}; |
|
4576 |
long bits; |
|
4577 | ||
4578 |
if (base < 2 || 36 < base) |
|
4579 |
rb_bug("invalid radix %d", base); |
|
4580 | ||
4581 |
if (FIXNUM_P(x)) { |
|
4582 |
bits = (SIZEOF_LONG*CHAR_BIT - 1)/2 + 1; |
|
4583 |
} |
|
4584 |
else if (BIGZEROP(x)) { |
|
4585 |
return 0; |
|
4586 |
} |
|
4587 |
else if (RBIGNUM_LEN(x) >= LONG_MAX/BITSPERDIG) { |
|
4588 |
rb_raise(rb_eRangeError, "bignum too big to convert into `string'"); |
|
4589 |
} |
|
4590 |
else { |
|
4591 |
bits = BITSPERDIG*RBIGNUM_LEN(x); |
|
4592 |
} |
|
4593 | ||
4594 |
/* @shyouhei note: vvvvvvvvvvvvv this cast is suspicious. But I believe it is OK, because if that cast loses data, this x value is too big, and should have raised RangeError. */ |
|
4595 |
return (long)ceil(((double)bits)/log_2[base - 2]); |
|
4596 |
} |
|
4597 | ||
4598 | 4525 |
struct big2str_struct { |
4599 | 4526 |
int negative; |
4600 | 4527 |
int base; |
... | ... | |
4976 | 4903 |
return big2str_generic(x, base); |
4977 | 4904 |
} |
4978 | 4905 | |
4979 |
/* deprecated */ |
|
4980 |
VALUE |
|
4981 |
rb_big2str0(VALUE x, int base, int trim) |
|
4982 |
{ |
|
4983 |
VALUE str; |
|
4984 |
long oldlen; |
|
4985 |
long n2; |
|
4986 | ||
4987 |
str = rb_big2str1(x, base); |
|
4988 | ||
4989 |
if (trim || FIXNUM_P(x) || BIGZEROP(x)) |
|
4990 |
return str; |
|
4991 | ||
4992 |
oldlen = RSTRING_LEN(str); |
|
4993 |
if (oldlen && RSTRING_PTR(str)[0] != '-') { |
|
4994 |
rb_str_resize(str, oldlen+1); |
|
4995 |
MEMMOVE(RSTRING_PTR(str)+1, RSTRING_PTR(str), char, oldlen); |
|
4996 |
RSTRING_PTR(str)[0] = '+'; |
|
4997 |
} |
|
4998 | ||
4999 |
n2 = big2str_find_n1(x, base); |
|
5000 | ||
5001 |
oldlen = RSTRING_LEN(str); |
|
5002 |
if (oldlen-1 < n2) { |
|
5003 |
long off = n2 - (oldlen-1); |
|
5004 |
rb_str_resize(str, n2+1); |
|
5005 |
MEMMOVE(RSTRING_PTR(str)+1+off, RSTRING_PTR(str)+1, char, oldlen-1); |
|
5006 |
memset(RSTRING_PTR(str)+1, '0', off); |
|
5007 |
} |
|
5008 | ||
5009 |
RSTRING_PTR(str)[RSTRING_LEN(str)] = '\0'; |
|
5010 | ||
5011 |
return str; |
|
5012 |
} |
|
5013 | ||
5014 | 4906 |
VALUE |
5015 | 4907 |
rb_big2str(VALUE x, int base) |
5016 | 4908 |
{ |
... | ... | |
5071 | 4963 |
return num; |
5072 | 4964 |
} |
5073 | 4965 | |
5074 |
/* deprecated */ |
|
5075 |
VALUE |
|
5076 |
rb_big2ulong_pack(VALUE x) |
|
5077 |
{ |
|
5078 |
unsigned long num; |
|
5079 |
rb_integer_pack(x, &num, 1, sizeof(num), 0, |
|
5080 |
INTEGER_PACK_NATIVE_BYTE_ORDER|INTEGER_PACK_2COMP); |
|
5081 |
return num; |
|
5082 |
} |
|
5083 | ||
5084 | 4966 |
VALUE |
5085 | 4967 |
rb_big2ulong(VALUE x) |
5086 | 4968 |
{ |
ext/-test-/old_thread_select/depend (working copy) | ||
---|---|---|
1 |
$(OBJS): $(HDRS) $(ruby_headers) \ |
|
2 |
$(hdrdir)/ruby/io.h \ |
|
3 |
$(hdrdir)/ruby/encoding.h \ |
|
4 |
$(hdrdir)/ruby/oniguruma.h |
ext/-test-/old_thread_select/extconf.rb (working copy) | ||
---|---|---|
1 |
$warnflags = "-Wno-deprecated-declarations" |
|
2 |
$warnflags = "" unless try_compile("", $warnflags) |
|
3 | ||
4 |
create_makefile("-test-/old_thread_select/old_thread_select") |
ext/-test-/old_thread_select/old_thread_select.c (working copy) | ||
---|---|---|
1 |
/* test case for deprecated C API */ |
|
2 |
#include "ruby/ruby.h" |
|
3 |
#include "ruby/io.h" |
|
4 | ||
5 |
static fd_set * array2fdset(fd_set *fds, VALUE ary, int *max) |
|
6 |
{ |
|
7 |
long i; |
|
8 | ||
9 |
if (NIL_P(ary)) |
|
10 |
return NULL; |
|
11 | ||
12 |
FD_ZERO(fds); |
|
13 |
Check_Type(ary, T_ARRAY); |
|
14 |
for (i = 0; i < RARRAY_LEN(ary); i++) { |
|
15 |
VALUE val = RARRAY_PTR(ary)[i]; |
|
16 |
int fd; |
|
17 | ||
18 |
Check_Type(val, T_FIXNUM); |
|
19 |
fd = FIX2INT(val); |
|
20 |
if (fd >= *max) |
|
21 |
*max = fd + 1; |
|
22 |
FD_SET(fd, fds); |
|
23 |
} |
|
24 | ||
25 |
return fds; |
|
26 |
} |
|
27 | ||
28 |
static void fdset2array(VALUE dst, fd_set *fds, int max) |
|
29 |
{ |
|
30 |
int i; |
|
31 | ||
32 |
rb_ary_clear(dst); |
|
33 | ||
34 |
for (i = 0; i < max; i++) { |
|
35 |
if (FD_ISSET(i, fds)) |
|
36 |
rb_ary_push(dst, INT2NUM(i)); |
|
37 |
} |
|
38 |
} |
|
39 | ||
40 |
static VALUE |
|
41 |
old_thread_select(VALUE klass, VALUE r, VALUE w, VALUE e, VALUE timeout) |
|
42 |
{ |
|
43 |
struct timeval tv; |
|
44 |
struct timeval *tvp = NULL; |
|
45 |
fd_set rfds, wfds, efds; |
|
46 |
fd_set *rp, *wp, *ep; |
|
47 |
int rc; |
|
48 |
int max = 0; |
|
49 | ||
50 |
if (!NIL_P(timeout)) { |
|
51 |
tv = rb_time_timeval(timeout); |
|
52 |
tvp = &tv; |
|
53 |
} |
|
54 |
rp = array2fdset(&rfds, r, &max); |
|
55 |
wp = array2fdset(&wfds, w, &max); |
|
56 |
ep = array2fdset(&efds, e, &max); |
|
57 |
rc = rb_thread_select(max, rp, wp, ep, tvp); |
|
58 |
if (rc == -1) |
|
59 |
rb_sys_fail("rb_wait_for_single_fd"); |
|
60 | ||
61 |
if (rp) |
|
62 |
fdset2array(r, &rfds, max); |
|
63 |
if (wp) |
|
64 |
fdset2array(w, &wfds, max); |
|
65 |
if (ep) |
|
66 |
fdset2array(e, &efds, max); |
|
67 |
return INT2NUM(rc); |
|
68 |
} |
|
69 | ||
70 |
void |
|
71 |
Init_old_thread_select(void) |
|
72 |
{ |
|
73 |
rb_define_singleton_method(rb_cIO, "old_thread_select", |
|
74 |
old_thread_select, 4); |
|
75 |
} |
ext/socket/rubysocket.h (working copy) | ||
---|---|---|
256 | 256 | |
257 | 257 |
#include "constdefs.h" |
258 | 258 | |
259 |
#define BLOCKING_REGION(func, arg) (long)rb_thread_blocking_region((func), (arg), RUBY_UBF_IO, 0) |
|
260 | 259 |
#define BLOCKING_REGION_FD(func, arg) (long)rb_thread_io_blocking_region((func), (arg), (arg)->fd) |
261 | 260 | |
262 | 261 |
#define SockAddrStringValue(v) rsock_sockaddr_string_value(&(v)) |
gc.c (working copy) | ||
---|---|---|
5795 | 5795 |
} |
5796 | 5796 | |
5797 | 5797 |
void |
5798 |
rb_gc_set_params(void) |
|
5799 |
{ |
|
5800 |
ruby_gc_set_params(rb_safe_level()); |
|
5801 |
} |
|
5802 | ||
5803 |
void |
|
5804 | 5798 |
rb_objspace_reachable_objects_from(VALUE obj, void (func)(VALUE, void *), void *data) |
5805 | 5799 |
{ |
5806 | 5800 |
rb_objspace_t *objspace = &rb_objspace; |
include/ruby/backward/rubysig.h (working copy) | ||
---|---|---|
29 | 29 | |
30 | 30 |
RUBY_SYMBOL_EXPORT_BEGIN |
31 | 31 | |
32 |
struct rb_blocking_region_buffer; |
|
33 |
DEPRECATED(RUBY_EXTERN struct rb_blocking_region_buffer *rb_thread_blocking_region_begin(void)); |
|
34 |
DEPRECATED(RUBY_EXTERN void rb_thread_blocking_region_end(struct rb_blocking_region_buffer *)); |
|
35 |
#define TRAP_BEG do {struct rb_blocking_region_buffer *__region = rb_thread_blocking_region_begin(); |
|
36 |
#define TRAP_END rb_thread_blocking_region_end(__region);} while (0) |
|
37 | 32 |
#define RUBY_CRITICAL(statements) do {statements;} while (0) |
38 | 33 |
#define DEFER_INTS (0) |
39 | 34 |
#define ENABLE_INTS (1) |
include/ruby/intern.h (working copy) | ||
---|---|---|
102 | 102 |
VALUE rb_cstr2inum(const char*, int); |
103 | 103 |
VALUE rb_str2inum(VALUE, int); |
104 | 104 |
VALUE rb_big2str(VALUE, int); |
105 |
DEPRECATED(VALUE rb_big2str0(VALUE, int, int)); |
|
106 | 105 |
SIGNED_VALUE rb_big2long(VALUE); |
107 | 106 |
#define rb_big2int(x) rb_big2long(x) |
108 | 107 |
VALUE rb_big2ulong(VALUE); |
109 | 108 |
#define rb_big2uint(x) rb_big2ulong(x) |
110 |
DEPRECATED(VALUE rb_big2ulong_pack(VALUE x)); |
|
111 | 109 |
#if HAVE_LONG_LONG |
112 | 110 |
LONG_LONG rb_big2ll(VALUE); |
113 | 111 |
unsigned LONG_LONG rb_big2ull(VALUE); |
114 | 112 |
#endif /* HAVE_LONG_LONG */ |
115 |
DEPRECATED(void rb_quad_pack(char*,VALUE)); |
|
116 |
DEPRECATED(VALUE rb_quad_unpack(const char*,int)); |
|
117 | 113 |
void rb_big_pack(VALUE val, unsigned long *buf, long num_longs); |
118 | 114 |
VALUE rb_big_unpack(unsigned long *buf, long num_longs); |
119 | 115 |
int rb_uv_to_utf8(char[6],unsigned long); |
... | ... | |
427 | 423 |
int rb_thread_fd_writable(int); |
428 | 424 |
void rb_thread_fd_close(int); |
429 | 425 |
int rb_thread_alone(void); |
430 |
DEPRECATED(void rb_thread_polling(void)); |
|
431 | 426 |
void rb_thread_sleep(int); |
432 | 427 |
void rb_thread_sleep_forever(void); |
433 | 428 |
void rb_thread_sleep_deadly(void); |
... | ... | |
437 | 432 |
VALUE rb_thread_run(VALUE); |
438 | 433 |
VALUE rb_thread_kill(VALUE); |
439 | 434 |
VALUE rb_thread_create(VALUE (*)(ANYARGS), void*); |
440 |
DEPRECATED(int rb_thread_select(int, fd_set *, fd_set *, fd_set *, struct timeval *)); |
|
441 | 435 |
int rb_thread_fd_select(int, rb_fdset_t *, rb_fdset_t *, rb_fdset_t *, struct timeval *); |
442 | 436 |
void rb_thread_wait_for(struct timeval); |
443 | 437 |
VALUE rb_thread_current(void); |
... | ... | |
482 | 476 |
VALUE rb_gc_enable(void); |
483 | 477 |
VALUE rb_gc_disable(void); |
484 | 478 |
VALUE rb_gc_start(void); |
485 |
DEPRECATED(void rb_gc_set_params(void)); |
|
486 | 479 |
VALUE rb_define_finalizer(VALUE, VALUE); |
487 | 480 |
VALUE rb_undefine_finalizer(VALUE); |
488 | 481 |
size_t rb_gc_count(void); |
... | ... | |
623 | 616 |
/* process.c */ |
624 | 617 |
void rb_last_status_set(int status, rb_pid_t pid); |
625 | 618 |
VALUE rb_last_status_get(void); |
626 |
struct rb_exec_arg { |
|
627 |
VALUE execarg_obj; |
|
628 |
}; |
|
629 |
DEPRECATED(int rb_proc_exec_n(int, VALUE*, const char*)); |
|
630 | 619 |
int rb_proc_exec(const char*); |
631 |
DEPRECATED(VALUE rb_exec_arg_init(int argc, VALUE *argv, int accept_shell, struct rb_exec_arg *e)); |
|
632 |
DEPRECATED(int rb_exec_arg_addopt(struct rb_exec_arg *e, VALUE key, VALUE val)); |
|
633 |
DEPRECATED(void rb_exec_arg_fixup(struct rb_exec_arg *e)); |
|
634 |
DEPRECATED(int rb_run_exec_options(const struct rb_exec_arg *e, struct rb_exec_arg *s)); |
|
635 |
DEPRECATED(int rb_run_exec_options_err(const struct rb_exec_arg *e, struct rb_exec_arg *s, char*, size_t)); |
|
636 |
DEPRECATED(int rb_exec(const struct rb_exec_arg*)); |
|
637 |
DEPRECATED(int rb_exec_err(const struct rb_exec_arg*, char*, size_t)); |
|
638 |
DEPRECATED(rb_pid_t rb_fork(int*, int (*)(void*), void*, VALUE)); |
|
639 |
DEPRECATED(rb_pid_t rb_fork_err(int*, int (*)(void*, char*, size_t), void*, VALUE, char*, size_t)); |
|
640 | 620 |
VALUE rb_f_exec(int,VALUE*); |
641 | 621 |
rb_pid_t rb_waitpid(rb_pid_t pid, int *status, int flags); |
642 | 622 |
void rb_syswait(rb_pid_t pid); |
... | ... | |
853 | 833 |
VALUE rb_struct_aref(VALUE, VALUE); |
854 | 834 |
VALUE rb_struct_aset(VALUE, VALUE, VALUE); |
855 | 835 |
VALUE rb_struct_getmember(VALUE, ID); |
856 |
DEPRECATED(VALUE rb_struct_iv_get(VALUE, const char*)); |
|
857 | 836 |
VALUE rb_struct_s_members(VALUE); |
858 | 837 |
VALUE rb_struct_members(VALUE); |
859 | 838 |
VALUE rb_struct_alloc_noinit(VALUE); |
... | ... | |
866 | 845 |
void rb_thread_check_ints(void); |
867 | 846 |
int rb_thread_interrupted(VALUE thval); |
868 | 847 | |
869 |
/* Use rb_thread_call_without_gvl family instead. */ |
|
870 |
DEPRECATED(VALUE rb_thread_blocking_region(rb_blocking_function_t *func, void *data1, |
|
871 |
rb_unblock_function_t *ubf, void *data2)); |
|
872 | 848 |
#define RUBY_UBF_IO ((rb_unblock_function_t *)-1) |
873 | 849 |
#define RUBY_UBF_PROCESS ((rb_unblock_function_t *)-1) |
874 | 850 |
VALUE rb_mutex_new(void); |
include/ruby/io.h (working copy) | ||
---|---|---|
195 | 195 | |
196 | 196 |
void rb_io_read_check(rb_io_t*); |
197 | 197 |
int rb_io_read_pending(rb_io_t*); |
198 |
DEPRECATED(void rb_read_check(FILE*)); |
|
199 | 198 | |
200 | 199 |
struct stat; |
201 | 200 |
VALUE rb_stat_new(const struct stat *); |
include/ruby/ruby.h (working copy) | ||
---|---|---|
541 | 541 |
#define StringValueCStr(v) rb_string_value_cstr(&(v)) |
542 | 542 | |
543 | 543 |
void rb_check_safe_obj(VALUE); |
544 |
DEPRECATED(void rb_check_safe_str(VALUE)); |
|
545 | 544 |
#define SafeStringValue(v) do {\ |
546 | 545 |
StringValue(v);\ |
547 | 546 |
rb_check_safe_obj(v);\ |
548 | 547 |
} while (0) |
549 |
/* obsolete macro - use SafeStringValue(v) */ |
|
550 |
#define Check_SafeStr(v) rb_check_safe_str((VALUE)(v)) |
|
551 | 548 | |
552 | 549 |
VALUE rb_str_export(VALUE); |
553 | 550 |
#define ExportStringValue(v) do {\ |
include/ruby/win32.h (working copy) | ||
---|---|---|
782 | 782 |
== ***CAUTION*** |
783 | 783 |
Since this function is very dangerous, ((*NEVER*)) |
784 | 784 |
* lock any HANDLEs(i.e. Mutex, Semaphore, CriticalSection and so on) or, |
785 |
* use anything like TRAP_BEG...TRAP_END block structure,
|
|
785 |
* use anything like rb_thread_call_without_gvl,
|
|
786 | 786 |
in asynchronous_func_t. |
787 | 787 |
*/ |
788 | 788 |
typedef uintptr_t (*asynchronous_func_t)(uintptr_t self, int argc, uintptr_t* argv); |
io.c (working copy) | ||
---|---|---|
397 | 397 |
#define argf_of(obj) (*(struct argf *)DATA_PTR(obj)) |
398 | 398 |
#define ARGF argf_of(argf) |
399 | 399 | |
400 |
#ifdef _STDIO_USES_IOSTREAM /* GNU libc */ |
|
401 |
# ifdef _IO_fpos_t |
|
402 |
# define STDIO_READ_DATA_PENDING(fp) ((fp)->_IO_read_ptr != (fp)->_IO_read_end) |
|
403 |
# else |
|
404 |
# define STDIO_READ_DATA_PENDING(fp) ((fp)->_gptr < (fp)->_egptr) |
|
405 |
# endif |
|
406 |
#elif defined(FILE_COUNT) |
|
407 |
# define STDIO_READ_DATA_PENDING(fp) ((fp)->FILE_COUNT > 0) |
|
408 |
#elif defined(FILE_READEND) |
|
409 |
# define STDIO_READ_DATA_PENDING(fp) ((fp)->FILE_READPTR < (fp)->FILE_READEND) |
|
410 |
#elif defined(__BEOS__) || defined(__HAIKU__) |
|
411 |
# define STDIO_READ_DATA_PENDING(fp) ((fp)->_state._eof == 0) |
|
412 |
#else |
|
413 |
# define STDIO_READ_DATA_PENDING(fp) (!feof(fp)) |
|
414 |
#endif |
|
415 | ||
416 | 400 |
#define GetWriteIO(io) rb_io_get_write_io(io) |
417 | 401 | |
418 | 402 |
#define READ_DATA_PENDING(fptr) ((fptr)->rbuf.len) |
... | ... | |
866 | 850 |
} |
867 | 851 | |
868 | 852 |
void |
869 |
rb_read_check(FILE *fp) |
|
870 |
{ |
|
871 |
if (!STDIO_READ_DATA_PENDING(fp)) { |
|
872 |
rb_thread_wait_fd(fileno(fp)); |
|
873 |
} |
|
874 |
} |
|
875 | ||
876 |
void |
|
877 | 853 |
rb_io_read_check(rb_io_t *fptr) |
878 | 854 |
{ |
879 | 855 |
if (!READ_DATA_PENDING(fptr)) { |
process.c (working copy) | ||
---|---|---|
1222 | 1222 |
#endif |
1223 | 1223 |
} |
1224 | 1224 | |
1225 |
/* deprecated */ |
|
1226 |
static int |
|
1227 |
proc_exec_v(char **argv, const char *prog) |
|
1228 |
{ |
|
1229 |
char fbuf[MAXPATHLEN]; |
|
1230 | ||
1231 |
if (!prog) |
|
1232 |
prog = argv[0]; |
|
1233 |
prog = dln_find_exe_r(prog, 0, fbuf, sizeof(fbuf)); |
|
1234 |
if (!prog) { |
|
1235 |
errno = ENOENT; |
|
1236 |
return -1; |
|
1237 |
} |
|
1238 |
before_exec(); |
|
1239 |
execv(prog, argv); |
|
1240 |
preserving_errno(try_with_sh(prog, argv, 0); after_exec()); |
|
1241 |
return -1; |
|
1242 |
} |
|
1243 | ||
1244 |
/* deprecated */ |
|
1245 |
int |
|
1246 |
rb_proc_exec_n(int argc, VALUE *argv, const char *prog) |
|
1247 |
{ |
|
1248 |
#define ARGV_COUNT(n) ((n)+1) |
|
1249 |
#define ARGV_SIZE(n) (sizeof(char*) * ARGV_COUNT(n)) |
|
1250 |
#define ALLOC_ARGV(n, v) ALLOCV_N(char*, (v), ARGV_COUNT(n)) |
|
1251 | ||
1252 |
char **args; |
|
1253 |
int i; |
|
1254 |
int ret = -1; |
|
1255 |
VALUE v; |
|
1256 | ||
1257 |
args = ALLOC_ARGV(argc+1, v); |
|
1258 |
for (i=0; i<argc; i++) { |
|
1259 |
args[i] = RSTRING_PTR(argv[i]); |
|
1260 |
} |
|
1261 |
args[i] = 0; |
|
1262 |
if (args[0]) { |
|
1263 |
ret = proc_exec_v(args, prog); |
|
1264 |
} |
|
1265 |
ALLOCV_END(v); |
|
1266 |
return ret; |
|
1267 | ||
1268 |
#undef ARGV_COUNT |
|
1269 |
#undef ARGV_SIZE |
|
1270 |
#undef ALLOC_ARGV |
|
1271 |
} |
|
1272 | ||
1273 | 1225 |
/* This function should be async-signal-safe. Actually it is. */ |
1274 | 1226 |
static int |
1275 | 1227 |
proc_exec_sh(const char *str, VALUE envp_str) |
... | ... | |
1796 | 1748 |
return ST_CONTINUE; |
1797 | 1749 |
} |
1798 | 1750 | |
1799 |
int |
|
1800 |
rb_exec_arg_addopt(struct rb_exec_arg *e, VALUE key, VALUE val) |
|
1801 |
{ |
|
1802 |
return rb_execarg_addopt(e->execarg_obj, key, val); |
|
1803 |
} |
|
1804 | ||
1805 | 1751 |
static int |
1806 | 1752 |
check_exec_options_i(st_data_t st_key, st_data_t st_val, st_data_t arg) |
1807 | 1753 |
{ |
... | ... | |
2252 | 2198 |
return ret; |
2253 | 2199 |
} |
2254 | 2200 | |
2255 |
VALUE |
|
2256 |
rb_exec_arg_init(int argc, VALUE *argv, int accept_shell, struct rb_exec_arg *e) |
|
2257 |
{ |
|
2258 |
return rb_execarg_init(argc, argv, accept_shell, e->execarg_obj); |
|
2259 |
} |
|
2260 | ||
2261 | 2201 |
void |
2262 | 2202 |
rb_execarg_setenv(VALUE execarg_obj, VALUE env) |
2263 | 2203 |
{ |
... | ... | |
2360 | 2300 |
RB_GC_GUARD(execarg_obj); |
2361 | 2301 |
} |
2362 | 2302 | |
2363 |
void |
|
2364 |
rb_exec_arg_fixup(struct rb_exec_arg *e) |
|
2365 |
{ |
|
2366 |
rb_execarg_fixup(e->execarg_obj); |
|
2367 |
} |
|
2368 | ||
2303 |
#if defined(__APPLE__) || defined(__HAIKU__) |
|
2369 | 2304 |
static int rb_exec_without_timer_thread(const struct rb_execarg *eargp, char *errmsg, size_t errmsg_buflen); |
2305 |
#endif |
|
2370 | 2306 | |
2371 | 2307 |
/* |
2372 | 2308 |
* call-seq: |
... | ... | |
2825 | 2761 |
run_exec_pgroup(const struct rb_execarg *eargp, struct rb_execarg *sargp, char *errmsg, size_t errmsg_buflen) |
2826 | 2762 |
{ |
2827 | 2763 |
/* |
2828 |
* If FD_CLOEXEC is available, rb_fork waits the child's execve. |
|
2829 |
* So setpgid is done in the child when rb_fork is returned in the parent. |
|
2764 |
* If FD_CLOEXEC is available, rb_fork_internal waits the child's execve. |
|
2765 |
* So setpgid is done in the child when rb_fork_internal is returned in |
|
2766 |
* the parent. |
|
2830 | 2767 |
* No race condition, even without setpgid from the parent. |
2831 | 2768 |
* (Is there an environment which has setpgid but no FD_CLOEXEC?) |
2832 | 2769 |
*/ |
... | ... | |
3050 | 2987 |
return 0; |
3051 | 2988 |
} |
3052 | 2989 | |
3053 |
int |
|
3054 |
rb_run_exec_options_err(const struct rb_exec_arg *e, struct rb_exec_arg *s, char *errmsg, size_t errmsg_buflen) |
|
3055 |
{ |
|
3056 |
return rb_execarg_run_options(rb_execarg_get(e->execarg_obj), rb_execarg_get(s->execarg_obj), errmsg, errmsg_buflen); |
|
3057 |
} |
|
3058 | ||
3059 |
int |
|
3060 |
rb_run_exec_options(const struct rb_exec_arg *e, struct rb_exec_arg *s) |
|
3061 |
{ |
|
3062 |
return rb_execarg_run_options(rb_execarg_get(e->execarg_obj), rb_execarg_get(s->execarg_obj), NULL, 0); |
|
3063 |
} |
|
3064 | ||
3065 | 2990 |
/* This function should be async-signal-safe. Hopefully it is. */ |
3066 | 2991 |
int |
3067 | 2992 |
rb_exec_async_signal_safe(const struct rb_execarg *eargp, char *errmsg, size_t errmsg_buflen) |
... | ... | |
3096 | 3021 |
return -1; |
3097 | 3022 |
} |
3098 | 3023 | |
3024 |
#if defined(__APPLE__) || defined(__HAIKU__) |
|
3099 | 3025 |
static int |
3100 | 3026 |
rb_exec_without_timer_thread(const struct rb_execarg *eargp, char *errmsg, size_t errmsg_buflen) |
3101 | 3027 |
{ |
... | ... | |
3105 | 3031 |
preserving_errno(after_exec_non_async_signal_safe()); /* not async-signal-safe because it calls rb_thread_start_timer_thread. */ |
3106 | 3032 |
return ret; |
3107 | 3033 |
} |
3108 | ||
3109 |
int |
|
3110 |
rb_exec_err(const struct rb_exec_arg *e, char *errmsg, size_t errmsg_buflen) |
|
3111 |
{ |
|
3112 |
return rb_exec_without_timer_thread(rb_execarg_get(e->execarg_obj), errmsg, errmsg_buflen); |
|
3113 |
} |
|
3114 | ||
3115 |
int |
|
3116 |
rb_exec(const struct rb_exec_arg *e) |
|
3117 |
{ |
|
3118 |
#if !defined FD_CLOEXEC && !defined HAVE_SPAWNV |
|
3119 |
char errmsg[80] = { '\0' }; |
|
3120 |
int ret = rb_exec_without_timer_thread(rb_execarg_get(e->execarg_obj), errmsg, sizeof(errmsg)); |
|
3121 |
preserving_errno( |
|
3122 |
if (errmsg[0]) { |
|
3123 |
fprintf(stderr, "%s\n", errmsg); |
|
3124 |
} |
|
3125 |
else { |
|
3126 |
fprintf(stderr, "%s:%d: command not found: %s\n", |
|
3127 |
rb_sourcefile(), rb_sourceline(), |
|
3128 |
RSTRING_PTR(e->use_shell ? e->invoke.sh.shell_script : e->invoke.cmd.command_name)); |
|
3129 |
} |
|
3130 |
); |
|
3131 |
return ret; |
|
3132 |
#else |
|
3133 |
return rb_exec_without_timer_thread(rb_execarg_get(e->execarg_obj), NULL, 0); |
|
3134 | 3034 |
#endif |
3135 |
} |
|
3136 | 3035 | |
3137 | 3036 |
#ifdef HAVE_FORK |
3138 | 3037 |
/* This function should be async-signal-safe. Hopefully it is. */ |
... | ... | |
3450 | 3349 |
} |
3451 | 3350 | |
3452 | 3351 |
rb_pid_t |
3453 |
rb_fork_err(int *status, int (*chfunc)(void*, char *, size_t), void *charg, VALUE fds, |
|
3454 |
char *errmsg, size_t errmsg_buflen) |
|
3455 |
{ |
|
3456 |
return rb_fork_internal(status, chfunc, charg, FALSE, fds, errmsg, errmsg_buflen); |
|
3457 |
} |
|
3458 | ||
3459 |
rb_pid_t |
|
3460 | 3352 |
rb_fork_async_signal_safe(int *status, int (*chfunc)(void*, char *, size_t), void *charg, VALUE fds, |
3461 | 3353 |
char *errmsg, size_t errmsg_buflen) |
3462 | 3354 |
{ |
3463 | 3355 |
return rb_fork_internal(status, chfunc, charg, TRUE, fds, errmsg, errmsg_buflen); |
3464 | 3356 |
} |
3465 | 3357 | |
3466 |
struct chfunc_wrapper_t { |
|
3467 |
int (*chfunc)(void*); |
|
3468 |
void *arg; |
|
3469 |
}; |
|
3470 | ||
3471 |
static int |
|
3472 |
chfunc_wrapper(void *arg_, char *errmsg, size_t errmsg_buflen) |
|
3473 |
{ |
|
3474 |
struct chfunc_wrapper_t *arg = arg_; |
|
3475 |
return arg->chfunc(arg->arg); |
|
3476 |
} |
|
3477 | ||
3478 |
rb_pid_t |
|
3479 |
rb_fork(int *status, int (*chfunc)(void*), void *charg, VALUE fds) |
|
3480 |
{ |
|
3481 |
if (chfunc) { |
|
3482 |
struct chfunc_wrapper_t warg; |
|
3483 |
warg.chfunc = chfunc; |
|
3484 |
warg.arg = charg; |
|
3485 |
return rb_fork_internal(status, chfunc_wrapper, &warg, FALSE, fds, NULL, 0); |
|
3486 |
} |
|
3487 |
else { |
|
3488 |
return rb_fork_internal(status, NULL, NULL, FALSE, fds, NULL, 0); |
|
3489 |
} |
|
3490 | ||
3491 |
} |
|
3492 | ||
3493 | 3358 |
rb_pid_t |
3494 | 3359 |
rb_fork_ruby(int *status) |
3495 | 3360 |
{ |
safe.c (working copy) | ||
---|---|---|
127 | 127 |
} |
128 | 128 | |
129 | 129 |
void |
130 |
rb_check_safe_str(VALUE x) |
|
131 |
{ |
|
132 |
rb_check_safe_obj(x); |
|
133 |
if (!RB_TYPE_P(x, T_STRING)) { |
|
134 |
rb_raise(rb_eTypeError, "wrong argument type %s (expected String)", |
|
135 |
rb_obj_classname(x)); |
|
136 |
} |
|
137 |
} |
|
138 | ||
139 |
void |
|
140 | 130 |
Init_safe(void) |
141 | 131 |
{ |
142 | 132 |
rb_define_virtual_variable("$SAFE", safe_getter, safe_setter); |
struct.c (working copy) | ||
---|---|---|
30 | 30 |
} |
31 | 31 | |
32 | 32 |
VALUE |
33 |
rb_struct_iv_get(VALUE c, const char *name) |
|
34 |
{ |
|
35 |
return struct_ivar_get(c, rb_intern(name)); |
|
36 |
} |
|
37 | ||
38 |
VALUE |
|
39 | 33 |
rb_struct_s_members(VALUE klass) |
40 | 34 |
{ |
41 | 35 |
VALUE members = struct_ivar_get(klass, id_members); |
test/-ext-/old_thread_select/test_old_thread_select.rb (working copy) | ||
---|---|---|
1 |
require 'test/unit' |
|
2 | ||
3 |
class TestOldThreadSelect < Test::Unit::TestCase |
|
4 |
require '-test-/old_thread_select/old_thread_select' |
|
5 | ||
6 |
ANCIENT_LINUX = RUBY_PLATFORM =~ /linux/ && `uname -r`.chomp < '2.6.32' |
|
7 |
DARWIN_10 = RUBY_PLATFORM =~ /darwin10/ |
|
8 |
WINDOWS = RUBY_PLATFORM =~ /mswin|mingw/ |
|
9 | ||
10 |
def with_pipe |
|
11 |
r, w = IO.pipe |
|
12 |
begin |
|
13 |
yield r, w |
|
14 |
ensure |
|
15 |
r.close unless r.closed? |
|
16 |
w.close unless w.closed? |
|
17 |
end |
|
18 |
end |
|
19 | ||
20 |
def test_old_select_read_timeout |
|
21 |
with_pipe do |r, w| |
|
22 |
t0 = Time.now |
|
23 |
rc = IO.old_thread_select([r.fileno], nil, nil, 0.001) |
|
24 |
diff = Time.now - t0 |
|
25 |
assert_equal 0, rc |
|
26 |
assert_operator diff, :>=, 0.001, "returned too early: diff=#{diff}" |
|
27 |
end |
|
28 |
end unless ANCIENT_LINUX |
|
29 | ||
30 |
def test_old_select_error_timeout |
|
31 |
bug5299 = '[ruby-core:39380]' |
|
32 |
with_pipe do |r, w| |
|
33 |
t0 = Time.now |
|
34 |
rc = IO.old_thread_select(nil, nil, [r.fileno], 0.001) |
|
35 |
diff = Time.now - t0 |
|
36 |
assert_equal 0, rc, bug5299 |
|
37 |
assert_operator diff, :>=, 0.001, "returned too early: diff=#{diff}" |
|
38 |
end |
|
39 |
end unless ANCIENT_LINUX |
|
40 | ||
41 |
def test_old_select_false_positive |
|
42 |
bug5306 = '[ruby-core:39435]' |
|
43 |
with_pipe do |r2, w2| |
|
44 |
with_pipe do |r, w| |
|
45 |
t0 = Time.now |
|
46 |
w.syswrite '.' |
|
47 |
rfds = [ r.fileno, r2.fileno ] |
|
48 |
rc = IO.old_thread_select(rfds, nil, nil, nil) |
|
49 |
diff = Time.now - t0 |
|
50 |
assert_equal [ r.fileno ], rfds, bug5306 |
|
51 |
assert_equal 1, rc, bug5306 |
|
52 |
assert_operator diff, :>=, 0, "returned too early: diff=#{diff}" |
|
53 |
end |
|
54 |
end |
|
55 |
end |
|
56 | ||
57 |
def test_old_select_read_write_check |
|
58 |
with_pipe do |r, w| |
|
59 |
w.syswrite('.') |
|
60 |
rc = IO.old_thread_select([r.fileno], nil, nil, nil) |
|
61 |
assert_equal 1, rc |
|
62 | ||
63 |
rc = IO.old_thread_select([r.fileno], [w.fileno], nil, nil) |
|
64 |
assert_equal 2, rc |
|
65 | ||
66 |
assert_equal '.', r.read(1) |
|
67 | ||
68 |
rc = IO.old_thread_select([r.fileno], [w.fileno], nil, nil) |
|
69 |
assert_equal 1, rc |
|
70 |
end |
|
71 |
end |
|
72 | ||
73 |
def test_old_select_signal_safe |
|
74 |
return unless Process.respond_to?(:kill) |
|
75 |
received = false |
|
76 |
trap(:INT) { received = true } |
|
77 |
main = Thread.current |
|
78 |
thr = Thread.new do |
|
79 |
Thread.pass until main.stop? |
|
80 |
Process.kill(:INT, $$) |
|
81 |
true |
|
82 |
end |
|
83 | ||
84 |
rc = nil |
|
85 |
diff = nil |
|
86 |
with_pipe do |r,w| |
|
87 |
assert_nothing_raised do |
|
88 |
t0 = Time.now |
|
89 |
rc = IO.old_thread_select([r.fileno], nil, nil, 1) |
|
90 |
diff = Time.now - t0 |
|
91 |
end |
|
92 |
end |
|
93 | ||
94 |
unless ANCIENT_LINUX || DARWIN_10 || WINDOWS |
|
95 |
assert_operator diff, :>=, 1, "interrupted or short wait: diff=#{diff}" |
|
96 |
end |
|
97 |
assert_equal 0, rc |
|
98 |
assert_equal true, thr.value |
|
99 |
assert_not_equal false, received, "SIGINT not received" |
|
100 |
ensure |
|
101 |
trap(:INT, "DEFAULT") |
|
102 |
end |
|
103 |
end |
thread.c (working copy) | ||
---|---|---|
1099 | 1099 |
sleep_timeval(th, double2timeval(sleepsec), spurious_check); |
1100 | 1100 |
} |
1101 | 1101 | |
1102 |
static void |
|
1103 |
sleep_for_polling(rb_thread_t *th) |
|
1104 |
{ |
|
1105 |
struct timeval time; |
|
1106 |
time.tv_sec = 0; |
|
1107 |
time.tv_usec = 100 * 1000; /* 0.1 sec */ |
|
1108 |
sleep_timeval(th, time, 1); |
|
1109 |
} |
|
1110 | ||
1111 | 1102 |
void |
1112 | 1103 |
rb_thread_wait_for(struct timeval time) |
1113 | 1104 |
{ |
... | ... | |
1115 | 1106 |
sleep_timeval(th, time, 1); |
1116 | 1107 |
} |
1117 | 1108 | |
1118 |
void |
|
1119 |
rb_thread_polling(void) |
|
1120 |
{ |
|
1121 |
if (!rb_thread_alone()) { |
|
1122 |
rb_thread_t *th = GET_THREAD(); |
|
1123 |
RUBY_VM_CHECK_INTS_BLOCKING(th); |
|
1124 |
sleep_for_polling(th); |
|
1125 |
} |
|
1126 |
} |
|
1127 | ||
1128 | 1109 |
/* |
1129 | 1110 |
* CAUTION: This function causes thread switching. |
1130 | 1111 |
* rb_thread_check_ints() check ruby's interrupts. |
... | ... | |
1225 | 1206 |
} |
1226 | 1207 |
} |
1227 | 1208 | |
1228 |
struct rb_blocking_region_buffer * |
|
1229 |
rb_thread_blocking_region_begin(void) |
|
1230 |
{ |
|
1231 |
rb_thread_t *th = GET_THREAD(); |
|
1232 |
struct rb_blocking_region_buffer *region = ALLOC(struct rb_blocking_region_buffer); |
|
1233 |
blocking_region_begin(th, region, ubf_select, th, FALSE); |
|
1234 |
return region; |
|
1235 |
} |
|
1236 | ||
1237 |
void |
|
1238 |
rb_thread_blocking_region_end(struct rb_blocking_region_buffer *region) |
|
1239 |
{ |
|
1240 |
int saved_errno = errno; |
|
1241 |
rb_thread_t *th = ruby_thread_from_native(); |
|
1242 |
blocking_region_end(th, region); |
|
1243 |
xfree(region); |
|
1244 |
RUBY_VM_CHECK_INTS_BLOCKING(th); |
|
1245 |
errno = saved_errno; |
|
1246 |
} |
|
1247 | ||
1248 | 1209 |
static void * |
1249 | 1210 |
call_without_gvl(void *(*func)(void *), void *data1, |
1250 | 1211 |
rb_unblock_function_t *ubf, void *data2, int fail_if_interrupted) |
... | ... | |
1406 | 1367 |
return val; |
1407 | 1368 |
} |
1408 | 1369 | |
1409 |
VALUE |
|
1410 |
rb_thread_blocking_region( |
|
1411 |
rb_blocking_function_t *func, void *data1, |
|
1412 |
rb_unblock_function_t *ubf, void *data2) |
|
1413 |
{ |
|
1414 |
void *(*f)(void*) = (void *(*)(void*))func; |
|
1415 |
return (VALUE)rb_thread_call_without_gvl(f, data1, ubf, data2); |
|
1416 |
} |
|
1417 | ||
1418 | 1370 |
/* |
1419 | 1371 |
* rb_thread_call_with_gvl - re-enter the Ruby world after GVL release. |
1420 | 1372 |
* |
1421 |
* After releasing GVL using rb_thread_blocking_region() or
|
|
1373 |
* After releasing GVL using |
|
1422 | 1374 |
* rb_thread_call_without_gvl() you can not access Ruby values or invoke |
1423 | 1375 |
* methods. If you need to access Ruby you must use this function |
1424 | 1376 |
* rb_thread_call_with_gvl(). |
... | ... | |
3274 | 3226 |
memcpy(dst->fdset, src, size); |
3275 | 3227 |
} |
3276 | 3228 | |
3277 |
static void |
|
3278 |
rb_fd_rcopy(fd_set *dst, rb_fdset_t *src) |
|
3279 |
{ |
|
3280 |
size_t size = howmany(rb_fd_max(src), NFDBITS) * sizeof(fd_mask); |
|
3281 | ||
3282 |
if (size > sizeof(fd_set)) { |
|
3283 |
rb_raise(rb_eArgError, "too large fdsets"); |
|
3284 |
} |
|
3285 |
memcpy(dst, rb_fd_ptr(src), sizeof(fd_set)); |
|
3286 |
} |
|
3287 | ||
3288 | 3229 |
void |
3289 | 3230 |
rb_fd_dup(rb_fdset_t *dst, const rb_fdset_t *src) |
3290 | 3231 |
{ |
... | ... | |
3348 | 3289 |
rb_fd_dup(dst, src); |
3349 | 3290 |
} |
3350 | 3291 | |
3351 |
static void |
|
3352 |
rb_fd_rcopy(fd_set *dst, rb_fdset_t *src) |
|
3353 |
{ |
|
3354 |
int max = rb_fd_max(src); |
|
3355 | ||
3356 |
/* we assume src is the result of select() with dst, so dst should be |
|
3357 |
* larger or equal than src. */ |
|
3358 |
if (max > FD_SETSIZE || (UINT)max > dst->fd_count) { |
|
3359 |
rb_raise(rb_eArgError, "too large fdsets"); |
|
3360 |
} |
|
3361 | ||
3362 |
memcpy(dst->fd_array, src->fdset->fd_array, max); |
|
3363 |
dst->fd_count = max; |
|
3364 |
} |
|
3365 | ||
3366 | 3292 |
void |
3367 | 3293 |
rb_fd_term(rb_fdset_t *set) |
3368 | 3294 |
{ |
... | ... | |
3399 | 3325 |
#define FD_CLR(i, f) rb_fd_clr((i), (f)) |
3400 | 3326 |
#define FD_ISSET(i, f) rb_fd_isset((i), (f)) |
3401 | 3327 | |
3402 |
#else |
|
3403 |
#define rb_fd_rcopy(d, s) (*(d) = *(s)) |
|
3404 | 3328 |
#endif |
3405 | 3329 | |
3406 | 3330 |
static int |
... | ... | |
3514 | 3438 |
} |
3515 | 3439 | |
3516 | 3440 |
int |
3517 |
rb_thread_select(int max, fd_set * read, fd_set * write, fd_set * except, |
|
3518 |
struct timeval *timeout) |
|
3519 |
{ |
|
3520 |
rb_fdset_t fdsets[3]; |
|
3521 |
rb_fdset_t *rfds = NULL; |
|
3522 |
rb_fdset_t *wfds = NULL; |
|
3523 |
rb_fdset_t *efds = NULL; |
|
3524 |
int retval; |
|
3525 | ||
3526 |
if (read) { |
|
3527 |
rfds = &fdsets[0]; |
|
3528 |
rb_fd_init(rfds); |
|
3529 |
rb_fd_copy(rfds, read, max); |
|
3530 |
} |
|
3531 |
if (write) { |
|
3532 |
wfds = &fdsets[1]; |
|
3533 |
rb_fd_init(wfds); |
|
3534 |
rb_fd_copy(wfds, write, max); |
|
3535 |
} |
|
3536 |
if (except) { |
|
3537 |
efds = &fdsets[2]; |
|
3538 |
rb_fd_init(efds); |
|
3539 |
rb_fd_copy(efds, except, max); |
|
3540 |
} |
|
3541 | ||
3542 |
retval = rb_thread_fd_select(max, rfds, wfds, efds, timeout); |
|
3543 | ||
3544 |
if (rfds) { |
|
3545 |
rb_fd_rcopy(read, rfds); |
|
3546 |
rb_fd_term(rfds); |
|
3547 |
} |
|
3548 |
if (wfds) { |
|
3549 |
rb_fd_rcopy(write, wfds); |
|
3550 |
rb_fd_term(wfds); |
|
3551 |
} |
|
3552 |
if (efds) { |
|
3553 |
rb_fd_rcopy(except, efds); |
|
3554 |
rb_fd_term(efds); |
|
3555 |
} |
|
3556 | ||
3557 |
return retval; |
|
3558 |
} |
|
3559 | ||
3560 |
int |
|
3561 | 3441 |
rb_thread_fd_select(int max, rb_fdset_t * read, rb_fdset_t * write, rb_fdset_t * except, |
3562 | 3442 |
struct timeval *timeout) |
3563 | 3443 |
{ |