From: Charlie Savage Date: 2009-02-15T06:27:35+09:00 Subject: [ruby-core:22116] [Bug #1162] Build Assertion Failure with VC+++ - Incorrect flushing of stdout/stderr Bug #1162: Build Assertion Failure with VC+++ - Incorrect flushing of stdout/stderr http://redmine.ruby-lang.org/issues/show/1162 Author: Charlie Savage Status: Open, Priority: Normal Category: core ruby -v: ruby 1.9.1p0 (2009-01-30 revision 21907) [i386-mswin32_90] Build ruby 1.9.1 with VC 2008 using the following flags: RUNTIMEFLAG = -MDd OPTFLAGS = -Od -RTC1 LDFLAGS = -link -INCREMENTAL:NO -DEBUG -OPT:REF -OPT:ICF Failure occurs when running miniruby.exe for the first time: File: f:\dd\vctools\crt_bld\self_x86\src\commit.c, line 69. Expression: ("Invalid file descriptor. File possibly closed by a different thread", 0) The call sequence: rb_io_flush -> fsync -> _commit -> FlushFileBuffers The stream is stdout or stderr. From Microsoft's documentation of FlushFileBuffers (http://msdn.microsoft.com/en-us/library/aa364439(VS.85).aspx): The function fails if hFile is a handle to the console output. That is because the console output is not buffered. The function returns FALSE, and GetLastError returns ERROR_INVALID_HANDLE. Thus calling _commit on STDOUT or STDERR is invalid. This patch fixes the problem: --- io.old.c 2009-02-14 14:27:15 -0700 +++ io.c 2009-02-14 14:27:20 -0700 @@ -1002,7 +1002,8 @@ if (io_fflush(fptr) < 0) rb_sys_fail(0); #ifdef _WIN32 - fsync(fptr->fd); + if (io != rb_stdout && io != rb_stderr) + fsync(fptr->fd); #endif } if (fptr->mode & FMODE_READABLE) { ---------------------------------------- http://redmine.ruby-lang.org