bool querier::router_groups_function(bool subscribe) const { HC_LOG_TRACE(""); //MLDv1 RFC 2710: Section 8. link-scope all-routers (FF02::2), link-scope all-routers (FF05::2)| IANA: site local scope all-routers //MLDv2 RFC 3810: Section 7. all MLDv2-capable routers (FF02::16) //IGMPv1 //IGMPv2 RFC 2236: Section 9. ALL-ROUTERS (224.0.0.2) //IGMPv3 IANA: IGMP (224.0.0.22) mc_filter mf; if (subscribe) { mf = EXCLUDE_MODE; } else { mf = INCLUDE_MODE; } bool rc = true; if (is_IPv4(m_db.querier_version_mode)) { rc = rc && m_sender->send_record(m_if_index, mf, addr_storage(IPV4_ALL_IGMP_ROUTERS_ADDR), source_list<source>()); rc = rc && m_sender->send_record(m_if_index, mf, addr_storage(IPV4_IGMPV3_ADDR), source_list<source>()); } else if (is_IPv6(m_db.querier_version_mode)) { rc = rc && m_sender->send_record(m_if_index, mf, addr_storage(IPV6_ALL_NODE_LOCAL_ROUTER), source_list<source>()); rc = rc && m_sender->send_record(m_if_index, mf, addr_storage(IPV6_ALL_SITE_LOCAL_ROUTER), source_list<source>()); rc = rc && m_sender->send_record(m_if_index, mf, addr_storage(IPV6_ALL_MLDv2_CAPABLE_ROUTERS), source_list<source>()); } else { HC_LOG_ERROR("unknown ip version"); return false; } return rc; }
void if_prop::print_if_addr(const struct ifaddrs* if_p) const{ cout << "\tif name: " << if_p->ifa_name << endl; cout << "\t- addr: " << addr_storage(*if_p->ifa_addr) << endl; cout << "\t- netmask: " << addr_storage(*if_p->ifa_netmask) << endl; cout << "\t- flags:"; if(if_p->ifa_flags & IFF_UP) cout << "IFF_UP "; if(if_p->ifa_flags & IFF_RUNNING) cout << "IFF_RUNNING "; if(if_p->ifa_flags & IFF_LOOPBACK) cout << "IFF_LOOPBACK "; if(if_p->ifa_flags & IFF_BROADCAST) cout << "IFF_BROADCAST "; if(if_p->ifa_flags & IFF_ALLMULTI) cout << "IFF_ALLMULTI "; if(if_p->ifa_flags & IFF_MULTICAST) cout << "IFF_MULTICAST "; if(if_p->ifa_flags & IFF_PROMISC) cout << "IFF_PROMISCIFF_PROMISC "; if(if_p->ifa_flags & IFF_POINTOPOINT) cout << "IFF_POINTOPOINT "; cout << endl; if(if_p->ifa_flags & IFF_POINTOPOINT){ if(if_p->ifa_dstaddr != NULL){ cout << "\t- dstaddr: " << addr_storage(*if_p->ifa_dstaddr) << endl; } }else if(if_p->ifa_addr->sa_family == AF_INET){ //broadcast addr cout << "\t- broadaddr: " << addr_storage(*if_p->ifa_broadaddr) << endl; } }
bool mld_sender::create_mc_query(msg_type type, unsigned char* buf, const addr_storage* g_addr){ HC_LOG_TRACE(""); if(m_version == 1){ struct mld_hdr* mld_Hdr = (struct mld_hdr*)buf; mld_Hdr->mld_type = MLD_LISTENER_QUERY; mld_Hdr->mld_code = 0; mld_Hdr->mld_cksum = MC_MASSAGES_AUTO_FILL; mld_Hdr->mld_reserved = 0; if(type==GENERAL_QUERY){ mld_Hdr->mld_maxdelay = htons(MC_TV_QUERY_RESPONSE_INTERVAL * MC_TV_MAX_RESPONSE_DELAY_UNIT); mld_Hdr->mld_addr = addr_storage(m_addr_family).get_in6_addr(); //0.0.0.0 }else if(type== MC_ADDR_SPECIFIC_QUERY){ if(!g_addr){ HC_LOG_ERROR("g_addr is NULL"); return false; } mld_Hdr->mld_maxdelay = htons(MC_TV_LAST_LISTENER_QUERY_INTERVAL * MC_TV_MAX_RESPONSE_DELAY_UNIT); mld_Hdr->mld_addr = g_addr->get_in6_addr(); }else{ HC_LOG_ERROR("wrong type: " << type); return false; } return true; }else{ HC_LOG_ERROR("wrong verson: "<< m_version); return false; } }
bool igmp_sender::create_mc_query(msg_type type, unsigned char* buf,const addr_storage* g_addr){ HC_LOG_TRACE(""); if(m_version == 2){ struct igmp* igmp_Hdr = (struct igmp*)(buf); igmp_Hdr->igmp_type = IGMP_MEMBERSHIP_QUERY; igmp_Hdr->igmp_cksum = 0; if(type==GENERAL_QUERY){ igmp_Hdr->igmp_code = MC_TV_QUERY_RESPONSE_INTERVAL*MC_TV_MAX_RESPONSE_TIME_UNIT; igmp_Hdr->igmp_group = addr_storage(m_addr_family).get_in_addr(); //0.0.0.0 }else if(type== GROUP_SPECIFIC_QUERY){ if(!g_addr){ HC_LOG_ERROR("g_addr is NULL"); return false; } igmp_Hdr->igmp_code = MC_TV_LAST_MEMBER_QUERY_INTEVAL*MC_TV_MAX_RESPONSE_TIME_UNIT; igmp_Hdr->igmp_group = g_addr->get_in_addr(); }else{ HC_LOG_ERROR("wrong type: " << type); return false; } igmp_Hdr->igmp_cksum = m_sock.calc_checksum((unsigned char*)igmp_Hdr,sizeof(struct igmp)); return true; }else{ HC_LOG_ERROR("wrong verson: "<< m_version); return false; } }
bool if_prop::refresh_network_interfaces(){ HC_LOG_TRACE(""); //clean if(is_getaddrs_valid()){ freeifaddrs(m_if_addrs); } m_if_map.clear(); //create if(getifaddrs(&m_if_addrs) < 0){ HC_LOG_ERROR("getifaddrs failed! Error: " << strerror(errno) ); return false; } struct ifaddrs* ifEntry=NULL; for(ifEntry=m_if_addrs; ifEntry!=NULL; ifEntry=ifEntry->ifa_next) { if(ifEntry->ifa_addr->sa_data == NULL) { continue; } if(ifEntry->ifa_addr->sa_family==AF_INET) { if_prop_map::iterator iter = m_if_map.find(ifEntry->ifa_name); if(iter != m_if_map.end()){ //existing interface if(iter->second.ip4_addr != NULL){ HC_LOG_WARN("more than one ipv4 address for one interface configurated! used:" << addr_storage(*(iter->second.ip4_addr->ifa_addr)) << "; don't used:" << addr_storage(*(ifEntry->ifa_addr)) << ";"); //return false; }else{ iter->second.ip4_addr = ifEntry; } }else{ //new interface m_if_map.insert(if_prop_pair(ifEntry->ifa_name, ipv4_6_pair(ifEntry,list<const struct ifaddrs*>()))); } } else if(ifEntry->ifa_addr->sa_family==AF_INET6) { if_prop_map::iterator iter = m_if_map.find(ifEntry->ifa_name); if(iter != m_if_map.end()){ //existing interface list<const struct ifaddrs*>* l = &iter->second.ip6_addr; l->push_back(ifEntry); }else{ //new interface list<const struct ifaddrs*> l; l.push_back(ifEntry); m_if_map.insert(if_prop_pair(ifEntry->ifa_name, ipv4_6_pair(NULL,l))); } } else { //It isn't IPv4 or IPv6 continue; } } return true; }