2010-07-26 18 views
9

Voglio sapere se esiste un modo per sapere dove è stata chiamata la funzione attualmente in esecuzione, cioè in quale file e riga. Sto usando il linguaggio C, e sto cercando qualcosa di simile a __FUNCTION__, __LINE__ o __FILE__ macros.Come sapere quale funzione si chiama un altro

+1

È possibile ottenere questo utilizzando macro. Guarda la mia soluzione. – bits

+0

Se si desidera che si tratti di dati che è possibile utilizzare nel codice, si tratta di una richiesta insolita. Perché lo vuoi? Forse possiamo aiutarti a risolvere qualunque problema abbia provocato questa domanda? – WillfulWizard

risposta

11

Rinominare la funzione

void Function(param1) 
{ 
} 

a

void Function_debug(param1, char * file, char * func, unsigned long line) 
{ 
} 

Poi #define una macro così:

#define Function(param1) Function_debug(param1, __FILE__, __FUNCTION__, __LINE__) 
+1

E a proposito, ciò significa che il codice cliente rimarrà invariato. – bits

+1

Oh, davvero un modo bello e facile per farlo. Grazie mille Sérgio –

+1

Se vuoi davvero ringraziare i bit devi cliccare sulla casella a sinistra della sua risposta per dire che è quella che ha risolto il tuo problema. – WillfulWizard

3

Non c'è niente nella C stessa che possa darti questa informazione. È possibile rintracciare le informazioni da soli (all'entrata/uscita) o fare affidamento su API specifiche della piattaforma per gestire lo stack di chiamate e determinare la funzione di chiamata, ma non molto di più.

0

Se è necessario conoscerlo in fase di runtime, non penso sia possibile.

Se avete bisogno di sapere che a debugtime, è possibile inserire un punto di interruzione sulla funzione che si desidera, e poi, usando GDB (usando bt comando) o debugger di vistual Studio, ispezionare l'analisi dello stack corrente.

2

__FILE__, __LINE__ ecc sono macro del preprocessore che possono essere facilmente estese al valore corretto in fase di compilazione. Una funzione può essere richiamata da molti posti possibili, quindi non può essere eseguita tramite il preprocessore. Trovare il nome del chiamante sarebbe molto difficile; implica il camminare nello stack e abbinare gli indirizzi ai simboli.

Se si può vivere con un piccolo hack, questo potrebbe funzionare (non testata):

/* Add a called argument to your function */ 
void _myFunction(char *caller, int more_args) 

/* And define a macro that adds it automagically */ 
#define myFunction(a) _myFunction(__FUNCTION__, a) 
0

Questo è in realtà un po 'più complicato da fare. La soluzione migliore è ottenere un backtrace su un debugger o trovare qualcosa di simile a pstack per la tua piattaforma. Il modo manuale dovrebbe coinvolgere lo stack di chiamate e utilizzare i simboli di debug per tradurlo in file e righe.

0

È possibile utilizzare i registri.

#define BEGIN_FUNC(X,Y,Z) printf("Function %s Entered at line %d from file %s",X,Z,Y) 
#define END_FUNC(X) printf("Function %s Exited at line %d from file %s",X,Z,Y) 

foo() 
{ 
BEGIN_FUNC(__func__,__FILE__,__LINE__); 

//Your code here 


END_FUNC(__func___FILE__,__LINE__); 

}

O

Usa bt in gdb. Lo chiamo backtrace.

1

Non c'è nulla che sia supportato in tutte le implementazioni che farà ciò che vuoi. Ho a volte mi sono trovato nella stessa situazione, in cui avevo bisogno di tenere traccia di chi chiama per alcuni metodi e ha fatto qualcosa di simile al seguente:

#ifdef TRACKBACK 
int foo(int arg1, int arg2, const char * file, int line) 
{ 
    SEND_TO_LOG("foo", file, line); 
#else 
int foo(int arg1, int arg2) 
{ 
#endif 
    ... 
    ... 

Naturalmente, si fa per un po 'di mal di testa alla fine chiamata, quindi ti consigliamo di fare qualcosa di simile:

#ifdef TRACKBACK 
    #define TRACKING, __FILE__, __LINE__ 
#else 
    #define TRACKING 
#endif 

Poi la chiamata:

foo(arg1, arg2 TRACKING); //note the lack of the comma 

si fa il trucco quando tutto il resto fallisce.

Problemi correlati