@@ -86,10 +86,11 @@ inline string trim(const std::string& str, const std::string& whitespace = " \t"
86
86
return str.substr (strBegin, strRange);
87
87
}
88
88
89
- AclRule::AclRule (AclOrch *aclOrch, string rule, string table) :
89
+ AclRule::AclRule (AclOrch *aclOrch, string rule, string table, acl_table_type_t type ) :
90
90
m_pAclOrch(aclOrch),
91
91
m_id(rule),
92
92
m_tableId(table),
93
+ m_tableType(type),
93
94
m_tableOid(SAI_NULL_OBJECT_ID),
94
95
m_ruleOid(SAI_NULL_OBJECT_ID),
95
96
m_counterOid(SAI_NULL_OBJECT_ID),
@@ -420,18 +421,45 @@ AclRuleCounters AclRule::getCounters()
420
421
return AclRuleCounters (counter_attr[0 ].value .u64 , counter_attr[1 ].value .u64 );
421
422
}
422
423
423
- shared_ptr<AclRule> AclRule::makeShared (acl_table_type_t type, AclOrch *acl, MirrorOrch *mirror, string rule, string table)
424
+ shared_ptr<AclRule> AclRule::makeShared (acl_table_type_t type, AclOrch *acl, MirrorOrch *mirror, const string& rule, const string& table, const KeyOpFieldsValuesTuple& data )
424
425
{
425
- switch (type)
426
+ string action;
427
+ bool action_found = false ;
428
+ /* Find action configured by user. Based on action type create rule. */
429
+ for (const auto & itr : kfvFieldsValues (data))
430
+ {
431
+ string attr_name = toUpper (fvField (itr));
432
+ string attr_value = fvValue (itr);
433
+ if (attr_name == ACTION_PACKET_ACTION || attr_name == ACTION_MIRROR_ACTION)
434
+ {
435
+ action_found = true ;
436
+ action = attr_name;
437
+ break ;
438
+ }
439
+ }
440
+
441
+ if (!action_found)
442
+ {
443
+ throw runtime_error (" ACL rule action is not found in rule " + rule);
444
+ }
445
+
446
+ if (type != ACL_TABLE_L3 && type != ACL_TABLE_MIRROR)
447
+ {
448
+ throw runtime_error (" Unknown table type." );
449
+ }
450
+
451
+ /* Mirror rules can exist in both tables*/
452
+ if (action == ACTION_MIRROR_ACTION)
453
+ {
454
+ return make_shared<AclRuleMirror>(acl, mirror, rule, table, type);
455
+ }
456
+ /* L3 rules can exist only in L3 table */
457
+ else if (type == ACL_TABLE_L3)
426
458
{
427
- case ACL_TABLE_L3:
428
- return make_shared<AclRuleL3>(acl, rule, table);
429
- case ACL_TABLE_MIRROR:
430
- return make_shared<AclRuleMirror>(acl, mirror, rule, table);
431
- case ACL_TABLE_UNKNOWN:
432
- default :
433
- throw runtime_error (" Unknown rule type." );
459
+ return make_shared<AclRuleL3>(acl, rule, table, type);
434
460
}
461
+
462
+ throw runtime_error (" Wrong combination of table type and action in rule " + rule);
435
463
}
436
464
437
465
bool AclRule::createCounter ()
@@ -499,8 +527,8 @@ bool AclRule::removeCounter()
499
527
return true ;
500
528
}
501
529
502
- AclRuleL3::AclRuleL3 (AclOrch *aclOrch, string rule, string table) :
503
- AclRule(aclOrch, rule, table)
530
+ AclRuleL3::AclRuleL3 (AclOrch *aclOrch, string rule, string table, acl_table_type_t type ) :
531
+ AclRule(aclOrch, rule, table, type )
504
532
{
505
533
}
506
534
@@ -662,8 +690,8 @@ void AclRuleL3::update(SubjectType, void *)
662
690
// Do nothing
663
691
}
664
692
665
- AclRuleMirror::AclRuleMirror (AclOrch *aclOrch, MirrorOrch *mirror, string rule, string table) :
666
- AclRule(aclOrch, rule, table),
693
+ AclRuleMirror::AclRuleMirror (AclOrch *aclOrch, MirrorOrch *mirror, string rule, string table, acl_table_type_t type ) :
694
+ AclRule(aclOrch, rule, table, type ),
667
695
m_state(false ),
668
696
m_pMirrorOrch(mirror)
669
697
{
@@ -688,6 +716,17 @@ bool AclRuleMirror::validateAddAction(string attr_name, string attr_value)
688
716
return true ;
689
717
}
690
718
719
+ bool AclRuleMirror::validateAddMatch (string attr_name, string attr_value)
720
+ {
721
+ if (m_tableType == ACL_TABLE_L3 && attr_name == MATCH_DSCP)
722
+ {
723
+ SWSS_LOG_ERROR (" DSCP match is not supported for the tables of type L3" );
724
+ return false ;
725
+ }
726
+
727
+ return AclRule::validateAddMatch (attr_name, attr_value);
728
+ }
729
+
691
730
bool AclRuleMirror::validate ()
692
731
{
693
732
SWSS_LOG_ENTER ();
@@ -749,11 +788,6 @@ bool AclRuleMirror::create()
749
788
750
789
bool AclRuleMirror::remove ()
751
790
{
752
- if (!m_pMirrorOrch->decreaseRefCount (m_sessionName))
753
- {
754
- throw runtime_error (" Failed to decrease mirror session reference count" );
755
- }
756
-
757
791
if (!m_state)
758
792
{
759
793
return true ;
@@ -764,6 +798,11 @@ bool AclRuleMirror::remove()
764
798
return false ;
765
799
}
766
800
801
+ if (!m_pMirrorOrch->decreaseRefCount (m_sessionName))
802
+ {
803
+ throw runtime_error (" Failed to decrease mirror session reference count" );
804
+ }
805
+
767
806
m_state = false ;
768
807
769
808
return true ;
@@ -991,11 +1030,6 @@ void AclOrch::update(SubjectType type, void *cntx)
991
1030
992
1031
for (const auto & table : m_AclTables)
993
1032
{
994
- if (table.second .type != ACL_TABLE_MIRROR)
995
- {
996
- continue ;
997
- }
998
-
999
1033
for (auto & rule : table.second .rules )
1000
1034
{
1001
1035
rule.second ->update (type, cntx);
@@ -1169,9 +1203,9 @@ void AclOrch::doAclRuleTask(Consumer &consumer)
1169
1203
1170
1204
if (bAllAttributesOk)
1171
1205
{
1172
- newRule = AclRule::makeShared (m_AclTables[table_oid].type , this , m_mirrorOrch, rule_id, table_id);
1206
+ newRule = AclRule::makeShared (m_AclTables[table_oid].type , this , m_mirrorOrch, rule_id, table_id, t );
1173
1207
1174
- for (auto itr : kfvFieldsValues (t))
1208
+ for (const auto & itr : kfvFieldsValues (t))
1175
1209
{
1176
1210
string attr_name = toUpper (fvField (itr));
1177
1211
string attr_value = fvValue (itr);
@@ -1198,6 +1232,7 @@ void AclOrch::doAclRuleTask(Consumer &consumer)
1198
1232
}
1199
1233
}
1200
1234
}
1235
+
1201
1236
// validate and create ACL rule
1202
1237
if (bAllAttributesOk && newRule->validate ())
1203
1238
{
0 commit comments