Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 09c8f48c authored by Jeff Sharkey's avatar Jeff Sharkey Committed by Android (Google) Code Review
Browse files

Merge "Report leaked Context registrations to StrictMode."

parents 681abe6e d7026f16
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -15326,6 +15326,7 @@ package android.os {
    method public android.os.StrictMode.VmPolicy.Builder detectActivityLeaks();
    method public android.os.StrictMode.VmPolicy.Builder detectAll();
    method public android.os.StrictMode.VmPolicy.Builder detectLeakedClosableObjects();
    method public android.os.StrictMode.VmPolicy.Builder detectLeakedRegistrationObjects();
    method public android.os.StrictMode.VmPolicy.Builder detectLeakedSqlLiteObjects();
    method public android.os.StrictMode.VmPolicy.Builder penaltyDeath();
    method public android.os.StrictMode.VmPolicy.Builder penaltyDropBox();
+7 −0
Original line number Diff line number Diff line
@@ -512,6 +512,7 @@ public final class LoadedApk {

    public void removeContextRegistrations(Context context,
            String who, String what) {
        final boolean reportRegistrationLeaks = StrictMode.vmRegistrationLeaksEnabled();
        HashMap<BroadcastReceiver, LoadedApk.ReceiverDispatcher> rmap =
            mReceivers.remove(context);
        if (rmap != null) {
@@ -525,6 +526,9 @@ public final class LoadedApk {
                        "call to unregisterReceiver()?");
                leak.setStackTrace(rd.getLocation().getStackTrace());
                Slog.e(ActivityThread.TAG, leak.getMessage(), leak);
                if (reportRegistrationLeaks) {
                    StrictMode.onIntentReceiverLeaked(leak);
                }
                try {
                    ActivityManagerNative.getDefault().unregisterReceiver(
                            rd.getIIntentReceiver());
@@ -546,6 +550,9 @@ public final class LoadedApk {
                        + sd.getServiceConnection() + " that was originally bound here");
                leak.setStackTrace(sd.getLocation().getStackTrace());
                Slog.e(ActivityThread.TAG, leak.getMessage(), leak);
                if (reportRegistrationLeaks) {
                    StrictMode.onServiceConnectionLeaked(leak);
                }
                try {
                    ActivityManagerNative.getDefault().unbindService(
                            sd.getIServiceConnection());
+42 −3
Original line number Diff line number Diff line
@@ -20,7 +20,10 @@ import android.app.ActivityManagerNative;
import android.app.ActivityThread;
import android.app.ApplicationErrorReport;
import android.app.IActivityManager;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.util.Log;
import android.util.Printer;
import android.util.Singleton;
@@ -195,9 +198,15 @@ public final class StrictMode {
     */
    private static final int DETECT_VM_INSTANCE_LEAKS = 0x1000;  // for VmPolicy

    /**
     * @hide
     */
    public static final int DETECT_VM_REGISTRATION_LEAKS = 0x2000;  // for VmPolicy

    private static final int ALL_VM_DETECT_BITS =
            DETECT_VM_CURSOR_LEAKS | DETECT_VM_CLOSABLE_LEAKS |
            DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_INSTANCE_LEAKS;
            DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_INSTANCE_LEAKS |
            DETECT_VM_REGISTRATION_LEAKS;

    /**
     * @hide
@@ -618,8 +627,8 @@ public final class StrictMode {
             * but will likely expand in future releases.
             */
            public Builder detectAll() {
                return enable(DETECT_VM_ACTIVITY_LEAKS |
                        DETECT_VM_CURSOR_LEAKS | DETECT_VM_CLOSABLE_LEAKS);
                return enable(DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_CURSOR_LEAKS
                        | DETECT_VM_CLOSABLE_LEAKS | DETECT_VM_REGISTRATION_LEAKS);
            }

            /**
@@ -647,6 +656,15 @@ public final class StrictMode {
                return enable(DETECT_VM_CLOSABLE_LEAKS);
            }

            /**
             * Detect when a {@link BroadcastReceiver} or
             * {@link ServiceConnection} is leaked during {@link Context}
             * teardown.
             */
            public Builder detectLeakedRegistrationObjects() {
                return enable(DETECT_VM_REGISTRATION_LEAKS);
            }

            /**
             * Crashes the whole process on violation.  This penalty runs at
             * the end of all enabled penalties so yo you'll still get
@@ -1496,6 +1514,13 @@ public final class StrictMode {
        return (sVmPolicyMask & DETECT_VM_CLOSABLE_LEAKS) != 0;
    }

    /**
     * @hide
     */
    public static boolean vmRegistrationLeaksEnabled() {
        return (sVmPolicyMask & DETECT_VM_REGISTRATION_LEAKS) != 0;
    }

    /**
     * @hide
     */
@@ -1510,6 +1535,20 @@ public final class StrictMode {
        onVmPolicyViolation(null, originStack);
    }

    /**
     * @hide
     */
    public static void onIntentReceiverLeaked(Throwable originStack) {
        onVmPolicyViolation(null, originStack);
    }

    /**
     * @hide
     */
    public static void onServiceConnectionLeaked(Throwable originStack) {
        onVmPolicyViolation(null, originStack);
    }

    // Map from VM violation fingerprint to uptime millis.
    private static final HashMap<Integer, Long> sLastVmViolationTime = new HashMap<Integer, Long>();