?? mld6igmp_node.cc
字號:
} mld6igmp_vif->enable(); return (XORP_OK);}/** * Mld6igmpNode::disable_vif: * @vif_name: The name of the vif to disable. * @error_msg: The error message (if error). * * Disable an existing MLD6IGMP vif. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::disable_vif(const string& vif_name, string& error_msg){ Mld6igmpVif *mld6igmp_vif = vif_find_by_name(vif_name); if (mld6igmp_vif == NULL) { error_msg = c_format("Cannot disable vif %s: no such vif", vif_name.c_str()); XLOG_ERROR("%s", error_msg.c_str()); return (XORP_ERROR); } mld6igmp_vif->disable(); return (XORP_OK);}/** * Mld6igmpNode::start_vif: * @vif_name: The name of the vif to start. * @error_msg: The error message (if error). * * Start an existing MLD6IGMP vif. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::start_vif(const string& vif_name, string& error_msg){ Mld6igmpVif *mld6igmp_vif = vif_find_by_name(vif_name); if (mld6igmp_vif == NULL) { error_msg = c_format("Cannot start vif %s: no such vif", vif_name.c_str()); XLOG_ERROR("%s", error_msg.c_str()); return (XORP_ERROR); } if (mld6igmp_vif->start(error_msg) != XORP_OK) { error_msg = c_format("Cannot start vif %s: %s", vif_name.c_str(), error_msg.c_str()); XLOG_ERROR("%s", error_msg.c_str()); return (XORP_ERROR); } return (XORP_OK);}/** * Mld6igmpNode::stop_vif: * @vif_name: The name of the vif to stop. * @error_msg: The error message (if error). * * Stop an existing MLD6IGMP vif. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::stop_vif(const string& vif_name, string& error_msg){ Mld6igmpVif *mld6igmp_vif = vif_find_by_name(vif_name); if (mld6igmp_vif == NULL) { error_msg = c_format("Cannot stop vif %s: no such vif", vif_name.c_str()); XLOG_ERROR("%s", error_msg.c_str()); return (XORP_ERROR); } if (mld6igmp_vif->stop(error_msg) != XORP_OK) { error_msg = c_format("Cannot stop vif %s: %s", vif_name.c_str(), error_msg.c_str()); XLOG_ERROR("%s", error_msg.c_str()); return (XORP_ERROR); } return (XORP_OK);}/** * Mld6igmpNode::start_all_vifs: * @: * * Start MLD/IGMP on all enabled interfaces. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::start_all_vifs(){ vector<Mld6igmpVif *>::iterator iter; string error_msg; int ret_value = XORP_OK; for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = (*iter); if (mld6igmp_vif == NULL) continue; if (start_vif(mld6igmp_vif->name(), error_msg) != XORP_OK) ret_value = XORP_ERROR; } return (ret_value);}/** * Mld6igmpNode::stop_all_vifs: * @: * * Stop MLD/IGMP on all interfaces it was running on. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::stop_all_vifs(){ vector<Mld6igmpVif *>::iterator iter; string error_msg; int ret_value = XORP_OK; for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = (*iter); if (mld6igmp_vif == NULL) continue; if (stop_vif(mld6igmp_vif->name(), error_msg) != XORP_OK) ret_value = XORP_ERROR; } return (ret_value);}/** * Mld6igmpNode::enable_all_vifs: * @: * * Enable MLD/IGMP on all interfaces. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::enable_all_vifs(){ vector<Mld6igmpVif *>::iterator iter; string error_msg; int ret_value = XORP_OK; for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = (*iter); if (mld6igmp_vif == NULL) continue; if (enable_vif(mld6igmp_vif->name(), error_msg) != XORP_OK) ret_value = XORP_ERROR; } return (ret_value);}/** * Mld6igmpNode::disable_all_vifs: * @: * * Disable MLD/IGMP on all interfaces. All running interfaces are stopped * first. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::disable_all_vifs(){ vector<Mld6igmpVif *>::iterator iter; string error_msg; int ret_value = XORP_OK; for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = (*iter); if (mld6igmp_vif == NULL) continue; if (disable_vif(mld6igmp_vif->name(), error_msg) != XORP_OK) ret_value = XORP_ERROR; } return (ret_value);}/** * Mld6igmpNode::delete_all_vifs: * @: * * Delete all MLD/IGMP vifs. **/voidMld6igmpNode::delete_all_vifs(){ list<string> vif_names; vector<Mld6igmpVif *>::iterator iter; // // Create the list of all vif names to delete // for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = (*iter); if (mld6igmp_vif != NULL) { string vif_name = mld6igmp_vif->name(); vif_names.push_back(mld6igmp_vif->name()); } } // // Delete all vifs // list<string>::iterator vif_names_iter; for (vif_names_iter = vif_names.begin(); vif_names_iter != vif_names.end(); ++vif_names_iter) { const string& vif_name = *vif_names_iter; string error_msg; if (delete_vif(vif_name, error_msg) != XORP_OK) { error_msg = c_format("Cannot delete vif %s: internal error", vif_name.c_str()); XLOG_ERROR("%s", error_msg.c_str()); } }}/** * A method called when a vif has completed its shutdown. * * @param vif_name the name of the vif that has completed its shutdown. */voidMld6igmpNode::vif_shutdown_completed(const string& vif_name){ vector<Mld6igmpVif *>::iterator iter; // // If all vifs have completed the shutdown, then de-register with // the MFEA. // for (iter = proto_vifs().begin(); iter != proto_vifs().end(); ++iter) { Mld6igmpVif *mld6igmp_vif = *iter; if (mld6igmp_vif == NULL) continue; if (! mld6igmp_vif->is_down()) return; } // // De-register with the FEA and MFEA // if (ServiceBase::status() == SERVICE_SHUTTING_DOWN) { mfea_register_shutdown(); fea_register_shutdown(); } UNUSED(vif_name);}intMld6igmpNode::proto_recv(const string& if_name, const string& vif_name, const IPvX& src_address, const IPvX& dst_address, uint8_t ip_protocol, int32_t ip_ttl, int32_t ip_tos, bool ip_router_alert, bool ip_internet_control, const vector<uint8_t>& payload, string& error_msg){ Mld6igmpVif *mld6igmp_vif = NULL; int ret_value = XORP_ERROR; debug_msg("Received message on %s/%s from %s to %s: " "ip_ttl = %d ip_tos = %#x ip_router_alert = %d " "ip_internet_control = %d rcvlen = %u\n", if_name.c_str(), vif_name.c_str(), cstring(src_address), cstring(dst_address), ip_ttl, ip_tos, ip_router_alert, ip_internet_control, XORP_UINT_CAST(payload.size())); UNUSED(if_name); // // XXX: We registered to receive only one protocol, hence we ignore // the ip_protocol value. // UNUSED(ip_protocol); // // Check whether the node is up. // if (! is_up()) { error_msg = c_format("MLD/IGMP node is not UP"); return (XORP_ERROR); } // // Find the vif for that packet // mld6igmp_vif = vif_find_by_name(vif_name); if (mld6igmp_vif == NULL) { error_msg = c_format("Cannot find vif with vif_name = %s", vif_name.c_str()); return (XORP_ERROR); } // Copy the data to the receiving #buffer_t BUFFER_RESET(_buffer_recv); BUFFER_PUT_DATA(&payload[0], _buffer_recv, payload.size()); // Process the data by the vif ret_value = mld6igmp_vif->mld6igmp_recv(src_address, dst_address, ip_ttl, ip_tos, ip_router_alert, ip_internet_control, _buffer_recv, error_msg); return (ret_value); buflen_error: XLOG_UNREACHABLE(); return (XORP_ERROR);}intMld6igmpNode::mld6igmp_send(const string& if_name, const string& vif_name, const IPvX& src_address, const IPvX& dst_address, uint8_t ip_protocol, int32_t ip_ttl, int32_t ip_tos, bool ip_router_alert, bool ip_internet_control, buffer_t *buffer, string& error_msg){ if (! is_up()) { error_msg = c_format("MLD/IGMP node is not UP"); return (XORP_ERROR); } if (proto_send(if_name, vif_name, src_address, dst_address, ip_protocol, ip_ttl, ip_tos, ip_router_alert, ip_internet_control, BUFFER_DATA_HEAD(buffer), BUFFER_DATA_SIZE(buffer), error_msg) != XORP_OK) { return (XORP_ERROR); } return (XORP_OK);}/** * Mld6igmpNode::add_protocol: * @module_instance_name: The module instance name of the protocol to add. * @module_id: The #xorp_module_id of the protocol to add. * @vif_index: The vif index of the interface to add the protocol to. * * Add a protocol to the list of entries that would be notified if there * is membership change on a particular interface. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::add_protocol(const string& module_instance_name, xorp_module_id module_id, uint32_t vif_index){ Mld6igmpVif *mld6igmp_vif = vif_find_by_vif_index(vif_index); if (mld6igmp_vif == NULL) { XLOG_ERROR("Cannot add protocol instance %s on vif_index %d: " "no such vif", module_instance_name.c_str(), vif_index); return (XORP_ERROR); } if (mld6igmp_vif->add_protocol(module_id, module_instance_name) != XORP_OK) return (XORP_ERROR); return (XORP_OK);}/** * Mld6igmpNode::delete_protocol: * @module_instance_name: The module instance name of the protocol to delete. * @module_id: The #xorp_module_id of the protocol to delete. * @vif_index: The vif index of the interface to delete the protocol from. * * Delete a protocol from the list of entries that would be notified if there * is membership change on a particular interface. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::delete_protocol(const string& module_instance_name, xorp_module_id module_id, uint32_t vif_index){ Mld6igmpVif *mld6igmp_vif = vif_find_by_vif_index(vif_index); if (mld6igmp_vif == NULL) { XLOG_ERROR("Cannot delete protocol instance %s on vif_index %d: " "no such vif", module_instance_name.c_str(), vif_index); return (XORP_ERROR); } if (mld6igmp_vif->delete_protocol(module_id, module_instance_name) != XORP_OK) { return (XORP_ERROR); } return (XORP_OK);}/** * Mld6igmpNode::join_prune_notify_routing: * @module_instance_name: The module instance name of the protocol to notify. * @module_id: The #xorp_module_id of the protocol to notify. * @vif_index: The vif index of the interface with membership change. * @source: The source address of the (S,G) or (*,G) entry that has changed. * In case of group-specific membership, it is IPvX::ZERO(). * @group: The group address of the (S,G) or (*,G) entry that has changed. * @action_jp: The membership change type #action_jp_t: * either %ACTION_JOIN or %ACTION_PRUNE. * * Notify the protocol instance with name @module_instance_name that there is * multicast membership change on interface with vif index of @vif_index. * * Return value: %XORP_OK on success, otherwise %XORP_ERROR. **/intMld6igmpNode::join_prune_notify_routing(const string& module_instance_name, xorp_module_id module_id, uint32_t vif_index, const IPvX& source, const IPvX& group, action_jp_t action_jp){ // // Send add/delete membership to the registered protocol instance. // switch (action_jp) { case ACTION_JOIN: send_add_membership(module_instance_name, module_id, vif_index, source, group); break; case ACTION_PRUNE: send_delete_membership(module_instance_name, module_id, vif_index, source, group); break; default: XLOG_UNREACHABLE(); break; } return (XORP_OK);}/** * Mld6igmpNode::is_directly_connected: * @mld6igmp_vif: The virtual interface to test against. * @ipaddr_test: The address to test. * * Note that the virtual interface the address is directly connected to * must be UP. * * Return value: True if @ipaddr_test is directly connected to @mld6igmp_vif, * otherwise false. **/boolMld6igmpNode::is_directly_connected(const Mld6igmpVif& mld6igmp_vif, const IPvX& ipaddr_test) const{ if (! mld6igmp_vif.is_up()) return (false);#if 0 // TODO: not implemented yet // // Test the alternative subnets // list<IPvXNet>::const_iterator iter; for (iter = mld6igmp_vif.alternative_subnet_list().begin(); iter != mld6igmp_vif.alternative_subnet_list().end(); ++iter) { const IPvXNet& ipvxnet = *iter; if (ipvxnet.contains(ipaddr_test)) return true; }#endif // // Test the same subnet addresses, or the P2P addresses // return (mld6igmp_vif.is_same_subnet(ipaddr_test) || mld6igmp_vif.is_same_p2p(ipaddr_test));}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -