socket函数
int socket(int domain,int type,int protocol);
domain为协议簇,取值为以下几点
- AF_INET:使用Ipv4协议
- AF_INET6:使用Ipv6协议
- AF_UNIX:本地通信,一般是指在当客户端与服务器在同一个机器上使用。
- AF_NETLINK:内核与用户态之间通信
type是指套接字的类型,取值为以下几点
- SOCK_STREAM:数据流通信,即使用TCP通信。
- SOCK_DGRAM:数据包通信,即使用UDP通信。
protocol一般为0
头文件#include<sys/types.h> #include<sys/socket.h>
返回值:
函数执行成功,则返回一个正整数,该正整数为套接字描述符,如果函数执行失败,则返回-1。
#include<sys/types.h> //基本系统数据类型
#include<sys/socket.h>
#include<iostream>
using namespace std;
int main()
{
int sockfd;
sockfd = socket(AF_INET,SOCK_STREAM,0);
if(sockfd < 0)
{
cout<<"create socket error"<<endl;
}
cout<<sockfd<<endl;
return 0;
}
bin函数
bin函数为绑定地址空间函数,在套接字结构体中,有一个默认的IP地址与默认的端口号,但是服务器程序必须调用bind函数绑定自己的IP地址信息和特定的端口号。
int bind(int sockfd,const struct sockaddr* addr,socklen_t addrlen)
- sockfd:标识一个待绑定的套接字描述符
- addr:是一个sockadddr的结构体,其有3种形式,分别为Ipv4、Ipv6、Unix
- addrlen:指定addr的缓冲区长度
//Ipv4地址域
struct sockaddr_in{
sa_family_t sin_family; //地址簇AF_INET
in_port_t sin_port; //端口
struct in_addr sin_addr; //地址
};
struct in_addr{
uint32_t s_addr; //网络字节序
};
//Ipv6地址域
struct sockaddr_in6{
sa_family_t sin6_family; //AF_INET6
in_port_t sin6_port; //端口
uint32_t sin6_flowinfo;
struct in6_addr sin6_addr;
uint32_t sin6_scope_id;
}
struct in6_addr{
unsigned char s6_addr[16];
};
bin函数的使用
#include<sys/types.h> //基本系统数据类型
#include<sys/socket.h>
#include<iostream>
using namespace std;
int main()
{
struct sockaddr_in sockaddr;
int port = 3000;
int socketfd;
memset(&sockaddr,0,sizeof(sockaddr));
sockaddr.sin_family = AF_INET;
sockaddr.sin_addr.s_addr = htonl(127.0.0.1);
sockaddr.sin_port = htons(port);
socketfd = socket(AF_INET,SOCK_STREAM,0);
if(sockfd == -1)
{
cout<<"socket create error"<<endl;
return -1;
}
return 0;
}
listen函数
主要是用于服务端监控。
int listen(int pid,int backlog);
pid:为监控的套接字描述符
backlog:表示连接请求的最大连接数
accept函数
用于服务器程序从处于监听状态的流式套接字的客户连接请求队列中获取第一个客户端请求,并创建一个新的套接字用于和客户端通信。
int accetp(int pid,struct sockaddr* addr,socklen_t *addrlen)
- pid:为处于监听状态的流式套接字描述符
- addr:获得客户端的协议地址,包括Ip与端口号
- addrlen:客户端地址结构的大小。
struct sockaddr_in NewSocket;
int addrlen;
addrlen = sizeof(NewSocket);
int NewServerSocket = accept(ListenSocket,(struct sockaddr*)&NewSocket,&addrlen);
if(NewServerSocket == -1)
{
cout<<"accept socket error"<<endl;
}
connect函数
用于客户端连接服务器
int connect(int pid,const struct sockaddr* name,socklen_t namelen)
- pid:还没有连接的套接字描述符
- name:服务器套接字的地址结构的指针
- namelen:套接字地址结构的大小
如果函数执行成功,则返回0,否则返回-1
write函数
无论是客户端还是服务器都可以使用write函数向TCP连接的另一端发送数据。
int write(int pid,const char* buf,int len)
- pid:发送端的套接字
- buf:发送缓冲区
- len:缓冲区的大小
返回值:返回实际发送的字节数
read函数
无论是客户端还是服务器都可以使用read函数接收数据。
int read(int pid,char *buf,int len)
- pid:套接字描述符
- buf:缓冲区,用于存储读取到的数据
- len:缓冲区的大小
返回值:返回实际读取的字节数,如果连接关闭,则返回0
send函数
功能类似于write函数
size_t send(int pid,const char* buf,size_t len,int flag)
前三个参数的含义于write类似,flag为传输控制标志。
- 0:表示常规,与write类似
- MSG_DONTROUTE:通知内核目的主机在直接连接的本地网络上
- MSG_DONTWAIT:将单个I\O操作设置为非阻塞模式
返回值:返回实际发送的字节数
recv函数
功能类似于read函数
ssize_t recv(int sockfd,void *buf,size_t len,ing flag)
前三个参数的含义于read类似,flag为传输控制标志。
- 0:表示常规,与read类似
- MSG_DONTWAIT:将单个I\O操作设置为非阻塞模式
- MSG_OOB:读物数据是带外数据而不是一般数据
返回值:返回实际读取的字节数,如果连接关闭,则返回0
close
关闭套接字
int close(int sockfd)
成功返回0,失败返回-1