Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Override android:vmSafeMode attribute for debug builds

While trying to optimize the build and deployment speed for debugging an app I found large chunk of time was spent executing /system/bin/dex2oat during installation. This is the ART ahead of time compiler.

I found when targeting API 22 you can now stop the ART AOT compilation:

<application
    ...
    android:vmSafeMode="true">
 </application>

I saw a noticeable deployment speed improvement, however I have concerns as to possible side effects of making this change. It must cause a small runtime performance hit, but are there any other consequences of enabling the android:vmSafeMode option?

Is it possible to override this attribute, for debug builds, in the gradle build file? Or is creating a debug specific manifest file the only solution?

like image 835
BrentM Avatar asked Jul 02 '15 02:07

BrentM


2 Answers

The best way to enable android:vmSafeMode for your debug build only is by using a debug manifest to complement the contents of your main AndroidManifest.xml.

To add this, create a new file …/app/src/debug/AndroidManifest.xml and add the following xml:

<manifest
 xmlns:android="http://schemas.android.com/apk/res/android"> 
 <application android:vmSafeMode="true" />
</manifest>

After adding this debug manifest and installing your app you should inspect your device logcat output to ensure that the vmSafeMode flag is being correctly applied when the dex2oat process is executed. Look for the argument --compiler-filter=interpret-only. This output also reports the time taken for the dex2oat process to execute so you can compare before and after making the change.

I/dex2oat﹕ /system/bin/dex2oat --zip-fd=6 --zip-location=/data/app/com.testing.sample.myapp-1/base.apk --oat-fd=7 --oat-location=/data/dalvik-cache/arm/data@[email protected]@[email protected] --instruction-set=arm --instruction-set-features=div --runtime-arg -Xms64m --runtime-arg -Xmx512m --compiler-filter=interpret-only --swap-fd=8
I/dex2oat﹕ dex2oat took 1.258ms (threads: 4) arena alloc=0B java alloc=2MB native alloc=502KB free=7MB

It is also possible to use the aapt tool to check if an APK has vmSafeMode enabled:

aapt list -a myapkfile.apk
...
A: android:vmSafeMode(0x010102b8)=(type 0x12)0xffffffff
...

I have not seen any reports of bugs caused by removing the ahead-of-time compilation. However, it is possible your application may expose issues that were not visible before making this change due to the reduction in performance.

It is possible very intensive processing may be slower by a factor of many times. If your app fits into this category it is best not to remove the ahead-of-time compilation.

like image 94
BrentM Avatar answered Sep 26 '22 15:09

BrentM


I'm reviving this for posterity because i know a cleaner approach.

You can use manifest placeholders in gradle to avoid having to duplicate your entire manifest file.

in your build.gradle add the following:

default {
        manifestPlaceholders = [vmSafeModeEnabled: "true"]
}
buildTypes{
    release {
        manifestPlaceholders = [vmSafeModeEnabled: "false"]
    }
}

and then in the manifest use this instead

android:vmSafeMode="${vmSafeModeEnabled}"

when the gradle build runs it will apply the appropriate value based on build type.

like image 22
Travis Castillo Avatar answered Sep 22 '22 15:09

Travis Castillo