2011-02-12 2 views
0

Linux에서 실행되는이 오래된 C++ 프로그램을 작성하고 있습니다. 내가 읽으려고했던 코드 중 최악의 코드이며, ValGrind로 실행하면 많은 메모리 문제가 발생합니다.Seg 결함 디버깅을 통한 제안 필요

내가 seg faults를 하나씩 골라 내고 싶지만, ValGrind가 코드 손상으로 인해 코드가 충돌 할 때까지 라인을 찾습니다. 이 코드는 자생 라이브러리뿐만 아니라 자생 라이브러리를 사용합니다. 제 3 자 라이브러리는 신뢰할 수 있지만 재배되지는 않습니다.

누구든지 seg 오류를 일으키는 메모리 손상을 찾는 방법에 대한 제안 사항이 있습니까? 다른 누군가의 코드, 특히 문서가없는 코드에서 seg 결함을 발견 할 필요가 없었습니다.

오늘 알게 된 두 가지는 컴파일러 설정이 자동으로 초기화되지 않도록 변경되었습니다. 값과 단어 크기가 32 비트에서 64 비트로 변경되었습니다.

나는 현명함을 보이기 위해 노력하고있다. 누군가 깊은 기억 분석 아이디어를 가지고 있는가?

감사합니다.

+0

gdb로 DDD를 사용하고 있습니다. –

답변

0

GDB는 좋은 제안입니다. 또한 프로그램이 충돌 할 때 ulimit unlimited (man page)을 사용하여 코어 파일을 덤프 할 수 있습니다.

즉, 이러한 도구가 제공하는 정보는 메모리 오류를 처리 할 때 오해의 소지가 있다고합니다. 메모리 손상으로 인해 프로그램 소스가 문제의 원인과 관련이 거의없는 임의의 위치에서 충돌 할 수 있습니다. 코어 덤프 나 GDB 출력을보고 프로그램이 어떻게 그 상태에 빠져들 수 있었는지 궁금해지면, 이것이 진행될 가능성이 있습니다.

그런 경우 valgrind는 가장 친한 친구입니다. 메모리 오류 목록의 맨 위에서 시작하여 한 번에 하나씩 수정하십시오 (하나를 수정 한 다음 다시 실행하고 다음을 수정하는 등). 하나의 오류를 수정하면 여러 다른 오류를 제거 할 수 있기 때문입니다) 모두 사라질 때까지. 그러면 프로그램이 더 안정적이되거나 도구가 유용한 정보를 다시 제공합니다.

+0

한 번에 하나의 valgrind 오류를 해결하고 싶지만 그 중 일부는 초기화 오류가있는 libs에 문제가 있습니다. 액세스 권한이 없습니다. 이 프로그램은 내 이해에서 거대한 이중 링크 목록처럼 작동하며 손상으로 인해 링크가 제거 된 것처럼 보입니다. seg 오류는 영구 파일 쓰기에서 발생합니다. 저장 작업이 오래 걸리기 전에 메모리가 손상된 경우 valgrind 또는 디버거를 중지 할 수 없습니다. –

+1

유용한 트릭 중 하나는 모든 객체가 소멸자에서 모든 포인터를 null로 설정하도록하는 것입니다. 이렇게하면 코드에서 해제 된 객체를 사용하려고하면 최종 충돌로 이어지는 정의되지 않은 동작 대신 즉각적인 세그멘트가 발생합니다. 또한 valgrind가 아무 것도 할 수없는 오류를 무시하도록 구성 할 수 있습니다. 나는 내 머리 꼭대기에서 정확히 어떻게 돌아 왔는지는 모르지만, 문서는 당신에게 말해야한다. –

+0

나는이 코드를 다시 사용할 수있다. –

0

Gdb가 valgrind보다 나은 선택입니다. gdb에서 실행중인 응용 프로그램이 SIGSEGV를 받으면 gdb는 실행을 중단하고 해당 지점까지 호출 된 함수가 나열된 스택 추적을 생성하고 사용자의 프로그램 메모리 상태를 보존합니다. 이 작업을 수행하려면 디버깅 정보 (gcc에서 -g)를 사용하여 응용 프로그램을 빌드해야합니다. 도서관을 재건 할 수 없더라도 프로그램 메모리를 보존하는 것이 큰 도움이 될 것입니다.

0

메모리 손상을 디버그하는 가장 쉬운 방법은 가능한 한 일찍 가능한 한 빨리 손상을 잡는 것입니다. 정확한 시간에 수행하는 것이 좋습니다. 그러면 어떤 스레드와 메소드가 잘못되었는지 확인할 수 있습니다.

일반적으로 손상은 손상 후 일정 시간 후에 만 ​​발생하기 때문에 파악하기 어렵습니다. Valgrind 및 기타 도구는 버퍼 오버플로 및 다른 오버레이가 포착되었는지 확인하기 위해 일부 검사를 사용하여 손상을 미리 캡처하는 데 도움이됩니다.

사용자 가이드를 살펴 보거나 다른 도구를 사용하여 충돌이나 중단 점을 강제로 손상시킬 수 있는지 확인하십시오.

즉, 자연 충돌 지점에서 디버거를 사용하면 손상된 메모리에 대한 정보를 표시 할 수 있지만 때로는 어려운 경고가 될 수 있습니다. valgrind와 같은 도구는 문제가 사라지지 않거나 허용 할 수 없을 정도로 낮은 성능을 초래하지 않으면 매우 중요합니다.

0

메모리 할당 자에서 디버깅 기능을 활성화 할 수 있는지 확인하십시오. glibc의 malloc 구현에는 어떻게 든 활성화 될 수있는 몇 가지 온 전성 검사가 있습니다.

응용 프로그램이 사용 된 메모리 할당 자의 내부 데이터 구조를 덮어 쓴 경우 (예 : 간단한 체인 기반 malloc이있는 임베디드 시스템에서) - 메모리 할당에 산발적 인 오류가 발생했습니다.

0

모두에게 감사의 말을 전하려 고 감사하지만 valGrind가 내 문제를 발견했다면 코드가 필요한 저장 작업 전에 개체를 삭제하는 것처럼 보입니다. 그것은 나에게 조금 걸렸지 만 valgrind의 결과물을 얻는 데는 잘못된 것이 었습니다.

관련 문제