📄 rtpconnection.cpp
字号:
int RTPConnection::SendRTCPCompoundData(void *data,int len){ struct sockaddr_in addr; unsigned long ip; int port,rtcpport; if (!socketsopened) return ERR_RTP_SOCKETSNOTOPEN; if (len <= 0) // nothing to send return 0; if (len > maxpacksize) return ERR_RTP_PACKETTOOLARGE; destinations.InitRetrieval(); addr.sin_family = AF_INET; while (destinations.GetNext(&ip,&port,&rtcpport)) { addr.sin_port = rtcpport; // already in network byte order addr.sin_addr.s_addr = ip; // already in network byte order sendto(sendsock,(const char *)data,len,0,(struct sockaddr *)&addr,sizeof(struct sockaddr)); } return 0;}int RTPConnection::ReceiveRTPData(unsigned char **data,int *len,unsigned long *ip,int *port){ RawDataBlock *tmp; if (rtp_first == NULL) return ERR_RTP_NORTPDATAAVAILABLE; *data = rtp_first->data; *len = rtp_first->datalen; *ip = rtp_first->ip; *port = rtp_first->port; tmp = rtp_first; rtp_first = rtp_first->next; delete tmp; return 0;}int RTPConnection::ReceiveRTCPData(unsigned char **data,int *len,unsigned long *ip,int *port){ RawDataBlock *tmp; if (rtcp_first == NULL) return ERR_RTP_NORTCPDATAAVAILABLE; *data = rtcp_first->data; *len = rtcp_first->datalen; *ip = rtcp_first->ip; *port = rtcp_first->port; tmp = rtcp_first; rtcp_first = rtcp_first->next; delete tmp; return 0;}int RTPConnection::Poll(bool rtp){ unsigned long len,ip; RawDataBlock *tmpblk; bool acceptpacket; int port,sock; struct sockaddr_in addr; unsigned char *data2; int len2; RTPSOCKLENTYPE fromlen; if (!socketsopened) return ERR_RTP_SOCKETSNOTOPEN; if (rtp) sock = rtpsock; else sock = rtcpsock; len = 0; RTPIOCTL(sock,FIONREAD,&len); if (!rtp && len > 0) gettimeofday(&rtcprecvtime,NULL); // I assume that we can read faster than the packets arrive // This version of the routine should also work with buggy ioctl versions: // in some ioctl versions, ioctl(sock,FIONREAD,&len) doesn't put the size of // the first packet in 'len', but the total size of all packets in the queue. while (len > 0) { fromlen = sizeof(struct sockaddr); len2 = recvfrom(sock,(char *)packetbuffer,(int)len,0,(struct sockaddr *)&addr,&fromlen); if (len2 > 0) { /* Check if this packet comes from a source from which we want to receive */ ip = ntohl(addr.sin_addr.s_addr); port = ntohs(addr.sin_port); if (receivemode != RECEIVEMODE_ALL) { if (receivemode == RECEIVEMODE_IGNORESOME) { if (ignoreIPs.Exists(ip,true,0)) acceptpacket = false; else if (ignoreIPs.Exists(ip,false,port)) acceptpacket = false; else acceptpacket = true; } else // RECEIVEMODE_ACCEPTSOME { if (acceptIPs.Exists(ip,true,0)) acceptpacket = true; else if (acceptIPs.Exists(ip,false,port)) acceptpacket = true; else acceptpacket = false; } } else acceptpacket = true; if (acceptpacket) { /* Process packet */ data2 = new unsigned char[len2]; if (data2 == NULL) return ERR_RTP_OUTOFMEM; memcpy(data2,packetbuffer,len2); tmpblk = new RawDataBlock; if (tmpblk == NULL) { delete [] data2; return ERR_RTP_OUTOFMEM; } if (rtp) { if (rtp_first == NULL) rtp_first = tmpblk; else rtp_last->next = tmpblk; rtp_last = tmpblk; } else { if (rtcp_first == NULL) rtcp_first = tmpblk; else rtcp_last->next = tmpblk; rtcp_last = tmpblk; } tmpblk->next = NULL; tmpblk->data = data2; tmpblk->datalen = len2; tmpblk->ip = ip; tmpblk->port = port; } } len = 0; RTPIOCTL(sock,FIONREAD,&len); } return 0;}void RTPConnection::FlushPackets(){ while (rtp_first != NULL) { rtp_last = rtp_first->next; if (rtp_first->data != NULL) delete [] rtp_first->data; delete rtp_first; rtp_first = rtp_last; } while (rtcp_first != NULL) { rtcp_last = rtcp_first->next; if (rtcp_first->data != NULL) delete [] rtcp_first->data; delete rtcp_first; rtcp_first = rtcp_last; }}#ifdef RTP_VXWORKSunsigned long RTPConnection::CalcLocalIP(){ unsigned long ip; char name[256]; gethostname(name,255); ip = (unsigned long)hostGetByName(name); ip = ntohl(ip);}#else // other systemsunsigned long RTPConnection::CalcLocalIP(){ struct hostent *he; char name[256]; unsigned long ip; bool done; int i,j; gethostname(name,255); name[255] = 0; he = gethostbyname(name); if (he == NULL) return 0; ip = 0; i = 0; done = false; while (!done) { if (he->h_addr_list[i] == NULL) done = true; else { ip = 0; for (j = 0 ; j < 4 ; j++) ip |= ((unsigned long)((unsigned char)he->h_addr_list[i][j])<<((3-j)*8)); if (he->h_addr_list[i][0] != 127 && he->h_addr_list[i][0] != 0) done = true; else i++; } } return ip;}#endif // RTP_VXWORKS#ifndef RTP_MULTICAST/***************************************************************************** ROUTINES FOR USE WITHOUT MULTICASTING SUPPORT*****************************************************************************/bool RTPConnection::SupportsMulticasting(){ return false;}int RTPConnection::JoinMulticastGroup(unsigned long mcastIP){ return ERR_RTP_MULTICASTINGNOTSUPPORTED;}int RTPConnection::LeaveMulticastGroup(unsigned long mcastIP){ return ERR_RTP_MULTICASTINGNOTSUPPORTED;}void RTPConnection::LeaveAllMulticastGroups(){}int RTPConnection::SetMulticastTTL(unsigned char ttl){ return ERR_RTP_MULTICASTINGNOTSUPPORTED;}#else/***************************************************************************** ROUTINES FOR USE WITH MULTICASTING SUPPORT ENABLED*****************************************************************************/bool RTPConnection::SupportsMulticasting(){ return true;}int RTPConnection::JoinMulticastGroup(unsigned long mcastIP){ int status; if (!socketsopened) return ERR_RTP_SOCKETSNOTOPEN; if (!RTP_IS_MCASTADDR(mcastIP)) return ERR_RTP_NOTAMULTICASTADDRESS; status = mcasttable.AddMCastAddress(mcastIP); if (status < 0) return status; RTP_MCASTMEMBERSHIP(rtpsock,IP_ADD_MEMBERSHIP,mcastIP,status); if (status != 0) { mcasttable.DeleteMCastAddress(mcastIP); return ERR_RTP_MULTICASTJOINFAILED; } RTP_MCASTMEMBERSHIP(rtcpsock,IP_ADD_MEMBERSHIP,mcastIP,status); if (status != 0) { RTP_MCASTMEMBERSHIP(rtpsock,IP_DROP_MEMBERSHIP,mcastIP,status); mcasttable.DeleteMCastAddress(mcastIP); return ERR_RTP_MULTICASTJOINFAILED; } return 0;}int RTPConnection::LeaveMulticastGroup(unsigned long mcastIP){ int status; if (!socketsopened) return ERR_RTP_SOCKETSNOTOPEN; if (!RTP_IS_MCASTADDR(mcastIP)) return ERR_RTP_NOTAMULTICASTADDRESS; status = mcasttable.DeleteMCastAddress(mcastIP); if (status < 0) return status; RTP_MCASTMEMBERSHIP(rtpsock,IP_DROP_MEMBERSHIP,mcastIP,status); RTP_MCASTMEMBERSHIP(rtcpsock,IP_DROP_MEMBERSHIP,mcastIP,status); return 0;}void RTPConnection::LeaveAllMulticastGroups(){ unsigned long mcastip; int status; if (!socketsopened) return; mcasttable.GotoFirstMCastAddress(); while (mcasttable.GetNextMCastAddress(&mcastip)) { RTP_MCASTMEMBERSHIP(rtpsock,IP_DROP_MEMBERSHIP,mcastip,status); RTP_MCASTMEMBERSHIP(rtcpsock,IP_DROP_MEMBERSHIP,mcastip,status); } mcasttable.Clear();}int RTPConnection::SetMulticastTTL(unsigned char ttl){ int status; if (!socketsopened) return ERR_RTP_SOCKETSNOTOPEN; #ifdef _AIX status = setsockopt(sendsock,IPPROTO_IP,IP_MULTICAST_TTL,&ttl,sizeof(unsigned char));#else int ttl2; ttl2 = (int)ttl; status = setsockopt(sendsock,IPPROTO_IP,IP_MULTICAST_TTL,(const char *)&ttl2,sizeof(int));#endif // _AIX if (status != 0) return ERR_RTP_CANTSETMULTICASTTTL; return 0;}#endif // RTP_MULTICAST
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -