패킷분석

[패킷분석] TCP 3-Way Handshake / 4-Way Handshake

HoOn_Y 2024. 12. 18. 05:59
TCP?

 

TCPTransmission Control Protocol의 약자로 신뢰성 있는 연결을 보장하는 전송계층 프로토콜이다.

 

 

TCP의 주요 특징
  1. 연결 지향(Connection-oriented) 프로토콜
    • 데이터를 전송하기 전에 3-Way Handshake를 통해 통신 연결을 설정한다.
    • 통신이 끝나면 4-Way Handshake로 연결을 정상적으로 종료한다.
  2. 신뢰성 보장
    • 데이터가 손실되거나 중복될 경우 재전송을 통해 데이터의 무결성을 보장한다.
    • 수신 측에서 데이터의 도착 여부를 확인하는 ACK(확인 응답) 메커니즘을 사용한다.
  3. 순서 보장
    • 전송된 데이터는 시퀀스 번호(Sequence Number)를 통해 순서를 보장하며, 패킷이 순서대로 도착하지 않으면 수신 측에서 재정렬한다.
  4. 흐름 제어 및 혼잡 제어
    • 흐름 제어: 수신 측의 처리 속도에 맞게 데이터를 전송한다. (윈도 크기 사용)
    • 혼잡 제어: 네트워크 혼잡 상황을 감지하고 전송 속도를 조절한다.

 

 

 

TCP 3-Way Handshake

TCP 3-way Handshake의 과정을 와이어샤크 패킷 분석을 통해 알아보는 시간을 가져보도록 하겠다.

 

 

 

1. 172.30.1.67 > 211.115.106.209

로컬PC에서 해당 아이피로 접속을 시도하려고 한다.

66은 패킷의 크기이다.

 

52808은 클라이언트가 서버로 접속할 때 할당한 동적포트이다.

동적포트는 49152 ~ 65535범위 내에서 랜덤으로 할당된다.

 

80은 HTTP의 포트번호이다. 따라서 웹서버로의 연결을 시도하는 것이다.

 

[SYN]은 클라이언트가 서버에게 서버 접속을 하고 싶다는 요청 메시지를 뜻한다.

Seq=0순서번호이다. TCP연결은 순서를 보장한다.

 

뒤의 Len=0데이터가 패킷에 포함되지 않았다는 것이다.

앞의 66헤더 필드옵션 필드만 포함된다.

 

 MSS(Maximum Segment Size)는 최대전송데이터크기를 뜻하고

WS는 윈도 스케일, SACK_PERM (Selective Acknowledgment Permitted)은

선택적 확인 응답을 뜻한다. 다만 우리가 알아볼 유의미한 데이터들은

 

출발지, 목적지 아이피, 포트 번호, [SYN], [SYN-ACK], [ACK]등의 메시지, Sequence Number이다.

 

 

 

2. 211.115.106.209 > 172.30.1.67

이번엔 웹서버에서 클라이언트로 응답을 하는 과정이다.

 

 

[SYN, ACK] 메시지는 앞서 클라이언트가 요청한 [SYN] 메시지를 받았다고 확인차 회신하는 것이다.

Seq=0은 서버가 자신의 초기 시퀀스 번호를 0으로 시작함을 의미한다.

Ack=1클라이언트의 다음 예상 시퀀스 번호(0+1)를 의미한다.

 

Seq 초기번호를 제외한 그다음 번호들, Ack 번호들은 어떻게 계산되는 건지 아직 정확히 이해하지는 못했다.

 

 

 

 

3. 172.30.1.67 > 211.115.106.209

마지막으로 최종 연결이 완료되는 과정이다.

 

클라이언트에서 서버로 [ACK] 메시지를 보냄으로써 최종 연결된다.

여기서 [ACK]는 [SYN, ACK] 메시지를 받았다는 확인 메시지이다.

 

 

 


 

 

4-Way HandShake

 

이번엔 4-Way HandShake에 대하여 알아보도록 하겠다.

3-Way HandShake가 연결을 위해서였다면 4-Way HandShake는 연결 종료의 과정에서 수행된다.

그리고 연결을 닫을 때에는 3-way HandSahke와 달리 양방향 통신을 독립적으로 종료해야 하므로

4단계로 이루어진다.

 

 

1. 클라이언트 > 서버 

 

[FIN] 메시지(패킷)를 서버에 요청한다.

더 이상 보낼 데이터가 없음을 FIN으로 알린다.

 

클라이언트는 서버로부터의 ACK 응답을 기다리는 FIN_WAIT_1 상태가 된다.

서버는 

 

시퀀스 번호(Seq): 현재 클라이언트의 마지막 전송된 데이터 바이트 번호.

ex) 172.30.1.67 → 211.115.106.209  TCP  [FIN]  Seq=1000  Ack=2000

 

2. 서버 > 클라이언트

클라이언트로부터 받은 [FIN] 메시지를 수신하고

[ACK] 메시지(패킷)를 보낸다. 아직 서버는 닫힌 것이 아니라

남은 데이터 전송이 있다면 끝날 때까지 이루어지게 된다.

 

클라이언트는 서버가 모든 데이터 전송이 끝내고 보낼 FIN 메시지(패킷)를 기다린다. FIN_WAIT_2

서버는 보낼 데이터가 남아있다면 끝날 때까지 전송하는 CLOSE_WAIT 상태가 된다.

(이 시점에서 '클라이언트 > 서버' 로이 연결은 완전히 종료된 것이다.)

 

응답 번호(Ack): FIN 패킷의 시퀀스 번호 + 1

ex) 211.115.106.209 → 172.30.1.67  TCP  [ACK]  Seq=2000  Ack=1001

 

 

3. 서버 > 클라이언트

서버도 더 이상 보낼 데이터가 없으면 종료 연결 요청 메시지(패킷)인

[FIN]을 보낸다.

 

클라이언트는 서버의 연결 종료 요청을 받아들이고 이에 대한 확인 응답으로

ACK를 보낼 준비를 한다. TIME_WAIT 상태가 된다.

 

서버는 마지막 ACK 응답을 기다리는 LAST_ACK 상태가 된다.

 

시퀀스 번호(Seq): 서버의 마지막 전송된 데이터 바이트 번호.

ex) 211.115.106.209 → 172.30.1.67  TCP  [FIN, ACK]  Seq=2000  Ack=1001

 

4. 클라이언트 > 서버

클라이언트는 서버로부터 받은 [FIN] 패킷을 확인하고 최종적으로 연결을 종료하겠다는 확인 응답인

[ACK] 패킷을 서버로 전송한다. 비로소 완전히 TCP 연결을 종료한다.

 

클라이언트는 최종 확인 메시지로 [ACK]를 보내고 TCP 연결을 종료한다. CLOSED 상태가 된다.

서버도 마찬가지로 TCP 연결을 종료하면서 CLOSED 상태가 된다.

(이 시점에서 '서버 > 클라이언트' 로의 연결은 완전히 종료된 것이다.)

(하지만 마찬가지로 '클라이언트 > 서버'도 먼저 종료됐기 때문에 양방향 TCP 통신이 이 단계에서 완전 종료됐다.)

 

응답 번호(Ack): 서버 FIN 패킷의 시퀀스 번호 + 1

ex) 172.30.1.67 → 211.115.106.209  TCP  [ACK]  Seq=1001  Ack=2001