BSD 소켓이란?
BSD소켓은 인터넷 소켓 또는 Unix domain 소켓에 대한 인터페이스이며, 프로세스 간의 통신(IPC)에 쓰인다. Berkeley Software Distribution에서 개발되어 BSD 소켓이라는 이름이 붙었으며, POSIX socket 이라고도 불린다. 이 인터페이스는 현재 인터넷에서 실행되는 응용 프로그램들의 표준 인터페이스이다.
흔히 소켓은 인터넷 통신 과정에서 사용하는 것으로 알려져 있다. 인터넷 통신 과정에서 소켓을 많이 활용하지만, 같은 디바이스 내에서 서로 다른 프로세스가 통신을 하는 과정에서도 소켓이 활용된다.
소켓의 연결 과정
소켓이 연결되는 과정은 위의 그림과 같다. 크게 서버와 클라이언트로 나누어서 생각해 보자
Server
1. Socket : 소켓 객체를 생성한다. 각 소켓은 file descriptor로 구분된다.
2. Bind : 1에서 생성한 소켓에게 IP 주소와 Port 번호를 연결한다.
3. Listen : 소켓은 클라이언트의 연결 요청을 기다린다.
4. Accept : 이 과정에서 서버는 소켓을 하나 더 생성한다. 클라이언트 소켓에서 연결 요청이 왔을 때 함수가 불려지며, Listen 소켓은 현재 클라이언트 말고 다른 클라이언트에서 올 수도 있는 요청을 대기해야 하기 때문에, 연결 요청이 온 소켓에 대해서 새로운 소켓을 만들어 연결해 준다.
5. Send & Receive : 연결을 맺은 클라이언트 소켓과 데이터를 주고받는 과정이다.
6. Close Socket : 클라이언트 소켓이 연결을 종료하면 연결되어 있던 소켓을 반환한다.
Client
1. Socket : 서버와 같이 소켓 객체를 생성하는 과정이다.
2. Connect : 서버와는 달리 클라이언트 소켓은 bind 과정이 빠져있다. 이는 클라이언트가 연결을 요청하는 주체이기 때문에 굳이 포트 번호를 알고 있을 필요가 없기 때문이다. connect 과정에서 소켓에게는 임의의 소켓 번호가 부여되며, 서버 소켓과 연결을 맺는다(3-way handshake).
3. Send & Receive : 연결을 맺은 서버 소켓과 데이터를 주고받는 과정이다.
4. Close Socket : 서버와 연결을 종료하고 소켓에게 할당된 자원을 반납한다.
위의 과정을 보면, 소켓 통신은 1:N 통신이 아닌 1:1 통신을 지원한다는 것을 알 수 있다. 물론 이러한 특징은 TCP Socket에만 국한되며, UDP Socket은 서버에서 하나의 소켓이 여러 개의 클라이언트 소켓과 통신할 수 있다. 이는 TCP와 UDP 프로토콜의 연결 지향성의 차이에서 기인한다.
Unix 시스템에서는 소켓 또한 하나의 파일처럼 인식하며, 네트워크 입출력 또한 파일 입출력과 유사하게 다룬다. 하지만 TCP packet의 경우 payload의 크기가 커지면 패킷을 쪼개서 보내기 때문에, read 함수 한 번으로는 모든 데이터를 읽을 수 없다. 이러한 점을 보완하기 위해 실제 소켓 입출력 시 버퍼를 이용하는 경우가 많고, 버퍼를 이용하여 입력을 받거나 쓰는 함수는 write, read 함수의 래핑 함수이다.
이렇게 소켓끼리 연결을 맺고 통신하는 과정을 살펴보았다. 물론 조금 더 정확한 이해를 위해서는 TCP Connection이 맺어지는 과정, 유닉스 시스템의 buffered I/O 등 추가적으로 알아야 하는 내용들이 있는데, 이 내용들은 다음에 이어서 다루자..!