重定向分叉蟒蛇过程的输出管道
问题描述:
我想从一个分叉Python进程的父写一些记录的过程,所以我用一管为:重定向分叉蟒蛇过程的输出管道
rpipe, wpipe = os.pipe()
pid = os.fork()
if pid == -1:
raise TestError("Failed to fork() in prepare_test_dir")
if pid == 0:
# Child -- do the copy, print log to pipe and exit
try:
os.close(rpipe)
os.dup2(wpipe, sys.stdout.fileno())
os.dup2(wpipe, sys.stderr.fileno())
os.close(wpipe)
self._prepare_test_dir(test)
sys.stdout.write(self.copy_log)
finally:
os._exit(1)
os.close(wpipe)
_, status = os.waitpid(pid, 0)
# XXX: if copy_log is larger than PIPE_BUF (4-8k), everything
# then is going badly
outf = os.fdopen(rpipe)
self.copy_log = outf.read()
return os.WEXITSTATUS(status)
它不工作,没有什么出现在self.copy_log
。我也试图明确建设标准输出对象与fdopen
:
sys.stdout = os.fdopen(wpipe, 'w')
不是工作压力太大。但是,如果我把print
dup2
前:
if pid == 0:
try:
print 'HELLO'
os.close(rpipe)
os.dup2(wpipe, sys.stdout.fileno())
os.dup2(wpipe, sys.stderr.fileno())
...
复制日志被成功传递到家长和“HELLO”打印到控制终端。我假设print
以某种方式影响sys.stdout
(与懒惰初始化或其他)。有任何想法吗?
我在各种Linux平台上使用Python 2.6和2.7。
答
该问题似乎不在pipe/dup2相关代码中,而是os._exit
。这是杀死python解释器的残酷方法(但对于分叉进程可以,因此它不会触及“共享”对象),但会导致stdout
和stderr
不会被刷新,并且数据会丢失。
我的孩子来到了下面的代码:
try:
os.close(rpipe)
os.dup2(wpipe, sys.stdout.fileno())
os.dup2(wpipe, sys.stderr.fileno())
os.close(wpipe)
print 'aaaaaaaaa'
except:
traceback.print_exc(20, sys.stderr)
finally:
sys.stdout.flush()
sys.stderr.flush()
os._exit(1)
你正在做硬盘的方式,使用[模块子(https://docs.python.org/2/library/subprocess.html )。 – msw
我知道'subprocess',但我必须使用fork。不幸的是,只能保证fds是关闭的。此外,'fork()'不共享任何内容,它执行所有可写段上的写时复制。 – myaut