앞선 포스트에서는 메모리덤프를 이용한 디버깅에 대해 살펴보았습니다.
디버깅을 하다보면 메모리덤프 외에 리모트 디버깅이 필요한 경우도 있습니다. 예를 들면...
위와 같은 경우에는 Remote Debugging이 유용합니다.
Remote Debugging의 원리는 대략 다음과 같습니다.
로컬 디버깅의 경우 Debugger Process가 Debuggee Process를 Attach하여 Break Point를 설정하거나 메모리를 수정하거나... 기타등등 디버깅 Action이 가능합니다. 일반적으로는 Debugger Process는 Visual Studio가 되고, Debuggee Process가 우리가 개발한 프로그램이 되죠.
리모트 디버깅도 기본적으로는 로컬 디버깅과 동일한 원리입니다. Debugger Process를 원격에서 조정하는 방식이라고 보면 되죠.
위의 그림에서는 Remote Debug Client가 Visual Studio가 됩니다. 그렇다면 디버거 역할을 해 줄 "Remote Debug Server"는?
Visual Studio를 설치하면 Remote Debug를 하기 위한 Tool이 함께 설치됩니다. 따라서, 원래는 Debugger PC와 Debuggee PC에 모두 Visual Studio를 설치해야 하지요.
하지만, Visual Studio를 꼭 설치하지 않더라도 Remote Debugging Tool만 설치(복사)하면 Remote Debugging을 할 수 있습니다.
약간 비유를 하자면... "Remote Debug Server" 가 Avatar가 되고, Visual Studio는 Avatar 조종사가 되는 셈이지요. ^^
먼저 Remote Debugging을 하기 위한 환경 Setting을 살펴보겠습니다.
전체적인 과정은 대략 다음과 같습니다.
먼저 Debuggee PC에 Server 모듈을 설치합시다.
Visual Studio가 설치된 PC에서 "프로그램" 메뉴에서 "Visual Studio 2005 Remote Debugger" 아이콘의 "속성"을 열어보면, 우리가 원하는 모듈의 위치를 찾을 수 있습니다. (Visual Studio 버젼에 따라 차이가 있을 수 있지만... 2005 기준으로 설명하겠습니다.)
아이콘의 속성 창에서 아이콘이 가리키는 "대상" Dir을 확인합니다.
확인된 경로에 가보면, Debuggee Platform 별로 폴더가 있네요.
Debugging할 대상 PC의 Platform에 맞는 폴더를 골라서 Debuggee PC에 복사합니다.
Debuggee PC에 아래와 같이 폴더가 복사되면, "msvsmon.exe" 를 실행하여 Remote Debug Server를 실행합니다. (Vista 이후 PC인 경우 관리자 권한으로 실행합니다.)
실행하면 아래와 같이 창이 뜨는데, 옵션 설정하는 화면을 엽니다.
Options 설정 메뉴에서 "No Authentication (native only)"를 선택하고 "Allow any user to debug"를 체크합니다. 이 설정은 재실행하면 초기화됩니다. (이렇게 하지 않고 Windows login 계정과 Password를 일치시키면 될것 같긴 한데.. 해보면 잘 안됩니다. ^^)
만약 로컬 보안정책 상의 문제로 인해 디버깅이 불가능한 상황이라면 아래와 같은 창이 뜹니다.
그러면 "제어판 > 관리도구 > 로컬 보안 정책" 에서 로컬보안정책을 수정해줍니다.
"보안설정 > 로컬 정책 >보안 옵션" 에서 "네트워크 액세스 : 로컬 계정에 대한 공유 및 보안" 항목이 "게스트 전용 - 로컬 사용자를 게스트로 인증" 으로 설정되어 있을 것입니다.
해당 항목을 더블클릭하여 아래와 같이 "일반 - 로컬 사용자를 그대로 인증"으로 수정한 후 저장합니다.
혹시, 윈도우즈 방화벽 설정이 되어 있을 경우 아래와 같은 경고창이 뜰 수 있으니 적당히 방화벽을 해제해줍니다.
가급적이면 Debugger PC와 Debuggee PC 모두 해제해주는 것이 좋습니다.
성공적으로 Remote Debug Server 모듈이 실행되면 아래와 같이 Tray Icon이 나타납니다.
자, 이제 Debuggee PC에 준비는 끝났습니다.
디버깅할 모듈을 새로 빌드하여 Debuggee PC의 실행 위치에 복사해 넣습니다. (만약 PDB가 Match 되기만 한다면 굳이 새로 빌드할 필요는 없습니다.)
이제 Debugger 쪽의 설정을 해봅시다.
Visual Studio의 프로젝트 설정 창을 엽니다.
Project Setting 창에서 "Configuration Properties > Debugging" 탭을 펼친 후
- Debugger to launch 항목을 "Remote Windows Debugger"로 설정해 줍니다. (디폴트는 "Local Windows Debugger")
- Remote Command : Debuggee PC에서 실행시킬 명령어를 입력해 줍니다. 디버깅할 모듈이 exe라면 exe의 Full Path를 입력해주면 되겠지만, DLL이라면 DLL을 로딩할 Host Exe의 경로를 입력해주어야 하겠지요.
- Command Arguments : 말그대로 실행할 때 인자가 필요하다면 입력해줍니다.
- Remote Server Name : Debuggee PC의 IP주소를 적어줍니다. 만약 동일 Subnet이라면 NETBIOS Name을 적어주어도 됩니다.
- Connection : "Remote with no authentication (Native Only)"를 선택해줍니다. 이부분은 Debuggee PC의 설정과 일치시켜야 하겠지요?
- Debugger Type : 이부분은 상기 "Connection" 항목을 설정하면 자동으로 "Native Only"로 설정됩니다.
- Attach : 만약 서비스 프로세스를 디버깅하는 경우 등, 이미 실행중인 Process에 Attach해야 하는 경우엔 이부분을 "Yes"로 설정해줍니다. "No"로 설정하면 로컬디버깅할 때와 마찬가지로 디버거가 디버깅 대상 프로세스를 실행시켜줍니다.
자 모든 설정이 끝났으면, Visual Studio에서 BreakPoint를 설정한 후 F5 (Go)를 누르거나, F10 등을 눌러 디버깅을 시작합니다.
Debugger PC에서 디버깅을 시작하면, Debuggee PC에서는 아래와 같이 해당 프로세스가 실행되면서 디버깅이 시작됩니다.
정상적으로 연결되었을 경우 Remote Debug Server에서는 아래와 같은 메시지를 확인할 수 있습니다.
이 상태에서 Debugger PC의 Visual Studio를 통해 Local Debugging과 동일하게 디버깅이 가능합니다. (Break Point 설정, Memory / 변수 / Register 값 조회 등등... )
만약 서비스 프로세스를 디버깅하는 등, 이미 실행중인 프로세스를 디버깅해야 할 경우 Visual Studio의 아래 항목을 설정해주면 됩니다.
실제로 해보면.. 그닥 어렵지 않으면서도 유용한 디버깅 방법입니다. ^^
디버깅을 하다보면 메모리덤프 외에 리모트 디버깅이 필요한 경우도 있습니다. 예를 들면...
1) Visual Studio가 설치되지 않은 PC에서 문제가 발생했는데... exception이 발생하거나 Hang이 걸리는 경우가 아니어서 Memory Dump로 분석하기 어려운 경우 (브레이크포인트를 걸고 Line 단위로 쫓아가 보고 싶은 경우)
2) 디버깅할 모듈이 svchost.exe 등 중요 시스템프로세스에 로딩되어, 로컬 디버깅이 불가능한 경우
(svchost 와 같은 프로세스에 디버거를 붙이면... 시스템이 서 버릴 수도 있습니다. 디버깅하느라 시스템이 서는건 괜찮지만...
서버린 시스템에선 디버거가 제대로 동작하지 않겠죠.)
3) Visual Studio가 Debuggee OS를 지원하지 않는 경우 (예를 들면 IA64 라던지...)
4) 기타 VMWare 등 디버거를 설치하기가 곤란한 환경에서 발생한 문제 분석
2) 디버깅할 모듈이 svchost.exe 등 중요 시스템프로세스에 로딩되어, 로컬 디버깅이 불가능한 경우
(svchost 와 같은 프로세스에 디버거를 붙이면... 시스템이 서 버릴 수도 있습니다. 디버깅하느라 시스템이 서는건 괜찮지만...
서버린 시스템에선 디버거가 제대로 동작하지 않겠죠.)
3) Visual Studio가 Debuggee OS를 지원하지 않는 경우 (예를 들면 IA64 라던지...)
4) 기타 VMWare 등 디버거를 설치하기가 곤란한 환경에서 발생한 문제 분석
위와 같은 경우에는 Remote Debugging이 유용합니다.
Remote Debugging의 원리는 대략 다음과 같습니다.
로컬 디버깅의 경우 Debugger Process가 Debuggee Process를 Attach하여 Break Point를 설정하거나 메모리를 수정하거나... 기타등등 디버깅 Action이 가능합니다. 일반적으로는 Debugger Process는 Visual Studio가 되고, Debuggee Process가 우리가 개발한 프로그램이 되죠.
리모트 디버깅도 기본적으로는 로컬 디버깅과 동일한 원리입니다. Debugger Process를 원격에서 조정하는 방식이라고 보면 되죠.
위의 그림에서는 Remote Debug Client가 Visual Studio가 됩니다. 그렇다면 디버거 역할을 해 줄 "Remote Debug Server"는?
Visual Studio를 설치하면 Remote Debug를 하기 위한 Tool이 함께 설치됩니다. 따라서, 원래는 Debugger PC와 Debuggee PC에 모두 Visual Studio를 설치해야 하지요.
하지만, Visual Studio를 꼭 설치하지 않더라도 Remote Debugging Tool만 설치(복사)하면 Remote Debugging을 할 수 있습니다.
약간 비유를 하자면... "Remote Debug Server" 가 Avatar가 되고, Visual Studio는 Avatar 조종사가 되는 셈이지요. ^^
먼저 Remote Debugging을 하기 위한 환경 Setting을 살펴보겠습니다.
전체적인 과정은 대략 다음과 같습니다.
1. 디버깅될 PC (Debuggee PC)에 Remote Debug Server 프로그램을 설치하여 환경을 설정하고 Remote Debug Server 실행
2. 디버깅할 PC (Debugger PC : Visual Studio가 설치된 PC)에서 빌드한 실행 모듈을 Debuggee PC의 실행 위치에 복사해놓습니다. 만약 Debugger PC에 있는 PDB와 Debuggee PC의 모듈이 Match한다면 굳이 새로 빌드해서 가져다놓을 필요는 없겠죠.
2. 디버깅할 PC (Debugger PC : Visual Studio가 설치된 PC)에서 Visual Studio 에 원격 디버깅 설정을 하고 디버깅을 시작합니다.
2. 디버깅할 PC (Debugger PC : Visual Studio가 설치된 PC)에서 빌드한 실행 모듈을 Debuggee PC의 실행 위치에 복사해놓습니다. 만약 Debugger PC에 있는 PDB와 Debuggee PC의 모듈이 Match한다면 굳이 새로 빌드해서 가져다놓을 필요는 없겠죠.
2. 디버깅할 PC (Debugger PC : Visual Studio가 설치된 PC)에서 Visual Studio 에 원격 디버깅 설정을 하고 디버깅을 시작합니다.
먼저 Debuggee PC에 Server 모듈을 설치합시다.
Visual Studio가 설치된 PC에서 "프로그램" 메뉴에서 "Visual Studio 2005 Remote Debugger" 아이콘의 "속성"을 열어보면, 우리가 원하는 모듈의 위치를 찾을 수 있습니다. (Visual Studio 버젼에 따라 차이가 있을 수 있지만... 2005 기준으로 설명하겠습니다.)
아이콘의 속성 창에서 아이콘이 가리키는 "대상" Dir을 확인합니다.
확인된 경로에 가보면, Debuggee Platform 별로 폴더가 있네요.
Debugging할 대상 PC의 Platform에 맞는 폴더를 골라서 Debuggee PC에 복사합니다.
Debuggee PC에 아래와 같이 폴더가 복사되면, "msvsmon.exe" 를 실행하여 Remote Debug Server를 실행합니다. (Vista 이후 PC인 경우 관리자 권한으로 실행합니다.)
실행하면 아래와 같이 창이 뜨는데, 옵션 설정하는 화면을 엽니다.
Options 설정 메뉴에서 "No Authentication (native only)"를 선택하고 "Allow any user to debug"를 체크합니다. 이 설정은 재실행하면 초기화됩니다. (이렇게 하지 않고 Windows login 계정과 Password를 일치시키면 될것 같긴 한데.. 해보면 잘 안됩니다. ^^)
만약 로컬 보안정책 상의 문제로 인해 디버깅이 불가능한 상황이라면 아래와 같은 창이 뜹니다.
그러면 "제어판 > 관리도구 > 로컬 보안 정책" 에서 로컬보안정책을 수정해줍니다.
"보안설정 > 로컬 정책 >보안 옵션" 에서 "네트워크 액세스 : 로컬 계정에 대한 공유 및 보안" 항목이 "게스트 전용 - 로컬 사용자를 게스트로 인증" 으로 설정되어 있을 것입니다.
해당 항목을 더블클릭하여 아래와 같이 "일반 - 로컬 사용자를 그대로 인증"으로 수정한 후 저장합니다.
혹시, 윈도우즈 방화벽 설정이 되어 있을 경우 아래와 같은 경고창이 뜰 수 있으니 적당히 방화벽을 해제해줍니다.
가급적이면 Debugger PC와 Debuggee PC 모두 해제해주는 것이 좋습니다.
성공적으로 Remote Debug Server 모듈이 실행되면 아래와 같이 Tray Icon이 나타납니다.
자, 이제 Debuggee PC에 준비는 끝났습니다.
디버깅할 모듈을 새로 빌드하여 Debuggee PC의 실행 위치에 복사해 넣습니다. (만약 PDB가 Match 되기만 한다면 굳이 새로 빌드할 필요는 없습니다.)
이제 Debugger 쪽의 설정을 해봅시다.
Visual Studio의 프로젝트 설정 창을 엽니다.
Project Setting 창에서 "Configuration Properties > Debugging" 탭을 펼친 후
- Debugger to launch 항목을 "Remote Windows Debugger"로 설정해 줍니다. (디폴트는 "Local Windows Debugger")
- Remote Command : Debuggee PC에서 실행시킬 명령어를 입력해 줍니다. 디버깅할 모듈이 exe라면 exe의 Full Path를 입력해주면 되겠지만, DLL이라면 DLL을 로딩할 Host Exe의 경로를 입력해주어야 하겠지요.
- Command Arguments : 말그대로 실행할 때 인자가 필요하다면 입력해줍니다.
- Remote Server Name : Debuggee PC의 IP주소를 적어줍니다. 만약 동일 Subnet이라면 NETBIOS Name을 적어주어도 됩니다.
- Connection : "Remote with no authentication (Native Only)"를 선택해줍니다. 이부분은 Debuggee PC의 설정과 일치시켜야 하겠지요?
- Debugger Type : 이부분은 상기 "Connection" 항목을 설정하면 자동으로 "Native Only"로 설정됩니다.
- Attach : 만약 서비스 프로세스를 디버깅하는 경우 등, 이미 실행중인 Process에 Attach해야 하는 경우엔 이부분을 "Yes"로 설정해줍니다. "No"로 설정하면 로컬디버깅할 때와 마찬가지로 디버거가 디버깅 대상 프로세스를 실행시켜줍니다.
자 모든 설정이 끝났으면, Visual Studio에서 BreakPoint를 설정한 후 F5 (Go)를 누르거나, F10 등을 눌러 디버깅을 시작합니다.
Debugger PC에서 디버깅을 시작하면, Debuggee PC에서는 아래와 같이 해당 프로세스가 실행되면서 디버깅이 시작됩니다.
정상적으로 연결되었을 경우 Remote Debug Server에서는 아래와 같은 메시지를 확인할 수 있습니다.
이 상태에서 Debugger PC의 Visual Studio를 통해 Local Debugging과 동일하게 디버깅이 가능합니다. (Break Point 설정, Memory / 변수 / Register 값 조회 등등... )
만약 서비스 프로세스를 디버깅하는 등, 이미 실행중인 프로세스를 디버깅해야 할 경우 Visual Studio의 아래 항목을 설정해주면 됩니다.
실제로 해보면.. 그닥 어렵지 않으면서도 유용한 디버깅 방법입니다. ^^
'C++ > Debug' 카테고리의 다른 글
Debugging Tips (10) - 메모리 덤프 분석시 CallStack 수동으로 재구성하기 (6) | 2012.03.07 |
---|---|
Windbg 에서 IAT 확인하는 방법 (0) | 2012.01.12 |
Debugging Tips (7) - Application Memory Dump 분석하기 (part 2) (3) | 2010.08.11 |
Debugging Tips (6) - Application Memory Dump 분석하기 (part 1) (2) | 2010.07.25 |
IDA에 Debug Symbol 경로 설정하기 (2) | 2009.12.04 |