java安卓j建立进程_app_process: 启动java进程(1)

app_process是Android系统中的关键组件,负责启动zygote和system_server进程。它根据参数不同,既可以启动zygote,也可以运行指定的Java程序。在启动过程中,涉及AndroidRuntime类的使用,包括创建虚拟机、注册JNI接口和执行指定类的main方法。
摘要由CSDN通过智能技术生成

app_process: 启动java进程(1)

app_process: 启动java进程(1)

[var1]

android-8.0.0_r1\frameworks\base\cmds\app_process

android- 8.0.0_r1\frameworks\base\core\jni\AndroidRuntime.cpp

[var1]

app_process是Android系统中一个重要的编译出来的可执行文件。该执行文件在开机过程中负责启动Android核心的进程zygote和system_server。

app_process也可以用来运行可执行的java程序。

[var1]

app_process可执行文件的核心文件是

frameworks\base\cmds\app_process\app_main.cpp

frameworks\base\core\jni\AndroidRuntime.cpp

61c43066888b227e1a3286c93c19a0d7.png

创建运行时类对象(AndroidRuntime类)

图像模块底层初始化

app_process命令的参数解析

使用AndroidRuntime对象启动java进程。注意: 启动的java进程有两种类型:

4.1. 不指定类名和应用名,按照系统默认配置,启动zygote和system_server

4.2 按照指定的类名和应用,查找其中的main函数作为入口,运行java程序

运行java程序。运行java程序,并不是直接执行指定程序的main函数,而是在中间加了一层,通过ZygoteInit或RuntimeInit来运行最终要运行的java可执行程序

// file: frameworks\base\cmds\app_process\app_main.cpp

// function: main

if (zygote) {

/*

启动zygote和system_server.在参数解析不能体现启动system_server是调用ZygoteInit,

在更深层的代码追踪,会发现system_server通过ZygoteInit启动。也即启动system_server,

zygote一定为true,除非通过命令直接启动system_server.此处主要呈现的是Android系统启动过程.

*/

runtime.start("com.android.internal.os.ZygoteInit", args, zygote);

} else if (className) {

// 启动其他

runtime.start("com.android.internal.os.RuntimeInit", args, zygote);

} else {

fprintf(stderr, "Error: no class name or --zygote supplied.\n");

app_usage();

LOG_ALWAYS_FATAL("app_process: no class name or --zygote supplied.");

}

重点说明AndroidRuntime start函数

在AndroidRuntime的start中,执行了运行java程序核心步骤:

创建虚拟机

在创建虚拟机代码中可以看到初始化很多数据,了解虚拟用到的参数,可以根据设备特性,更优的配置参数和满足产品及用户需求

// file: frameworks\base\core\jni\AndroidRuntime.cpp

int AndroidRuntime::startVm(JavaVM** pJavaVM, JNIEnv** pEnv, bool zygote)

{

// 1.初始化参数

JavaVMInitArgs initArgs;

char propBuf[PROPERTY_VALUE_MAX];

char stackTraceFileBuf[sizeof("-Xstacktracefile:")-1 + PROPERTY_VALUE_MAX];

char jniOptsBuf[sizeof("-Xjniopts:")-1 + PROPERTY_VALUE_MAX];

char heapstartsizeOptsBuf[sizeof("-Xms")-1 + PROPERTY_VALUE_MAX];

char heapsizeOptsBuf[sizeof("-Xmx")-1 + PROPERTY_VALUE_MAX];

char heapgrowthlimitOptsBuf[sizeof("-XX:HeapGrowthLimit=")-1 + PROPERTY_VALUE_MAX];

char heapminfreeOptsBuf[sizeof("-XX:HeapMinFree=")-1 + PROPERTY_VALUE_MAX];

char heapmaxfreeOptsBuf[sizeof("-XX:HeapMaxFree=")-1 + PROPERTY_VALUE_MAX];

char usejitOptsBuf[sizeof("-Xusejit:")-1 + PROPERTY_VALUE_MAX];

char jitmaxsizeOptsBuf[sizeof("-Xjitmaxsize:")-1 + PROPERTY_VALUE_MAX];

...

char dex2oatThreadsImageBuf[sizeof("-j")-1 + PROPERTY_VALUE_MAX];

char dex2oat_isa_variant_key[PROPERTY_KEY_MAX];

char dex2oat_isa_variant[sizeof("--instruction-set-variant=") -1 + PROPERTY_VALUE_MAX];

char dex2oat_isa_features_key[PROPERTY_KEY_MAX];

char dex2oat_isa_features[sizeof("--instruction-set-features=") -1 + PROPERTY_VALUE_MAX];

char dex2oatFlagsBuf[PROPERTY_VALUE_MAX];

char dex2oatImageFlagsBuf[PROPERTY_VALUE_MAX];

char extraOptsBuf[PROPERTY_VALUE_MAX];

char voldDecryptBuf[PROPERTY_VALUE_MAX];

...

// 2.真正创建虚拟机

/*

* Initialize the VM.

*

* The JavaVM* is essentially per-process, and the JNIEnv* is per-thread.

* If this call succeeds, the VM is ready, and we can start issuing

* JNI calls.

*/

if (JNI_CreateJavaVM(pJavaVM, pEnv, &initArgs) < 0) {

ALOGE("JNI_CreateJavaVM failed\n");

return -1;

}

return 0;

}

针对每个虚拟机,注册运行时用到的jni接口

在Android系统中做垂直开发,避免不了增加jni接口。添加jni接口有两种方式:

2.1 jni接口继承到系统运行时库中

2.2 单独编译一个动态库,在运行的java程序中,通过调用System.loadLibrary加载动态库

此处是加载系统运行时库

// file: frameworks\base\core\jni\AndroidRuntime.cpp

/*

* Register android native functions with the VM.

*/

/*static*/ int AndroidRuntime::startReg(JNIEnv* env)

{

ATRACE_NAME("RegisterAndroidNatives");

/*

* This hook causes all future threads created in this process to be

* attached to the JavaVM. (This needs to go away in favor of JNI

* Attach calls.)

*/

// 创建和java环境关联的线程

androidSetCreateThreadFunc((android_create_thread_fn) javaCreateThreadEtc);

ALOGV("--- registering native functions ---\n");

/*

* Every "register" function calls one or more things that return

* a local reference (e.g. FindClass). Because we haven't really

* started the VM yet, they're all getting stored in the base frame

* and never released. Use Push/Pop to manage the storage.

*/

env->PushLocalFrame(200);

// 注册jni接口:多个模块的

if (register_jni_procs(gRegJNI, NELEM(gRegJNI), env) < 0) {

env->PopLocalFrame(NULL);

return -1;

}

env->PopLocalFrame(NULL);

//createJavaThread("fubar", quickTest, (void*) "hello");

return 0;

}

注意变量gRegJNI

// file: frameworks\base\core\jni\AndroidRuntime.cpp

// array是传入的gRegJNI

static int register_jni_procs(const RegJNIRec array[], size_t count, JNIEnv* env)

{

for (size_t i = 0; i < count; i++) {

if (array[i].mProc(env) < 0) {

#ifndef NDEBUG

ALOGD("----------!!! %s failed to load\n", array[i].mName);

#endif

return -1;

}

}

return 0;

}

// 包含了Android系统中各模块的jni

static const RegJNIRec gRegJNI[] = {

REG_JNI(register_com_android_internal_os_RuntimeInit),

REG_JNI(register_com_android_internal_os_ZygoteInit),

...

REG_JNI(register_android_os_Binder),

REG_JNI(register_android_os_Parcel),

REG_JNI(register_android_os_HwBinder),

REG_JNI(register_android_os_HwBlob),

...

REG_JNI(register_android_graphics_Canvas),

REG_JNI(register_android_graphics_Graphics),

...

REG_JNI(register_android_hardware_Camera),

REG_JNI(register_android_hardware_camera2_CameraMetadata), REG_JNI(register_android_hardware_camera2_legacy_LegacyCameraDevice),

...

REG_JNI(register_com_android_internal_content_NativeLibraryHelper),

REG_JNI(register_com_android_internal_net_NetworkStatsFactory),

REG_JNI(register_com_android_internal_os_FuseAppLoop),

};

查找入口函数main,然后运行java程序

在实际运行过程会创建独立进程,这个在后面的细节部分展现。

// file: frameworks\base\core\jni\AndroidRuntime.cpp

// function: start函数

/*

* Start VM. This thread becomes the main thread of the VM, and will

* not return until the VM exits.

*/

char* slashClassName = toSlashClassName(className);

jclass startClass = env->FindClass(slashClassName);

if (startClass == NULL) {

ALOGE("JavaVM unable to locate class '%s'\n", slashClassName);

/* keep going */

} else {

// 查找main函数

jmethodID startMeth = env->GetStaticMethodID(startClass, "main",

"([Ljava/lang/String;)V");

if (startMeth == NULL) {

ALOGE("JavaVM unable to find main() in '%s'\n", className);

/* keep going */

} else {

// 执行main函数

env->CallStaticVoidMethod(startClass, startMeth, strArray);

}

}

...

}

app_process: 启动java进程(1)相关教程

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值