Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 9 additions & 4 deletions capirca/lib/cisco.py
Original file line number Diff line number Diff line change
Expand Up @@ -698,7 +698,10 @@ def GetProtocolName(proto, af: int):
proto_name = IOSXEMap._PROTO_NAMES[af][proto]
return proto_name
except KeyError:
return proto
try:
return IOSXEMap._PROTO_NAMES[af][int(proto)]
except (KeyError, ValueError):
return proto

@staticmethod
def GetPortName(port, proto: str):
Expand Down Expand Up @@ -766,8 +769,10 @@ def __init__(self, term, af=4, proto_int=True, enable_dsmo=False,
self.text_af = 'inet'
else:
self.text_af = 'inet6'
self.ALLOWED_PROTO_STRINGS = list(self.ALLOWED_PROTO_STRINGS)
self.ALLOWED_PROTO_STRINGS.extend([self.PROTO_MAP.get(x) # pyrefly: ignore[bad-argument-type]
for x in self.ALWAYS_PROTO_NUM])
for x in self.ALWAYS_PROTO_NUM
if self.PROTO_MAP.get(x) not in self.ALLOWED_PROTO_STRINGS])

def __str__(self):
# Verify platform specific terms. Skip whole term if platform does not
Expand Down Expand Up @@ -822,7 +827,7 @@ def __str__(self):
protocol = ['hbh']
elif self.proto_int:
protocol = [proto if proto in self.ALLOWED_PROTO_STRINGS
else self.PROTO_MAP.get(proto)
else self.PROTO_MAP.get(proto, proto)
for proto in self.term.protocol]
else:
protocol = self.term.protocol
Expand Down Expand Up @@ -1225,7 +1230,7 @@ def __str__(self):

else:
protocol = [proto if proto in self.ALLOWED_PROTO_STRINGS
else self.PROTO_MAP.get(proto)
else self.PROTO_MAP.get(proto, proto)
for proto in self.term.protocol]

# addresses
Expand Down
54 changes: 54 additions & 0 deletions tests/lib/cisco_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -469,6 +469,12 @@
action:: accept
}
"""
GOOD_TERM_31_NUMERIC_PROTO = """
term good_term_31_numeric_proto {
protocol:: 50
action:: accept
}
"""

SUPPORTED_TOKENS = {
'action',
Expand Down Expand Up @@ -1893,5 +1899,53 @@ def testIcmpTypeCodeNames(self):
)


def testNumericProtocol(self):
pol = policy.ParsePolicy(
GOOD_HEADER + GOOD_TERM_31_NUMERIC_PROTO, self.naming
)
acl = cisco.Cisco(pol, EXP_INFO)
self.assertIn('permit 50 any any', str(acl))
self.assertNotIn('None', str(acl))

def testNumericProtocolObjectGroup(self):
pol = policy.ParsePolicy(
GOOD_OBJGRP_HEADER_1 + GOOD_TERM_31_NUMERIC_PROTO, self.naming
)
acl = cisco.Cisco(pol, EXP_INFO)
self.assertIn('permit 50 any any', str(acl))
self.assertNotIn('None', str(acl))

def testNumericProtocolInet6(self):
header = """
header {
target:: cisco test-filter inet6
}
"""
pol = policy.ParsePolicy(header + GOOD_TERM_31_NUMERIC_PROTO, self.naming)
acl = cisco.Cisco(pol, EXP_INFO)
self.assertIn('permit 50 any any', str(acl))
self.assertNotIn('None', str(acl))

def testNumericProtocolConfigureReplaceCompatible(self):
header = """
header {
target:: cisco test-filter extended configure_replace_compatible
}
"""
pol = policy.ParsePolicy(header + GOOD_TERM_31_NUMERIC_PROTO, self.naming)
acl = cisco.Cisco(pol, EXP_INFO)
self.assertIn('permit esp any any', str(acl))
self.assertNotIn('None', str(acl))

def testAllowedProtoStringsNotMutated(self):
before = list(cisco.Term.ALLOWED_PROTO_STRINGS)
pol = policy.ParsePolicy(
GOOD_HEADER + GOOD_TERM_31_NUMERIC_PROTO, self.naming
)
_ = cisco.Cisco(pol, EXP_INFO)
_ = cisco.Cisco(pol, EXP_INFO)
self.assertEqual(before, cisco.Term.ALLOWED_PROTO_STRINGS)


if __name__ == '__main__':
absltest.main()
Loading