Bug 8398 - communication between two tenant network failed while using
[netvirt.git] / vpnservice / aclservice / impl / src / main / java / org / opendaylight / netvirt / aclservice / listeners / AclInterfaceListener.java
1 /*
2  * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.netvirt.aclservice.listeners;
9
10 import java.util.List;
11 import javax.annotation.PostConstruct;
12 import javax.inject.Inject;
13 import javax.inject.Singleton;
14 import org.opendaylight.controller.md.sal.binding.api.ClusteredDataTreeChangeListener;
15 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
16 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
17 import org.opendaylight.genius.datastoreutils.AsyncDataTreeChangeListenerBase;
18 import org.opendaylight.netvirt.aclservice.api.AclServiceManager;
19 import org.opendaylight.netvirt.aclservice.api.AclServiceManager.Action;
20 import org.opendaylight.netvirt.aclservice.api.utils.AclInterface;
21 import org.opendaylight.netvirt.aclservice.api.utils.AclInterfaceCacheUtil;
22 import org.opendaylight.netvirt.aclservice.utils.AclClusterUtil;
23 import org.opendaylight.netvirt.aclservice.utils.AclDataUtil;
24 import org.opendaylight.netvirt.aclservice.utils.AclServiceUtils;
25 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.Interfaces;
26 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface;
27 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.aclservice.rev160608.InterfaceAcl;
29 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
30 import org.slf4j.Logger;
31 import org.slf4j.LoggerFactory;
32
33 @Singleton
34 public class AclInterfaceListener extends AsyncDataTreeChangeListenerBase<Interface, AclInterfaceListener>
35         implements ClusteredDataTreeChangeListener<Interface> {
36     private static final Logger LOG = LoggerFactory.getLogger(AclInterfaceListener.class);
37
38     private final AclServiceManager aclServiceManager;
39     private final AclClusterUtil aclClusterUtil;
40     private final DataBroker dataBroker;
41     private final AclDataUtil aclDataUtil;
42
43     @Inject
44     public AclInterfaceListener(AclServiceManager aclServiceManager, AclClusterUtil aclClusterUtil,
45             DataBroker dataBroker, AclDataUtil aclDataUtil) {
46         super(Interface.class, AclInterfaceListener.class);
47         this.aclServiceManager = aclServiceManager;
48         this.aclClusterUtil = aclClusterUtil;
49         this.dataBroker = dataBroker;
50         this.aclDataUtil = aclDataUtil;
51     }
52
53     @Override
54     @PostConstruct
55     public void init() {
56         LOG.info("{} start", getClass().getSimpleName());
57         registerListener(LogicalDatastoreType.CONFIGURATION, dataBroker);
58     }
59
60     @Override
61     protected InstanceIdentifier<Interface> getWildCardPath() {
62         return InstanceIdentifier
63                 .create(Interfaces.class)
64                 .child(Interface.class);
65     }
66
67     @Override
68     protected void remove(InstanceIdentifier<Interface> key, Interface port) {
69         String interfaceId = port.getName();
70         AclInterface aclInterface = AclInterfaceCacheUtil.getAclInterfaceFromCache(interfaceId);
71         if (AclServiceUtils.isOfInterest(aclInterface)) {
72             AclInterfaceCacheUtil.removeAclInterfaceFromCache(interfaceId);
73             if (aclClusterUtil.isEntityOwner()) {
74                 aclServiceManager.notify(aclInterface, null, Action.UNBIND);
75             }
76         }
77     }
78
79     @Override
80     protected void update(InstanceIdentifier<Interface> key, Interface portBefore, Interface portAfter) {
81         InterfaceAcl aclInPortAfter = portAfter.getAugmentation(InterfaceAcl.class);
82         InterfaceAcl aclInPortBefore = portBefore.getAugmentation(InterfaceAcl.class);
83         if (aclInPortAfter != null && aclInPortAfter.isPortSecurityEnabled()
84                 || aclInPortBefore != null && aclInPortBefore.isPortSecurityEnabled()) {
85             String interfaceId = portAfter.getName();
86             AclInterface aclInterface = AclInterfaceCacheUtil.getAclInterfaceFromCache(interfaceId);
87             if (aclInterface != null) {
88                 aclInterface = getOldAclInterfaceObject(aclInterface, aclInPortAfter);
89             } else {
90                 aclInterface = addAclInterfaceToCache(interfaceId, aclInPortAfter);
91             }
92
93             AclInterface oldAclInterface = getOldAclInterfaceObject(aclInterface, aclInPortBefore);
94             List<Uuid> deletedAclList = AclServiceUtils.getUpdatedAclList(oldAclInterface.getSecurityGroups(),
95                     aclInterface.getSecurityGroups());
96             org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang
97                 .ietf.interfaces.rev140508.interfaces.state.Interface interfaceState =
98                     AclServiceUtils.getInterfaceStateFromOperDS(dataBroker, portAfter.getName());
99             if (aclClusterUtil.isEntityOwner() && interfaceState != null && interfaceState.getOperStatus().equals(
100                     org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang
101                         .ietf.interfaces.rev140508.interfaces.state.Interface.OperStatus.Up)) {
102                 aclServiceManager.notify(aclInterface, oldAclInterface, AclServiceManager.Action.UPDATE);
103             }
104             if (deletedAclList != null && !deletedAclList.isEmpty()) {
105                 aclDataUtil.removeAclInterfaceMap(deletedAclList, aclInterface);
106             }
107
108         }
109     }
110
111     private AclInterface getOldAclInterfaceObject(AclInterface aclInterface, InterfaceAcl aclInPortBefore) {
112         AclInterface oldAclInterface = new AclInterface();
113         if (aclInPortBefore == null) {
114             oldAclInterface.setPortSecurityEnabled(false);
115         } else {
116             oldAclInterface.setInterfaceId(aclInterface.getInterfaceId());
117             oldAclInterface.setDpId(aclInterface.getDpId());
118             oldAclInterface.setLPortTag(aclInterface.getLPortTag());
119             oldAclInterface.setElanId(aclInterface.getElanId());
120             oldAclInterface.setVpnId(aclInterface.getVpnId());
121
122             oldAclInterface.setPortSecurityEnabled(aclInPortBefore.isPortSecurityEnabled());
123             oldAclInterface.setAllowedAddressPairs(aclInPortBefore.getAllowedAddressPairs());
124             oldAclInterface.setSecurityGroups(aclInPortBefore.getSecurityGroups());
125         }
126         return oldAclInterface;
127     }
128
129     @Override
130     protected void add(InstanceIdentifier<Interface> key, Interface port) {
131         InterfaceAcl aclInPort = port.getAugmentation(InterfaceAcl.class);
132         if (aclInPort != null && aclInPort.isPortSecurityEnabled()) {
133             AclInterface aclInterface = addAclInterfaceToCache(port.getName(), aclInPort);
134             if (aclClusterUtil.isEntityOwner()) {
135                 aclServiceManager.notify(aclInterface, null, Action.BIND);
136             }
137         }
138     }
139
140     private AclInterface addAclInterfaceToCache(String interfaceId, InterfaceAcl aclInPort) {
141         AclInterface aclInterface = buildAclInterfaceState(interfaceId, aclInPort);
142         AclInterfaceCacheUtil.addAclInterfaceToCache(interfaceId, aclInterface);
143         return aclInterface;
144     }
145
146     private AclInterface buildAclInterfaceState(String interfaceId, InterfaceAcl aclInPort) {
147         AclInterface aclInterface = new AclInterface();
148         aclInterface.setInterfaceId(interfaceId);
149         aclInterface.setPortSecurityEnabled(aclInPort.isPortSecurityEnabled());
150         aclInterface.setSecurityGroups(aclInPort.getSecurityGroups());
151         aclInterface.setAllowedAddressPairs(aclInPort.getAllowedAddressPairs());
152         aclInterface.setElanId(AclServiceUtils.getElanIdFromInterface(interfaceId, dataBroker));
153         aclInterface.setVpnId(AclServiceUtils.getVpnIdFromInterface(dataBroker, interfaceId));
154         return aclInterface;
155     }
156
157     @Override
158     protected AclInterfaceListener getDataTreeChangeListener() {
159         return this;
160     }
161 }