Przeczytaj raporty o błędach

Błędy są rzeczywistością w każdym typie rozwoju, a raporty o błędach mają kluczowe znaczenie dla identyfikowania i rozwiązywania problemów. Wszystkie wersje Androida obsługują przechwytywanie raportów o błędach za pomocą Android Debug Bridge (adb) ; Wersje Androida 4.2 i nowsze obsługują opcję programisty umożliwiającą sporządzanie raportów o błędach i udostępnianie ich za pośrednictwem poczty elektronicznej, dysku itp.

Raporty o błędach Androida zawierają dane dumpsys , dumpstate i logcat w formacie tekstowym (.txt), co pozwala łatwo wyszukiwać określone treści. Poniższe sekcje szczegółowo opisują komponenty raportów o błędach, opisują typowe problemy oraz zawierają pomocne wskazówki i polecenia grep dotyczące znajdowania dzienników powiązanych z tymi błędami. Większość sekcji zawiera także przykłady poleceń grep oraz danych wyjściowych i/lub wyników dumpsys .

Logcat

Dziennik logcat to oparty na ciągach zrzut wszystkich informacji logcat . Część systemowa jest zarezerwowana dla frameworka i ma dłuższą historię niż główna , która zawiera wszystko inne. Każdy wiersz zazwyczaj zaczyna się od timestamp UID PID TID log-level , chociaż identyfikator UID może nie być wyświetlany w starszych wersjach Androida.

Zobacz dziennik zdarzeń

Ten dziennik zawiera ciągi reprezentujące komunikaty dziennika w formacie binarnym. Jest mniej zaszumiony niż dziennik logcat , ale jest też nieco trudniejszy do odczytania. Przeglądając dzienniki zdarzeń, możesz przeszukać tę sekcję pod kątem konkretnego identyfikatora procesu (PID), aby zobaczyć, co proces robił. Podstawowy format to: timestamp PID TID log-level log-tag tag-values .

Poziomy dziennika obejmują:

  • V: szczegółowe
  • D: debuguj
  • Ja: informacja
  • W: ostrzeżenie
  • E: błąd

Inne przydatne znaczniki dziennika zdarzeń można znaleźć w pliku /services/core/java/com/android/server/EventLogTags.logtags .

Błędy ANR i zakleszczenia

Raporty o błędach mogą pomóc w zidentyfikowaniu przyczyny błędów i zakleszczeń aplikacji (ANR) .

Zidentyfikuj aplikacje, które nie odpowiadają

Gdy aplikacja nie odpowiada w określonym czasie, zwykle z powodu zablokowanego lub zajętego wątku głównego, system przerywa proces i zrzuca stos do /data/anr . Aby odkryć winowajcę błędu ANR, wpisz grep dla am_anr w binarnym dzienniku zdarzeń.

Możesz także grepować w poszukiwaniu ANR in dzienniku logcat , który zawiera więcej informacji o tym, co używało procesora w momencie wystąpienia błędu ANR.

Znajdź ślady stosu

Często można znaleźć ślady stosu odpowiadające ANR. Upewnij się, że sygnatura czasowa i PID w śladach maszyny wirtualnej odpowiadają badanemu ANR, a następnie sprawdź główny wątek procesu. Pamiętać:

  • Główny wątek informuje tylko o tym, co wątek robił w momencie wystąpienia błędu ANR, co może, ale nie musi, odpowiadać prawdziwej przyczynie błędu ANR. (Stos w raporcie o błędzie może być niewinny; coś innego mogło utknąć na długi czas — ale nie na tyle długo, aby wystąpił ANR — zanim zostanie odblokowany.)
  • Może istnieć więcej niż jeden zestaw śladów stosu ( VM TRACES JUST NOW i VM TRACES AT LAST ANR ). Upewnij się, że przeglądasz właściwą sekcję.

Znajdź zakleszczenia

Zakleszczenia często pojawiają się najpierw jako błędy ANR, ponieważ wątki utknęły. Jeśli zakleszczenie dotrze do serwera systemowego, watchdog ostatecznie go zabije, co doprowadzi do wpisu w dzienniku podobnego do: WATCHDOG KILLING SYSTEM PROCESS . Z punktu widzenia użytkownika urządzenie uruchamia się ponownie, chociaż technicznie rzecz biorąc jest to restart w czasie wykonywania, a nie prawdziwy restart.

  • Podczas restartu środowiska wykonawczego serwer systemowy umiera i zostaje ponownie uruchomiony; użytkownik widzi powrót urządzenia do animacji rozruchu.
  • Podczas ponownego uruchamiania jądro uległo awarii; użytkownik widzi, że na urządzeniu powraca logo startowe Google.

Aby znaleźć zakleszczenia, sprawdź sekcje śladów VM pod kątem wzorca wątku A oczekującego na coś trzymanego przez wątek B, który z kolei czeka na coś trzymanego przez wątek A.

Zajęcia

Działanie to komponent aplikacji udostępniający ekran, na którym użytkownik może wykonać jakąś czynność, np. wybrać numer, zrobić zdjęcie, wysłać wiadomość e-mail itp. Z perspektywy raportu o błędzie działanie to pojedyncza, konkretna czynność, którą może wykonać użytkownik , co sprawia, że ​​zlokalizowanie aktywności, na której koncentrowano się podczas awarii, jest bardzo ważne. Działania (za pośrednictwem ActivityManager) uruchamiają procesy, więc zlokalizowanie wszystkich zatrzymań i startów procesów dla danego działania może również pomóc w rozwiązywaniu problemów.

Zobacz ukierunkowane działania

Aby wyświetlić historię ukierunkowanych działań, wyszukaj am_focused_activity .

Rozpoczyna się proces przeglądania

Aby wyświetlić historię uruchomień procesów, wyszukaj opcję Start proc .

Sprawdź, czy urządzenie się zawiesza

Aby ustalić, czy urządzenie się zawiesza , sprawdź, czy w krótkim czasie nie nastąpił nietypowy wzrost aktywności wokół am_proc_died i am_proc_start .

Pamięć

Ponieważ urządzenia z Androidem często mają ograniczoną pamięć fizyczną, zarządzanie pamięcią o dostępie swobodnym (RAM) ma kluczowe znaczenie. Raporty o błędach zawierają kilka wskaźników braku pamięci, a także stan zrzutu, który zapewnia migawkę pamięci.

Zidentyfikuj brak pamięci

Mało pamięci może spowodować awarię systemu, ponieważ zabija niektóre procesy, aby zwolnić pamięć, ale nadal uruchamia inne procesy. Aby wyświetlić potwierdzające dowody małej ilości pamięci, sprawdź koncentrację wpisów am_proc_died i am_proc_start w dzienniku zdarzeń binarnych.

Mało pamięci może również spowolnić przełączanie zadań i udaremnić próby powrotu (ponieważ zadanie, do którego użytkownik próbował wrócić, zostało zakończone). Jeśli program uruchamiający został wyłączony, uruchamia się ponownie, gdy użytkownik dotknie przycisku strony głównej, a dzienniki pokazują, że program uruchamiający ponownie załadował swoją zawartość.

Zobacz wskaźniki historyczne

Wpis am_low_memory w dzienniku zdarzeń binarnych wskazuje, że ostatni proces buforowany został uszkodzony. Następnie system zaczyna zabijać usługi.

Zobacz wskaźniki bicia

Inne wskaźniki awarii systemu (stronicowanie, bezpośrednie odzyskiwanie itp.) obejmują cykle zużywania kswapd , kworker i mmcqd . (Pamiętaj, że gromadzony raport o błędach może mieć wpływ na wskaźniki rzucania.)

Dzienniki ANR mogą zapewnić podobną migawkę pamięci.

Uzyskaj migawkę pamięci

Migawka pamięci to stan zrzutu zawierający listę uruchomionych procesów Java i procesów natywnych (więcej informacji można znaleźć w części Wyświetlanie ogólnych alokacji pamięci ). Należy pamiętać, że migawka przedstawia tylko stan w określonym momencie; system mógł być w lepszym (lub gorszym) stanie przed wykonaniem migawki.

Transmisje

Aplikacje generują emisje w celu wysyłania zdarzeń w ramach bieżącej aplikacji lub do innej aplikacji. Odbiorcy transmisji subskrybują określone wiadomości (poprzez filtry), umożliwiając im zarówno słuchanie transmisji, jak i odpowiadanie na nią. Raporty o błędach zawierają informacje o wysłanych i niewysłanych transmisjach, a także listę wszystkich odbiorników słuchających określonej transmisji.

Zobacz historyczne transmisje

Transmisje historyczne to te, które zostały już wysłane, wymienione w odwrotnej kolejności chronologicznej.

Sekcja podsumowująca zawiera przegląd ostatnich 300 transmisji na pierwszym planie i ostatnich 300 transmisji w tle.

Sekcja szczegółów zawiera pełne informacje o ostatnich 50 transmisjach na pierwszym planie i ostatnich 50 transmisjach w tle, a także o odbiornikach każdej transmisji. Odbiorniki posiadające:

  • Wpisy BroadcastFilter są rejestrowane w czasie wykonywania i wysyłane tylko do już uruchomionych procesów.
  • Wpisy ResolveInfo są rejestrowane poprzez wpisy manifestu. ActivityManager uruchamia proces dla każdego ResolveInfo , jeśli nie jest jeszcze uruchomiony.

Zobacz aktywne transmisje

Transmisje aktywne to te, które nie zostały jeszcze wysłane. Duża liczba w kolejce oznacza, że ​​system nie może wysłać transmisji wystarczająco szybko, aby dotrzymać kroku.

Wyświetl słuchaczy transmisji

Aby wyświetlić listę odbiorników nasłuchujących transmisji, sprawdź tabelę rozpoznawania odbiorników w dumpsys activity broadcasts . Poniższy przykład wyświetla wszystkie odbiorniki nasłuchujące USER_PRESENT .

Monitoruj rywalizację

Rejestrowanie rywalizacji monitora może czasami wskazywać na rzeczywistą rywalizację monitora, ale najczęściej wskazuje, że system jest tak obciążony, że wszystko uległo spowolnieniu. Możesz zobaczyć zdarzenia długiego monitora rejestrowane przez ART w systemie lub dzienniku zdarzeń.

W dzienniku systemowym:

10-01 18:12:44.343 29761 29914 W art     : Long monitor contention event with owner method=void android.database.sqlite.SQLiteClosable.acquireReference() from SQLiteClosable.java:52 waiters=0 for 3.914s

W dzienniku zdarzeń:

10-01 18:12:44.364 29761 29914 I dvm_lock_sample: [com.google.android.youtube,0,pool-3-thread-9,3914,ScheduledTaskMaster.java,138,SQLiteClosable.java,52,100]

Kompilacja tła

Kompilacja może być kosztowna i ładować urządzenie.

Kompilacja może odbywać się w tle podczas pobierania aktualizacji sklepu Google Play. W takim przypadku wiadomości z aplikacji sklepu Google Play ( finsky ) i installd aplikacji pojawiają się przed wiadomościami dex2oat .

Kompilacja może również odbywać się w tle, gdy aplikacja ładuje plik dex, który nie został jeszcze skompilowany. W takim przypadku nie zobaczysz dziennika finsky ani installd .

Narracja

Ustalenie narracji problemu (jak się zaczął, co się stało, jak zareagował system) wymaga solidnego harmonogramu wydarzeń. Możesz użyć informacji zawartych w raporcie o błędzie, aby zsynchronizować osie czasu w wielu dziennikach i określić dokładną sygnaturę czasową raportu o błędzie.

Synchronizuj osie czasu

Raport o błędzie odzwierciedla wiele równoległych osi czasu: dziennik systemu, dziennik zdarzeń, dziennik jądra i wiele wyspecjalizowanych osi czasu dla emisji, statystyki baterii itp. Niestety osie czasu są często zgłaszane przy użyciu różnych podstaw czasu.

Sygnatury czasowe systemu i dziennika zdarzeń znajdują się w tej samej strefie czasowej co użytkownik (podobnie jak większość innych sygnatur czasowych). Na przykład, gdy użytkownik dotknie przycisku strony głównej, dziennik systemowy zgłasza:

10-03 17:19:52.939  1963  2071 I ActivityManager: START u0 {act=android.intent.action.MAIN cat=[android.intent.category.HOME] flg=0x10200000 cmp=com.google.android.googlequicksearchbox/com.google.android.launcher.GEL (has extras)} from uid 1000 on display 0

W przypadku tej samej akcji dziennik zdarzeń zgłasza:

10-03 17:19:54.279  1963  2071 I am_focused_activity: [0,com.google.android.googlequicksearchbox/com.google.android.launcher.GEL]

Dzienniki jądra ( dmesg ) używają innej podstawy czasu, oznaczając elementy dziennika sekundami od zakończenia programu ładującego. Aby zarejestrować tę skalę czasową w innych skalach czasowych, wyszukaj komunikaty o zawieszeniu wyjścia i zawieszeniu wejścia :

<6>[201640.779997] PM: suspend exit 2015-10-03 19:11:06.646094058 UTC
…
<6>[201644.854315] PM: suspend entry 2015-10-03 19:11:10.720416452 UTC

Ponieważ dzienniki jądra mogą nie uwzględniać czasu zawieszenia, należy rejestrować dziennik fragmentarycznie pomiędzy komunikatami o zawieszeniu i wyjściu. Ponadto dzienniki jądra korzystają ze strefy czasowej UTC i muszą być dostosowane do strefy czasowej użytkownika.

Określ czas zgłoszenia błędu

Aby ustalić, kiedy sporządzono raport o błędzie, najpierw sprawdź dziennik systemowy (Logcat) pod kątem dumpstate: begin :

10-03 17:19:54.322 19398 19398 I dumpstate: begin

Następnie sprawdź znaczniki czasu dziennika jądra ( dmesg ) pod kątem komunikatu Starting service 'bugreport' :

<5>[207064.285315] init: Starting service 'bugreport'...

Pracuj wstecz, aby powiązać oba zdarzenia, pamiętając o zastrzeżeniach wymienionych w części Synchronizowanie osi czasu . Chociaż po zainicjowaniu raportu o błędzie wiele się dzieje, większość działań nie jest zbyt użyteczna, ponieważ samo przyjęcie raportu o błędzie znacznie obciąża system.

Moc

Dziennik zdarzeń zawiera stan zasilania ekranu, gdzie 0 oznacza ekran wyłączony, 1 ekran włączony, a 2 oznacza włączenie blokady klawiatury.

Raporty o błędach zawierają także statystyki dotyczące blokad wybudzania – mechanizmu stosowanego przez twórców aplikacji w celu wskazania, że ​​ich aplikacja musi mieć włączone urządzenie. (Aby uzyskać szczegółowe informacje na temat blokad wybudzania, zobacz PowerManager.WakeLock i Keep the CPU on .)

Zagregowane statystyki czasu trwania blokady wybudzania śledzą tylko czas, w którym blokada wybudzania faktycznie odpowiada za utrzymanie urządzenia w stanie czuwania, i nie uwzględniają czasu, w którym ekran jest włączony. Ponadto, jeśli jednocześnie utrzymuje się wiele blokad wybudzania, czas trwania blokady wybudzania jest rozkładany na te blokady wybudzania.

Aby uzyskać dodatkową pomoc w wizualizacji stanu zasilania, użyj Battery Historian , narzędzia Google typu open source umożliwiającego analizowanie zużycia baterii przy użyciu plików raportów o błędach systemu Android.

Pakiety

Sekcja DUMP OF SERVICE package zawiera wersje aplikacji (i inne przydatne informacje).

Procesy

Raporty o błędach zawierają ogromną ilość danych dotyczących procesów, w tym czas rozpoczęcia i zakończenia, długość czasu działania, powiązane usługi, wynik oom_adj itp. Aby uzyskać szczegółowe informacje na temat zarządzania procesami przez Androida, zobacz Procesy i wątki .

Określ czas działania procesu

Sekcja procstats zawiera kompletne statystyki dotyczące czasu działania procesów i powiązanych z nimi usług. Aby uzyskać szybkie, czytelne dla człowieka podsumowanie, wyszukaj AGGREGATED OVER , aby wyświetlić dane z ostatnich trzech lub 24 godzin, a następnie wyszukaj Summary: aby wyświetlić listę procesów, czas działania tych procesów przy różnych priorytetach i ich pamięć RAM użycie sformatowane jako min-średnia-maks PSS/min-średnia-maks USS.

Powody działania procesu

Sekcja dumpsys activity processes zawiera listę wszystkich aktualnie uruchomionych procesów uporządkowanych według wyniku oom_adj (Android wskazuje ważność procesu, przypisując procesowi wartość oom_adj , która może być dynamicznie aktualizowana przez ActivityManager). Dane wyjściowe są podobne do wyników migawki pamięci , ale zawierają dodatkowe informacje o przyczynie uruchomienia procesu. W poniższym przykładzie pogrubione wpisy wskazują, że proces gms.persistent działa z priorytetem vis (visible), ponieważ proces systemowy jest powiązany ze swoją NetworkLocationService .

Skany

Wykonaj poniższe czynności, aby zidentyfikować aplikacje wykonujące nadmierne skanowanie Bluetooth Low Energy (BLE):

  • Znajdź komunikaty dziennika dla BluetoothLeScanner :
    $ grep 'BluetoothLeScanner' ~/downloads/bugreport.txt
    07-28 15:55:19.090 24840 24851 D BluetoothLeScanner: onClientRegistered() - status=0 clientIf=5
    
  • Znajdź identyfikator PID w komunikatach dziennika. W tym przykładzie „24840” i „24851” to PID (identyfikator procesu) i TID (identyfikator wątku).
  • Znajdź aplikację powiązaną z PID:
    PID #24840: ProcessRecord{4fe996a 24840:com.badapp/u0a105}
    

    W tym przykładzie nazwa pakietu to com.badapp .

  • Wyszukaj nazwę pakietu w Google Play, aby zidentyfikować odpowiedzialną aplikację: https://play.google.com/store/apps/details?id=com.badapp .

Uwaga : w przypadku urządzeń z systemem Android 7.0 system zbiera dane do skanów BLE i kojarzy te działania z aplikacją inicjującą. Aby uzyskać szczegółowe informacje, zobacz Skanowanie przy niskim zużyciu energii (LE) i Bluetooth .