1. 程式人生 > >Android ANR問題原因分析

Android ANR問題原因分析

    final void appNotResponding(ProcessRecord app, ActivityRecord activity,
            ActivityRecord parent, boolean aboveSystem, final String annotation) {
        ArrayList firstPids = new ArrayList(5);
        SparseArray lastPids = new SparseArray(20);
        //[+LEUI][RUBY-13467]zhangp add dump focued window at monkey
        if (ActivityManager.isUserAMonkey() && mWindowManagerService.getFocusedWindowToken() == null) {
            ActivityRecord ar = mStackSupervisor.getFocusedStack().mResumedActivity;
            if (ar != null) {
                Slog.i(TAG, "ANR ***** Current resumed activity window status as below *****");
                mWindowManager.dumpWindowStatus(ar.appToken);
            } else {
                Slog.i(TAG, "ANR ***** Current resumed activity is null *****");
            }

            if (activity != null && ar != null && ar != activity) {
                Slog.i(TAG, "ANR ***** Current anr activity window status as below *****");
                mWindowManager.dumpWindowStatus(activity.appToken);
            } else {
                Slog.i(TAG, "ANR ***** Current anr activity cannot dump *****");
            }
        }
        //[+LEUI]end
        if (mController != null) {
            try {
                // 0 == continue, -1 = kill process immediately
                int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation);
                if (res < 0 && app.pid != MY_PID) {
                    app.kill("anr", true);
                }
            } catch (RemoteException e) {
                mController = null;
                Watchdog.getInstance().setActivityController(null);
            }
        }

        long anrTime = SystemClock.uptimeMillis();
        if (MONITOR_CPU_USAGE) {
            updateCpuStatsNow();
        }

        synchronized (this) {
            // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down.
            if (mShuttingDown) {
                Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation);
                return;
            } else if (app.notResponding) {
                Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation);
                return;
            } else if (app.crashing) {
                Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation);
                return;
            }

            // In case we come through here for the same app before completing
            // this one, mark as anring now so we will bail out.
            app.notResponding = true;

            // Log the ANR to the event log.
            EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid,
                    app.processName, app.info.flags, annotation);

            // Dump thread traces as quickly as we can, starting with "interesting" processes.
            firstPids.add(app.pid);

            int parentPid = app.pid;
            if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid;
            if (parentPid != app.pid) firstPids.add(parentPid);

            if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID);

            for (int i = mLruProcesses.size() - 1; i >= 0; i--) {
                ProcessRecord r = mLruProcesses.get(i);
                if (r != null && r.thread != null) {
                    int pid = r.pid;
                    if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) {
                        if (r.persistent) {
                            firstPids.add(pid);
                        } else {
                            lastPids.put(pid, Boolean.TRUE);
                        }
                    }
                }
            }
        }

        // Log the ANR to the main log.
        StringBuilder info = new StringBuilder();
        info.setLength(0);
        info.append("ANR in ").append(app.processName);
        if (activity != null && activity.shortComponentName != null) {
            info.append(" (").append(activity.shortComponentName).append(")");
        }
        info.append("\n");
        info.append("PID: ").append(app.pid).append("\n");
        if (annotation != null) {
            info.append("Reason: ").append(annotation).append("\n");
        }
        if (parent != null && parent != activity) {
            info.append("Parent: ").append(parent.shortComponentName).append("\n");
        }

        final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true);

        File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids,
                NATIVE_STACKS_OF_INTEREST);

        //[+LEUI][XIII-13037]add
        long percent = processCpuTracker.getCpuPercentByName("system_server");
        if(DEBUG_TRACEVIEW && percent >= 50 ){
            Slog.d(TAG, " debug traceview opened, auto save traceview file because system high cpu:"+percent);
            asyncOpenTraceView(false);
        }//[+LEUI]end

        String cpuInfo = null;
        if (MONITOR_CPU_USAGE) {
            updateCpuStatsNow();
            synchronized (mProcessCpuTracker) {
                cpuInfo = mProcessCpuTracker.printCurrentState(anrTime);
            }
            info.append(processCpuTracker.printCurrentLoad());
            info.append(cpuInfo);
        }

        info.append(processCpuTracker.printCurrentState(anrTime));

        Slog.e(TAG, info.toString());
        if (tracesFile == null) {
            // There is no trace file, so dump (only) the alleged culprit's threads to the log
            Process.sendSignal(app.pid, Process.SIGNAL_QUIT);
        }

        addErrorToDropBox("anr", app, app.processName, activity, parent, annotation,
                cpuInfo, tracesFile, null);

        if (mController != null) {
            try {
                // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately
                int res = mController.appNotResponding(app.processName, app.pid, info.toString());
                if (res != 0) {
                    if (res < 0 && app.pid != MY_PID) {
                        app.kill("anr", true);
                    } else {
                        synchronized (this) {
                            mServices.scheduleServiceTimeoutLocked(app);
                        }
                    }
                    return;
                }
            } catch (RemoteException e) {
                mController = null;
                Watchdog.getInstance().setActivityController(null);
            }
        }

        // Unless configured otherwise, swallow ANRs in background processes & kill the process.
        boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(),
                Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0;

        synchronized (this) {
            mBatteryStatsService.noteProcessAnr(app.processName, app.uid);

            if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) {
                app.kill("bg anr", true);
                return;
            }

            // Set the app's notResponding state, and look up the errorReportReceiver
            makeAppNotRespondingLocked(app,
                    activity != null ? activity.shortComponentName : null,
                    annotation != null ? "ANR " + annotation : "ANR",
                    info.toString());

            //Set the trace file name to app name + current date format to avoid overrinding trace file
            String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null);
            if (tracesPath != null && tracesPath.length() != 0) {
                File traceRenameFile = new File(tracesPath);
                String newTracesPath;
                int lpos = tracesPath.lastIndexOf (".");
                if (-1 != lpos)
                    newTracesPath = tracesPath.substring (0, lpos) + "_" + app.processName + "_" + mTraceDateFormat.format(new Date()) + tracesPath.substring (lpos);
                else
                    newTracesPath = tracesPath + "_" + app.processName;

                traceRenameFile.renameTo(new File(newTracesPath));
            }

            // Bring up the infamous App Not Responding dialog
            Message msg = Message.obtain();
            HashMap map = new HashMap();
            msg.what = SHOW_NOT_RESPONDING_MSG;
            msg.obj = map;
            msg.arg1 = aboveSystem ? 1 : 0;
            map.put("app", app);
            if (activity != null) {
                map.put("activity", activity);
            }

            mUiHandler.sendMessage(msg);
        }
    }

相關推薦

Android ANR日誌分析指南

當你的專案越做越複雜,或者你的使用者達到某個數量級的時候,你的程式碼不小心出現細小的問題,你會收到各種各樣的bug,其中ANR的問題你一定不會陌生。本文將詳細講解ANR的型別、出現的原因、ANR案例詳細分析、經典的案例。 定義 ANR(Application Not Responding) 應用

Android ANR問題分析

備註:展訊平臺 案例分析: 1.等待鎖引起的ANR問題 現在遇到一個Monkey跑出來的Camera bug. 1).找出ANR發生的時間 一般情況下,拿到測試提供的log之後,需要在trace目錄下開啟ANR log檔案(這裡有可能有很多anr日誌檔案,找到和你有關

Android ANR Log分析

1)什麼引發了ANR? 在Android裡,應用程式的響應性是由Activity Manager和WindowManager系統服務監視的。當它監測到以下情況中的一個時,Android就會針對特定的應用程式顯示ANR: 在5秒內沒有響應輸入的事件(例如,按鍵按下,螢幕觸控) BroadcastReceive

ANR原因分析及解決方法

內容目錄 1       ANR是如何產生的 1.1       ANR產生條件 ANR的產生需要同時滿足三個條件: 主執行緒:只有應用程式程序的主執行緒響應超時才會產生ANR;超時時間:產生ANR的上下文不同,超時時間也不同,但只要超過這個時間

android ANR原始碼分析 --- 之一

概述: ANR(ApplicationNot responding),是指應用程式未響應,Android系統對於一些事件需要在一定的時間範圍內完成,如果超過預定時間 能未能得到有效響應或者響應時間過長,都會造成ANR。一般地,這時往往會彈出一個提示框,告知使用者當前xxx未

android ANR異常分析技巧總結

前言 ANR異常是android開發中比較常見的異常之一,最近為了看ANR異常,差了不少資料,現在做一個總結。 本文將從以下幾個角

Android ANR分析實踐(一):北京×××搭建ANR是什麽、產生的原因及如何避免ANR

例如 三種 handler 線程處理 不足 線程阻塞 種類 工具 input 一、 什麽是北京×××搭建 dsluntan.com VX:17061863513ANR ANR,(Application Not Responding) 即應用程序無響應,在android應

Android ANR問題原因分析

final void appNotResponding(ProcessRecord app, ActivityRecord activity, ActivityRecord parent, boolean aboveSystem, final String annotation

Android ANR產生的原因以及其定位分析

前言    ANR是Android中一個獨有的概念,它的全稱是Application Not Responding(應用程式無響應)。    相信從事Android開發的同學,或多或少都遇到過,對於

Android 4.X 系統加載 so 失敗的原因分析

tabs mod ext 問題 用戶 統計數據 crash 情況 text 1 so 加載過程 so 加載的過程可以參考小米的系統工程師的文章loadLibrary動態庫加載過程分析 2 問題分析 2.1 問題 年前項目裏新加了一個 so庫,但發現native 方法的找不到

android anr分析

感知 pda destroy waiting query kill 事件機制 卡住 targe 轉自:https://blog.csdn.net/fishmai/article/details/71077047 ANR簡介 ANR,是“Applic

Android ANR 分析 /data/anr/trace.txt 該文件記錄了產生ANR的函數堆棧可以幫助分析

threads closed 格式 activity andro mpstat 內存 進程 repeat Log 在android中的地位非常重要,要是作為一個android程序員不能過分析log這關,算是android沒有入門吧 。 下面我們就來說說如何處理log文件 。

Android ANR 分析

dal http 但是 tin 輸入 暫停 initial cmd 找到 ANR``Application Not Responding。在Android中,如果一些耗時操作造成主線程阻塞了一定時間,則系統會顯示ANR提示用戶此應用處於未響應的狀態。 ANR ANR出現的原

android ANR、traces檔案獲取及例項分析

前言:前段時間專案開發中遇到anr的問題,時間緊急,一時間又難以定位,通過臨時方法解決後,最近有時間對ANR的問題做一次份細的解決方案,本文中的解決方案是通過綜合其他部落格後自己再通過例項驗證後得出的可行方案,讀者如遇類似問題可做參考,歡迎評論交流。

android anr簡介與traces日誌分析方法

一:什麼是ANR ANR:Application Not Responding,即應用無響應 二:ANR的型別 ANR一般有三種類型: 1:KeyDispatchTimeout(5 seconds) --主要型別 按鍵或觸控事件在特定時間內無響應 2:BroadcastTim

android ANR traces.txt檔案匯出分析

來源:https://blog.csdn.net/qq_31939617/article/details/79756718 一:什麼是ANR ANR:Application Not Responding,即應用無響應,ANR找原因,基本是通過traces.txt檔案分析的 先說發生ANR後,如何匯出tra

android ANR traces.txt文件導出分析

txt net ace cat 文件 手機 可能 模式 ati 來源:https://blog.csdn.net/qq_31939617/article/details/79756718 一:什麽是ANR ANR:Application Not Responding,即應用

如何分析解決Android ANR

來自: http://blog.csdn.net/tjy1985/article/details/6777346 http://blog.csdn.net/tjy1985/article/details/6777355 http://blog.csdn.net/tjy1985

Android Studio中使用git功能無法clone原因分析

  最近在使用git的時候發現一個非常詭異的問題,我用cmd命令列可以進行clone,push,pull等操作時都可以完美的成功,但是換到Android Studio中進行這些與遠端庫的操作的時候,就是各種失敗。。。。   一開始以為是ssh key出現了問

Android重啟原因分析

重啟原因分類 1.上層造成重啟 system_server被殺watchdog重啟重要執行緒阻塞2.kernel造成重啟 空指標非法地址3.kernel watchdog造成重啟,原因不確定 記憶體原因nand驅動log檢視步驟及關鍵字 1. 重啟後的kernel.log或