@@ -30,6 +30,17 @@ BufferMgr::BufferMgr(DBConnector *cfgDb, DBConnector *applDb, string pg_lookup_f
3030 m_applBufferEgressProfileListTable(applDb, APP_BUFFER_PORT_EGRESS_PROFILE_LIST_NAME)
3131{
3232 readPgProfileLookupFile (pg_lookup_file);
33+
34+ char *platform = getenv (" ASIC_VENDOR" );
35+ if (NULL == platform)
36+ {
37+ SWSS_LOG_WARN (" Platform environment variable is not defined" );
38+ }
39+ else
40+ {
41+ m_platform = platform;
42+ }
43+
3344 dynamic_buffer_model = false ;
3445}
3546
@@ -122,9 +133,9 @@ Create/update two tables: profile (in m_cfgBufferProfileTable) and port buffer (
122133 }
123134 }
124135*/
125- task_process_status BufferMgr::doSpeedUpdateTask (string port)
136+ task_process_status BufferMgr::doSpeedUpdateTask (string port, bool admin_up )
126137{
127- vector<FieldValueTuple> fvVector ;
138+ vector<FieldValueTuple> fvVectorPg, fvVectorProfile ;
128139 string cable;
129140 string speed;
130141
@@ -142,20 +153,50 @@ task_process_status BufferMgr::doSpeedUpdateTask(string port)
142153 }
143154
144155 speed = m_speedLookup[port];
156+
157+ string buffer_pg_key = port + m_cfgBufferPgTable.getTableNameSeparator () + LOSSLESS_PGS;
158+ // key format is pg_lossless_<speed>_<cable>_profile
159+ string buffer_profile_key = " pg_lossless_" + speed + " _" + cable + " _profile" ;
160+ string profile_ref = buffer_profile_key;
161+
162+ m_cfgBufferPgTable.get (buffer_pg_key, fvVectorPg);
163+
164+ if (!admin_up && m_platform == " mellanox" )
165+ {
166+ // Remove the entry in BUFFER_PG table if any
167+ if (!fvVectorPg.empty ())
168+ {
169+ for (auto &prop : fvVectorPg)
170+ {
171+ if (fvField (prop) == " profile" )
172+ {
173+ if (fvValue (prop) == profile_ref)
174+ {
175+ SWSS_LOG_NOTICE (" Removing PG %s from port %s which is administrative down" , buffer_pg_key.c_str (), port.c_str ());
176+ m_cfgBufferPgTable.del (buffer_pg_key);
177+ }
178+ else
179+ {
180+ SWSS_LOG_NOTICE (" Not default profile %s is configured on PG %s, won't reclaim buffer" , fvValue (prop).c_str (), buffer_pg_key.c_str ());
181+ }
182+ }
183+ }
184+ }
185+
186+ return task_process_status::task_success;
187+ }
188+
145189 if (m_pgProfileLookup.count (speed) == 0 || m_pgProfileLookup[speed].count (cable) == 0 )
146190 {
147191 SWSS_LOG_ERROR (" Unable to create/update PG profile for port %s. No PG profile configured for speed %s and cable length %s" ,
148192 port.c_str (), speed.c_str (), cable.c_str ());
149193 return task_process_status::task_invalid_entry;
150194 }
151195
152- // Crete record in BUFFER_PROFILE table
153- // key format is pg_lossless_<speed>_<cable>_profile
154- string buffer_profile_key = " pg_lossless_" + speed + " _" + cable + " _profile" ;
155-
156196 // check if profile already exists - if yes - skip creation
157- m_cfgBufferProfileTable.get (buffer_profile_key, fvVector);
158- if (fvVector.size () == 0 )
197+ m_cfgBufferProfileTable.get (buffer_profile_key, fvVectorProfile);
198+ // Create record in BUFFER_PROFILE table
199+ if (fvVectorProfile.size () == 0 )
159200 {
160201 SWSS_LOG_NOTICE (" Creating new profile '%s'" , buffer_profile_key.c_str ());
161202
@@ -170,32 +211,24 @@ task_process_status BufferMgr::doSpeedUpdateTask(string port)
170211 // profile threshold field name
171212 mode += " _th" ;
172213
173- fvVector .push_back (make_pair (" pool" , INGRESS_LOSSLESS_PG_POOL_NAME));
174- fvVector .push_back (make_pair (" xon" , m_pgProfileLookup[speed][cable].xon ));
214+ fvVectorProfile .push_back (make_pair (" pool" , INGRESS_LOSSLESS_PG_POOL_NAME));
215+ fvVectorProfile .push_back (make_pair (" xon" , m_pgProfileLookup[speed][cable].xon ));
175216 if (m_pgProfileLookup[speed][cable].xon_offset .length () > 0 ) {
176- fvVector .push_back (make_pair (" xon_offset" ,
217+ fvVectorProfile .push_back (make_pair (" xon_offset" ,
177218 m_pgProfileLookup[speed][cable].xon_offset ));
178219 }
179- fvVector .push_back (make_pair (" xoff" , m_pgProfileLookup[speed][cable].xoff ));
180- fvVector .push_back (make_pair (" size" , m_pgProfileLookup[speed][cable].size ));
181- fvVector .push_back (make_pair (mode, m_pgProfileLookup[speed][cable].threshold ));
182- m_cfgBufferProfileTable.set (buffer_profile_key, fvVector );
220+ fvVectorProfile .push_back (make_pair (" xoff" , m_pgProfileLookup[speed][cable].xoff ));
221+ fvVectorProfile .push_back (make_pair (" size" , m_pgProfileLookup[speed][cable].size ));
222+ fvVectorProfile .push_back (make_pair (mode, m_pgProfileLookup[speed][cable].threshold ));
223+ m_cfgBufferProfileTable.set (buffer_profile_key, fvVectorProfile );
183224 }
184225 else
185226 {
186227 SWSS_LOG_NOTICE (" Reusing existing profile '%s'" , buffer_profile_key.c_str ());
187228 }
188229
189- fvVector.clear ();
190-
191- string buffer_pg_key = port + m_cfgBufferPgTable.getTableNameSeparator () + LOSSLESS_PGS;
192-
193- string profile_ref = buffer_profile_key;
194-
195230 /* Check if PG Mapping is already then log message and return. */
196- m_cfgBufferPgTable.get (buffer_pg_key, fvVector);
197-
198- for (auto & prop : fvVector)
231+ for (auto & prop : fvVectorPg)
199232 {
200233 if ((fvField (prop) == " profile" ) && (profile_ref == fvValue (prop)))
201234 {
@@ -204,10 +237,10 @@ task_process_status BufferMgr::doSpeedUpdateTask(string port)
204237 }
205238 }
206239
207- fvVector .clear ();
240+ fvVectorPg .clear ();
208241
209- fvVector .push_back (make_pair (" profile" , profile_ref));
210- m_cfgBufferPgTable.set (buffer_pg_key, fvVector );
242+ fvVectorPg .push_back (make_pair (" profile" , profile_ref));
243+ m_cfgBufferPgTable.set (buffer_pg_key, fvVectorPg );
211244 return task_process_status::task_success;
212245}
213246
@@ -379,26 +412,35 @@ void BufferMgr::doTask(Consumer &consumer)
379412 task_process_status task_status = task_process_status::task_success;
380413 if (op == SET_COMMAND)
381414 {
382- for ( auto i : kfvFieldsValues (t) )
415+ if (table_name == CFG_PORT_CABLE_LEN_TABLE_NAME )
383416 {
384- if (table_name == CFG_PORT_CABLE_LEN_TABLE_NAME)
417+ // receive and cache cable length table
418+ for (auto i : kfvFieldsValues (t))
385419 {
386- // receive and cache cable length table
387420 task_status = doCableTask (fvField (i), fvValue (i));
388421 }
389- if (m_pgfile_processed && table_name == CFG_PORT_TABLE_NAME && (fvField (i) == " speed" || fvField (i) == " admin_status" ))
422+ }
423+ else if (m_pgfile_processed && table_name == CFG_PORT_TABLE_NAME)
424+ {
425+ bool admin_up = false ;
426+ for (auto i : kfvFieldsValues (t))
390427 {
391428 if (fvField (i) == " speed" )
392429 {
393430 m_speedLookup[port] = fvValue (i);
394431 }
395-
396- if (m_speedLookup.count (port) != 0 )
432+ if (fvField (i) == " admin_status" )
397433 {
398- // create/update profile for port
399- task_status = doSpeedUpdateTask (port);
434+ admin_up = (" up" == fvValue (i));
400435 }
401436 }
437+
438+ if (m_speedLookup.count (port) != 0 )
439+ {
440+ // create/update profile for port
441+ task_status = doSpeedUpdateTask (port, admin_up);
442+ }
443+
402444 if (task_status != task_process_status::task_success)
403445 {
404446 break ;
0 commit comments