广播和组播

守給你的承諾、 提交于 2019-11-26 00:36:10

一。广播

服务端向192.168.1.1~192.168.1.254的所有IP的9000端口发送数据

服务端

 1 #include <stdio.h>
 2 #include <unistd.h>
 3 #include <stdlib.h>
 4 #include <sys/socket.h>
 5 #include <string.h>
 6 #include <arpa/inet.h>
 7 #include <net/if.h>
 8 
 9 #define SERVER_PORT 8000                                    //服务器端口
10 #define MAXLINE 1500
11 
12 #define BROADCAST_IP "192.168.1.255"                       //广播地址
13 #define CLIENT_PORT 9000                                    //广播的端口
14 
15 int main(void)
16 {
17     int sockfd;
18     struct sockaddr_in serveraddr, clientaddr;
19     char buf[MAXLINE];
20 
21     /* 构造用于UDP通信的套接字 */
22     sockfd = socket(AF_INET, SOCK_DGRAM, 0);
23 
24     bzero(&serveraddr, sizeof(serveraddr));
25     serveraddr.sin_family = AF_INET;                        /* IPv4 */
26     serveraddr.sin_addr.s_addr = htonl(INADDR_ANY);         /* 本地任意IP INADDR_ANY = 0 */
27     serveraddr.sin_port = htons(SERVER_PORT);
28 
29     bind(sockfd, (struct sockaddr *)&serveraddr, sizeof(serveraddr));
30 
31     int flag = 1;
32     setsockopt(sockfd, SOL_SOCKET, SO_BROADCAST, &flag, sizeof(flag));   //设置套接字打开广播权限
33 
34     /*构造 client 地址 IP+端口  192.168.1.255+9000 */
35     bzero(&clientaddr, sizeof(clientaddr));
36     clientaddr.sin_family = AF_INET;
37     inet_pton(AF_INET, BROADCAST_IP, &clientaddr.sin_addr.s_addr);
38     clientaddr.sin_port = htons(CLIENT_PORT);
39 
40     int i = 0;
41     while (1) {
42         sprintf(buf, "this is the %d datagram\n", i++);
43         //fgets(buf, sizeof(buf), stdin);
44         sendto(sockfd, buf, strlen(buf), 0, (struct sockaddr *)&clientaddr, sizeof(clientaddr));//发送数据
45         sleep(1);
46     }
47     close(sockfd);
48     return 0;
49 }
客户端 1 #include <stdio.h>
 2 #include <unistd.h>
 3 #include <string.h>
 4 #include <sys/socket.h>
 5 #include <arpa/inet.h>
 6 
 7 #define SERVER_PORT 8000
 8 #define MAXLINE 4096
 9 #define CLIENT_PORT 9000
10 
11 int main(int argc, char *argv[])
12 {
13     struct sockaddr_in localaddr;
14     int confd;
15     ssize_t len;
16     char buf[MAXLINE];
17 
18     //1.创建一个socket
19     confd = socket(AF_INET, SOCK_DGRAM, 0);
20 
21     //2.初始化本地端地址
22     bzero(&localaddr, sizeof(localaddr));
23     localaddr.sin_family = AF_INET;
24     inet_pton(AF_INET, "0.0.0.0" , &localaddr.sin_addr.s_addr);
25     localaddr.sin_port = htons(CLIENT_PORT);
26 
27     int ret = bind(confd, (struct sockaddr *)&localaddr, sizeof(localaddr));  //显式绑定不能省略
28     if (ret == 0)
29         printf("...bind ok...\n");
30 
31     while (1) {
32         len = recvfrom(confd, buf, sizeof(buf), 0, NULL, 0);  //接收数据
33         write(STDOUT_FILENO, buf, len);
34     }
35     close(confd);
36 
37     return 0;
38 }

 

 

二。组播

服务端向所有加入239.0.0.2多播组的所有IP的9000端口发送数据

 

 

服务端

 1 #include <stdio.h>
 2 #include <unistd.h>
 3 #include <string.h>
 4 #include <arpa/inet.h>
 5 #include <net/if.h>
 6 
 7 #define SERVER_PORT 8000
 8 #define CLIENT_PORT 9000
 9 #define MAXLINE 1500
10 
11 #define GROUP "239.0.0.2"
12 
13 int main(void)
14 {
15     int sockfd;
16     struct sockaddr_in serveraddr, clientaddr;
17     char buf[MAXLINE];
18     struct ip_mreqn group;
19 
20     /*
21     struct ip_mreqn {
22         struct in_addr  imr_multiaddr;          /* IP multicast address of group */
23         struct in_addr  imr_address;            /* local IP address of interface */
24         int             imr_ifindex;            /* Interface index */
25     };*/
26     
27     sockfd = socket(AF_INET, SOCK_DGRAM, 0);                /* 构造用于UDP通信的套接字 */
28     
29     bzero(&serveraddr, sizeof(serveraddr));
30     serveraddr.sin_family = AF_INET;                        /* IPv4 */
31     serveraddr.sin_addr.s_addr = htonl(INADDR_ANY);         /* 本地任意IP INADDR_ANY = 0 */
32     serveraddr.sin_port = htons(SERVER_PORT);
33 
34     bind(sockfd, (struct sockaddr *)&serveraddr, sizeof(serveraddr));
35 
36     inet_pton(AF_INET, GROUP, &group.imr_multiaddr);        /* 设置组地址 */
37     inet_pton(AF_INET, "0.0.0.0", &group.imr_address);      /* 本地任意IP */
38     group.imr_ifindex = if_nametoindex("eth0");             /* 给出网卡名,转换为对应编号: eth0 --> 编号  命令:ip ad */
39 
40     setsockopt(sockfd, IPPROTO_IP, IP_MULTICAST_IF, &group, sizeof(group));  /* 组播权限 */
41 
42     bzero(&clientaddr, sizeof(clientaddr));                 /* 构造 client 地址 IP+端口 */
43     clientaddr.sin_family = AF_INET;
44     inet_pton(AF_INET, GROUP, &clientaddr.sin_addr.s_addr); /* IPv4  239.0.0.2+9000 */
45     clientaddr.sin_port = htons(CLIENT_PORT);
46 
47     int i = 0;
48     while (1) {
49         sprintf(buf, "this is the %d datagram\n", i++);
50         //fgets(buf, sizeof(buf), stdin);
51         sendto(sockfd, buf, strlen(buf), 0, (struct sockaddr *)&clientaddr, sizeof(clientaddr)); //向多播组9000端口发送数据
52         sleep(1);
53     }
54 
55     close(sockfd);
56 
57     return 0;
58 }

客户端

#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <arpa/inet.h>
#include <net/if.h>

#define SERVER_PORT 8000
#define CLIENT_PORT 9000

#define GROUP "239.0.0.2"  //组播地址

int main(int argc, char *argv[])
{
    struct sockaddr_in localaddr;
    int confd;
    ssize_t len;
    char buf[BUFSIZ];

    struct ip_mreqn group;                                                  /* 组播结构体 */

    confd = socket(AF_INET, SOCK_DGRAM, 0);

    bzero(&localaddr, sizeof(localaddr));                                   /* 初始化 */
    localaddr.sin_family = AF_INET;
    inet_pton(AF_INET, "0.0.0.0" , &localaddr.sin_addr.s_addr);
    localaddr.sin_port = htons(CLIENT_PORT);

    bind(confd, (struct sockaddr *)&localaddr, sizeof(localaddr));

    inet_pton(AF_INET, GROUP, &group.imr_multiaddr);                        /* 设置组地址 */
    inet_pton(AF_INET, "0.0.0.0", &group.imr_address);                      /* 使用本地任意IP添加到组播组 */
    group.imr_ifindex = if_nametoindex("eth0");                             /* 通过网卡名-->编号 ip ad */
    
    setsockopt(confd, IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group));/* 设置client 加入多播组 */

    while (1) {
        len = recvfrom(confd, buf, sizeof(buf), 0, NULL, 0);  //接收数据
        write(STDOUT_FILENO, buf, len);
    }
    close(confd);

    return 0;
}

 

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!