[Network] UDP

park9910·2022년 5월 21일
0

윤성우의 열혈 TCP/IP 소켓 프로그래밍을 보며 내용과 생각을 정리하는 글입니다.

지난 글에서 네트워크 프로그래밍 이란 소켓을 통해 데이터를 송수신 하는 프로그램을 작성하는 것 이라고 하였다.

이어서 데이터 송수신 방법에 따라 TCP/UDP 로 소켓 종류를 나누었는데, 이번 글에서 알아볼 것은 UDP 이다.


UDP

UDP 는 User Datagram Protocol 의 약자로 데이터를 Datagram 이라는 메세지 단위로 전송이 되며, 그 크기는 65535 바이트이다.

TCP 와는 다르게 데이터의 경계가 정해져 있고, 그 범위를 넘으면 데이터가 나눠서 보낸진다.

여기서 다시 나오는 이야기가 데이터의 경계인데 일전에 이야기 했듯이 TCP 와 UDP 의 데이터 경계의 의미는 한번에 보내진 데이터(패킷 모음)을 여러번에 걸쳐서 받을 수 있냐는 것이다.

왜 TCP 가 데이터의 경계를 가지지 않는가에 대해서는 이 글을 쓰면서 생각하건데, TCP 방식에서는 1:1 통신 구조, 즉 통신 대상이 명확하기 때문에 상대방이 보낸 데이터를 어떻게 읽던지 크게 제한을 둘 필요가 없어 보인다. 또 어차피 손실된 데이터 없이 받을 수 있기 때문에 더더욱이 문제가 되지 않는다.

반대로 UDP 는 송신자가 다수일 수도 있고, 수신자 입장에서는 날아온 데이터가 누가 몇개를 보냈는지 알 수 있는 방법이 없기 때문에 하나의 데이터그램 단위로 수신하게 된다.

UDP 는 비연결형 통신 을 지향하는데, 비연결형이란 송신자와 수신자간의 연결이 따로 존재하지 않는다는 것이다.

연결이 존재하지 않는다는 것은 수신측에서 송신자가 누군지 모른다는 것을 의미하고 그렇기 때문에 전송과정에서 데이터가 유실되었는지 여부를 확인할 수 없다.

TCP 통신에서는 송신자가 "0번 부터 상자 10개 보냈어~" 라고 한다면 수신측에서 0번부터 9번까지 상자가 잘 도착했는지 확인하고 누락된게 있으면 "0번 부터 상자 10개 다시 보내줘~" 의 방식으로 패킷의 안정적인 전송을 보장했는데

UDP 수신자가 "어 패킷 왔네" 하고 데이터를 받으면 그냥 끝이다 송신자가 누군지 보낸 데이터가 이거 하나 뿐인지는 궁금해하지 않는다

송신지가 어딘지 알 순 있다

특징

  • 통신 절차가 간단하여 데이터 송수신 속도가 빠르다
  • 연결이 없기 때문에 매 전송시 마다 목적지(sockaddr)를 명시해야 한다
  • 데이터가 잘 도착하였는지 확인할 수 있는 방법이 없다
  • 데이터 전송 순서가 바뀔 수 있다
  • 서버 소켓의 개념이 존재하지 않는다
  • 1:N N:M 통신도 가능하다

코드

udp 소켓 생성

#include <sys/socket.h>
#include <arpa/inet.h>
socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)

bind : TCP 와 동일하지만, 클라이언트는 따로 bind 과정을 거치지 않는다
sendto 호출 시 자동으로 IP 와 port 가 할당되기 때문

데이터 전송

ssize_t sendto(int sock, void *buff, size_t nbytes, 
int flags, struct sockaddr *to, socklen_t addrlen);

TCP 와 다른 점은 TCP 는 connect 로 한번 연결해놓으면 socket 을 통해 데이터가 전송가능한 반면 UDP 는 coonection 의 개념이 없기 때문에 매 데이터 전송 시 마다 이렇게 목적지 정보를 명시해야한다.

sock : 데이터를 보낼 소켓
buff / nbytes : 데이터를 얼마만큼 보낼지
flags : 전송 옵션 지정
to : 전송지 정보
addrlen : 전송지 정보 크기

데이터 수신

recvfrom(int fd, void *buff, size_t, nbytes, int flags,
struct sockaddr *from, socklen_t *addrlen)

UDP 통신은 1:N 즉 전송지가 여러곳이 될 수 있다. 따라서 전송지의 정보를 식별할 수 있는 방법을 제공한다.

하지만 여전히 전송자가 총 몇개의 데이터를 보냈는지에 대한 정보는 존재하지 않는다.

* connect 를 사용하여 connected UDP 를 구현할 수 있지만 실질적으로 연결된 것은 아니고 서버 주소 정보만을 저장한다는 의미를 가진다

profile
Keep Practicing

0개의 댓글