2009-07-07 18 views
5

Używam Yourkit 8.0 do profilowania matematycznie intensywnej aplikacji działającej pod Mac OS X (10.5.7, Apple JDK 1.6.0_06-b06-57) i zauważyłem pewne dziwne zachowanie w wynikach profilowania procesora.Profilowanie natywnych metod w Javie - dziwne wyniki

Na przykład - wykonałem próbę profilowania za pomocą próbkowania, które zgłosiło, że 40% 10-minutowego czasu działania aplikacji zostało wydane w metodzie StrictMath.atan. Znalazłem to zagadkowe, ale wziąłem to pod uwagę i spędziłem trochę czasu zastępując atan wyjątkowo skrajnym wielomianem.

Kiedy ponownie uruchomiłem aplikację, zajęło to prawie dokładnie tyle samo co poprzednio (10 minut) - ale mój zamiennik atanu nie pojawił się w wynikach profilowania. Zamiast tego, wartości procentowe runtime innych głównych hotspotów po prostu wzrosły, aby to nadrobić.

Podsumowując

wyniki z StrictMath.atan (metoda podstawowa)
Całkowity czas trwania: 10 minut
Metoda 1: 20%
metoda 2: 20%
Metoda 3: 20%
StrictMath.atan: 40%

wyniki z uproszczonej, czystej Javie ATAN
Łączny czas trwania: 10 minu tes
Metoda 1: 33%
Metoda 2: 33%
Metoda 3: 33%

(Metody 1,2,3 nie wykonywać żadnych połączeń Atan)

Każdy pomysł co jest z tym zachowaniem? Otrzymałem te same wyniki przy użyciu JProfiler firmy EJ-Technologies. Wygląda na to, że interfejs API profilowania JDK zgłasza niedokładne wyniki dla natywnych metod, przynajmniej w OS X.

+0

Nie byłbym zaskoczony, gdyby 'atan' był nieodłączny - zamiast wywoływania metody, odpowiadający kod maszynowy jest wstrzykiwany inline. –

+0

Doświadczyłem tego również z różnymi metodami w StrictMath na Mac OS X 10.7 (i wcześniejszych wersjach też). –

+0

Czy istnieje rozwiązanie tego problemu? – ziggystar

Odpowiedz

3

Może się to zdarzyć z powodu niespójności, kiedy pobierane są próbki. Na przykład, jeśli metoda wykorzystuje sporą ilość czasu, ale jej wykonanie nie trwa zbyt długo, można ją pominąć. Ponadto, myślę, że wyrzucanie śmieci nigdy nie dzieje się podczas próby, ale jeśli jakiś kod powoduje dużo wyrzucania śmieci, może znacznie przyczynić się do spowolnienia bez pojawiania się w próbce.

W podobnej sytuacji okazało się, że bardzo pomocne jest dwukrotne uruchomienie, jednokrotne ze śledzeniem, a także jednokrotne z próbkowaniem. Jeśli metoda pojawia się w obu procesorach, prawdopodobnie używa dużo procesora, w przeciwnym razie może być po prostu artefaktem procesu próbkowania.

0

Uważam, że YourKit znacznie wyolbrzymia koszt wywoływania pod-metod (z powodu jego metody rejestrowania, zakładam). Jeśli będziesz postępować zgodnie z poradą, którą daje ci profil, skończysz po prostu łącząc funkcje bez żadnego rzeczywistego zysku, ponieważ HotSpot zwykle świetnie się do tego nadaje.

Dlatego bardzo zalecałbym testowanie partii całkowicie poza profilerami, aby uzyskać lepszy pomysł, czy zmiany są naprawdę korzystne (może wydawać się oczywiste, ale kosztowało to trochę czasu rozwoju).

0

Ponieważ używasz komputera Mac, możesz wypróbować wersję Apple's Shark profiler (do pobrania bezpłatnie z ADC), która obsługuje język Java, a grupa wydajności firmy Apple umieściła w nim sporo czasu.

Jak zaznaczył Nick, próbkowanie może wprowadzać w błąd, jeśli odstęp między próbkami jest wystarczająco zbliżony do czasu wykonania funkcji, a profiler rzadko sprawdza, czy funkcja faktycznie jest wykonywana. Nie wiem, czy obsługuje go YourKit, ale w Shark można zmienić interwał próbkowania na coś innego niż domyślne 10 ms i sprawdzić, czy wyniki są zasadniczo różne. Istnieje również oddzielny tryb śledzenia połączeń, który rejestruje każdą funkcję wejścia/powrotu - to całkowicie eliminuje możliwość wystąpienia błędów aliasingu, ale zbiera mnóstwo danych i zwiększa obciążenie, co może mieć znaczenie, jeśli aplikacja działa w czasie rzeczywistym przetwarzanie.

0

Możesz przyjrzeć się parametrom, które są przekazywane do trzech metod. Być może czas spędzany jest na generowaniu wartości zwracanych lub metodach, które tworzą wiele tymczasowych obiektów.

-1

Profilerowie mogą być tacy.

This is the method I use.

działa za każdym razem.

And this is why.

+0

Chcesz wyjaśnić, dlaczego prowadzi to do innych wyników niż wyniki profilera próbkowania, który automatyzuje ten proces? – ziggystar

+0

@ziggystar: Niektóre programy do profilowania próbkowania automatyzują połowę procesu, a mianowicie te, które próbkują cały stos, na czas zegarowy (nie procesora). Połowa procesu, którego nie automatyzują, polega na wykrywaniu problemów z wydajnością, które można naprawić. Jeśli instrukcja lub funkcja ma mały% włącznie, problem występuje gdzie indziej, ale nie zawęża to problemu. Samo stwierdzenie, że linia kodu, funkcji lub "ścieżka" jest "gorąca", nie mówi zbyt wiele. To bardziej odkrywcze, jeśli możesz zbadać konkretne reprezentatywne próbki w całości. ... –

+0

@ziggystar: ... Inny wynik prowadzi do tego, że można znaleźć przyspieszenia, których nie można znaleźć nawet z bardzo dobrym profilerem. Gdy je naprawisz i powtórzysz, problemy, które były małe wcześniej, są teraz większe, ponieważ program zajmuje mniej czasu. Tak więc, jeden po drugim, naprawiasz je, a zwiększone przyspieszenie może być zaskakujące. Ile przyspieszenia udało Ci się uzyskać dzięki profilerowi? Jeśli odpowiedź przekracza 40%, zaskoczyłoby mnie to. –

0

warto zauważyć, że metody Java mogą być wstawiane, jeśli są one na tyle małe, jednak metody natywne są wstawiane pod różnymi zasadami. Jeśli metoda jest wstawiona, nie pojawia się w profilerze (z pewnością nie jest to YourKit).

Powiązane problemy