예제 #1
0
def __start_neubot_agent():
    ''' Fork a new process and run neubot agent '''

    # Fork a new process
    pid = os.fork()
    if pid > 0:
        syslog.syslog(syslog.LOG_INFO, 'Neubot agent PID: %d' % pid)
        return pid

    #
    # The child code is surrounded by this giant try..except
    # because we don't want the child process to eventually
    # return to the caller.
    #
    try:
        syslog.openlog('neubot', syslog.LOG_PID, syslog.LOG_DAEMON)

        # Add neubot directory to python search path
        if not os.access(VERSIONDIR, os.R_OK|os.X_OK):
            raise RuntimeError('Cannot access: %s' % VERSIONDIR)

        if not VERSIONDIR in sys.path:
            syslog.syslog(syslog.LOG_ERR,
                          'Prepending "%s" to Python search path' %
                          VERSIONDIR)
            sys.path.insert(0, VERSIONDIR)

        # Import the required modules
        from neubot.log import LOG
        from neubot.net.poller import POLLER
        from neubot import agent

        #
        # Redirect logger to syslog now, so early errors in
        # agent.py:main() are logged.
        #
        LOG.redirect()

        #
        # Close all unneeded file descriptors, but save stdio,
        # which has just been redirected.
        #
        for tmpdesc in range(3, 64):
            try:
                os.close(tmpdesc)
            except OSError:
                pass
            except:
                pass

        # Handle SIGTERM gracefully
        sigterm_handler = lambda signo, frame: POLLER.break_loop()
        signal.signal(signal.SIGTERM, sigterm_handler)

        #
        # Here we're running as root but this is OK because
        # neubot/agent.py is going to drop the privileges to
        # the unprivileged user `_neubot`.
        #
        agent.main(['neubot/agent.py',
                    '-D agent.daemonize=OFF',
                    '-D agent.use_syslog=ON'])

    #
    # We must employ __exit() instead of sys.exit() because
    # the latter is catched below by our catch-all clauses and
    # the child process will start running the parent code.
    # OTOH __exit() exits immediately.
    #
    except:
        try:
            why = asyncore.compact_traceback()
            syslog.syslog(syslog.LOG_ERR,
                          'Unhandled exception in the Neubot agent: %s' %
                          str(why))
        except:
            pass
        __exit(1)
    else:
        __exit(0)
예제 #2
0
def main(argv):

    slowpath = False
    webgui = False
    start = False
    status = False
    stop = False

    if sys.version_info[0] > 2 or sys.version_info[1] < 5:
        sys.stderr.write("fatal: wrong Python version\n")
        sys.stderr.write("please run neubot using Python >= 2.5 and < 3.0\n")
        sys.exit(1)

    if os.environ.get("NEUBOT_DEBUG", ""):
        from neubot import utils
        if utils.intify(os.environ["NEUBOT_DEBUG"]):
            sys.stderr.write("Running in debug mode\n")
            from neubot.debug import PROFILER
            sys.setprofile(PROFILER.notify_event)

    if os.environ.get("NEUBOT_MEMLEAK", ""):
        from neubot import utils
        if utils.intify(os.environ["NEUBOT_MEMLEAK"]):
            sys.stderr.write("Running in leak-detection mode\n")
            import gc
            gc.set_debug(gc.DEBUG_LEAK)

    # Hook for Neubot for MacOSX
    if os.name == 'posix' and sys.platform == 'darwin':
        from neubot import main_macos
        main_macos.main(argv)
        return

    # Quick argv classification

    if len(argv) == 1:
        start = True
        webgui = True

    elif len(argv) == 2:
        command = argv[1]
        if command == "--help":
            sys.stdout.write(USAGE)
            sys.exit(0)
        elif command == "-V":
            sys.stdout.write(VERSION + "\n")
            sys.exit(0)
        elif command == "start":
            start = True
        elif command == "status":
            status = True
        elif command == "stop":
            stop = True
        else:
            slowpath = True

    else:
        slowpath = True

    # Slow / quick startup

    if slowpath:
        from neubot.main import module
        module.run(argv)

    else:
        running = False

        # Running?
        if start or status or stop:
            try:
                import httplib

                connection = httplib.HTTPConnection("127.0.0.1", "9774")
                connection.request("GET", "/api/version")
                response = connection.getresponse()
                if response.status == 200:
                    running = True
                response.read()
                connection.close()

            except (SystemExit, KeyboardInterrupt):
                raise
            except:
                pass

        if status:
            if not running:
                sys.stdout.write("Not running\n")
            else:
                sys.stdout.write("Running\n")
            sys.exit(0)

        if running and start:
            sys.stdout.write("Already running\n")
        if not running and stop:
            sys.stdout.write("Not running\n")

        # Stop
        if running and stop:
            try:

                connection = httplib.HTTPConnection("127.0.0.1", "9774")
                connection.request("POST", "/api/exit")

                # New /api/exit does not send any response
                #response = connection.getresponse()

                connection.close()

            except (SystemExit, KeyboardInterrupt):
                raise
            except:
                logging.error('Exception', exc_info=1)
                sys.exit(1)

        # start / webbrowser

        if os.name == "posix":

            #
            # Fork off a child and use it to start the
            # Neubot agent.  The parent process will
            # open the browser, if needed.  Otherwise
            # it will exit.
            #
            if not running and start:
                if os.fork() == 0:
                    from neubot import agent
                    arguments = [ argv[0] ]
                    agent.main(arguments)
                    sys.exit(0)

            #
            # It's not wise at all to open the browser when
            # we are running as root.  Assume that when we
            # are root the user wants just to start the agent.
            #
            if webgui and "DISPLAY" in os.environ:
                if os.getuid() != 0:
                    from neubot.main import browser
                    browser.open_patient("127.0.0.1", "9774")

        elif os.name == "nt":

            if webgui:
                from neubot.main import browser

                if not running and start:
                    browser.open_patient("127.0.0.1", "9774", True)
                else:
                    browser.open_patient("127.0.0.1", "9774")

            if not running and start:
                from neubot import agent
                agent.main([argv[0]])

        else:
            sys.stderr.write("Your operating system is not supported\n")
            sys.exit(1)