From: Tanaka Akira Date: 2005-07-23T00:55:09+09:00 Subject: Re: [BUG] Segmentation fault with a threads/forks script In article , nobuyoshi nakada writes: > It seems to have new related bug(s), I'll investigate it more. The all three fd_sets must be long enough for select. Index: eval.c =================================================================== RCS file: /src/ruby/eval.c,v retrieving revision 1.803 diff -u -r1.803 eval.c --- eval.c 19 Jul 2005 14:57:47 -0000 1.803 +++ eval.c 22 Jul 2005 15:49:31 -0000 @@ -9880,10 +9880,8 @@ } } -void -rb_fd_set(n, fds) - int n; - rb_fdset_t *fds; +static void +rb_fd_resize(int n, rb_fdset_t *fds) { int m = howmany(n + 1, NFDBITS) * sizeof(fd_mask); int o = howmany(fds->maxfd, NFDBITS) * sizeof(fd_mask); @@ -9896,6 +9894,14 @@ memset((char *)fds->fdset + o, 0, m - o); } if (n >= fds->maxfd) fds->maxfd = n + 1; +} + +void +rb_fd_set(n, fds) + int n; + rb_fdset_t *fds; +{ + rb_fd_resize(n, fds); FD_SET(n, fds->fdset); } @@ -9931,6 +9937,15 @@ memcpy(dst->fdset, src, size); } +int +rb_fd_select(int n, rb_fdset_t *readfds, rb_fdset_t *writefds, rb_fdset_t *exceptfds, struct timeval *timeout) +{ + rb_fd_resize(n-1, readfds); + rb_fd_resize(n-1, writefds); + rb_fd_resize(n-1, exceptfds); + return select(n, rb_fd_ptr(readfds), rb_fd_ptr(writefds), rb_fd_ptr(exceptfds), timeout); +} + #undef FD_ZERO #undef FD_SET #undef FD_CLR @@ -10795,7 +10810,7 @@ delay_ptr = &delay_tv; } - n = select(max+1, rb_fd_ptr(&readfds), rb_fd_ptr(&writefds), rb_fd_ptr(&exceptfds), delay_ptr); + n = rb_fd_select(max+1, &readfds, &writefds, &exceptfds, delay_ptr); if (n < 0) { int e = errno; Index: intern.h =================================================================== RCS file: /src/ruby/intern.h,v retrieving revision 1.172 diff -u -r1.172 intern.h --- intern.h 14 Jul 2005 15:11:52 -0000 1.172 +++ intern.h 22 Jul 2005 15:49:32 -0000 @@ -162,6 +162,7 @@ void rb_fd_clr _((int, rb_fdset_t *)); int rb_fd_isset _((int, const rb_fdset_t *)); void rb_fd_copy _((rb_fdset_t *, const fd_set *, int)); +int rb_fd_select(int, rb_fdset_t *, rb_fdset_t *, rb_fdset_t *, struct timeval *); #define rb_fd_ptr(f) ((f)->fdset) #define rb_fd_max(f) ((f)->maxfd) @@ -178,6 +179,7 @@ #define rb_fd_init(f) FD_ZERO(f) #define rb_fd_term(f) (f) #define rb_fd_max(f) FD_SETSIZE +#define rb_fd_select(n, rfds, wfds, efds, timeout) select(n, rfds, wfds, efds, timeout) #endif -- Tanaka Akira