组播的介绍以及CS模型实现

mac2022-06-30  23

1.组播介绍

  组播组可以是永久的也可以是临时的。组播组地址中,有一部分由官方分配的,称为永久组播组。

  永久组播组保持不变的是它的ip地址,组中的成员构成可以发生变化。永久组播组中成员的数量都可以是任意的,甚至可以为零。

  那些没有保留下来供永久组播组使用的ip组播地址,可以被临时组播组利用。

  224.0.0.0~224.0.0.255      为预留的组播地址(永久组地址),地址224.0.0.0保留不做分配,其它地址供路由协议使用;

  224.0.1.0~224.0.1.255      是公用组播地址,可以用于Internet;欲使用需申请。

  224.0.2.0~238.255.255.255  为用户可用的组播地址(临时组地址),全网范围内有效;

  239.0.0.0~239.255.255.255  为本地管理组播地址,仅在特定的本地范围内有效。

  可使用ip ad命令查看网卡编号或者if_nametoindex() 函数可以根据网卡名,获取网卡序号。

2.代码实现

server.c

1 #include<stdio.h> 2 #include<unistd.h> 3 #include<stdlib.h> 4 #include<strings.h> 5 #include<string.h> 6 #include<sys/socket.h> 7 #include<arpa/inet.h> 8 #include<net/if.h> 9 10 #define SERVER_PORT 8000 11 #define MAXLINE 1024 12 #define CLIENT_PORT 9000 13 14 #define GROUP "239.0.0.2" 15 16 int main(int argc,char* argv[]) 17 { 18 int sockfd; 19 struct sockaddr_in servaddr,clieaddr; 20 char buf[MAXLINE]; 21 struct ip_mreqn group; 22 //构造用于UDP通信的套接字 23 sockfd = socket(AF_INET,SOCK_DGRAM,0); 24 25 bzero(&servaddr,sizeof(servaddr)); 26 servaddr.sin_family = AF_INET; 27 servaddr.sin_addr.s_addr = htonl(INADDR_ANY); 28 servaddr.sin_port = htons(SERVER_PORT); 29 30 bind(sockfd,(struct sockaddr*)&servaddr,sizeof(servaddr)); 31 32 inet_pton(AF_INET,GROUP,&group.imr_multiaddr);//设置组地址 33 inet_pton(AF_INET,"0.0.0.0",&group.imr_address);//本地有效IP 34 group.imr_ifindex = if_nametoindex("eth0");//给出网卡名,转换为对应编号 35 36 setsockopt(sockfd,IPPROTO_IP,IP_MULTICAST_IF,&group,sizeof(group));//组播的权限设置 37 38 bzero(&clieaddr,sizeof(clieaddr)); 39 clieaddr.sin_family = AF_INET; 40 inet_pton(AF_INET,GROUP,&clieaddr.sin_addr.s_addr); 41 clieaddr.sin_port = htons(CLIENT_PORT); 42 43 int i = 1; 44 while(1) 45 { 46 sprintf(buf,"服务端组播了 %d次\n",i++); 47 sendto(sockfd,buf,strlen(buf),0,(struct sockaddr*)&clieaddr,sizeof(clieaddr)); 48 sleep(1); 49 } 50 close(sockfd); 51 return 0; 52 }

client.c

1 #include<stdio.h> 2 #include<unistd.h> 3 #include<stdlib.h> 4 #include<strings.h> 5 #include<string.h> 6 #include<sys/socket.h> 7 #include<arpa/inet.h> 8 #include<net/if.h> 9 10 #define SERVER_PORT 8000 11 #define CLIENT_PORT 9000 12 13 #define GROUP "239.0.0.2" 14 15 int main(int argc,char* argv[]) 16 { 17 struct sockaddr_in localaddr; 18 int confd; 19 ssize_t len; 20 char buf[BUFSIZ]; 21 22 struct ip_mreqn group; 23 24 confd = socket(AF_INET,SOCK_DGRAM,0); 25 26 bzero(&localaddr,sizeof(localaddr)); 27 localaddr.sin_family = AF_INET; 28 inet_pton(AF_INET,"0.0.0.0",&localaddr.sin_addr.s_addr); 29 localaddr.sin_port = htons(CLIENT_PORT); 30 31 bind(confd,(struct sockaddr*)&localaddr,sizeof(localaddr)); 32 33 inet_pton(AF_INET,GROUP,&group.imr_multiaddr); 34 inet_pton(AF_INET,"0.0.0.0",&group.imr_address); 35 group.imr_ifindex = if_nametoindex("eth0"); 36 37 setsockopt(confd,IPPROTO_IP,IP_ADD_MEMBERSHIP,&group,sizeof(group)); 38 39 while(1) 40 { 41 len = recvfrom(confd,buf,sizeof(buf),0,NULL,0); 42 write(STDOUT_FILENO,buf,len); 43 } 44 close(confd); 45 return 0; 46 }

3.测试结果

 

  可以看到服务端启动后,客户端可以接收到服务端发送的组播信息

 

转载于:https://www.cnblogs.com/liunianshiwei/p/6050826.html

最新回复(0)