首先我们先看一下dex2oat都支持一些什么样的命令行参数:
上面我们学习了dex2oat的参数的简介,下面我们学以致用,看看在真实的环境中它们是如何被使用的。
我们直接看build时,dex2oat的参数是如何被传进去的,在build/core/dex_preopt_libart.mk中:
91# For a single jar or APK
92
93# $(1): the input .jar or .apk file
94# $(2): the output .odex file
95define dex2oat-one-file
96$(hide) rm -f $(2)
97$(hide) mkdir -p $(dir $(2))
98$(hide) $(DEX2OAT) \
99 --runtime-arg -Xms$(DEX2OAT_XMS) --runtime-arg -Xmx$(DEX2OAT_XMX) \
首先指定两个运行时参数,这两个参数是在前面定义的:
44DEX2OAT_XMS := $(call get-product-default-property,dalvik.vm.dex2oat-Xms)
45DEX2OAT_XMX := $(call get-product-default-property,dalvik.vm.dex2oat-Xmx)
也就是说,这两个值取自属性dalvik.vm.dex2oat-Xms和vm.dex2oat-Xmx。这两个属性是哪里来的呢,是在/build/target/product/runtime_libart.mk中,编译的时候指定进来的:
48PRODUCT_DEFAULT_PROPERTY_OVERRIDES += \
49 dalvik.vm.image-dex2oat-Xms=64m \
50 dalvik.vm.image-dex2oat-Xmx=64m \
51 dalvik.vm.dex2oat-Xms=64m \
52 dalvik.vm.dex2oat-Xmx=512m \
53 ro.dalvik.vm.native.bridge=0 \
这样,这两个值分别是64m和512m。
我们回到dex_preopt_libart.mk中继续看:
100 --boot-image=$(PRIVATE_DEX_PREOPT_IMAGE_LOCATION) \
查这个PRIVATE_DEX_PREOPT_IMAGE_LOCATION,定义于/build/core/setup_one_odex.mk中:
30$(my_built_odex): PRIVATE_DEX_PREOPT_IMAGE_LOCATION := $(my_dex_preopt_image_location)
然后再向上追my_dex_preopt_image_location
22ifdef LOCAL_DEX_PREOPT_IMAGE_LOCATION
23my_dex_preopt_image_location := $(LOCAL_DEX_PREOPT_IMAGE_LOCATION)
24else
25my_dex_preopt_image_location := $($(my_2nd_arch_prefix)DEFAULT_DEX_PREOPT_BUILT_IMAGE_LOCATION)
26endif
LOCAL_DEX_PREOPT_IMAGE_LOCATION没有定义,继续顺藤摸瓜。
23$(my_2nd_arch_prefix)DEFAULT_DEX_PREOPT_BUILT_IMAGE_LOCATION := $(DEXPREOPT_BOOT_JAR_DIR_FULL_PATH)/boot.art
再继续追DEXPREOPT_BOOT_JAR_DIR_FULL_PATH:
17DEXPREOPT_BOOT_JAR_DIR_FULL_PATH := $(DEXPREOPT_PRODUCT_DIR_FULL_PATH)/$(DEXPREOPT_BOOT_JAR_DIR)
先看后面的DEXPREOPT_BOOT_JAR_DIR,原来就是system/framework
16DEXPREOPT_BOOT_JAR_DIR := system/framework
再看前面的DEXPREOPT_PRODUCT_DIR_FULL_PATH,是out下的dex_bootjars
14DEXPREOPT_PRODUCT_DIR_FULL_PATH := $(PRODUCT_OUT)/dex_bootjars
最后--boot-image
的值为out/dex_bootjars/system/framework/boot.art
这个就不多说了
101 --dex-file=$(1) \
102 --dex-location=$(PRIVATE_DEX_LOCATION) \
103 --oat-file=$(2) \
104 --android-root=$(PRODUCT_OUT)/system \
105 --instruction-set=$($(PRIVATE_2ND_ARCH_VAR_PREFIX)DEX2OAT_TARGET_ARCH) \
追查:
604DEX2OAT_TARGET_ARCH := $(TARGET_ARCH)
这个板级驱动已经配好了。
106 --instruction-set-variant=$($(PRIVATE_2ND_ARCH_VAR_PREFIX)DEX2OAT_TARGET_CPU_VARIANT) \
107 --instruction-set-features=$($(PRIVATE_2ND_ARCH_VAR_PREFIX)DEX2OAT_TARGET_INSTRUCTION_SET_FEATURES) \
在同样的位置定义:
604DEX2OAT_TARGET_ARCH := $(TARGET_ARCH)
605ifeq ($(TARGET_CPU_VARIANT),)
606ifeq ($(TARGET_ARCH_VARIANT),)
607DEX2OAT_TARGET_CPU_VARIANT := default
608else
609DEX2OAT_TARGET_CPU_VARIANT := $(TARGET_ARCH_VARIANT)
610endif
611else
612DEX2OAT_TARGET_CPU_VARIANT := $(TARGET_CPU_VARIANT)
613endif
614DEX2OAT_TARGET_INSTRUCTION_SET_FEATURES := default
615
108 --include-patch-information --runtime-arg -Xnorelocate --no-generate-debug-info \
109 --abort-on-hard-verifier-error \
110 $(PRIVATE_DEX_PREOPT_FLAGS)
111endef
include-patch-information兼runtime-arg -Xnorelocate,生成重定位的信息,因为后面还要走patchoat呢。
no-generate-debug-info,不生成调试信息
大家留神啊,现在已经是selinux的时代了,dex2oat也需要配置相关的权限:
# dex2oat
type dex2oat, domain;
type dex2oat_exec, exec_type, file_type;
allow dex2oat dalvikcache_data_file:file write;
# Read symlinks in /data/dalvik-cache
allow dex2oat dalvikcache_data_file:lnk_file read;
allow dex2oat installd:fd use;
# Read already open asec_apk_file file descriptors passed by installd.
# Also allow reading unlabeled files, to allow for upgrading forward
# locked APKs.
allow dex2oat asec_apk_file:file read;
allow dex2oat unlabeled:file read;
allow dex2oat oemfs:file read;
allow dex2oat apk_tmp_file:file read;
这还不算,在installd的权限配置/external/sepolicy/installd.te中,明确设置了
71# Run dex2oat in its own sandbox.
72domain_auto_trans(installd, dex2oat_exec, dex2oat)