From 21bdaf14a2bb9dc5baeb3109d3af99518572ce51 Mon Sep 17 00:00:00 2001 From: Tamas Berghammer Date: Fri, 29 Jan 2016 12:07:00 +0000 Subject: [PATCH] [DO NOT MERGE] Add flag to "am start" to enable native debugging [Backported form internal CL854980] Specifying the new flag will enable several features in the runtime required by the native debugger to debug Java and C++ code at the same time. The enabled features: * Force JIT (never use the interpreter) * Debug info generation * Disable some optimizations Change-Id: Iaf5ab649715a0c274bd1b0fc64e483705da53cd0 --- cmds/am/src/com/android/commands/am/Am.java | 5 +++- core/java/android/app/ActivityManager.java | 7 ++++++ core/java/android/os/Process.java | 6 +++++ core/java/com/android/internal/os/Zygote.java | 4 ++++ .../com/android/internal/os/ZygoteConnection.java | 4 ++++ .../android/server/am/ActivityManagerService.java | 27 ++++++++++++++++++++++ .../android/server/am/ActivityStackSupervisor.java | 4 ++++ 7 files changed, 56 insertions(+), 1 deletion(-) diff --git a/cmds/am/src/com/android/commands/am/Am.java b/cmds/am/src/com/android/commands/am/Am.java index d64e2707139d..74a1fbf1b490 100644 --- a/cmds/am/src/com/android/commands/am/Am.java +++ b/cmds/am/src/com/android/commands/am/Am.java @@ -104,7 +104,7 @@ public class Am extends BaseCommand { public void onShowUsage(PrintStream out) { out.println( "usage: am [subcommand] [options]\n" + - "usage: am start [-D] [-W] [-P ] [--start-profiler ]\n" + + "usage: am start [-D] [-N] [-W] [-P ] [--start-profiler ]\n" + " [--sampling INTERVAL] [-R COUNT] [-S] [--opengl-trace]\n" + " [--track-allocation] [--user | current] \n" + " am startservice [--user | current] \n" + @@ -153,6 +153,7 @@ public class Am extends BaseCommand { "\n" + "am start: start an Activity. Options are:\n" + " -D: enable debugging\n" + + " -N: enable native debugging\n" + " -W: wait for launch to complete\n" + " --start-profiler : start profiler and send results to \n" + " --sampling INTERVAL: use sample profiling with INTERVAL microseconds\n" + @@ -676,6 +677,8 @@ public class Am extends BaseCommand { intent = new Intent(); } else if (opt.equals("-D")) { mStartFlags |= ActivityManager.START_FLAG_DEBUG; + } else if (opt.equals("-N")) { + mStartFlags |= ActivityManager.START_FLAG_NATIVE_DEBUGGING; } else if (opt.equals("-W")) { mWaitOption = true; } else if (opt.equals("-P")) { diff --git a/core/java/android/app/ActivityManager.java b/core/java/android/app/ActivityManager.java index 84c6d6a256d6..161c1fa43cc6 100644 --- a/core/java/android/app/ActivityManager.java +++ b/core/java/android/app/ActivityManager.java @@ -217,6 +217,13 @@ public class ActivityManager { public static final int START_FLAG_TRACK_ALLOCATION = 1<<3; /** + * Flag for IActivityManaqer.startActivity: launch the app with + * native debugging support. + * @hide + */ + public static final int START_FLAG_NATIVE_DEBUGGING = 1<<4; + + /** * Result for IActivityManaqer.broadcastIntent: success! * @hide */ diff --git a/core/java/android/os/Process.java b/core/java/android/os/Process.java index 366ba0b60858..65f43f67e0d5 100644 --- a/core/java/android/os/Process.java +++ b/core/java/android/os/Process.java @@ -635,6 +635,12 @@ public class Process { if ((debugFlags & Zygote.DEBUG_GENERATE_DEBUG_INFO) != 0) { argsForZygote.add("--generate-debug-info"); } + if ((debugFlags & Zygote.DEBUG_ALWAYS_JIT) != 0) { + argsForZygote.add("--always-jit"); + } + if ((debugFlags & Zygote.DEBUG_NATIVE_DEBUGGABLE) != 0) { + argsForZygote.add("--native-debuggable"); + } if ((debugFlags & Zygote.DEBUG_ENABLE_ASSERT) != 0) { argsForZygote.add("--enable-assert"); } diff --git a/core/java/com/android/internal/os/Zygote.java b/core/java/com/android/internal/os/Zygote.java index d23f26d675c4..919254a36a76 100644 --- a/core/java/com/android/internal/os/Zygote.java +++ b/core/java/com/android/internal/os/Zygote.java @@ -41,6 +41,10 @@ public final class Zygote { public static final int DEBUG_ENABLE_JNI_LOGGING = 1 << 4; /** Force generation of native debugging information. */ public static final int DEBUG_GENERATE_DEBUG_INFO = 1 << 5; + /** Always use JIT-ed code. */ + public static final int DEBUG_ALWAYS_JIT = 1 << 6; + /** Make the code debuggable with turning off some optimizations. */ + public static final int DEBUG_NATIVE_DEBUGGABLE = 1 << 7; /** No external storage should be mounted. */ public static final int MOUNT_EXTERNAL_NONE = 0; diff --git a/core/java/com/android/internal/os/ZygoteConnection.java b/core/java/com/android/internal/os/ZygoteConnection.java index a40f9a82ace7..85d84bb3f986 100644 --- a/core/java/com/android/internal/os/ZygoteConnection.java +++ b/core/java/com/android/internal/os/ZygoteConnection.java @@ -434,6 +434,10 @@ class ZygoteConnection { debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; } else if (arg.equals("--generate-debug-info")) { debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; + } else if (arg.equals("--always-jit")) { + debugFlags |= Zygote.DEBUG_ALWAYS_JIT; + } else if (arg.equals("--native-debuggable")) { + debugFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE; } else if (arg.equals("--enable-jni-logging")) { debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; } else if (arg.equals("--enable-assert")) { diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java index 43e4375044df..128448e9a5e4 100644 --- a/services/core/java/com/android/server/am/ActivityManagerService.java +++ b/services/core/java/com/android/server/am/ActivityManagerService.java @@ -1229,6 +1229,7 @@ public final class ActivityManagerService extends ActivityManagerNative int mMemWatchDumpPid; int mMemWatchDumpUid; String mTrackAllocationApp = null; + String mNativeDebuggingApp = null; final long[] mTmpLong = new long[1]; @@ -3352,6 +3353,13 @@ public final class ActivityManagerService extends ActivityManagerNative if ("1".equals(SystemProperties.get("debug.assert"))) { debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; } + if (mNativeDebuggingApp != null && mNativeDebuggingApp.equals(app.processName)) { + // Enable all debug flags required by the native debugger. + debugFlags |= Zygote.DEBUG_ALWAYS_JIT; // Don't interpret anything + debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; // Generate debug info + debugFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE; // Disbale optimizations + mNativeDebuggingApp = null; + } String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; if (requiredAbi == null) { @@ -10651,6 +10659,16 @@ public final class ActivityManagerService extends ActivityManagerNative } } + void setNativeDebuggingAppLocked(ApplicationInfo app, String processName) { + boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); + if (!isDebuggable) { + if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { + throw new SecurityException("Process not debuggable: " + app.packageName); + } + } + mNativeDebuggingApp = processName; + } + @Override public void setAlwaysFinish(boolean enabled) { enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, @@ -13726,6 +13744,15 @@ public final class ActivityManagerService extends ActivityManagerNative pw.println(" mProfileType=" + mProfileType); } } + if (mNativeDebuggingApp != null) { + if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) { + if (needSep) { + pw.println(); + needSep = false; + } + pw.println(" mNativeDebuggingApp=" + mNativeDebuggingApp); + } + } if (dumpPackage == null) { if (mAlwaysFinishActivities || mController != null) { pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities diff --git a/services/core/java/com/android/server/am/ActivityStackSupervisor.java b/services/core/java/com/android/server/am/ActivityStackSupervisor.java index 70c4821c8486..1e1ed37e2b4a 100644 --- a/services/core/java/com/android/server/am/ActivityStackSupervisor.java +++ b/services/core/java/com/android/server/am/ActivityStackSupervisor.java @@ -894,6 +894,10 @@ public final class ActivityStackSupervisor implements DisplayListener { mService.setOpenGlTraceApp(aInfo.applicationInfo, aInfo.processName); } + if ((startFlags & ActivityManager.START_FLAG_NATIVE_DEBUGGING) != 0) { + mService.setNativeDebuggingAppLocked(aInfo.applicationInfo, aInfo.processName); + } + if ((startFlags & ActivityManager.START_FLAG_TRACK_ALLOCATION) != 0) { mService.setTrackAllocationApp(aInfo.applicationInfo, aInfo.processName); } -- 2.11.0