def parser(cls, buf): kwargs, rest = super(BMPPeerUpNotification, cls).parser(buf) (local_address, local_port, remote_port) = struct.unpack_from(cls._PACK_STR, six.binary_type(rest)) if '.' in kwargs['peer_address']: local_address = addrconv.ipv4.bin_to_text(local_address[:4]) elif ':' in kwargs['peer_address']: local_address = addrconv.ipv6.bin_to_text(local_address) else: raise ValueError("invalid local_address: %s" % local_address) kwargs['local_address'] = local_address kwargs['local_port'] = local_port kwargs['remote_port'] = remote_port rest = rest[cls._MIN_LEN:] sent_open_msg, _, rest = BGPMessage.parser(rest) received_open_msg, _, rest = BGPMessage.parser(rest) kwargs['sent_open_message'] = sent_open_msg kwargs['received_open_message'] = received_open_msg return kwargs
def parser(cls, buf): kwargs, rest = super(BMPPeerUpNotification, cls).parser(buf) (local_address, local_port, remote_port) = struct.unpack_from(cls._PACK_STR, buffer(rest)) local_address = buffer(local_address) if '.' in kwargs['peer_address']: local_address = addrconv.ipv4.bin_to_text(local_address[:4]) elif ':' in kwargs['peer_address']: local_address = addrconv.ipv6.bin_to_text(local_address) else: raise ValueError("invalid local_address: %s" % local_address) kwargs['local_address'] = local_address kwargs['local_port'] = local_port kwargs['remote_port'] = remote_port rest = rest[cls._MIN_LEN:] sent_open_msg, rest = BGPMessage.parser(rest) received_open_msg, rest = BGPMessage.parser(rest) kwargs['sent_open_message'] = sent_open_msg kwargs['received_open_message'] = received_open_msg return kwargs
def _data_received(self, next_bytes): """Maintains buffer of bytes received from peer and extracts bgp message from this buffer if enough data is received. Validates bgp message marker, length, type and data and constructs appropriate bgp message instance and calls handler. :Parameters: - `next_bytes`: next set of bytes received from peer. """ # Append buffer with received bytes. self._recv_buff += next_bytes while True: # If current buffer size is less then minimum bgp message size, we # return as we do not have a complete bgp message to work with. if len(self._recv_buff) < BGP_MIN_MSG_LEN: return # Parse message header into elements. auth, length, ptype = BgpProtocol.parse_msg_header( self._recv_buff[:BGP_MIN_MSG_LEN]) # Check if we have valid bgp message marker. # We should get default marker since we are not supporting any # authentication. if (auth != BgpProtocol.MESSAGE_MARKER): LOG.error('Invalid message marker received: %s', auth) raise bgp.NotSync() # Check if we have valid bgp message length. check = lambda: length < BGP_MIN_MSG_LEN\ or length > BGP_MAX_MSG_LEN # RFC says: The minimum length of the OPEN message is 29 # octets (including the message header). check2 = lambda: ptype == BGP_MSG_OPEN\ and length < BGPOpen._MIN_LEN # RFC says: A KEEPALIVE message consists of only the # message header and has a length of 19 octets. check3 = lambda: ptype == BGP_MSG_KEEPALIVE\ and length != BGPKeepAlive._MIN_LEN # RFC says: The minimum length of the UPDATE message is 23 # octets. check4 = lambda: ptype == BGP_MSG_UPDATE\ and length < BGPUpdate._MIN_LEN if check() or check2() or check3() or check4(): raise bgp.BadLen(ptype, length) # If we have partial message we wait for rest of the message. if len(self._recv_buff) < length: return msg, rest = BGPMessage.parser(self._recv_buff) self._recv_buff = rest # If we have a valid bgp message we call message handler. self._handle_msg(msg)
def test_20_check_withdrawal_2(self): g1 = self.gobgp g2 = self.quaggas['g2'] dumpfile = g2.start_tcpdump() g1.add_route('10.40.0.0/24') time.sleep(1) paths = g2.get_global_rib('10.40.0.0/24') self.assertTrue(len(paths) == 1) g1.local('gobgp global rib del 10.40.0.0/24') time.sleep(1) paths = g2.get_global_rib('10.40.0.0/24') self.assertTrue(len(paths) == 0) g2.stop_tcpdump() time.sleep(1) cnt = 0 for pkt in pcap.Reader(open(dumpfile)): last = Packet(pkt[1]).protocols[-1] if type(last) == str: pkt = BGPMessage.parser(last)[0] if type(pkt) == BGPUpdate: cnt += len(pkt.withdrawn_routes) self.assertTrue(cnt == 1)
def test_20_check_withdrawal_2(self): g1 = self.gobgp g2 = self.quaggas['g2'] dumpfile = g2.start_tcpdump() g1.add_route('10.40.0.0/24') time.sleep(1) paths = g2.get_global_rib('10.40.0.0/24') self.assertTrue(len(paths) == 1) g1.local('gobgp global rib del 10.40.0.0/24') time.sleep(1) paths = g2.get_global_rib('10.40.0.0/24') self.assertTrue(len(paths) == 0) g2.stop_tcpdump() time.sleep(1) cnt = 0 for pkt in pcap.Reader(open(dumpfile)): last = Packet(pkt[1]).protocols[-1] if type(last) == str: pkt = BGPMessage.parser(last)[0] cnt += len(pkt.withdrawn_routes) self.assertTrue(cnt == 1)
def parser(cls, buf): kwargs, buf = super(BMPRouteMonitoring, cls).parser(buf) bgp_update, buf = BGPMessage.parser(buf) kwargs['bgp_update'] = bgp_update return kwargs
def parser(cls, buf): kwargs, buf = super(BMPRouteMonitoring, cls).parser(buf) bgp_update, _, buf = BGPMessage.parser(buf) kwargs['bgp_update'] = bgp_update return kwargs
def parser(cls, buf): reason, = struct.unpack_from('!B', buffer(buf)) buf = buf[struct.calcsize('!B'):] if reason == BMP_PEER_DOWN_REASON_LOCAL_BGP_NOTIFICATION: data, rest = BGPMessage.parser(buf) elif reason == BMP_PEER_DOWN_REASON_LOCAL_NO_NOTIFICATION: data = struct.unpack_from('!H', buffer(buf)) elif reason == BMP_PEER_DOWN_REASON_REMOTE_BGP_NOTIFICATION: data, rest = BGPMessage.parser(buf) elif reason == BMP_PEER_DOWN_REASON_REMOTE_NO_NOTIFICATION: data = None else: reason = BMP_PEER_DOWN_REASON_UNKNOWN data = buf kwargs = {} kwargs['reason'] = reason kwargs['data'] = data return kwargs
def parser(cls, buf): kwargs, buf = super(BMPPeerDownNotification, cls).parser(buf) reason, = struct.unpack_from('!B', six.binary_type(buf)) buf = buf[struct.calcsize('!B'):] if reason == BMP_PEER_DOWN_REASON_LOCAL_BGP_NOTIFICATION: data, _, rest = BGPMessage.parser(buf) elif reason == BMP_PEER_DOWN_REASON_LOCAL_NO_NOTIFICATION: data = struct.unpack_from('!H', six.binary_type(buf)) elif reason == BMP_PEER_DOWN_REASON_REMOTE_BGP_NOTIFICATION: data, _, rest = BGPMessage.parser(buf) elif reason == BMP_PEER_DOWN_REASON_REMOTE_NO_NOTIFICATION: data = None else: reason = BMP_PEER_DOWN_REASON_UNKNOWN data = buf kwargs['reason'] = reason kwargs['data'] = data return kwargs