tcpdump를 통해 이해할 수 있는 TCP 연결 만들기

7894 단어 TCPtcpdump
본 항목에서 tcpdump 명령을 사용하여 연결의 구축, 끝을 확인하고 TCP의 연결에 대한 이해를 깊이 있게 합니다.

TCP 접속의 목적 이해


TCP의 연결을 이해하는 데는 주로 다음과 같은 장점이 있다.
  • NW 연결(주로 TCP 연결을 둘러싸고)의 문제 분할·고장 제거력이 향상되었다.
  • NW 관련(주로 TCP 연결을 둘러싸고)의 테스트 용례 관점을 배울 수 있다.
  • NW와 관련된 통용어를 배울 수 있다.
  • TCP 접속


    TCP를 통해 데이터를 전송할 때는 데이터를 전송하기 전에 연결을 설정해야 한다.
    TCP 접속을 설정할 때는 다음 3가지 방법으로 처리됩니다.
  • TCP 클라이언트(TCP A)가 TCP 서버(TCP B)에 접속 구성 요청을 전송합니다.(syn)
  • 연결 요청을 받은 TCP 서버(TCP B)가 TCP 클라이언트(TCP A)에게 응답 확인 및 연결 요청을 반환합니다.(syn+ack)
  • 연결 요청을 받은 TCP 클라이언트(TCP A)가 TCP 서버(TCP B)로 응답 확인을 반환합니다.(ack)

  • 3way handshake(3 Way Handshake)에 대한 자세한 내용은 다음 URL을 참조하십시오.
  • https://tools.ietf.org/html/rfc793#section-3.4
  • https://ja.wikipedia.org/wiki/Transmission_Control_Protocol#연결 설정
  • tcpdump 명령으로 상기 패키지의 절차를 실제적으로 확인합니다.

    tcpdump를 통해 이해할 수 있는 TCP 연결 만들기


    0. 사전 준비


    사용할 네트워크 명령


    이 항목에서는 다음 Linux 명령을 사용합니다.
  • tcpdump
  • 네트워크의 패킷을 출력하는 데 사용됩니다.
  • nc,telnet
  • 는 tcp 서버/클라이언트로 사용됩니다.
  • netstat
  • 접속 상태를 확인할 수 있습니다.
  • 위 명령이 설치되지 않은 경우 다음 명령을 사용하여 설치합니다.
    $ sudo yum -y install tcpdump nc telnet net-tools 
    

    1. TCP 서버 시작


    nc 명령의 l 옵션을 사용하여 모든 port 번호로 TCP 서버를 시작합니다.여기는 12345호를 사용합니다.
    $ nc -lk 12345
    
    다른 터미널을 열고 netstat 명령을 통해 12345 포트가 LISTEN인지 확인합니다.
    $ netstat -anp | grep 12345
    tcp  0  0  0.0.0.0:12345  0.0.0.0:*  LISTEN  <PID>/nc             
    
  • 1열에 프로필이 표시됩니다.tcp인지 확인해 주세요.
  • 4열에는local 주소와port이 표시됩니다.포트가 12345
  • 인지 확인하십시오.
  • 6열은 소켓의 상태를 나타낸다.LISTEN인지 확인하십시오.
  • 이로써 TCP 접속 준비가 완료되었습니다.

    2. TCP 클라이언트의 시작, 연결 설정


    텔넷이나 nc 명령으로 TCP 클라이언트를 시작하여 로컬에서 시작합니다.의 TCP 서버입니다.
    $ telnet 127.0.0.1 12345
    Trying 127.0.0.1...
    Connected to 127.0.0.1.
    Escape character is '^]'.
    
    
    다른 터미널을 열고 netstat 명령을 통해 nc와telnet의 연결이 설정되었는지 확인하십시오. (ESTABLISH)
    $ netstat -anp | grep 12345
    tcp  0  0 0.0.0.0:12345     0.0.0.0:*        LISTEN      <PID>/nc
    tcp  0  0 127.0.0.1:<port>  127.0.0.1:12345  ESTABLISHED <PID>/telnet
    tcp  0  0 127.0.0.1:12345   127.0.0.1:<port> ESTABLISHED <PID>/nc 
    
    두 번째 줄은 TCP 클라이언트 텔넷 프로세스의 플러그인입니다.
    * 5열에는 Foreign 주소가 표시됩니다.nc LISTEN에서 만든 12345 port인지 확인하십시오.
    * 6열은 소켓의 상태를 나타냅니다.ESTABLISH인지 확인하십시오.
    텔넷 실행 중인 터미널로 돌아가서 Ctrl + [과quit 명령을 사용하여 Close를 연결합니다.
    $ telnet 127.0.0.1 12345
    Trying 127.0.0.1...
    Connected to 127.0.0.1.
    Escape character is '^]'.
    ^]
    telnet> quit
    Connection closed.
    $ 
    
    이렇게 되면 연결을 구축할 수 있는 테스트가 끝났다.

    3. tcpdump를 통해 연결된 3wayhandshake(3WayHandshake)


    1. 시작한 TCP 서버가 시작되었는지 확인합니다.
    $ netstat -anp | grep 12345
    tcp  0  0  0.0.0.0:12345  0.0.0.0:*  LISTEN  <PID>/nc             
    
    tcpdump 명령을 사용하여 local interface의port 12345 실행을 지정합니다.
    $ sudo tcpdump -i lo -nnn port 12345
    tcpdump: verbose output suppressed, use -v or -vv for full protocol decode
    listening on lo, link-type EN10MB (Ethernet), capture size 65535 bytes
    
    텔넷이나 nc 명령으로 TCP 클라이언트를 시작하여 로컬에서 시작합니다.의 TCP 서버입니다.
    $ telnet 127.0.0.1 12345
    Trying 127.0.0.1...
    Connected to 127.0.0.1.
    Escape character is '^]'.
    
    
    tcpdump의 출력을 확인합니다.
    08:52:48.685189 IP 127.0.0.1.<port> > 127.0.0.1.12345:  Flags [S], seq ...
    08:52:48.685221 IP 127.0.0.1.12345  > 127.0.0.1.<port>: Flags [S.], seq ...
    08:52:48.685237 IP 127.0.0.1.<port> > 127.0.0.1.12345:  Flags [.], ack ...
    
    위의 Tcpdump 출력 형식은 다음과 같습니다.
    timestamp src > dst: flags  
    
  • timestamp: 시간 스탬프
  • src: 소스 IP를 전송합니다.포트
  • dst: 대상 IP.포트
  • flags: 플래그 S(SYN),'."(ACK)
  • 위의 그룹 캡처는 TCP 서버의 다음 동작을 보여 줍니다.
  • TCP 클라이언트(telnet)가 TCP 서버(nc)에 SYN 그룹을 보냅니다.(SYN-SENT)
  • TCP 서버(nc)는 TCP 클라이언트(telnet)에 SYN+ACK 그룹을 보냅니다.(SYN-RECEIVED)
  • TCP 클라이언트(telnet)가 TCP 서버(nc)에 ACK 그룹을 보냅니다.(ESTABLISH)
  • 다음은 서열의 개요도이다.

    다른 터미널을 열고 netstat 명령을 통해 nc와telnet의 연결이 설정되었는지 확인하십시오. (ESTABLISH)
    $ netstat -anp | grep 12345
    tcp  0  0 0.0.0.0:12345     0.0.0.0:*        LISTEN      <PID>/nc
    tcp  0  0 127.0.0.1:<port>  127.0.0.1:12345  ESTABLISHED <PID>/telnet
    tcp  0  0 127.0.0.1:12345   127.0.0.1:<port> ESTABLISHED <PID>/nc 
    

    4. tcpdump로 연결 끝 보기


    tcpdump 명령이 끝나지 않은 상태에서 텔넷 실행 중인 터미널로 돌아가서 Ctrl + [quit 명령 Close와 연결합니다.
    $ telnet 127.0.0.1 12345
    Trying 127.0.0.1...
    Connected to 127.0.0.1.
    Escape character is '^]'.
    ^]
    telnet> quit
    Connection closed.
    $ 
    
    tcpdump의 출력을 확인합니다.
    09:11:41.290540 IP 127.0.0.1.<port> > 127.0.0.1.12345:  Flags [F.], seq 1,
    09:11:41.290800 IP 127.0.0.1.12345  > 127.0.0.1.<port>: Flags [F.], seq 1,
    09:11:41.290814 IP 127.0.0.1.<port> > 127.0.0.1.12345:  Flags [.], ack 2,
    
    위의 Tcpdump 출력 형식은 다음과 같습니다.
    timestamp src > dst: flags  
    
  • timestamp: 시간 스탬프
  • src: 소스 IP를 전송합니다.포트
  • dst: 대상 IP.포트
  • flags: 플래그 F(FIN),'."(ACK)
  • TCP 클라이언트(telnet), TCP 서버(nc) 쌍방이 FIN/ACK를 보내서 연결을 끝냅니다.

    시퀀스 소스

    note left of TCP A: CLOSED
    note right of TCP B: LISTEN
    TCP A->TCP B: syn
    note left of TCP A: SYN-SENT
    note right of TCP B: SYN-RECEIVED
    TCP B->TCP A: syn + ack
    note left of TCP A: ESTABLISHED
    TCP A->TCP B: ack
    note right of TCP B: ESTABLISHED
    note over TCP A ,TCP B: ESTABLISHED
    

    경품:strace 명령으로 TCP 연결 확인


    이 항목에 사용된nc/telnet 명령을strace 명령에 전달하고 연결 요청을 보내서 시스템 호출을 확인합니다.
    nc측에서 socket,bind,listen,accept 시스템 호출을 확인할 수 있습니다.
    $ strace -Ttt -e trace=network nc -l 12345 
    15:47:30.162392 socket(PF_INET, SOCK_STREAM, IPPROTO_TCP) = 3 <0.000017>
    15:47:30.162494 setsockopt(3, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0 <0.000010>
    15:47:30.162529 setsockopt(3, SOL_SOCKET, SO_REUSEPORT, [1], 4) = 0 <0.000008>
    15:47:30.162556 bind(3, {sa_family=AF_INET, sin_port=htons(12345), sin_addr=inet_addr("0.0.0.0")}, 16) = 0 <0.000011>
    15:47:30.162592 listen(3, 1)            = 0 <0.000011>
    15:47:30.162621 accept(3, {sa_family=AF_INET, sin_port=htons(48162), sin_addr=inet_addr("127.0.0.1")}, [16]) = 4 <3.104111>
    15:47:41.423396 shutdown(4, SHUT_RD)    = 0 <0.000009>
    15:47:41.423670 +++ exited with 0 +++
    $ 
    ──────────────────────────
    
    텔넷에서는 socket,connect 시스템 호출을 확인할 수 있습니다.
    $ strace -Ttt -e trace=network telnet 127.0.0.1 12345
    Trying 127.0.0.1...
    15:47:33.266522 socket(PF_INET, SOCK_STREAM, IPPROTO_TCP) = 3 <0.000018>
    15:47:33.266617 setsockopt(3, SOL_IP, IP_TOS, [16], 4) = 0 <0.000010>
    15:47:33.266650 connect(3, {sa_family=AF_INET, sin_port=htons(12345), sin_addr=inet_addr("127.0.0.1")}, 16) = 0 <0.000116>
    Connected to 127.0.0.1.
    Escape character is '^]'.
    15:47:33.266976 setsockopt(3, SOL_SOCKET, SO_OOBINLINE, [1], 4) = 0 <0.000008>
    
    telnet> quit
    15:47:41.423280 shutdown(3, SHUT_RDWR)  = 0 <0.000171>
    Connection closed.
    15:47:41.424360 +++ exited with 0 +++
    $ 
    

    좋은 웹페이지 즐겨찾기