2929 sai_thrift_read_pg_shared_watermark ,
3030 sai_thrift_read_buffer_pool_watermark ,
3131 sai_thrift_read_headroom_pool_watermark ,
32+ sai_thrift_read_queue_occupancy ,
3233 sai_thrift_port_tx_disable ,
3334 sai_thrift_port_tx_enable )
3435from switch_sai_thrift .ttypes import (sai_thrift_attribute_value_t ,
@@ -146,6 +147,21 @@ def get_counter_names(sonic_version):
146147
147148 return ingress_counters , egress_counters
148149
150+ def fill_leakout_plus_one (test_case , src_port_id , dst_port_id , pkt , queue , asic_type ):
151+ # Attempts to queue 1 packet while compensating for a varying packet leakout.
152+ # Returns whether 1 packet was successfully enqueued.
153+ if asic_type in ['cisco-8000' ]:
154+ queue_counters_base = sai_thrift_read_queue_occupancy (test_case .client , dst_port_id )
155+ max_packets = 100
156+ for packet_i in range (max_packets ):
157+ send_packet (test_case , src_port_id , pkt , 1 )
158+ queue_counters = sai_thrift_read_queue_occupancy (test_case .client , dst_port_id )
159+ if queue_counters [queue ] > queue_counters_base [queue ]:
160+ print >> sys .stderr , "fill_leakout_plus_one: Success, sent %d packets, queue occupancy bytes rose from %d to %d" % (packet_i + 1 , queue_counters_base [queue ], queue_counters [queue ])
161+ return True
162+ return False
163+
164+
149165class ARPpopulate (sai_base_test .ThriftInterfaceDataPlane ):
150166 def setUp (self ):
151167 sai_base_test .ThriftInterfaceDataPlane .setUp (self )
@@ -2222,12 +2238,24 @@ def runTest(self):
22222238 buf_pool_roid = int (self .test_params ['buf_pool_roid' ], 0 )
22232239 print >> sys .stderr , "buf_pool_roid: 0x%lx" % (buf_pool_roid )
22242240
2241+ buffer_pool_wm_base = 0
2242+ if 'cisco-8000' in asic_type :
2243+ # Some small amount of memory is always occupied
2244+ buffer_pool_wm_base = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid )
2245+
22252246 # Prepare TCP packet data
22262247 tos = dscp << 2
22272248 tos |= ecn
22282249 ttl = 64
2229- default_packet_length = 64
2230- pkt = simple_tcp_packet (pktlen = default_packet_length ,
2250+
2251+ if 'packet_size' in self .test_params .keys ():
2252+ packet_length = int (self .test_params ['packet_size' ])
2253+ else :
2254+ packet_length = 64
2255+
2256+ cell_occupancy = (packet_length + cell_size - 1 ) / cell_size
2257+
2258+ pkt = simple_tcp_packet (pktlen = packet_length ,
22312259 eth_dst = router_mac if router_mac != '' else dst_port_mac ,
22322260 eth_src = src_port_mac ,
22332261 ip_src = src_port_ip ,
@@ -2237,15 +2265,19 @@ def runTest(self):
22372265 # Add slight tolerance in threshold characterization to consider
22382266 # the case that cpu puts packets in the egress queue after we pause the egress
22392267 # or the leak out is simply less than expected as we have occasionally observed
2240- upper_bound_margin = 2
2241- # On TD2, we found the watermark value is always short of the expected
2242- # value by 1
2243- lower_bound_margin = 1
2268+ upper_bound_margin = 2 * cell_occupancy
2269+ if 'cisco-8000' in asic_type :
2270+ lower_bound_margin = 2 * cell_occupancy
2271+ else :
2272+ # On TD2, we found the watermark value is always short of the expected
2273+ # value by 1
2274+ lower_bound_margin = 1
2275+
22442276 # On TH2 using scheduler-based TX enable, we find the Q min being inflated
22452277 # to have 0x10 = 16 cells. This effect is captured in lossy traffic ingress
22462278 # buffer pool test and lossy traffic egress buffer pool test to illusively
22472279 # have extra capacity in the buffer pool space
2248- extra_cap_margin = 8
2280+ extra_cap_margin = 8 * cell_occupancy
22492281
22502282 # Adjust the methodology to enable TX for each incremental watermark value test
22512283 # To this end, send the total # of packets instead of the incremental amount
@@ -2266,7 +2298,7 @@ def runTest(self):
22662298 send_packet (self , src_port_id , pkt , pkts_num_to_send )
22672299 sai_thrift_port_tx_enable (self .client , asic_type , [dst_port_id ])
22682300 time .sleep (8 )
2269- buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid )
2301+ buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid ) - buffer_pool_wm_base
22702302 print >> sys .stderr , "Init pkts num sent: %d, min: %d, actual watermark value to start: %d" % ((pkts_num_leak_out + pkts_num_fill_min ), pkts_num_fill_min , buffer_pool_wm )
22712303 if pkts_num_fill_min :
22722304 assert (buffer_pool_wm <= upper_bound_margin * cell_size )
@@ -2281,22 +2313,31 @@ def runTest(self):
22812313 # send packet batch of fixed packet numbers to fill shared
22822314 # first round sends only 1 packet
22832315 expected_wm = 0
2284- total_shared = pkts_num_fill_shared - pkts_num_fill_min
2285- pkts_inc = total_shared >> 2
2286- pkts_num = 1 + upper_bound_margin
2316+ total_shared = (pkts_num_fill_shared - pkts_num_fill_min ) * cell_occupancy
2317+ pkts_inc = (total_shared >> 2 ) // cell_occupancy
2318+ if 'cisco-8000' in asic_type :
2319+ # No additional packet margin needed while sending,
2320+ # but small margin still needed during boundary checks below
2321+ pkts_num = 1
2322+ else :
2323+ pkts_num = (1 + upper_bound_margin ) // cell_occupancy
22872324 while (expected_wm < total_shared ):
2288- expected_wm += pkts_num
2325+ expected_wm += pkts_num * cell_occupancy
22892326 if (expected_wm > total_shared ):
2290- pkts_num -= (expected_wm - total_shared )
2327+ pkts_num -= (expected_wm - total_shared + cell_occupancy - 1 ) // cell_occupancy
22912328 expected_wm = total_shared
22922329 print >> sys .stderr , "pkts num to send: %d, total pkts: %d, shared: %d" % (pkts_num , expected_wm , total_shared )
22932330
22942331 sai_thrift_port_tx_disable (self .client , asic_type , [dst_port_id ])
22952332 pkts_num_to_send += pkts_num
2296- send_packet (self , src_port_id , pkt , pkts_num_to_send )
2333+ if 'cisco-8000' in asic_type :
2334+ assert (fill_leakout_plus_one (self , src_port_id , dst_port_id , pkt , queue , asic_type ))
2335+ send_packet (self , src_port_id , pkt , pkts_num_to_send - 1 )
2336+ else :
2337+ send_packet (self , src_port_id , pkt , pkts_num_to_send )
22972338 sai_thrift_port_tx_enable (self .client , asic_type , [dst_port_id ])
22982339 time .sleep (8 )
2299- buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid )
2340+ buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid ) - buffer_pool_wm_base
23002341 print >> sys .stderr , "lower bound (-%d): %d, actual value: %d, upper bound (+%d): %d" % (lower_bound_margin , (expected_wm - lower_bound_margin )* cell_size , buffer_pool_wm , upper_bound_margin , (expected_wm + upper_bound_margin ) * cell_size )
23012342 assert (buffer_pool_wm <= (expected_wm + upper_bound_margin ) * cell_size )
23022343 assert ((expected_wm - lower_bound_margin )* cell_size <= buffer_pool_wm )
@@ -2306,10 +2347,15 @@ def runTest(self):
23062347 # overflow the shared pool
23072348 sai_thrift_port_tx_disable (self .client , asic_type , [dst_port_id ])
23082349 pkts_num_to_send += pkts_num
2309- send_packet (self , src_port_id , pkt , pkts_num_to_send )
2350+ if 'cisco-8000' in asic_type :
2351+ assert (fill_leakout_plus_one (self , src_port_id , dst_port_id , pkt , queue , asic_type ))
2352+ send_packet (self , src_port_id , pkt , pkts_num_to_send - 1 )
2353+ else :
2354+ send_packet (self , src_port_id , pkt , pkts_num_to_send )
2355+
23102356 sai_thrift_port_tx_enable (self .client , asic_type , [dst_port_id ])
23112357 time .sleep (8 )
2312- buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid )
2358+ buffer_pool_wm = sai_thrift_read_buffer_pool_watermark (self .client , buf_pool_roid ) - buffer_pool_wm_base
23132359 print >> sys .stderr , "exceeded pkts num sent: %d, expected watermark: %d, actual value: %d" % (pkts_num , (expected_wm * cell_size ), buffer_pool_wm )
23142360 assert (expected_wm == total_shared )
23152361 assert ((expected_wm - lower_bound_margin )* cell_size <= buffer_pool_wm )
0 commit comments