diff mercurial/utils/procutil.py @ 46175:a04c03b0678e

procutil: assign pseudo file object if sys.stdout/stderr is missing This basically simulates the Python 2 behavior. If libc stdio were used, these file objects would be available and raise EBADF. There is subtle difference between py2 and py3, but I think py3 behavior (i.e. exit 255) is more correct. "if" conditions are adjust so that they look similar to dispatch.initstdio().
author Yuya Nishihara <yuya@tcha.org>
date Fri, 18 Dec 2020 20:09:11 +0900
parents a1601ff3877c
children 128a17d8436f
line wrap: on
line diff
--- a/mercurial/utils/procutil.py	Sat Dec 19 11:10:18 2020 +0900
+++ b/mercurial/utils/procutil.py	Fri Dec 18 20:09:11 2020 +0900
@@ -131,17 +131,25 @@
 
 
 if pycompat.ispy3:
-    # Python 3 implements its own I/O streams.
+    # Python 3 implements its own I/O streams. Unlike stdio of C library,
+    # sys.stdin/stdout/stderr may be None if underlying fd is closed.
+
     # TODO: .buffer might not exist if std streams were replaced; we'll need
     # a silly wrapper to make a bytes stream backed by a unicode one.
 
-    # sys.stdin can be None
-    if sys.stdin:
+    if sys.stdin is None:
+        stdin = BadFile()
+    else:
         stdin = sys.stdin.buffer
+    if sys.stdout is None:
+        stdout = BadFile()
     else:
-        stdin = BadFile()
-    stdout = _make_write_all(sys.stdout.buffer)
-    stderr = _make_write_all(sys.stderr.buffer)
+        stdout = _make_write_all(sys.stdout.buffer)
+    if sys.stderr is None:
+        stderr = BadFile()
+    else:
+        stderr = _make_write_all(sys.stderr.buffer)
+
     if pycompat.iswindows:
         # Work around Windows bugs.
         stdout = platform.winstdout(stdout)