UDP协议
UDP协议:
面向无连接的不可靠的通信协议,想要保证可靠性可以采用重新传送
1、不可靠的原因:
1.非面向连接(不关心接收端是否在线)-一》没有三次握手
2.丢包不重发
3.错误的包不重发
4.没有信道拥堵控制
5.有一个最大传输长度限制
6.没有严格的校验机制
2、TCP和UDP的选择问题
需要:可靠性>实时性 用:TCP
需要:实时性>可靠性 用:TCP
3、UDP模型
服务端:socket->bind->IO函数(recvfrom/sendto)
客户端:socket->IO函数(sendto/recvfrom)
服务器样例:
#include<stdio.h> #include <sys/types.h> /* See NOTES */ #include <sys/socket.h> #include <string.h> #include <unistd.h> #include <arpa/inet.h> int main(void) { int skt = socket(AF_INET, SOCK_DGRAM, 0); if(-1 == skt) { printf("socker error\n"); return -1; } //将IP和端口号存入结构体 struct sockaddr_in sddr; sddr.sin_family = AF_INET; sddr.sin_port = htons(6666); sddr.sin_addr.s_addr = inet_addr("0.0.0.0"); int len = sizeof(struct sockaddr_in); //将套接字和IP、端口号进行绑定 int ret = bind(skt, (struct sockaddr *)&sddr, sizeof(sddr)); if(-1 == ret) { printf("bind error\n"); return -1; } char buf[100] = {'\0'}; while(1) { recvfrom(skt, buf, sizeof(buf), 0, (struct sockaddr *)&sddr, &len);//0表示阻塞 puts(buf); sendto(skt, buf, sizeof(buf), 0, (struct sockaddr *)&sddr, len);//0表示阻塞 memset(buf, 0,sizeof(buf)); } close(skt); return 0; }
客户端样例:
#include<stdio.h> #include <sys/types.h> /* See NOTES */ #include <sys/socket.h> #include <string.h> #include <unistd.h> #include <arpa/inet.h> int main(void) { int skt = socket(AF_INET, SOCK_DGRAM, 0); if(-1 == skt) { printf("socker error\n"); return -1; } //将IP和端口号存入结构体 struct sockaddr_in sddr; sddr.sin_family = AF_INET; sddr.sin_port = htons(6666); sddr.sin_addr.s_addr = inet_addr("192.168.4.159"); int len = sizeof(struct sockaddr_in); char buf[100] = {'\0'}; while(1) { fgets(buf,100,stdin); sendto(skt, buf, sizeof(buf), 0, (struct sockaddr *)&sddr, len); memset(buf, 0,sizeof(buf)); recvfrom(skt, buf, sizeof(buf), 0, (struct sockaddr *)&sddr, &len); puts(buf); } close(skt); return 0; }