Restore SIGPIPE default action for subprocesses

Python ignores SIGPIPE on startup, because it prefers to check every
write and raise an IOError exception rather than taking the signal. Most
Unix subprocesses don't expect to work this way. This patch (adapted
from Colin Watson's post at http://tinyurl.com/2a7mzh5) sets SIGPIPE
back to the default action for nova.utils.execute and nova-rootwrap
created subprocesses.

Fixes bug 1053364

Change-Id: I17e1629bb4ef4268515c6734ddb6e12746739c52
This commit is contained in:
Thierry Carrez 2012-09-20 14:11:38 +02:00
parent 59ad151a29
commit a694b9e5ad
2 changed files with 17 additions and 0 deletions

View File

@ -34,6 +34,7 @@
import ConfigParser
import os
import signal
import subprocess
import sys
@ -42,6 +43,13 @@ RC_UNAUTHORIZED = 99
RC_NOCOMMAND = 98
RC_BADCONFIG = 97
def _subprocess_setup():
# Python installs a SIGPIPE handler by default. This is usually not what
# non-Python subprocesses expect.
signal.signal(signal.SIGPIPE, signal.SIG_DFL)
if __name__ == '__main__':
# Split arguments, require at least a command
execname = sys.argv.pop(0)
@ -77,6 +85,7 @@ if __name__ == '__main__':
stdin=sys.stdin,
stdout=sys.stdout,
stderr=sys.stderr,
preexec_fn=_subprocess_setup,
env=filtermatch.get_environment(userargs))
obj.wait()
sys.exit(obj.returncode)

View File

@ -31,6 +31,7 @@ import random
import re
import shlex
import shutil
import signal
import socket
import struct
import sys
@ -112,6 +113,12 @@ def vpn_ping(address, port, timeout=0.05, session_id=None):
return server_sess
def _subprocess_setup():
# Python installs a SIGPIPE handler by default. This is usually not what
# non-Python subprocesses expect.
signal.signal(signal.SIGPIPE, signal.SIG_DFL)
def execute(*cmd, **kwargs):
"""Helper method to execute command with optional retry.
@ -180,6 +187,7 @@ def execute(*cmd, **kwargs):
stdout=_PIPE,
stderr=_PIPE,
close_fds=True,
preexec_fn=_subprocess_setup,
shell=shell)
result = None
if process_input is not None: