Ejemplo n.º 1
0
void tidy_and_exit(int sig)
{
  if (Glob->params.debug)
    fprintf(stderr, "test2gate quitting\n");

  PMU_auto_unregister();

  /*
   * exit with code sig
   */

  exit(sig);
}
Ejemplo n.º 2
0
int
main(int argc, char *argv[]) {
    // Let logx get and strip out its arguments
    logx::ParseLogArgs(argc, argv);
    
    // Instantiate our QCoreApplication
    App = new QCoreApplication(argc, argv);

    // XML-RPC server port number
    static const int DEFAULT_XMLRPC_PORT = HCREXECUTIVE_PORT;
    int xmlrpcPortNum;
    
    // procmap instance name
    std::string instanceName;

    // Get HcrExecutive's options
    po::options_description opts("Options");
    opts.add_options()
        ("help,h", "Describe options")
        ("instance,i",
                po::value<std::string>(&instanceName)->default_value("ops"),
                "instance name for procmap connection")
        ("xmlrpcPortNum,x",
                po::value<int>(&xmlrpcPortNum)->default_value(DEFAULT_XMLRPC_PORT),
                "XML-RPC server port number")
        ;
    bool argError = false;
    po::variables_map vm;
    try {
        po::store(po::command_line_parser(argc, argv).options(opts).run(), vm);
        po::notify(vm);
    } catch (...) {
        argError = true;
    }

    // Give usage information and exit if 1) help was requested, or 2) there
    // is an argument error
    if (vm.count("help") || argError) {
        std::cout << "Usage: " << argv[0] <<
                  " [OPTION]..." << std::endl;
        std::cout << opts << std::endl;
        exit(1);
    }
    
    // Initialize registration with procmap if instance is specified
    if (instanceName.size() > 0) {
        PMU_auto_init("HcrExecutive", instanceName.c_str(), PROCMAP_REGISTER_INTERVAL);
        ILOG << "Initializing procmap registration as instance '" << 
                instanceName << "'";
    }

    ILOG << "HcrExecutive (" << getpid() << ") started";

    PMU_auto_register("initializing");

    // Initialize our RPC server
    xmlrpc_c::registry myRegistry;
    myRegistry.addMethod("getStatus", new GetStatusMethod);
    myRegistry.addMethod("setApsValveControl", new SetApsValveControlMethod);
    myRegistry.addMethod("setRequestedHmcMode", new SetRequestedHmcModeMethod);
    myRegistry.addMethod("setHvRequested", new SetHvRequestedMethod);
    QXmlRpcServerAbyss rpcServer(&myRegistry, xmlrpcPortNum);
    
    // Start a thread to get HcrPmc730Daemon status on a regular basis.
    HcrPmc730StatusThread hcrPmc730StatusThread("localhost",
                                                HCRPMC730DAEMON_PORT);
    QObject::connect(App, SIGNAL(aboutToQuit()),
                     &hcrPmc730StatusThread, SLOT(quit()));
    hcrPmc730StatusThread.start();
    
    // Start a thread to get MotionControlDaemon status on a regular basis
    MotionControlStatusThread mcStatusThread("localhost",
                                             MOTIONCONTROLDAEMON_PORT);
    QObject::connect(App, SIGNAL(aboutToQuit()), &mcStatusThread, SLOT(quit()));
    mcStatusThread.start();
    
    // MaxPowerFmqClient instance
    MaxPowerFmqClient maxPowerClient("fmqp://localhost/tmp/fmq/max_power/wband/shmem_15000");
    QObject::connect(App, SIGNAL(aboutToQuit()), &maxPowerClient, SLOT(quit()));
    
    // Instantiate the object which will monitor pressure and control the
    // Active Pressurization System (APS)
    TheApsControl = new ApsControl(hcrPmc730StatusThread);
    
    // Instantiate the object which will implement safety monitoring for the
    // transmitter
    TheTransmitControl = new TransmitControl(hcrPmc730StatusThread, 
                                             mcStatusThread,
                                             maxPowerClient);
    
    // catch a control-C or kill to shut down cleanly
    signal(SIGINT, sigHandler);
    signal(SIGTERM, sigHandler);
 
    // Set up a timer to periodically register with PMU so it knows we're still
    // alive.
    QTimer registrationTimer;
    registrationTimer.setInterval(REGISTRATION_INTERVAL_SECS * 1000);   // interval in ms
    QFunctionWrapper registrationFuncWrapper(updateRegistration);
    QObject::connect(&registrationTimer, SIGNAL(timeout()),
            &registrationFuncWrapper, SLOT(callFunction()));
    registrationTimer.start();

    // Set up a timer to log status information occasionally
    QTimer statusTimer;
    statusTimer.setInterval(LOG_STATUS_INTERVAL_SECS * 1000);
    QFunctionWrapper statusFuncWrapper(logStatus);
    QObject::connect(&statusTimer, SIGNAL(timeout()),
            &statusFuncWrapper, SLOT(callFunction()));
    statusTimer.start();
    
    // Now just run the application until somebody or something interrupts it
    try {
        App->exec();
    } catch (std::exception & e) {
        ELOG << "Application stopped on exception: " << e.what();
    } catch (...) {
        ELOG << "Application stopped on unknown exception";
    }

    // Unregister with procmap
    PMU_auto_unregister();

    // Clean up before exit
    delete(TheTransmitControl);
    delete(TheApsControl);

    // Wait up to 1/2 second (max) for all of our threads to finish
    int maxWaitMsecs = 500;
    QDateTime giveUpTime(QDateTime::currentDateTime().addMSecs(maxWaitMsecs));
    if (! mcStatusThread.wait(QDateTime::currentDateTime().msecsTo(giveUpTime))) {
        WLOG << "mcStatusThread is still running at exit";
    }
    if (! hcrPmc730StatusThread.wait(QDateTime::currentDateTime().msecsTo(giveUpTime))) {
        WLOG << "hcrPmc730StatusThread is still running at exit";
    }

    ILOG << "HcrExecutive (" << getpid() << ") exiting";

    return 0;
}