Example #1
0
/*
 * Crank up the heap worker thread.
 *
 * Does not return until the thread is ready for business.
 */
bool dvmHeapWorkerStartup(void)
{
    assert(!gDvm.haltHeapWorker);
    assert(!gDvm.heapWorkerReady);
    assert(gDvm.heapWorkerHandle == 0);
    assert(gDvm.heapWorkerInitialized);

    /* use heapWorkerLock/heapWorkerCond to communicate readiness */
    dvmLockMutex(&gDvm.heapWorkerLock);

//BUG: If a GC happens in here or in the new thread while we hold the lock,
//     the GC will deadlock when trying to acquire heapWorkerLock.
    if (!dvmCreateInternalThread(&gDvm.heapWorkerHandle,
                "HeapWorker", heapWorkerThreadStart, NULL))
    {
        dvmUnlockMutex(&gDvm.heapWorkerLock);
        return false;
    }

    /*
     * Wait for the heap worker to come up.  We know the thread was created,
     * so this should not get stuck.
     */
    while (!gDvm.heapWorkerReady) {
        dvmWaitCond(&gDvm.heapWorkerCond, &gDvm.heapWorkerLock);
    }

    dvmUnlockMutex(&gDvm.heapWorkerLock);
    return true;
}
Example #2
0
/**
 * Jit编译器入口点函数
 * @retval 0 表示失败
 * @retval 1 表示成功 
 */
bool dvmCompilerStartup(void)
{
	/* 初始化一些线程同步方面的变量 */
    dvmInitMutex(&gDvmJit.compilerLock);
    dvmInitMutex(&gDvmJit.compilerICPatchLock);
    dvmInitMutex(&gDvmJit.codeCacheProtectionLock);
    dvmLockMutex(&gDvmJit.compilerLock);
    pthread_cond_init(&gDvmJit.compilerQueueActivity, NULL);
    pthread_cond_init(&gDvmJit.compilerQueueEmpty, NULL);

    /* Reset the work queue */
	/* 设置工作队列 */
    gDvmJit.compilerWorkEnqueueIndex = gDvmJit.compilerWorkDequeueIndex = 0;
    gDvmJit.compilerQueueLength = 0;
    dvmUnlockMutex(&gDvmJit.compilerLock);

    /*
     * Defer rest of initialization until we're sure JIT'ng makes sense. Launch
     * the compiler thread, which will do the real initialization if and
     * when it is signalled to do so.
     */
	/*
	 * 以下这个函数创建compilerThreadStart编译线程,当这条线程会执行真正的初始化工作
	 */
    return dvmCreateInternalThread(&gDvmJit.compilerHandle, "Compiler",
                                   compilerThreadStart, NULL);
}
static bool gcDaemonStartup()
{
    dvmInitMutex(&gHs->gcThreadMutex);
    pthread_cond_init(&gHs->gcThreadCond, NULL);
    gHs->gcThreadShutdown = false;
    gHs->hasGcThread = dvmCreateInternalThread(&gHs->gcThread, "GC",
                       gcDaemonThread, NULL);
    return gHs->hasGcThread;
}
Example #4
0
bool dvmSystemCoreValuesStartup(){

	if(coreValuesflag == false)
		if (!dvmCreateInternalThread(&coreValuesHandle,
                "CAreDroid Core Values Update", coreValuesCatcherThreadStart, NULL))
			return false;

	coreValuesflag = true;
    return true;
}
/*
 * Crank up the signal catcher thread.
 *
 * Returns immediately.
 */
bool dvmSignalCatcherStartup(void)
{
    gDvm.haltSignalCatcher = false;

    if (!dvmCreateInternalThread(&gDvm.signalCatcherHandle,
                "Signal Catcher", signalCatcherThreadStart, NULL))
        return false;

    return true;
}
Example #6
0
/*
 * Crank up the stdout/stderr converter thread.
 *
 * Returns immediately.
 */
bool dvmStdioConverterStartup()
{
    gDvm.haltStdioConverter = false;

    dvmInitMutex(&gDvm.stdioConverterLock);
    pthread_cond_init(&gDvm.stdioConverterCond, NULL);

    if (pipe(gDvm.stdoutPipe) != 0) {
        ALOGW("pipe failed: %s", strerror(errno));
        return false;
    }
    if (pipe(gDvm.stderrPipe) != 0) {
        ALOGW("pipe failed: %s", strerror(errno));
        return false;
    }

    if (dup2(gDvm.stdoutPipe[1], kFilenoStdout) != kFilenoStdout) {
        ALOGW("dup2(1) failed: %s", strerror(errno));
        return false;
    }
    close(gDvm.stdoutPipe[1]);
    gDvm.stdoutPipe[1] = -1;
#ifdef HAVE_ANDROID_OS
    /* don't redirect stderr on sim -- logs get written there! */
    /* (don't need this on the sim anyway) */
    if (dup2(gDvm.stderrPipe[1], kFilenoStderr) != kFilenoStderr) {
        ALOGW("dup2(2) failed: %d %s", errno, strerror(errno));
        return false;
    }
    close(gDvm.stderrPipe[1]);
    gDvm.stderrPipe[1] = -1;
#endif


    /*
     * Create the thread.
     */
    dvmLockMutex(&gDvm.stdioConverterLock);

    if (!dvmCreateInternalThread(&gDvm.stdioConverterHandle,
                                 "Stdio Converter",
                                 stdioConverterThreadStart,
                                 NULL)) {
        return false;
    }

    while (!gDvm.stdioConverterReady) {
        dvmWaitCond(&gDvm.stdioConverterCond, &gDvm.stdioConverterLock);
    }
    dvmUnlockMutex(&gDvm.stdioConverterLock);

    return true;
}
Example #7
0
static bool gcDaemonStartup()
{
    dvmInitMutex(&gHs->gcThreadMutex);
#if defined(__APPLE__)
    pthread_cond_init(&gHs->gcThreadCond, NULL);
#else
    pthread_condattr_t condAttr;
    pthread_condattr_init(&condAttr);
    pthread_condattr_setclock(&condAttr, CLOCK_MONOTONIC);
    pthread_cond_init(&gHs->gcThreadCond, &condAttr);
#endif  // defined(__APPLE__)
    gHs->gcThreadShutdown = false;
    gHs->hasGcThread = dvmCreateInternalThread(&gHs->gcThread, "GC",
                       gcDaemonThread, NULL);
    return gHs->hasGcThread;
}
Example #8
0
bool dvmCompilerStartup(void)
{

    dvmInitMutex(&gDvmJit.compilerLock);
    dvmInitMutex(&gDvmJit.compilerICPatchLock);
    dvmInitMutex(&gDvmJit.codeCacheProtectionLock);
    dvmLockMutex(&gDvmJit.compilerLock);
    dvmInitCondForTimedWait(&gDvmJit.compilerQueueActivity);
    dvmInitCondForTimedWait(&gDvmJit.compilerQueueEmpty);

    /* Reset the work queue */
    gDvmJit.compilerWorkEnqueueIndex = gDvmJit.compilerWorkDequeueIndex = 0;
    gDvmJit.compilerQueueLength = 0;
    dvmUnlockMutex(&gDvmJit.compilerLock);

    /*
     * Defer rest of initialization until we're sure JIT'ng makes sense. Launch
     * the compiler thread, which will do the real initialization if and
     * when it is signalled to do so.
     */
    return dvmCreateInternalThread(&gDvmJit.compilerHandle, "Compiler",
                                   compilerThreadStart, NULL);
}
Example #9
0
/*
 * Initialize JDWP.
 *
 * Does not return until JDWP thread is running, but may return before
 * the thread is accepting network connections.
 */
JdwpState* dvmJdwpStartup(const JdwpStartupParams* pParams)
{
    JdwpState* state = NULL;

    /* comment this out when debugging JDWP itself */
    android_setMinPriority(LOG_TAG, ANDROID_LOG_DEBUG);

    state = (JdwpState*) calloc(1, sizeof(JdwpState));

    state->params = *pParams;

    state->requestSerial = 0x10000000;
    state->eventSerial = 0x20000000;
    dvmDbgInitMutex(&state->threadStartLock);
    dvmDbgInitMutex(&state->attachLock);
    dvmDbgInitMutex(&state->serialLock);
    dvmDbgInitMutex(&state->eventLock);
    state->eventThreadId = 0;
    dvmDbgInitMutex(&state->eventThreadLock);
    dvmDbgInitCond(&state->threadStartCond);
    dvmDbgInitCond(&state->attachCond);
    dvmDbgInitCond(&state->eventThreadCond);

    switch (pParams->transport) {
    case kJdwpTransportSocket:
        // LOGD("prepping for JDWP over TCP\n");
        state->transport = dvmJdwpSocketTransport();
        break;
    case kJdwpTransportAndroidAdb:
        // LOGD("prepping for JDWP over ADB\n");
        state->transport = dvmJdwpAndroidAdbTransport();
        /* TODO */
        break;
    default:
        LOGE("Unknown transport %d\n", pParams->transport);
        assert(false);
        goto fail;
    }

    if (!dvmJdwpNetStartup(state, pParams))
        goto fail;

    /*
     * Grab a mutex or two before starting the thread.  This ensures they
     * won't signal the cond var before we're waiting.
     */
    dvmDbgLockMutex(&state->threadStartLock);
    if (pParams->suspend)
        dvmDbgLockMutex(&state->attachLock);

    /*
     * We have bound to a port, or are trying to connect outbound to a
     * debugger.  Create the JDWP thread and let it continue the mission.
     */
    if (!dvmCreateInternalThread(&state->debugThreadHandle, "JDWP",
            jdwpThreadStart, state))
    {
        /* state is getting tossed, but unlock these anyway for cleanliness */
        dvmDbgUnlockMutex(&state->threadStartLock);
        if (pParams->suspend)
            dvmDbgUnlockMutex(&state->attachLock);
        goto fail;
    }

    /*
     * Wait until the thread finishes basic initialization.
     * TODO: cond vars should be waited upon in a loop
     */
    dvmDbgCondWait(&state->threadStartCond, &state->threadStartLock);
    dvmDbgUnlockMutex(&state->threadStartLock);


    /*
     * For suspend=y, wait for the debugger to connect to us or for us to
     * connect to the debugger.
     *
     * The JDWP thread will signal us when it connects successfully or
     * times out (for timeout=xxx), so we have to check to see what happened
     * when we wake up.
     */
    if (pParams->suspend) {
        dvmChangeStatus(NULL, THREAD_VMWAIT);
        dvmDbgCondWait(&state->attachCond, &state->attachLock);
        dvmDbgUnlockMutex(&state->attachLock);
        dvmChangeStatus(NULL, THREAD_RUNNING);

        if (!dvmJdwpIsActive(state)) {
            LOGE("JDWP connection failed\n");
            goto fail;
        }

        LOGI("JDWP connected\n");

        /*
         * Ordinarily we would pause briefly to allow the debugger to set
         * breakpoints and so on, but for "suspend=y" the VM init code will
         * pause the VM when it sends the VM_START message.
         */
    }

    return state;

fail:
    dvmJdwpShutdown(state);     // frees state
    return NULL;
}