@@ -173,8 +173,8 @@ def sndrcv(pks, pkt, timeout=None, inter=0, verbose=None, chainCC=False,
173173 timeout: how much time to wait after the last packet has been sent
174174 verbose: set verbosity level
175175 multi: whether to accept multiple answers for the same stimulus"""
176- if not isinstance (pkt , Gen ):
177- pkt = SetGen ( pkt )
176+ is_single = isinstance (pkt , Gen )
177+ pkts = [ pkt ] if is_single else pkt
178178 if verbose is None :
179179 verbose = conf .verb
180180 debug .recv = plist .PacketList ([],"Unanswered" )
@@ -183,15 +183,16 @@ def sndrcv(pks, pkt, timeout=None, inter=0, verbose=None, chainCC=False,
183183 nbrecv = 0
184184 ans = []
185185 # do it here to fix random fields, so that parent and child have the same
186- tobesent = [p for p in pkt ]
186+ tobesent = [p for p in ( pkt if is_single else SetGen ( pkt )) ]
187187 notans = len (tobesent )
188188
189189 if retry < 0 :
190- retry = - retry
191- autostop = retry
190+ autostop = retry = - retry
192191 else :
193192 autostop = 0
194193
194+ for pkt in pkts :
195+ pkt .sent_time = None
195196 while retry >= 0 :
196197 if timeout is not None and timeout < 0 :
197198 timeout = None
@@ -207,18 +208,28 @@ def sndrcv(pks, pkt, timeout=None, inter=0, verbose=None, chainCC=False,
207208 (rcv_pks or pks ), tobesent , stopevent , nbrecv , notans , verbose , chainCC , multi ,
208209 )
209210 thread .join ()
211+
210212 ans .extend (newans )
213+ to_set_time = [pkt for pkt in pkts if pkt .sent_time is None ]
214+ if to_set_time :
215+ try :
216+ sent_time = min (p .sent_time for p in tobesent if getattr (p , "sent_time" , None ))
217+ except ValueError :
218+ pass
219+ else :
220+ for pkt in to_set_time :
221+ pkt .sent_time = sent_time
211222
212- remain = list (itertools .chain (* six .itervalues (hsent )))
213- if multi :
214- remain = [p for p in remain if not hasattr (p , '_answered' )]
223+ remain = itertools .chain (* six .itervalues (hsent ))
224+ remain = [p for p in remain if not hasattr (p , '_answered' )] if multi else list (remain )
215225
216- if autostop and len (remain ) > 0 and len (remain ) != len (tobesent ):
226+ if not remain :
227+ break
228+
229+ if autostop and len (remain ) != len (tobesent ):
217230 retry = autostop
218231
219232 tobesent = remain
220- if len (tobesent ) == 0 :
221- break
222233 retry -= 1
223234
224235 if conf .debug_match :
@@ -497,9 +508,9 @@ def srploop(pkts, *args, **kargs):
497508def sndrcvflood (pks , pkt , inter = 0 , verbose = None , chainCC = False , prn = lambda x : x ):
498509 if not verbose :
499510 verbose = conf .verb
500- if not isinstance (pkt , Gen ):
501- pkt = SetGen ( pkt )
502- tobesent = [p for p in pkt ]
511+ is_single = isinstance (pkt , Gen )
512+ pkts = [ pkt ] if is_single else pkt
513+ tobesent = [p for p in ( pkt if is_single else SetGen ( pkt )) ]
503514
504515 stopevent = threading .Event ()
505516 count_packets = six .moves .queue .Queue ()
@@ -515,6 +526,8 @@ def send_in_loop(tobesent, stopevent, count_packets=count_packets):
515526
516527 infinite_gen = send_in_loop (tobesent , stopevent )
517528
529+ for pkt in pkts :
530+ pkt .sent_time = None
518531 # We don't use _sndrcv_snd verbose (it messes the logs up as in a thread that ends after recieving)
519532 thread = threading .Thread (
520533 target = _sndrcv_snd ,
@@ -524,9 +537,19 @@ def send_in_loop(tobesent, stopevent, count_packets=count_packets):
524537
525538 hsent , ans , nbrecv , notans = _sndrcv_rcv (pks , tobesent , stopevent , 0 , len (tobesent ), verbose , chainCC , False )
526539 thread .join ()
540+
541+ ans = [(x , prn (y )) for (x , y ) in ans ] # Apply prn
542+ to_set_time = [pkt for pkt in pkts if pkt .sent_time is None ]
543+ if to_set_time :
544+ try :
545+ sent_time = min (p .sent_time for p in tobesent if getattr (p , "sent_time" , None ))
546+ except ValueError :
547+ pass
548+ else :
549+ for pkt in to_set_time :
550+ pkt .sent_time = sent_time
551+
527552 remain = list (itertools .chain (* six .itervalues (hsent )))
528- # Apply prn
529- ans = [(x , prn (y )) for (x , y ) in ans ]
530553
531554 if verbose :
532555 print ("\n Received %i packets, got %i answers, remaining %i packets. Sent a total of %i packets." % (nbrecv + len (ans ), len (ans ), notans , count_packets .qsize ()))
0 commit comments