7 #include <boost/uuid/uuid_io.hpp>
9 #include <vnc_cfg_types.h>
27 #include <bgp_schema_types.h>
29 #include <arpa/inet.h>
30 #include <netinet/in.h>
38 (
"BgpAsAService", 500));
42 bgp_as_a_service_entry_map_(),
43 bgp_as_a_service_port_map_(),
44 service_delete_cb_list_(), health_check_cb_list_() {
105 it->set_del_pending(
true);
115 iter != list.end(); ++iter) {
117 iter->health_check_uuid_ != boost::uuids::nil_uuid()) {
118 std::vector<HealthCheckCb>::iterator hcb_it =
121 (*hcb_it)(vm_uuid, iter->source_port_,
122 iter->health_check_uuid_,
true);
126 iter->new_health_check_add_ =
false;
140 return vrf_node->
name();
142 return std::string();
153 return adj_node->
name();
156 return std::string();
160 std::list<IFMapNode *> &bgp_router_nodes,
162 const std::string &vm_vrf_name,
166 autogen::BgpAsAService *bgp_as_a_service =
167 dynamic_cast<autogen::BgpAsAService *
>(bgp_as_a_service_node->
GetObject());
168 assert(bgp_as_a_service);
171 uint32_t source_port = 0;
172 bool health_check_configured =
false;
174 uint64_t hc_delay_usecs = 0;
175 uint64_t hc_timeout_usecs = 0;
176 uint32_t hc_retries = 0;
177 std::string primary_control_node_zone;
178 std::string secondary_control_node_zone;
182 it != bgp_as_a_service_node->
end(table->
GetGraph()); ++it) {
189 autogen::ServiceHealthCheck *hc =
190 static_cast<autogen::ServiceHealthCheck *
> (adj_node->
GetObject());
193 if (hc->properties().monitor_type.find(
"BFD") == std::string::npos)
195 health_check_configured =
true;
196 autogen::IdPermsType id_perms = hc->id_perms();
197 CfgUuidSet(id_perms.uuid.uuid_mslong, id_perms.uuid.uuid_lslong,
199 hc_delay_usecs = hc->properties().delay * 1000000 +
200 hc->properties().delayUsecs;
201 hc_timeout_usecs = hc->properties().timeout * 1000000 +
202 hc->properties().timeoutUsecs;
203 hc_retries = hc->properties().max_retries;
208 autogen::BgpaasControlNodeZone
209 *bgpaas_cnz =
static_cast<autogen::BgpaasControlNodeZone *
>
211 const autogen::BGPaaSControlNodeZoneAttributes &attr =
212 static_cast<autogen::BGPaaSControlNodeZoneAttributes
>
213 (bgpaas_cnz->data());
215 if (cnz_name.size()) {
216 if (strcmp(attr.bgpaas_control_node_zone_type.c_str(),
218 primary_control_node_zone = cnz_name;
221 if (strcmp(attr.bgpaas_control_node_zone_type.c_str(),
223 secondary_control_node_zone = cnz_name;
232 it != bgp_as_a_service_node->
end(table->
GetGraph()); ++it) {
237 if (std::find(bgp_router_nodes.begin(), bgp_router_nodes.end(),
238 adj_node) == bgp_router_nodes.end()) {
241 autogen::BgpRouter *bgp_router=
242 dynamic_cast<autogen::BgpRouter *
>(adj_node->
GetObject());
243 const std::string &vrf_name =
245 if (vrf_name.empty() || (vrf_name != vm_vrf_name) ||
246 (strcmp(bgp_router->parameters().router_type.c_str(),
249 boost::system::error_code ec;
251 IpAddress::from_string(bgp_router->parameters().address, ec);
252 if (ec.value() != 0) {
253 std::stringstream ss;
254 ss <<
"Ip address parsing failed for ";
255 ss << bgp_router->parameters().address;
266 if (old_bgp_as_a_service_entry_list_iter !=
269 temp_bgp_as_a_service_entry_list.insert(
271 bgp_router->parameters().source_port,
272 bgp_router->parameters().port,
273 health_check_configured,
275 bgp_as_a_service->bgpaas_shared(),
279 primary_control_node_zone,
280 secondary_control_node_zone));
284 if (temp_bgp_as_a_service_entry_list ==
285 old_bgp_as_a_service_entry_list_iter->second->list_) {
286 source_port = bgp_router->parameters().source_port;
290 if (bgp_as_a_service->bgpaas_shared()) {
292 bgp_router->parameters().source_port,
295 source_port = bgp_router->parameters().source_port;
300 bgp_router->parameters().port,
301 health_check_configured,
303 bgp_as_a_service->bgpaas_shared(),
307 primary_control_node_zone,
308 secondary_control_node_zone));
316 std::list<IFMapNode *> &bgp_router_node_map,
317 std::list<IFMapNode *> &bgp_as_service_node_map,
319 std::list<IFMapNode *>::const_iterator it =
320 bgp_as_service_node_map.begin();
323 while (it != bgp_as_service_node_map.end()) {
325 new_bgp_as_a_service_entry_list,
333 bool changed =
false;
334 if (old_bgp_as_a_service_entry_list_iter !=
337 changed = AuditList<BgpAsAServiceList, BgpAsAServiceEntryListIterator>
338 (*(old_bgp_as_a_service_entry_list_iter->second),
339 old_bgp_as_a_service_entry_list_iter->second->list_.begin(),
340 old_bgp_as_a_service_entry_list_iter->second->list_.end(),
341 new_bgp_as_a_service_entry_list.begin(),
342 new_bgp_as_a_service_entry_list.end());
343 }
else if (new_bgp_as_a_service_entry_list.size() != 0) {
352 old_bgp_as_a_service_entry_list_iter->second->list_.begin();
354 old_bgp_as_a_service_entry_list_iter->second->list_.end()) {
356 if (prev->del_pending_) {
357 std::vector<ServiceDeleteCb>::iterator scb_it =
360 (*scb_it)(vm_uuid, prev->source_port_);
365 if ((prev->is_shared_ && vmi==NULL) || (prev->is_shared_ && vmi && vmi->
IsDeleted())) {
369 LOG(DEBUG,
"Undeleted vmi might have active bgp session with source port");
372 old_bgp_as_a_service_entry_list_iter->second->list_.erase(prev);
375 if (prev->old_health_check_delete_) {
377 prev->old_health_check_uuid_ != boost::uuids::nil_uuid()) {
378 std::vector<HealthCheckCb>::iterator hcb_it =
381 (*hcb_it)(vm_uuid, prev->source_port_,
382 prev->old_health_check_uuid_,
false);
386 prev->old_health_check_delete_ =
false;
387 prev->old_health_check_uuid_ = boost::uuids::nil_uuid();
389 if (prev->new_health_check_add_) {
391 prev->health_check_uuid_ != boost::uuids::nil_uuid()) {
392 std::vector<HealthCheckCb>::iterator hcb_it =
395 (*hcb_it)(vm_uuid, prev->source_port_,
396 prev->health_check_uuid_,
true);
400 prev->new_health_check_add_ =
false;
417 while (list_iter != list.end()) {
418 std::vector<ServiceDeleteCb>::iterator scb_it =
421 (*scb_it)(vm_uuid, (*list_iter).source_port_);
424 if ((*list_iter).is_shared_) {
446 iter->second->list_.begin();
447 while (it != iter->second->list_.end()) {
448 if ((*it).local_peer_ip_ == source_ip)
456 if (vn == NULL)
return false;
471 ports.first, ports.second);
479 size_t vmi_service_port_index = portinfo.second;
481 vmi_service_port_index);
482 port_map_it->second->Remove(vmi_service_port_index);
484 if (port_map_it->second->NoneIndexSet()) {
485 delete port_map_it->second;
513 std::stringstream ss;
514 ss <<
"Service Port Index is not available for ";
521 vmi_service_port_index,
522 ports.first, ports.second);
528 uint32_t *sport, uint32_t *dport)
const {
530 if (vn == NULL)
return false;
536 std::stringstream ss;
540 ss <<
"vmi-uuid:" << vm_intf->
GetUuid() <<
" not found";
547 while (it != map_it->second->list_.end()) {
548 bool cnz_configured = it->IsControlNodeZoneConfigured();
551 std::string xmpp_server;
552 std::string control_node_zone;
553 std::string *bgp_router_name;
555 if (cnz_configured) {
556 bgp_router = bgp_router_cfg->
557 GetBgpRouterFromControlNodeZone(
558 it->primary_control_node_zone_);
559 control_node_zone = it->primary_control_node_zone_;
562 if (xmpp_server.size())
563 bgp_router = bgp_router_cfg->
564 GetBgpRouterFromXmppServer(xmpp_server);
566 bgp_router_name = &it->primary_bgp_peer_;
567 }
else if (dest == dns) {
568 if (cnz_configured) {
569 bgp_router = bgp_router_cfg->
570 GetBgpRouterFromControlNodeZone(
571 it->secondary_control_node_zone_);
572 control_node_zone = it->secondary_control_node_zone_;
575 if (xmpp_server.size())
576 bgp_router = bgp_router_cfg->
577 GetBgpRouterFromXmppServer(xmpp_server);
579 bgp_router_name = &it->secondary_bgp_peer_;
584 if (bgp_router.get() == NULL) {
585 ss <<
"BgpRouter not found.";
586 ss <<
" bgpaas-source-ip:" << source_ip.to_string();
587 ss <<
" bgpaas-destination-ip:" << dest.to_string();
588 ss <<
" control-node-zone:" << control_node_zone;
589 ss <<
" xmpp-server:" << xmpp_server;
592 *bgp_router_name =
"";
595 *nat_server = bgp_router->ipv4_address();
596 *sport = it->source_port_;
597 *dport = it->dest_port_?it->dest_port_:bgp_router->port();
599 *bgp_router_name = bgp_router->name();
602 ss <<
"BgpRouter not found ";
603 ss <<
" bgpaas-source-ip:" << source_ip.to_string();
604 ss <<
" bgpaas-destination-ip" << dest.to_string();
616 found->second->list_.begin();
617 while (it != found->second->list_.end()) {
618 if (it->health_check_configured_) {
619 *health_check_uuid = it->health_check_uuid_;
620 std::ostringstream ss;
621 ss<<
"searched for vm_intf_uuid: "<<boost::uuids::to_string(vm_intf->
GetUuid())
622 <<
" - found: "<<boost::uuids::to_string(*health_check_uuid);
629 std::ostringstream ss;
630 ss<<
"vm_intf_uuid: "<<boost::uuids::to_string(vm_intf->
GetUuid())+
" - not found in BgpAaS entry map";
638 unsigned int source_port = 0;
639 unsigned int index = 0;
644 std::pair<BgpAsAServiceEntryListIterator, bool> ret;
650 while (list_iter != list.end()) {
653 list_iter->source_port_,
656 source_port = portinfo.first;
657 index = portinfo.second;
667 if (list_iter->source_port_ != source_port) {
670 list_iter->dest_port_,
671 list_iter->health_check_configured_,
672 list_iter->health_check_uuid_,
673 list_iter->is_shared_,
674 list_iter->hc_delay_usecs_,
675 list_iter->hc_timeout_usecs_,
676 list_iter->hc_retries_,
677 list_iter->primary_control_node_zone_,
678 list_iter->secondary_control_node_zone_);
679 std::vector<ServiceDeleteCb>::iterator scb_it =
682 (*scb_it)(iter->first, list_iter->source_port_);
685 iter->second->list_.erase(*list_iter);
686 iter->second->list_.insert(temp);
702 local_peer_ip_(), source_port_(0), dest_port_(0),
703 health_check_configured_(false), health_check_uuid_(),
704 new_health_check_add_(false),old_health_check_delete_(false),
705 old_health_check_uuid_(),hc_delay_usecs_(0),
706 hc_timeout_usecs_(0), hc_retries_(0), is_shared_(false),
707 primary_control_node_zone_(), secondary_control_node_zone_() {
713 installed_(rhs.installed_),
714 local_peer_ip_(rhs.local_peer_ip_),
715 source_port_(rhs.source_port_),
716 dest_port_(rhs.dest_port_),
717 health_check_configured_(rhs.health_check_configured_),
718 health_check_uuid_(rhs.health_check_uuid_),
719 new_health_check_add_(rhs.new_health_check_add_),
720 old_health_check_delete_(rhs.old_health_check_delete_),
721 old_health_check_uuid_(rhs.old_health_check_uuid_),
722 hc_delay_usecs_(rhs.hc_delay_usecs_),
723 hc_timeout_usecs_(rhs.hc_timeout_usecs_),
724 hc_retries_(rhs.hc_retries_), is_shared_(rhs.is_shared_),
725 primary_control_node_zone_(rhs.primary_control_node_zone_),
726 secondary_control_node_zone_(rhs.secondary_control_node_zone_) {
730 (
const IpAddress &local_peer_ip, uint32_t source_port, uint32_t dest_port,
732 bool is_shared, uint64_t hc_delay_usecs, uint64_t hc_timeout_usecs,
733 uint32_t hc_retries,
const std::string &primary_control_node_zone,
734 const std::string &secondary_control_node_zone) :
737 local_peer_ip_(local_peer_ip),
738 source_port_(source_port),
739 dest_port_(dest_port),
740 health_check_configured_(health_check_configured),
741 health_check_uuid_(health_check_uuid),
742 new_health_check_add_(health_check_configured),
743 old_health_check_delete_(false), old_health_check_uuid_(),
744 hc_delay_usecs_(hc_delay_usecs), hc_timeout_usecs_(hc_timeout_usecs),
745 hc_retries_(hc_retries), is_shared_(is_shared),
746 primary_control_node_zone_(primary_control_node_zone),
747 secondary_control_node_zone_(secondary_control_node_zone) {
753 bool BgpAsAService::BgpAsAServiceEntry::operator ==
755 return ((source_port_ == rhs.source_port_) &&
756 (local_peer_ip_ == rhs.local_peer_ip_) &&
757 (is_shared_ == rhs.is_shared_));
760 bool BgpAsAService::BgpAsAServiceEntry::operator()
762 return lhs.IsLess(&rhs);
778 void BgpAsAServiceSandeshReq::HandleRequest()
const {
779 BgpAsAServiceSandeshResp *resp =
new BgpAsAServiceSandeshResp();
780 resp->set_context(context());
788 std::vector<BgpAsAServiceSandeshList> bgpaas_map;
789 std::string vmi_uuid_str = get_vmi_uuid();
790 while (map_it != map_entry.end()) {
791 if (vmi_uuid_str.empty() ==
false) {
793 if (vmi_uuid != map_it->first) {
799 map_it->second->list_.begin();
800 while (it != map_it->second->list_.end()) {
801 BgpAsAServiceSandeshList entry;
802 entry.set_vm_bgp_peer_ip((*it).local_peer_ip_.to_string());
803 entry.set_vm_nat_source_port((*it).source_port_);
805 entry.set_health_check_configured((*it).health_check_configured_);
806 entry.set_health_check_uuid(
UuidToString((*it).health_check_uuid_));
807 entry.set_health_check_delay_usecs((*it).hc_delay_usecs_);
808 entry.set_health_check_timeout_usecs((*it).hc_timeout_usecs_);
809 entry.set_health_check_retries((*it).hc_retries_);
810 entry.set_is_shared((*it).is_shared_);
811 entry.set_primary_control_node_zone(
812 (*it).primary_control_node_zone_);
813 entry.set_secondary_control_node_zone(
814 (*it).secondary_control_node_zone_);
815 entry.set_primary_bgp_peer((*it).primary_bgp_peer_);
816 entry.set_secondary_bgp_peer((*it).secondary_bgp_peer_);
817 bgpaas_map.push_back(entry);
822 resp->set_bgp_as_a_service_list(bgpaas_map);
boost::asio::ip::address IpAddress
boost::intrusive_ptr< const Interface > InterfaceConstRef
static void CfgUuidSet(uint64_t ms_long, uint64_t ls_long, boost::uuids::uuid &u)
static const std::string GetBgpRouterVrfName(const Agent *agent, IFMapNode *node)
static const std::string GetControlNodeZoneName(IFMapNode *node)
SandeshTraceBufferPtr BgpAsAServiceTraceBuf(SandeshTraceBufferCreate("BgpAsAService", 500))
#define BGPASASERVICETRACE(obj,...)
#define BGP_ROUTER_CONFIG_NAME
#define BGPAAS_CONTROL_NODE_ZONE_CONFIG_NAME
#define VALID_BGP_ROUTER_TYPE
#define CONTROL_NODE_ZONE_CONFIG_NAME
boost::shared_ptr< BgpRouter > BgpRouterPtr
IFMapAgentTable * cfg_vrf_table() const
IFMapAgentTable * cfg_health_check_table() const
InterfaceTable * interface_table() const
ConfigManager * config_manager() const
ResourceManager * resource_manager() const
AgentConfig * cfg() const
const std::string & controller_ifmap_xmpp_server(uint8_t idx) const
static Agent * GetInstance()
std::pair< uint32_t, size_t > BgpAsServicePortIndexPair
static BgpAsServicePortIndexPair DecodeBgpaasServicePort(const uint32_t sport, const uint16_t port_range_start, const uint16_t port_range_end)
static uint32_t EncodeBgpaasServicePort(const uint32_t sport, const size_t index, const uint16_t port_range_start, const uint16_t port_range_end)
void StartHealthCheck(const boost::uuids::uuid &vm_uuid, const BgpAsAServiceEntryList &list)
BGPaaServiceParameters bgp_as_a_service_parameters_
BgpAsAServiceEntryList::iterator BgpAsAServiceEntryListIterator
std::vector< HealthCheckCb > health_check_cb_list_
uint32_t AddBgpVmiServicePortIndex(const uint32_t source_port, const boost::uuids::uuid vm_uuid)
void ProcessConfig(const std::string &vrf_name, std::list< IFMapNode * > &bgp_router_node_list, std::list< IFMapNode * > &bgp_as_service_node_list, const boost::uuids::uuid &vmi_uuid)
size_t AllocateBgpVmiServicePortIndex(const uint32_t sport, const boost::uuids::uuid vm_uuid)
BgpAsAServiceEntryMap::iterator BgpAsAServiceEntryMapIterator
const BgpAsAService::BgpAsAServicePortMap & bgp_as_a_service_port_map() const
std::map< boost::uuids::uuid, BgpAsAServiceList * > BgpAsAServiceEntryMap
std::set< BgpAsAServiceEntry, BgpAsAServiceEntry > BgpAsAServiceEntryList
BgpAsAServiceEntryMap bgp_as_a_service_entry_map_
std::map< uint32_t, IndexVector< boost::uuids::uuid > * > BgpAsAServicePortMap
bool IsBgpService(const VmInterface *vm_intf, const IpAddress &source_ip, const IpAddress &dest_ip) const
BGPaaServiceParameters::BGPaaServicePortRangePair bgp_as_a_service_port_range() const
BgpAsAServiceEntryList::const_iterator BgpAsAServiceEntryListConstIterator
BgpAsAServiceEntryMap::const_iterator BgpAsAServiceEntryMapConstIterator
const BgpAsAService::BgpAsAServiceEntryMap & bgp_as_a_service_map() const
void UpdateBgpAsAServiceSessionInfo()
void BuildBgpAsAServiceInfo(IFMapNode *bgp_as_a_service_node, std::list< IFMapNode * > &bgp_router_nodes, BgpAsAServiceEntryList &new_list, const std::string &vrf_name, const boost::uuids::uuid &vm_uuid)
std::vector< ServiceDeleteCb > service_delete_cb_list_
BgpAsAServicePortMap::iterator BgpAsAServicePortMapIterator
void FreeBgpVmiServicePortIndex(const uint32_t sport)
bool GetBgpHealthCheck(const VmInterface *vm_intf, boost::uuids::uuid *health_check_uuid) const
bool GetBgpRouterServiceDestination(const VmInterface *vm_intf, const IpAddress &source, const IpAddress &dest, IpAddress *nat_server, uint32_t *sport, uint32_t *dport) const
BgpAsAServicePortMap bgp_as_a_service_port_map_
void DeleteVmInterface(const boost::uuids::uuid &vmi_uuid)
BgpAsAService(const Agent *agent)
bool SkipNode(IFMapNode *node)
adjacency_iterator end(DBGraph *graph)
adjacency_iterator begin(DBGraph *graph)
BGPaaServiceParameters::BGPaaServicePortRangePair bgpaas_port_range() const
const DBGraph * GetGraph() const
const std::string & name() const
IFMapObject * GetObject()
virtual const char * Typename() const =0
InterfaceConstRef FindVmi(const boost::uuids::uuid &u)
const boost::uuids::uuid & GetUuid() const
GlobalSystemConfig * global_system_config() const
BgpAsAService * bgp_as_a_service() const
BgpRouterConfig * bgp_router_config() const
boost::shared_ptr< ResourceKey > KeyPtr
ResourceManager::DataPtr Allocate(KeyPtr key)
const VnEntry * vn() const
const Ip4Address & primary_ip_addr() const
IpAddress GetGatewayFromIpam(const IpAddress &ip) const
IpAddress GetDnsFromIpam(const IpAddress &ip) const
#define LOG(_Level, _Msg)
boost::shared_ptr< TraceBuffer< SandeshTrace > > SandeshTraceBufferPtr
SandeshTraceBufferPtr SandeshTraceBufferCreate(const std::string &buf_name, size_t buf_size, bool trace_enable=true)
static boost::uuids::uuid StringToUuid(const std::string &str)
static std::string UuidToString(const boost::uuids::uuid &id)
std::pair< uint16_t, uint16_t > BGPaaServicePortRangePair
bool IsLess(const BgpAsAServiceEntry *rhs) const
boost::uuids::uuid health_check_uuid_
bool health_check_configured_
bool old_health_check_delete_
boost::uuids::uuid old_health_check_uuid_
bool new_health_check_add_
std::string secondary_control_node_zone_
std::string primary_control_node_zone_
uint64_t hc_timeout_usecs_
void Insert(const BgpAsAServiceEntry *rhs)
void Remove(BgpAsAServiceEntryListIterator &it)
void Update(const BgpAsAServiceEntry *lhs, const BgpAsAServiceEntry *rhs)
BgpAsAServiceEntryList list_