def poll(self, device_number=0, port_number=None, timeout=-1, exp_pkt=None, filters=[]): """ Poll one or all dataplane ports for a packet If port_number is given, get the oldest packet from that port (and for that device). Otherwise, find the port with the oldest packet and return that packet. If exp_pkt is true, discard all packets until that one is found @param device_number Get packet from this device @param port_number If set, get packet from this port @param timeout If positive and no packet is available, block until a packet is received or for this many seconds @param exp_pkt If not None, look for this packet and ignore any others received. Note that if port_number is None, all packets from all ports will be discarded until the exp_pkt is found @return The tuple device_number, port_number, packet, pkt_time where packet is received from device_number, port_number at time pkt_time. If a timeout occurs, return None, None, None, None """ def filter_check(pkt): for f in filters: if not f(pkt): return False return True if exp_pkt and (port_number is None): self.logger.warn("Dataplane poll with exp_pkt but no port number") # Retrieve the packet. Returns (device number, port number, packet, time). def grab(): self.logger.debug("Grabbing packet") for (rcv_port_number, pkt, time) in self.packets(device_number, port_number): rcv_device_number = device_number self.logger.debug("Checking packet from device %d, port %d", rcv_device_number, rcv_port_number) if not filter_check(pkt): self.logger.debug("Paket does not match filter, discarding") continue if not exp_pkt or match_exp_pkt(exp_pkt, pkt): return (rcv_device_number, rcv_port_number, pkt, time) self.logger.debug("Did not find packet") return None with self.cvar: ret = ptfutils.timed_wait(self.cvar, grab, timeout=timeout) if ret != None: return ret else: self.logger.debug("Poll time out, no packet from device %d, port %r", device_number, port_number) return (None, None, None, None)
def poll(self, device_number=0, port_number=None, timeout=-1, exp_pkt=None, filters=[]): """ Poll one or all dataplane ports for a packet If port_number is given, get the oldest packet from that port (and for that device). Otherwise, find the port with the oldest packet and return that packet. If exp_pkt is true, discard all packets until that one is found @param device_number Get packet from this device @param port_number If set, get packet from this port @param timeout If positive and no packet is available, block until a packet is received or for this many seconds @param exp_pkt If not None, look for this packet and ignore any others received. Note that if port_number is None, all packets from all ports will be discarded until the exp_pkt is found @return A PollSuccess object on success, or a PollFailure object on failure. See the definitions of those classes for more details. """ def filter_check(pkt): for f in filters: if not f(pkt): return False return True if exp_pkt and (port_number is None): self.logger.warn("Dataplane poll with exp_pkt but no port number") # A nested function can't assign to variables in its enclosing function # in Python 2, so the conventional hack is to put them in a dict. grab_log = { # A ring buffer to hold recent non-matching packets. 'recent_packets': deque(maxlen=DataPlane.POLL_MAX_RECENT_PACKETS), # A count of the total packets received. Since 'recent_packets' is a # ring buffer, we can't simply check its length. 'packet_count': 0 } # Retrieve the packet. Returns (device number, port number, packet, time). def grab(): self.logger.debug("Grabbing packet") for (rcv_port_number, pkt, time) in self.packets(device_number, port_number): rcv_device_number = device_number grab_log['recent_packets'].append(pkt) grab_log['packet_count'] += 1 self.logger.debug("Checking packet from device %d, port %d", rcv_device_number, rcv_port_number) if not filter_check(pkt): self.logger.debug( "Paket does not match filter, discarding") continue if not exp_pkt or match_exp_pkt(exp_pkt, pkt): return DataPlane.PollSuccess(rcv_device_number, rcv_port_number, pkt, exp_pkt, time) self.logger.debug("Did not find packet") return None with self.cvar: ret = ptfutils.timed_wait(self.cvar, grab, timeout=timeout) if ret is None: self.logger.debug( "Poll timeout, no packet from device %d, port %r", device_number, port_number) return DataPlane.PollFailure(exp_pkt, grab_log['recent_packets'], grab_log['packet_count']) return ret