picture:
组播发送时,向指定的组播地址发送。使用UDP套接字
接收时,将收方的套接字加入多播组,绑定接收地址和端口,接收数据。
加入多播组需要用到结构体ip_mreq, setsockopt()函数;
/*recv.c*/ #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include<sys/types.h> #include <sys/socket.h> #include<netinet/in.h> #include <arpa/inet.h> #define N 64 int main(int argc, const char *argv[]) { int sockfd; char buf[N] = "0"; struct sockaddr_in myaddr, peeraddr; struct ip_mreq mreq; socklen_t peerlen = sizeof(peeraddr); if((sockfd = socket(PF_INET, SOCK_DGRAM, 0)) == -1) { perror("socket"); exit(-1); } bzero(&mreq, sizeof(mreq)); mreq.imr_multiaddr.s_addr = inet_addr(argv[1]); mreq.imr_interface.s_addr = htonl(INADDR_ANY); if(setsockopt(sockfd, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)) < 0) { perror("setsockopt"); exit(-1); } if((sockfd = socket(PF_INET, SOCK_DGRAM, 0)) == -1) { perror("socket"); exit(-1); } bzero(myaddr, sizeof(myaddr)); myaddr.sin_family = PF_INET; myaddr.sin_port = htons(atoi(argv[2])); myaddr.sin_addr.s_addr = inet_addr(argv[1]); if(bind(sockfd, (struct sockaddr *)&myaddr, sizeof(myaddr)) < 0) { perror("fail to bind\n"); exit(-1); } while(1) { recvfrom(sockfd, buf, N, 0, (struct sockaddr *)&peeraddr, &peerlen); printf("%s : %d %s\n", inet_ntoa(peeraddr.sin_addr), ntohs(peeraddr.sin_port), buf); } return 0; }编译并运行 ./recv 224.10.10.1 9999
/*send.c*/ #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include<sys/types.h> #include <sys/socket.h> #include<netinet/in.h> #include <arpa/inet.h> #define N 64 int main(int argc, const char *argv[]) { int sockfd; char buf[N] = "This is a multicast test "; struct sockaddr_in dstaddr; if((sockfd = socket(PF_INET, SOCK_DGRAM, 0)) == -1) { perror("socket"); exit(-1); } bzero(dstaddr, sizeof(dstaddr)); dstaddr.sin_family = PF_INET; dstaddr.sin_port = htons(atoi(argv[2])); dstaddr.sin_addr.s_addr = inet_addr(argv[1]); while(1) { sendto(sockfd, buf, N, 0, (sockaddr *)&dstaddr, sizeof(dstaddr)); sleep(1); } return 0; }编译并运行 ./send 224.10.10.1 9999