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

Commit 5232271a authored by Dianne Hackborn's avatar Dianne Hackborn
Browse files

Fix issue #17146552: system anr

Add a safe path for Slog.wtf that doesn't acquire an activity manager
lock or block in any way.

Change-Id: I8fef8251a0cb85081442cae55d85063944248d15
parent 80e29b66
Loading
Loading
Loading
Loading
+4 −2
Original line number Diff line number Diff line
@@ -1392,8 +1392,9 @@ public abstract class ActivityManagerNative extends Binder implements IActivityM
            data.enforceInterface(IActivityManager.descriptor);
            IBinder app = data.readStrongBinder();
            String tag = data.readString();
            boolean system = data.readInt() != 0;
            ApplicationErrorReport.CrashInfo ci = new ApplicationErrorReport.CrashInfo(data);
            boolean res = handleApplicationWtf(app, tag, ci);
            boolean res = handleApplicationWtf(app, tag, system, ci);
            reply.writeNoException();
            reply.writeInt(res ? 1 : 0);
            return true;
@@ -4069,7 +4070,7 @@ class ActivityManagerProxy implements IActivityManager
        data.recycle();
    }

    public boolean handleApplicationWtf(IBinder app, String tag,
    public boolean handleApplicationWtf(IBinder app, String tag, boolean system,
            ApplicationErrorReport.CrashInfo crashInfo) throws RemoteException
    {
        Parcel data = Parcel.obtain();
@@ -4077,6 +4078,7 @@ class ActivityManagerProxy implements IActivityManager
        data.writeInterfaceToken(IActivityManager.descriptor);
        data.writeStrongBinder(app);
        data.writeString(tag);
        data.writeInt(system ? 1 : 0);
        crashInfo.writeToParcel(data, 0);
        mRemote.transact(HANDLE_APPLICATION_WTF_TRANSACTION, data, reply, 0);
        reply.readException();
+1 −1
Original line number Diff line number Diff line
@@ -266,7 +266,7 @@ public interface IActivityManager extends IInterface {
    // Special low-level communication with activity manager.
    public void handleApplicationCrash(IBinder app,
            ApplicationErrorReport.CrashInfo crashInfo) throws RemoteException;
    public boolean handleApplicationWtf(IBinder app, String tag,
    public boolean handleApplicationWtf(IBinder app, String tag, boolean system,
            ApplicationErrorReport.CrashInfo crashInfo) throws RemoteException;

    // A StrictMode violation to be handled.  The violationMask is a
+10 −9
Original line number Diff line number Diff line
@@ -96,12 +96,12 @@ public final class Log {
     * @hide
     */
    public interface TerribleFailureHandler {
        void onTerribleFailure(String tag, TerribleFailure what);
        void onTerribleFailure(String tag, TerribleFailure what, boolean system);
    }

    private static TerribleFailureHandler sWtfHandler = new TerribleFailureHandler() {
            public void onTerribleFailure(String tag, TerribleFailure what) {
                RuntimeInit.wtf(tag, what);
            public void onTerribleFailure(String tag, TerribleFailure what, boolean system) {
                RuntimeInit.wtf(tag, what, system);
            }
        };

@@ -253,7 +253,7 @@ public final class Log {
     * @param msg The message you would like logged.
     */
    public static int wtf(String tag, String msg) {
        return wtf(LOG_ID_MAIN, tag, msg, null, false);
        return wtf(LOG_ID_MAIN, tag, msg, null, false, false);
    }

    /**
@@ -262,7 +262,7 @@ public final class Log {
     * @hide
     */
    public static int wtfStack(String tag, String msg) {
        return wtf(LOG_ID_MAIN, tag, msg, null, true);
        return wtf(LOG_ID_MAIN, tag, msg, null, true, false);
    }

    /**
@@ -272,7 +272,7 @@ public final class Log {
     * @param tr An exception to log.
     */
    public static int wtf(String tag, Throwable tr) {
        return wtf(LOG_ID_MAIN, tag, tr.getMessage(), tr, false);
        return wtf(LOG_ID_MAIN, tag, tr.getMessage(), tr, false, false);
    }

    /**
@@ -283,14 +283,15 @@ public final class Log {
     * @param tr An exception to log.  May be null.
     */
    public static int wtf(String tag, String msg, Throwable tr) {
        return wtf(LOG_ID_MAIN, tag, msg, tr, false);
        return wtf(LOG_ID_MAIN, tag, msg, tr, false, false);
    }

    static int wtf(int logId, String tag, String msg, Throwable tr, boolean localStack) {
    static int wtf(int logId, String tag, String msg, Throwable tr, boolean localStack,
            boolean system) {
        TerribleFailure what = new TerribleFailure(msg, tr);
        int bytes = println_native(logId, ASSERT, tag, msg + '\n'
                + getStackTraceString(localStack ? what : tr));
        sWtfHandler.onTerribleFailure(tag, what);
        sWtfHandler.onTerribleFailure(tag, what, system);
        return bytes;
    }

+4 −4
Original line number Diff line number Diff line
@@ -74,19 +74,19 @@ public final class Slog {
    }

    public static int wtf(String tag, String msg) {
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, null, false);
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, null, false, true);
    }

    public static int wtfStack(String tag, String msg) {
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, null, true);
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, null, true, true);
    }

    public static int wtf(String tag, Throwable tr) {
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, tr.getMessage(), tr, false);
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, tr.getMessage(), tr, false, true);
    }

    public static int wtf(String tag, String msg, Throwable tr) {
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, tr, false);
        return Log.wtf(Log.LOG_ID_SYSTEM, tag, msg, tr, false, true);
    }

    public static int println(int priority, String tag, String msg) {
+2 −2
Original line number Diff line number Diff line
@@ -338,10 +338,10 @@ public class RuntimeInit {
     * @param tag to record with the error
     * @param t exception describing the error site and conditions
     */
    public static void wtf(String tag, Throwable t) {
    public static void wtf(String tag, Throwable t, boolean system) {
        try {
            if (ActivityManagerNative.getDefault().handleApplicationWtf(
                    mApplicationObject, tag, new ApplicationErrorReport.CrashInfo(t))) {
                    mApplicationObject, tag, system, new ApplicationErrorReport.CrashInfo(t))) {
                // The Activity Manager has already written us off -- now exit.
                Process.killProcess(Process.myPid());
                System.exit(10);
Loading