組播提供了在網路中進行一對多的傳送的機制,組播可以是在乙個網段內,也可以是跨網段的,不過跨網段需要交換機、路由器等網路裝置支援組播。
hosts可以在任何時間加入或者離開組播組,對於組播組的成員沒有所處位置的限制,也沒有數量的限制,d類網際網路位址是用於組播的:224.0.0.0 - 239.255.255.255。
通過無連線socket程式設計可以實現組播資料的傳送和接收。組播資料只能通過乙個網路介面傳送,即使裝置上有多個網路介面。
組播是一對多的傳輸機制,不能通過面向連線的socket實現組播。
建立了sock_dgram型別的socket以後,通過呼叫setsockopt()函式來控制該socket的組播,
函式原型:getsockopt(int sockfd, int level, int optname, void *optval, socklen_t *optlen),
對於ipproto_ip level,optval有如下選擇:
ip_add_membership,加入指定的組播組。
ip_drop_membership,離開指定的組播組。
ip_multicast_if,指定傳送組播資料的網路介面。
ip_multicast_ttl,給出傳送組播資料時的ttl,預設是1。
ip_multicast_loop,傳送組播資料的主機是否作為接收組播資料的組播成員。
下面的兩個例子給出了傳送和接收組播資料的實現,接收和傳送組播資料的步驟是有區別的。
1、組播server,傳送組播資料的例子
實現組播資料報傳送的步驟如下:
①建立af_inet, sock_dgram的socket。
②用組播ip位址和埠初始化sockaddr_in型別資料。
③ip_multicast_loop,設定本機是否作為組播組成員接收資料。
④ip_multicast_if,設定傳送組播資料的埠。
⑤傳送組播資料。
#include #include #include #include #include #include struct in_addr localinte***ce;
struct sockaddr_in groupsock;
int sd;
char databuf[1024] = "multicast test message lol!";
int datalen = sizeof(databuf);
int main (int argc, char *ar**[ ])
else
printf("opening the datagram socket...ok.\n");
memset((char *) &groupsock, 0, sizeof(groupsock));
groupsock.sin_family = af_inet;
groupsock.sin_addr.s_addr = inet_addr("226.1.1.1");
groupsock.sin_port = htons(4321);
localinte***ce.s_addr = inet_addr("203.106.93.94");
if(setsockopt(sd, ipproto_ip, ip_multicast_if, (char *)&localinte***ce, sizeof(localinte***ce)) < 0) else
printf("setting the local inte***ce...ok\n");
if(sendto(sd, databuf, datalen, 0, (struct sockaddr*)&groupsock, sizeof(groupsock)) < 0)
else
printf("sending datagram message...ok\n");
return 0;
}
2、組播client,接收組播資料的例子
①建立af_inet, sock_dgram型別的socket。
②設定 so_reuseaddr,允許多個應用繫結同乙個本地埠接收資料報。
③用bind繫結本地埠,ip為inaddr_any,從而能接收組播資料報。
④採用 ip_add_membership加入組播組,需針對每個埠採用 ip_add_membership。
⑤接收組播資料報。
ps:接收組播的網路埠需要設定乙個ip位址,我除錯的計算機有兩個埠,我在第二個埠上接收組播,開始沒有設定這個埠的ip位址,只是給出了組播路由到第二個埠,結果收不到資料,後來設了乙個ip位址就ok了。
//結構體的定義
struct ip_mreq
#include #include #include #include #include #include #include struct sockaddr_in localsock;
struct ip_mreq group;
int sd;
int datalen;
char databuf[1500];
int main(int argc, char *ar**)
else
printf("opening datagram socket....ok.\n");
#if 1
int reuse = 1;
if(setsockopt(sd, sol_socket, so_reuseaddr, (char *)&reuse, sizeof(reuse)) < 0) else
printf("setting so_reuseaddr...ok.\n");
#endif
memset((char *) &localsock, 0, sizeof(localsock));
localsock.sin_family = af_inet;
localsock.sin_port = htons(49500);
localsock.sin_addr.s_addr = inaddr_any;
if(bind(sd, (struct sockaddr*)&localsock, sizeof(localsock))) else
printf("binding datagram socket...ok.\n");
#if 0 //加入組播組
ip_mreq multicast;
multicast.imr_multiaddr.s_un.s_addr=inet_addr("234.2.2.2"); //組播組的ip位址。
multicast.imr_inte***ce.s_un.s_addr=inaddr_any; //本地某一網路裝置介面的ip位址。
setsockopt(sersocket,ipproto_ip,ip_add_membership,(char*)&multicast,sizeof(multicast));
#endif
group.imr_multiaddr.s_addr = inet_addr("227.0.0.25");
group.imr_inte***ce.s_addr = inet_addr("150.158.231.2");
if(setsockopt(sd, ipproto_ip, ip_add_membership, (char *)&group, sizeof(group)) < 0) else
printf("adding multicast group...ok.\n");
datalen = sizeof(databuf);
if(read(sd, databuf, datalen) < 0) else
return 0;
}
linux下組播的實現
目前有三種通訊方式 單播 unicast 廣播 broadcast 組播 multicast 單播解決了點對點通訊的需求 廣播是點對多點的通訊,其存在兩個缺點 1 只能在同一網段內實現廣播 2 不能指定目的主機,所有網段內的主機都將收到廣播報文,存在頻寬浪費。組播組可以是永久的也可以是臨時的。組播組...
linux下c 實現udp組播模式
組播 傳送的資訊,小組內所有成員都能同時接受到。組播發送端跟接收端的具體流程為 傳送方 a.建立socket socket fd socket af inet,sock dgram,0 if socket fd 0 b.設定傳送的群組的位址 set up the destination addres...
Zigbee組播的實現
typedef struct aps group t 2.對aps group t結構體賦值,示例如下 by default,all devices start out in group 1 void osal memcpy void dst,const void generic src,unsig...