diff --git a/vpp/reconciler.py b/vpp/reconciler.py
index fbe219b..b46f87c 100644
--- a/vpp/reconciler.py
+++ b/vpp/reconciler.py
@@ -721,67 +721,94 @@ class Reconciler():
         return ret
 
     def sync_bondethernets(self):
-        for idx, bond in self.vpp.config['bondethernets'].items():
-            vpp_ifname = bond.interface_name
-            config_bond_ifname, config_bond_iface = bondethernet.get_by_name(self.cfg, vpp_ifname)
+        for ifname in bondethernet.get_bondethernets(self.cfg):
+            if ifname in self.vpp.config['interface_names']:
+                vpp_bond_sw_if_index = self.vpp.config['interface_names'][ifname].sw_if_index
+                vpp_members = [self.vpp.config['interfaces'][x].interface_name for x in self.vpp.config['bondethernet_members'][vpp_bond_sw_if_index]]
+            else:
+                ## New BondEthernet
+                vpp_members = []
+
+            config_bond_ifname, config_bond_iface = bondethernet.get_by_name(self.cfg, ifname)
             if not 'interfaces' in config_bond_iface:
                 continue
-            bond_iface = self.vpp.config['interfaces'][bond.sw_if_index]
-            config_mtu = interface.get_mtu(self.cfg, config_bond_ifname)
-            bondmac = bond_iface.l2_address
-            bondmac_changed = False
+            config_ifname, config_iface = interface.get_by_name(self.cfg, ifname)
+            bondmac = None
             for member_ifname in sorted(config_bond_iface['interfaces']):
+                member_ifname, member_iface = interface.get_by_name(self.cfg, member_ifname)
                 member_iface = self.vpp.config['interface_names'][member_ifname]
-                if not member_iface.sw_if_index in self.vpp.config['bondethernet_members'][bond.sw_if_index]:
-                    if bond.members == 0 and member_iface.l2_address != bondmac:
-                        bondmac_changed = True
+                if not member_ifname in vpp_members:
+                    if len(vpp_members) == 0:
                         bondmac = member_iface.l2_address
-                    self.logger.info("1> bond add %s %s" % (vpp_ifname, member_iface.interface_name))
-
-            config_ifname, config_iface = interface.get_by_name(self.cfg, vpp_ifname)
-            if bondmac_changed and 'lcp' in config_iface:
+                    self.logger.info("1> bond add %s %s" % (config_bond_ifname, member_iface.interface_name))
+            if bondmac and 'lcp' in config_iface:
                 ## TODO(pim) - Ensure LCP has the same MAC as the BondEthernet
                 ## VPP, when creating a BondEthernet, will give it an ephemeral MAC. Then, when the
                 ## first member is enslaved, the MAC address changes to that of the first member.
                 ## However, LinuxCP does not propagate this change to the Linux side (because there
                 ## is no API callback for MAC address changes). To ensure consistency, every time we
                 ## sync members, we ought to ensure the Linux device has the same MAC as its BondEthernet.
-                self.logger.info("5> comment { ip link set %s address %s }" % (config_iface['lcp'], str(bondmac)))
+                self.logger.info("2> comment { ip link set %s address %s }" % (config_iface['lcp'], str(bondmac)))
         return True
 
     def sync_bridgedomains(self):
-        for idx, bridge in self.vpp.config['bridgedomains'].items():
-            bridge_sw_if_index_list = [x.sw_if_index for x in bridge.sw_if_details]
-            config_bridge_ifname, config_bridge_iface = bridgedomain.get_by_name(self.cfg, "bd%d"%idx)
+        for ifname in bridgedomain.get_bridgedomains(self.cfg):
+            instance = int(ifname[2:])
+            if instance in self.vpp.config['bridgedomains']:
+                vpp_bridge = self.vpp.config['bridgedomains'][instance]
+                bvi_sw_if_index = vpp_bridge.bvi_sw_if_index
+                bridge_sw_if_index_list = [x.sw_if_index for x in vpp_bridge.sw_if_details]
+                bridge_members = [self.vpp.config['interfaces'][x].interface_name for x in bridge_sw_if_index_list]
+            else:
+                ## New BridgeDomain
+                bvi_sw_if_index = -1
+                bridge_members = []
+
+            config_bridge_ifname, config_bridge_iface = bridgedomain.get_by_name(self.cfg, "bd%d"%instance)
             if 'lcp' in config_bridge_iface:
-                bviname = "bvi%d" % idx
-                bvi_iface = self.vpp.config['interface_names'][bviname]
-                if bvi_iface.sw_if_index != bridge.bvi_sw_if_index:
-                    self.logger.info("1> set interface l2 bridge bvi%d %d bvi" % (idx, idx))
+                bviname = "bvi%d" % instance
+                if not bviname in bridge_members:
+                    self.logger.info("1> set interface l2 bridge bvi%d %d bvi" % (instance, instance))
             if not 'interfaces' in config_bridge_iface:
                 continue
             for member_ifname in config_bridge_iface['interfaces']:
-                member_iface = self.vpp.config['interface_names'][member_ifname]
-                if not member_iface.sw_if_index in bridge_sw_if_index_list:
-                    self.logger.info("2> set interface l2 bridge %s %d" % (member_ifname, idx))
-                    if member_iface.sub_number_of_tags > 0:
-                        self.logger.info("3> set interface l2 tag-rewrite %s pop %d" % (member_ifname, member_iface.sub_number_of_tags))
+                member_ifname, member_iface = interface.get_by_name(self.cfg, member_ifname)
+                if not member_ifname in bridge_members:
+                    self.logger.info("2> set interface l2 bridge %s %d" % (member_ifname, instance))
+                    if interface.is_qinx(self.cfg, member_ifname):
+                        self.logger.info("3> set interface l2 tag-rewrite %s pop 2" % (member_ifname))
+                    elif interface.is_sub(self.cfg, member_ifname):
+                        self.logger.info("3> set interface l2 tag-rewrite %s pop 1" % (member_ifname))
         return True
 
     def sync_l2xcs(self):
         for ifname in interface.get_l2xc_interfaces(self.cfg):
-            config_ifname, config_iface = interface.get_by_name(self.cfg, ifname)
-            rx_iface = self.vpp.config['interface_names'][config_ifname]
-            tx_iface = self.vpp.config['interface_names'][config_iface['l2xc']]
+            config_rx_ifname, config_rx_iface = interface.get_by_name(self.cfg, ifname)
+            config_tx_ifname, config_tx_iface = interface.get_by_name(self.cfg, config_rx_iface['l2xc'])
+            vpp_rx_iface = None
+            vpp_rx_iface = None
+            if config_rx_ifname in self.vpp.config['interface_names']:
+                vpp_rx_iface = self.vpp.config['interface_names'][config_rx_ifname]
+            if config_tx_ifname in self.vpp.config['interface_names']:
+                vpp_tx_iface = self.vpp.config['interface_names'][config_tx_ifname]
+
             l2xc_changed = False
-            if not rx_iface.sw_if_index in self.vpp.config['l2xcs']:
-                self.logger.info("1> set interface l2 xconnect %s %s" % (rx_iface.interface_name, tx_iface.interface_name))
+            if not vpp_rx_iface or not vpp_tx_iface:
+                self.logger.info("1> set interface l2 xconnect %s %s" % (config_rx_ifname, config_tx_ifname))
                 l2xc_changed = True
-            elif not tx_iface.sw_if_index == self.vpp.config['l2xcs'][rx_iface.sw_if_index].tx_sw_if_index:
-                self.logger.info("2> set interface l2 xconnect %s %s" % (rx_iface.interface_name, tx_iface.interface_name))
+            elif not vpp_rx_iface.sw_if_index in self.vpp.config['l2xcs']:
+                self.logger.info("2> set interface l2 xconnect %s %s" % (config_rx_ifname, config_tx_ifname))
                 l2xc_changed = True
-            if l2xc_changed and rx_iface.sub_number_of_tags > 0:
-                self.logger.info("3> set interface l2 tag-rewrite %s pop %d" % (rx_iface.interface_name, rx_iface.sub_number_of_tags))
+            elif not vpp_tx_iface.sw_if_index == self.vpp.config['l2xcs'][vpp_rx_iface.sw_if_index].tx_sw_if_index:
+                self.logger.info("3> set interface l2 xconnect %s %s" % (config_rx_ifname, config_tx_ifname))
+                l2xc_changed = True
+            if l2xc_changed:
+                tags = 0
+                if interface.is_qinx(self.cfg, config_rx_ifname):
+                    tags = 2
+                elif interface.is_sub(self.cfg, config_rx_ifname):
+                    tags = 1
+                self.logger.info("4> set interface l2 tag-rewrite %s pop %d" % (config_rx_ifname, tags))
         return True
 
     def sync_mtu_direction(self, shrink=True):
@@ -791,36 +818,49 @@ class Reconciler():
             tag_list = [ 0, 1, 2 ]
 
         for numtags in tag_list:
-            for idx, vpp_iface in self.vpp.config['interfaces'].items():
-                if vpp_iface.sub_number_of_tags != numtags:
+            for ifname in interface.get_interfaces(self.cfg) + loopback.get_loopbacks(self.cfg) + bridgedomain.get_bridgedomains(self.cfg):
+                if numtags == 0 and interface.is_sub(self.cfg, ifname):
                     continue
-                if vpp_iface.interface_dev_type=='local':
+                if numtags == 1 and not interface.is_sub(self.cfg, ifname):
                     continue
-                if self.__tap_is_lcp(vpp_iface.sw_if_index):
+                if numtags == 1 and interface.is_qinx(self.cfg, ifname):
                     continue
-
-                if vpp_iface.interface_dev_type=='Loopback':
-                    config_ifname, config_iface = loopback.get_by_name(self.cfg, vpp_iface.interface_name)
-                elif vpp_iface.interface_dev_type=='BVI':
-                    config_ifname, config_iface = bridgedomain.get_by_bvi_name(self.cfg, vpp_iface.interface_name)
-                else:
-                    config_ifname, config_iface = interface.get_by_name(self.cfg, vpp_iface.interface_name)
-                if not config_iface:
-                    self.logger.warning("Interface %s exists in VPP but not in config, this is dangerous" % vpp_iface.interface_name)
+                if numtags == 2 and not interface.is_qinx(self.cfg, ifname):
                     continue
-
                 config_mtu = 1500
-                if 'mtu' in config_iface:
-                    config_mtu = config_iface['mtu']
-
-                if shrink and config_mtu < vpp_iface.mtu[0]:
-                    self.logger.info("1> set interface mtu packet %d %s" % (config_mtu, vpp_iface.interface_name))
-                elif not shrink and config_mtu > vpp_iface.mtu[0]:
-                    self.logger.info("2> set interface mtu packet %d %s" % (config_mtu, vpp_iface.interface_name))
+                vpp_mtu = 9000
+                if ifname.startswith("loop"):
+                    if ifname in self.vpp.config['interface_names']:
+                        vpp_mtu = self.vpp.config['interface_names'][ifname].mtu[0]
+                    config_ifname, config_iface = loopback.get_by_name(self.cfg, ifname)
+                    if 'mtu' in config_iface:
+                        config_mtu = config_iface['mtu']
+                    vpp_ifname = config_ifname
+                elif ifname.startswith("bd"):
+                    instance=int(ifname[2:])
+                    bviname="bvi%d" % instance
+                    if bviname in self.vpp.config['interface_names']:
+                        vpp_mtu = self.vpp.config['interface_names'][bviname].mtu[0]
+                    config_ifname, config_iface = bridgedomain.get_by_name(self.cfg, ifname)
+                    if 'mtu' in config_iface:
+                        config_mtu = config_iface['mtu']
+                    vpp_ifname = bviname
+                else:
+                    if numtags > 0:
+                        vpp_mtu = 0
+                    if ifname in self.vpp.config['interface_names']:
+                        vpp_mtu = self.vpp.config['interface_names'][ifname].mtu[0]
+                    config_ifname, config_iface = interface.get_by_name(self.cfg, ifname)
+                    config_mtu = interface.get_mtu(self.cfg, ifname)
+                    vpp_ifname = config_ifname
 
+                if shrink and config_mtu < vpp_mtu:
+                    self.logger.info("1> set interface mtu packet %d %s" % (config_mtu, vpp_ifname))
+                elif not shrink and config_mtu > vpp_mtu:
+                    self.logger.info("2> set interface mtu packet %d %s" % (config_mtu, vpp_ifname))
         return True
 
-    def sync_link_mtu(self):
+    def sync_link_mtu_direction(self, shrink=True):
         for idx, vpp_iface in self.vpp.config['interfaces'].items():
             if vpp_iface.sub_number_of_tags != 0:
                 continue
@@ -831,6 +871,8 @@ class Reconciler():
             if not config_iface:
                 self.logger.warning("Interface %s exists in VPP but not in config, this is dangerous" % vpp_iface.interface_name)
                 continue
+            if not interface.is_phy(self.cfg, vpp_iface.interface_name):
+                continue
             config_mtu = interface.get_mtu(self.cfg, vpp_iface.interface_name)
 
             if vpp_iface.interface_dev_type=='bond' and vpp_iface.link_mtu < config_mtu:
@@ -838,21 +880,30 @@ class Reconciler():
                         (vpp_iface.interface_name, vpp_iface.link_mtu, config_mtu))
                 continue
 
-            if interface.is_phy(self.cfg, vpp_iface.interface_name) and config_mtu != vpp_iface.link_mtu:
+            if shrink and config_mtu < vpp_iface.link_mtu:
                 ## If the interface is up, temporarily down it in order to change the Max Frame Size
                 if vpp_iface.flags & 1: # IF_STATUS_API_FLAG_ADMIN_UP
-                    self.logger.info("2> set interface state %s down" % (vpp_iface.interface_name))
+                    self.logger.info("1> set interface state %s down" % (vpp_iface.interface_name))
 
-                self.logger.info("2> set interface mtu %d %s" % (config_mtu, vpp_iface.interface_name))
+                self.logger.info("1> set interface mtu %d %s" % (config_mtu, vpp_iface.interface_name))
 
                 if vpp_iface.flags & 1: # IF_STATUS_API_FLAG_ADMIN_UP
-                    self.logger.info("2> set interface state %s up" % (vpp_iface.interface_name))
+                    self.logger.info("1> set interface state %s up" % (vpp_iface.interface_name))
+            elif not shrink and config_mtu > vpp_iface.link_mtu:
+                ## If the interface is up, temporarily down it in order to change the Max Frame Size
+                if vpp_iface.flags & 1: # IF_STATUS_API_FLAG_ADMIN_UP
+                    self.logger.info("1> set interface state %s down" % (vpp_iface.interface_name))
+
+                self.logger.info("1> set interface mtu %d %s" % (config_mtu, vpp_iface.interface_name))
+
+                if vpp_iface.flags & 1: # IF_STATUS_API_FLAG_ADMIN_UP
+                    self.logger.info("1> set interface state %s up" % (vpp_iface.interface_name))
         return True
 
     def sync_mtu(self):
         ret = True
-        if not self.sync_link_mtu():
-            self.logger.warning("Could not sync interface Max Frame Size in VPP")
+        if not self.sync_link_mtu_direction(shrink=False):
+            self.logger.warning("Could not sync growing interface Max Frame Size in VPP")
             ret = False
         if not self.sync_mtu_direction(shrink=True):
             self.logger.warning("Could not sync shrinking interface MTU in VPP")
@@ -860,6 +911,9 @@ class Reconciler():
         if not self.sync_mtu_direction(shrink=False):
             self.logger.warning("Could not sync growing interface MTU in VPP")
             ret = False
+        if not self.sync_link_mtu_direction(shrink=True):
+            self.logger.warning("Could not sync shrinking interface Max Frame Size in VPP")
+            ret = False
         return ret
 
     def sync_addresses(self):