def _VerifyDaemonUser(daemon_name):
"""Verifies the process uid matches the configured uid.
- This method verifies that a daemon is started as the user it is intended to be
- run
+ This method verifies that a daemon is started as the user it is
+ intended to be run
@param daemon_name: The name of daemon to be started
@return: A tuple with the first item indicating success or not,
daemon_uids[daemon_name])
+def _BeautifyError(err):
+ """Try to format an error better.
+
+ Since we're dealing with daemon startup errors, in many cases this
+ will be due to socket error and such, so we try to format these cases better.
+
+ @param err: an exception object
+ @rtype: string
+ @return: the formatted error description
+
+ """
+ try:
+ if isinstance(err, socket.error):
+ return "Socket-related error: %s (errno=%s)" % (err.args[1], err.args[0])
+ elif isinstance(err, EnvironmentError):
+ if err.filename is None:
+ return "%s (errno=%s)" % (err.strerror, err.errno)
+ else:
+ return "%s (file %s) (errno=%s)" % (err.strerror, err.filename,
+ err.errno)
+ else:
+ return str(err)
+ except Exception: # pylint: disable-msg=W0703
+ logging.exception("Error while handling existing error %s", err)
+ return "%s" % str(err)
+
+
def GenericMain(daemon_name, optionparser,
check_fn, prepare_fn, exec_fn,
multithreaded=False, console_logging=False,
if options.fork:
utils.CloseFDs()
- utils.Daemonize(logfile=constants.DAEMONS_LOGFILES[daemon_name])
+ wpipe = utils.Daemonize(logfile=constants.DAEMONS_LOGFILES[daemon_name])
+ else:
+ wpipe = None
utils.WritePidFile(utils.DaemonPidFileName(daemon_name))
try:
- utils.SetupLogging(logfile=constants.DAEMONS_LOGFILES[daemon_name],
- debug=options.debug,
- stderr_logging=not options.fork,
- multithreaded=multithreaded,
- program=daemon_name,
- syslog=options.syslog,
- console_logging=console_logging)
- logging.info("%s daemon startup", daemon_name)
- if callable(prepare_fn):
- prep_results = prepare_fn(options, args)
- else:
- prep_results = None
+ try:
+ utils.SetupLogging(logfile=constants.DAEMONS_LOGFILES[daemon_name],
+ debug=options.debug,
+ stderr_logging=not options.fork,
+ multithreaded=multithreaded,
+ program=daemon_name,
+ syslog=options.syslog,
+ console_logging=console_logging)
+ if callable(prepare_fn):
+ prep_results = prepare_fn(options, args)
+ else:
+ prep_results = None
+ logging.info("%s daemon startup", daemon_name)
+ except Exception, err:
+ utils.WriteErrorToFD(wpipe, _BeautifyError(err))
+ raise
+
+ if wpipe is not None:
+ # we're done with the preparation phase, we close the pipe to
+ # let the parent know it's safe to exit
+ os.close(wpipe)
exec_fn(options, args, prep_results)
finally: