您的位置:首页 > 移动开发 > Android开发

深入理解Android(05)——深入理解zygote

2015-02-01 23:20 525 查看

1、概述

Android系统运行这两个完全不同的世界

1)Java世界,Google提供的SDK主要就是针对这个世界的。在这里运行的程序都是基于Dalvik虚拟机的Java程序。

2)Native世界,也就是用Native语言C或者C++开发的程序,他们组成了Native世界。

zygote中文名为“受精卵”,它和Android系统中的Java世界有着重要的关系。

2、zygote分析

zygote源码位于:framework/base/cmds/app_process/App_main.cpp。

main函数代码信息如下:

int main(int argc, const char* const argv[])
{
    // These are global variables in ProcessState.cpp
// zygote进程由init通过fork而来
    mArgC = argc;
    mArgV = argv;
    
    mArgLen = 0;
    for (int i=0; i<argc; i++) {
        mArgLen += strlen(argv[i]) + 1;
    }
    mArgLen--;

    AppRuntime runtime;
    const char *arg;
    const char *argv0;

    argv0 = argv[0];

    // Process command line arguments
    // ignore argv[0]
    argc--;
    argv++;

// 调用Appruntime的addVmArguments
    int i = runtime.addVmArguments(argc, argv);

    // Next arg is parent directory
    if (i < argc) {
// 设置runtime的mParentDir为/system/bin
        runtime.mParentDir = argv[i++];
    }

    // Next arg is startup classname or "--zygote"
    if (i < argc) {
        arg = argv[i++];
// 我们传入的参数满足if条件,而且下面的startSystemServer的值为true
        if (0 == strcmp("--zygote", arg)) {
            bool startSystemServer = (i < argc) ? 
                    strcmp(argv[i], "--start-system-server") == 0 : false;
            setArgv0(argv0, "zygote");
// 设置本进程的名称为zygote,将main换了一个名字
            set_process_name("zygote");
// 调用runtime的start,注意第二个参数的值为true
            runtime.start("com.android.internal.os.ZygoteInit",
                startSystemServer);
        } else {
            ......
        }
    } else {
        ......
        return 10;
    }

}


代码就不过多解读了,上文中的注释已经写得非常完整了。读者也可以自己去查看Android源码中的该部分代码。

3、AppRuntime分析

AppRuntime类的声明和实现均在App_main.cpp中,它是从AndroidRuntime类派生出来的。

AppRuntime重载了onStarted、onZygotelnit和onExit函数。前面的代码调用了AndroidRuntime的start函数,这个start函数使用的是基类AndroidRuntime的start。我们看看它调用的参数信息。

AppRuntime源码位置:/frameworks/base/core/jni/AndroidRuntime.cpp

void AndroidRuntime::start(const char* className, const bool startSystemServer)
{
    LOGD("\n>>>>>> AndroidRuntime START %s <<<<<<\n",
            className != NULL ? className : "(unknown)");

	// className的值是"com.android.internal.os.ZygoteInit"
    char* slashClassName = NULL;
    char* cp;
    JNIEnv* env;

    blockSigpipe();

    // ......

    /* 1、创建虚拟机---start the virtual machine */
    if (startVm(&mJavaVM, &env) != 0)
        goto bail;

    /*
     * 2、注册JNI函数---Register android functions.
     */
    if (startReg(env) < 0) {
        LOGE("Unable to register all android natives\n");
        goto bail;
    }

    /*
     * We want to call main() with a String array with arguments in it.
     * At present we only have one argument, the class name.  Create an
     * array to hold it.
     */
    // ......

    /*
     * Start VM.  This thread becomes the main thread of the VM, and will
     * not return until the VM exits.
     */
    
	// 通过JNI调用Java函数,注意调用的函数是main,所属的类是com.android.internal.os.ZygoteInit,传递的参数是“com.android.internal.os.ZygoteInit true”
	
    LOGD("Shutting down VM\n");
    if (mJavaVM->DetachCurrentThread() != JNI_OK)
        LOGW("Warning: unable to detach main thread\n");
    if (mJavaVM->DestroyJavaVM() != 0)
        LOGW("Warning: VM did not shut down cleanly\n");

bail:
    free(slashClassName);
}


AppRuntime主要主要完成三个步骤:创建虚拟机、注册JNI函数、调用Java函数。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: