Wiadomości o usłudze

Zwiększanie wydajności Androida: przedstawiamy AutoFDO dla jądra

Czas czytania: 4 min
Wyświetl profil użytkownika Charles Munger
Yabin Cui Inżynier oprogramowania

Jesteśmy zespołem odpowiedzialnym za łańcuch narzędzi LLVM na Androida. Jednym z naszych priorytetów jest poprawa wydajności Androida dzięki technikom optymalizacji w ekosystemie LLVM. Cały czas szukamy sposobów na to, aby Android działał szybciej, płynniej i wydajniej. Chociaż większość prac optymalizacyjnych odbywa się w przestrzeni użytkownika, jądro pozostaje sercem systemu. Z przyjemnością informujemy, że wprowadzamy do jądra Androida automatyczną optymalizację na podstawie informacji zwrotnych (AutoFDO), aby zapewnić użytkownikom znaczny wzrost wydajności.

Czym jest AutoFDO?

Podczas standardowej kompilacji oprogramowania kompilator podejmuje tysiące drobnych decyzji, takich jak to, czy wstawić funkcję i która gałąź warunku zostanie prawdopodobnie wybrana, na podstawie statycznych wskazówek dotyczących kodu.Chociaż te heurystyki są przydatne, nie zawsze dokładnie przewidują wykonywanie kodu podczas rzeczywistego korzystania z telefonu.

AutoFDO zmienia to, wykorzystując rzeczywiste wzorce wykonywania do kierowania kompilatorem. Wzorce te reprezentują najczęstsze ścieżki wykonywania instrukcji, które kod przyjmuje podczas rzeczywistego użytkowania, zarejestrowane przez historię rozgałęzień procesora. Te dane można zbierać z urządzeń we flocie, ale w przypadku jądra syntetyzujemy je w środowisku laboratoryjnym, używając reprezentatywnych zbiorów zadań, takich jak uruchamianie 100 najpopularniejszych aplikacji. Do zbierania tych danych używamy profilera próbkowania, który identyfikuje, które części kodu są „gorące” (często używane), a które „zimne”. Gdy przebudowujemy jądro za pomocą tych profili, kompilator może podejmować znacznie mądrzejsze decyzje dotyczące optymalizacji, dostosowane do rzeczywistych zadań Androida.

Aby zrozumieć wpływ tej optymalizacji, weź pod uwagę te kluczowe fakty:

  • Na Androidzie jądro odpowiada za około 40% czasu pracy procesora.
  • Używamy już AutoFDO do optymalizacji natywnych plików wykonywalnych i bibliotek w przestrzeni użytkownika, co pozwala nam skrócić czas uruchamiania aplikacji na zimno o około 4% i czas uruchamiania urządzenia o 1%.

Rzeczywiste korzyści związane z wydajnością

Dzięki wykorzystaniu profili z kontrolowanych środowisk laboratoryjnych zaobserwowaliśmy znaczną poprawę kluczowych wskaźników Androida. Te profile zostały zebrane podczas indeksowania i uruchamiania aplikacji, a następnie zmierzone na urządzeniach Pixel z jądrami 6.1, 6.6 i 6.12.

Poniżej wymieniono najbardziej zauważalne ulepszenia. Szczegółowe informacje o profilach AutoFDO dla tych wersji jądra znajdziesz w odpowiednich repozytoriach jądra Androida dla jądra android16-6.12 i android15-6.6.

boosting_2.png

To nie są tylko teoretyczne liczby. Przekłada się to na szybsze działanie interfejsu, szybsze przełączanie aplikacji, dłuższą żywotność baterii i ogólnie bardziej responsywne urządzenie dla użytkownika.

Jak to działa: potok

Nasza strategia wdrażania obejmuje zaawansowany potok, który zapewnia aktualność profili i stabilność wydajności.

boosting_3.png

Krok 1. Zbieranie informacji do profilu

Do profilowania plików binarnych w przestrzeni użytkownika używamy naszej wewnętrznej floty testowej, ale w przypadku ogólnego obrazu jądra (GKI) przeszliśmy na kontrolowane środowisko laboratoryjne. Oddzielenie profilowania od cyklu wydawania urządzeń umożliwia elastyczne i natychmiastowe aktualizacje niezależnie od wdrożonych wersji jądra. Co ważne, testy potwierdzają, że te dane laboratoryjne zapewniają wzrost wydajności porównywalny z tym, który można uzyskać w przypadku rzeczywistych flot.

  • Narzędzia i środowisko: flashujemy urządzenia testowe z najnowszym obrazem jądra i używamy narzędzia simpleperf do przechwytywania strumieni wykonywania instrukcji. Ten proces opiera się na możliwościach sprzętowych, które pozwalają rejestrować historię rozgałęzień, w szczególności na rozszerzeniach  ARM Embedded Trace Extension (ETE) i ARM Trace Buffer Extension (TRBE) na urządzeniach Pixel.
  • Zadania: tworzymy reprezentatywne zadanie, korzystając ze 100 najpopularniejszych aplikacji z zestawu testów zgodności aplikacji na Androida (C-Suite). Aby uzyskać jak najdokładniejsze dane, skupiamy się na:
    • Uruchamianie aplikacji: optymalizacja pod kątem najbardziej widocznych opóźnień dla użytkowników
    • AI-Driven App Crawling: symulowanie ciągłych, ewoluujących interakcji użytkownika.
    • Monitorowanie całego systemu: rejestrowanie nie tylko działań aplikacji na pierwszym planie, ale też krytycznych zadań w tle i komunikacji między procesami.
  • Weryfikacja: ten syntetyczny zbiór zadań wykazuje 85% podobieństwa do wzorców wykonywania zebranych z naszej wewnętrznej floty.
  • Dane docelowe: powtarzając te testy wystarczająco dużo razy, uzyskujemy bardzo dokładne wzorce wykonywania, które odzwierciedlają rzeczywiste interakcje użytkowników z najpopularniejszymi aplikacjami. Ponadto ta rozszerzalna platforma umożliwia nam bezproblemową integrację dodatkowych zbiorów zadań i testów porównawczych w celu rozszerzenia zakresu działania.

Krok 2. Przetwarzanie profilu

Przetwarzamy nieprzetworzone dane śledzenia, aby upewnić się, że są czyste, skuteczne i gotowe do kompilacji.

  • Agregacja: konsolidujemy dane z wielu testów i urządzeń w jeden widok systemu.
  • Konwersja: konwertujemy nieprzetworzone logi śledzenia na format profilu AutoFDO, odfiltrowując w razie potrzeby niechciane symbole.
  • Przycinanie profilu: przycinamy profile, aby usunąć dane dotyczące „zimnych” funkcji, co pozwala im korzystać ze standardowej optymalizacji. Zapobiega to regresjom w rzadko używanym kodzie i niepotrzebnemu zwiększaniu rozmiaru pliku binarnego.

Krok 3. Testowanie profilu

Przed wdrożeniem profile przechodzą rygorystyczną weryfikację, aby zapewnić stałą wydajność bez ryzyka dla stabilności.

  • Analiza profilu i plików binarnych: dokładnie porównujemy zawartość nowego profilu (w tym funkcje hot, liczbę próbek i rozmiar profilu) z poprzednimi wersjami. Używamy też profilu do utworzenia nowego obrazu jądra, analizując pliki binarne, aby upewnić się, że zmiany w sekcji tekstowej są zgodne z oczekiwaniami.
  • Weryfikacja wydajności: przeprowadzamy ukierunkowane testy porównawcze nowego obrazu jądra. Potwierdza to, że utrzymuje on poprawę skuteczności uzyskaną dzięki poprzednim wartościom bazowym.

Ciągłe aktualizacje

Kod z czasem naturalnie „dryfuje”, więc profil statyczny ostatecznie straciłby skuteczność. Aby utrzymać najwyższą wydajność, stale uruchamiamy potok, aby regularnie wprowadzać aktualizacje:

  • Regularne odświeżanie: przed każdą wersją GKI odświeżamy profile w gałęziach LTS jądra Androida, aby każda kompilacja zawierała najnowsze dane profilu.
  • Przyszłe rozszerzenie: obecnie dostarczamy te aktualizacje do gałęzi android16-6.12 i android15-6.6, a w przyszłości rozszerzymy obsługę na nowsze wersje GKI, takie jak nadchodząca wersja android17-6.18.

Zapewnianie stabilności

Często pojawia się pytanie, czy optymalizacja na podstawie profilu nie powoduje problemów ze stabilnością. AutoFDO wpływa głównie na heurystykę kompilatora, np. na wstawianie funkcji i układ kodu, a nie na logikę kodu źródłowego, dzięki czemu zachowuje integralność funkcjonalną jądra. Ta technologia została już sprawdzona na dużą skalę i od lat jest standardową optymalizacją bibliotek platformy Androida, ChromeOS i własnej infrastruktury serwerowej Google.

Aby zapewnić spójne działanie, stosujemy strategię „domyślnie konserwatywną”. Funkcje, które nie są uwzględnione w naszych profilach o wysokiej dokładności, są optymalizowane za pomocą standardowych metod kompilatora. Dzięki temu „zimne” lub rzadko wykonywane części jądra zachowują się dokładnie tak, jak w standardowej kompilacji, co zapobiega pogorszeniu wydajności lub nieoczekiwanym zachowaniom w przypadkach skrajnych.

Co dalej

Obecnie wdrażamy AutoFDO w gałęziach android16-6.12 i android15-6.6. Poza tym początkowym wdrożeniem widzimy kilka obiecujących sposobów na dalsze ulepszanie tej technologii:

  • Większy zasięg: planujemy wdrożyć profile AutoFDO w nowszych wersjach jądra GKI i dodatkowych środowiskach docelowych kompilacji poza obecną obsługą aarch64.
  • Optymalizacja modułów GKI: obecnie nasza optymalizacja koncentruje się na głównym pliku binarnym jądra (vmlinux). Rozszerzenie AutoFDO na moduły GKI może przynieść korzyści w zakresie wydajności większej części podsystemu jądra.
  • Obsługa modułów dostawców: chcemy też obsługiwać AutoFDO w przypadku modułów dostawców utworzonych za pomocą pakietu Driver Development Kit (DDK). Dzięki obsłudze dostępnej już w naszym systemie kompilacji (Kleaf) i narzędziach do profilowania (simpleperf) dostawcy mogą stosować te same techniki optymalizacji do swoich sterowników sprzętowych.
  • Szerszy zakres profili: istnieje możliwość zbierania profili z szerszego zakresu głównych ścieżek użytkownika w celu ich optymalizacji.

Dzięki wprowadzeniu AutoFDO do jądra Androida zapewniamy, że fundament systemu operacyjnego jest zoptymalizowany pod kątem codziennego korzystania z urządzenia.

Autor:
Czytaj dalej