def setup_handle_sig(subprocess=False):
if os.getpid() != os.getpgrp():
os.setpgrp()
sig_handler = main_handle_sig if not subprocess else sub_handle_sig
for sig in [signal.SIGINT, signal.SIGTERM, signal.SIGHUP]:
signal.signal(sig, sig_handler)
signal.signal(signal.SIGUSR1, handle_sig_usr1)
python类setpgrp()的实例源码
def sigint_ignore():
import os
os.setpgrp()
def fork(self):
pid = os.fork()
if pid:
log.debug('Forked worker PID is %d', pid)
self.stats['forks'] += 1
else:
os.setpgrp()
self.socket.close()
self.socket = None
exit_by_exception()
return pid
def main():
munkicheck = ['/usr/local/munki/managedsoftwareupdate', '--auto']
try:
munki = subprocess.Popen(munkicheck, preexec_fn=os.setpgrp)
except: # noqa
pass
def run_browser(self):
configpath = expanduser("~/.dockerproxy.conf")
logging.debug(configpath)
if os.path.isfile(configpath):
config = SafeConfigParser()
config.read(configpath)
httphandler = config.get('browser','httphandler')
if "chrome" in httphandler:
defaultbrowserpath = self.CHROMEPATH
elif "firefox" in httphandler:
defaultbrowserpath = self.FIREFOXPATH
elif "safari" in httphandler:
defaultbrowserpath = self.SAFARIPATH
else:
# *shrug* you're using something else
defaultbrowserpath = self.SAFARIPATH
#attempt to avoid cmd & arg injection
defaultbrowserpath += " {}"
cmd = shlex.split(defaultbrowserpath.format(pipes.quote(self.url)))
if self.DEBUG:
logging.debug("### Invoking: " + str(cmd))
result = Popen(cmd, shell=False, env=self.ENVIRONMENT, stdin=None, stdout=None, stderr=None, close_fds=True, preexec_fn=os.setpgrp)
# need to give the process a little time to load before exiting :)
time.sleep(2)
sys.exit(0)
else:
tkMessageBox.showinfo("Error", "Config file does not exist")
def run_throwaway(self):
import getpass
username = getpass.getuser()
#attempt to avoid cmd & arg injection
self.DOCKER_THROWAWAYCMDARGS = self.DOCKER_THROWAWAYCMDARGS.format(username, pipes.quote(self.url))
cmd = shlex.split("docker " + self.DOCKER_THROWAWAYCMDARGS)
if self.DEBUG:
logging.debug("### Invoking: " + str(cmd))
result = Popen(cmd, shell=False, env=self.ENVIRONMENT, stdin=None, stdout=None, stderr=None, close_fds=True, preexec_fn=os.setpgrp)
#need to give the process a little time to load before exiting :)
time.sleep(5)
sys.exit(0)
def sh_spawn(*args, **kwargs):
logfile = kwargs.pop('log', None)
mode = kwargs.pop('mode', 'w')
nofail = kwargs.pop('nofail', False)
detach = kwargs.pop('detach', False)
cmd = e(' '.join(args), **get_caller_vars())
if logfile:
sh('mkdir -p', os.path.dirname(logfile))
f = open(logfile, mode)
def preexec():
os.setpgrp()
debug('sh: {0}', cmd)
return subprocess.Popen(cmd, stdout=f if logfile else None, preexec_fn=preexec if detach else None, stderr=subprocess.STDOUT, shell=True)
def start(self, path, game):
info("chat %s: frob start", self._chat_id)
self._process = await asyncio.create_subprocess_shell(
'frob -iplain {}/{}.gam'.format(path, game),
stdin=asyncio.subprocess.PIPE, stdout=asyncio.subprocess.PIPE,
stderr=asyncio.subprocess.STDOUT, preexec_fn=os.setpgrp)
if os.path.exists(path + '/last.sav'):
await self._read_output() # just ignore all previous output
self.restore_game('last')
else:
self._messages_to_skip = 1 # ignore frobTADS intro msg
def get_command_line_args_ext(self, runargs, config, ext_call):
'''
When production of the target algorithm is done from a source other than python,
override this method to return a command call list to execute whatever you need to produce the command line.
Args:
runargs: a map of any non-configuration arguments required for the execution of the solver.
config: a mapping from parameter name (with prefix) to parameter value.
ext_call: string to call external program to get callstring of target algorithm
Returns:
A command call list to execute the command producing a single line of output containing the solver command string
'''
callstring_in = NamedTemporaryFile(suffix=".csv", prefix="callstring", dir=self._tmp_dir, delete=False)
callstring_in.write("%s\n" %(runargs["instance"]))
callstring_in.write("%d\n" %(runargs["seed"]))
for name,value in config.items():
callstring_in.write("%s,%s\n" %(name,value))
callstring_in.flush()
cmd = ext_call.split(" ")
cmd.append(callstring_in.name)
self.print_d(" ".join(cmd))
try:
io = Popen(cmd, shell=False, preexec_fn=os.setpgrp, stdout=PIPE, universal_newlines=True)
self._subprocesses.append(io)
out_, _ = io.communicate()
self._subprocesses.remove(io)
except OSError:
self._ta_misc = "failed to run external program for output parsing : %s" %(" ".join(cmd))
self._ta_runtime = self._cutoff
self._exit_code = 2
sys.exit(2)
if not out_ :
self._ta_misc = "external program for output parsing yielded empty output: %s" %(" ".join(cmd))
self._ta_runtime = self._cutoff
self._exit_code = 2
sys.exit(2)
callstring_in.close()
os.remove(callstring_in.name)
self._instance = runargs["instance"]
return out_.strip('\n\r\b')
def process_results_ext(self, filepointer, out_args, ext_call):
'''
Args:
filepointer: a pointer to the file containing the solver execution standard out.
exit_code : exit code of target algorithm
Returns:
A map containing the standard AClib run results. The current standard result map as of AClib 2.06 is:
{
"status" : <"SAT"/"UNSAT"/"TIMEOUT"/"CRASHED"/"ABORT">,
"quality" : <a domain specific measure of the quality of the solution [optional]>,
"misc" : <a (comma-less) string that will be associated with the run [optional]>
}
'''
cmd = ext_call.split(" ")
cmd.append(filepointer.name)
self.print_d(" ".join(cmd))
try:
io = Popen(cmd, shell=False, preexec_fn=os.setpgrp, stdout=PIPE, universal_newlines=True)
self._subprocesses.append(io)
out_, _ = io.communicate()
self._subprocesses.remove(io)
except OSError:
self._ta_misc = "failed to run external program for output parsing"
self._ta_runtime = self._cutoff
self._exit_code = 2
sys.exit(2)
result_map = {}
for line in out_.split("\n"):
if line.startswith("status:"):
result_map["status"] = line.split(":")[1].strip(" ")
elif line.startswith("quality:"):
result_map["quality"] = line.split(":")[1].strip(" ")
elif line.startswith("misc:"):
result_map["misc"] = line.split(":")[1]
return result_map
def _subproc_pre():
os.setpgrp()
signal.signal(signal.SIGTSTP, lambda n, f: signal.pause())
def start_subproc(self):
close_fds = False if sys.platform == 'win32' else True
if sys.platform == 'win32':
self._pipe = subprocess.Popen(self._subproc_command, shell=False, close_fds=close_fds, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, bufsize=0, startupinfo=self._startupinfo, env=os.environ)
elif sys.platform == 'linux2':
self._pipe = subprocess.Popen(self._subproc_command, shell=False, close_fds=close_fds,
stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
bufsize=0, env=os.environ, preexec_fn=os.setpgrp)
self._birthtime = time.time()
def start_subprocess(self, execution_id: int, command: str, environment: dict, timeout: int) -> None:
"""
Start a subprocess:
- extend the parent process's environment with custom environment variables
- track stdout and stderr file descriptors for later reading
- set process group to facilitate killing any children of the command
:param execution_id: the ID of the Execution instance being run
:param command: a list of arguments, first argument must be an executable
:param environment: environment variables from the WorkflowRun
:param timeout: maximum number of seconds the process should be allowed to run for
"""
process_environment = os.environ.copy()
for key, value in environment.items():
# all variables must be strings, be explicit so it fail in our code
process_environment[key] = str(value)
logger.info('Starting execution #%s', execution_id)
process = subprocess.Popen(command, stdout=subprocess.PIPE, stderr=subprocess.PIPE,
preexec_fn=os.setpgrp, env=process_environment, shell=True)
# store references to the process and file descriptors
# Popen gives us io.BufferedReader; get the raw file handle instead
execution = Execution(process, execution_id, timeout)
self.pipes.update({
process.stdout.raw: execution,
process.stderr.raw: execution
})
self.running[execution_id] = execution
def setup_tunnel(user, odd_host, remote_host, remote_port, tunnel_port):
tunnel_port = get_port(tunnel_port)
if not tunnel_port:
raise ClickException('Could not get a free local port for listening')
ssh_command = ['ssh',
'-oExitOnForwardFailure=yes',
'-oBatchMode=yes',
'-L', '{}:{}:{}'.format(tunnel_port, remote_host, remote_port),
'{}@{}'.format(user, odd_host),
'-N']
process = subprocess.Popen(ssh_command, preexec_fn=os.setpgrp)
logging.debug("Testing if tunnel is listening")
for i in range(10):
try:
time.sleep(0.1)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('localhost', tunnel_port))
s.close()
return tunnel_port, process
except Exception:
pass
finally:
s.close()
logging.warning("Could not connect to port {}, killing ssh process with pid {}".format(tunnel_port, process.pid))
process.kill()
process, tunnel_port = None, None
return tunnel_port, process
def run_bitmessage(self):
if self.bm_active is not True:
try:
if sys.platform.startswith('win'):
self.enable_bm = subprocess.Popen(os.path.join(self.program_dir, 'bitmessagemain.py'),
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
stdin=subprocess.PIPE,
bufsize=0,
cwd=self.program_dir)
else:
self.enable_bm = subprocess.Popen(os.path.join(self.program_dir, 'bitmessagemain.py'),
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
stdin=subprocess.PIPE,
bufsize=0,
cwd=self.program_dir,
preexec_fn=os.setpgrp,
close_fds=True)
self.bm_active = True
except OSError as e:
if 'Permission denied' in e:
print('Got "Permission denied" when trying to access bitmessagemain.py')
print("Please double-check the permissions on the file and ensure it can be ran.")
print("Otherwise, it may be a folder permission issue.")
else:
print('Is the CLI in the same directory as bitmessagemain.py?')
self.kill_program()
for each in self.enable_bm.stdout:
if 'Another instance' in each:
if self.first_run is True:
# print("bitmessagemain.py is already running")
# print("Please close it and re-run the Bitmessage CLI")
# self.kill_program()
pass
break
elif each.startswith('Running as a daemon.'):
self.bm_active = True
break
def run(args, output=sys.stdout, stdin=sys.stdin,
stdin_buffer=sys.stdin.buffer):
"""Observe an Ethernet interface and print ARP bindings."""
# First, become a progress group leader, so that signals can be directed
# to this process and its children; see p.u.twisted.terminateProcess.
os.setpgrp()
network_monitor = None
if args.input_file is None:
if args.interface is None:
raise ActionScriptError("Required argument: interface")
cmd = [get_path("/usr/lib/maas/network-monitor"), args.interface]
cmd = sudo(cmd)
network_monitor = subprocess.Popen(
cmd, stdin=subprocess.DEVNULL, stdout=subprocess.PIPE)
infile = network_monitor.stdout
else:
if args.input_file == '-':
mode = os.fstat(stdin.fileno()).st_mode
if not stat.S_ISFIFO(mode):
raise ActionScriptError("Expected stdin to be a pipe.")
infile = stdin_buffer
else:
infile = open(args.input_file, "rb")
return_code = observe_arp_packets(
bindings=True, verbose=args.verbose, input=infile, output=output)
if return_code is not None:
raise SystemExit(return_code)
if network_monitor is not None:
return_code = network_monitor.poll()
if return_code is not None:
raise SystemExit(return_code)
def run(args, output=sys.stdout, stdin=sys.stdin,
stdin_buffer=sys.stdin.buffer):
"""Observe an Ethernet interface and print beaconing packets."""
# First, become a progress group leader, so that signals can be directed
# to this process and its children; see p.u.twisted.terminateProcess.
os.setpgrp()
network_monitor = None
if args.input_file is None:
if args.interface is None:
raise ActionScriptError("Required argument: interface")
cmd = sudo(
[get_path("/usr/lib/maas/beacon-monitor"), args.interface])
network_monitor = subprocess.Popen(
cmd, stdin=subprocess.DEVNULL, stdout=subprocess.PIPE)
infile = network_monitor.stdout
else:
if args.input_file == '-':
mode = os.fstat(stdin.fileno()).st_mode
if not stat.S_ISFIFO(mode):
raise ActionScriptError("Expected stdin to be a pipe.")
infile = stdin_buffer
else:
infile = open(args.input_file, "rb")
return_code = observe_beaconing_packets(input=infile, out=output)
if return_code is not None:
raise SystemExit(return_code)
if network_monitor is not None:
return_code = network_monitor.poll()
if return_code is not None:
raise SystemExit(return_code)
def fork_task(self, task_info):
self.log_debug("Forking task %s" % self._task_str(task_info))
pid = os.fork()
if pid:
self.log_info("Task forked %s: pid=%s" % (self._task_str(task_info), pid))
return pid
# in no circumstance should we return after the fork
# nor should any exceptions propagate past here
try:
# set process group
os.setpgrp()
# set a do-nothing handler for sigusr2
# do not use signal.signal(signal.SIGUSR2, signal.SIG_IGN) - it completely masks interrups !!!
signal.signal(signal.SIGUSR2, lambda *args: None)
# set a default handler for SIGTERM
signal.signal(signal.SIGTERM, signal.SIG_DFL)
# run the task
self.run_task(task_info)
finally:
# die
os._exit(os.EX_OK)
def _ignoreSignal():
"Detach from process group to ignore all signals"
os.setpgrp()
def _ignoreSignal():
"Detach from process group to ignore all signals"
os.setpgrp()