Project

General

Profile

Actions

Bug #13405

closed

IO#close raises "stream closed"

Added by matthewd (Matthew Draper) over 7 years ago. Updated over 7 years ago.

Status:
Closed
Assignee:
-
Target version:
-
[ruby-core:80583]

Description

IO#close is supposed to ignore an IOError indicating the stream is already closed.

Since #10153, however, it can raise the ruby_error_closed_stream special exception, because that exception's message is "stream closed" instead of "closed stream".

The fix seems easy -- the mismatched string should be updated to use the more common spelling, with something like:

diff --git a/test/lib/test/unit.rb b/test/lib/test/unit.rb
index 6cb22e725a..d1efa5dcfd 100644
--- a/test/lib/test/unit.rb
+++ b/test/lib/test/unit.rb
@@ -228,7 +228,7 @@ def run(task,type)
           rescue Errno::EPIPE
             died
           rescue IOError
-            raise unless ["stream closed","closed stream"].include? $!.message
+            raise unless $!.message == "closed stream"
             died
           end
         end
diff --git a/test/lib/test/unit/parallel.rb b/test/lib/test/unit/parallel.rb
index 50d4427189..09a5530b04 100644
--- a/test/lib/test/unit/parallel.rb
+++ b/test/lib/test/unit/parallel.rb
@@ -61,7 +61,7 @@ def _run_suite(suite, type) # :nodoc:
         begin
           th.join
         rescue IOError
-          raise unless ["stream closed","closed stream"].include? $!.message
+          raise unless $!.message == "closed stream"
         end
         i.close
 
diff --git a/test/ruby/test_io.rb b/test/ruby/test_io.rb
index ca3f1e2d3b..5775e31dde 100644
--- a/test/ruby/test_io.rb
+++ b/test/ruby/test_io.rb
@@ -3411,7 +3411,7 @@ def test_race_closed_stream
       end
       sleep 0.01
       r.close
-      assert_raise_with_message(IOError, /stream closed/) do
+      assert_raise_with_message(IOError, /closed stream/) do
         thread.join
       end
       assert_equal(true, closed, "#{bug13158}: stream should be closed")
diff --git a/thread.c b/thread.c
index 5d27681b40..4e6faf6dc8 100644
--- a/thread.c
+++ b/thread.c
@@ -4883,7 +4883,7 @@ Init_Thread(void)
     rb_define_method(rb_cThread, "name=", rb_thread_setname, 1);
     rb_define_method(rb_cThread, "inspect", rb_thread_inspect, 0);
 
-    rb_vm_register_special_exception(ruby_error_closed_stream, rb_eIOError, "stream closed");
+    rb_vm_register_special_exception(ruby_error_closed_stream, rb_eIOError, "closed stream");
 
     cThGroup = rb_define_class("ThreadGroup", rb_cObject);
     rb_define_alloc_func(cThGroup, thgroup_s_alloc);

I can't work out how to prove this fixes the problem, however. :(

The existing test in test_io.rb shows how to cause the special exception to be raised from gets, but I haven't managed to synthetically force close to raise it.

I know it's possible, though: we're seeing this problem semi-frequently in the Rails test suite (e.g. https://travis-ci.org/rails/rails/jobs/218895049#L499) -- though it's partly hidden by #13239 when it occurs on 2.2 and 2.3.


Related issues 3 (0 open3 closed)

Related to Ruby master - Feature #10718: IO#close should not raise IOError on closed IO objects.ClosedActions
Related to Ruby master - Bug #13158: UNIXServer#closed? returns false after UNIXServer#close calledClosedActions
Related to Ruby master - Bug #10153: File.open block does not throw "No space left on device (Errno::ENOSPC)" if the data fits the buffer of IO.write Closedmatz (Yukihiro Matsumoto)08/19/2014Actions
Actions

Also available in: Atom PDF

Like0
Like0Like0Like0Like0Like0Like0Like0Like0Like0