From: Jos Backus Date: 2002-11-07T04:35:06+09:00 Subject: Re: io_write()/fwrite() and EINTR on Solaris My apologies for sending a bad patch. This is the correct one. Comments appreciated. I'll report back if I hear anything from Sun on this issue. Index: io.c =================================================================== RCS file: /src/ruby/io.c,v retrieving revision 1.167 diff -u -r1.167 io.c --- io.c 29 Oct 2002 21:35:28 -0000 1.167 +++ io.c 6 Nov 2002 19:32:24 -0000 @@ -24,6 +24,11 @@ #include #include +#if defined(sun) +# define BROKEN_FWRITE +# include +#endif + #if defined(MSDOS) || defined(__BOW__) || defined(__CYGWIN__) || defined(NT) || defined(__human68k__) || defined(__EMX__) || defined(__BEOS__) # define NO_SAFE_RENAME #endif @@ -359,6 +364,9 @@ FILE *f; long n, r; register char *ptr; +#ifdef BROKEN_FWRITE + sigset_t set; +#endif rb_secure(4); if (TYPE(str) != T_STRING) @@ -384,7 +392,20 @@ } } while (--n > 0); #else - while (ptr += (r = fwrite(ptr, 1, n, f)), (n -= r) > 0) { +#ifdef BROKEN_FWRITE + /* Prevent the fwrite() from being interrupted by a VTALRM signal */ + sigemptyset(&set); + sigaddset(&set, SIGVTALRM); +#endif + for (;;) { +#ifdef BROKEN_FWRITE + sigprocmask(SIG_BLOCK, &set, 0); +#endif + ptr += (r = fwrite(ptr, 1, n, f)); +#ifdef BROKEN_FWRITE + sigprocmask(SIG_UNBLOCK, &set, 0); +#endif + if ((n -= r) <= 0) break; if (ferror(f)) { if (rb_io_wait_writable(fileno(f))) { clearerr(f); -- Jos Backus _/ _/_/_/ Sunnyvale, CA _/ _/ _/ _/ _/_/_/ _/ _/ _/ _/ jos at catnook.com _/_/ _/_/_/ require 'std/disclaimer'