OpenSDN source code
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
acl.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2013 Juniper Networks, Inc. All rights reserved.
3  */
4 
5 #include <vector>
6 #include <boost/uuid/uuid_io.hpp>
7 
8 #include <base/parse_object.h>
9 #include <ifmap/ifmap_link.h>
10 #include <ifmap/ifmap_table.h>
11 #include <base/logging.h>
12 #include <base/address_util.h>
13 
14 #include <cmn/agent_cmn.h>
15 #include <vnc_cfg_types.h>
16 #include <agent_types.h>
17 
18 #include <cfg/cfg_init.h>
19 
20 #include <filter/traffic_action.h>
21 #include <filter/acl_entry_match.h>
22 #include <filter/acl_entry_spec.h>
23 #include <filter/acl_entry.h>
24 
25 #include <filter/acl.h>
26 #include <cmn/agent_cmn.h>
27 #include <oper/vn.h>
28 #include <oper/sg.h>
29 #include <oper/vrf.h>
30 #include <oper/agent_sandesh.h>
31 #include <oper/nexthop.h>
32 #include <oper/mirror_table.h>
33 #include <oper/qos_config.h>
34 #include <oper/config_manager.h>
35 
37 
38 using namespace autogen;
39 
41 
42 FlowPolicyInfo::FlowPolicyInfo(const std::string &u)
43  : uuid(u), drop(false), terminal(false), other(false),
44  src_match_vn(), dst_match_vn(), acl_name() {
45 }
46 
47 bool AclDBEntry::IsLess(const DBEntry &rhs) const {
48  const AclDBEntry &a = static_cast<const AclDBEntry &>(rhs);
49  return (uuid_ < a.uuid_);
50 }
51 
52 std::string AclDBEntry::ToString() const {
53  std::string str = "ACL DB Entry:";
54  str.insert(str.end(), name_.begin(), name_.end());
55  return str;
56 }
57 
59  AclKey *key = new AclKey(uuid_);
60  return DBEntryBase::KeyPtr(key);
61 }
62 
63 void AclDBEntry::SetKey(const DBRequestKey *key) {
64  const AclKey *k = static_cast<const AclKey *>(key);
65  uuid_ = k->uuid_;
66 }
67 
68 bool AclDBEntry::DBEntrySandesh(Sandesh *sresp, std::string &uuid) const {
69  AclResp *resp = static_cast<AclResp *>(sresp);
70 
71  std::string str_uuid = UuidToString(GetUuid());
72 
73  // request uuid is null, then display upto size given by sandesh req
74  // request uuid is not null, then disply the ACL that matches the uuid.
75  if ((uuid.empty()) || (str_uuid == uuid)) {
76  AclSandeshData data;
77  SetAclSandeshData(data);
78  std::vector<AclSandeshData> &list =
79  const_cast<std::vector<AclSandeshData>&>(resp->get_acl_list());
80  data.uuid = UuidToString(GetUuid());
81  data.set_dynamic_acl(GetDynamicAcl());
82  data.name = name_;
83  list.push_back(data);
84  return true;
85  }
86  return false;
87 }
88 
89 void AclDBEntry::SetAclSandeshData(AclSandeshData &data) const {
90  AclEntries::const_iterator iter;
91  for (iter = acl_entries_.begin();
92  iter != acl_entries_.end(); ++iter) {
93  AclEntrySandeshData acl_entry_sdata;
94  // Get ACL entry oper data and add it to the list
95  iter->SetAclEntrySandeshData(acl_entry_sdata);
96  data.entries.push_back(acl_entry_sdata);
97  }
98  return;
99 }
100 
101 std::unique_ptr<DBEntry> AclTable::AllocEntry(const DBRequestKey *k) const {
102  const AclKey *key = static_cast<const AclKey *>(k);
103  AclDBEntry *acl = new AclDBEntry(key->uuid_);
104  return std::unique_ptr<DBEntry>(static_cast<DBEntry *>(acl));
105 }
106 
108  AclKey *key = static_cast<AclKey *>(req->key.get());
109  AclData *data = static_cast<AclData *>(req->data.get());
110  AclDBEntry *acl = new AclDBEntry(key->uuid_);
111  acl->SetName(data->cfg_name_);
112  acl->SetDynamicAcl(data->acl_spec_.dynamic_acl);
113  std::vector<AclEntrySpec>::iterator it;
114  std::vector<AclEntrySpec> *acl_spec_ptr = &(data->acl_spec_.acl_entry_specs_);
115  for (it = acl_spec_ptr->begin(); it != acl_spec_ptr->end();
116  ++it) {
117  acl->AddAclEntry(*it, acl->acl_entries_);
118  }
119 
120  AclSandeshData sandesh_data;
121  acl->SetAclSandeshData(sandesh_data);
122  ACL_TRACE(AclTrace, "Add", UuidToString(acl->uuid_), sandesh_data);
123 
124  return acl;
125 }
126 
127 bool AclTable::OperDBOnChange(DBEntry *entry, const DBRequest *req) {
128  bool changed = false;
129  AclDBEntry *acl = static_cast<AclDBEntry *>(entry);
130  AclData *data = dynamic_cast<AclData *>(req->data.get());
131  AclResyncQosConfigData *qos_config_data =
132  dynamic_cast<AclResyncQosConfigData *>(req->data.get());
133 
135 
136  if (qos_config_data != NULL) {
137  changed = acl->ResyncQosConfigEntries();
138  if (acl->IsQosConfigResolved() == false) {
139  AddUnresolvedEntry(acl);
140  }
141  return changed;
142  }
143 
144  if (!data) {
145  return false;
146  }
147 
148  if (data->ace_id_to_del_) {
149  acl->DeleteAclEntry(data->ace_id_to_del_);
150  return true;
151  }
152 
153  AclDBEntry::AclEntries entries;
154  std::vector<AclEntrySpec>::iterator it;
155  std::vector<AclEntrySpec> *acl_spec_ptr = &(data->acl_spec_.acl_entry_specs_);
156  for (it = acl_spec_ptr->begin(); it != acl_spec_ptr->end();
157  ++it) {
158  if (!data->ace_add) { //Replace existing aces
159  acl->AddAclEntry(*it, entries);
160  } else { // Add to the existing entries
161  if (acl->AddAclEntry(*it, acl->acl_entries_)) {
162  changed = true;
163  }
164  }
165  }
166 
167  // Replace the existing aces, ace_add is to add to the existing
168  // entries
169  if (!data->ace_add) {
170  if (acl->Changed(entries)) {
171  //Delete All acl entries for now and set newly created one.
172  acl->DeleteAllAclEntries();
173  acl->SetAclEntries(entries);
174  changed = true;
175  }
176  }
177 
178  if (changed == false) {
179  //Remove temporary create acl entries
180  AclDBEntry::AclEntries::iterator iter;
181  iter = entries.begin();
182  while (iter != entries.end()) {
183  AclEntry *ae = iter.operator->();
184  entries.erase(iter++);
185  delete ae;
186  }
187  }
188 
189  if (acl->IsQosConfigResolved() == false) {
190  AddUnresolvedEntry(acl);
191  }
192 
193  AclSandeshData sandesh_data;
194  acl->SetAclSandeshData(sandesh_data);
195  ACL_TRACE(AclTrace, "Changed", UuidToString(acl->uuid_), sandesh_data);
196  return changed;
197 }
198 
199 bool AclTable::OperDBResync(DBEntry *entry, const DBRequest *req) {
200  return OperDBOnChange(entry, req);
201 }
202 
203 bool AclTable::OperDBDelete(DBEntry *entry, const DBRequest *req) {
204  AclDBEntry *acl = static_cast<AclDBEntry *>(entry);
205  ACL_TRACE(Info, "Delete " + UuidToString(acl->GetUuid()));
207  acl->DeleteAllAclEntries();
208  return true;
209 }
210 
212  ta_map_["deny"] = TrafficAction::DENY;
213  ta_map_["pass"] = TrafficAction::PASS;
214  ta_map_["mirror"] = TrafficAction::MIRROR;
215 }
216 
218 AclTable::ConvertActionString(std::string action_str) const {
219  TrafficActionMap::const_iterator it;
220  it = ta_map_.find(action_str);
221  if (it != ta_map_.end()) {
222  return it->second;
223  } else {
224  return TrafficAction::UNKNOWN;
225  }
226 }
227 
229  unresolved_acl_entries_.insert(entry);
230 }
231 
233  unresolved_acl_entries_.erase(entry);
234 }
235 
237  DBEntryBase *e) {
238  AgentQosConfig *qc = static_cast<AgentQosConfig *>(e);
239  DBState *state = qc->GetState(partition->parent(), qos_config_listener_id_);
240 
241  if (qc->IsDeleted()) {
242  qc->ClearState(partition->parent(), qos_config_listener_id_);
243  delete state;
244  }
245 
246  if (state) {
247  return;
248  }
249 
250  state = new DBState();
251  qc->SetState(partition->parent(), qos_config_listener_id_, state);
252 
253  UnResolvedAclEntries::const_iterator it = unresolved_acl_entries_.begin();
254  for (; it != unresolved_acl_entries_.end(); it++) {
255  DBRequest req;
257 
258  AclKey *key = new AclKey((*it)->GetUuid());
259  key->sub_op_ = AgentKey::RESYNC;
260 
261  req.key.reset(key);
262  req.data.reset(new AclResyncQosConfigData(NULL, NULL));
263  Enqueue(&req);
264  }
265  unresolved_acl_entries_.clear();
266 }
267 
270  boost::bind(&AclTable::Notify, this, _1, _2));
271 
272 }
273 
274 DBTableBase *AclTable::CreateTable(DB *db, const std::string &name) {
275  acl_table_ = new AclTable(db, name);
276  acl_table_->Init();
277  acl_table_->ActionInit();
278  return acl_table_;
279 }
280 
281 static void AclEntryObjectTrace(AclEntrySandeshData &ace_sandesh, AclEntrySpec &ace_spec)
282 {
283  uint32_t id;
284 
285  if (stringToInteger(ace_spec.id.id_, id)) {
286  //XXX ci sanity expects integers
287  //and since we are now comparing string
288  //id are prepended with 0, and verification fails
289  //To be removed once ci scripts would be corrected.
290  ace_sandesh.set_ace_id(integerToString(id));
291  } else {
292  ace_sandesh.set_ace_id(ace_spec.id.id_);
293  }
294  if (ace_spec.terminal) {
295  ace_sandesh.set_rule_type("T");
296  } else {
297  ace_sandesh.set_rule_type("NT");
298  }
299  ace_sandesh.set_uuid(ace_spec.rule_uuid);
300 
301  std::string src;
302  if (ace_spec.src_addr_type == AddressMatch::NETWORK_ID) {
303  src = ace_spec.src_policy_id_str;
304  } else if (ace_spec.src_addr_type == AddressMatch::IP_ADDR) {
306  } else if (ace_spec.src_addr_type == AddressMatch::SG) {
307  src = integerToString(ace_spec.src_sg_id);
308  } else {
309  src = "UnKnown Adresss";
310  }
311  ace_sandesh.set_src(src);
312 
313  std::string dst;
314  if (ace_spec.dst_addr_type == AddressMatch::NETWORK_ID) {
315  dst = ace_spec.dst_policy_id_str;
316  } else if (ace_spec.dst_addr_type == AddressMatch::IP_ADDR) {
318  } else if (ace_spec.dst_addr_type == AddressMatch::SG) {
319  dst = integerToString(ace_spec.dst_sg_id);
320  } else {
321  dst = "UnKnown Adresss";
322  }
323  ace_sandesh.set_dst(dst);
324 
325  std::vector<SandeshRange> sr_l;
326  std::vector<RangeSpec>::iterator it;
327  for (it = ace_spec.protocol.begin(); it != ace_spec.protocol.end(); ++it) {
328  SandeshRange sr;
329  sr.min = (*it).min;
330  sr.max = (*it).max;
331  sr_l.push_back(sr);
332  }
333  ace_sandesh.set_proto_l(sr_l);
334  sr_l.clear();
335 
336  for (it = ace_spec.src_port.begin(); it != ace_spec.src_port.end(); ++it) {
337  SandeshRange sr;
338  sr.min = (*it).min;
339  sr.max = (*it).max;
340  sr_l.push_back(sr);
341  }
342  ace_sandesh.set_src_port_l(sr_l);
343  sr_l.clear();
344 
345  for (it = ace_spec.dst_port.begin(); it != ace_spec.dst_port.end(); ++it) {
346  SandeshRange sr;
347  sr.min = (*it).min;
348  sr.max = (*it).max;
349  sr_l.push_back(sr);
350  }
351  ace_sandesh.set_dst_port_l(sr_l);
352  sr_l.clear();
353 
354  std::vector<ActionStr> astr_l;
355  std::vector<ActionSpec>::iterator action_it;
356  for (action_it = ace_spec.action_l.begin(); action_it != ace_spec.action_l.end();
357  ++ action_it) {
358  ActionSpec action = *action_it;
359  ActionStr astr;
360  if (action.ta_type == TrafficAction::SIMPLE_ACTION) {
361  astr.action = TrafficAction::ActionToString(action.simple_action);
362  } else if (action.ta_type == TrafficAction::LOG_ACTION) {
363  astr.action = TrafficAction::kActionLogStr;
364  } else if (action.ta_type == TrafficAction::ALERT_ACTION) {
365  astr.action = TrafficAction::kActionAlertStr;
366  } else if (action.ta_type == TrafficAction::HBS_ACTION) {
367  astr.action = TrafficAction::kActionHbsStr;
368  } else if (action.ta_type == TrafficAction::MIRROR_ACTION) {
369  astr.action = action.ma.vrf_name + " " +
370  action.ma.analyzer_name + " " +
371  action.ma.ip.to_string() + " " +
372  integerToString(action.ma.port);
373  }
374  if (astr.action.size()) {
375  astr_l.push_back(astr);
376  }
377  }
378  ace_sandesh.set_action_l(astr_l);
379 }
380 
381 static void AclObjectTrace(AgentLogEvent::type event, AclSpec &acl_spec)
382 {
383  AclSandeshData acl;
384  acl.set_uuid(UuidToString(acl_spec.acl_id));
385  acl.set_dynamic_acl(acl_spec.dynamic_acl);
386  if (event == AgentLogEvent::ADD || event == AgentLogEvent::CHANGE) {
387  std::vector<AclEntrySpec>::iterator it;
388  std::vector<AclEntrySandeshData> acl_entries;
389  for (it = acl_spec.acl_entry_specs_.begin();
390  it != acl_spec.acl_entry_specs_.end(); ++it) {
391  AclEntrySandeshData ae_sandesh;
392  AclEntrySpec ae_spec = *it;
393  AclEntryObjectTrace(ae_sandesh, ae_spec);
394  acl_entries.push_back(ae_sandesh);
395  }
396  acl.set_entries(acl_entries);
397  ACL_TRACE(AclTrace, "Add", "", acl);
398  } else if (event == AgentLogEvent::DEL) {
399  ACL_TRACE(AclTrace, "Delete", UuidToString(acl_spec.acl_id), acl);
400  }
401 }
402 
404  AccessControlList *cfg_acl = dynamic_cast <AccessControlList *> (node->GetObject());
405  if (cfg_acl) {
406  autogen::IdPermsType id_perms = cfg_acl->id_perms();
407  CfgUuidSet(id_perms.uuid.uuid_mslong, id_perms.uuid.uuid_lslong, u);
408  }
409 
410  FirewallPolicy *fw_acl =
411  dynamic_cast <FirewallPolicy *> (node->GetObject());
412  if (fw_acl) {
413  autogen::IdPermsType id_perms = fw_acl->id_perms();
414  CfgUuidSet(id_perms.uuid.uuid_mslong, id_perms.uuid.uuid_lslong, u);
415  }
416 
417  return true;
418 }
419 
420 static void AddAceToAcl(AclSpec *acl_spec, const AclTable *acl_table,
421  AccessControlList *cfg_acl,
422  const MatchConditionType *match_condition,
423  const ActionListType action_list,
424  const string rule_uuid, uint32_t id) {
425  // ACE clean up
426  AclEntrySpec ace_spec;
427  std::stringstream stream;
428  stream << std::setfill('0') << std::setw(8) << id;
429  ace_spec.id.id_ = stream.str();
430 
431  if (ace_spec.Populate(match_condition) == false) {
432  return;
433  }
434  // Make default as terminal rule,
435  // all the dynamic acl have non-terminal rules
436  if (cfg_acl->entries().dynamic) {
437  ace_spec.terminal = false;
438  } else {
439  ace_spec.terminal = true;
440  }
441 
442  ace_spec.PopulateAction(acl_table, action_list);
443  ace_spec.rule_uuid = rule_uuid;
444  // Add the Ace to the acl
445  acl_spec->acl_entry_specs_.push_back(ace_spec);
446 
447 
448  // Trace acl entry object
449  AclEntrySandeshData ae_spec;
450  AclEntryObjectTrace(ae_spec, ace_spec);
451  ACL_TRACE(EntryTrace, ae_spec);
452 }
453 
455  IFMapAgentTable *firewall_rule_table =
456  static_cast<IFMapAgentTable *>(node->table());
457  DBGraph *graph = firewall_rule_table->GetGraph();
458 
459  for (DBGraphVertex::adjacency_iterator iter = node->begin(graph);
460  iter != node->end(graph); ++iter) {
461  IFMapNode *service_group_node =
462  static_cast<IFMapNode *>(iter.operator->());
463  if (agent()->config_manager()->SkipNode(service_group_node,
464  agent()->cfg()->cfg_service_group_table())) {
465  continue;
466  }
467 
468  const ServiceGroup *service_group =
469  static_cast<const ServiceGroup*>(service_group_node->GetObject());
470  ace_spec.PopulateServiceGroup(service_group);
471  }
472 }
473 
475  IFMapAgentTable *fp_fr_table =
476  static_cast<IFMapAgentTable *>(node->table());
477  DBGraph *graph = fp_fr_table->GetGraph();
478 
479  for (DBGraphVertex::adjacency_iterator iter = node->begin(graph);
480  iter != node->end(graph); iter++) {
481  IFMapNode *firewall_rule_node =
482  static_cast<IFMapNode *>(iter.operator->());
483 
484  if (agent()->config_manager()->SkipNode(firewall_rule_node,
485  agent()->cfg()->cfg_firewall_rule_table())) {
486  continue;
487  }
488 
489  return firewall_rule_node;
490  }
491 
492  return NULL;
493 }
494 
496  const FirewallRule *rule) {
497  if ((rule->direction().compare("<>") == 0)) {
498  AclEntrySpec implicit_forward_ace_spec(ace_spec);
499  implicit_forward_ace_spec.Reverse(&ace_spec,
501  true, false);
502  acl_spec.acl_entry_specs_.push_back(implicit_forward_ace_spec);
503  }
504 }
505 
507  const boost::uuids::uuid &u,
508  AclSpec &acl_spec) {
509  IFMapAgentTable *firewall_policy_table =
510  static_cast<IFMapAgentTable *>(node->table());
511  DBGraph *graph = firewall_policy_table->GetGraph();
512 
513  for (DBGraphVertex::adjacency_iterator iter = node->begin(graph);
514  iter != node->end(graph); ++iter) {
515  IFMapNode *fp_fr_rule_node =
516  static_cast<IFMapNode *>(iter.operator->());
517  if (agent()->config_manager()->SkipNode(fp_fr_rule_node,
518  agent()->cfg()->cfg_firewall_policy_firewall_rule_table())) {
519  continue;
520  }
521 
522  const FirewallPolicyFirewallRule *fp_fr =
523  static_cast<const FirewallPolicyFirewallRule *>(
524  fp_fr_rule_node->GetObject());
525  if (fp_fr->data().sequence == Agent::NullString()) {
526  continue;
527  }
528  IFMapNode *rule = GetFirewallRule(fp_fr_rule_node);
529  if (rule == NULL) {
530  continue;
531  }
532 
533  const FirewallRule *fw_rule =
534  static_cast<const FirewallRule *>(rule->GetObject());
535  AclEntrySpec ace_spec;
536  ace_spec.Populate(agent(), rule, fw_rule);
537  ace_spec.id.id_ = fp_fr->data().sequence;
538  ace_spec.terminal = true;
539 
540  //Parse thru FW rule to service group and populate service group
541  PopulateServicePort(ace_spec, rule);
542 
543  boost::uuids::uuid rule_uuid;
544  autogen::IdPermsType id_perms = fw_rule->id_perms();
545  CfgUuidSet(id_perms.uuid.uuid_mslong,
546  id_perms.uuid.uuid_lslong, rule_uuid);
547 
548  ace_spec.rule_uuid = UuidToString(rule_uuid);
549  ace_spec.PopulateAction(this, fw_rule->action_list());
550 
551  if ((fw_rule->direction().compare("<") == 0)) {
552  AclEntrySpec rev_ace_spec;
553  rev_ace_spec.Reverse(&ace_spec, AclEntryID::FORWARD,
554  true, false);
555  acl_spec.acl_entry_specs_.push_back(rev_ace_spec);
556  } else {
557  acl_spec.acl_entry_specs_.push_back(ace_spec);
558  if ((fw_rule->direction().compare("<>") == 0)) {
559  AddImplicitRule(acl_spec, ace_spec, fw_rule);
560  }
561  }
562  }
563 }
564 
565 bool AclTable::SubnetTypeEqual(const autogen::SubnetType &lhs,
566  const autogen::SubnetType &rhs) const {
567  if (lhs.ip_prefix.compare(rhs.ip_prefix) != 0)
568  return false;
569  if (lhs.ip_prefix_len != rhs.ip_prefix_len)
570  return false;
571  return true;
572 }
573 
574 bool AclTable::AddressTypeEqual(const autogen::AddressType &lhs,
575  const autogen::AddressType &rhs) const {
576  if (!SubnetTypeEqual(lhs.subnet, rhs.subnet))
577  return false;
578  if (lhs.virtual_network.compare(rhs.virtual_network) != 0)
579  return false;
580  if (lhs.security_group.compare(rhs.security_group) != 0)
581  return false;
582  if (lhs.network_policy.compare(rhs.network_policy) != 0)
583  return false;
584  if (lhs.subnet_list.size() != rhs.subnet_list.size())
585  return false;
586  std::vector<SubnetType>::const_iterator lit = lhs.subnet_list.begin();
587  std::vector<SubnetType>::const_iterator rit = lhs.subnet_list.begin();
588  while ((lit != lhs.subnet_list.end()) &&
589  (rit != rhs.subnet_list.end())) {
590  if (!SubnetTypeEqual(*lit, *rit))
591  return false;
592  ++lit;
593  ++rit;
594  }
595  return true;
596 }
597 
598 bool AclTable::PortTypeEqual(const autogen::PortType &src,
599  const autogen::PortType &dst) const {
600  if ((src.start_port == dst.start_port) &&
601  (src.end_port == dst.end_port)) {
602  return true;
603  }
604  return false;
605 }
606 
608  const boost::uuids::uuid &u,
609  AclSpec &acl_spec) {
610  AccessControlList *cfg_acl =
611  dynamic_cast <AccessControlList *> (node->GetObject());
612  const std::vector<AclRuleType> &entrs = cfg_acl->entries().acl_rule;
613 
614  acl_spec.acl_id = u;
615  acl_spec.dynamic_acl = cfg_acl->entries().dynamic;
616 
617  //AclEntrySpec *ace_spec;
618  std::vector<AclRuleType>::const_iterator ir;
619  uint32_t id = 1;
620  for(ir = entrs.begin(); ir != entrs.end(); ++ir) {
621  AddAceToAcl(&acl_spec, this, cfg_acl, &(ir->match_condition),
622  ir->action_list, ir->rule_uuid, id++);
623  bool address_same = false;
624  if (AddressTypeEqual(ir->match_condition.src_address,
625  ir->match_condition.dst_address)) {
626  address_same = true;
627  }
628 
629  bool port_same = false;
630  if (PortTypeEqual(ir->match_condition.src_port,
631  ir->match_condition.dst_port)) {
632  port_same = true;
633  }
634 
635  //Add reverse rule if needed
636  if ((ir->direction.compare("<>") == 0) &&
637  (!address_same || !port_same)) {
638  MatchConditionType rmatch_condition;
639  rmatch_condition = ir->match_condition;
640  rmatch_condition.src_address = ir->match_condition.dst_address;
641  rmatch_condition.dst_address = ir->match_condition.src_address;
642  rmatch_condition.src_port = ir->match_condition.dst_port;
643  rmatch_condition.dst_port = ir->match_condition.src_port;
644  AddAceToAcl(&acl_spec, this, cfg_acl, &rmatch_condition,
645  ir->action_list, ir->rule_uuid, id++);
646  }
647  }
648 }
649 
651  const boost::uuids::uuid &u) {
652 
653  assert(!u.is_nil());
654  // Delete ACL
655  if (req.oper == DBRequest::DB_ENTRY_DELETE) {
656  AclSpec acl_spec;
657  AclKey *key = new AclKey(u);
658  req.key.reset(key);
659  req.data.reset(NULL);
660  Enqueue(&req);
661  acl_spec.acl_id = u;
662  AclObjectTrace(AgentLogEvent::DEL, acl_spec);
663  return false;
664  }
665 
666  AccessControlList *cfg_acl = dynamic_cast <AccessControlList *> (node->GetObject());
667  AclSpec acl_spec;
668  acl_spec.acl_id = u;
669  if (cfg_acl) {
670  AclIFNodeToReq(node, req, u, acl_spec);
671  } else {
672  //Firewall Policy also has ACL table as handler
673  FirewallPolicyIFNodeToReq(node, req, u, acl_spec);
674  }
675 
676  AclKey *key = new AclKey(acl_spec.acl_id);
677  AclData *data = new AclData(agent(), node, acl_spec);
678  data->cfg_name_ = node->name();
679  req.key.reset(key);
680  req.data.reset(data);
681  Enqueue(&req);
682  AclObjectTrace(AgentLogEvent::ADD, acl_spec);
683  return false;
684 }
685 
686 // ACL methods
688 {
689  AclEntries::iterator it, tmp;
690  it = entries.begin();
691  while (it != entries.end()) {
692  AclEntry *ae = it.operator->();
693  tmp = it++;
694  entries.erase(tmp);
695  acl_entries_.insert(acl_entries_.end(), *ae);
696  }
697 }
698 
700  AclEntries::iterator it;
701  it = acl_entries_.begin();
702  while (it != acl_entries_.end()) {
703  AclEntry *ae = it.operator->();
704  if (ae->IsQosConfigResolved() == false) {
705  return false;
706  }
707  it++;
708  }
709  return true;
710 }
711 
713  bool ret = false;
714  AclEntries::iterator it;
715  it = acl_entries_.begin();
716  while (it != acl_entries_.end()) {
717  AclEntry *ae = it.operator->();
718  if (ae->ResyncQosConfigEntries()) {
719  ret = true;
720  }
721  it++;
722  }
723  return ret;
724 }
725 
726 AclEntry *AclDBEntry::AddAclEntry(const AclEntrySpec &acl_entry_spec, AclEntries &entries)
727 {
728  AclEntries::iterator iter;
729 
730  for (iter = entries.begin();
731  iter != entries.end(); ++iter) {
732  if (acl_entry_spec.id == iter->id()) {
733  ACL_TRACE(Err, "acl entry id " + acl_entry_spec.id.id_ +
734  " already exists");
735  return NULL;
736  } else if (iter->id() > acl_entry_spec.id) {
737  // Insert
738  break;
739  }
740  }
741 
742  AclEntry *entry = new AclEntry();
743  entry->PopulateAclEntry(acl_entry_spec);
744 
745  std::vector<ActionSpec>::const_iterator it;
746  for (it = acl_entry_spec.action_l.begin(); it != acl_entry_spec.action_l.end();
747  ++it) {
748  if ((*it).ta_type == TrafficAction::MIRROR_ACTION) {
749  Ip4Address sip;
750  if (Agent::GetInstance()->router_id() == (*it).ma.ip) {
752  } else {
753  sip = Agent::GetInstance()->router_id();
754  }
755  MirrorEntryKey mirr_key((*it).ma.analyzer_name);
756  MirrorEntry *mirr_entry = static_cast<MirrorEntry *>
758  assert(mirr_entry);
759  // Store the mirror entry
760  entry->set_mirror_entry(mirr_entry);
761  }
762  }
763  entries.insert(iter, *entry);
764  ACL_TRACE(Info, "acl entry " + integerToString(acl_entry_spec.id.id_) + " added");
765  return entry;
766 }
767 
768 bool AclDBEntry::DeleteAclEntry(const uint32_t acl_entry_id)
769 {
770  AclEntries::iterator iter;
771  for (iter = acl_entries_.begin();
772  iter != acl_entries_.end(); ++iter) {
773  AclEntryID ace_id(acl_entry_id);
774  if (ace_id == iter->id()) {
775  AclEntry *ae = iter.operator->();
776  acl_entries_.erase(acl_entries_.iterator_to(*iter));
777  ACL_TRACE(Info, "acl entry " + integerToString(acl_entry_id) + " deleted");
778  delete ae;
779  return true;
780  }
781  }
782  ACL_TRACE(Err, "acl entry " + integerToString(acl_entry_id) + " doesn't exist");
783  return false;
784 }
785 
787 {
788  AclEntries::iterator iter;
789  iter = acl_entries_.begin();
790  while (iter != acl_entries_.end()) {
791  AclEntry *ae = iter.operator->();
792  acl_entries_.erase(iter++);
793  delete ae;
794  }
795  return;
796 }
797 
798 bool AclDBEntry::PacketMatch(const PacketHeader &packet_header,
799  MatchAclParams &m_acl, FlowPolicyInfo *info) const
800 {
801  AclEntries::const_iterator iter;
802  bool ret_val = false;
803  m_acl.terminal_rule = false;
804  m_acl.action_info.action = 0;
805 
806  for (iter = acl_entries_.begin();
807  iter != acl_entries_.end();
808  ++iter) {
809  /* Check if packet and acl_entry address_family match */
810  if (iter->family() != Address::UNSPEC &&
811  packet_header.family != Address::UNSPEC &&
812  packet_header.family != iter->family()) {
813  continue;
814  }
815  const AclEntry::ActionList &al = iter->PacketMatch(packet_header, info);
816  AclEntry::ActionList::const_iterator al_it;
817  for (al_it = al.begin(); al_it != al.end(); ++al_it) {
818  TrafficAction *ta = static_cast<TrafficAction *>(*al_it.operator->());
819  m_acl.action_info.action |= 1 << ta->action();
821  MirrorAction *a = static_cast<MirrorAction *>(*al_it.operator->());
822  MirrorActionSpec as;
823  as.ip = a->GetIp();
824  as.port = a->GetPort();
825  as.vrf_name = a->vrf_name();
826  as.analyzer_name = a->GetAnalyzerName();
827  as.encap = a->GetEncap();
828  m_acl.action_info.mirror_l.push_back(as);
829  }
831  const VrfTranslateAction *a =
832  static_cast<VrfTranslateAction *>(*al_it.operator->());
833  VrfTranslateActionSpec vrf_translate_action(a->vrf_name(),
834  a->ignore_acl());
835  m_acl.action_info.vrf_translate_action_ = vrf_translate_action;
836  }
837  if (ta->action_type() == TrafficAction::QOS_ACTION) {
838  const QosConfigAction *a =
839  static_cast<const QosConfigAction *>(*al_it.operator->());
840  if (a->qos_config_ref() != NULL) {
841  QosConfigActionSpec qos_action_spec(a->name());
842  if (a->qos_config_ref() &&
843  a->qos_config_ref()->IsDeleted() == false) {
844  qos_action_spec.set_id(a->qos_config_ref()->id());
845  m_acl.action_info.qos_config_action_ = qos_action_spec;
846  }
847  }
848  }
849 
850  if (info && ta->IsDrop()) {
851  if (!info->drop) {
852  info->drop = true;
853  info->terminal = false;
854  info->other = false;
855  info->uuid = iter->uuid();
856  info->acl_name = GetName();
857  }
858  }
859  }
860  if (!(al.empty())) {
861  ret_val = true;
862  m_acl.ace_id_list.push_back(iter->id());
863  if (iter->IsTerminal()) {
864  m_acl.terminal_rule = true;
865  /* Set uuid only if it is NOT already set as
866  * drop/terminal uuid */
867  if (info && !info->drop && !info->terminal) {
868  info->terminal = true;
869  info->other = false;
870  info->uuid = iter->uuid();
871  info->acl_name = GetName();
872  }
873  return ret_val;
874  }
875  /* If the ace action is not drop and if ace is not terminal rule
876  * then set the uuid with the first matching uuid */
877  if (info && !info->drop && !info->terminal && !info->other) {
878  info->other = true;
879  info->uuid = iter->uuid();
880  info->acl_name = GetName();
881  }
882  }
883  }
884  return ret_val;
885 }
886 
887 const AclEntry*
888 AclDBEntry::GetAclEntryAtIndex(uint32_t index) const {
889  uint32_t i = 0;
890  AclEntries::const_iterator it = acl_entries_.begin();
891  while (it != acl_entries_.end()) {
892  if (i == index) {
893  return it.operator->();
894  }
895  it++;
896  i++;
897  }
898 
899  return NULL;
900 }
901 
902 bool AclDBEntry::Changed(const AclEntries &new_entries) const {
903  AclEntries::const_iterator it = acl_entries_.begin();
904  AclEntries::const_iterator new_entries_it = new_entries.begin();
905  while (it != acl_entries_.end() &&
906  new_entries_it != new_entries.end()) {
907  if (*it == *new_entries_it) {
908  it++;
909  new_entries_it++;
910  continue;
911  }
912  return true;
913  }
914  if (it == acl_entries_.end() &&
915  new_entries_it == new_entries.end()) {
916  return false;
917  }
918  return true;
919 }
920 
921 const AclDBEntry* AclTable::GetAclDBEntry(const string acl_uuid_str,
922  const string ctx,
923  SandeshResponse *resp) {
924  if (acl_uuid_str.empty()) {
925  return NULL;
926  }
927 
928  // Get acl entry from acl uuid string
929  AclTable *table = Agent::GetInstance()->acl_table();
930  boost::uuids::uuid acl_id = StringToUuid(acl_uuid_str);
931  AclKey key(acl_id);
932  AclDBEntry *acl_entry = static_cast<AclDBEntry *>(table->FindActiveEntry(&key));
933 
934  return acl_entry;
935 }
936 
937 bool AclDBEntry::IsRulePresent(const string &rule_uuid) const {
938  AclDBEntry::AclEntries::const_iterator it = acl_entries_.begin();
939  while (it != acl_entries_.end()) {
940  const AclEntry *ae = it.operator->();
941  if (ae->uuid() == rule_uuid) {
942  return true;
943  }
944  ++it;
945  }
946  return false;
947 }
948 
949 void AclTable::AclFlowResponse(const string acl_uuid_str, const string ctx,
950  const int last_count) {
951  AclFlowResp *resp = new AclFlowResp();
952  const AclDBEntry *acl_entry = AclTable::GetAclDBEntry(acl_uuid_str, ctx, resp);
953 
954  if (acl_entry) {
955  AclTable *table = Agent::GetInstance()->acl_table();
956  if (!table->flow_acl_sandesh_data_cb_.empty()) {
957  table->flow_acl_sandesh_data_cb_(acl_entry, *resp, last_count);
958  }
959  }
960 
961  resp->set_context(ctx);
962  resp->Response();
963 }
964 
965 void AclTable::AclFlowCountResponse(const string acl_uuid_str,
966  const string ctx,
967  const string &ace_id) {
968  AclFlowCountResp *resp = new AclFlowCountResp();
969  const AclDBEntry *acl_entry = AclTable::GetAclDBEntry(acl_uuid_str, ctx, resp);
970 
971  if (acl_entry) {
972  AclTable *table = Agent::GetInstance()->acl_table();
973  if (!table->flow_ace_sandesh_data_cb_.empty()) {
974  table->flow_ace_sandesh_data_cb_(acl_entry, *resp, ace_id);
975  }
976  }
977  resp->set_context(ctx);
978  resp->Response();
979 }
980 
981 void AclReq::HandleRequest() const {
982  AgentSandeshPtr sand(new AgentAclSandesh(context(), get_uuid()));
983  sand->DoSandesh(sand);
984 }
985 
987  const std::string &context) {
988  return AgentSandeshPtr(new AgentAclSandesh(context,
989  args->GetString("name")));
990 }
991 
992 void NextAclFlowReq::HandleRequest() const {
993  string key = get_iteration_key();
994  int last_count = 0;
995  size_t n = std::count(key.begin(), key.end(), ':');
996  if (n != 1) {
997  AclFlowCountResp *resp = new AclFlowCountResp();
998  resp->set_context(context());
999  resp->Response();
1000  }
1001  std::stringstream ss(key);
1002  string item, uuid;
1003  if (getline(ss, item, ':')) {
1004  uuid = item;
1005  }
1006  if (getline(ss, item, ':')) {
1007  std::istringstream(item) >> last_count;
1008  }
1009 
1010  AclTable::AclFlowResponse(uuid, context(), last_count);
1011 }
1012 
1013 void AclFlowReq::HandleRequest() const {
1014  AclTable::AclFlowResponse(get_uuid(), context(), 0);
1015 }
1016 
1017 void AclFlowCountReq::HandleRequest() const {
1018  AclTable::AclFlowCountResponse(get_uuid(), context(), Agent::NullString());
1019 }
1020 
1021 void NextAclFlowCountReq::HandleRequest() const {
1022  string key = get_iteration_key();
1023  size_t n = std::count(key.begin(), key.end(), ':');
1024  if (n != 1) {
1025  AclFlowCountResp *resp = new AclFlowCountResp();
1026  resp->set_context(context());
1027  resp->Response();
1028  }
1029  std::stringstream ss(key);
1030  string uuid_str, item;
1031  std::string ace_id = "";
1032  if (getline(ss, item, ':')) {
1033  uuid_str = item;
1034  }
1035  if (getline(ss, item, ':')) {
1036  ace_id = item;
1037  }
1038 
1039  AclTable::AclFlowCountResponse(uuid_str, context(), ace_id);
1040 }
1041 
1042 void AclEntrySpec::BuildAddressInfo(const std::string &prefix, int plen,
1043  std::vector<AclAddressInfo> *list) {
1044  AclAddressInfo info;
1045  boost::system::error_code ec;
1046  info.ip_addr = IpAddress::from_string(prefix.c_str(), ec);
1047  if (ec.value() != 0) {
1048  ACL_TRACE(Err, "Invalid source ip prefix " + prefix);
1049  return;
1050  }
1051  info.ip_plen = plen;
1052  if (info.ip_addr.is_v4()) {
1053  info.ip_mask = PrefixToIpNetmask(plen);
1054  info.ip_addr = Address::GetIp4SubnetAddress(info.ip_addr.to_v4(), plen);
1055  } else{
1056  info.ip_mask = PrefixToIp6Netmask(plen);
1057  info.ip_addr = Address::GetIp6SubnetAddress(info.ip_addr.to_v6(), plen);
1058  }
1059  list->push_back(info);
1060 }
1061 
1062 void AclEntrySpec::PopulateServiceType(const FirewallServiceType *fst) {
1063  ServicePort sp;
1064  if (fst == NULL) {
1065  service_group.push_back(sp);
1066  return;
1067  }
1068 
1069  if (fst->protocol.compare("any") == 0) {
1070  sp.protocol.min = 0x0;
1071  sp.protocol.max = 0xff;
1072  //Ignore port
1073  Range port;
1074  port.min = 0x0;
1075  port.max = 0xFFFF;
1076  sp.src_port = port;
1077  sp.dst_port = port;
1078  } else {
1079  sp.protocol.min = fst->protocol_id;
1080  sp.protocol.max = sp.protocol.min;
1081 
1082  sp.src_port.min = fst->src_ports.start_port;
1083  sp.src_port.max = fst->src_ports.end_port;
1084 
1085  sp.dst_port.min = fst->dst_ports.start_port;
1086  sp.dst_port.max = fst->dst_ports.end_port;
1087  }
1088  service_group.push_back(sp);
1089 }
1090 
1091 bool AclEntrySpec::PopulateServiceGroup(const ServiceGroup *s_group) {
1092  if (s_group->firewall_service_list().size() == 0) {
1093  PopulateServiceType(NULL);
1094  }
1095 
1096  std::vector<FirewallServiceType>::const_iterator it =
1097  s_group->firewall_service_list().begin();
1098  for (; it != s_group->firewall_service_list().end(); it++) {
1099  PopulateServiceType(&(*it));
1100  }
1101  return true;
1102 }
1103 
1105  src_addr_type = reverse->dst_addr_type;
1106  src_ip_list = reverse->dst_ip_list;
1107  src_policy_id = reverse->dst_policy_id;
1109  src_sg_id = reverse->dst_sg_id;
1110  src_tags = reverse->dst_tags;
1111 
1112  dst_addr_type = reverse->src_addr_type;
1113  dst_ip_list = reverse->src_ip_list;
1114  dst_policy_id = reverse->src_policy_id;
1116  dst_sg_id = reverse->src_sg_id;
1117  dst_tags = reverse->src_tags;
1118 }
1119 
1121  src_port = reverse->dst_port;
1122  dst_port = reverse->src_port;
1123 
1124  service_group.clear();
1125 
1126  ServiceGroupMatch::ServicePortList::const_iterator it;
1127  for (it = reverse->service_group.begin(); it != reverse->service_group.end();
1128  it++) {
1129  ServicePort sp;
1130  sp.protocol = it->protocol;
1131  sp.src_port = it->dst_port;
1132  sp.dst_port = it->src_port;
1133  service_group.push_back(sp);
1134  }
1135 }
1136 
1138  bool swap_address, bool swap_port) {
1139  type = reverse->type;
1140  id = reverse->id;
1141  id.type_ = id_type;
1142 
1143  if (swap_address) {
1144  ReverseAddress(reverse);
1145  }
1146 
1147  if (swap_port) {
1148  ReversePort(reverse);
1149  }
1150 
1151  protocol = reverse->protocol;
1152 
1153  terminal = reverse->terminal;
1154  action_l = reverse->action_l;
1155 
1156  match_tags = reverse->match_tags;
1157  rule_uuid = reverse->rule_uuid;
1158 }
1159 
1160 IFMapNode*
1162  const std::string &name) {
1163 
1164  IFMapAgentTable *fr_table = static_cast<IFMapAgentTable *>(node->table());
1165  DBGraph *graph = fr_table->GetGraph();
1166 
1167  for (DBGraphVertex::adjacency_iterator iter = node->begin(graph);
1168  iter != node->end(graph); ++iter) {
1169  IFMapNode *ag_node =
1170  static_cast<IFMapNode *>(iter.operator->());
1171  if (agent->config_manager()->SkipNode(ag_node,
1172  agent->cfg()->cfg_address_group_table())) {
1173  continue;
1174  }
1175 
1176  if (ag_node->name() == name) {
1177  return ag_node;
1178  }
1179  }
1180 
1181  return NULL;
1182 }
1183 
1185  const std::string &name,
1186  bool source) {
1187 
1188  IFMapNode *ag_ifmap_node = GetAddressGroup(agent, node, name);
1189  if (!ag_ifmap_node) {
1190  return false;
1191  }
1192 
1193  AddressGroup *ag = static_cast<AddressGroup *>(ag_ifmap_node->GetObject());
1194 
1195  //Walk thru all the labels associated with address_group
1196  IFMapAgentTable *ag_table =
1197  static_cast<IFMapAgentTable *>(ag_ifmap_node->table());
1198  DBGraph *graph = ag_table->GetGraph();
1199 
1200  for (DBGraphVertex::adjacency_iterator iter = ag_ifmap_node->begin(graph);
1201  iter != ag_ifmap_node->end(graph); ++iter) {
1202  IFMapNode *tag_node =
1203  static_cast<IFMapNode *>(iter.operator->());
1204  if (agent->config_manager()->SkipNode(tag_node,
1205  agent->cfg()->cfg_tag_table())) {
1206  continue;
1207  }
1208 
1209  const Tag* tag=
1210  static_cast<const Tag *>(tag_node->GetObject());
1211  if (strtol(tag->id().c_str(), NULL, 16) == 0) {
1212  continue;
1213  }
1214 
1215  if (source) {
1216  src_tags.push_back(strtol(tag->id().c_str(), NULL, 16));
1217  } else {
1218  dst_tags.push_back(strtol(tag->id().c_str(), NULL, 16));
1219  }
1220  }
1221 
1222  std::vector<AclAddressInfo> ip_list;
1223  std::vector<SubnetType>::const_iterator it = ag->prefix().begin();
1224  for (; it != ag->prefix().end(); it++) {
1225  BuildAddressInfo(it->ip_prefix, it->ip_prefix_len, &ip_list);
1226  }
1227 
1228  if (source) {
1229  src_ip_list = ip_list;
1230  } else {
1231  dst_ip_list = ip_list;
1232  }
1233 
1234  return true;
1235 }
1236 
1237 bool AclEntrySpec::Populate(Agent *agent, IFMapNode *fw_rule_node,
1238  const FirewallRule *fw_rule) {
1239  if (fw_rule->IsPropertySet(FirewallRule::SERVICE)) {
1240  PopulateServiceType(&(fw_rule->service()));
1241  }
1242 
1243  if (fw_rule->match_tags().size()) {
1244  std::vector<int>::const_iterator it =
1245  fw_rule->match_tag_types().begin();
1246  for (; it != fw_rule->match_tag_types().end(); it++) {
1247  match_tags.push_back(*it);
1248  }
1249  std::sort(match_tags.begin(), match_tags.end());
1250  }
1251 
1252  /* We need to support both subnet and subnet-list configurations being
1253  * present in a single ACL rule */
1254  if (fw_rule->endpoint_1().subnet.ip_prefix.size()) {
1256  //Build src_ip_list from 'subnet'
1257  if (fw_rule->endpoint_1().subnet.ip_prefix.size()) {
1258  BuildAddressInfo(fw_rule->endpoint_1().subnet.ip_prefix,
1259  fw_rule->endpoint_1().subnet.ip_prefix_len,
1260  &src_ip_list);
1261  }
1262  } else if (fw_rule->endpoint_1().virtual_network.size()) {
1263  std::string nt;
1264  nt = fw_rule->endpoint_1().virtual_network;
1266  src_policy_id_str = nt;
1267  } else if (fw_rule->endpoint_1().tags.size()) {
1269  std::vector<int>::const_iterator it =
1270  fw_rule->endpoint_1().tag_ids.begin();
1271  for (;it != fw_rule->endpoint_1().tag_ids.end(); it++) {
1272  src_tags.push_back(*it);
1273  }
1274  //Sort the tags for optimizing comparision
1275  std::sort(src_tags.begin(), src_tags.end());
1276  } else if (fw_rule->endpoint_1().address_group.size()) {
1277  if (BuildAddressGroup(agent, fw_rule_node,
1278  fw_rule->endpoint_1().address_group, true)) {
1280  }
1281  }
1282 
1283  /* We need to support both subnet and subnet-list configurations being
1284  * present in a single ACL rule */
1285  if (fw_rule->endpoint_2().subnet.ip_prefix.size()) {
1287  //Build src_ip_list from 'subnet'
1288  if (fw_rule->endpoint_2().subnet.ip_prefix.size()) {
1289  BuildAddressInfo(fw_rule->endpoint_2().subnet.ip_prefix,
1290  fw_rule->endpoint_2().subnet.ip_prefix_len,
1291  &dst_ip_list);
1293  }
1294  } else if (fw_rule->endpoint_2().virtual_network.size()) {
1295  std::string nt;
1296  nt = fw_rule->endpoint_2().virtual_network;
1298  dst_policy_id_str = nt;
1299  } else if (fw_rule->endpoint_2().tags.size()) {
1301  std::vector<int>::const_iterator it =
1302  fw_rule->endpoint_2().tag_ids.begin();
1303  for (;it != fw_rule->endpoint_2().tag_ids.end(); it++) {
1304  dst_tags.push_back(*it);
1305  }
1306  //Sort the tags for optimizing comparision
1307  std::sort(dst_tags.begin(), dst_tags.end());
1308  } else if (fw_rule->endpoint_2().address_group.size()) {
1309  if (BuildAddressGroup(agent, fw_rule_node,
1310  fw_rule->endpoint_2().address_group, false)) {
1312  }
1313  }
1314 
1315  return true;
1316 }
1317 
1318 bool AclEntrySpec::Populate(const MatchConditionType *match_condition) {
1319  RangeSpec rs;
1320  if (match_condition->protocol.compare("any") == 0) {
1321  rs.min = 0x0;
1322  rs.max = 0xff;
1323  } else {
1324  std::stringstream ss;
1325  ss<<match_condition->protocol;
1326  ss>>rs.min;
1327  ss.clear();
1328  rs.max = rs.min;
1329  }
1330  protocol.push_back(rs);
1331 
1332  // Update AddressFamily based on ethertype in match_condition
1333  if (match_condition->ethertype.compare("IPv6") == 0) {
1335  } else if (match_condition->ethertype.compare("IPv4") == 0) {
1337  } else {
1339  }
1340 
1341  // check for not icmp/icmpv6
1342  if ((match_condition->protocol.compare("1") != 0) &&
1343  (match_condition->protocol.compare("58") != 0)) {
1344  //src port
1345  PortType sp;
1346  sp = match_condition->src_port;
1347  rs.min = sp.start_port;
1348  rs.max = sp.end_port;
1349  if ((sp.start_port == -1) && (sp.end_port == -1)) {
1350  rs.min = 0;
1351  }
1352  src_port.push_back(rs);
1353 
1354  //dst port
1355  PortType dp;
1356  dp = match_condition->dst_port;
1357  rs.min = dp.start_port;
1358  rs.max = dp.end_port;
1359  if ((dp.start_port == -1) && (dp.end_port == -1)) {
1360  rs.min = 0;
1361  }
1362  dst_port.push_back(rs);
1363  }
1364 
1365  /* We need to support both subnet and subnet-list configurations being
1366  * present in a single ACL rule */
1367  const std::vector<SubnetType> &slist =
1368  match_condition->src_address.subnet_list;
1369  if (slist.size() ||
1370  match_condition->src_address.subnet.ip_prefix.size()) {
1372  //Build src_ip_list from 'subnet'
1373  if (match_condition->src_address.subnet.ip_prefix.size()) {
1374  BuildAddressInfo(match_condition->src_address.subnet.ip_prefix,
1375  match_condition->src_address.subnet.ip_prefix_len,
1376  &src_ip_list);
1377  }
1378  //Build src_ip_list from 'subnet-list'
1379  std::vector<SubnetType>::const_iterator it = slist.begin();
1380  while (it != slist.end()) {
1381  const SubnetType &subnet = *it;
1382  BuildAddressInfo(subnet.ip_prefix, subnet.ip_prefix_len,
1383  &src_ip_list);
1384  ++it;
1385  }
1386  } else if (match_condition->src_address.virtual_network.size()) {
1387  std::string nt;
1388  nt = match_condition->src_address.virtual_network;
1390  src_policy_id_str = nt;
1391  } else if (match_condition->src_address.security_group.size()) {
1392  std::stringstream ss;
1393  ss<<match_condition->src_address.security_group;
1394  ss>>src_sg_id;
1396  }
1397 
1398  /* We need to support both subnet and subnet-list configurations being
1399  * present in a single ACL rule */
1400  const std::vector<SubnetType> &dlist =
1401  match_condition->dst_address.subnet_list;
1402  if (dlist.size() ||
1403  match_condition->dst_address.subnet.ip_prefix.size()) {
1405  //Build src_ip_list from 'subnet'
1406  if (match_condition->dst_address.subnet.ip_prefix.size()) {
1407  BuildAddressInfo(match_condition->dst_address.subnet.ip_prefix,
1408  match_condition->dst_address.subnet.ip_prefix_len,
1409  &dst_ip_list);
1411  }
1412  //Build src_ip_list from 'subnet-list'
1413  std::vector<SubnetType>::const_iterator it = dlist.begin();
1414  while (it != dlist.end()) {
1415  const SubnetType &subnet = *it;
1416  BuildAddressInfo(subnet.ip_prefix, subnet.ip_prefix_len,
1417  &dst_ip_list);
1418  ++it;
1419  }
1420  } else if (match_condition->dst_address.virtual_network.size()) {
1421  std::string nt;
1422  nt = match_condition->dst_address.virtual_network;
1424  dst_policy_id_str = nt;
1425  } else if (match_condition->dst_address.security_group.size()) {
1426  std::stringstream ss;
1427  ss<<match_condition->dst_address.security_group;
1428  ss>>dst_sg_id;
1430  }
1431  return true;
1432 }
1433 
1435  std::vector<ActionSpec>::const_iterator it;
1436  for (it = action_l.begin(); it != action_l.end(); ++it) {
1437  ActionSpec action = *it;
1438  if (action.ta_type != TrafficAction::MIRROR_ACTION) {
1439  continue;
1440  }
1441  // Check for nic assisted mirroring
1442  if (action.ma.nic_assisted_mirroring) {
1443  agent->mirror_table()->AddMirrorEntry(
1444  action.ma.analyzer_name,
1446  continue;
1447  }
1448 
1449  IpAddress sip = agent->GetMirrorSourceIp(action.ma.ip);
1450  MirrorEntryData::MirrorEntryFlags mirror_flag =
1452  action.ma.juniper_header);
1453  if (mirror_flag == MirrorEntryData::DynamicNH_With_JuniperHdr) {
1454  agent->mirror_table()->AddMirrorEntry(action.ma.analyzer_name,
1455  action.ma.vrf_name, sip, agent->mirror_port(), action.ma.ip,
1456  action.ma.port);
1457  } else if (mirror_flag == MirrorEntryData::DynamicNH_Without_JuniperHdr) {
1458  // remote_vm_analyzer mac provided from the config
1459  agent->mirror_table()->AddMirrorEntry(action.ma.analyzer_name,
1460  action.ma.vrf_name, sip, agent->mirror_port(), action.ma.ip,
1461  action.ma.port, 0, mirror_flag, action.ma.mac);
1462  } else if (mirror_flag == MirrorEntryData::StaticNH_Without_JuniperHdr) {
1463  // Vtep dst ip & Vni will be provided from the config
1464  agent->mirror_table()->AddMirrorEntry(action.ma.analyzer_name,
1465  action.ma.vrf_name, sip, agent->mirror_port(),
1466  action.ma.staticnhdata.vtep_dst_ip, action.ma.port,
1467  action.ma.staticnhdata.vni, mirror_flag,
1468  action.ma.staticnhdata.vtep_dst_mac);
1469  } else {
1470  LOG(ERROR, "Mirror nh mode not supported");
1471  }
1472  }
1473 }
1474 
1476  const ActionListType &action_list) {
1477  if (!action_list.simple_action.empty()) {
1478  ActionSpec saction;
1480  saction.simple_action =
1481  acl_table->ConvertActionString(action_list.simple_action);
1482  action_l.push_back(saction);
1483  }
1484 
1485  if (action_list.log) {
1487  action_l.push_back(action);
1488  }
1489 
1490  if (action_list.alert) {
1492  action_l.push_back(action);
1493  }
1494  // Check for nic assisted mirroring
1495  ActionSpec maction;
1498  // Check nic assisted mirroring supported.
1499  // Then Copy only mirroring_vlan.
1500  if (!action_list.mirror_to.analyzer_name.empty()
1501  && action_list.mirror_to.nic_assisted_mirroring) {
1502  maction.ma.nic_assisted_mirroring =
1503  action_list.mirror_to.nic_assisted_mirroring;
1505  action_list.mirror_to.nic_assisted_mirroring_vlan;
1506  maction.ma.analyzer_name = action_list.mirror_to.analyzer_name;
1507  action_l.push_back(maction);
1508  AddMirrorEntry(acl_table->agent());
1509  } else if (!action_list.mirror_to.analyzer_name.empty()) {
1510  boost::system::error_code ec;
1511  maction.ma.vrf_name = std::string();
1512  maction.ma.analyzer_name = action_list.mirror_to.analyzer_name;
1513  maction.ma.ip =
1514  IpAddress::from_string(action_list.mirror_to.analyzer_ip_address, ec);
1515  maction.ma.juniper_header = action_list.mirror_to.juniper_header;
1516  maction.ma.nh_mode = action_list.mirror_to.nh_mode;
1517  MirrorEntryData::MirrorEntryFlags mirror_flag =
1519  maction.ma.juniper_header);
1520  if (mirror_flag == MirrorEntryData::StaticNH_Without_JuniperHdr) {
1521  maction.ma.staticnhdata.vtep_dst_ip =
1522  IpAddress::from_string(
1523  action_list.mirror_to.static_nh_header.vtep_dst_ip_address, ec);
1524  maction.ma.staticnhdata.vtep_dst_mac =
1525  MacAddress::FromString(action_list.mirror_to.static_nh_header.vtep_dst_mac_address);
1526  maction.ma.staticnhdata.vni =
1527  action_list.mirror_to.static_nh_header.vni;
1528  } else if(mirror_flag == MirrorEntryData::DynamicNH_Without_JuniperHdr) {
1529  maction.ma.vrf_name = action_list.mirror_to.routing_instance;
1530  maction.ma.mac =
1531  MacAddress::FromString(action_list.mirror_to.analyzer_mac_address);
1532  }
1533 
1534  if (ec.value() == 0) {
1535  if (action_list.mirror_to.udp_port) {
1536  maction.ma.port = action_list.mirror_to.udp_port;
1537  } else {
1538  // Adding default port
1540  }
1541  action_l.push_back(maction);
1542  AddMirrorEntry(acl_table->agent());
1543  } else {
1544  ACL_TRACE(Err, "Invalid analyzer ip address " +
1545  action_list.mirror_to.analyzer_ip_address);
1546  }
1547  }
1548 
1549  if (!action_list.assign_routing_instance.empty()) {
1550  ActionSpec vrf_translate_spec;
1551  vrf_translate_spec.ta_type = TrafficAction::VRF_TRANSLATE_ACTION;
1552  vrf_translate_spec.simple_action = TrafficAction::VRF_TRANSLATE;
1553  vrf_translate_spec.vrf_translate.set_vrf_name(
1554  action_list.assign_routing_instance);
1555  vrf_translate_spec.vrf_translate.set_ignore_acl(false);
1556  action_l.push_back(vrf_translate_spec);
1557  }
1558 
1559  if (!action_list.qos_action.empty()) {
1560  ActionSpec qos_translate_spec;
1561  qos_translate_spec.ta_type = TrafficAction::QOS_ACTION;
1562  qos_translate_spec.simple_action = TrafficAction::APPLY_QOS;
1563  qos_translate_spec.qos_config_action.set_name(
1564  action_list.qos_action);
1565  action_l.push_back(qos_translate_spec);
1566  }
1567 
1568  if (action_list.host_based_service) {
1569  ActionSpec action;
1572  action_l.push_back(action);
1573  }
1574 }
1575 
1578 }
1579 
1582 }
virtual bool IFNodeToUuid(IFMapNode *node, boost::uuids::uuid &u)
Definition: acl.cc:403
TagList dst_tags
AclSpec acl_spec_
Definition: acl.h:84
std::string dst_policy_id_str
void ReversePort(AclEntrySpec *ace_spec)
Definition: acl.cc:1120
void ReverseAddress(AclEntrySpec *ace_spec)
Definition: acl.cc:1104
bool IsQosConfigResolved()
Definition: acl_entry.cc:198
bool Changed(const AclEntries &new_acl_entries) const
Definition: acl.cc:902
IpAddress GetMirrorSourceIp(const IpAddress &dest)
Definition: agent.cc:76
void SetName(const std::string name)
Definition: acl.h:114
boost::function< void(const AclDBEntry *acl, AclFlowResp &data, const int last_count)> FlowAclSandeshDataFn
Definition: acl.h:158
std::string GetAnalyzerName()
bool drop
Definition: acl.h:26
VrfTranslateActionSpec vrf_translate
static Agent * GetInstance()
Definition: agent.h:436
static boost::uuids::uuid StringToUuid(const std::string &str)
Definition: string_util.h:145
static void CfgUuidSet(uint64_t ms_long, uint64_t ls_long, boost::uuids::uuid &u)
Definition: agent_cmn.h:67
AclEntryIDList ace_id_list
Definition: acl.h:57
AddressMatch::AddressType dst_addr_type
DBState * GetState(DBTableBase *tbl_base, ListenerId listener) const
Definition: db_entry.cc:37
std::vector< AclEntrySpec > acl_entry_specs_
std::string GetString(const std::string &key) const
virtual bool OperDBOnChange(DBEntry *entry, const DBRequest *req)
Definition: acl.cc:127
virtual DBEntry * OperDBAdd(const DBRequest *req)
Definition: acl.cc:107
std::string nh_mode
virtual bool OperDBDelete(DBEntry *entry, const DBRequest *req)
Definition: acl.cc:203
void set_name(const std::string &name)
std::list< TrafficAction * > ActionList
Definition: acl_entry.h:94
Definition: acl.h:147
void SetDynamicAcl(bool dyn)
Definition: acl.h:125
bool DBEntrySandesh(Sandesh *resp, std::string &name) const
Definition: acl.cc:68
void ActionInit()
Definition: acl.cc:211
bool IsDeleted() const
Definition: db_entry.h:49
void PopulateServiceType(const autogen::FirewallServiceType *fst)
Definition: acl.cc:1062
ConfigManager * config_manager() const
Definition: agent.cc:889
void SetState(DBTableBase *tbl_base, ListenerId listener, DBState *state)
Definition: db_entry.cc:22
static AclTable * acl_table_
Definition: acl.cc:36
boost::asio::ip::address IpAddress
Definition: address.h:13
const AgentQosConfig * qos_config_ref() const
uint8_t sub_op_
Definition: agent_db.h:106
bool stringToInteger(const std::string &str, NumberType &num)
Definition: string_util.h:71
QosConfigActionSpec qos_config_action
Definition: acl.h:62
const std::string & vrf_name() const
Agent * agent() const
Definition: agent_db.h:213
Definition: acl.h:69
std::unique_ptr< DBRequestData > data
Definition: db_table.h:49
static DBTableBase * CreateTable(DB *db, const std::string &name)
Definition: acl.cc:274
bool ResyncQosConfigEntries()
Definition: acl.cc:712
void FirewallPolicyIFNodeToReq(IFMapNode *node, DBRequest &req, const boost::uuids::uuid &u, AclSpec &acl_spec)
Definition: acl.cc:506
DBTableBase * parent()
bool ace_add
Definition: acl.h:82
void set_id(uint32_t id)
AgentDBEntry * FindActiveEntry(const DBEntry *key)
Definition: agent_db.cc:110
bool Enqueue(DBRequest *req)
Definition: db_table.cc:194
uint32_t id() const
Definition: qos_config.h:73
boost::uuids::uuid uuid
std::string vrf_name
std::vector< RangeSpec > protocol
std::vector< AclAddressInfo > dst_ip_list
uint32_t action
Definition: acl.h:44
#define METADATA_IP_ADDR
Definition: agent.h:294
void ListenerInit()
Definition: acl.cc:268
const std::string & name() const
bool IsDrop() const
adjacency_iterator end(DBGraph *graph)
IFMapAgentTable * cfg_address_group_table() const
Definition: cfg_init.h:126
static std::string UuidToString(const boost::uuids::uuid &id)
Definition: string_util.h:138
const boost::uuids::uuid & GetUuid() const
Definition: acl.h:112
std::string id_
Definition: acl_entry.h:81
IFMapTable * table()
Definition: ifmap_node.h:29
std::vector< ActionSpec > action_l
ServiceGroupMatch::ServicePortList service_group
virtual bool IFNodeToReq(IFMapNode *node, DBRequest &req, const boost::uuids::uuid &u)
Definition: acl.cc:650
boost::shared_ptr< TraceBuffer< SandeshTrace > > SandeshTraceBufferPtr
Definition: sandesh_trace.h:18
std::vector< RangeSpec > src_port
bool terminal
Definition: acl.h:27
static Ip4Address GetIp4SubnetAddress(const Ip4Address &prefix, uint16_t plen)
Definition: address.cc:179
std::unique_ptr< DBRequestKey > KeyPtr
Definition: db_entry.h:25
SandeshTraceBufferPtr AclTraceBuf
static const std::string kActionLogStr
QosConfigActionSpec qos_config_action_
Definition: acl.h:49
#define ACL_TRACE(obj,...)
Definition: acl.h:223
AclTable(DB *db, const std::string &name)
Definition: acl.h:160
bool SubnetTypeEqual(const autogen::SubnetType &lhs, const autogen::SubnetType &rhs) const
Definition: acl.cc:565
MirrorTable * mirror_table() const
Definition: agent.h:525
static Ip6Address GetIp6SubnetAddress(const Ip6Address &prefix, uint16_t plen)
Definition: address.cc:200
const DBGraph * GetGraph() const
std::vector< MirrorActionSpec > mirror_l
Definition: acl.h:47
ListenerId Register(ChangeCallback callback, const std::string &name="unspecified")
Definition: db_table.cc:181
Definition: db.h:24
std::string GetEncap()
void set_acl_flow_sandesh_data_cb(FlowAclSandeshDataFn fn)
Definition: acl.cc:1580
KeyPtr GetDBRequestKey() const
Definition: acl.cc:58
void Init()
Definition: db_table.cc:387
bool IsQosConfigResolved()
Definition: acl.cc:699
int ace_id_to_del_
Definition: acl.h:80
const std::string & GetName() const
Definition: acl.h:113
virtual bool OperDBResync(DBEntry *entry, const DBRequest *req)
Definition: acl.cc:199
bool IsRulePresent(const std::string &uuid) const
Definition: acl.cc:937
TagList src_tags
void DeleteAllAclEntries()
Definition: acl.cc:786
uint8_t type
Definition: load_balance.h:109
static const std::string integerToString(const NumberType &num)
Definition: string_util.h:19
AclTypeSpecT type
MirrorActionSpec ma
MacAddress vtep_dst_mac
Definition: agent.h:358
void Notify(DBTablePartBase *partition, DBEntryBase *e)
Definition: acl.cc:236
VrfTranslateActionSpec vrf_translate_action_
Definition: acl.h:48
AclEntry * AddAclEntry(const AclEntrySpec &acl_entry_spec, AclEntries &entries)
Definition: acl.cc:726
static void AclEntryObjectTrace(AclEntrySandeshData &ace_sandesh, AclEntrySpec &ace_spec)
Definition: acl.cc:281
static const uint16_t AnalyzerUdpPort()
static void AclFlowCountResponse(const std::string acl_uuid_str, const std::string ctx, const std::string &ace_id)
Definition: acl.cc:965
static void AddAceToAcl(AclSpec *acl_spec, const AclTable *acl_table, AccessControlList *cfg_acl, const MatchConditionType *match_condition, const ActionListType action_list, const string rule_uuid, uint32_t id)
Definition: acl.cc:420
void BuildAddressInfo(const std::string &prefix, int plen, std::vector< AclAddressInfo > *list)
Definition: acl.cc:1042
static const std::string kActionHbsStr
virtual std::unique_ptr< DBEntry > AllocEntry(const DBRequestKey *k) const
Definition: acl.cc:101
void Reverse(AclEntrySpec *ace_spec, AclEntryID::Type type, bool swap_address, bool swap_port)
Definition: acl.cc:1137
bool Populate(const autogen::MatchConditionType *match_condition)
Ip4Address router_id() const
Definition: agent.h:666
void PopulateServicePort(AclEntrySpec &ace_spec, IFMapNode *node)
Definition: acl.cc:454
std::unique_ptr< DBRequestKey > key
Definition: db_table.h:48
IFMapAgentTable * cfg_tag_table() const
Definition: cfg_init.h:134
static std::string BuildIpMaskList(const std::vector< AclAddressInfo > &list)
Definition: acl_entry.cc:624
std::string encap
bool BuildAddressGroup(Agent *agent, IFMapNode *node, const std::string &name, bool source)
Definition: acl.cc:1184
bool AddressTypeEqual(const autogen::AddressType &lhs, const autogen::AddressType &rhs) const
Definition: acl.cc:574
DBOperation oper
Definition: db_table.h:42
std::string rule_uuid
static const std::string & NullString()
Definition: agent.h:437
IpAddress ip_addr
std::string name_
Definition: acl.h:142
bool PopulateServiceGroup(const autogen::ServiceGroup *service_group)
Definition: acl.cc:1091
virtual AgentSandeshPtr GetAgentSandesh(const AgentSandeshArguments *args, const std::string &context)
Definition: acl.cc:986
uint32_t GetPort()
class boost::shared_ptr< AgentSandesh > AgentSandeshPtr
Definition: agent_db.h:18
bool PortTypeEqual(const autogen::PortType &src, const autogen::PortType &dst) const
Definition: acl.cc:598
uint16_t nic_assisted_mirroring_vlan
static MirrorEntryData::MirrorEntryFlags DecodeMirrorFlag(const std::string &nh_mode, bool juniper_header)
IpAddress PrefixToIp6Netmask(uint32_t plen)
void PopulateAction(const AclTable *acl_table, const autogen::ActionListType &action_list)
Definition: acl.cc:1475
StaticMirrorNhData staticnhdata
static std::string ActionToString(enum Action at)
const std::string & name() const
Definition: ifmap_node.h:48
uint16_t max
void ClearState(DBTableBase *tbl_base, ListenerId listener)
Definition: db_entry.cc:73
TrafficActionMap ta_map_
Definition: acl.h:215
boost::uuids::uuid uuid_
Definition: acl.h:64
bool ignore_acl() const
std::string analyzer_name
boost::asio::ip::address_v4 Ip4Address
Definition: address.h:14
TrafficAction::Action simple_action
void AddMirrorEntry(Agent *agent) const
Definition: acl.cc:1434
bool DeleteAclEntry(const uint32_t acl_entry_id)
Definition: acl.cc:768
static void AddMirrorEntry(const std::string &analyzer_name, const std::string &vrf_name, const IpAddress &sip, uint16_t sport, const IpAddress &dip, uint16_t dport)
std::string uuid
Definition: acl.h:25
bool ResyncQosConfigEntries()
Definition: acl_entry.cc:211
IpAddress ip_mask
const AclEntry * GetAclEntryAtIndex(uint32_t) const
Definition: acl.cc:888
IFMapObject * GetObject()
Definition: ifmap_node.cc:63
void set_ignore_acl(bool ignore_acl)
FlowAclSandeshDataFn flow_acl_sandesh_data_cb_
Definition: acl.h:217
bool GetDynamicAcl() const
Definition: acl.h:126
IFMapNode * GetFirewallRule(IFMapNode *node)
Definition: acl.cc:474
bool IsLess(const DBEntry &rhs) const
Definition: acl.cc:47
bool PacketMatch(const PacketHeader &packet_header, MatchAclParams &m_acl, FlowPolicyInfo *info) const
Definition: acl.cc:798
IpAddress GetIp()
void AddImplicitRule(AclSpec &acl_spec, AclEntrySpec &ace_spec, const autogen::FirewallRule *rule)
Definition: acl.cc:495
AgentQosConfigTable * qos_config_table() const
Definition: agent.h:554
TrafficAction::Action ConvertActionString(std::string action) const
Definition: acl.cc:218
AclEntryID id
void DeleteUnresolvedEntry(AclDBEntry *entry)
Definition: acl.cc:232
uint16_t min
std::string vrf_name()
bool other
Definition: acl.h:28
AclEntries acl_entries_
Definition: acl.h:143
void PopulateAclEntry(const AclEntrySpec &acl_entry_spec)
Definition: acl_entry.cc:46
std::string acl_name
Definition: acl.h:31
static void AclFlowResponse(const std::string acl_uuid_str, const std::string ctx, const int last_count)
Definition: acl.cc:949
Action action() const
#define LOG(_Level, _Msg)
Definition: logging.h:33
DBTableBase::ListenerId qos_config_listener_id_
Definition: acl.h:213
FlowAction action_info
Definition: acl.h:58
UnResolvedAclEntries unresolved_acl_entries_
Definition: acl.h:214
uint16_t min
static const std::string kActionAlertStr
AddressMatch::AddressType src_addr_type
Address::Family family
const std::string & uuid() const
Definition: acl_entry.h:121
AgentConfig * cfg() const
Definition: agent.cc:865
void SetAclEntries(AclEntries &entries)
Definition: acl.cc:687
static void AclObjectTrace(AgentLogEvent::type event, AclSpec &acl_spec)
Definition: acl.cc:381
std::string ToString() const
Definition: acl.cc:52
bool SkipNode(IFMapNode *node)
boost::function< void(const AclDBEntry *acl, AclFlowCountResp &data, const std::string &ace_id)> FlowAceSandeshDataFn
Definition: acl.h:156
static MacAddress FromString(const std::string &str, boost::system::error_code *error=NULL)
Definition: mac_address.cc:71
AclTable * acl_table() const
Definition: agent.h:515
void AclIFNodeToReq(IFMapNode *node, DBRequest &req, const boost::uuids::uuid &u, AclSpec &acl_spec)
Definition: acl.cc:607
IFMapNode * GetAddressGroup(Agent *agent, IFMapNode *node, const std::string &name)
Definition: acl.cc:1161
uint16_t max
TrafficAction::TrafficActionType ta_type
bool terminal_rule
Definition: acl.h:59
adjacency_iterator begin(DBGraph *graph)
boost::intrusive::list< AclEntry, AclEntryNode > AclEntries
Definition: acl.h:97
void SetAclSandeshData(AclSandeshData &data) const
Definition: acl.cc:89
IpAddress PrefixToIpNetmask(uint32_t prefix_len)
void SetKey(const DBRequestKey *key)
Definition: acl.cc:63
TrafficActionType action_type() const
FlowPolicyInfo(const std::string &u)
Definition: acl.cc:42
void set_vrf_name(const std::string &vrf_name)
std::string src_policy_id_str
std::string cfg_name_
Definition: acl.h:83
std::vector< AclAddressInfo > src_ip_list
Type type_
Definition: acl_entry.h:82
Definition: acl.h:92
uint16_t mirror_port() const
Definition: agent.h:1111
bool dynamic_acl
Address::Family family
Definition: packet_header.h:31
void set_mirror_entry(MirrorEntryRef me)
Definition: acl_entry.cc:228
TagList match_tags
void AddUnresolvedEntry(AclDBEntry *entry)
Definition: acl.cc:228
boost::uuids::uuid uuid_
Definition: acl.h:140
void set_ace_flow_sandesh_data_cb(FlowAceSandeshDataFn fn)
Definition: acl.cc:1576
SandeshTraceBufferPtr SandeshTraceBufferCreate(const std::string &buf_name, size_t buf_size, bool trace_enable=true)
Definition: sandesh_trace.h:46
FlowAceSandeshDataFn flow_ace_sandesh_data_cb_
Definition: acl.h:216
std::vector< RangeSpec > dst_port
static const AclDBEntry * GetAclDBEntry(const std::string uuid_str, const std::string ctx, SandeshResponse *resp)
Definition: acl.cc:921