def unpack (data,negotiated): communities = Communities() while data: if data and len(data) < 4: raise Notify(3,1,'could not decode community %s' % str([hex(ord(_)) for _ in data])) communities.add(Community.unpack(data[:4],negotiated)) data = data[4:] return communities
def unpack (data,negotiated): communities = Communities() while data: if data and len(data) < 4: raise Notify(3,1,'could not decode community %s' % str([hex(ord(_)) for _ in data])) communities.add(Community.unpack(data[:4],negotiated)) data = data[4:] return communities
def _community(value): separator = value.find(':') if separator > 0: prefix = value[:separator] suffix = value[separator + 1:] if not prefix.isdigit() or not suffix.isdigit(): raise ValueError('invalid community %s' % value) prefix, suffix = int(prefix), int(suffix) if prefix > Community.MAX: raise ValueError('invalid community %s (prefix too large)' % value) if suffix > Community.MAX: raise ValueError('invalid community %s (suffix too large)' % value) return Community(pack('!L', (prefix << 16) + suffix)) elif value[:2].lower() == '0x': number = long(value, 16) if number > Community.MAX: raise ValueError('invalid community %s (too large)' % value) return Community(pack('!L', number)) else: low = value.lower() if low == 'no-export': return Community(Community.NO_EXPORT) elif low == 'no-advertise': return Community(Community.NO_ADVERTISE) elif low == 'no-export-subconfed': return Community(Community.NO_EXPORT_SUBCONFED) # no-peer is not a correct syntax but I am sure someone will make the mistake :) elif low == 'nopeer' or low == 'no-peer': return Community(Community.NO_PEER) elif low == 'blackhole': return Community(Community.BLACKHOLE) elif value.isdigit(): number = int(value) if number > Community.MAX: raise ValueError('invalid community %s (too large)' % value) return Community(pack('!L', number)) else: raise ValueError('invalid community name %s' % value)
def _community(value): separator = value.find(':') if separator > 0: prefix = value[:separator] suffix = value[separator + 1:] if not prefix.isdigit() or not suffix.isdigit(): raise ValueError('invalid community %s' % value) prefix, suffix = int(prefix), int(suffix) # XXX: FIXME: add a Community.MAX to pow(2,16) -1 if prefix >= pow(2, 16): raise ValueError('invalid community %s (prefix too large)' % value) # XXX: FIXME: add a Community.MAX to pow(2,16) -1 if suffix >= pow(2, 16): raise ValueError('invalid community %s (suffix too large)' % value) return Community(pack('!L', (prefix << 16) + suffix)) elif value[:2].lower() == '0x': value = long(value, 16) # XXX: FIXME: add a Community.MAX to pow(2,16) -1 if value >= pow(2, 32): raise ValueError('invalid community %s (too large)' % value) return Community(pack('!L', value)) else: low = value.lower() if low == 'no-export': return Community(Community.NO_EXPORT) elif low == 'no-advertise': return Community(Community.NO_ADVERTISE) elif low == 'no-export-subconfed': return Community(Community.NO_EXPORT_SUBCONFED) # no-peer is not a correct syntax but I am sure someone will make the mistake :) elif low == 'nopeer' or low == 'no-peer': return Community(Community.NO_PEER) elif value.isdigit(): value = unpack('!L', value)[0] if value >= pow(2, 32): raise ValueError('invalid community %s (too large)' % value) return Community(pack('!L', value)) else: raise ValueError('invalid community name %s' % value)
def test_1_community(self): self.assertEqual(Community(256), 256)
@classmethod def unpack (cls,community,negotiated): return cls(community) @classmethod def cached (cls,community): if cls.caching and community in cls.cache: return cls.cache[community] instance = cls(community) if cls.caching: cls.cache[community] = instance return instance # Always cache well-known communities, they will be used a lot if not Community.cache: Community.cache[Community.NO_EXPORT] = Community(Community.NO_EXPORT) Community.cache[Community.NO_ADVERTISE] = Community(Community.NO_ADVERTISE) Community.cache[Community.NO_EXPORT_SUBCONFED] = Community(Community.NO_EXPORT_SUBCONFED) Community.cache[Community.NO_PEER] = Community(Community.NO_PEER) # ============================================================== Communities (8) # http://www.iana.org/assignments/bgp-extended-communities from exabgp.bgp.message.update.attribute.attribute import Attribute from exabgp.bgp.message.update.attribute.community import Community from exabgp.bgp.message.update.attribute.community.extended import ExtendedCommunity from exabgp.bgp.message.notification import Notify # Unused but required for the registration of the classes from exabgp.bgp.message.update.attribute.community.extended.encapsulation import Encapsulation