linux下不同主机间实现组播(练习代码)

来源:互联网 发布:js判断用户名是否合法 编辑:程序博客网 时间:2024/05/16 18:28

在写聊天室程序时,遇到一个组播问题,不能在不同主机上进行发送接收消息。。。

深究发现,是本人对sendto与recvfrom的理解太浅薄。

以下代码发送端与接收端可在同一主机,也可在不同主机上运行。

代码直接编译运行即可。

程序为练习程序,比较难堪,勿怪。

确定是在局域网内。。

不能运行可试着关闭防火墙。。。

以下例子,发送端只能发送消息,接收端只能接收消息。

若两台主机都加入组播组的话,那么它们都能收发消息。代码就不写了

发送端:(此主机未加入组播组)

#include  <stdio.h>#include  <sys/types.h>#include  <sys/socket.h>#include  <sys/types.h>#include  <sys/socket.h>#include  <netinet/in.h>#include  <arpa/inet.h>#include  <time.h>#include  <string.h>#include  <stdio.h>#include  <unistd.h>#include  <stdlib.h>#include  <netinet/in.h>#include  <arpa/inet.h>#define   MAXBUF   30#define   PORT   5000char multicast_addr[] = "224.0.1.1 ";int main(int argc, char *argv[]) {int s;char name[MAXBUF] = { '\0' };struct sockaddr_in srv, mcast;if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {perror("Opening   socket ");return 0;}memset(&srv, 0, sizeof(srv));srv.sin_family = AF_INET;srv.sin_port = htons(PORT);srv.sin_addr.s_addr = htonl(INADDR_ANY); memset(&mcast, 0, sizeof(mcast)); mcast.sin_port = htons(PORT); mcast.sin_family = AF_INET; mcast.sin_addr.s_addr = inet_addr(multicast_addr);int opt = SO_REUSEADDR;setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));if (bind(s, (struct sockaddr*) &srv, sizeof(srv)) < 0) {perror("bind ");return 0;}/*发送端无需加入组播组,所以以下注释语句可以不要mreq.imr_multiaddr.s_addr = inet_addr(multicast_addr);mreq.imr_interface.s_addr = htonl(INADDR_ANY); if (setsockopt(s, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)) < 0) { perror("setsockopt:   IP_ADD_MEMBERSHIP "); return 0; } */while (1) {fgets(name, MAXBUF, stdin);sendto(s, name, strlen(name), 0, (struct sockaddr*) &mcast, sizeof(mcast));//此处是mcast!!切记!!perror("sendto");}return 1;}


接收端:(此主机加入组播组)

#include  <stdio.h>#include  <sys/types.h>#include  <sys/socket.h>#include  <netinet/in.h>#include  <arpa/inet.h>#include  <time.h>#include  <string.h>#include  <unistd.h>#include  <stdlib.h>#define   MAXBUF   30#define  PORT   5000char multicast_addr[] = "224.0.1.1 ";int main(int argc, char *argv[]) {int s, n;char name[MAXBUF] = { '\0' };struct sockaddr_in srv;socklen_t srv_len = sizeof(srv);struct ip_mreq mreq;if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {perror("Opening   socket ");return 0;}memset(&srv, 0, sizeof(srv));srv.sin_family = AF_INET;srv.sin_port = htons(PORT);srv.sin_addr.s_addr = htonl(INADDR_ANY);int opt = SO_REUSEADDR;setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));if (bind(s, (struct sockaddr*) &srv, sizeof(srv)) < 0) {perror("bind ");return 0;}mreq.imr_multiaddr.s_addr = inet_addr(multicast_addr);mreq.imr_interface.s_addr = htonl(INADDR_ANY);if (setsockopt(s, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)) < 0) {perror("setsockopt:   IP_ADD_MEMBERSHIP ");return 0;}while (1) {n = recvfrom(s, name, MAXBUF, 0, (struct sockaddr*) &srv, &srv_len);//此处是srv,切记!!!perror("recvfrom");name[n] = '\0';fputs(name, stdout);}return 1;}




0 0