套接字是一种通信机制,凭借这种机制,客户/服务器系统的开发工作既可以在本地单机上进行,也可以跨网络进行,Linux所提供的功能(如打印服务,ftp等)通常都是通过套接字来进行通信的,套接字的创建和使用与管道是有区别的,因为套接字明确地将客户和服务器区分出来,套接字可以实现将多个客户连接到一个服务器。
套接字属性
套接字的特性由3个属性确定,他们是,域,类型和协议
域指定套接字通信中使用的网络介质,最常见的套接字域是AF_INET,它指的是Internet网络
套接字类型
一个套接字可能有多种不同的通信方式
流套接字,流套接字提供一个有序,可靠,双向节流的链接,流套接字由类型SOCK_STREAM指定,它是在AF_INET域中通过TCP/IP链接实现的,这就是套接字类型(其实就是通信方式)
与流套接字相反,由类型SOCK_DGRAM指定的数据报套接字不建立和维持一个连接,它对可以发送的数据长度有限制,数据报作为一个单独的网络消息被传输,它可能会丢失,复制或乱序
最后一个是套接字协议,通常使用默认就可以了(也就是最后一个参数填0)
创建套接字
socket系统调用创建一个套接字并返回一个描述符,该描述符可以用来访问该套接字
#include
#include
int socket(int domain,int type,int protocol);
创建的套接字是一条通信线路的一个端点,domain参数指定协议族(使用的网络介质),type参数指定这个套接字的通信类型(通信方式),protocot参数指定使用的协议
domain参数可以指定如下协议族
AF_UNIX UNIX域协议(文件系统套接字)
AF_INET ARPA因特网协议
AF_ISSO ISO标准协议
AF_NS Xerox网络协议
AF_IPX Novell IPX协议
AF_APPLETALK Appletalk DDS协议
最常用的套接字域是AF_UNIX和AF_INET,前者用于通过UNIX和Linux文件系统实现本地套接字
socket函数的第二个参数type指定用于新套接字的特性,它的取值包括SOCK_STREAM和SOCK_DGRAM
SOCK_STREAM是一个有序,可靠,面向连接的双向字节流,一般用这个
最后一个protocol参数,将参数设为0表示使用默认协议。
套接字地址
每个套接字(端点)都有其自己的地址格式,对于AF_UNIX套接字来说,它的地址由结构sockaddr_un来描述,该结构体定义在头文件sys/un.h中,如下:
struct sockaddr_un {
sa_family_t sun_family; //套接字域
char sun_path[];//名字
};
而在AF_INET域中,套接字地址结构由sockaddr_in来指定,该结构体定义在头文件netinet/in.h中
struct sockaddr_in {
short int sin_family;//套接字域
unsigned short int sin_port;//接口
struct in_addr sin_addr;
}
IP地址结构in_addr被定义如下:
struct in_addr {
unsigned long int s_addr;
};
命名套接字
要想让通过socket调用创建的套接字可以被其它进程使用,服务器程序就必须给该套接字命名,如下,AF_INET套接字就会关联到一个IP端口号
#include
int bind(int socket,const struct sockaddr *address,size_t address_len);
bind系统调用把参数address中的地址分配给与文件描述符socket关联的未命名套接字
创建套接字队列
为了能够在套接字上接受进入链接,服务器程序必须创建一个队列来保存未处理的请求,它用listen系统调用来完成这一工作
#include
int listen(int socket,int backlog);
Linux系统可能会对队列中未处理的连接的最大数目做出限制
接受连接
一旦服务器程序创建并命名套接字之后,他就可以通过accept系统调用来等待客户建立对该套接字的连接
#include
int accept(int socket,struct sockaddr *address,size_t *address_len);
accept函数将创建一个新套接字来与该客户进行通信,并且返回新套接字描述符(这个描述符和客户端中描述符是一样等同)
请求连接
客户程序通过一个未命名套接字和服务器监听套接字之间建立的连接的方法来连接到服务器,如下:
#include
int connect(int socket,const struct sockaddr *address,size_t address_len);
参数socket指定的套接字将连接到参数address指定的服务器套接字
关闭套接字
你可以通过调用close函数来终止服务器和客户上的套接字连接
套接字通信
套接字可以通过调用read(),write()系统调用来进行传输数据
嵌入式物联网需要学的东西真的非常多,千万不要学错了路线和内容,导致工资要不上去!
分享大家一个资料包,差不多150多G。里面学习内容、面经、项目都比较新也比较全!
点击找小助理免费领取:扫码进群领资料https://s.pdb2.com/pages/20230519/16QijNiGb32IFIn.html