Exemple #1
0
/*
    Schedule events.
    This routine will service events until the timeout expires or if MPR_SERVICE_NO_BLOCK is specified in flags,
    until there are no more events to service. This routine will also return when the MPR is stopping. This will
    service all enabled non-running dispatcher queues and pending I/O events.
    An app should dedicate only one thread to be an event service thread.
    @param timeout Time in milliseconds to wait. Set to zero for no wait. Set to -1 to wait forever.
    @param flags Set to MPR_SERVICE_NO_BLOCK for non-blocking.
    @returns Number of events serviced.
 */
PUBLIC int mprServiceEvents(MprTicks timeout, int flags)
{
    MprEventService     *es;
    MprDispatcher       *dp;
    MprTicks            expires, delay;
    int                 beginEventCount, eventCount;

    if (MPR->eventing) {
        mprLog("warn mpr event", 0, "mprServiceEvents called reentrantly");
        return 0;
    }
    mprAtomicBarrier();
    if (mprIsDestroying()) {
        return 0;
    }
    MPR->eventing = 1;
    es = MPR->eventService;
    beginEventCount = eventCount = es->eventCount;
    es->now = mprGetTicks();
    expires = timeout < 0 ? MPR_MAX_TIMEOUT : (es->now + timeout);
    if (expires < 0) {
        expires = MPR_MAX_TIMEOUT;
    }
    mprSetWindowsThread(0);

    while (es->now <= expires) {
        eventCount = es->eventCount;
        mprServiceSignals();

        while ((dp = getNextReadyDispatcher(es)) != NULL) {
            assert(!isRunning(dp));
            queueDispatcher(es->runQ, dp);
            if (dp->flags & MPR_DISPATCHER_IMMEDIATE) {
                dispatchEventsWorker(dp);
            } else {
                if (mprStartWorker((MprWorkerProc) dispatchEventsWorker, dp) < 0) {
                    /* Should not get here */
                    queueDispatcher(es->pendingQ, dp);
                    break;
                }
            }
        }
        if (flags & MPR_SERVICE_NO_BLOCK) {
            expires = 0;
            /* But still service I/O events below */
        }
        if (es->eventCount == eventCount) {
            lock(es);
            delay = getIdleTicks(es, expires - es->now);
            es->willAwake = es->now + delay;
            es->waiting = 1;
            unlock(es);
            /*
                Service IO events
             */
            mprWaitForIO(MPR->waitService, delay);
        }
        es->now = mprGetTicks();
        if (flags & MPR_SERVICE_NO_BLOCK) {
            break;
        }
        if (mprIsStopping()) {
            break;
        }
    }
    MPR->eventing = 0;
    mprSignalCond(MPR->cond);
    return abs(es->eventCount - beginEventCount);
}
APIENTRY WinMain(HINSTANCE inst, HINSTANCE junk, char *command, int junk2)
{
    char    *argv[ME_MAX_ARGC], *argp;
    int     argc, err, nextArg, manage, stop;

	argv[0] = ME_NAME "Monitor";
    argc = mprParseArgs(command, &argv[1], ME_MAX_ARGC - 1) + 1;

    if (mprCreate(argc, argv, MPR_USER_EVENTS_THREAD | MPR_NO_WINDOW) == NULL) {
        exit(1);
    }
    if ((app = mprAllocObj(App, manageApp)) == NULL) {
        exit(2);
    }
    mprAddRoot(app);

    err = 0;
    stop = 0;
    manage = 0;
    app->appInst = inst;
    app->company = sclone(ME_COMPANY);
    app->serviceName = sclone(ME_NAME);
    mprSetLogHandler(logHandler);

    chdir(mprGetAppDir());

    /*
        Parse command line arguments
     */
    for (nextArg = 1; nextArg < argc; nextArg++) {
        argp = argv[nextArg];
        if (*argp != '-') {
            break;
        }
        if (strcmp(argp, "--manage") == 0) {
            manage++;
        } else if (strcmp(argp, "--stop") == 0) {
            stop++;
        } else {
            err++;
        }
        if (err) {
            mprError("appweb monitor", "Bad command line: %s\n"
                "  Usage: %s [options]\n"
                "  Switches:\n"
                "    --manage             # Launch browser to manage",
                "    --stop               # Stop a running monitor",
                command, mprGetAppName());
            return -1;
        }
    }
    if (stop) {
        stopMonitor();
        return 0;
    }
    if (findInstance()) {
        mprError("appweb monitor", "Application %s is already active.", mprGetAppTitle());
        return MPR_ERR_BUSY;
    }
    app->hwnd = mprSetWindowsThread(0);
    mprSetWinMsgCallback(msgProc);

    if (app->taskBarIcon > 0) {
        ShowWindow(app->hwnd, SW_MINIMIZE);
        UpdateWindow(app->hwnd);
    }
    if (manage) {
        /*
            Launch the browser 
         */
        runBrowser("/index.html");

    } else {
        if (openMonitorIcon() < 0) {
            mprError("appweb monitor", "Cannot open %s tray", mprGetAppName());
        } else {
            mprServiceEvents(-1, 0);
            closeMonitorIcon();
        }
    }
    mprDestroy();
    return 0;
}