19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* 29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2006 The Android Open Source Project 39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License. 69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at 79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * 109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and 149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License. 159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */ 169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpackage com.android.server.am; 189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 199046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roosimport com.android.internal.logging.MetricsLogger; 20383db5ebcc3a4a615faf249bf4f126f42e80b82eTamas Berghammerimport com.android.internal.logging.nano.MetricsProto; 219046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos 22f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazskiimport android.content.ActivityNotFoundException; 239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.content.Context; 24f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazskiimport android.content.DialogInterface; 25f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazskiimport android.content.Intent; 269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.content.res.Resources; 27a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport android.os.Bundle; 289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.os.Handler; 299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport android.os.Message; 30890f1f372e9bdaeefc1707acbbd97de95709db39Adrian Roosimport android.text.BidiFormatter; 318a9b22056b13477f59df934928c00c58b5871c95Joe Onoratoimport android.util.Slog; 32a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport android.view.LayoutInflater; 33a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport android.view.View; 345fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackbornimport android.view.WindowManager; 35a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport android.widget.FrameLayout; 36a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport android.widget.TextView; 379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 38a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosimport static com.android.server.am.ActivityManagerService.IS_USER_BUILD; 39a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 40a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roosfinal class AppNotRespondingDialog extends BaseErrorDialog implements View.OnClickListener { 41f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski private static final String TAG = "AppNotRespondingDialog"; 42f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski 43f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski // Event 'what' codes 44f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski static final int FORCE_CLOSE = 1; 45f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski static final int WAIT = 2; 46f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski static final int WAIT_AND_REPORT = 3; 47f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski 489046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos public static final int CANT_SHOW = -1; 499046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos public static final int ALREADY_SHOWING = -2; 509046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos 519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project private final ActivityManagerService mService; 529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project private final ProcessRecord mProc; 53a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project public AppNotRespondingDialog(ActivityManagerService service, Context context, 555fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn ProcessRecord app, ActivityRecord activity, boolean aboveSystem) { 569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project super(context); 57a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project mService = service; 599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project mProc = app; 609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project Resources res = context.getResources(); 61a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project setCancelable(false); 639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project int resid; 659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project CharSequence name1 = activity != null 669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project ? activity.info.loadLabel(context.getPackageManager()) 679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project : null; 689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project CharSequence name2 = null; 699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if ((app.pkgList.size() == 1) && 709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project (name2=context.getPackageManager().getApplicationLabel(app.info)) != null) { 719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (name1 != null) { 729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project resid = com.android.internal.R.string.anr_activity_application; 739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } else { 749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project name1 = name2; 759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project name2 = app.processName; 769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project resid = com.android.internal.R.string.anr_application_process; 779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } else { 799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (name1 != null) { 809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project name2 = app.processName; 819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project resid = com.android.internal.R.string.anr_activity_process; 829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } else { 839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project name1 = app.processName; 849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project resid = com.android.internal.R.string.anr_process; 859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 88890f1f372e9bdaeefc1707acbbd97de95709db39Adrian Roos BidiFormatter bidi = BidiFormatter.getInstance(); 89890f1f372e9bdaeefc1707acbbd97de95709db39Adrian Roos 90a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos setTitle(name2 != null 91890f1f372e9bdaeefc1707acbbd97de95709db39Adrian Roos ? res.getString(resid, bidi.unicodeWrap(name1.toString()), bidi.unicodeWrap(name2.toString())) 92890f1f372e9bdaeefc1707acbbd97de95709db39Adrian Roos : res.getString(resid, bidi.unicodeWrap(name1.toString()))); 939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 945fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn if (aboveSystem) { 955fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 965fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn } 975fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn WindowManager.LayoutParams attrs = getWindow().getAttributes(); 985fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn attrs.setTitle("Application Not Responding: " + app.info.processName); 9995c42974f719d1fac90fc0438eac778e9795681fAdam Lesinski attrs.privateFlags = WindowManager.LayoutParams.PRIVATE_FLAG_SYSTEM_ERROR | 10095c42974f719d1fac90fc0438eac778e9795681fAdam Lesinski WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 1015fe7e2a3043d6a8ca933c77ccf95c791b57b221aDianne Hackborn getWindow().setAttributes(attrs); 1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 1039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 104a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos @Override 105a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos protected void onCreate(Bundle savedInstanceState) { 106a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos super.onCreate(savedInstanceState); 10751efddbd3bb304de2dd47fa8cd1114ac555958bbAlan Viverette final FrameLayout frame = findViewById(android.R.id.custom); 108a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos final Context context = getContext(); 109a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos LayoutInflater.from(context).inflate( 110a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos com.android.internal.R.layout.app_anr_dialog, frame, true); 111a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 11251efddbd3bb304de2dd47fa8cd1114ac555958bbAlan Viverette final TextView report = findViewById(com.android.internal.R.id.aerr_report); 113a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos report.setOnClickListener(this); 114a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos final boolean hasReceiver = mProc.errorReportReceiver != null; 115a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos report.setVisibility(hasReceiver ? View.VISIBLE : View.GONE); 11651efddbd3bb304de2dd47fa8cd1114ac555958bbAlan Viverette final TextView close = findViewById(com.android.internal.R.id.aerr_close); 117a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos close.setOnClickListener(this); 11851efddbd3bb304de2dd47fa8cd1114ac555958bbAlan Viverette final TextView wait = findViewById(com.android.internal.R.id.aerr_wait); 119a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos wait.setOnClickListener(this); 120a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 121a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos findViewById(com.android.internal.R.id.customPanel).setVisibility(View.VISIBLE); 122a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos } 123a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 124a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos @Override 125a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos public void onClick(View v) { 126a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos switch (v.getId()) { 127a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos case com.android.internal.R.id.aerr_report: 128a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos mHandler.obtainMessage(WAIT_AND_REPORT).sendToTarget(); 129a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos break; 130a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos case com.android.internal.R.id.aerr_close: 131a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos mHandler.obtainMessage(FORCE_CLOSE).sendToTarget(); 132a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos break; 133a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos case com.android.internal.R.id.aerr_wait: 134a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos mHandler.obtainMessage(WAIT).sendToTarget(); 135a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos break; 136a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos default: 137a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos break; 138a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos } 1399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 1409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project 1419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project private final Handler mHandler = new Handler() { 1429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project public void handleMessage(Message msg) { 143f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski Intent appErrorIntent = null; 1449046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos 1459046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos MetricsLogger.action(getContext(), MetricsProto.MetricsEvent.ACTION_APP_ANR, 1469046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos msg.what); 1479046222cb2b1bd57278ddbf71d9f628f8dd254aeAdrian Roos 1489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project switch (msg.what) { 149f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski case FORCE_CLOSE: 1509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // Kill the application. 15142471dd5552a346dd82a58a663159875ccc4fb79Dan Egnor mService.killAppAtUsersRequest(mProc, AppNotRespondingDialog.this); 1529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project break; 153f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski case WAIT_AND_REPORT: 154f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski case WAIT: 1559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project // Continue waiting for the application. 1569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project synchronized (mService) { 1579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project ProcessRecord app = mProc; 158f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski 159f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski if (msg.what == WAIT_AND_REPORT) { 16020d7df3c3ff0000678a208b25fcf7ddf90c5abe4Adrian Roos appErrorIntent = mService.mAppErrors.createAppErrorIntentLocked(app, 16141a9fd55ac0f50afb3d70b1ba0786dbb316eebceJacek Surazski System.currentTimeMillis(), null); 162f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski } 163f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski 1649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project app.notResponding = false; 1659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project app.notRespondingReport = null; 1669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project if (app.anrDialog == AppNotRespondingDialog.this) { 1679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project app.anrDialog = null; 1689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 1692be00933163bb2bfa6b43cf2e1ddde7c284c7c4cDianne Hackborn mService.mServices.scheduleServiceTimeoutLocked(app); 1709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 1719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project break; 1729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 173f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski 174f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski if (appErrorIntent != null) { 175f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski try { 176f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski getContext().startActivity(appErrorIntent); 177f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski } catch (ActivityNotFoundException e) { 1788a9b22056b13477f59df934928c00c58b5871c95Joe Onorato Slog.w(TAG, "bug report receiver dissappeared", e); 179f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski } 180f5b9c72022f574417862e064cc0fdd8ea2d846dcJacek Surazski } 181a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos 182a85a2c63f191ae8c567ba6845c063cbe3dd750fcAdrian Roos dismiss(); 1839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project } 1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project }; 1859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} 186