2010-03-29 15 views
10

Uruchamiamy linuksa uclibc na ARM 9. Problem polega na tym, że uclibc nie obsługuje śledzenia wstecznego. Kiedy dochodzi do zrzutu pamięci, nie mogę pobrać stosu wywołań.Dowolne portowanie dostępne dla śledzenia wstecznego dla uclibc?

Czy ktoś ma dobre rozwiązanie?

Na przykład istniejące przeniesienie śledzenia wstecznego dla uclibc lub jakąkolwiek dobrą metodę przechwytywania stosu wywołań podczas zrzutu pamięci (uclibc + ARM + Linux)?

Odpowiedz

5

Aktualizacja:

Wydaje się, że patch został stworzony w celu wspierania backtrace() na uClibc dla x86 i ARM (XScale), a to sprawia, że ​​korzystanie z __libc_stack_end symbolem.


Original Odpowiedź:

pracowałem nad projektem, gdzie wersja glibc używaliśmy nie stanowią funkcjonalną backtrace() dla naszego procesora ARM, więc stworzyliśmy nasz własny poza glibc pomocą __libc_stack_end symbol. Poniżej znajduje się wynikowy kod. Być może możesz go użyć do napisania funkcji 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; 
} 

Uwaga: __libc_stack_end symbol nie jest już eksportowana w nowszych wersjach glibc i nie jestem pewien, o istnieniu tego lub podobnego symbolu w uClibc.

+0

z powyższego kodu Otrzymuję błąd runtime error backtrace” : __builtin_return_address (0)! = frame_p-> lr ". jak rozwiązać ten warunek. – Mandar

+0

Standardowa konwencja wywoływania ARM ([pdf link] (http://infocenter.arm.com/help/topic/com.arm.doc.ihi0042d/IHI0042D_aapcs.pdf)) przydziela r14 jako rejestr linków. Instrukcja BL, używana w wywołaniu podprogramu, przechowuje adres zwrotny w tym rejestrze. Funkcje '__builtin_frame_address (0)' i '__builtin_return_address (0)' są używane do [otrzymania adresu powrotu i ramki funkcji wywołującej] (http://gcc.gnu.org/onlinedocs/gcc/Return-Address.html). Twój błąd mówi, że rejestr linków nie zawiera adresu zwrotnego lub struktura 'backtrace_frame_t' nie pasuje do twojej ramki stosu. – jschmier

Powiązane problemy