디버거(DeBugger) 사용법( GDB ) / 바이트 오더( byte order )에 대해서 정리한다.
! 디버거 사용법
- De + Bugger
- Bug: 벌레( 그레이스 호퍼 )
- 프로그램에 오류를 일으킬수 있는 존재( Bug )
- De Bug -> Debugging -> DeBugger
- linux에는 GDB가 있다.
!! gcc 컴파일시에 -g 옵션을 이용하면 디버깅 모드로 컴파일이 된다.
( 컴파일시 디버깅에 대한 정보를 담는다 )
! 디버거를 통한 프로그램의 실행
#> ./myshell -> execve -> 프로세스
- 그냥 실행할 시에는 실행되는 프로세스에 접근 불가
#> ./myshell -> 디버거 -> execve -> 프로세스
- 디버거를 통해 프로세스를 직접 제어(접근)
!! 디버거에서는 항상 절대 경로로 실행된다.
!!! 디버거의 명령어는 인터넷 검색을 통해서 사용할때마다 참고할 것!!
1. 코드 확인
- gdb [파일]
- C로 작성된 경우 entry point -> main
- assembly로 작성된 경우 entry point -> _start
* 확인을 할때 처음 entry point부터 시작해서 프로그램의 전체적인 구조와 동작방식을 파악해 나간다.
!! gdb에서는 INTEL 방식이 아닌 AT&T 방식을 지원한다.
( 인텔 방식으로 보려면 set disassemble-flavor intel 명령을 이용해서 변경 해준다 )
!! gdb에서는 tab키 기능을 지원해준다.
(gdb) disassemble 주소
* 위 명령을 이용하면 프로그램의 코드를 해당 주소부터 시작해서 disassemble 된 형태로 보여준다.
( 보통 프로세스의 흐름을 파악할때는 entry point부터 시작해서 전체 어셈블리 코드를 보면서
파악하기 때문에 위에서는 어셈블리로 컴파일된 프로그램이기 때문에 _start로 entry point를 지정 해줬다 )
( GDB에서는 AT&T 방식을 지원하기 때문에 INTEL 방식으로 보는게 편하다면 set disassembly-flavor intel 명령을
이용해서 출력해주는 방식을 INTEL 방식으로 설정 해줄수 있다. )
2. 프로그램 실행 제어
1). 브레이크 포인트
(gdb) break *(주소)
* break를 주소에 걸어두게 되면 해당 주소가 실행될때 break가 걸리게 된다.
( 즉, 해당 코드가 실행되지 않는다면 break는 걸리지 않게 되니 주의한다!! )
(gdb) continue
* continue 명령을 이용하면 break 상태에서 다시 break가 걸리기 전까지 실행이 된다.
( continue로 실행을 했을때 break가 없다면 프로세스의 끝까지 실행이 된다 )
* 브레이크 포인트는 해당 명령이 실행될때마다 멈추게 된다.
( 해당 명령어가 실행되지 않으면 브레이크에 걸리지 않게 된다!! )
! 소프트웨어 브레이크 포인트( gdb가 사용하는 브레이크 포인트 )
- 갯수의 제한없이 설정이 가능
- 해당 주소의 명령어가 실행되지 않으면 브레이크도 걸리지 않는다.
( break 명령으로 break point를 지정해주게 되면 해당 주소 이전까지만 명령이 실행되게 된다 )
( break point를 만난 이후에 다음 break point까지 실행을 하고 싶다면 continue 명령을 이용한다 )
* 프로세스의 실행과정에 대한 흐름이나 메모리 상태를 한단계씩 파악하려고 할때는
si 명령이나 ni 명령을 이용해준다!!
3. 출력 명령어: x, print
- 메모리 덤프: x/출력갯수/출력형태/출력단위 메모리주소
- 기본형태 ( 1개, 16진수, 4바이트 )
(gdb) x/1xh
- 출력형태: 10진수( d ), 8진수( o ), 16진수( x ), 문자열( s ), 명령어( i )
- 출력단위: 1바이트( b ), 2바이트( h ), 4바이트( w )
* 다음 명령 실행시 출력 형태와 단위를 지정하지 않는다면 마지막에 지정한 출력 형태와 출력 단위를 그대로 사용한다.
* 주소를 붙여주지 않으면 명령을 실행 할 때마다 그다음 주소를 계속해서 출력한다.
! 바이트 오더
- CPU가 메모리에 저장하는 바이트의 순서
1). little-endian
- 일반적으로 사람이 읽는 순서 왼쪽 -> 오른쪽 방식이 아닌 바이트 단위로 거꾸로 저장
- intel CPU는 little-endian 방식을 사용
- 0x12345678 -> 0x78563412
2). big-endian
- 0x12345678 -> 0x12345678
!! x 명령어를 사용하면 해당 값을 주소로 인식해서 접근하기 때문에 사용할 때 주의가 필요하다.
!! 디버거 모드에서 프로세스를 한줄씩 실행하려면 si 명령이나 ni 명령을 사용한다.
!! 현재 사용하는 gdb 버전에서는 프롤로그와 에필로그 부분에서는 si 명령을 이용해서 실행해줘야 한다.
( 그 외에는 ni 명령을 사용하고 두 명령의 차이점은 si 명령을 사용하면 함수로 실행을 따라 들어가게 되고
ni 명령의 경우에는 함수로 따라 들어가지 않고 다음 명령을 실행하게 된다. )
'프로그래밍 > SYSTEM HACKING' 카테고리의 다른 글
[SYSTEM HACKING] 시스템 취약점 - 버퍼 오버플로우( Buffer Overflow ) / 인자에 대한 취약점 및 표준입력에서 취약점 (0) | 2017.11.16 |
---|---|
[SYSTEM HACKING] GDB를 이용한 바이너리 분석 실습 (0) | 2017.11.13 |
[SYSTEM HACKING] 시스템 콜 실습 ( mymkdir, mycat, myshell ) (0) | 2017.11.02 |
[SYSTEM HACKING] main 함수의 인자 / 시스템 프로그래밍( 시스템 콜 ) (0) | 2017.11.01 |
[SYSTEM HACKING] 어셈블리 call & jmp 명령의 차이 / 스택 메모리를 이용한 인자 전달 / reverse.asm 지역변수 사용해서 표현하는 실습 (2) | 2017.11.01 |
댓글