C -Analisi con GProf

Effettuare il tuning di un modulo C.

Effettuare il tuning di un modulo C.

L’efficenza di un algoritmo e di un programma va affrotata in due passi: un analisi teorica dell’algoritmo e una analisi “on the road” in cui l’algoritmo va implementato e testato sulle varie architetture reali.

Ovviamente, come abbiamo avuto modo di vedere, non c’è linguaggio che possa vantare le capacità prestazionali del C, anche senza contare le capacità di interfacciarsi direttamente a basso livello con innesti di codice assembly grazie al costrutto _asm_.

Ma come tutti gli strumenti potenti vanno saputi utilizzare, molto spesso differenze impercettibili e che pensiamo irrilevanti si ripercuotono in maniera catastrofica sul nostro software. Ad esempio ho avuto modo di vedere algoritmi in cui la sola variazione di due parametri strutturali faceva passare il tempo di esecuzione da 2 minuti a 11 giorni.

E’ quindi importante identificare, in un software, quali sono le funzioni e le procedure che occupano più tempo, e quale è il loro peso nel tempo complessivo di esecuzione.

A venirci incontro è proprio GProf.

GProf è un tool che permette di interpretare con statistiche avanzate sui tempi di esecuzioni delle singole funzioni il file di profiling generato dagli eseguibili compilati con il parametro -pg.

Ma andiamo con ordine. Per utilizzare GProf per prima cosa prendiamo il nostro codice C e compiliamolo come consueto ma aggiungendo il parametro -pg.

gcc prova.c -o prova -pg

Dopo aver compilato correttamente il file non ci resta che eseguirlo. Una volta terminato ci accorgeremo che nella cartella dell’eseguibile è stato creato un file chiamato gmon.out.

Ora per leggere il report dettagliato non ci resta che dare il comando:

gprof prova | less

I primi dati ce potremo consultare sono i tempi di esecuzioni delle singole funzioni del programma ordinate in ordine decrescente in base alla percentuale di tempo di esecuzione. Ma non solo, possiamo vedere anche quante volte una data funzione viene chiamata. Come ad esempio:

% cumulative  self              self     total
 time seconds  seconds  calls s/call s/call name
43.32   46.03  46.03 339952989  0.00  0.00 CompareNodes(Node *,Node *)
25.06   72.66  26.63    55000   0.00  0.00 getNode(char *,NodeListNode *&)
16.80   90.51  17.85 339433374  0.00  0.00 CompareEdges(Edge *,AnnotatedEdge *)
12.70  104.01  13.50    51987   0.00  0.00 addAnnotatedEdge(AnnotatedGraph *,Edge *)
 1.98  106.11   2.10    51987   0.00  0.00 addEdge(Graph *,Node *,Node *)
 0.07  106.18   0.07        1   0.07  0.07 FindTreshold(AnnotatedEdge *,int)
 0.06  106.24   0.06        1   0.06 28.79 getGraphFromFile(char *,NodeListNode *&,Config *)
 0.02  106.26   0.02        1   0.02 77.40 summarize(GraphListNode *,Config *)
 0.00  106.26   0.00    55000   0.00  0.00 FixName(char *)

Un altro modo che abbiamo per consultare il file di profiling è usando alcuni tool grafici, fra i quali vi cito KProf per KDE, con il quale potrete accedere alle stesse informazioni grazie all’interfaccia grafica spartana ma completa.

Una volta che abbiamo a disposizione questi dati non ci resta che individuare le funzioni anomale, apportare modifiche, ricompilare e vedere le eventuali variazioni in termini di tempo di esecuzione… sperando siano positive! 🙂

Fate alcuni esperimenti e vedrete che GProf sarà il vostro migliore amico nel debellare il virus dell’inefficenza! 😉

LINK UTILI:

Comments are closed.