1. RDT란

 

RDT란 Reliable data transfer의 약자로, TCP에서 신뢰성 있는 데이터 전송을 보장하기 위한 개념이다. RDT는 TCP가 UDP와 구분되는 가장 큰 특징이라고 볼 수 있으며, 사실상 TCP 네트워킹에서 가장 중요한 개념으로 봐도 무방하다.

네트워크는 공식적으로 7개의 계층으로 이루어져 있다(OSI 7 Layer 참고). RDT란 이때, 상위 계층에서 전송한 데이터가 손상되거나 손실되지 않도록 보장하는 개념으로써, 하위 계층에서 신뢰성을 보장할 수 없기 때문에 특정 계층에서 신뢰성을 보장하도록 하면, 그 상위 계층의 신뢰성은 모두 보장된다는 개념으로 볼 수 있다.

RDT 개념

패킷을 송신하는 경우, 상위레이어에서 rdt_send()를 이용하여 RDT 프로토콜로 데이터를 전송한다. 이후 RDT 프로토콜에서 신뢰할 수 없는 채널인 하위 레이어로 보낼 때, udt_send()를 이용하여 패킷을 전송한다.

패킷을 수신하는 경우, rdt_rcv()를 통하여 하위 레이어에서 RDT 프로토콜로 데이터를 전송하고, RDT 프로토콜에서 상위 레이어로 데이터를 보낼 때 deliver_data()를 호출하여 데이터를 전송한다.

즉, 하위 Unreliable Channel을 통과하더라도, 신뢰성 있는 전달을 보장하는 것이 RDT 프로토콜의 기본이라고 볼 수 있다.

 

2. RDT 1.0

 

RDT 1.0은 네트워크의 모든 채널이 완벽하게 신뢰성 있다고 가정할 때 사용하는 방식으로, 단순히 데이터의 송신 및 수신만 이루어지는 구조이다. 채널이 안정적이기 때문에, 패킷 손실 등의 에러가 전혀 발생하지 않는다고 가정한다.

RDT 1.0

rdt_sender는 상위 계층에서 데이터를 받고 데이터를 포함한 패킷을 생성한 뒤, 이를 송신한다.

rdt_receiver는 하위 채널에서 패킷을 수신하고, 데이터를 추출한 뒤, 이를 상위 계층으로 전달한다.

이때 만약 하위 채널이 안정적이지 못하다면, 그래서 비트 오류가 발생할 수 있다는 것을 가정하여 RDT 2.0으로 발전하게 된다. 

 

3. RDT 2.0

 

RDT 2.0부터는 비트 에러가 발생할 수 있다고 생각하고 이때의 에러 처리에 대해 생각하고 설계를 진행하였다. 따라서 ACK, NAK 라는 신호를 보내는데, 이를 통해 수신된 패킷이 손상되었는지 여부를 수신자가 송신자에게 반환해 준다.

RDT 2.0

이때 rdt_sender는 두 가지의 상태를 갖는다. sender는 파일을 보낸 후, ACK/NAK 신호를 기다린다. 이후 오류가 없다면 상위 계층에서 데이터를 기다리는 상태로 돌아간다. NAK가 수신된다면 데이터를 재전송하고, 또다시 ACK/NAK 신호를 기다린다.

rdt_receiver는 단일 상태를 갖는다. 패킷이 도착했을 때, 수신된 패킷의 손상 여부에 따라 ACK/NAK로 응답하고, NAK를 응답한 뒤에는 다시 패킷이 도착하는 것을 기다린다.

RDT 2.0은 이론상 잘 동작하는 것처럼 보이지만, 치명적인 결함이 존재한다. ACK와 NAK 패킷 자체의 손상을 가정하지 않는다는 점이다. 예를 들어, 수신자가 ACK를 보내야 하는데, 이것이 손상되어 제대로 전달이 되지 않는다면 송신자는 패킷을 수신 측으로 다시 보내야 할 것이다. 이때 수신 측은 혼란이 있을 것이다. 아까 받은 데이터에 대한 ACK를 보냈는데, 동일한 데이터가 다시 왔으니 해당 데이터가 다음 데이터인지 중복으로 온 이상 있는 데이터인지 확인이 불가능하다. 따라서 이런 문제점들을 해결하기 위해 RDT 2.1이 도입되었다.

 

4. RDT 2.1

 

RDT 2.1은 RDT 2.0에 시퀀스 넘버를 추가한 방식이다. RDT 2.0에 비해 이런 순서 번호를 갖고 있는 이유는 각 패킷에 대한 순서를 정함으로써 해당 패킷이 새로운 데이터를 전송하는 것인지 NAK를 받아 재전송한 것인지를 구분하기 위한 것이다. 만약 송신자가 NAK 1이라는 데이터를 받으면, 송신자는 1번 패킷이 문제가 있다는 것을 확인할 수 있다. 그림에서는 편의상 시퀀스 넘버가 0, 1 두가지만 있다고 가정한다.

RDT 2.1 Sender

rdt_sender는 총 4가지 상태가 존재한다. 패킷을 만들고 시퀀스 0을 넣어서 전송하고, 상태를 전환한 뒤 ACK/NAK를 기다린다. 이후 rdt_receiver가 0번 패킷에 대한 ACK/NAK를 전송해 주고, ACK를 받으면 시퀀스 1을 넣은 새로운 패킷을 보내 주며, NAK를 받거나 오류가 있는 패킷이 들어온다면(corrupt 발생), 시퀀스 0을 넣은 기존 패킷을 보낸다. 따라서 0번 패킷을 보내기 전 상태, 0번 패킷을 보내고 ACK/NAK를 기다리는 상태, 1번 패킷을 보내기 전 상태, 1번 패킷을 보내고 ACK/NAK를 기다리는 상태 총 4가지 상태가 존재하게 된다.

RDT 2.1 Receiver

rdt_receiver는 2가지 상태가 존재한다. 0번 패킷을 보내기 전 상태, 1번 패킷을 보내기 전 상태이다. 1번 패킷을 보내기 전 상태에서 1번 패킷이 수신되면 ACK를 보내면 되고, 0번 패킷이 도착하면 0번 패킷이 중복도착했으므로 무언가 중간에 문제가 생겼음을 확인하고, 0번 패킷에 대한 ACK를 보낸다. 그 외 NAK를 보내는 상황은 RDT 2.0과 동일하게 이루어진다.

 

5. RDT 2.2

 

RDT 2.2는 RDT 2.1에서 NAK 신호를 삭제한 프로토콜이다. NAK 대신 가장 최근에 잘 받은 패킷에 대한 ACK를 보냄으로써 NAK를 보내는 것과 동일한 효과를 얻을 수 있다.

RDT 2.2 Sender
RDT 2.2 Receiver

RDT 2.1과 동일하게 이루어지지만, 송신 측이 1번 패킷을 보냈을 때, 수신 측에서 1번 패킷에 대한 ACK가 아니라 0번 패킷에 대한 ACK가 돌아온다면 송신 측은 1번 패킷의 전송에 문제가 있다는 것을 확인하고 재전송하게 된다.

그러나 RDT 2.2까지 적용하더라도 전송 도중 패킷이 유실될 수 있는 상황은 확인이 불가능하다. 모종의 이유로 데이터 패킷 자체가 유실될 수 있는데, 이러한 문제를 해결하기 위해 RDT 3.0이 등장했다.

 

6. RDT 3.0

 

RDT 3.0에서는 일정 시간을 기다리는 timer를 이용하여 패킷 손실을 검출하고, 손실이 발생했을 때 어떤 행동을 해야 하는지 판단할 수 있다. 타이머는 100% 패킷 손실이 일어났다고 보장할 수는 없지만, 손실이 일어났다고 판단할 수 있는 시간을 선택할 수 있다. 만일 ACK가 특정 시간 안에 수신되지 않는 경우 패킷이 재전송될 수 있으며, 이 경우는 특정 패킷이 전송 딜레이가 너무 커져서 타이머 시간보다 늦게 도착하는 경우에도 패킷이 재전송될 수 있다는 것을 의미한다. 따라서 중복 데이터 패킷이 존재할 수 있으며, 이는 RDT 2.2에서 시퀀스 넘버를 이용하여 이미 해결한 부분이다.

RDT 3.0 Sender

RDT 3.0의 receiver의 경우, RDT 2.2의 receiver와 동일한 역할을 한다.

 

RDT 3.0까지 발전하면서 네트워크에서 신뢰성 있는 전송에 대한 성능은 향상되었지만, 기본적으로 RDT는 전송 후 대기하는 방식의 프로토콜이기 때문에, 현대 고속 네트워크에 대한 요구를 모두 만족시키지는 못했다. 따라서 이러한 문제점들을 해결하기 위해, ACK를 기다리지 않고 여러 패킷을 전송하도록 허용함으로써 성능 향상을 가져올 수 있다. 이러한 기술을 파이프라이닝이라고 하며, 파이프라이닝 기술을 위해서 고려해야 할 다양한 사항들이 생겨났다.

- Sequence Number 범위의 증가 : 여러 패킷을 보내야 하므로 0과 1로는 부족함

- 버퍼 필요 : 송/수신측에서 모두 각각 여러 패킷을 담을 수 있는 버퍼가 필요함

- 파이프라이닝에서의 오류 회복 방법 : 파이프라이닝 시스템에서 패킷 손실 및 지연 패킷에 대한 처리 방식이 필요

따라서 해당 방법을 처리하기 위해 Go-Back-N 방식과 Selective Repeat 방식을 이용하여 패킷 손실 및 지연 패킷에 대한 처리를 진행하게 된다.

반응형

'Development > Network' 카테고리의 다른 글

내 PC에 구글 웹 페이지가 보이기까지  (0) 2021.03.03

+ Recent posts