diff --git a/files/image_config/caclmgrd/caclmgrd b/files/image_config/caclmgrd/caclmgrd index dee85d2e26e..0dc59766b3d 100755 --- a/files/image_config/caclmgrd/caclmgrd +++ b/files/image_config/caclmgrd/caclmgrd @@ -11,6 +11,7 @@ # try: + import ipaddr as ipaddress import os import subprocess import sys @@ -113,12 +114,22 @@ class ControlPlaneAclManager(object): # Add iptables command to delete all non-default chains iptables_cmds.append("iptables -X") + # Add same set of commands for ip6tables + iptables_cmds.append("ip6tables -P INPUT ACCEPT") + iptables_cmds.append("ip6tables -P FORWARD ACCEPT") + iptables_cmds.append("ip6tables -P OUTPUT ACCEPT") + iptables_cmds.append("ip6tables -F") + iptables_cmds.append("ip6tables -X") + # Get current ACL tables and rules from Config DB self._tables_db_info = self.config_db.get_table(self.ACL_TABLE) self._rules_db_info = self.config_db.get_table(self.ACL_RULE) # Walk the ACL tables for (table_name, table_data) in self._tables_db_info.iteritems(): + + table_ip_version = None + # Ignore non-control-plane ACL tables if table_data["type"] != self.ACL_TABLE_TYPE_CTRLPLANE: continue @@ -144,6 +155,23 @@ class ControlPlaneAclManager(object): if rule_table_name == table_name: acl_rules[rule_props["PRIORITY"]] = rule_props + # If we haven't determined the IP version for this ACL table yet, + # try to do it now. We determine heuristically based on whether the + # src IP is an IPv4 or IPv6 address. + if not table_ip_version and "SRC_IP" in rule_props and rule_props["SRC_IP"]: + ip_addr = ipaddress.IPAddress(rule_props["SRC_IP"].split("/")[0]) + if isinstance(ip_addr, ipaddress.IPv6Address): + table_ip_version = 6 + elif isinstance(ip_addr, ipaddress.IPv4Address): + table_ip_version = 4 + + # If we were unable to determine whether this ACL table contains + # IPv4 or IPv6 rules, log a message and skip processing this table. + if not table_ip_version: + log_warning("Unable to determine if ACL table '{}' contains IPv4 or IPv6 rules. Skipping table..." + .format(table_name)) + continue + # For each ACL rule in this table (in descending order of priority) for priority in sorted(acl_rules.iterkeys(), reverse=True): rule_props = acl_rules[priority] @@ -155,7 +183,8 @@ class ControlPlaneAclManager(object): # Apply the rule to the default protocol(s) for this ACL service for ip_protocol in ip_protocols: for dst_port in dst_ports: - rule_cmd = "iptables -A INPUT -p {}".format(ip_protocol) + rule_cmd = "ip6tables" if table_ip_version == 6 else "iptables" + rule_cmd += " -A INPUT -p {}".format(ip_protocol) if "SRC_IP" in rule_props and rule_props["SRC_IP"]: rule_cmd += " -s {}".format(rule_props["SRC_IP"])