LCOV - code coverage report
Current view: top level - dns/mgr - dns_oper.cc (source / functions) Hit Total Coverage
Test: OpenSDN C/C++ coverage (all TARGET_SET jobs) Lines: 392 516 76.0 %
Date: 2026-11-09 02:10:49 Functions: 51 64 79.7 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :  * Copyright (c) 2013 Juniper Networks, Inc. All rights reserved.
       3             :  * Copyright Contributors to the OpenSDN project
       4             :  */
       5             : 
       6             : #include <cmn/dns.h>
       7             : #include <bind/bind_util.h>
       8             : #include <bind/bind_resolver.h>
       9             : #include <mgr/dns_mgr.h>
      10             : #include <mgr/dns_oper.h>
      11             : #include <bind/named_config.h>
      12             : #include <agent/agent_xmpp_channel.h>
      13             : #include <sandesh/sandesh_types.h>
      14             : #include <sandesh/common/vns_types.h>
      15             : #include <vnc_cfg_types.h>
      16             : 
      17             : #include <boost/bind/bind.hpp>
      18             : #include "base/logging.h"
      19             : #include "base/task.h"
      20             : #include "base/util.h"
      21             : #include "bind/bind_util.h"
      22             : #include "cfg/dns_config.h"
      23             : #include "cfg/config_listener.h"
      24             : #include "ifmap/ifmap_link.h"
      25             : #include "ifmap/ifmap_table.h"
      26             : #include "cmn/dns.h"
      27             : #include "xmpp/xmpp_server.h"
      28             : 
      29             : using namespace std;
      30             : using namespace boost::placeholders;
      31             : 
      32             : ////////////////////////////////////////////////////////////////////////////////
      33             : 
      34             : const std::string DnsConfig::EventString[] = {
      35             :     "Add",
      36             :     "Change",
      37             :     "Delete"
      38             : };
      39             : DnsConfig::Callback DnsConfig::VdnsCallback;
      40             : DnsConfig::Callback DnsConfig::VdnsRecordCallback;
      41             : DnsConfig::ZoneCallback DnsConfig::VdnsZoneCallback;
      42             : VnniConfig::DataMap VnniConfig::vnni_config_;
      43             : IpamConfig::DataMap IpamConfig::ipam_config_;
      44             : VirtualDnsConfig::DataMap VirtualDnsConfig::virt_dns_config_;
      45             : VirtualDnsRecordConfig::DataMap VirtualDnsRecordConfig::virt_dns_rec_config_;
      46             : GlobalQosConfig *GlobalQosConfig::singleton_;
      47             : 
      48             : ////////////////////////////////////////////////////////////////////////////////
      49             : 
      50          16 : VnniConfig::VnniConfig(IFMapNode *node)
      51          16 :                      : DnsConfig(node->name()), ipam_(NULL) {
      52          16 :     vnni_config_.insert(DataPair(GetName(), this));
      53          16 :     UpdateIpam(node);
      54          16 : }
      55             : 
      56          16 : VnniConfig::~VnniConfig() {
      57          16 :     vnni_config_.erase(name_);
      58          16 : }
      59             : 
      60          16 : void VnniConfig::OnAdd(IFMapNode *node) {
      61          16 :     MarkValid();
      62          16 :     FindSubnets(node, subnets_);
      63          16 :     if (!ipam_) {
      64           0 :         UpdateIpam(node);
      65             :     }
      66          16 :     if (ipam_ && ipam_->IsValid() && ipam_->GetVirtualDns()) {
      67           5 :         Subnets subnets;
      68           5 :         NotifySubnets(subnets, subnets_, ipam_->GetVirtualDns());
      69           5 :         ipam_->GetVirtualDns()->NotifyPendingDnsRecords();
      70           5 :     }
      71          16 : }
      72             : 
      73          16 : void VnniConfig::OnDelete() {
      74          16 :     MarkDelete();
      75          16 :     if (ipam_) {
      76           7 :         if (ipam_->IsValid() && ipam_->GetVirtualDns()) {
      77          18 :             for (unsigned int i = 0; i < subnets_.size(); i++) {
      78          11 :                 VdnsZoneCallback(subnets_[i], ipam_->GetVirtualDns(),
      79             :                                  DnsConfig::CFG_DELETE);
      80             :             }
      81           7 :             ipam_->GetVirtualDns()->NotifyPendingDnsRecords();
      82             :         }
      83           7 :         ipam_->DelVnni(this);
      84             :     }
      85          16 : }
      86             : 
      87          14 : void VnniConfig::OnChange(IFMapNode *node) {
      88          14 :     Subnets old_subnets;
      89          14 :     subnets_.swap(old_subnets);
      90          14 :     FindSubnets(node, subnets_);
      91          14 :     if (!ipam_) {
      92           0 :         UpdateIpam(node);
      93             :     }
      94          28 :     if (ipam_ && ipam_->IsValid() && ipam_->GetVirtualDns() &&
      95          14 :         NotifySubnets(old_subnets, subnets_, ipam_->GetVirtualDns())) {
      96           6 :             ipam_->GetVirtualDns()->NotifyPendingDnsRecords();
      97             :     }
      98          14 : }
      99             : 
     100          16 : void VnniConfig::UpdateIpam(IFMapNode *node) {
     101          16 :     if (node) {
     102          16 :         IFMapNode *ipam_node = Dns::GetDnsConfigManager()->FindTarget(node,
     103             :                                "virtual-network-network-ipam", "network-ipam");
     104          16 :         if (ipam_node == NULL) {
     105           0 :             DNS_TRACE(DnsError, "VirtualNetworkNetworkIpam <" + GetName() +
     106             :                                 "> does not have Ipam link");
     107           0 :             return;
     108             :         }
     109          16 :         ipam_ = IpamConfig::Find(ipam_node->name());
     110          16 :         if (!ipam_) {
     111           0 :             ipam_ = new IpamConfig(ipam_node);
     112             :         }
     113          16 :         ipam_->AddVnni(this);
     114             :     }
     115             : }
     116             : 
     117          30 : void VnniConfig::FindSubnets(IFMapNode *node, Subnets &subnets) {
     118          30 :     if (!node || node->IsDeleted())
     119           0 :         return;
     120             : 
     121             :     autogen::VirtualNetworkNetworkIpam *vnni =
     122          30 :         static_cast<autogen::VirtualNetworkNetworkIpam *> (node->GetObject());
     123          30 :     if (!vnni)
     124           0 :         return;
     125             : 
     126          30 :     const autogen::VnSubnetsType &subnets_type = vnni->data();
     127          73 :     for (unsigned int i = 0; i < subnets_type.ipam_subnets.size(); ++i) {
     128          86 :         Subnet subnet(subnets_type.ipam_subnets[i].subnet.ip_prefix,
     129          43 :                subnets_type.ipam_subnets[i].subnet.ip_prefix_len);
     130          43 :         subnets.push_back(subnet);
     131             :     }
     132          30 :     std::sort(subnets.begin(), subnets.end());
     133             : }
     134             : 
     135          19 : bool VnniConfig::NotifySubnets(Subnets &old_nets, Subnets &new_nets,
     136             :                          VirtualDnsConfig *vdns) {
     137          19 :     bool change = false;
     138          19 :     Subnets::iterator it_old = old_nets.begin();
     139          19 :     Subnets::iterator it_new = new_nets.begin();
     140          39 :     while (it_old != old_nets.end() && it_new != new_nets.end()) {
     141          20 :         if (*it_old < *it_new) {
     142             :             // old entry is deleted
     143           2 :             it_old->MarkDelete();
     144           2 :             VdnsZoneCallback(*it_old, vdns, DnsConfig::CFG_DELETE);
     145           2 :             change = true;
     146           2 :             it_old++;
     147          18 :         } else if (*it_new < *it_old) {
     148             :             // new entry
     149           0 :             VdnsZoneCallback(*it_new, vdns, DnsConfig::CFG_ADD);
     150           0 :             change = true;
     151           0 :             it_new++;
     152             :         } else {
     153             :             // no change in entry
     154          18 :             it_old++;
     155          18 :             it_new++;
     156             :         }
     157             :     }
     158             : 
     159             :     // delete remaining old entries
     160          21 :     for (; it_old != old_nets.end(); ++it_old) {
     161           2 :         it_old->MarkDelete();
     162           2 :         VdnsZoneCallback(*it_old, vdns, DnsConfig::CFG_DELETE);
     163           2 :         change = true;
     164             :     }
     165             : 
     166             :     // add remaining new entries
     167          28 :     for (; it_new != new_nets.end(); ++it_new) {
     168           9 :         VdnsZoneCallback(*it_new, vdns, DnsConfig::CFG_ADD);
     169           9 :         change = true;
     170             :     }
     171             : 
     172          19 :     return change;
     173             : }
     174             : 
     175          46 : VnniConfig *VnniConfig::Find(std::string name) {
     176          46 :     if (name.empty())
     177           0 :         return NULL;
     178          46 :     DataMap::iterator iter = vnni_config_.find(name);
     179          46 :     if (iter != vnni_config_.end())
     180          30 :         return iter->second;
     181          16 :     return NULL;
     182             : }
     183             : 
     184             : ////////////////////////////////////////////////////////////////////////////////
     185             : 
     186           9 : IpamConfig::IpamConfig(IFMapNode *node)
     187           9 :     : DnsConfig(node->name()), virtual_dns_(NULL) {
     188           9 :     GetObject(node, rec_);
     189           9 :     ipam_config_.insert(DataPair(GetName(), this));
     190           9 : }
     191             : 
     192           9 : IpamConfig::~IpamConfig() {
     193           9 :     for (VnniList::iterator it = vnni_list_.begin();
     194          18 :          it != vnni_list_.end(); ++it) {
     195           9 :         (*it)->ipam_ = NULL;
     196             :     }
     197           9 :     ipam_config_.erase(name_);
     198           9 : }
     199             : 
     200           9 : void IpamConfig::OnAdd(IFMapNode *node) {
     201           9 :     MarkValid();
     202           9 :     GetObject(node, rec_);
     203           9 :     Add(VirtualDnsConfig::Find(GetVirtualDnsName()));
     204           9 :     if (GetVirtualDns())
     205           0 :         GetVirtualDns()->NotifyPendingDnsRecords();
     206           9 : }
     207             : 
     208           9 : void IpamConfig::OnDelete() {
     209           9 :     Delete();
     210           9 :     if (GetVirtualDns())
     211           6 :         GetVirtualDns()->NotifyPendingDnsRecords();
     212           9 : }
     213             : 
     214          18 : void IpamConfig::OnChange(IFMapNode *node) {
     215          18 :     autogen::IpamType new_rec;
     216          18 :     GetObject(node, new_rec);
     217          18 :     if (new_rec.ipam_dns_server.virtual_dns_server_name != GetVirtualDnsName()) {
     218           5 :         Delete();
     219           5 :         if (GetVirtualDns())
     220           5 :             GetVirtualDns()->NotifyPendingDnsRecords();
     221           5 :         ClearDelete();
     222           5 :         rec_ = new_rec;
     223           5 :         Add(VirtualDnsConfig::Find(GetVirtualDnsName()));
     224           5 :         if (GetVirtualDns())
     225           2 :             GetVirtualDns()->NotifyPendingDnsRecords();
     226             :     } else
     227          13 :         rec_ = new_rec;
     228          18 : }
     229             : 
     230          14 : void IpamConfig::Add(VirtualDnsConfig *vdns) {
     231          14 :     virtual_dns_ = vdns;
     232          14 :     if (virtual_dns_) {
     233           2 :         virtual_dns_->AddIpam(this);
     234           2 :         Notify(DnsConfig::CFG_ADD);
     235             :     }
     236          14 : }
     237             : 
     238          14 : void IpamConfig::Delete() {
     239          14 :     MarkDelete();
     240          14 :     if (virtual_dns_) {
     241          11 :         Notify(DnsConfig::CFG_DELETE);
     242          11 :         virtual_dns_->DelIpam(this);
     243             :     }
     244          14 : }
     245             : 
     246          13 : void IpamConfig::Notify(DnsConfigEvent ev) {
     247          13 :     for (IpamConfig::VnniList::iterator it = vnni_list_.begin();
     248          30 :          it != vnni_list_.end(); ++it) {
     249          17 :         Subnets &subnets = (*it)->GetSubnets();
     250          35 :         for (unsigned int i = 0; i < subnets.size(); i++) {
     251          18 :             VdnsZoneCallback(subnets[i], virtual_dns_, ev);
     252             :         }
     253             :     }
     254          13 : }
     255             : 
     256          36 : bool IpamConfig::GetObject(IFMapNode *node, autogen::IpamType &data) {
     257          36 :     if (!node)
     258           0 :         return false;
     259             : 
     260             :     autogen::NetworkIpam *ipam =
     261          36 :         static_cast<autogen::NetworkIpam *>(node->GetObject());
     262          36 :     if (!ipam)
     263           3 :         return false;
     264             : 
     265          33 :     data = ipam->mgmt();
     266          33 :     return true;
     267             : }
     268             : 
     269           0 : void IpamConfig::Trace(const std::string &ev) {
     270           0 :     DNS_TRACE(IpamTrace, name_, GetVirtualDnsName(), ev);
     271           0 : }
     272             : 
     273          52 : IpamConfig *IpamConfig::Find(std::string name) {
     274          52 :     if (name.empty())
     275           0 :         return NULL;
     276          52 :     DataMap::iterator iter = ipam_config_.find(name);
     277          52 :     if (iter != ipam_config_.end())
     278          43 :         return iter->second;
     279           9 :     return NULL;
     280             : }
     281             : 
     282          11 : void IpamConfig::AssociateIpamVdns(VirtualDnsConfig *vdns) {
     283          11 :     for (DataMap::iterator iter = ipam_config_.begin();
     284          38 :          iter != ipam_config_.end(); ++iter) {
     285          27 :         IpamConfig *ipam = iter->second;
     286          42 :         if (!ipam->GetVirtualDns() &&
     287          15 :             ipam->GetVirtualDnsName() == vdns->GetName()) {
     288           9 :             ipam->virtual_dns_ = vdns;
     289           9 :             vdns->AddIpam(ipam);
     290             :         }
     291             :     }
     292          11 : }
     293             : 
     294             : ////////////////////////////////////////////////////////////////////////////////
     295             : 
     296          11 : VirtualDnsConfig::VirtualDnsConfig(IFMapNode *node) : DnsConfig(node->name()) {
     297          11 :     GetObject(node, rec_);
     298          11 :     old_rec_ = rec_;
     299          11 :     virt_dns_config_.insert(DataPair(GetName(), this));
     300          11 : }
     301             : 
     302           0 : VirtualDnsConfig::VirtualDnsConfig(const std::string &name) : DnsConfig(name) {
     303           0 :     rec_.external_visible = false;
     304           0 :     rec_.reverse_resolution = false;
     305           0 :     old_rec_ = rec_;
     306           0 :     virt_dns_config_.insert(DataPair(GetName(), this));
     307           0 : }
     308             : 
     309          11 : VirtualDnsConfig::~VirtualDnsConfig() {
     310          11 :     virt_dns_config_.erase(name_);
     311          11 : }
     312             : 
     313          11 : void VirtualDnsConfig::OnAdd(IFMapNode *node) {
     314          11 :     if (!GetObject(node, rec_) || GetDomainName().empty())
     315           0 :         return;
     316          11 :     MarkValid();
     317             :     // Update any ipam configs dependent on this virtual dns
     318          11 :     IpamConfig::AssociateIpamVdns(this);
     319             :     // Update any records dependent on this virtual dns
     320          11 :     VirtualDnsRecordConfig::UpdateVirtualDns(this);
     321          11 :     VdnsCallback(this, DnsConfig::CFG_ADD);
     322          11 :     old_rec_ = rec_;
     323             :     // No notification for subnets is required here as the config was
     324             :     // available in the above notify
     325          11 :     NotifyPendingDnsRecords();
     326          11 :     Trace("Add");
     327             : }
     328             : 
     329          11 : void VirtualDnsConfig::OnDelete() {
     330          11 :     Trace("Delete");
     331          11 :     MarkDelete();
     332          11 :     VdnsCallback(this, DnsConfig::CFG_DELETE);
     333          11 :     for (VirtualDnsConfig::IpamList::iterator iter = ipams_.begin();
     334          11 :          iter != ipams_.end(); ++iter) {
     335           0 :         (*iter)->virtual_dns_ = NULL;
     336             :     }
     337          11 :     for (VirtualDnsConfig::VDnsRec::iterator it =
     338          11 :          virtual_dns_records_.begin();
     339          15 :          it != virtual_dns_records_.end(); ++it) {
     340           4 :         (*it)->virt_dns_ = NULL;
     341           4 :         (*it)->ClearNotified();
     342             :     }
     343          11 :     NotifyPendingDnsRecords();
     344          11 : }
     345             : 
     346           8 : void VirtualDnsConfig::OnChange(IFMapNode *node) {
     347           8 :     Trace("Change");
     348           8 :     if (!GetObject(node, rec_) || !HasChanged())
     349           0 :         return;
     350             : 
     351           8 :     bool notify = false;
     352           8 :     if (!IsValid()) {
     353           0 :         MarkValid();
     354             :         // Update any ipam configs dependent on this virtual dns
     355           0 :         IpamConfig::AssociateIpamVdns(this);
     356             :         // Update any records dependent on this virtual dns
     357           0 :         VirtualDnsRecordConfig::UpdateVirtualDns(this);
     358           0 :         notify = true;
     359             :     }
     360             : 
     361           8 :     VdnsCallback(this, DnsConfig::CFG_CHANGE);
     362           8 :     old_rec_ = rec_;
     363           8 :     if (notify) NotifyPendingDnsRecords();
     364             : }
     365             : 
     366          47 : void VirtualDnsConfig::AddRecord(VirtualDnsRecordConfig *record) {
     367          47 :     virtual_dns_records_.insert(record);
     368          47 : }
     369             : 
     370          19 : void VirtualDnsConfig::DelRecord(VirtualDnsRecordConfig *record) {
     371          19 :     virtual_dns_records_.erase(record);
     372          19 : }
     373             : 
     374          30 : bool VirtualDnsConfig::GetObject(IFMapNode *node,
     375             :                                  autogen::VirtualDnsType &data) {
     376          30 :     if (!node)
     377           0 :         return false;
     378             : 
     379             :     autogen::VirtualDns *dns =
     380          30 :         static_cast<autogen::VirtualDns *>(node->GetObject());
     381             :     // if (!dns || !dns->IsPropertySet(autogen::VirtualDns::ID_PERMS))
     382          30 :     if (!dns)
     383           0 :         return false;
     384             : 
     385          30 :     data = dns->data();
     386          30 :     return true;
     387             : }
     388             : 
     389          14 : bool VirtualDnsConfig::GetSubnet(const IpAddress &addr, Subnet &subnet) const {
     390          14 :     for (IpamList::iterator ipam_iter = ipams_.begin();
     391          14 :          ipam_iter != ipams_.end(); ++ipam_iter) {
     392          12 :         IpamConfig *ipam = *ipam_iter;
     393          12 :         const IpamConfig::VnniList &vnni = ipam->GetVnniList();
     394          12 :         for (IpamConfig::VnniList::iterator vnni_it = vnni.begin();
     395          16 :              vnni_it != vnni.end(); ++vnni_it) {
     396          16 :             Subnets &subnets = (*vnni_it)->GetSubnets();
     397          24 :             for (unsigned int i = 0; i < subnets.size(); i++) {
     398          20 :                 if (subnets[i].Contains(addr)) {
     399          12 :                     subnet = subnets[i];
     400          12 :                     return true;
     401             :                 }
     402             :             }
     403             :         }
     404             :     }
     405           2 :     return false;
     406             : }
     407             : 
     408          53 : void VirtualDnsConfig::NotifyPendingDnsRecords() {
     409          53 :     for (VirtualDnsConfig::VDnsRec::iterator it = virtual_dns_records_.begin();
     410         131 :          it != virtual_dns_records_.end(); ++it) {
     411          78 :         VirtualDnsRecordConfig *rec = *it;
     412          78 :         if (rec->CanNotify()) {
     413          72 :             if (!rec->IsNotified()) {
     414          18 :                 VdnsRecordCallback(rec, DnsConfig::CFG_ADD);
     415             :             }
     416             :         } else {
     417           6 :             rec->ClearNotified();
     418             :         }
     419             :     }
     420          53 : }
     421             : 
     422           8 : bool VirtualDnsConfig::HasChanged() {
     423           8 :     if (rec_.domain_name == old_rec_.domain_name &&
     424          16 :         rec_.dynamic_records_from_client == old_rec_.dynamic_records_from_client &&
     425           8 :         rec_.record_order == old_rec_.record_order &&
     426          16 :         rec_.default_ttl_seconds == old_rec_.default_ttl_seconds &&
     427           8 :         rec_.next_virtual_DNS == old_rec_.next_virtual_DNS &&
     428           8 :         rec_.external_visible == old_rec_.external_visible &&
     429          16 :         rec_.reverse_resolution == old_rec_.reverse_resolution &&
     430           0 :         rec_.soa_record.negative_cache_ttl_seconds == old_rec_.soa_record.negative_cache_ttl_seconds)
     431           0 :         return false;
     432           8 :     return true;
     433             : }
     434             : 
     435          30 : void VirtualDnsConfig::VirtualDnsTrace(VirtualDnsTraceData &rec) {
     436          30 :     rec.name = name_;
     437          30 :     rec.dns_name = rec_.domain_name;
     438          30 :     rec.dns_dyn_rec = rec_.dynamic_records_from_client;
     439          30 :     rec.dns_order = rec_.record_order;
     440          30 :     rec.dns_ttl = rec_.default_ttl_seconds;
     441          30 :     rec.dns_next = rec_.next_virtual_DNS;
     442          30 :     rec.installed = (IsNotified() ? "true" : "false");
     443          30 :     rec.floating_ip_record = rec_.floating_ip_record;
     444          30 :     rec.external_visible = (rec_.external_visible ? "yes" : "no");
     445          30 :     rec.reverse_resolution = (rec_.reverse_resolution ? "yes" : "no");
     446          30 :     rec.flags = flags_;
     447          30 :     rec.negative_cache_ttl_seconds = rec_.soa_record.negative_cache_ttl_seconds;
     448          30 : }
     449             : 
     450          30 : void VirtualDnsConfig::Trace(const std::string &ev) {
     451          30 :     VirtualDnsTraceData rec;
     452          30 :     VirtualDnsTrace(rec);
     453          30 :     DNS_TRACE(VirtualDnsTrace, ev, rec);
     454          30 : }
     455             : 
     456         721 : std::string VirtualDnsConfig::GetViewName() const {
     457         721 :     std::string name(GetName());
     458         721 :     BindUtil::RemoveSpecialChars(name);
     459         721 :     return name;
     460           0 : }
     461             : 
     462         193 : std::string VirtualDnsConfig::GetNextDns() const {
     463         193 :     std::string name(rec_.next_virtual_DNS);
     464         193 :     BindUtil::RemoveSpecialChars(name);
     465         193 :     return name;
     466           0 : }
     467             : 
     468           0 : bool VirtualDnsConfig::DynamicUpdatesEnabled() const {
     469           0 :     return rec_.dynamic_records_from_client;
     470             : }
     471             : 
     472          67 : VirtualDnsConfig *VirtualDnsConfig::Find(std::string name) {
     473          67 :     if (name.empty())
     474           3 :         return NULL;
     475          64 :     DataMap::iterator iter = virt_dns_config_.find(name);
     476          64 :     if (iter != virt_dns_config_.end())
     477          44 :         return iter->second;
     478          20 :     return NULL;
     479             : }
     480             : 
     481             : ////////////////////////////////////////////////////////////////////////////////
     482             : 
     483          23 : VirtualDnsRecordConfig::VirtualDnsRecordConfig(IFMapNode *node)
     484          23 :       : DnsConfig(node->name()), virt_dns_(NULL), src_(VirtualDnsRecordConfig::Config) {
     485          23 :     GetObject(node, rec_);
     486          23 :     virt_dns_rec_config_.insert(DataPair(GetName(), this));
     487          23 :     UpdateVdns(node);
     488          23 : }
     489             : 
     490           0 : VirtualDnsRecordConfig::VirtualDnsRecordConfig(const std::string &name,
     491             :                                                const std::string &vdns_name,
     492           0 :                                                const DnsItem &item)
     493           0 :       : DnsConfig(name), rec_(item), virt_dns_(NULL),
     494           0 :         src_(VirtualDnsRecordConfig::Agent) {
     495           0 :     virt_dns_rec_config_.insert(DataPair(GetName(), this));
     496           0 :     virt_dns_ = VirtualDnsConfig::Find(vdns_name);
     497           0 :     if (!virt_dns_) {
     498           0 :         virt_dns_ = new VirtualDnsConfig(vdns_name);
     499           0 :         virt_dns_->AddRecord(this);
     500             :     }
     501           0 :     virtual_dns_name_ = virt_dns_->GetName();
     502           0 : }
     503             : 
     504          23 : VirtualDnsRecordConfig::~VirtualDnsRecordConfig() {
     505          23 :     virt_dns_rec_config_.erase(name_);
     506          23 : }
     507             : 
     508          24 : void VirtualDnsRecordConfig::OnAdd(IFMapNode *node) {
     509          24 :     MarkValid();
     510          24 :     if (!virt_dns_) {
     511           0 :         if (!UpdateVdns(node)) {
     512           0 :             ClearValid();
     513             :         }
     514          24 :     } else if (!virt_dns_->IsValid()) {
     515          18 :         virt_dns_->AddRecord(this);
     516             :     } else {
     517           6 :         virt_dns_->AddRecord(this);
     518           6 :         if (CanNotify()) {
     519           6 :             VdnsRecordCallback(this, DnsConfig::CFG_ADD);
     520             :         }
     521             :     }
     522          24 :     Trace("Add");
     523          24 : }
     524             : 
     525          23 : void VirtualDnsRecordConfig::OnDelete() {
     526          23 :     Trace("Delete");
     527          23 :     MarkDelete();
     528          23 :     if (virt_dns_) {
     529          19 :         if (IsNotified()) {
     530          19 :             VdnsRecordCallback(this, DnsConfig::CFG_DELETE);
     531             :         }
     532          19 :         virt_dns_->DelRecord(this);
     533             :     }
     534          23 : }
     535             : 
     536          19 : void VirtualDnsRecordConfig::OnChange(IFMapNode *node) {
     537          19 :     DnsItem new_rec;
     538          57 :     if (!GetObject(node, new_rec) ||
     539          38 :         (IsValid() && !HasChanged(new_rec))) {
     540          19 :         return;
     541             :     }
     542           0 :     if (!virt_dns_) {
     543           0 :         MarkValid();
     544           0 :         if (!UpdateVdns(node)) {
     545           0 :             ClearValid();
     546             :         }
     547             :     }
     548             :     // For records, notify a change with a delete of the old record
     549             :     // followed by addition of new record; If only TTL has changed,
     550             :     // do not delete, as the order of delete and add processing is
     551             :     // not controlled and we might end up with deleted record
     552           0 :     if (IsNotified() && !OnlyTtlChange(new_rec)) {
     553           0 :         VdnsRecordCallback(this, DnsConfig::CFG_DELETE);
     554             :     }
     555           0 :     OnChange(new_rec);
     556          19 : }
     557             : 
     558           0 : void VirtualDnsRecordConfig::OnChange(const DnsItem &new_rec) {
     559           0 :     rec_ = new_rec;
     560           0 :     if (CanNotify()) {
     561           0 :         VdnsRecordCallback(this, DnsConfig::CFG_ADD);
     562             :     }
     563           0 :     Trace("Change");
     564           0 : }
     565             : 
     566          23 : bool VirtualDnsRecordConfig::UpdateVdns(IFMapNode *node) {
     567          23 :     if (!node) {
     568           0 :         return false;
     569             :     }
     570             : 
     571          23 :     IFMapNode *vdns_node = Dns::GetDnsConfigManager()->FindTarget(node,
     572             :                            "virtual-DNS-virtual-DNS-record");
     573          23 :     if (vdns_node == NULL) {
     574           0 :         DNS_TRACE(DnsError, "Virtual DNS Record <" + GetName() +
     575             :                             "> does not have virtual DNS link");
     576           0 :         return false;
     577             :     }
     578          23 :     virt_dns_ = VirtualDnsConfig::Find(vdns_node->name());
     579          23 :     if (!virt_dns_) {
     580           8 :         virt_dns_ = new VirtualDnsConfig(vdns_node);
     581             :     }
     582          23 :     virt_dns_->AddRecord(this);
     583          23 :     virtual_dns_name_ = virt_dns_->GetName();
     584          23 :     return true;
     585             : }
     586             : 
     587          84 : bool VirtualDnsRecordConfig::CanNotify() {
     588          84 :     if (!IsValid() || !virt_dns_ || !virt_dns_->IsValid())
     589           4 :         return false;
     590             : 
     591          80 :     if (rec_.eclass == DNS_CLASS_IN && rec_.type == DNS_PTR_RECORD) {
     592           9 :         if (!virt_dns_->IsReverseResolutionEnabled()) {
     593           0 :             return false;
     594             :         }
     595           9 :         IpAddress addr;
     596          17 :         if (BindUtil::IsIP(rec_.name, addr) ||
     597           8 :             BindUtil::GetAddrFromPtrName(rec_.name, addr)) {
     598           9 :             Subnet net;
     599           9 :             return virt_dns_->GetSubnet(addr, net);
     600             :         }
     601           0 :         if (!IsErrorLogged()) {
     602           0 :             DNS_CONFIGURATION_LOG(
     603             :              g_vns_constants.CategoryNames.find(Category::DNSAGENT)->second,
     604             :              SandeshLevel::SYS_ERR, "Invalid PTR Name",
     605             :              GetName(), rec_.name);
     606           0 :             MarkErrorLogged();
     607             :         }
     608           0 :         return false;
     609             :     }
     610             : 
     611          71 :     return true;
     612             : }
     613             : 
     614          19 : bool VirtualDnsRecordConfig::HasChanged(DnsItem &rhs) {
     615          38 :     if (rec_.name == rhs.name && rec_.type == rhs.type &&
     616          19 :         rec_.eclass == rhs.eclass && rec_.data == rhs.data &&
     617          38 :         rec_.ttl == rhs.ttl && rec_.priority == rhs.priority)
     618          19 :         return false;
     619           0 :     return true;
     620             : }
     621             : 
     622           0 : bool VirtualDnsRecordConfig::OnlyTtlChange(DnsItem &rhs) {
     623           0 :     if (rec_.name == rhs.name && rec_.type == rhs.type &&
     624           0 :         rec_.eclass == rhs.eclass && rec_.data == rhs.data &&
     625           0 :         rec_.ttl != rhs.ttl && rec_.priority == rhs.priority)
     626           0 :         return true;
     627           0 :     return false;
     628             : }
     629             : 
     630          83 : autogen::VirtualDnsType VirtualDnsRecordConfig::GetVDns() const {
     631          83 :     autogen::VirtualDnsType data;
     632          83 :     data.dynamic_records_from_client = false;
     633          83 :     data.default_ttl_seconds = 0;
     634          83 :     data.soa_record.negative_cache_ttl_seconds = 0;
     635          83 :     if (virt_dns_)
     636          83 :         data = virt_dns_->GetVDns();
     637          83 :     return data;
     638           0 : }
     639             : 
     640          88 : std::string VirtualDnsRecordConfig::GetViewName() const {
     641          88 :     if (virt_dns_) {
     642          88 :         return virt_dns_->GetViewName();
     643             :     } else
     644           0 :         return "";
     645             : }
     646             : 
     647          42 : bool VirtualDnsRecordConfig::GetObject(IFMapNode *node, DnsItem &item) {
     648          42 :     if (!node)
     649           0 :         return false;
     650             : 
     651             :     autogen::VirtualDnsRecord *rec =
     652          42 :         static_cast<autogen::VirtualDnsRecord *>(node->GetObject());
     653          42 :     if (!rec)
     654           0 :         return false;
     655             : 
     656          42 :     autogen::VirtualDnsRecordType rec_data = rec->data();
     657          42 :     item.eclass = BindUtil::DnsClass(rec_data.record_class);
     658          42 :     item.type = BindUtil::DnsType(rec_data.record_type);
     659          42 :     item.name = rec_data.record_name;
     660          42 :     item.data = rec_data.record_data;
     661          42 :     item.ttl = rec_data.record_ttl_seconds;
     662          42 :     item.priority = rec_data.record_mx_preference;
     663          42 :     item.source_name = rec_data.record_source_name;
     664          42 :     return true;
     665          42 : }
     666             : 
     667          62 : void VirtualDnsRecordConfig::VirtualDnsRecordTrace(VirtualDnsRecordTraceData &rec) {
     668          62 :     rec.name = name_;
     669          62 :     rec.rec_name = rec_.name;
     670          62 :     rec.rec_type = BindUtil::DnsType(rec_.type);
     671          62 :     if (rec_.eclass == DNS_CLASS_IN)
     672          62 :         rec.rec_class = "IN";
     673          62 :     rec.rec_data = rec_.data;
     674          62 :     rec.rec_ttl = rec_.ttl;
     675          62 :     if (src_ == VirtualDnsRecordConfig::Config)
     676          62 :         rec.source = "Config";
     677             :     else
     678           0 :         rec.source = "Agent";
     679          62 :     if (IsNotified())
     680          39 :         rec.installed = "true";
     681             :     else
     682          23 :         rec.installed = "false";
     683          62 :     rec.flags = flags_;
     684          62 :     rec.rec_source_name = rec_.source_name;
     685          62 :     rec.rec_vm_uuid = rec_.vm_uuid;
     686          62 : }
     687             : 
     688          47 : void VirtualDnsRecordConfig::Trace(const std::string &ev) {
     689          47 :     VirtualDnsRecordTraceData rec;
     690          47 :     VirtualDnsRecordTrace(rec);
     691          47 :     std::string dns_name;
     692          47 :     if (virt_dns_)
     693          43 :         dns_name = virt_dns_->name_;
     694          47 :     DNS_TRACE(VirtualDnsRecordTrace, ev, dns_name, rec);
     695          47 : }
     696             : 
     697          67 : VirtualDnsRecordConfig *VirtualDnsRecordConfig::Find(std::string name) {
     698          67 :     if (name.empty())
     699           0 :         return NULL;
     700          67 :     DataMap::iterator iter = virt_dns_rec_config_.find(name);
     701          67 :     if (iter != virt_dns_rec_config_.end())
     702          44 :         return iter->second;
     703          23 :     return NULL;
     704             : }
     705             : 
     706             : // Check virtual dns records having empty VDNS to see if they belong to
     707             : // the vdns being added now; update the reference accordingly
     708          11 : void VirtualDnsRecordConfig::UpdateVirtualDns(VirtualDnsConfig *vdns) {
     709          11 :     for (DataMap::iterator it = virt_dns_rec_config_.begin();
     710          77 :          it != virt_dns_rec_config_.end(); ++it) {
     711          66 :         if (!it->second || it->second->GetVirtualDns()) continue;
     712           0 :         if (it->second->virtual_dns_name_ == vdns->GetName()) {
     713           0 :             it->second->virt_dns_ = vdns;
     714           0 :             vdns->AddRecord(it->second);
     715             :         }
     716             :     }
     717          11 : }
     718             : 
     719           0 : GlobalQosConfig::GlobalQosConfig(IFMapNode *node)
     720           0 :     : DnsConfig(node->name()) {
     721           0 :     assert(singleton_ == NULL);
     722           0 :     singleton_ = this;
     723           0 : }
     724             : 
     725           0 : GlobalQosConfig::~GlobalQosConfig() {
     726           0 :     singleton_ = NULL;
     727           0 : }
     728             : 
     729           0 : GlobalQosConfig* GlobalQosConfig::Find(const string &name) {
     730           0 :     return singleton_;
     731             : }
     732             : 
     733           0 : void GlobalQosConfig::SetDscp() {
     734           0 :     XmppServer *server = Dns::GetXmppServer();
     735           0 :     if (server) {
     736           0 :         server->SetDscpValue(control_dscp_);
     737             :     }
     738           0 : }
     739             : 
     740           0 : void GlobalQosConfig::OnAdd(IFMapNode *node) {
     741           0 :     MarkValid();
     742             :     autogen::GlobalQosConfig *qos =
     743           0 :         static_cast<autogen::GlobalQosConfig *>(node->GetObject());
     744           0 :     if (!qos)
     745           0 :         return;
     746           0 :     const autogen::ControlTrafficDscpType &dscp = qos->control_traffic_dscp();
     747           0 :     if (control_dscp_ != dscp.control) {
     748           0 :         control_dscp_ = dscp.control;
     749           0 :         Sandesh::SetDscpValue(dscp.control);
     750           0 :         SetDscp();
     751             :     }
     752           0 :     if (analytics_dscp_ != dscp.analytics) {
     753           0 :         analytics_dscp_ = dscp.analytics;
     754             :     }
     755             : }
     756             : 
     757           0 : void GlobalQosConfig::OnDelete() {
     758           0 :     if (control_dscp_ != 0) {
     759           0 :         control_dscp_ = 0;
     760           0 :         SetDscp();
     761             :     }
     762           0 :     analytics_dscp_ = 0;
     763           0 : }
     764             : 
     765           0 : void GlobalQosConfig::OnChange(IFMapNode *node) {
     766           0 :     OnAdd(node);
     767           0 : }
     768             : 
     769             : ////////////////////////////////////////////////////////////////////////////////

Generated by: LCOV version 1.14