Skip to content

Commit 6cbec6b

Browse files
authored
[multi-ASIC] CRM show/config commands changes for multi-asic (#1127)
- What I did Updated the CRM show/config commands to handle the multi-ASIC platforms. - How I did it The threshold values configured by user is programmed in the CONFIG_DB in all the namespaces. While show/displaying the thresholds, it is retrieved from the database docker in case of single asic, and from the first namespace docker eg: database0 in case of multi-asic platforms. The crm resources usage details are retrieved from the databases in the respective namespaces and displayed with the additional "ASIC name" as a header. - How to verify it Verified on the single and multi-asic devices.
1 parent b693cf6 commit 6cbec6b

File tree

9 files changed

+1819
-45
lines changed

9 files changed

+1819
-45
lines changed

crm/main.py

+99-44
Original file line numberDiff line numberDiff line change
@@ -3,28 +3,39 @@
33
import click
44
import swsssdk
55
from tabulate import tabulate
6+
from utilities_common import multi_asic as multi_asic_util
7+
from sonic_py_common import multi_asic
68

79
class Crm:
8-
def __init__(self):
10+
def __init__(self, db=None):
911
self.cli_mode = None
1012
self.addr_family = None
1113
self.res_type = None
14+
self.db = None
15+
self.cfgdb = db
16+
self.multi_asic = multi_asic_util.MultiAsic()
1217

18+
@multi_asic_util.run_on_multi_asic
1319
def config(self, attr, val):
1420
"""
1521
CRM handler for 'config' CLI commands.
1622
"""
17-
configdb = swsssdk.ConfigDBConnector()
18-
configdb.connect()
19-
20-
configdb.mod_entry("CRM", 'Config', {attr: val})
23+
if self.cfgdb:
24+
self.config_db = self.cfgdb
25+
self.config_db.mod_entry("CRM", 'Config', {attr: val})
2126

2227
def show_summary(self):
2328
"""
2429
CRM Handler to display general information.
2530
"""
26-
configdb = swsssdk.ConfigDBConnector()
27-
configdb.connect()
31+
32+
configdb = self.cfgdb
33+
if configdb is None:
34+
# Get the namespace list
35+
namespaces = multi_asic.get_namespace_list()
36+
37+
configdb = swsssdk.ConfigDBConnector(namespace=namespaces[0])
38+
configdb.connect()
2839

2940
crm_info = configdb.get_entry('CRM', 'Config')
3041

@@ -37,8 +48,14 @@ def show_thresholds(self, resource):
3748
"""
3849
CRM Handler to display thresholds information.
3950
"""
40-
configdb = swsssdk.ConfigDBConnector()
41-
configdb.connect()
51+
52+
configdb = self.cfgdb
53+
if configdb is None:
54+
# Get the namespace list
55+
namespaces = multi_asic.get_namespace_list()
56+
57+
configdb = swsssdk.ConfigDBConnector(namespace=namespaces[0])
58+
configdb.connect()
4259

4360
crm_info = configdb.get_entry('CRM', 'Config')
4461

@@ -60,16 +77,11 @@ def show_thresholds(self, resource):
6077
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
6178
click.echo()
6279

63-
def show_resources(self, resource):
80+
def get_resources(self, resource):
6481
"""
65-
CRM Handler to display resources information.
82+
CRM Handler to get resources information.
6683
"""
67-
countersdb = swsssdk.SonicV2Connector(host='127.0.0.1')
68-
countersdb.connect(countersdb.COUNTERS_DB)
69-
70-
crm_stats = countersdb.get_all(countersdb.COUNTERS_DB, 'CRM:STATS')
71-
72-
header = ("Resource Name", "Used Count", "Available Count")
84+
crm_stats = self.db.get_all(self.db.COUNTERS_DB, 'CRM:STATS')
7385
data = []
7486

7587
if crm_stats:
@@ -79,26 +91,18 @@ def show_resources(self, resource):
7991
data.append([res, crm_stats['crm_stats_' + res + "_used"], crm_stats['crm_stats_' + res + "_available"]])
8092
else:
8193
data.append([resource, crm_stats['crm_stats_' + resource + "_used"], crm_stats['crm_stats_' + resource + "_available"]])
82-
else:
83-
click.echo('\nCRM counters are not ready. They would be populated after the polling interval.')
8494

85-
click.echo()
86-
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
87-
click.echo()
95+
return data
8896

89-
def show_acl_resources(self):
97+
def get_acl_resources(self):
9098
"""
91-
CRM Handler to display ACL recources information.
99+
CRM Handler to get ACL recources information.
92100
"""
93-
countersdb = swsssdk.SonicV2Connector(host='127.0.0.1')
94-
countersdb.connect(countersdb.COUNTERS_DB)
95-
96-
header = ("Stage", "Bind Point", "Resource Name", "Used Count", "Available Count")
97101
data = []
98102

99103
for stage in ["INGRESS", "EGRESS"]:
100104
for bind_point in ["PORT", "LAG", "VLAN", "RIF", "SWITCH"]:
101-
crm_stats = countersdb.get_all(countersdb.COUNTERS_DB, 'CRM:ACL_STATS:{0}:{1}'.format(stage, bind_point))
105+
crm_stats = self.db.get_all(self.db.COUNTERS_DB, 'CRM:ACL_STATS:{0}:{1}'.format(stage, bind_point))
102106

103107
if crm_stats:
104108
for res in ["acl_group", "acl_table"]:
@@ -108,51 +112,102 @@ def show_acl_resources(self):
108112
crm_stats['crm_stats_' + res + "_available"]
109113
])
110114

111-
click.echo()
112-
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
113-
click.echo()
114-
115-
def show_acl_table_resources(self):
115+
return data
116+
def get_acl_table_resources(self):
116117
"""
117118
CRM Handler to display ACL table information.
118119
"""
119-
countersdb = swsssdk.SonicV2Connector(host='127.0.0.1')
120-
countersdb.connect(countersdb.COUNTERS_DB)
121-
122-
header = ("Table ID", "Resource Name", "Used Count", "Available Count")
123-
124120
# Retrieve all ACL table keys from CRM:ACL_TABLE_STATS
125-
crm_acl_keys = countersdb.keys(countersdb.COUNTERS_DB, 'CRM:ACL_TABLE_STATS*')
121+
crm_acl_keys = self.db.keys(self.db.COUNTERS_DB, 'CRM:ACL_TABLE_STATS*')
122+
data = []
126123

127124
for key in crm_acl_keys or [None]:
128-
data = []
129-
130125
if key:
131126
id = key.replace('CRM:ACL_TABLE_STATS:', '')
132127

133-
crm_stats = countersdb.get_all(countersdb.COUNTERS_DB, key)
128+
crm_stats = self.db.get_all(self.db.COUNTERS_DB, key)
134129

135130
for res in ['acl_entry', 'acl_counter']:
136131
if ('crm_stats_' + res + '_used' in crm_stats) and ('crm_stats_' + res + '_available' in crm_stats):
137132
data.append([id, res, crm_stats['crm_stats_' + res + '_used'], crm_stats['crm_stats_' + res + '_available']])
138133

134+
return data
135+
136+
@multi_asic_util.run_on_multi_asic
137+
def show_resources(self, resource):
138+
"""
139+
CRM Handler to display resources information.
140+
"""
141+
if multi_asic.is_multi_asic():
142+
header = (self.multi_asic.current_namespace.upper() + "\n\nResource Name", "\n\nUsed Count", "\n\nAvailable Count")
143+
err_msg = '\nCRM counters are not ready for '+ self.multi_asic.current_namespace.upper() + '. They would be populated after the polling interval.'
144+
else:
145+
header = ("Resource Name", "Used Count", "Available Count")
146+
err_msg = '\nCRM counters are not ready. They would be populated after the polling interval.'
147+
148+
data = []
149+
data = self.get_resources(resource)
150+
151+
if data:
139152
click.echo()
140153
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
141154
click.echo()
155+
else:
156+
click.echo(err_msg)
157+
158+
@multi_asic_util.run_on_multi_asic
159+
def show_acl_resources(self):
160+
"""
161+
CRM Handler to display ACL recources information.
162+
"""
163+
164+
if multi_asic.is_multi_asic():
165+
header = (self.multi_asic.current_namespace.upper() + "\n\nStage", "\n\nBind Point", "\n\nResource Name", "\n\nUsed Count", "\n\nAvailable Count")
166+
else:
167+
header = ("Stage", "Bind Point", "Resource Name", "Used Count", "Available Count")
168+
169+
data = []
170+
data = self.get_acl_resources()
171+
172+
click.echo()
173+
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
174+
click.echo()
142175

176+
@multi_asic_util.run_on_multi_asic
177+
def show_acl_table_resources(self):
178+
"""
179+
CRM Handler to display ACL table information.
180+
"""
181+
if multi_asic.is_multi_asic():
182+
header = (self.multi_asic.current_namespace.upper() + "\n\nTable ID", "\n\nResource Name", "\n\nUsed Count", "\n\nAvailable Count")
183+
else:
184+
header = ("Table ID", "Resource Name", "Used Count", "Available Count")
185+
186+
data = []
187+
data = self.get_acl_table_resources()
188+
189+
click.echo()
190+
click.echo(tabulate(data, headers=header, tablefmt="simple", missingval=""))
191+
click.echo()
143192

144193
@click.group()
145194
@click.pass_context
146195
def cli(ctx):
147196
"""
148197
Utility entry point.
149198
"""
199+
# Use the db object if given as input.
200+
db = None if ctx.obj is None else ctx.obj.cfgdb
201+
150202
context = {
151-
"crm": Crm()
203+
"crm": Crm(db)
152204
}
153205

154206
ctx.obj = context
155207

208+
# Load the global config file database_global.json once.
209+
swsssdk.SonicDBConfig.load_sonic_global_db_config()
210+
156211
@cli.group()
157212
@click.pass_context
158213
def config(ctx):

0 commit comments

Comments
 (0)