Socket이란?
네트워크 프로그램을 개발할 수 있도록 운영체제에서 제공하는 인터페이스라고 표현할 수 있다.
즉, 네트워크를 통해 데이터 Pecket을 주고 받는 개체인 통신 종점이다.
스트림(Stream) 이란?
- Stream Sockets − Delivery in a networked environment is guaranteed. If you send through the stream socket three items “A, B, C”, they will arrive in the same order − “A, B, C”. These sockets use TCP (Transmission Control Protocol) for data transmission. If delivery is impossible, the sender receives an error indicator. Data records do not have any boundaries.
>> 서로 연결 됨을 확인 후 데이터를 전송하는 TCP를 의미한다. - Datagram Sockets − Delivery in a networked environment is not guaranteed. They’re connectionless because you don’t need to have an open connection as in Stream Sockets − you build a packet with the destination information and send it out. They use UDP (User Datagram Protocol).
>> 연결 확인 없이 무작정 데이터를 전송하는 UDP를 의미한다. - Raw Sockets − These provide users access to the underlying communication protocols, which support socket abstractions. These sockets are normally datagram oriented, though their exact characteristics are dependent on the interface provided by the protocol. Raw sockets are not intended for the general user; they have been provided mainly for those interested in developing new communication protocols, or for gaining access to some of the more cryptic facilities of an existing protocol.
>> 프로토콜의 기본적인 stream을 의미한다.
에러 처리 관련 함수
에러 메시지를 출력하는 예제
#include <stdio.h> #include <string.h> #include <errno.h> int main(void) { printf("errno\t: %d\n",errno); printf("malloc\t: %s\n",strerror(errno)); return 0; }
출력
errno : 0 malloc : Success Press <RETURN> to close this window...
Socket 관련 함수
리눅스와 윈도우 공통으로 사용이 가능한 함수와 리눅스 전용 함수 만을 정리 되어있으며,
header 정보는 리눅스에서 사용하기 위한 header이다. 윈도우는 해당 함수를 사용하기 위한 헤더를 따로 사용해야 한다.
(대부분의 경우 윈도우는 <winsock2.h>를 사용 하면 된다.)
header : #include <sys/types.h>
#include <sys/socket.h>
int socket(int domain, int type, int protocol)
> 소켓을 초기화 하는 함수
인자 설명
- int domain : 통신 domain 지정하는 인자로 어떤 네트워크에서 사용될 socket인지 정한다.
- int type : socket의 형태를 지정하는 것으로 스트림을 의미하는
SOCK_STREAM
이 있으며, 데이터 그램을 의미하는SOCK_DGRAM
이 있다.
또한SOCK_RAW
형태로 소켓을 생성하여 직접 프로토콜 헤더를 만들 수도 있다. - int protocol : 어떤 통신 프로토콜을 사용할지 지정하는 것이다.
소켓이 정상적으로 생성되면 소켓을 구분 할 수 있는 소켓 디스크립터(socket descriptor)가 리턴 되며, 소켓을 생성하는 과정 중에서 오류가 발생하면 0보다 작은 값이 반환 된다.
header : #include <sys/types.h>
#include <sys/socket.h>
int connect(int sockfd, const strcut sockadd *addr, socklen_t addrlen)
> 연결 대기 중인 서버로 실제 연결을 맺는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const strcut sockaddr * addr : 접속하고자 하는 아이피 및 서버 포트 정보가 있는 sockaddr 구조체의 주소 값을 지정 한다.
해당 구조체는 아래와 같다.struct sockaddr{
sa_family_t sa_family;
char sa_data[14];
} - socklen_t addrlen : 전달 하고자 하는 구조체의 주소 값, 즉 sockaddr 구조체의 길이를 지정하면 된다.
∗ sockaddr 구조체는 소켓 관련 함수를 사용하기 위해서 최종적으로 반환 되는 구조체로 TCP/IP의 실제 주소 정보를 저장하기 위해서는 sockaddr과 같은 크기의 sockaddr_in 구조체가 사용된다. sockaddr_in 구조체는 아래와 같다.struct sockaddr_in{
sin_family_t sin_family;
uint16_t sin_port;
struct in_addr sin_addr;
char sin_zero[8];
}
여기서 sin_addr은 ip주소 값을 저장하기 위한 멤버 변수로 주소를 저장할 수 있는 구조체 in_addr을 사용하며 아래와 같다struct in_addr{
in_addr_t s_addr;
}
header : #include <sys/types.h>
#include <sys/socket.h>
int bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen)
> 서버에서 소켓 연결에 사용되는 주소를 소켓에 할당하기 위한 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const strcut sockaddr * addr : 접속하고자 하는 아이피 및 서버 포트 정보가 있는 sockaddr 구조체의 주소 값을 지정 한다.
- socklen_t addrlen : 전달 하고자 하는 구조체의 주소 값, 즉 sockaddr 구조체의 길이를 지정하면 된다.
∗ connet()함수에서 sockaddr 구조체의 주소 값은 접속하려는 서버의 정보지만 bind()에서의 sockaddr는 소켓 디스크립터가 연결 받고자 하는 주소값이 저장된 sockaddr 구조체의 주소 값이다.
header : #include <sys/types.h>
#include <sys/socket.h>
int listen(int sockfd, int backlog)
> 해당 소켓에서 연결을 기다리는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- int backlog : 연결을 기다리는 대기열 큐의 사이즈이다.
header : #include <sys/types.h>
#include <sys/socket.h>
int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen)
> 해당 소켓에 연결 요청이 왔을 때 연결을 받아들이는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const strcut sockaddr * addr : 클라이언트의 아이피 및 서버 포트 정보가 있는 sockaddr 구조체의 주소 값이다.
- socklen_t *addrlen : sockaddr 구조체의 길이가 저장된 변수의 주소 값이다.
∗ 연결에 실패하면 0보다 작은 값을 반환한다. 또한 해당 소켓으로 연결 요청이 없는 경우, 클라이언트가 연결을 요청할 때 까지 소켓을 계속 감시하며 대기 상태를 유지한다.켓
header : #include <sys/types.h>
#include <sys/socket.h>
ssize_t send(int sockfd, const void *buf, size_t len,int flags)
> 스트림 기반(SOCK_STREAM)으로 생성된 소켓에서 데이터를 전송하는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const void *buf : 보내고자 하는 데이터의 시작 주소 값
- size_t len : 데이터의 시작 주소부터 얼마만큼 데이터를 전송할지 데이터의 길이를 나타낸다.
- int flags : send() 함수를 호출할 때 사용되는 옵션 플래그 (일반적으로 0을 사용)
header : #include <sys/types.h>
#include <sys/socket.h>
int recv(int sockfd,void *buf, size_t len,int flags)
> 스트림 기반으로 생성된 소켓에서 데이터를 수신 받기 위한 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const void *buf : 수신 받은 데이터가 저장될 버퍼의 주소 값
- size_t len :버퍼의 최대 길이를 나타낸다.
- int flags : send() 함수를 호출할 때 사용되는 옵션 플래그 (일반적으로 0을 사용)
header : #include <sys/types.h>
#include <sys/socket.h>
int sendto(int sockfd,const void *buf, size_t len, int flags, const struct sockaddr *dest_addr, socklen_t addrlen)
> send()와는 다르게 데이터그램(SOCK_DGRAM)으로 생성된 소켓 연결에서 데이터를 전송하는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const void *buf : 보내고자 하는 데이터의 시작 주소 값
- size_t len : 데이터의 시작 주소부터 얼마만큼 데이터를 전송할지 데이터의 길이를 나타낸다.
- int flags : send() 함수를 호출할 때 사용되는 옵션 플래그 (일반적으로 0을 사용)
- const strcut sockaddr * dest_addr : 전송하려는 대상의 주소 정보가 저장된 sockaddr 구조체
- socklen_t addrlen : sockaddr 구조체의 길이를 나타낸다.
header : #include <sys/types.h>
#include <sys/socket.h>
int recvfrom(int sockfd, void *buf, size_t len, int flags, struct sockaddr *src_addr, socklen_t *addrlen)
> recv()와는 다르게 데이터그램(SOCK_DGRAM)으로 생성된 소켓 연결에서 데이터를 수신하는 함수
인자 설명
- int sockfd : int socket()로 생성된 소켓 디스크립터가 들어간다.
- const void *buf : 수신 받은 데이터가 저장될 버퍼의 주소 값
- size_t len :버퍼의 최대 길이를 나타낸다.
- int flags : send() 함수를 호출할 때 사용되는 옵션 플래그 (일반적으로 0을 사용)
- strcut sockaddr * src_addr : 수신지의 주소 정보가 저장된 sockaddr 구조체
- socklen_t *addrlen : sockaddr 구조체의 길이의 주소 값을 나타낸다.
== 리눅스 전용 함수 ==
header : #include <unistd.h>
int close(int fd)
> 파일의 디스크립터를 닫는데 사용되는 함수 + 소켓 디스크립터를 닫는 데도 사용되는 함수는
인자 설명
- int fd : 파일이나 소켓의 디스크립터
윈도우의 경우 소켓 디스크립터를 닫기 위한 함수가 따로 존재하니 참고 바란다.
“[Network Baisc] Socket Function”에 대한 한개의 댓글