2012-03-03 16 views
17

Jak wyświetlić listę wszystkich funkcji wywoływanych w aplikacji. Próbowałem używać GDB, ale jego listę śledzenia wstecznego tylko do głównego wywołania funkcji.Lista wszystkich wywołań funkcji utworzonych w aplikacji

Potrzebuję głębszej listy, tj. Listy wszystkich funkcji wywoływanych przez funkcję główną i funkcji wywoływanej z tych wywoływanych funkcji i tak dalej.

Czy można to uzyskać w gdb? Czy możesz dać mi sugestie, jak to uzyskać?

+0

Za pomocą dowolnego narzędzia: http://stackoverflow.com/questions/311840/tool-to-trace-local-function-calls-in-linux?lq=1 –

+0

Możliwy duplikat funkcji [Make GDB print control function funkcji, jak się je nazywa] (http://stackoverflow.com/questions/311948/make-gdb-print-control-flow-of-functions-as-they-are- o nazwie) – jww

+0

https://balau82.wordpress.com/2010/10/06/trace-and-profile-function-calls-w-gcc/ –

Odpowiedz

17

Jak możemy wymienić wszystkie funkcje są nazywane w aplikacji

Dla każdego realistycznie wielkości aplikacji, lista ta będzie miała tysiące wpisów, które prawdopodobnie będzie to bezużyteczne.

Można znaleźć wszystkie funkcje zdefiniowane jako (ale niekoniecznie wywoływane) w aplikacji z komendą nm, np.

nm /path/to/a.out | egrep ' [TW] ' 

Można również użyć GDB aby ustawić punkt przerwania na każdej funkcji:

(gdb) set logging on  # collect trace in gdb.txt 
(gdb) set confirm off # you wouldn't want to confirm every one of them 
(gdb) rbreak .   # set a breakpoint on each function 

Gdy będziesz kontynuować, trafisz przerwania dla każdej funkcji o nazwie. Użyj poleceń disable i continue, aby przejść do przodu. Nie wierzę, że istnieje łatwy sposób zautomatyzowania tego, chyba że chcesz używać skryptów w języku Python.

Już wspomniano gprof to kolejna dobra opcja.

+0

Uwaga: spowoduje to również złamanie kodu, który jest uruchamiany przed '_start': http : //stackoverflow.com/questions/31379422/why-is-init-from-glibcs-csu-init-first-c-called-before-start-even-if-start-i –

+0

gdb siedzi w 100% cpu odkąd wprowadziłem polecenie 'rbreak .' –

+0

bez logowania,' set height 0' będzie pomocne (brak stronicowania dla wyjścia) – Blauhirn

9

Potrzebujesz wykresu połączeń. Narzędzie, którego chcesz użyć, nie jest gdb, to jest gprof. Kompilujesz swój program za pomocą -pg, a następnie uruchamiasz go. Po uruchomieniu zostanie utworzony plik gmon.out. Następnie przetwarzasz ten plik za pomocą gprof i ciesz się wynikami.

1

To pytanie może wymagać wyjaśnienia, aby zdecydować, jakie są obecnie 2 odpowiedzi. Zależy, czego potrzebujesz:

1) Musisz wiedzieć, ile razy każda funkcja jest wywoływana w prostym formacie lista/wykresu funkcji zgodnych z # zaproszeń. Może to prowadzić do niejednoznacznych/niejednoznacznych rezultatów, jeśli twój kod nie jest proceduralny (tj. Funkcje wywołujące inne funkcje w strukturze rozgałęzienia bez niejasności tego, co wywołuje co). Jest to podstawowa funkcjonalność gprof, która wymaga ponownej kompilacji z flagą -pg.

2) Potrzebujesz listy funkcji w kolejności, w jakiej zostały wywołane, zależy to od twojego programu, który jest najlepszą/możliwą opcją: a) JEŻELI twój program działa i kończy się bez błędów środowiska wykonawczego, możesz użyć gprof w tym celu. b) powyżej, stosując opcję ELSE DBG z logowaniem i złamać punktów jest pozostały opcja, że ​​dowiedziałem się po przeczytaniu tego.

3) Trzeba wiedzieć nie tylko porządek, ale na przykład, argumenty funkcji dla każdego połączenia, jak również. Moja obecna praca jest symulacje fizyki transportu cząstek, więc to absolutnie być przydatne w tropieniu gdzie anomalne wyniki pochodzą z ... to znaczy, gdy argumenty uzyskiwanie przekazywane wokół zatrzymać sensu.Wyobrażam sobie jeden sposób, aby to zrobić, będzie to wariacja na temat tego, co Zatrudniony zrobił rosyjski wyjątkiem stosując następujący:

(gdb) Informacje args

Logging wyniki tego polecenia z każdego punktu krytycznego (ustawione przy każdym wywołaniu funkcji) podaje argumenty bieżącej funkcji.

4

rekord funkcja-call-historia

https://sourceware.org/gdb/onlinedocs/gdb/Process-Record-and-Replay.html

To powinno być wielkim przyspieszane sprzętowo możliwość, jeśli jesteś jednym z niewielu ludzi (2015) z procesorem obsługującym Intel Processor Tracing (Intel PT, intel_pt w /proc/cpuinfo).

GDB docs twierdzą, że może produkować wyjście jak:

(gdb) list 1, 10 
1 void foo (void) 
2 { 
3 } 
4 
5 void bar (void) 
6 { 
7  ... 
8  foo(); 
9  ... 
10 } 
(gdb) record function-call-history /ilc 
1 bar  inst 1,4  at foo.c:6,8 
2 foo inst 5,10 at foo.c:2,3 
3 bar  inst 11,13 at foo.c:9,10 

Przed użyciem trzeba uruchomić:

start 
record btrace 

czyli tam, gdzie non zdolny CPU nie powiedzie się z:

Target does not support branch tracing. 

Wsparcie procesorów jest dalej omawiane pod adresem: How to run record instruction-history and function-call-history in GDB?

Podobne wątki:

wbudowanych, można również rozważyć Box i sprzętu wspierającego jak ARM DSTREAM, ale wsparcie x86 nie wydaje się bardzo dobry: debugging x86 kernel using a hardware debugger

Powiązane problemy