2
2
"""
3
3
using aclshow to display SONiC switch acl rules and counters
4
4
5
- usage: aclshow [-h] [-v] [-c] [-d] [-vv] [-p PORTS ] [-t TABLES] [-r RULES]
5
+ usage: aclshow [-h] [-v] [-c] [-vv ] [-t TABLES] [-r RULES]
6
6
7
7
Display SONiC switch ACL Counters/status
8
8
@@ -12,10 +12,8 @@ optional arguments:
12
12
-vv, --verbose verbose output (progress, etc)
13
13
-c, --clear clear ACL counters statistics
14
14
-a, --all show all ACL counters
15
- -p PORTS, --ports PORTS action by specific port list: Ethernet0,Ethernet12
16
15
-r RULES, --rules RULES action by specific rules list: Rule_1,Rule_2
17
16
-t TABLES, --tables TABLES action by specific tables list: Table_1,Table_2
18
- -d, --details display detailed ACL info
19
17
"""
20
18
21
19
from __future__ import print_function
@@ -37,7 +35,7 @@ from natsort import natsorted
37
35
COUNTER_POSITION = '/tmp/.counters_acl.p'
38
36
39
37
### acl display header
40
- ACL_HEADER = ["RULE NAME" , "TABLE NAME" , "TYPE" , "PRIO" , "ACTION" , " PACKETS COUNT" , "BYTES COUNT" ]
38
+ ACL_HEADER = ["RULE NAME" , "TABLE NAME" , "PACKETS COUNT" , "BYTES COUNT" ]
41
39
42
40
# some constants for rule properties
43
41
PACKETS_COUNTER = "packets counter"
@@ -51,14 +49,11 @@ class AclStat(object):
51
49
ACL_TABLE = "ACL_TABLE"
52
50
ACL_RULE = "ACL_RULE"
53
51
54
- def __init__ (self , ports , rules , tables ):
55
- self .port_map = {}
52
+ def __init__ (self , rules , tables ):
56
53
self .acl_tables = {}
57
54
self .acl_rules = {}
58
55
self .acl_counters = {}
59
56
self .saved_acl_counters = {}
60
- self .ports = ports
61
- self .port_list = []
62
57
self .rule_list = []
63
58
self .table_list = []
64
59
@@ -75,30 +70,6 @@ class AclStat(object):
75
70
self .configdb = swsssdk .ConfigDBConnector ()
76
71
self .configdb .connect ()
77
72
78
- self .read_port_map ()
79
- self .validate_ports ()
80
-
81
- def read_port_map (self ):
82
- """
83
- Redis database interface mapping for SAI interface index and interface name
84
- """
85
- self .port_map = self .db .get_all (self .db .COUNTERS_DB , "COUNTERS_PORT_NAME_MAP" )
86
-
87
- def validate_ports (self ):
88
- """
89
- if user give -p port option, make sure the port names are valid
90
- """
91
- if self .ports is not None :
92
- p_list = self .ports .split (',' )
93
- for p in p_list :
94
- pname = p .strip ().title ()
95
- if pname not in self .port_map :
96
- raise Exception ("Wrong ports interface name" )
97
- else :
98
- self .port_list .append (pname )
99
- else :
100
- self .port_list = self .port_map .keys ()
101
-
102
73
def previous_counters (self ):
103
74
"""
104
75
if user ever did a clear counter action, then read the saved counter reading when clear statistics
@@ -137,7 +108,11 @@ class AclStat(object):
137
108
self .acl_tables = self .configdb .get_table (self .ACL_TABLE )
138
109
139
110
if verboseflag :
140
- print ("ACL Tables to show:" , len (self .acl_tables ))
111
+ print ("Total number of ACL Tables: %d" % len (self .acl_tables ))
112
+ if self .table_list :
113
+ self .acl_tables = { table :content for (table , content ) in self .acl_tables .items () if table in self .table_list }
114
+ else :
115
+ self .acl_tables = { table :content for (table , content ) in self .acl_tables .items () if table in ['DATAACL' ] }
141
116
142
117
def fetch_acl_rules ():
143
118
"""
@@ -146,17 +121,18 @@ class AclStat(object):
146
121
self .acl_rules = self .configdb .get_table (self .ACL_RULE )
147
122
148
123
if verboseflag :
149
- print ("ACL Rules to show:" , len (self .acl_rules ))
124
+ print ("Total number of ACL Rules: %d" % len (self .acl_rules ))
125
+ if self .table_list :
126
+ self .acl_rules = { (table , rule ):content for ((table , rule ), content ) in self .acl_rules .items () if table in self .table_list }
127
+ if self .rule_list :
128
+ self .acl_rules = { (table , rule ):content for ((table , rule ), content ) in self .acl_rules .items () if rule in self .rule_list }
150
129
151
130
def fetch_acl_counters ():
152
131
"""
153
132
Get ACL counters from the DB
154
133
"""
155
134
acl_counters_cmd = "docker exec -it database redis-cli --csv -n 2 hgetall COUNTERS:"
156
135
counters_cnt = len (self .acl_rules ) # num of counters should be the same as rules
157
- if verboseflag :
158
- print ("ACL Counters found:" , counters_cnt )
159
-
160
136
for table , rule in self .acl_rules .keys ():
161
137
cnt_props = lowercase_keys (self .db .get_all (self .db .COUNTERS_DB , "COUNTERS:%s:%s" % (table , rule )))
162
138
self .acl_counters [table , rule ] = cnt_props
@@ -179,7 +155,7 @@ class AclStat(object):
179
155
180
156
if key in self .saved_acl_counters :
181
157
new_value = int (self .acl_counters [key ][type ]) - int (self .saved_acl_counters [key ][type ])
182
- if new_value > 0 :
158
+ if new_value >= 0 :
183
159
return str (new_value )
184
160
185
161
return str (self .acl_counters [key ][type ])
@@ -202,9 +178,6 @@ class AclStat(object):
202
178
continue
203
179
rule = self .acl_rules [rule_key ]
204
180
line = [rule_key [1 ], rule_key [0 ],
205
- self .acl_tables [rule_key [0 ]]['type' ],
206
- rule ['PRIORITY' ],
207
- get_action (rule ),
208
181
self .get_counter_value (rule_key , 'packets' ),
209
182
self .get_counter_value (rule_key , 'bytes' )]
210
183
aclstat .append (line )
@@ -213,63 +186,6 @@ class AclStat(object):
213
186
aclstat .sort (key = lambda x : (x [1 ], - int (x [3 ])))
214
187
print (tabulate (aclstat , header ))
215
188
216
- def display_acl_details (self ):
217
- """
218
- print out acl details
219
- """
220
- def adj_len (text , mlen ):
221
- return text + "." * (mlen - len (text ))
222
-
223
- if not self .acl_tables :
224
- return
225
-
226
- # determine max len of the table and rule properties
227
- onetable = self .acl_tables .itervalues ().next ()
228
- tlen = len (onetable .keys ()[0 ])
229
- for property in onetable .keys ():
230
- if len (property ) > tlen :
231
- tlen = len (property )
232
-
233
- if not self .acl_rules :
234
- rlen = 0
235
- else :
236
- onerule = self .acl_rules .itervalues ().next ()
237
- rlen = len (onerule .keys ()[0 ])
238
- for property in onerule .keys () + [PACKETS_COUNTER , BYTES_COUNTER ]:
239
- if len (property ) > rlen :
240
- rlen = len (property )
241
-
242
- mlen = max (rlen , tlen ) + 1
243
-
244
- for table_name in self .acl_tables .keys ():
245
- ports = self .acl_tables [table_name ]['ports' ]
246
- header = "ACL Table: " + table_name
247
- print (header )
248
- print ("=" * len (header ))
249
- table_props = []
250
- table = self .acl_tables [table_name ]
251
- for tk in table .keys ():
252
- line = [adj_len (tk , mlen ), table [tk ]]
253
- table_props .append (line )
254
- print (tabulate (table_props , headers = ['Property' , 'Value' ]), "\n " )
255
-
256
- acl_rules_sort = self .acl_rules .keys ()
257
- acl_rules_sort = natsorted (acl_rules_sort , key = lambda x : (x [0 ], x [1 ]))
258
-
259
- for table_name , rule_name in acl_rules_sort :
260
- rule_props = []
261
- rule = self .acl_rules [table_name , rule_name ]
262
- header = "ACL Table: " + table_name + ", ACL Rule: " + rule_name
263
- print (header )
264
- print ("=" * len (header ))
265
- for rk in rule .keys ():
266
- line = [adj_len (rk , mlen ), rule [rk ]]
267
- rule_props .append (line )
268
- rule_props .append ([adj_len (PACKETS_COUNTER , mlen ), self .get_counter_value ((table_name , rule_name ), 'packets' )])
269
- rule_props .append ([adj_len (BYTES_COUNTER , mlen ), self .get_counter_value ((table_name , rule_name ), 'bytes' )])
270
- rule_props .append ([adj_len ('ports' , mlen ), ports ])
271
- print (tabulate (rule_props , headers = ['Property' , 'Value' ]), "\n " )
272
-
273
189
def clear_counters (self ):
274
190
"""
275
191
clear counters -- write current counters to file in /tmp
@@ -286,24 +202,19 @@ def main():
286
202
formatter_class = argparse .RawTextHelpFormatter )
287
203
parser .add_argument ('-a' , '--all' , action = 'store_true' , help = 'Show all ACL counters' )
288
204
parser .add_argument ('-c' , '--clear' , action = 'store_true' , help = 'Clear ACL counters statistics' )
289
- parser .add_argument ('-p' , '--ports' , type = str , help = 'action by specific port list: Ethernet0,Ethernet12' , default = None )
290
205
parser .add_argument ('-r' , '--rules' , type = str , help = 'action by specific rules list: Rule1_Name,Rule2_Name' , default = None )
291
206
parser .add_argument ('-t' , '--tables' , type = str , help = 'action by specific tables list: Table1_Name,Table2_Name' , default = None )
292
- parser .add_argument ('-d' , '--details' , action = 'store_true' , help = 'Display detailed ACL info' , default = False )
293
207
parser .add_argument ('-vv' , '--verbose' , action = 'store_true' , help = 'Verbose output' , default = False )
294
208
args = parser .parse_args ()
295
209
296
210
try :
297
- acls = AclStat (args .ports , args . rules , args .tables )
211
+ acls = AclStat (args .rules , args .tables )
298
212
acls .redis_acl_read (args .verbose )
299
213
if args .clear :
300
214
acls .clear_counters ()
301
215
return
302
216
acls .previous_counters ()
303
- if args .details :
304
- acls .display_acl_details ()
305
- else :
306
- acls .display_acl_stat (args .all )
217
+ acls .display_acl_stat (args .all )
307
218
except Exception as e :
308
219
print (e .message , file = sys .stderr )
309
220
sys .exit (1 )
0 commit comments