2015-01-23 5 views
0

C/C++의 프로그램은 HW 중단 점 기능이있는 디버거에서 내장 된 PowerPC에서 실행됩니다. 2 개의 파일 및 2 개의 작업에 해당하는 전역 변수 'char Name [256]'이 있습니다. 한 작업은 이름을 읽고, 다른 작업은 텍스트를 '1234567 ...'으로 채 웁니다. 잠시 후 전역 변수 Name이 손상됩니다. 변수 주소 gdb가 요청되면 (및 응용 프로그램이 디버그 출력물로 출력 함) 주소는 0x31323334와 같습니다.HW BP가 전역 변수 주소 손상을 catch하는 위치는 어디입니까?

HW 중단 점으로이 버그를 잡는 방법? 나는 HWBP를 놓을 주소가 무엇인지를 의미한다. 내가 어셈블러로 볼 때 , 내가 볼 :
LIS 9 이름 @ 하
LWZ (9) (9) 그래서

, NAMEL은 L @, 메모리 손상이 응용 프로그램의 흐름에 영향을주지 않고 코드를 변경하는 방법 - 그것은해야 즉시 충돌, 안돼?

감사에 앞서

답변

1

0x31323334 많은 "1234" 산세가 터미네이터를 NULL입니다. 또한 "전역 변수 주소 손상"은 "전역 변수"(주소가 인 경우을 변경하지 않음) 또는 크기가 256 인 배열에 대해서는별로 의미가 없습니다 (포인터를 어딘가에 사용하지 않는 한 그렇지 않은 경우). 손상됨). 따라서 GDB에 익숙하지 않을 수도 있습니다.

다음 테스트 파일과 86 (인정 하듯이,하지 PPC는하지만, 기본적으로 동일한 소프트웨어)에 GNU gdb (Ubuntu 7.7.1-0ubuntu5~14.04.2) 7.7.1 사용 :

// g++ test.cpp -g 
#include <iostream> 

char Name[256] = "123456789"; 

int main() { 
    Name[0] = 'a'; 
    std::cout << Name << std::endl; 
} 

내가 GDB에서 다음과 같은 출력을 얻을 수 있습니다

(gdb) break main 
Breakpoint 2 at 0x40086a: file test.cpp, line 6. 
(gdb) r 
Starting program: /home/keithb/dev/mytest/a.out 

Breakpoint 2, main() at test.cpp:6 
6  Name[0] = 'a'; 
(gdb) whatis Name 
type = char [256] 
(gdb) print Name 
$1 = "123456789", '\000' <repeats 246 times> 
(gdb) print &Name 
$2 = (char (*)[256]) 0x6010c0 <Name> 

을 어떤 경우 에든 실제로 "하드웨어 중단 점"(GDB calls those "watchpoints")을 설정하려는 경우 손상되기 전에 Name의 주소를 가져올 수 있습니다. 그런 다음 watchpoint를 설정하고 프로그램이 주소에 쓸 때까지 기다리십시오.

(gdb) c 
Continuing. 
a23456789 
[Inferior 1 (process 21878) exited normally] 
(gdb) delete 2 
(gdb) watch *0x6010c0 
Hardware watchpoint 3: *0x6010c0 
(gdb) r 
Starting program: /home/keithb/dev/mytest/a.out 
Hardware watchpoint 3: *0x6010c0 

Old value = 875770417 
New value = 875770465 
main() at test.cpp:7 
7  std::cout << Name << std::endl; 
(gdb) 
+1

저는 지난 17 년 동안 gcc/gdb에서 작업합니다. 그리고 정확하게 이것 때문에, 저는 질문합니다. 글로벌 변수의 주소가 바뀔 수있는 방법을 상상할 수 없기 때문입니다. 내가 잘못 설명 하겠지만, 이것은 내용이 아닌 '이름'의 주소입니다. 문제가 발생하기 전에 이름 주소를 출력하도록 gdb에 요청하면 0x51c18이 인쇄됩니다. 그러나 문제가 발생하면 0x31323334가 인쇄됩니다.이 텍스트는 memcpy로 복사 된 텍스트의 일부입니다. 그것은 복사 된 유일한 텍스트가 아니지만. – leonp

+1

상황이 멀티 태스킹 및 잡기가 쉽기 때문에 watchpoint에 관해서 이야기했습니다. 이미 BP, 인쇄물, 메모리 로그까지 시도했습니다. 모든 것이 ADDRESS가 텍스트로 변경되었음을 보여줍니다 - 문제의 유일한 징후 (더 이상의 버스 오류를 제외하고 ...-) – leonp

+0

GDB가 'Name'의 주소를 변경한다고 생각한다면 1) 'Name'이 로컬'Name'에 의해 숨겨져 있지 않은지 확인하십시오, 2)'Name' 주소가 하드 코드 된 명령에 대한 감시 점 설정 (예 :'lis'와'lws'), – inetknght