UDP SOCKET网络编程

目录

1.UDP编程框架

2.UDP设计常用函数

3.UDP组播


1.UDP编程框架

2.UDP设计常用函数

2.1 socket函数

#include <sys/types.h>          
#include <sys/socket.h>
int socket(int domain, int type, int protocol);

domain用于设置网络通信的域,常用的协议簇有AF_INET(IPV4)、AF_INET6(IPV6)、AF_LOCAL(或称AF_UNIX,Unix域socket)

type用来指定socket类型,常用的有SOCK_STREAM(TCP)、SOCK_DGRAM(UDP)

protocol用来指定协议,常用的协议有IPPROTO_TCP、IPPTOTO_UDP,分别对应TCP传输协议、UDP传输协议,通常传0选择type类型对应的协议

返回值:失败返回-1,成功返回非负的文件描述符

2.2 bind函数

#include <sys/types.h>
#include <sys/socket.h>
int bind(int sockfd, const struct sockaddr* my_addr, socklen_t addrlen);

 用来将socket返回的网络文件描述符和服务器的IP地址和端口号绑定起来

sockfd为socket返回的fd

addr为struct sockaddr类型的结构体指针,包含服务器的IP地址和端口号,绑定IP地址中遇到INADDR_ANY,转换过来为0.0.0.0,表示本机所有的IP地址

addrlen为第二个参数的长度

返回值:失败返回-1

2.3 recvfrom函数

#include <sys/types.h>
#include <sys/socket.h>
ssize_t recvfrom(int sockfd, void *buf, size_t len, int flags,
                struct sockaddr *src_addr, socklen_t *addrlen);

recvfrom函数为阻塞函数,没有接收到数据会一直等待

sockfd:正在监听端口的套接口文件描述符,通过socket获得

buf:接收缓冲区,定义的数组用来存放接收的数据

len:接收缓冲区的大小,单位是字节

flags:填0即可

src_addr:指向发送数据的主机地址信息的结构体,从src_addr结构体中可以得到发送者的参数

addrlen:表示第五个参数所指向内容的长度

返回值:成功返回接收成功的数据长度; 失败返回 -1

2.4 sendto函数

#include <sys/types.h>
#include <sys/socket.h>
ssize_t sendto(int sockfd, const void *buf, size_t len, int flags,
              const struct sockaddr *dest_addr, socklen_t addrlen);

sockfd:正在监听端口的套接口文件描述符,通过socket获得

buf:发送缓冲区,往往是使用者定义的数组,该数组装有要发送的数据

len:发送缓冲区的大小,单位是字节

flags:填0即可

dest_addr:指向接收数据的主机地址信息的结构体,也就是该参数指定buf中的数据要发送到哪个主机哪个进程,在发送之前需要绑定dest_addr结构体中的IP地址和端口号

addrlen:表示第五个参数所指向内容的长度

返回值:成功返回发送成功的数据长度;失败返回 -1

3.UDP组播

3.1 UDP组播示意图

3.2 UDP的单播、组播和广播

1.广播只能在内网即同一网段内有效,组播可实现跨网段群发数据,广播禁止在Internet宽带网上传输(广播风暴),单播和组播允许在Internet上进行传输

2.广播数据报的接收是被动的,连接到子网内的所有主机都要接收广播数据报,增加了网络流量,消耗更多的网络带宽

3.组播过程中让源主机和目标主机都加入到一个局部多播地址,源主机给该多播地址发送组播消息,多播在同一时间内把一个数据包由特定多播地址发送给多个IP地址,一台主机可以属于多个多播组,不属于一个多播组的主机也可以向该多播组IP地址发送数据包

4.组播组是维护在路由器中的,由路由器负责将组播消息转发给组内的多个主机,因此在实现多播时需要在代码中添加路由

5.不同子网内的组播通信依靠IGMP协议完成,同一子网内的组播通信不需要此组播路由协议;不同子网内的组播通信,发送端将数据向一个组内发送,网络中的路由器通过底层的IGMP协议自动将数据发送到所有监听这个组的终端,子网内的所有路由器都需要支持IGMP协议

6.多播的地址是特定的,D类地址用于多播。D类IP地址就是多播IP地址,即224.0.0.0至239.255.255.255之间的IP地址,并被划分为局部连接多播地址、预留多播地址和管理权限多播地址3类:

局部多播地址:在224.0.0.0~224.0.0.255之间,这是为路由协议和其他用途保留的地址,路由器并不转发属于此范围的IP包

预留多播地址:在224.0.1.0~238.255.255.255之间,可用于全球范围(如Internet)或网络协议

管理权限多播地址:在239.0.0.0~239.255.255.255之间,可供组织内部使用,类似于私有IP地址,不能用于Internet,可限制多播范围

7.udp单播,获取源主机的ip和子网掩码,得到该局域网的ip地址范围,然后使用udp单播轮询,找到对应的目标主机;udp广播,使用广播地址255.255.255.255 来广播定制好的消息

3.3 UDP组播的基本步骤

1.建立socket

2.socketfd和IP、端口进行绑定

3.加入一个组播组

4.通过sendto/recvfrom进行数据的收发

5.关闭socket

3.4 UDP组播相关

1.组播发送sendto中,源地址是一个单播地址,目的地址是一个组播地址;组播接收recvfrom中,源地址是一个组播地址,目的地址是一个单播地址。

2.加组示例代码

struct ip_mreq mreq;  
mreq.imr_multiaddr.s_addr = inet_addr("239.10.10.1");    /*组播地址*/  
mreq.imr_interface.s_addr = htonl(INADDR_ANY);           /*网络接口为默认*/
/*将本机加入广播组*/  
//组播,使用IPPROTO_IP
if(setsockopt(socket_handler, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)) < 0)  
{  
	perror("setsockopt");  
	return;  
}

inet_addr用来将点分十进制字符串格式的IP地址转换成32位二进制的IP地址

htonl将主机字节序调整为网络字节序,主机字节序有大端模式和小端模式,网络字节序譬如两个字节在网络中的传输次序为:0~7bit  8~15bit

IP_ADD_MEMBERSHIP为在指定的接口上加入组播组 IP_DROP_MEMBERSHIP为退出组播组

struct ip_mreq
{
	struct in_addr imr_multiaddr;   // 组播组的IP地址。
	struct in_addr imr_interface;   // 本地某一网络设备接口的IP地址。
};

即告诉路由器协议栈将哪个IP地址加入哪个组播组

3.在加组之前需要添加路由,不然加组会出现错误,示例:

route add -net 224.0.0.0 netmask 240.0.0.0 dev eth0

 

 

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值