2010-03-29 6 views
10

Stiamo eseguendo il uclibc linux su ARM 9. Il problema è che uclibc non supporta il backtrace. Quando si verifica un core dump, non riesco ad afferrare lo stack delle chiamate.Qualsiasi porting disponibile di backtrace per uclibc?

Qualcuno ha una buona soluzione per questo?

Ad esempio, un porting esistente di backtrace per uclibc, o qualsiasi buon metodo per afferrare lo stack di chiamate quando avviene un core dump (uclibc + ARM + Linux)?

risposta

5

Aggiornamento:

sembra che un patch è stato creato per sostenere backtrace() su uclibc per x86 e ARM (XScale) e si fa uso del simbolo __libc_stack_end.


risposta originale:

ho lavorato su un progetto in cui la versione di glibc stavamo usando non ha fornito un funzionale backtrace() per il nostro processore ARM, così abbiamo sviluppato la nostra al di fuori della glibc utilizzando il __libc_stack_end simbolo. Di seguito è riportato il codice risultante. Forse puoi usarlo per scrivere una funzione uclibc backtrace().

extern void * __libc_stack_end; 

struct backtrace_frame_t 
{ 
    void * fp; 
    void * sp; 
    void * lr; 
    void * pc; 
}; 

int backtrace(void ** array, int size) 
{ 
    void * top_frame_p; 
    void * current_frame_p; 
    struct backtrace_frame_t * frame_p; 
    int frame_count; 

    top_frame_p = __builtin_frame_address(0); 
    current_frame_p = top_frame_p; 
    frame_p = (struct backtrace_frame_t*)((void**)(current_frame_p)-3); 
    frame_count = 0; 

    if (__builtin_return_address(0) != frame_p->lr) 
    { 
     fprintf(stderr, "backtrace error: __builtin_return_address(0) != frame_p->lr\n"); 
     return frame_count; 
    } 

    if (current_frame_p != NULL 
     && current_frame_p > (void*)&frame_count 
     && current_frame_p < __libc_stack_end) 
    { 
     while (frame_count < size 
       && current_frame_p != NULL 
       && current_frame_p > (void*)&frame_count 
       && current_frame_p < __libc_stack_end) 
     { 
      frame_p = (struct backtrace_frame_t*)((void**)(current_frame_p)-3); 
      array[frame_count] = frame_p->lr; 
      frame_count++; 
      current_frame_p = frame_p->fp; 
     } 
    } 

    return frame_count; 
} 

Nota: Il simbolo __libc_stack_end non è più esportato nelle versioni più recenti di glibc e non sono sicuro dell'esistenza di esso o un simbolo simile in uClibc.

+0

dal codice di cui sopra sto ottenendo errore di runtime error backtrace" : __builtin_return_address (0)! = frame_p-> lr ". come risolvere questa condizione. – Mandar

+0

La convenzione di chiamata ARM standard ([link pdf] (http://infocenter.arm.com/help/topic/com.arm.doc.ihi0042d/IHI0042D_aapcs.pdf)) alloca r14 come registro dei collegamenti. L'istruzione BL, utilizzata in una chiamata di subroutine, memorizza l'indirizzo di ritorno in questo registro. Le funzioni '__builtin_frame_address (0)' e '__builtin_return_address (0)' sono usate per [ottenere l'indirizzo di ritorno e frame della funzione chiamante] (http://gcc.gnu.org/onlinedocs/gcc/Return-Address.html). Il tuo errore dice che il registro dei collegamenti non contiene l'indirizzo di ritorno o la struttura 'backtrace_frame_t' non corrisponde al tuo stack frame. – jschmier

Problemi correlati