[VOL-4050] Logging ONU Serial Number on ONOS Olt App

Change-Id: Icaf2a1c368c62420880b753ebd395a88962e725d
diff --git a/api/src/main/java/org/opencord/olt/AccessDevicePort.java b/api/src/main/java/org/opencord/olt/AccessDevicePort.java
new file mode 100644
index 0000000..8a1665d
--- /dev/null
+++ b/api/src/main/java/org/opencord/olt/AccessDevicePort.java
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.opencord.olt;
+
+import org.onosproject.net.AnnotationKeys;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.Port;
+import org.onosproject.net.PortNumber;
+
+/**
+ * OLT device port.
+ */
+public class AccessDevicePort {
+
+    Port port;
+    Type type;
+
+    /**
+     * OLT Port Type.
+     */
+    public enum Type {
+        NNI,
+        UNI,
+    }
+
+    /**
+     * Creates an AccessDevicePort with given ONOS port object and OLT port type.
+     *
+     * @param port ONOS port
+     * @param type OLT port type
+     */
+    public AccessDevicePort(Port port, Type type) {
+        this.port = port;
+        this.type = type;
+    }
+
+    /**
+     * Get ONOS Port object.
+     *
+     * @return ONOS port
+     */
+    public Port port() {
+        return this.port;
+    }
+
+    /**
+     * Get OLT port Type.
+     *
+     * @return OLT port type
+     */
+    public Type type() {
+        return this.type;
+    }
+
+    /**
+     * Check port is enabled state on ONOS.
+     *
+     * @return is Access Device Port enabled
+     */
+    public boolean isEnabled() {
+        return this.port.isEnabled();
+    }
+
+    /**
+     * Get Device ID of OLT which the port is connected.
+     *
+     * @return OLT Device ID
+     */
+    public DeviceId deviceId() {
+        return (DeviceId) this.port.element().id();
+    }
+
+    /**
+     * Get port number.
+     *
+     * @return port number
+     */
+    public PortNumber number() {
+        return this.port.number();
+    }
+
+    /**
+     * Get port name which is combination of serial number and uni index.
+     *
+     * @return port name (ex: BBSM00010001-1)
+     */
+    public String name() {
+        return this.port.annotations().value(AnnotationKeys.PORT_NAME);
+    }
+
+    @Override
+    public String toString() {
+        return deviceId().toString() + '/' + number() + '[' + name() + ']';
+    }
+
+}
diff --git a/impl/src/main/java/org/opencord/olt/impl/Olt.java b/impl/src/main/java/org/opencord/olt/impl/Olt.java
index a74699c..70a3753 100644
--- a/impl/src/main/java/org/opencord/olt/impl/Olt.java
+++ b/impl/src/main/java/org/opencord/olt/impl/Olt.java
@@ -58,6 +58,7 @@
 import org.onosproject.store.service.StorageService;
 import org.opencord.olt.AccessDeviceEvent;
 import org.opencord.olt.AccessDeviceListener;
+import org.opencord.olt.AccessDevicePort;
 import org.opencord.olt.AccessDeviceService;
 import org.opencord.olt.AccessSubscriberId;
 import org.opencord.olt.internalapi.AccessDeviceFlowService;
@@ -237,6 +238,8 @@
                 .register(KryoNamespaces.API)
                 .register(UniTagInformation.class)
                 .register(SubscriberFlowInfo.class)
+                .register(AccessDevicePort.class)
+                .register(AccessDevicePort.Type.class)
                 .register(LinkedBlockingQueue.class)
                 .build();
 
@@ -255,6 +258,8 @@
         KryoNamespace macSerializer = KryoNamespace.newBuilder()
                 .register(KryoNamespaces.API)
                 .register(SubscriberFlowInfo.class)
+                .register(AccessDevicePort.class)
+                .register(AccessDevicePort.Type.class)
                 .register(UniTagInformation.class)
                 .build();
 
@@ -356,9 +361,9 @@
     public boolean provisionSubscriber(ConnectPoint connectPoint) {
         log.info("Call to provision subscriber at {}", connectPoint);
         DeviceId deviceId = connectPoint.deviceId();
-        PortNumber subscriberPortNo = connectPoint.port();
-        checkNotNull(deviceService.getPort(deviceId, subscriberPortNo),
-                     "Invalid connect point:" + connectPoint);
+        Port subscriberPortOnos = deviceService.getPort(deviceId, connectPoint.port());
+        checkNotNull(subscriberPortOnos, "Invalid connect point:" + connectPoint);
+        AccessDevicePort subscriberPort = new AccessDevicePort(subscriberPortOnos, AccessDevicePort.Type.UNI);
 
         if (isSubscriberInstalled(connectPoint)) {
             log.warn("Subscriber at {} already provisioned or in the process .."
@@ -374,7 +379,7 @@
         }
 
         // Get the uplink port
-        Port uplinkPort = getUplinkPort(deviceService.getDevice(deviceId));
+        AccessDevicePort uplinkPort = getUplinkPort(deviceService.getDevice(deviceId));
         if (uplinkPort == null) {
             log.warn(NO_UPLINK_PORT, deviceId);
             return false;
@@ -383,8 +388,7 @@
         // delete Eapol authentication flow with default bandwidth
         // wait until Eapol rule with defaultBpId is removed to install subscriber-based rules
         // retry deletion if it fails/times-out
-        retryExecutor.execute(new DeleteEapolInstallSub(connectPoint,
-                                                        uplinkPort, sub, 1));
+        retryExecutor.execute(new DeleteEapolInstallSub(subscriberPort, uplinkPort, sub, 1));
         return true;
     }
 
@@ -412,15 +416,15 @@
     }
 
     private class DeleteEapolInstallSub implements Runnable {
-        ConnectPoint cp;
-        Port uplinkPort;
+        AccessDevicePort subscriberPort;
+        AccessDevicePort uplinkPort;
         SubscriberAndDeviceInformation sub;
         private int attemptNumber;
 
-        DeleteEapolInstallSub(ConnectPoint cp, Port uplinkPort,
+        DeleteEapolInstallSub(AccessDevicePort subscriberPort, AccessDevicePort uplinkPort,
                               SubscriberAndDeviceInformation sub,
                               int attemptNumber) {
-            this.cp = cp;
+            this.subscriberPort = subscriberPort;
             this.uplinkPort = uplinkPort;
             this.sub = sub;
             this.attemptNumber = attemptNumber;
@@ -429,34 +433,36 @@
         @Override
         public void run() {
             CompletableFuture<ObjectiveError> filterFuture = new CompletableFuture<>();
-            oltFlowService.processEapolFilteringObjectives(cp.deviceId(), cp.port(),
+            oltFlowService.processEapolFilteringObjectives(subscriberPort,
                                                      defaultBpId, filterFuture,
                                                      VlanId.vlanId(EAPOL_DEFAULT_VLAN),
                                                      false);
             filterFuture.thenAcceptAsync(filterStatus -> {
                 if (filterStatus == null) {
                     log.info("Default eapol flow deleted in attempt {} of {}"
-                            + "... provisioning subscriber flows {}",
-                             attemptNumber, eapolDeleteRetryMaxAttempts, cp);
+                            + "... provisioning subscriber flows on {}",
+                            attemptNumber, eapolDeleteRetryMaxAttempts, subscriberPort);
 
                     // FIXME this is needed to prevent that default EAPOL flow removal and
                     // data plane flows install are received by the device at the same time
                     provisionExecutor.schedule(
-                            () -> provisionUniTagList(cp, uplinkPort.number(), sub),
+                            () -> provisionUniTagList(subscriberPort, uplinkPort, sub),
                             provisionDelay, TimeUnit.MILLISECONDS);
                 } else {
                     if (attemptNumber <= eapolDeleteRetryMaxAttempts) {
-                        log.warn("The filtering future failed {} for subscriber {}"
+                        log.warn("The filtering future failed {} for subscriber on {}"
                                 + "... retrying {} of {} attempts",
-                                 filterStatus, cp, attemptNumber, eapolDeleteRetryMaxAttempts);
+                                 filterStatus, subscriberPort, attemptNumber, eapolDeleteRetryMaxAttempts);
                         retryExecutor.execute(
-                                         new DeleteEapolInstallSub(cp, uplinkPort, sub,
+                                         new DeleteEapolInstallSub(subscriberPort, uplinkPort, sub,
                                                                    attemptNumber + 1));
                     } else {
-                        log.error("The filtering future failed {} for subscriber {}"
+                        log.error("The filtering future failed {} for subscriber on {}"
                                 + "after {} attempts. Subscriber provisioning failed",
-                                  filterStatus, cp, eapolDeleteRetryMaxAttempts);
-                        sub.uniTagList().forEach(ut -> failedSubs.put(cp, ut));
+                                  filterStatus, subscriberPort, eapolDeleteRetryMaxAttempts);
+                        sub.uniTagList().forEach(ut ->
+                                failedSubs.put(
+                                        new ConnectPoint(subscriberPort.deviceId(), subscriberPort.number()), ut));
                     }
                 }
             });
@@ -466,13 +472,22 @@
 
     @Override
     public boolean removeSubscriber(ConnectPoint connectPoint) {
-        log.info("Call to un-provision subscriber at {}", connectPoint);
+        Port subscriberPort = deviceService.getPort(connectPoint);
+        if (subscriberPort == null) {
+            log.error("Subscriber port not found at: {}", connectPoint);
+            return false;
+        }
+        return removeSubscriber(new AccessDevicePort(subscriberPort, AccessDevicePort.Type.UNI));
+    }
+
+    private boolean removeSubscriber(AccessDevicePort subscriberPort) {
+        log.info("Call to un-provision subscriber at {}", subscriberPort);
 
         // Get the subscriber connected to this port from the local cache
         // If we don't know about the subscriber there's no need to remove it
-        DeviceId deviceId = connectPoint.deviceId();
-        PortNumber subscriberPortNo = connectPoint.port();
+        DeviceId deviceId = subscriberPort.deviceId();
 
+        ConnectPoint connectPoint = new ConnectPoint(deviceId, subscriberPort.number());
         Collection<? extends UniTagInformation> uniTagInformationSet = programmedSubs.get(connectPoint).value();
         if (uniTagInformationSet == null || uniTagInformationSet.isEmpty()) {
             log.warn("Subscriber on connectionPoint {} was not previously programmed, " +
@@ -481,7 +496,7 @@
         }
 
         // Get the uplink port
-        Port uplinkPort = getUplinkPort(deviceService.getDevice(deviceId));
+        AccessDevicePort uplinkPort = getUplinkPort(deviceService.getDevice(deviceId));
         if (uplinkPort == null) {
             log.warn(NO_UPLINK_PORT, deviceId);
             return false;
@@ -493,17 +508,16 @@
                 continue;
             }
 
-            unprovisionVlans(deviceId, uplinkPort.number(), subscriberPortNo, uniTag);
+            unprovisionVlans(uplinkPort, subscriberPort, uniTag);
 
             // remove eapol with subscriber bandwidth profile
-            oltFlowService.processEapolFilteringObjectives(deviceId, subscriberPortNo,
+            oltFlowService.processEapolFilteringObjectives(subscriberPort,
                                                            uniTag.getUpstreamBandwidthProfile(),
                                                            null, uniTag.getPonCTag(), false);
 
-            Port port = deviceService.getPort(deviceId, subscriberPortNo);
-            if (port != null && port.isEnabled()) {
+            if (subscriberPort.port() != null && subscriberPort.isEnabled()) {
                 // reinstall eapol with default bandwidth profile
-                oltFlowService.processEapolFilteringObjectives(deviceId, subscriberPortNo, defaultBpId,
+                oltFlowService.processEapolFilteringObjectives(subscriberPort, defaultBpId,
                                                                null, VlanId.vlanId(EAPOL_DEFAULT_VLAN), true);
             } else {
                 log.debug("Port {} is no longer enabled or it's unavailable. Not "
@@ -518,22 +532,23 @@
     public boolean provisionSubscriber(AccessSubscriberId subscriberId, Optional<VlanId> sTag,
                                        Optional<VlanId> cTag, Optional<Integer> tpId) {
 
-        log.info("Provisioning subscriber using subscriberId {}, sTag {}, cTag {}, tpId {}" +
-                         "", subscriberId, sTag, cTag, tpId);
+        log.info("Provisioning subscriber using subscriberId {}, sTag {}, cTag {}, tpId {}",
+                subscriberId, sTag, cTag, tpId);
 
         // Check if we can find the connect point to which this subscriber is connected
-        ConnectPoint subsPort = findSubscriberConnectPoint(subscriberId.toString());
-        if (subsPort == null) {
+        ConnectPoint cp = findSubscriberConnectPoint(subscriberId.toString());
+        if (cp == null) {
             log.warn("ConnectPoint for {} not found", subscriberId);
             return false;
         }
+        AccessDevicePort subscriberPort = new AccessDevicePort(deviceService.getPort(cp), AccessDevicePort.Type.UNI);
 
         if (!sTag.isPresent() && !cTag.isPresent()) {
-            return provisionSubscriber(subsPort);
+            return provisionSubscriber(cp);
         } else if (sTag.isPresent() && cTag.isPresent() && tpId.isPresent()) {
-            Port uplinkPort = getUplinkPort(deviceService.getDevice(subsPort.deviceId()));
+            AccessDevicePort uplinkPort = getUplinkPort(deviceService.getDevice(cp.deviceId()));
             if (uplinkPort == null) {
-                log.warn(NO_UPLINK_PORT, subsPort.deviceId());
+                log.warn(NO_UPLINK_PORT, cp.deviceId());
                 return false;
             }
 
@@ -541,12 +556,11 @@
             //wait until Eapol rule with defaultBpId is removed to install subscriber-based rules
             //install subscriber flows
             CompletableFuture<ObjectiveError> filterFuture = new CompletableFuture<>();
-            oltFlowService.processEapolFilteringObjectives(subsPort.deviceId(), subsPort.port(), defaultBpId,
+            oltFlowService.processEapolFilteringObjectives(subscriberPort, defaultBpId,
                                                            filterFuture, VlanId.vlanId(EAPOL_DEFAULT_VLAN), false);
             filterFuture.thenAcceptAsync(filterStatus -> {
                 if (filterStatus == null) {
-                    provisionUniTagInformation(subsPort.deviceId(), uplinkPort.number(), subsPort.port(),
-                                               cTag.get(), sTag.get(), tpId.get());
+                    provisionUniTagInformation(uplinkPort, subscriberPort, cTag.get(), sTag.get(), tpId.get());
                 }
             });
             return true;
@@ -560,30 +574,32 @@
     public boolean removeSubscriber(AccessSubscriberId subscriberId, Optional<VlanId> sTag,
                                     Optional<VlanId> cTag, Optional<Integer> tpId) {
         // Check if we can find the connect point to which this subscriber is connected
-        ConnectPoint subsPort = findSubscriberConnectPoint(subscriberId.toString());
-        if (subsPort == null) {
+        ConnectPoint cp = findSubscriberConnectPoint(subscriberId.toString());
+        if (cp == null) {
             log.warn("ConnectPoint for {} not found", subscriberId);
             return false;
         }
+        AccessDevicePort subscriberPort = new AccessDevicePort(deviceService.getPort(cp), AccessDevicePort.Type.UNI);
 
         if (!sTag.isPresent() && !cTag.isPresent()) {
-            return removeSubscriber(subsPort);
+            return removeSubscriber(cp);
         } else if (sTag.isPresent() && cTag.isPresent() && tpId.isPresent()) {
             // Get the uplink port
-            Port uplinkPort = getUplinkPort(deviceService.getDevice(subsPort.deviceId()));
+            AccessDevicePort uplinkPort = getUplinkPort(deviceService.getDevice(cp.deviceId()));
             if (uplinkPort == null) {
-                log.warn(NO_UPLINK_PORT, subsPort.deviceId());
+                log.warn(NO_UPLINK_PORT, cp.deviceId());
                 return false;
             }
 
-            Optional<UniTagInformation> tagInfo = getUniTagInformation(subsPort, cTag.get(), sTag.get(), tpId.get());
+            Optional<UniTagInformation> tagInfo = getUniTagInformation(subscriberPort, cTag.get(),
+                    sTag.get(), tpId.get());
             if (!tagInfo.isPresent()) {
-                log.warn("UniTagInformation does not exist for Device/Port {}, cTag {}, sTag {}, tpId {}",
-                         subsPort, cTag, sTag, tpId);
+                log.warn("UniTagInformation does not exist for {}, cTag {}, sTag {}, tpId {}",
+                        subscriberPort, cTag, sTag, tpId);
                 return false;
             }
 
-            unprovisionVlans(subsPort.deviceId(), uplinkPort.number(), subsPort.port(), tagInfo.get());
+            unprovisionVlans(uplinkPort, subscriberPort, tagInfo.get());
             return true;
         } else {
             log.warn("Removing subscriber is not possible - please check the provided information" +
@@ -663,15 +679,13 @@
     /**
      * Removes subscriber vlan flows.
      *
-     * @param deviceId       the device identifier
      * @param uplink         uplink port of the OLT
      * @param subscriberPort uni port
      * @param uniTag         uni tag information
      */
-    private void unprovisionVlans(DeviceId deviceId, PortNumber uplink,
-                                  PortNumber subscriberPort, UniTagInformation uniTag) {
-
-        log.info("Unprovisioning vlans for {} at {}/{}", uniTag, deviceId, subscriberPort);
+    private void unprovisionVlans(AccessDevicePort uplink, AccessDevicePort subscriberPort, UniTagInformation uniTag) {
+        log.info("Unprovisioning vlans for {} at {}", uniTag, subscriberPort);
+        DeviceId deviceId = subscriberPort.deviceId();
 
         CompletableFuture<ObjectiveError> downFuture = new CompletableFuture<>();
         CompletableFuture<ObjectiveError> upFuture = new CompletableFuture<>();
@@ -685,13 +699,14 @@
                 .getMeterIdFromBpMapping(deviceId, uniTag.getDownstreamBandwidthProfile());
 
         Optional<SubscriberFlowInfo> waitingMacSubFlowInfo =
-                getAndRemoveWaitingMacSubFlowInfoForCTag(new ConnectPoint(deviceId, subscriberPort), subscriberVlan);
+                getAndRemoveWaitingMacSubFlowInfoForCTag(new ConnectPoint(deviceId, subscriberPort.number()),
+                        subscriberVlan);
         if (waitingMacSubFlowInfo.isPresent()) {
             // only dhcp objectives applied previously, so only dhcp uninstallation objective will be processed
             log.debug("Waiting MAC service removed and dhcp uninstallation objective will be processed. " +
                     "waitingMacSubFlowInfo:{}", waitingMacSubFlowInfo.get());
             CompletableFuture<ObjectiveError> dhcpFuture = new CompletableFuture<>();
-            oltFlowService.processDhcpFilteringObjectives(deviceId, subscriberPort,
+            oltFlowService.processDhcpFilteringObjectives(subscriberPort,
                     upstreamMeterId, uniTag, false, true, Optional.of(dhcpFuture));
             dhcpFuture.thenAcceptAsync(dhcpStatus -> {
                 AccessDeviceEvent.Type type;
@@ -700,20 +715,19 @@
                     log.debug("Dhcp uninstallation objective was processed successfully for cTag {}, sTag {}, " +
                                     "tpId {} and Device/Port:{}", uniTag.getPonCTag(), uniTag.getPonSTag(),
                             uniTag.getTechnologyProfileId(), subscriberPort);
-                    updateProgrammedSubscriber(new ConnectPoint(deviceId, subscriberPort), uniTag, false);
+                    updateProgrammedSubscriber(subscriberPort, uniTag, false);
                 } else {
                     type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_UNREGISTRATION_FAILED;
                     log.error("Dhcp uninstallation objective was failed for cTag {}, sTag {}, " +
                                     "tpId {} and Device/Port:{} :{}", uniTag.getPonCTag(), uniTag.getPonSTag(),
                             uniTag.getTechnologyProfileId(), subscriberPort, dhcpStatus);
                 }
-                post(new AccessDeviceEvent(type, deviceId, deviceService.getPort(deviceId, subscriberPort),
+                post(new AccessDeviceEvent(type, deviceId, subscriberPort.port(),
                         deviceVlan, subscriberVlan, uniTag.getTechnologyProfileId()));
             });
             return;
         } else {
-            log.debug("There is no waiting MAC service for dev/port: {}/{} and subscriberVlan: {}",
-                    deviceId, subscriberPort, subscriberVlan);
+            log.debug("There is no waiting MAC service for {} and subscriberVlan: {}", subscriberPort, subscriberVlan);
         }
 
         ForwardingObjective.Builder upFwd =
@@ -723,12 +737,10 @@
         ForwardingObjective.Builder downFwd =
                 oltFlowService.createDownBuilder(uplink, subscriberPort, downstreamMeterId, uniTag, macAddress);
 
-        oltFlowService.processIgmpFilteringObjectives(deviceId, subscriberPort,
-                                                      upstreamMeterId, uniTag, false, true);
-        oltFlowService.processDhcpFilteringObjectives(deviceId, subscriberPort,
-                                                      upstreamMeterId, uniTag, false, true, Optional.empty());
-        oltFlowService.processPPPoEDFilteringObjectives(deviceId, subscriberPort,
-                                                        upstreamMeterId, uniTag, false, true);
+        oltFlowService.processIgmpFilteringObjectives(subscriberPort, upstreamMeterId, uniTag, false, true);
+        oltFlowService.processDhcpFilteringObjectives(subscriberPort,
+                upstreamMeterId, uniTag, false, true, Optional.empty());
+        oltFlowService.processPPPoEDFilteringObjectives(subscriberPort, upstreamMeterId, uniTag, false, true);
 
         flowObjectiveService.forward(deviceId, upFwd.remove(new ObjectiveContext() {
             @Override
@@ -757,23 +769,19 @@
         upFuture.thenAcceptBothAsync(downFuture, (upStatus, downStatus) -> {
             AccessDeviceEvent.Type type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_UNREGISTERED;
             if (upStatus == null && downStatus == null) {
-                log.debug("Uni tag information is unregistered successfully for cTag {}, sTag {}, tpId {}, and" +
-                                  "Device/Port{}", uniTag.getPonCTag(), uniTag.getPonSTag(),
-                          uniTag.getTechnologyProfileId(), subscriberPort);
-                updateProgrammedSubscriber(new ConnectPoint(deviceId, subscriberPort), uniTag, false);
+                log.debug("Uni tag information is unregistered successfully for cTag {}, sTag {}, tpId {} on {}",
+                        uniTag.getPonCTag(), uniTag.getPonSTag(), uniTag.getTechnologyProfileId(), subscriberPort);
+                updateProgrammedSubscriber(subscriberPort, uniTag, false);
             } else if (downStatus != null) {
-                log.error("Subscriber with vlan {} on device {} " +
-                                  "on port {} failed downstream uninstallation: {}",
-                          subscriberVlan, deviceId, subscriberPort, downStatus);
+                log.error("Subscriber with vlan {} on {} failed downstream uninstallation: {}",
+                          subscriberVlan, subscriberPort, downStatus);
                 type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_UNREGISTRATION_FAILED;
             } else if (upStatus != null) {
-                log.error("Subscriber with vlan {} on device {} " +
-                                  "on port {} failed upstream uninstallation: {}",
-                          subscriberVlan, deviceId, subscriberPort, upStatus);
+                log.error("Subscriber with vlan {} on {} failed upstream uninstallation: {}",
+                          subscriberVlan, subscriberPort, upStatus);
                 type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_UNREGISTRATION_FAILED;
             }
-            Port port = deviceService.getPort(deviceId, subscriberPort);
-            post(new AccessDeviceEvent(type, deviceId, port, deviceVlan, subscriberVlan,
+            post(new AccessDeviceEvent(type, deviceId, subscriberPort.port(), deviceVlan, subscriberVlan,
                                        uniTag.getTechnologyProfileId()));
         }, oltInstallers);
     }
@@ -797,29 +805,25 @@
     /**
      * Adds subscriber vlan flows, dhcp, eapol and igmp trap flows for the related uni port.
      *
-     * @param connectPoint the connection point of the subscriber
+     * @param subPort      the connection point of the subscriber
      * @param uplinkPort   uplink port of the OLT (the nni port)
      * @param sub          subscriber information that includes s, c tags, tech profile and bandwidth profile references
      */
-    private void provisionUniTagList(ConnectPoint connectPoint, PortNumber uplinkPort,
+    private void provisionUniTagList(AccessDevicePort subPort, AccessDevicePort uplinkPort,
                                      SubscriberAndDeviceInformation sub) {
 
-        log.debug("Provisioning vlans for subscriber on dev/port: {}", connectPoint.toString());
+        log.debug("Provisioning vlans for subscriber on {}", subPort);
         if (log.isTraceEnabled()) {
             log.trace("Subscriber informations {}", sub);
         }
 
         if (sub.uniTagList() == null || sub.uniTagList().isEmpty()) {
-            log.warn("Unitaglist doesn't exist for the subscriber {} on dev/port {}",
-                    sub.id(), connectPoint.toString());
+            log.warn("Unitaglist doesn't exist for the subscriber {} on {}", sub.id(), subPort);
             return;
         }
 
-        DeviceId deviceId = connectPoint.deviceId();
-        PortNumber subscriberPort = connectPoint.port();
-
         for (UniTagInformation uniTag : sub.uniTagList()) {
-            handleSubscriberFlows(deviceId, uplinkPort, subscriberPort, uniTag);
+            handleSubscriberFlows(uplinkPort, subPort, uniTag);
         }
     }
 
@@ -827,58 +831,53 @@
      * Finds the uni tag information and provisions the found information.
      * If the uni tag information is not found, returns
      *
-     * @param deviceId       the access device id
      * @param uplinkPort     the nni port
      * @param subscriberPort the uni port
      * @param innerVlan      the pon c tag
      * @param outerVlan      the pon s tag
      * @param tpId           the technology profile id
      */
-    private void provisionUniTagInformation(DeviceId deviceId, PortNumber uplinkPort,
-                                            PortNumber subscriberPort,
+    private void provisionUniTagInformation(AccessDevicePort uplinkPort,
+                                            AccessDevicePort subscriberPort,
                                             VlanId innerVlan,
                                             VlanId outerVlan,
                                             Integer tpId) {
 
-        ConnectPoint cp = new ConnectPoint(deviceId, subscriberPort);
-        Optional<UniTagInformation> gotTagInformation = getUniTagInformation(cp, innerVlan, outerVlan, tpId);
+        Optional<UniTagInformation> gotTagInformation = getUniTagInformation(subscriberPort, innerVlan,
+                outerVlan, tpId);
         if (!gotTagInformation.isPresent()) {
             return;
         }
         UniTagInformation tagInformation = gotTagInformation.get();
-        handleSubscriberFlows(deviceId, uplinkPort, subscriberPort, tagInformation);
+        handleSubscriberFlows(uplinkPort, subscriberPort, tagInformation);
     }
 
-    private void updateProgrammedSubscriber(ConnectPoint connectPoint, UniTagInformation tagInformation, Boolean add) {
+    private void updateProgrammedSubscriber(AccessDevicePort port, UniTagInformation tagInformation, boolean add) {
         if (add) {
-            programmedSubs.put(connectPoint, tagInformation);
+            programmedSubs.put(new ConnectPoint(port.deviceId(), port.number()), tagInformation);
         } else {
-            programmedSubs.remove(connectPoint, tagInformation);
+            programmedSubs.remove(new ConnectPoint(port.deviceId(), port.number()), tagInformation);
         }
     }
 
     /**
      * Installs a uni tag information flow.
      *
-     * @param deviceId       the access device id
      * @param uplinkPort     the nni port
      * @param subscriberPort the uni port
      * @param tagInfo        the uni tag information
      */
-    private void handleSubscriberFlows(DeviceId deviceId, PortNumber uplinkPort, PortNumber subscriberPort,
+    private void handleSubscriberFlows(AccessDevicePort uplinkPort, AccessDevicePort subscriberPort,
                                        UniTagInformation tagInfo) {
-
-        log.debug("Provisioning vlan-based flows for the uniTagInformation {} on dev/port {}/{}",
-                tagInfo, deviceId, subscriberPort);
-
-        Port port = deviceService.getPort(deviceId, subscriberPort);
+        log.debug("Provisioning vlan-based flows for the uniTagInformation {} on {}", tagInfo, subscriberPort);
+        DeviceId deviceId = subscriberPort.deviceId();
 
         if (multicastServiceName.equals(tagInfo.getServiceName())) {
             // IGMP flows are taken care of along with VOD service
             // Please note that for each service, Subscriber Registered event will be sent
-            post(new AccessDeviceEvent(AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTERED,
-                                       deviceId, port, tagInfo.getPonSTag(), tagInfo.getPonCTag(),
-                                       tagInfo.getTechnologyProfileId()));
+            post(new AccessDeviceEvent(AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTERED, deviceId,
+                    subscriberPort.port(), tagInfo.getPonSTag(), tagInfo.getPonCTag(),
+                    tagInfo.getTechnologyProfileId()));
             return;
         }
 
@@ -888,18 +887,15 @@
                 getBandwidthProfileInformation(tagInfo.getDownstreamBandwidthProfile());
         if (upstreamBpInfo == null) {
             log.warn("No meter installed since no Upstream BW Profile definition found for "
-                             + "ctag {} stag {} tpId {} and dev/port: {}/{}",
-                     tagInfo.getPonCTag(), tagInfo.getPonSTag(),
-                     tagInfo.getTechnologyProfileId(), deviceId,
-                     subscriberPort);
+                             + "ctag {} stag {} tpId {} on {}",
+                     tagInfo.getPonCTag(), tagInfo.getPonSTag(), tagInfo.getTechnologyProfileId(), subscriberPort);
             return;
         }
         if (downstreamBpInfo == null) {
             log.warn("No meter installed since no Downstream BW Profile definition found for "
-                             + "ctag {} stag {} tpId {} and dev/port: {}/{}",
+                             + "ctag {} stag {} tpId {} on {}",
                      tagInfo.getPonCTag(), tagInfo.getPonSTag(),
-                     tagInfo.getTechnologyProfileId(), deviceId,
-                     subscriberPort);
+                     tagInfo.getTechnologyProfileId(), subscriberPort);
             return;
         }
 
@@ -908,16 +904,16 @@
                 .getMeterIdFromBpMapping(deviceId, upstreamBpInfo.id());
         MeterId downMeterId = oltMeterService
                 .getMeterIdFromBpMapping(deviceId, downstreamBpInfo.id());
-        SubscriberFlowInfo fi = new SubscriberFlowInfo(deviceId, uplinkPort, subscriberPort,
+        SubscriberFlowInfo fi = new SubscriberFlowInfo(uplinkPort, subscriberPort,
                                                        tagInfo, downMeterId, upMeterId,
                                                        downstreamBpInfo.id(), upstreamBpInfo.id());
 
         if (upMeterId != null && downMeterId != null) {
-            log.debug("Meters are existing for upstream {} and downstream {} on dev/port {}/{}",
-                     upstreamBpInfo.id(), downstreamBpInfo.id(), deviceId, subscriberPort);
+            log.debug("Meters are existing for upstream {} and downstream {} on {}",
+                    upstreamBpInfo.id(), downstreamBpInfo.id(), subscriberPort);
             handleSubFlowsWithMeters(fi);
         } else {
-            log.debug("Adding {} on {}/{} to pending subs", fi, deviceId, subscriberPort);
+            log.debug("Adding {} on {} to pending subs", fi, subscriberPort);
             // one or both meters are not ready. It's possible they are in the process of being
             // created for other subscribers that share the same bandwidth profile.
             pendingSubscribersForDevice.compute(deviceId, (id, queue) -> {
@@ -925,17 +921,17 @@
                     queue = new LinkedBlockingQueue<>();
                 }
                 queue.add(fi);
-                log.info("Added {} to pending subscribers on {}/{}", fi, deviceId, subscriberPort);
+                log.info("Added {} to pending subscribers on {}", fi, subscriberPort);
                 return queue;
             });
 
             // queue up the meters to be created
             if (upMeterId == null) {
-                log.debug("Missing meter for upstream {} on {}/{}", upstreamBpInfo.id(), deviceId, subscriberPort);
+                log.debug("Missing meter for upstream {} on {}", upstreamBpInfo.id(), subscriberPort);
                 checkAndCreateDevMeter(deviceId, upstreamBpInfo);
             }
             if (downMeterId == null) {
-                log.debug("Missing meter for downstream {} on {}/{}", downstreamBpInfo.id(), deviceId, subscriberPort);
+                log.debug("Missing meter for downstream {} on {}", downstreamBpInfo.id(), subscriberPort);
                 checkAndCreateDevMeter(deviceId, downstreamBpInfo);
             }
         }
@@ -980,8 +976,8 @@
                         if (upMeterId != null && downMeterId != null) {
                             log.debug("Provisioning subscriber after meter {} " +
                                               "installation and both meters are present " +
-                                              "upstream {} and downstream {} on {}/{}",
-                                      meterId, upMeterId, downMeterId, deviceId, fi.getUniPort());
+                                              "upstream {} and downstream {} on {}",
+                                      meterId, upMeterId, downMeterId, fi.getUniPort());
                             // put in the meterIds  because when fi was first
                             // created there may or may not have been a meterId
                             // depending on whether the meter was created or
@@ -994,9 +990,8 @@
                         oltMeterService.removeFromPendingMeters(deviceId, bwpInfo);
                     } else {
                         // meter install failed
-                        log.error("Addition of subscriber {} on {}/{} failed due to meter " +
-                                          "{} with result {}", fi, deviceId, fi.getUniPort(),
-                                  meterId, result);
+                        log.error("Addition of subscriber {} on {} failed due to meter " +
+                                          "{} with result {}", fi, fi.getUniPort(), meterId, result);
                         queue.remove(fi);
                         oltMeterService.removeFromPendingMeters(deviceId, bwpInfo);
                     }
@@ -1021,7 +1016,8 @@
             Optional<MacAddress> macAddress =
                     getMacAddress(subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort(), tagInfo);
             if (subscriberFlowInfo.getTagInfo().getEnableMacLearning()) {
-                ConnectPoint cp = new ConnectPoint(subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort());
+                ConnectPoint cp = new ConnectPoint(subscriberFlowInfo.getDevId(),
+                        subscriberFlowInfo.getUniPort().number());
                 if (macAddress.isPresent()) {
                     log.debug("MAC Address {} obtained for {}", macAddress.get(), subscriberFlowInfo);
                 } else {
@@ -1030,9 +1026,8 @@
                 }
 
                 CompletableFuture<ObjectiveError> dhcpFuture = new CompletableFuture<>();
-                oltFlowService.processDhcpFilteringObjectives(subscriberFlowInfo.getDevId(),
-                        subscriberFlowInfo.getUniPort(), subscriberFlowInfo.getUpId(),
-                        tagInfo, true, true, Optional.of(dhcpFuture));
+                oltFlowService.processDhcpFilteringObjectives(subscriberFlowInfo.getUniPort(),
+                        subscriberFlowInfo.getUpId(), tagInfo, true, true, Optional.of(dhcpFuture));
                 dhcpFuture.thenAcceptAsync(dhcpStatus -> {
                     if (dhcpStatus != null) {
                         log.error("Dhcp Objective failed for {}: {}", subscriberFlowInfo, dhcpStatus);
@@ -1040,8 +1035,7 @@
                             waitingMacSubscribers.remove(cp, subscriberFlowInfo);
                         }
                         post(new AccessDeviceEvent(AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTRATION_FAILED,
-                                subscriberFlowInfo.getDevId(),
-                                deviceService.getPort(subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort()),
+                                subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort().port(),
                                 tagInfo.getPonSTag(), tagInfo.getPonCTag(), tagInfo.getTechnologyProfileId()));
                     } else {
                         log.debug("Dhcp Objective success for: {}", subscriberFlowInfo);
@@ -1062,20 +1056,19 @@
     }
 
     private void continueProvisioningSubs(SubscriberFlowInfo subscriberFlowInfo, Optional<MacAddress> macAddress) {
-        log.debug("Provisioning subscriber flows on {}/{} based on {}",
-                  subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort(), subscriberFlowInfo);
+        AccessDevicePort uniPort = subscriberFlowInfo.getUniPort();
+        log.debug("Provisioning subscriber flows on {} based on {}", uniPort, subscriberFlowInfo);
         UniTagInformation tagInfo = subscriberFlowInfo.getTagInfo();
         CompletableFuture<ObjectiveError> upFuture = new CompletableFuture<>();
         CompletableFuture<ObjectiveError> downFuture = new CompletableFuture<>();
 
         ForwardingObjective.Builder upFwd =
-                oltFlowService.createUpBuilder(subscriberFlowInfo.getNniPort(), subscriberFlowInfo.getUniPort(),
+                oltFlowService.createUpBuilder(subscriberFlowInfo.getNniPort(), uniPort,
                                                subscriberFlowInfo.getUpId(), subscriberFlowInfo.getTagInfo());
         flowObjectiveService.forward(subscriberFlowInfo.getDevId(), upFwd.add(new ObjectiveContext() {
             @Override
             public void onSuccess(Objective objective) {
-                log.debug("Upstream HSIA flow {} installed successfully on {}/{}",
-                        subscriberFlowInfo, subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort());
+                log.debug("Upstream HSIA flow {} installed successfully on {}", subscriberFlowInfo, uniPort);
                 upFuture.complete(null);
             }
 
@@ -1086,13 +1079,12 @@
         }));
 
         ForwardingObjective.Builder downFwd =
-                oltFlowService.createDownBuilder(subscriberFlowInfo.getNniPort(), subscriberFlowInfo.getUniPort(),
+                oltFlowService.createDownBuilder(subscriberFlowInfo.getNniPort(), uniPort,
                         subscriberFlowInfo.getDownId(), subscriberFlowInfo.getTagInfo(), macAddress);
         flowObjectiveService.forward(subscriberFlowInfo.getDevId(), downFwd.add(new ObjectiveContext() {
             @Override
             public void onSuccess(Objective objective) {
-                log.debug("Downstream HSIA flow {} installed successfully on {}/{}",
-                        subscriberFlowInfo, subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort());
+                log.debug("Downstream HSIA flow {} installed successfully on {}", subscriberFlowInfo, uniPort);
                 downFuture.complete(null);
             }
 
@@ -1105,47 +1097,32 @@
         upFuture.thenAcceptBothAsync(downFuture, (upStatus, downStatus) -> {
             AccessDeviceEvent.Type type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTERED;
             if (downStatus != null) {
-                log.error("Flow with innervlan {} and outerVlan {} on {}/{} failed downstream installation: {}",
-                          tagInfo.getPonCTag(), tagInfo.getPonSTag(), subscriberFlowInfo.getDevId(),
-                          subscriberFlowInfo.getUniPort(), downStatus);
+                log.error("Flow with innervlan {} and outerVlan {} on {} failed downstream installation: {}",
+                        tagInfo.getPonCTag(), tagInfo.getPonSTag(), uniPort, downStatus);
                 type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTRATION_FAILED;
             } else if (upStatus != null) {
-                log.error("Flow with innervlan {} and outerVlan {} on {}/{} failed upstream installation: {}",
-                          tagInfo.getPonCTag(), tagInfo.getPonSTag(), subscriberFlowInfo.getDevId(),
-                          subscriberFlowInfo.getUniPort(), upStatus);
+                log.error("Flow with innervlan {} and outerVlan {} on {} failed upstream installation: {}",
+                        tagInfo.getPonCTag(), tagInfo.getPonSTag(), uniPort, upStatus);
                 type = AccessDeviceEvent.Type.SUBSCRIBER_UNI_TAG_REGISTRATION_FAILED;
             } else {
-                log.debug("Upstream and downstream data plane flows are installed successfully " +
-                                 "for {}/{}", subscriberFlowInfo.getDevId(), subscriberFlowInfo.getUniPort());
-                oltFlowService.processEapolFilteringObjectives(subscriberFlowInfo.getDevId(),
-                                                               subscriberFlowInfo.getUniPort(),
-                                                               tagInfo.getUpstreamBandwidthProfile(),
+                log.debug("Upstream and downstream data plane flows are installed successfully on {}", uniPort);
+                oltFlowService.processEapolFilteringObjectives(uniPort, tagInfo.getUpstreamBandwidthProfile(),
                                                                null, tagInfo.getPonCTag(), true);
 
 
                 if (!tagInfo.getEnableMacLearning()) {
-                    oltFlowService.processDhcpFilteringObjectives(subscriberFlowInfo.getDevId(),
-                                                                  subscriberFlowInfo.getUniPort(),
-                                                                  subscriberFlowInfo.getUpId(),
+                    oltFlowService.processDhcpFilteringObjectives(uniPort, subscriberFlowInfo.getUpId(),
                                                                   tagInfo, true, true, Optional.empty());
                 }
 
-                oltFlowService.processIgmpFilteringObjectives(subscriberFlowInfo.getDevId(),
-                                                              subscriberFlowInfo.getUniPort(),
-                                                              subscriberFlowInfo.getUpId(),
+                oltFlowService.processIgmpFilteringObjectives(uniPort, subscriberFlowInfo.getUpId(),
                                                               tagInfo, true, true);
 
-                oltFlowService.processPPPoEDFilteringObjectives(subscriberFlowInfo.getDevId(),
-                                                                subscriberFlowInfo.getUniPort(),
-                                                                subscriberFlowInfo.getUpId(),
+                oltFlowService.processPPPoEDFilteringObjectives(uniPort, subscriberFlowInfo.getUpId(),
                                                                 tagInfo, true, true);
-                updateProgrammedSubscriber(new ConnectPoint(subscriberFlowInfo.getDevId(),
-                                                            subscriberFlowInfo.getUniPort()),
-                                           tagInfo, true);
+                updateProgrammedSubscriber(uniPort, tagInfo, true);
             }
-            post(new AccessDeviceEvent(type, subscriberFlowInfo.getDevId(),
-                                       deviceService.getPort(subscriberFlowInfo.getDevId(),
-                                                             subscriberFlowInfo.getUniPort()),
+            post(new AccessDeviceEvent(type, subscriberFlowInfo.getDevId(), uniPort.port(),
                                        tagInfo.getPonSTag(), tagInfo.getPonCTag(),
                                        tagInfo.getTechnologyProfileId()));
         }, oltInstallers);
@@ -1155,27 +1132,26 @@
      * Gets mac address from tag info if present, else checks the host service.
      *
      * @param deviceId device ID
-     * @param portNumber uni port
+     * @param port uni port
      * @param tagInformation tag info
      * @return MAC Address of subscriber
      */
-    private Optional<MacAddress> getMacAddress(DeviceId deviceId, PortNumber portNumber,
+    private Optional<MacAddress> getMacAddress(DeviceId deviceId, AccessDevicePort port,
                                                UniTagInformation tagInformation) {
         if (isMacAddressValid(tagInformation)) {
-            log.debug("Got MAC Address {} from the uniTagInformation for dev/port {}/{} and cTag {}",
-                    tagInformation.getConfiguredMacAddress(), deviceId, portNumber, tagInformation.getPonCTag());
+            log.debug("Got MAC Address {} from the uniTagInformation for {} and cTag {}",
+                    tagInformation.getConfiguredMacAddress(), port, tagInformation.getPonCTag());
             return Optional.of(MacAddress.valueOf(tagInformation.getConfiguredMacAddress()));
         } else if (tagInformation.getEnableMacLearning()) {
-            Optional<Host> optHost = hostService.getConnectedHosts(new ConnectPoint(deviceId, portNumber))
+            Optional<Host> optHost = hostService.getConnectedHosts(new ConnectPoint(deviceId, port.number()))
                     .stream().filter(host -> host.vlan().equals(tagInformation.getPonCTag())).findFirst();
             if (optHost.isPresent()) {
-                log.debug("Got MAC Address {} from the hostService for dev/port {}/{} and cTag {}",
-                        optHost.get().mac(), deviceId, portNumber, tagInformation.getPonCTag());
+                log.debug("Got MAC Address {} from the hostService for {} and cTag {}",
+                        optHost.get().mac(), port, tagInformation.getPonCTag());
                 return Optional.of(optHost.get().mac());
             }
         }
-        log.debug("Could not obtain MAC Address for dev/port {}/{} and cTag {}", deviceId, portNumber,
-                tagInformation.getPonCTag());
+        log.debug("Could not obtain MAC Address for {} and cTag {}", port, tagInformation.getPonCTag());
         return Optional.empty();
     }
 
@@ -1190,25 +1166,25 @@
      * using the pon c tag, pon s tag and the technology profile id
      * May return Optional<null>
      *
-     * @param cp        the connection point of the subscriber
+     * @param port        port of the subscriber
      * @param innerVlan pon c tag
      * @param outerVlan pon s tag
      * @param tpId      the technology profile id
      * @return the found uni tag information
      */
-    private Optional<UniTagInformation> getUniTagInformation(ConnectPoint cp, VlanId innerVlan, VlanId outerVlan,
-                                                             int tpId) {
-        log.debug("Getting uni tag information for cp: {}, innerVlan: {}, outerVlan: {}, tpId: {}",
-                cp.toString(), innerVlan, outerVlan, tpId);
-        SubscriberAndDeviceInformation subInfo = getSubscriber(cp);
+    private Optional<UniTagInformation> getUniTagInformation(AccessDevicePort port, VlanId innerVlan,
+                                                             VlanId outerVlan, int tpId) {
+        log.debug("Getting uni tag information for {}, innerVlan: {}, outerVlan: {}, tpId: {}",
+                port, innerVlan, outerVlan, tpId);
+        SubscriberAndDeviceInformation subInfo = getSubscriber(new ConnectPoint(port.deviceId(), port.number()));
         if (subInfo == null) {
-            log.warn("Subscriber information doesn't exist for the connect point {}", cp.toString());
+            log.warn("Subscriber information doesn't exist for {}", port);
             return Optional.empty();
         }
 
         List<UniTagInformation> uniTagList = subInfo.uniTagList();
         if (uniTagList == null) {
-            log.warn("Uni tag list is not found for the subscriber {} on {}", subInfo.id(), cp.toString());
+            log.warn("Uni tag list is not found for the subscriber {} on {}", subInfo.id(), port);
             return Optional.empty();
         }
 
@@ -1223,7 +1199,7 @@
 
         if (service == null) {
             log.warn("SADIS doesn't include the service with ponCtag {} ponStag {} and tpId {} on {}",
-                     innerVlan, outerVlan, tpId, cp.toString());
+                     innerVlan, outerVlan, tpId, port);
             return Optional.empty();
         }
 
@@ -1249,16 +1225,17 @@
                     continue;
                 }
                 if (isUniPort(dev, p)) {
+                    AccessDevicePort port = new AccessDevicePort(p, AccessDevicePort.Type.UNI);
                     if (!programmedSubs.containsKey(new ConnectPoint(dev.id(), p.number()))) {
-                        log.info("Creating Eapol on {}/{}", dev.id(), p.number());
-                        oltFlowService.processEapolFilteringObjectives(dev.id(), p.number(), defaultBpId, null,
+                        log.info("Creating Eapol on {}", port);
+                        oltFlowService.processEapolFilteringObjectives(port, defaultBpId, null,
                                                                        VlanId.vlanId(EAPOL_DEFAULT_VLAN), true);
                     } else {
-                        log.debug("Subscriber Eapol on {}/{} is already provisioned, not installing default",
-                                dev.id(), p.number());
+                        log.debug("Subscriber Eapol on {} is already provisioned, not installing default", port);
                     }
                 } else {
-                    oltFlowService.processNniFilteringObjectives(dev.id(), p.number(), true);
+                    AccessDevicePort port = new AccessDevicePort(p, AccessDevicePort.Type.NNI);
+                    oltFlowService.processNniFilteringObjectives(port, true);
                 }
             }
         }
@@ -1274,7 +1251,7 @@
      * @param dev Device to look for
      * @return The uplink Port of the OLT
      */
-    private Port getUplinkPort(Device dev) {
+    private AccessDevicePort getUplinkPort(Device dev) {
         // check if this device is provisioned in Sadis
         SubscriberAndDeviceInformation deviceInfo = getOltInfo(dev);
         log.trace("getUplinkPort: deviceInfo {}", deviceInfo);
@@ -1290,7 +1267,7 @@
                 .findFirst();
         if (optionalPort.isPresent()) {
             log.trace("getUplinkPort: Found port {}", optionalPort.get());
-            return optionalPort.get();
+            return new AccessDevicePort(optionalPort.get(), AccessDevicePort.Type.NNI);
         }
 
         log.warn("getUplinkPort: " + NO_UPLINK_PORT, dev.id());
@@ -1322,7 +1299,7 @@
      * @return true if the given port is a uni port
      */
     private boolean isUniPort(Device d, Port p) {
-        Port ulPort = getUplinkPort(d);
+        AccessDevicePort ulPort = getUplinkPort(d);
         if (ulPort != null) {
             return (ulPort.number().toLong() != p.number().toLong());
         }
@@ -1398,8 +1375,10 @@
                         break;
                     case HOST_UPDATED:
                         if (event.prevSubject() != null && !event.prevSubject().mac().equals(event.subject().mac())) {
-                            log.debug("Subscriber's MAC address changed. devId/port: {}/{} vlan: {}",
-                                    host.location().deviceId(), host.location().port(), host.vlan());
+                            log.debug("Subscriber's MAC address changed from {} to {}. " +
+                                            "devId/portNumber: {}/{} vlan: {}", event.prevSubject().mac(),
+                                    event.subject().mac(), host.location().deviceId(), host.location().port(),
+                                    host.vlan());
                             // TODO handle subscriber MAC Address changed
                         } else {
                             log.debug("Unhandled HOST_UPDATED event: {}", event);
@@ -1425,7 +1404,7 @@
             eventExecutor.execute(() -> {
                 DeviceId devId = event.subject().id();
                 Device dev = event.subject();
-                Port port = event.port();
+                Port p = event.port();
                 DeviceEvent.Type eventType = event.type();
 
                 if (DeviceEvent.Type.PORT_STATS_UPDATED.equals(eventType) ||
@@ -1464,6 +1443,14 @@
                         return;
                     }
                 }
+                AccessDevicePort port = null;
+                if (p != null) {
+                    if (isUniPort(dev, p)) {
+                        port = new AccessDevicePort(p, AccessDevicePort.Type.UNI);
+                    } else {
+                        port = new AccessDevicePort(p, AccessDevicePort.Type.NNI);
+                    }
+                }
 
                 switch (event.type()) {
                     //TODO: Port handling and bookkeeping should be improved once
@@ -1473,12 +1460,12 @@
                             log.warn("Received {} for disconnected device {}, ignoring", event, devId);
                             return;
                         }
-                        if (isUniPort(dev, port)) {
-                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_ADDED, devId, port));
+                        if (port.type().equals(AccessDevicePort.Type.UNI)) {
+                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_ADDED, devId, port.port()));
 
                             if (port.isEnabled() && !port.number().equals(PortNumber.LOCAL)) {
-                                log.info("eapol will be sent for port added {}/{}", devId, port);
-                                oltFlowService.processEapolFilteringObjectives(devId, port.number(), defaultBpId,
+                                log.info("eapol will be sent for port added {}", port);
+                                oltFlowService.processEapolFilteringObjectives(port, defaultBpId,
                                                                                null,
                                                                                VlanId.vlanId(EAPOL_DEFAULT_VLAN),
                                                                                true);
@@ -1486,29 +1473,28 @@
                         } else {
                             SubscriberAndDeviceInformation deviceInfo = getOltInfo(dev);
                             if (deviceInfo != null) {
-                                oltFlowService.processNniFilteringObjectives(dev.id(), port.number(), true);
+                                oltFlowService.processNniFilteringObjectives(port, true);
                             }
                         }
                         break;
                     case PORT_REMOVED:
-                        if (isUniPort(dev, port)) {
+                        if (port.type().equals(AccessDevicePort.Type.UNI)) {
                             // if no subscriber is provisioned we need to remove the default EAPOL
                             // if a subscriber was provisioned the default EAPOL will not be there and we can skip.
                             // The EAPOL with subscriber tag will be removed by removeSubscriber call.
                             Collection<? extends UniTagInformation> uniTagInformationSet =
-                                    programmedSubs.get(new ConnectPoint(port.element().id(), port.number())).value();
+                                    programmedSubs.get(new ConnectPoint(port.deviceId(), port.number())).value();
                             if (uniTagInformationSet == null || uniTagInformationSet.isEmpty()) {
-                                log.info("No subscriber provisioned on port {}/{} in PORT_REMOVED event, " +
-                                                 "removing default EAPOL flow", devId, port);
-                                oltFlowService.processEapolFilteringObjectives(devId, port.number(), defaultBpId,
-                                                                               null,
+                                log.info("No subscriber provisioned on port {} in PORT_REMOVED event, " +
+                                                 "removing default EAPOL flow", port);
+                                oltFlowService.processEapolFilteringObjectives(port, defaultBpId, null,
                                                                                VlanId.vlanId(EAPOL_DEFAULT_VLAN),
                                                                                false);
                             } else {
-                                removeSubscriber(new ConnectPoint(devId, port.number()));
+                                removeSubscriber(port);
                             }
 
-                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_REMOVED, devId, port));
+                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_REMOVED, devId, port.port()));
                         }
                         break;
                     case PORT_UPDATED:
@@ -1516,13 +1502,11 @@
                             log.warn("Received {} for disconnected device {}, ignoring", event, devId);
                             return;
                         }
-                        if (!isUniPort(dev, port)) {
+                        if (port.type().equals(AccessDevicePort.Type.NNI)) {
                             SubscriberAndDeviceInformation deviceInfo = getOltInfo(dev);
                             if (deviceInfo != null && port.isEnabled()) {
-                                log.debug("NNI dev/port {}/{} enabled", dev.id(),
-                                          port.number());
-                                oltFlowService.processNniFilteringObjectives(dev.id(),
-                                                                             port.number(), true);
+                                log.debug("NNI {} enabled", port);
+                                oltFlowService.processNniFilteringObjectives(port, true);
                             }
                             return;
                         }
@@ -1530,27 +1514,25 @@
                         Collection<? extends UniTagInformation> uniTagInformationSet = programmedSubs.get(cp).value();
                         if (uniTagInformationSet == null || uniTagInformationSet.isEmpty()) {
                             if (!port.number().equals(PortNumber.LOCAL)) {
-                                log.info("eapol will be {} for dev/port updated {}/{} with default vlan {}",
-                                         (port.isEnabled()) ? "added" : "removed",
-                                         devId, port.number(), EAPOL_DEFAULT_VLAN);
-                                oltFlowService.processEapolFilteringObjectives(devId, port.number(), defaultBpId,
-                                                                               null,
+                                log.info("eapol will be {} updated for {} with default vlan {}",
+                                         (port.isEnabled()) ? "added" : "removed", port, EAPOL_DEFAULT_VLAN);
+                                oltFlowService.processEapolFilteringObjectives(port, defaultBpId, null,
                                                                                VlanId.vlanId(EAPOL_DEFAULT_VLAN),
                                                                                port.isEnabled());
                             }
                         } else {
-                            log.info("eapol will be {} for dev/port updated {}/{}",
-                                     (port.isEnabled()) ? "added" : "removed",
-                                     devId, port.number());
-                            uniTagInformationSet.forEach(uniTag ->
-                                oltFlowService.processEapolFilteringObjectives(devId, port.number(),
-                                    uniTag.getUpstreamBandwidthProfile(), null,
-                                    uniTag.getPonCTag(), port.isEnabled()));
+                            log.info("eapol will be {} updated for {}", (port.isEnabled()) ? "added" : "removed",
+                                     port);
+                            for (UniTagInformation uniTag : uniTagInformationSet) {
+                                oltFlowService.processEapolFilteringObjectives(port,
+                                        uniTag.getUpstreamBandwidthProfile(), null,
+                                        uniTag.getPonCTag(), port.isEnabled());
+                            }
                         }
                         if (port.isEnabled()) {
-                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_ADDED, devId, port));
+                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_ADDED, devId, port.port()));
                         } else {
-                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_REMOVED, devId, port));
+                            post(new AccessDeviceEvent(AccessDeviceEvent.Type.UNI_REMOVED, devId, port.port()));
                         }
                         break;
                     case DEVICE_ADDED:
diff --git a/impl/src/main/java/org/opencord/olt/impl/OltFlowService.java b/impl/src/main/java/org/opencord/olt/impl/OltFlowService.java
index fed9546..83919a4 100644
--- a/impl/src/main/java/org/opencord/olt/impl/OltFlowService.java
+++ b/impl/src/main/java/org/opencord/olt/impl/OltFlowService.java
@@ -27,10 +27,8 @@
 import org.onosproject.core.ApplicationId;
 import org.onosproject.core.CoreService;
 import org.onosproject.mastership.MastershipService;
-import org.onosproject.net.AnnotationKeys;
 import org.onosproject.net.ConnectPoint;
 import org.onosproject.net.DeviceId;
-import org.onosproject.net.Port;
 import org.onosproject.net.PortNumber;
 import org.onosproject.net.device.DeviceService;
 import org.onosproject.net.flow.DefaultTrafficSelector;
@@ -50,6 +48,7 @@
 import org.onosproject.store.serializers.KryoNamespaces;
 import org.onosproject.store.service.Serializer;
 import org.onosproject.store.service.StorageService;
+import org.opencord.olt.AccessDevicePort;
 import org.opencord.olt.internalapi.AccessDeviceFlowService;
 import org.opencord.olt.internalapi.AccessDeviceMeterService;
 import org.opencord.sadis.BandwidthProfileInformation;
@@ -189,6 +188,8 @@
                 .register(KryoNamespaces.API)
                 .register(UniTagInformation.class)
                 .register(SubscriberFlowInfo.class)
+                .register(AccessDevicePort.class)
+                .register(AccessDevicePort.Type.class)
                 .register(LinkedBlockingQueue.class)
                 .build();
         pendingEapolForDevice = storageService.<DeviceId, BlockingQueue<SubscriberFlowInfo>>consistentMapBuilder()
@@ -268,7 +269,7 @@
     }
 
     @Override
-    public void processDhcpFilteringObjectives(DeviceId devId, PortNumber port,
+    public void processDhcpFilteringObjectives(AccessDevicePort port,
                                                MeterId upstreamMeterId,
                                                UniTagInformation tagInformation,
                                                boolean install,
@@ -277,17 +278,15 @@
         if (upstream) {
             // for UNI ports
             if (tagInformation != null && !tagInformation.getIsDhcpRequired()) {
-                log.debug("Dhcp provisioning is disabled for UNI port {} on "
-                        + "device {} for service {}", port, devId,
-                        tagInformation.getServiceName());
+                log.debug("Dhcp provisioning is disabled for UNI port {} for service {}",
+                        port, tagInformation.getServiceName());
                 dhcpFuture.ifPresent(f -> f.complete(null));
                 return;
             }
         } else {
             // for NNI ports
             if (!enableDhcpOnNni) {
-                log.debug("Dhcp provisioning is disabled for NNI port {} on "
-                        + "device {}", port, devId);
+                log.debug("Dhcp provisioning is disabled for NNI port {}", port);
                 dhcpFuture.ifPresent(f -> f.complete(null));
                 return;
             }
@@ -306,7 +305,7 @@
             EthType ethType = EthType.EtherType.IPV4.ethType();
             byte protocol = IPv4.PROTOCOL_UDP;
 
-            addDhcpFilteringObjectives(devId, port, udpSrc, udpDst, ethType,
+            addDhcpFilteringObjectives(port, udpSrc, udpDst, ethType,
                     upstreamMeterId, techProfileId, protocol, cTag, unitagMatch,
                                        vlanPcp, upstream, install, dhcpFuture);
         }
@@ -318,13 +317,13 @@
             EthType ethType = EthType.EtherType.IPV6.ethType();
             byte protocol = IPv6.PROTOCOL_UDP;
 
-            addDhcpFilteringObjectives(devId, port, udpSrc, udpDst, ethType,
+            addDhcpFilteringObjectives(port, udpSrc, udpDst, ethType,
                     upstreamMeterId, techProfileId, protocol, cTag, unitagMatch,
                                        vlanPcp, upstream, install, dhcpFuture);
         }
     }
 
-    private void addDhcpFilteringObjectives(DeviceId devId, PortNumber port, int udpSrc, int udpDst,
+    private void addDhcpFilteringObjectives(AccessDevicePort port, int udpSrc, int udpDst,
                                             EthType ethType, MeterId upstreamMeterId, int techProfileId, byte protocol,
                                             VlanId cTag, VlanId unitagMatch,
                                             Byte vlanPcp, boolean upstream,
@@ -342,7 +341,7 @@
         }
 
         FilteringObjective.Builder dhcpUpstreamBuilder = (install ? builder.permit() : builder.deny())
-                .withKey(Criteria.matchInPort(port))
+                .withKey(Criteria.matchInPort(port.number()))
                 .addCondition(Criteria.matchEthType(ethType))
                 .addCondition(Criteria.matchIPProtocol(protocol))
                 .addCondition(Criteria.matchUdpSrc(TpPort.tpPort(udpSrc)))
@@ -368,27 +367,27 @@
         FilteringObjective dhcpUpstream = dhcpUpstreamBuilder.add(new ObjectiveContext() {
             @Override
             public void onSuccess(Objective objective) {
-                log.info("DHCP {} filter for dev/port {}/{} {}.",
-                        (ethType.equals(EthType.EtherType.IPV4.ethType())) ? V4 : V6,
-                        devId, port, (install) ? INSTALLED : REMOVED);
+                log.info("DHCP {} filter for {} {}.",
+                        (ethType.equals(EthType.EtherType.IPV4.ethType())) ? V4 : V6, port,
+                        (install) ? INSTALLED : REMOVED);
                 dhcpFuture.ifPresent(f -> f.complete(null));
             }
 
             @Override
             public void onError(Objective objective, ObjectiveError error) {
-                log.error("DHCP {} filter for dev/port {}/{} failed {} because {}",
-                        (ethType.equals(EthType.EtherType.IPV4.ethType())) ? V4 : V6,
-                        devId, port, (install) ? INSTALLATION : REMOVAL,
+                log.error("DHCP {} filter for {} failed {} because {}",
+                        (ethType.equals(EthType.EtherType.IPV4.ethType())) ? V4 : V6, port,
+                        (install) ? INSTALLATION : REMOVAL,
                         error);
                 dhcpFuture.ifPresent(f -> f.complete(error));
             }
         });
-        flowObjectiveService.filter(devId, dhcpUpstream);
+        flowObjectiveService.filter(port.deviceId(), dhcpUpstream);
 
     }
 
     @Override
-    public void processPPPoEDFilteringObjectives(DeviceId devId, PortNumber portNumber,
+    public void processPPPoEDFilteringObjectives(AccessDevicePort port,
                                                  MeterId upstreamMeterId,
                                                  UniTagInformation tagInformation,
                                                  boolean install,
@@ -425,7 +424,7 @@
         }
 
         DefaultFilteringObjective.Builder pppoedBuilder = (install ? builder.permit() : builder.deny())
-                .withKey(Criteria.matchInPort(portNumber))
+                .withKey(Criteria.matchInPort(port.number()))
                 .addCondition(Criteria.matchEthType(EthType.EtherType.PPPoED.ethType()))
                 .fromApp(appId)
                 .withPriority(10000);
@@ -445,21 +444,20 @@
                 .add(new ObjectiveContext() {
                     @Override
                     public void onSuccess(Objective objective) {
-                        log.info("PPPoED filter for {} on {} {}.",
-                                devId, portNumber, (install) ? INSTALLED : REMOVED);
+                        log.info("PPPoED filter for {} {}.", port, (install) ? INSTALLED : REMOVED);
                     }
 
                     @Override
                     public void onError(Objective objective, ObjectiveError error) {
-                        log.info("PPPoED filter for {} on {} failed {} because {}",
-                                devId, portNumber, (install) ? INSTALLATION : REMOVAL, error);
+                        log.info("PPPoED filter for {} failed {} because {}", port,
+                                (install) ? INSTALLATION : REMOVAL, error);
                     }
                 });
-        flowObjectiveService.filter(devId, pppoed);
+        flowObjectiveService.filter(port.deviceId(), pppoed);
     }
 
     @Override
-    public void processIgmpFilteringObjectives(DeviceId devId, PortNumber port,
+    public void processIgmpFilteringObjectives(AccessDevicePort port,
                                                MeterId upstreamMeterId,
                                                UniTagInformation tagInformation,
                                                boolean install,
@@ -467,22 +465,19 @@
         if (upstream) {
             // for UNI ports
             if (tagInformation != null && !tagInformation.getIsIgmpRequired()) {
-                log.debug("Igmp provisioning is disabled for UNI port {} on "
-                        + "device {} for service {}", port, devId,
-                          tagInformation.getServiceName());
+                log.debug("Igmp provisioning is disabled for UNI port {} for service {}",
+                        port, tagInformation.getServiceName());
                 return;
             }
         } else {
             // for NNI ports
             if (!enableIgmpOnNni) {
-                log.debug("Igmp provisioning is disabled for NNI port {} on device {}",
-                          port, devId);
+                log.debug("Igmp provisioning is disabled for NNI port {}", port);
                 return;
             }
         }
 
-        log.debug("{} IGMP flows on {}:{}", (install) ?
-                "Installing" : "Removing", devId, port);
+        log.debug("{} IGMP flows on {}", (install) ? "Installing" : "Removing", port);
         DefaultFilteringObjective.Builder filterBuilder = DefaultFilteringObjective.builder();
         TrafficTreatment.Builder treatmentBuilder = DefaultTrafficTreatment.builder();
         if (upstream) {
@@ -513,7 +508,7 @@
         filterBuilder = install ? filterBuilder.permit() : filterBuilder.deny();
 
         FilteringObjective igmp = filterBuilder
-                .withKey(Criteria.matchInPort(port))
+                .withKey(Criteria.matchInPort(port.number()))
                 .addCondition(Criteria.matchEthType(EthType.EtherType.IPV4.ethType()))
                 .addCondition(Criteria.matchIPProtocol(IPv4.PROTOCOL_IGMP))
                 .withMeta(treatmentBuilder
@@ -523,61 +518,60 @@
                 .add(new ObjectiveContext() {
                     @Override
                     public void onSuccess(Objective objective) {
-                        log.info("Igmp filter for dev/port {}/{} {}.",
-                                devId, port, (install) ? INSTALLED : REMOVED);
+                        log.info("Igmp filter for {} {}.", port, (install) ? INSTALLED : REMOVED);
                     }
 
                     @Override
                     public void onError(Objective objective, ObjectiveError error) {
-                        log.error("Igmp filter for dev/port {}/{} failed {} because {}.",
-                                devId, port, (install) ? INSTALLATION : REMOVAL,
+                        log.error("Igmp filter for {} failed {} because {}.", port, (install) ? INSTALLATION : REMOVAL,
                                 error);
                     }
                 });
 
-        flowObjectiveService.filter(devId, igmp);
+        flowObjectiveService.filter(port.deviceId(), igmp);
     }
 
     @Override
-    public void processEapolFilteringObjectives(DeviceId devId, PortNumber portNumber, String bpId,
+    public void processEapolFilteringObjectives(AccessDevicePort port, String bpId,
                                                 CompletableFuture<ObjectiveError> filterFuture,
                                                 VlanId vlanId, boolean install) {
 
         if (!enableEapol) {
-            log.debug("Eapol filtering is disabled. Completing filteringFuture immediately for the device {}", devId);
+            log.debug("Eapol filtering is disabled. Completing filteringFuture immediately for the device {}",
+                    port.deviceId());
             if (filterFuture != null) {
                 filterFuture.complete(null);
             }
             return;
         }
-        log.info("Processing EAPOL with Bandwidth profile {} on {}/{}", bpId,
-                 devId, portNumber);
+        log.info("Processing EAPOL with Bandwidth profile {} on {}", bpId, port);
         BandwidthProfileInformation bpInfo = getBandwidthProfileInformation(bpId);
         if (bpInfo == null) {
             log.warn("Bandwidth profile {} is not found. Authentication flow"
-                    + " will not be installed on {}/{}", bpId, devId, portNumber);
+                    + " will not be installed on {}", bpId, port);
             if (filterFuture != null) {
                 filterFuture.complete(ObjectiveError.BADPARAMS);
             }
             return;
         }
 
-        ConnectPoint cp = new ConnectPoint(devId, portNumber);
+        ConnectPoint cp = new ConnectPoint(port.deviceId(), port.number());
         DefaultFilteringObjective.Builder filterBuilder = DefaultFilteringObjective.builder();
         TrafficTreatment.Builder treatmentBuilder = DefaultTrafficTreatment.builder();
         CompletableFuture<Object> meterFuture = new CompletableFuture<>();
         // check if meter exists and create it only for an install
-        final MeterId meterId = oltMeterService.getMeterIdFromBpMapping(devId, bpInfo.id());
-        log.info("Meter id {} for Bandwidth profile {} associated to EAPOL on {}", meterId, bpInfo.id(), devId);
+        final MeterId meterId = oltMeterService.getMeterIdFromBpMapping(port.deviceId(), bpInfo.id());
+        log.info("Meter id {} for Bandwidth profile {} associated to EAPOL on {}",
+                meterId, bpInfo.id(), port.deviceId());
         if (meterId == null) {
             if (install) {
-                log.debug("Need to install meter for EAPOL with bwp {} on dev/port {}", bpInfo.id(), cp.toString());
-                SubscriberFlowInfo fi = new SubscriberFlowInfo(devId, null, cp.port(),
+                log.debug("Need to install meter for EAPOL with bwp {} on {}", bpInfo.id(), port);
+                SubscriberFlowInfo fi = new SubscriberFlowInfo(null, port,
                                                                new UniTagInformation.Builder()
                                                                        .setPonCTag(vlanId).build(),
                                                                null, null,
                                                                null, bpInfo.id());
-                pendingEapolForDevice.compute(devId, (id, queue) -> {
+                pendingEapolForDevice.compute(port.deviceId(), (id, queue) -> {
                     if (queue == null) {
                         queue = new LinkedBlockingQueue<>();
                     }
@@ -586,11 +580,10 @@
                 });
 
                 //If false the meter is already being installed, skipping installation
-                if (!oltMeterService.checkAndAddPendingMeter(devId, bpInfo)) {
+                if (!oltMeterService.checkAndAddPendingMeter(port.deviceId(), bpInfo)) {
                     return;
                 }
-                MeterId innerMeterId = oltMeterService.createMeter(devId, bpInfo,
-                                                                   meterFuture);
+                MeterId innerMeterId = oltMeterService.createMeter(port.deviceId(), bpInfo, meterFuture);
                 fi.setUpMeterId(innerMeterId);
             } else {
                 // this case should not happen as the request to remove an eapol
@@ -598,8 +591,8 @@
                 // Nevertheless we can still delete the flow as we only need the
                 // correct 'match' to do so.
                 log.warn("Unknown meter id for bp {}, still proceeding with "
-                        + "delete of eapol flow for {}", bpInfo.id(), cp.toString());
-                SubscriberFlowInfo fi = new SubscriberFlowInfo(devId, null, cp.port(),
+                        + "delete of eapol flow on {}", bpInfo.id(), port);
+                SubscriberFlowInfo fi = new SubscriberFlowInfo(null, port,
                                                                new UniTagInformation.Builder()
                                                                        .setPonCTag(vlanId).build(),
                                                                null, meterId,
@@ -607,8 +600,8 @@
                 handleEapol(filterFuture, install, cp, filterBuilder, treatmentBuilder, fi, meterId);
             }
         } else {
-            log.debug("Meter {} was previously created for bp {} on {}", meterId, bpInfo.id(), cp.toString());
-            SubscriberFlowInfo fi = new SubscriberFlowInfo(devId, null, cp.port(),
+            log.debug("Meter {} was previously created for bp {} on {}", meterId, bpInfo.id(), port);
+            SubscriberFlowInfo fi = new SubscriberFlowInfo(null, port,
                                                            new UniTagInformation.Builder()
                                                                    .setPonCTag(vlanId).build(),
                                                            null, meterId,
@@ -619,33 +612,34 @@
         }
         meterFuture.thenAcceptAsync(result -> {
             //for each pending eapol flow we check if the meter is there.
-            BlockingQueue<SubscriberFlowInfo> queue = pendingEapolForDevice.get(devId);
+            BlockingQueue<SubscriberFlowInfo> queue = pendingEapolForDevice.get(port.deviceId());
             if (queue != null) {
                 while (true) {
                     SubscriberFlowInfo fi = queue.remove();
                     if (fi == null) {
-                        pendingEapolForDevice.replace(devId, queue);
+                        pendingEapolForDevice.replace(port.deviceId(), queue);
                         break;
                     }
                     //TODO this might return the reference and not the actual object
                     // so it can be actually swapped underneath us.
-                    log.debug("handing pending eapol on {}/{} for {}", fi.getDevId(), fi.getUniPort(), fi);
+                    log.debug("handing pending eapol on {} for {}", fi.getUniPort(), fi);
                     if (result == null) {
                         MeterId mId = oltMeterService
-                                .getMeterIdFromBpMapping(devId, fi.getUpBpInfo());
+                                .getMeterIdFromBpMapping(port.deviceId(), fi.getUpBpInfo());
                         if (mId != null) {
-                            log.debug("Meter installation completed for subscriber on {}, handling EAPOL trap flow",
-                                      cp.toString());
+                            log.debug("Meter installation completed for subscriber on {}, " +
+                                            "handling EAPOL trap flow", port);
                             handleEapol(filterFuture, install, cp, filterBuilder, treatmentBuilder, fi, mId);
                         }
                     } else {
                         log.warn("Meter installation error while sending EAPOL trap flow to {}. " +
-                                         "Result {} and MeterId {}", cp.toString(), result, meterId);
+                                         "Result {} and MeterId {}", port, result,
+                                meterId);
                     }
-                    oltMeterService.removeFromPendingMeters(devId, bpInfo);
+                    oltMeterService.removeFromPendingMeters(port.deviceId(), bpInfo);
                 }
             } else {
-                log.info("No pending EAPOLs on {}", devId);
+                log.info("No pending EAPOLs on {}", port.deviceId());
             }
         });
     }
@@ -655,17 +649,17 @@
                              DefaultFilteringObjective.Builder filterBuilder,
                              TrafficTreatment.Builder treatmentBuilder,
                              SubscriberFlowInfo fi, MeterId mId) {
-        log.info("Meter {} for {} on {}/{} exists. {} EAPOL trap flow",
-                 mId, fi.getUpBpInfo(), fi.getDevId(), fi.getUniPort(),
+        log.info("Meter {} for {} on {} exists. {} EAPOL trap flow",
+                 mId, fi.getUpBpInfo(), fi.getUniPort(),
                  (install) ? "Installing" : "Removing");
-        int techProfileId = getDefaultTechProfileId(fi.getDevId(), fi.getUniPort());
+        int techProfileId = getDefaultTechProfileId(fi.getUniPort());
         // can happen in case of removal
         if (mId != null) {
             treatmentBuilder.meter(mId);
         }
         //Authentication trap flow uses only tech profile id as write metadata value
         FilteringObjective eapol = (install ? filterBuilder.permit() : filterBuilder.deny())
-                .withKey(Criteria.matchInPort(fi.getUniPort()))
+                .withKey(Criteria.matchInPort(fi.getUniPort().number()))
                 .addCondition(Criteria.matchEthType(EthType.EtherType.EAPOL.ethType()))
                 .withMeta(treatmentBuilder
                                   .writeMetadata(createTechProfValueForWm(
@@ -680,9 +674,8 @@
                 .add(new ObjectiveContext() {
                     @Override
                     public void onSuccess(Objective objective) {
-                        log.info("Eapol filter {} for {} on {}/{} with meter {}.",
-                                 objective.id(), (install) ? INSTALLED : REMOVED,
-                                 fi.getDevId(), fi.getUniPort(), mId);
+                        log.info("Eapol filter {} for {} on {} with meter {}.",
+                                 objective.id(), (install) ? INSTALLED : REMOVED, fi.getUniPort(), mId);
                         if (filterFuture != null) {
                             filterFuture.complete(null);
                         }
@@ -690,9 +683,8 @@
 
                     @Override
                     public void onError(Objective objective, ObjectiveError error) {
-                        log.error("Eapol filter {} for {}/{} with meter {} " +
-                                         "failed {} because {}", objective.id(),
-                                 fi.getDevId(), fi.getUniPort(), mId,
+                        log.error("Eapol filter {} for {} with meter {} " +
+                                         "failed {} because {}", objective.id(), fi.getUniPort(), mId,
                                  (install) ? INSTALLATION : REMOVAL,
                                  error);
                         if (filterFuture != null) {
@@ -707,27 +699,26 @@
      * Installs trap filtering objectives for particular traffic types on an
      * NNI port.
      *
-     * @param devId   device ID
-     * @param port    port number
+     * @param nniPort    NNI port
      * @param install true to install, false to remove
      */
     @Override
-    public void processNniFilteringObjectives(DeviceId devId, PortNumber port, boolean install) {
-        log.info("{} flows for NNI port {} on device {}",
-                 install ? "Adding" : "Removing", port, devId);
-        processLldpFilteringObjective(devId, port, install);
-        processDhcpFilteringObjectives(devId, port, null, null, install, false, Optional.empty());
-        processIgmpFilteringObjectives(devId, port, null, null, install, false);
-        processPPPoEDFilteringObjectives(devId, port, null, null, install, false);
+    public void processNniFilteringObjectives(AccessDevicePort nniPort, boolean install) {
+        log.info("{} flows for NNI port {}",
+                 install ? "Adding" : "Removing", nniPort);
+        processLldpFilteringObjective(nniPort, install);
+        processDhcpFilteringObjectives(nniPort, null, null, install, false, Optional.empty());
+        processIgmpFilteringObjectives(nniPort, null, null, install, false);
+        processPPPoEDFilteringObjectives(nniPort, null, null, install, false);
     }
 
 
     @Override
-    public void processLldpFilteringObjective(DeviceId devId, PortNumber port, boolean install) {
+    public void processLldpFilteringObjective(AccessDevicePort port, boolean install) {
         DefaultFilteringObjective.Builder builder = DefaultFilteringObjective.builder();
 
         FilteringObjective lldp = (install ? builder.permit() : builder.deny())
-                .withKey(Criteria.matchInPort(port))
+                .withKey(Criteria.matchInPort(port.number()))
                 .addCondition(Criteria.matchEthType(EthType.EtherType.LLDP.ethType()))
                 .withMeta(DefaultTrafficTreatment.builder()
                         .setOutput(PortNumber.CONTROLLER).build())
@@ -736,31 +727,29 @@
                 .add(new ObjectiveContext() {
                     @Override
                     public void onSuccess(Objective objective) {
-                        log.info("LLDP filter for dev/port {}/{} {}.",
-                                devId, port, (install) ? INSTALLED : REMOVED);
+                        log.info("LLDP filter for {} {}.", port, (install) ? INSTALLED : REMOVED);
                     }
 
                     @Override
                     public void onError(Objective objective, ObjectiveError error) {
-                        log.error("LLDP filter for dev/port {}/{} failed {} because {}",
-                                devId, port, (install) ? INSTALLATION : REMOVAL,
+                        log.error("LLDP filter for {} failed {} because {}", port, (install) ? INSTALLATION : REMOVAL,
                                 error);
                     }
                 });
 
-        flowObjectiveService.filter(devId, lldp);
+        flowObjectiveService.filter(port.deviceId(), lldp);
     }
 
     @Override
-    public ForwardingObjective.Builder createTransparentBuilder(PortNumber uplinkPort,
-                                                                PortNumber subscriberPort,
+    public ForwardingObjective.Builder createTransparentBuilder(AccessDevicePort uplinkPort,
+                                                                AccessDevicePort subscriberPort,
                                                                 MeterId meterId,
                                                                 UniTagInformation tagInfo,
                                                                 boolean upstream) {
 
         TrafficSelector selector = DefaultTrafficSelector.builder()
                 .matchVlanId(tagInfo.getPonSTag())
-                .matchInPort(upstream ? subscriberPort : uplinkPort)
+                .matchInPort(upstream ? subscriberPort.number() : uplinkPort.number())
                 .matchInnerVlanId(tagInfo.getPonCTag())
                 .build();
 
@@ -770,22 +759,23 @@
         }
 
         TrafficTreatment treatment = tBuilder
-                .setOutput(upstream ? uplinkPort : subscriberPort)
+                .setOutput(upstream ? uplinkPort.number() : subscriberPort.number())
                 .writeMetadata(createMetadata(upstream ? tagInfo.getPonSTag() : tagInfo.getPonCTag(),
-                        tagInfo.getTechnologyProfileId(), upstream ? uplinkPort : subscriberPort), 0)
+                        tagInfo.getTechnologyProfileId(),
+                        upstream ? uplinkPort.number() : subscriberPort.number()), 0)
                 .build();
 
         return createForwardingObjectiveBuilder(selector, treatment, MIN_PRIORITY);
     }
 
     @Override
-    public ForwardingObjective.Builder createUpBuilder(PortNumber uplinkPort,
-                                                       PortNumber subscriberPort,
+    public ForwardingObjective.Builder createUpBuilder(AccessDevicePort uplinkPort,
+                                                       AccessDevicePort subscriberPort,
                                                        MeterId upstreamMeterId,
                                                        UniTagInformation uniTagInformation) {
 
         TrafficSelector selector = DefaultTrafficSelector.builder()
-                .matchInPort(subscriberPort)
+                .matchInPort(subscriberPort.number())
                 .matchVlanId(uniTagInformation.getUniTagMatch())
                 .build();
 
@@ -807,9 +797,9 @@
             treatmentBuilder.setVlanPcp((byte) uniTagInformation.getUsPonSTagPriority());
         }
 
-        treatmentBuilder.setOutput(uplinkPort)
+        treatmentBuilder.setOutput(uplinkPort.number())
                 .writeMetadata(createMetadata(uniTagInformation.getPonCTag(),
-                        uniTagInformation.getTechnologyProfileId(), uplinkPort), 0L);
+                        uniTagInformation.getTechnologyProfileId(), uplinkPort.number()), 0L);
 
         if (upstreamMeterId != null) {
             treatmentBuilder.meter(upstreamMeterId);
@@ -819,8 +809,8 @@
     }
 
     @Override
-    public ForwardingObjective.Builder createDownBuilder(PortNumber uplinkPort,
-                                                         PortNumber subscriberPort,
+    public ForwardingObjective.Builder createDownBuilder(AccessDevicePort uplinkPort,
+                                                         AccessDevicePort subscriberPort,
                                                          MeterId downstreamMeterId,
                                                          UniTagInformation tagInformation,
                                                          Optional<MacAddress> macAddress) {
@@ -828,7 +818,7 @@
         //subscriberVlan can be any valid Vlan here including ANY to make sure the packet is tagged
         TrafficSelector.Builder selectorBuilder = DefaultTrafficSelector.builder()
                 .matchVlanId(tagInformation.getPonSTag())
-                .matchInPort(uplinkPort)
+                .matchInPort(uplinkPort.number())
                 .matchInnerVlanId(tagInformation.getPonCTag());
 
 
@@ -844,11 +834,11 @@
 
         TrafficTreatment.Builder treatmentBuilder = DefaultTrafficTreatment.builder()
                 .popVlan()
-                .setOutput(subscriberPort);
+                .setOutput(subscriberPort.number());
 
         treatmentBuilder.writeMetadata(createMetadata(tagInformation.getPonCTag(),
                                                       tagInformation.getTechnologyProfileId(),
-                                                      subscriberPort), 0);
+                                                      subscriberPort.number()), 0);
 
         // Upstream pbit is used to remark inner vlan pbit.
         // Upstream is used to avoid trusting the BNG to send the packet with correct pbit.
@@ -919,18 +909,16 @@
      * If multiple services are found in uniServiceList, returns default tech profile id
      * If one service is found, returns the found one
      *
-     * @param devId
-     * @param portNumber
+     * @param port uni port
      * @return the default technology profile id
      */
-    private int getDefaultTechProfileId(DeviceId devId, PortNumber portNumber) {
+    private int getDefaultTechProfileId(AccessDevicePort port) {
         if (subsService == null) {
             log.warn(SADIS_NOT_RUNNING);
             return defaultTechProfileId;
         }
-        Port port = deviceService.getPort(devId, portNumber);
         if (port != null) {
-            SubscriberAndDeviceInformation info = subsService.get(port.annotations().value(AnnotationKeys.PORT_NAME));
+            SubscriberAndDeviceInformation info = subsService.get(port.name());
             if (info != null && info.uniTagList().size() == 1) {
                 return info.uniTagList().get(0).getTechnologyProfileId();
             }
diff --git a/impl/src/main/java/org/opencord/olt/impl/SubscriberFlowInfo.java b/impl/src/main/java/org/opencord/olt/impl/SubscriberFlowInfo.java
index 1ac5b08..444f45f 100644
--- a/impl/src/main/java/org/opencord/olt/impl/SubscriberFlowInfo.java
+++ b/impl/src/main/java/org/opencord/olt/impl/SubscriberFlowInfo.java
@@ -16,8 +16,8 @@
 package org.opencord.olt.impl;
 
 import org.onosproject.net.DeviceId;
-import org.onosproject.net.PortNumber;
 import org.onosproject.net.meter.MeterId;
+import org.opencord.olt.AccessDevicePort;
 import org.opencord.sadis.UniTagInformation;
 
 import java.util.Objects;
@@ -27,8 +27,8 @@
  */
 class SubscriberFlowInfo {
     private final DeviceId devId;
-    private final PortNumber nniPort;
-    private final PortNumber uniPort;
+    private final AccessDevicePort nniPort;
+    private final AccessDevicePort uniPort;
     private final UniTagInformation tagInfo;
     private MeterId downId;
     private MeterId upId;
@@ -37,7 +37,6 @@
 
     /**
      * Builds the mapper of information.
-     * @param devId the device id
      * @param nniPort the nni port
      * @param uniPort the uni port
      * @param tagInfo the tag info
@@ -46,10 +45,10 @@
      * @param downBpInfo the downstream bandwidth profile
      * @param upBpInfo the upstream bandwidth profile
      */
-    SubscriberFlowInfo(DeviceId devId, PortNumber nniPort, PortNumber uniPort,
+    SubscriberFlowInfo(AccessDevicePort nniPort, AccessDevicePort uniPort,
                        UniTagInformation tagInfo, MeterId downId, MeterId upId,
                        String downBpInfo, String upBpInfo) {
-        this.devId = devId;
+        this.devId = uniPort.deviceId();
         this.nniPort = nniPort;
         this.uniPort = uniPort;
         this.tagInfo = tagInfo;
@@ -73,7 +72,7 @@
      *
      * @return nni port
      */
-    PortNumber getNniPort() {
+    AccessDevicePort getNniPort() {
         return nniPort;
     }
 
@@ -82,7 +81,7 @@
      *
      * @return uni port
      */
-    PortNumber getUniPort() {
+    AccessDevicePort getUniPort() {
         return uniPort;
     }
 
diff --git a/impl/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java b/impl/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
index e3a612c..0012e28 100644
--- a/impl/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
+++ b/impl/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
@@ -18,10 +18,10 @@
 import org.onlab.packet.MacAddress;
 import org.onlab.packet.VlanId;
 import org.onosproject.net.DeviceId;
-import org.onosproject.net.PortNumber;
 import org.onosproject.net.flowobjective.ForwardingObjective;
 import org.onosproject.net.flowobjective.ObjectiveError;
 import org.onosproject.net.meter.MeterId;
+import org.opencord.olt.AccessDevicePort;
 import org.opencord.sadis.UniTagInformation;
 
 import java.util.Optional;
@@ -35,7 +35,6 @@
     /**
      * Provisions or removes trap-to-controller DHCP packets.
      *
-     * @param devId           the target device identifier
      * @param port            the uni port for which this trap flow is designated
      * @param upstreamMeterId the upstream meter id that includes the upstream
      *                        bandwidth profile values such as PIR,CIR. If no meter id needs to be referenced,
@@ -46,7 +45,7 @@
      *                        server, false if packets are flowing downstream towards client
      * @param dhcpFuture      gets result of dhcp objective when complete
      */
-    void processDhcpFilteringObjectives(DeviceId devId, PortNumber port,
+    void processDhcpFilteringObjectives(AccessDevicePort port,
                                         MeterId upstreamMeterId,
                                         UniTagInformation tagInformation,
                                         boolean install,
@@ -56,14 +55,13 @@
     /**
      * Trap igmp packets to the controller.
      *
-     * @param devId           Device identifier to send the flow
      * @param port            Uni Port number
      * @param upstreamMeterId upstream meter id that represents the upstream bandwidth profile
      * @param tagInformation  the uni tag information of the subscriber
      * @param install         the indicator to install or to remove the flow
      * @param upstream        determines the direction of the flow
      */
-    void processIgmpFilteringObjectives(DeviceId devId, PortNumber port,
+    void processIgmpFilteringObjectives(AccessDevicePort port,
                                         MeterId upstreamMeterId,
                                         UniTagInformation tagInformation,
                                         boolean install,
@@ -72,22 +70,20 @@
     /**
      * Trap eapol authentication packets to the controller.
      *
-     * @param devId        the device identifier
-     * @param portNumber   the port for which this trap flow is designated
+     * @param port         the port for which this trap flow is designated
      * @param bpId         bandwidth profile id to add the related meter to the flow
      * @param filterFuture completable future for this filtering objective operation
      * @param vlanId       the default or customer tag for a subscriber
      * @param install      true to install the flow, false to remove the flow
      */
-    void processEapolFilteringObjectives(DeviceId devId, PortNumber portNumber, String bpId,
+    void processEapolFilteringObjectives(AccessDevicePort port, String bpId,
                                          CompletableFuture<ObjectiveError> filterFuture,
                                          VlanId vlanId, boolean install);
 
     /**
      * Trap PPPoE discovery packets to the controller.
      *
-     * @param devId           the target device identifier
-     * @param portNumber      the uni port for which this trap flow is designated
+     * @param port            the uni port for which this trap flow is designated
      * @param upstreamMeterId the upstream meter id that includes the upstream
      *                        bandwidth profile values such as PIR,CIR. If no meter id needs to be referenced,
      *                        null can be sent
@@ -96,28 +92,26 @@
      * @param upstream        true if trapped packets are flowing upstream towards
      *                        server, false if packets are flowing downstream towards client
      **/
-    void processPPPoEDFilteringObjectives(DeviceId devId, PortNumber portNumber,
+    void processPPPoEDFilteringObjectives(AccessDevicePort port,
                                           MeterId upstreamMeterId, UniTagInformation tagInformation,
                                           boolean install, boolean upstream);
 
     /**
      * Trap lldp packets to the controller.
      *
-     * @param devId   the device identifier
      * @param port    the port for which this trap flow is designated
      * @param install true to install the flow, false to remove the flow
      */
-    void processLldpFilteringObjective(DeviceId devId, PortNumber port, boolean install);
+    void processLldpFilteringObjective(AccessDevicePort port, boolean install);
 
     /**
      * Installs trap filtering objectives for particular traffic types (LLDP, IGMP and DHCP) on an
      * NNI port.
      *
-     * @param devId   device ID
      * @param port    port number
      * @param install true to install, false to remove
      */
-    void processNniFilteringObjectives(DeviceId devId, PortNumber port, boolean install);
+    void processNniFilteringObjectives(AccessDevicePort port, boolean install);
 
     /**
      * Creates a ForwardingObjective builder with double-tag match criteria and output
@@ -131,8 +125,8 @@
      * @param upstream        true to create upstream, false to create downstream builder
      * @return ForwardingObjective.Builder
      */
-    ForwardingObjective.Builder createTransparentBuilder(PortNumber uplinkPort,
-                                                         PortNumber subscriberPort,
+    ForwardingObjective.Builder createTransparentBuilder(AccessDevicePort uplinkPort,
+                                                         AccessDevicePort subscriberPort,
                                                          MeterId meterId,
                                                          UniTagInformation tagInfo,
                                                          boolean upstream);
@@ -147,8 +141,8 @@
      * @param uniTagInformation the uni tag information
      * @return ForwardingObjective.Builder
      */
-    ForwardingObjective.Builder createUpBuilder(PortNumber uplinkPort,
-                                                PortNumber subscriberPort,
+    ForwardingObjective.Builder createUpBuilder(AccessDevicePort uplinkPort,
+                                                AccessDevicePort subscriberPort,
                                                 MeterId upstreamMeterId,
                                                 UniTagInformation uniTagInformation);
 
@@ -163,8 +157,8 @@
      * @param macAddress the mac address
      * @return ForwardingObjective.Builder
      */
-    ForwardingObjective.Builder createDownBuilder(PortNumber uplinkPort,
-                                                  PortNumber subscriberPort,
+    ForwardingObjective.Builder createDownBuilder(AccessDevicePort uplinkPort,
+                                                  AccessDevicePort subscriberPort,
                                                   MeterId downstreamMeterId,
                                                   UniTagInformation tagInformation,
                                                   Optional<MacAddress> macAddress);
diff --git a/impl/src/test/java/org/opencord/olt/impl/OltFlowTest.java b/impl/src/test/java/org/opencord/olt/impl/OltFlowTest.java
index 2947bf3..7ae3c8c 100644
--- a/impl/src/test/java/org/opencord/olt/impl/OltFlowTest.java
+++ b/impl/src/test/java/org/opencord/olt/impl/OltFlowTest.java
@@ -34,6 +34,9 @@
 import org.onosproject.cluster.RoleInfo;
 import org.onosproject.mastership.MastershipInfo;
 import org.onosproject.mastership.MastershipListener;
+import org.onosproject.net.AnnotationKeys;
+import org.onosproject.net.DefaultAnnotations;
+import org.onosproject.net.DefaultPort;
 import org.onosproject.net.DeviceId;
 import org.onosproject.net.MastershipRole;
 import org.onosproject.net.PortNumber;
@@ -55,6 +58,7 @@
 import org.onosproject.net.flowobjective.Objective;
 import org.onosproject.net.meter.MeterId;
 import org.onosproject.net.meter.MeterKey;
+import org.opencord.olt.AccessDevicePort;
 import org.opencord.sadis.BandwidthProfileInformation;
 import org.opencord.sadis.UniTagInformation;
 
@@ -65,9 +69,15 @@
 
 public class OltFlowTest extends TestBase {
     private OltFlowService oltFlowService;
-    PortNumber uniPortNumber = PortNumber.portNumber(1);
-    PortNumber uniPortNumber2 = PortNumber.portNumber(2);
-    PortNumber nniPortNumber = PortNumber.portNumber(65535);
+    AccessDevicePort uniPort1 = new AccessDevicePort(new DefaultPort(olt, PortNumber.portNumber(1), true,
+            DefaultAnnotations.builder().set(AnnotationKeys.PORT_NAME, "BBSM00010001-1").build()),
+            AccessDevicePort.Type.UNI);
+    AccessDevicePort uniPort2 = new AccessDevicePort(new DefaultPort(olt, PortNumber.portNumber(2), true,
+            DefaultAnnotations.builder().set(AnnotationKeys.PORT_NAME, "BBSM00010002-1").build()),
+            AccessDevicePort.Type.UNI);
+    AccessDevicePort nniPort = new AccessDevicePort(new DefaultPort(olt, PortNumber.portNumber(65535), true,
+            DefaultAnnotations.builder().set(AnnotationKeys.PORT_NAME, "nni-1048576").build()),
+            AccessDevicePort.Type.NNI);
 
     MacAddress macAddress = MacAddress.valueOf("00:00:00:00:0a:0b");
 
@@ -125,57 +135,58 @@
 
     @Test
     public void testDhcpFiltering() {
+        System.out.println(uniPort1);
         oltFlowService.flowObjectiveService.clearQueue();
         // ensure upstream dhcp traps can be added and removed
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 1;
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 false, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 2;
 
         // Ensure upstream flow has no pcp unless properly specified.
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber2,
+        oltFlowService.processDhcpFilteringObjectives(uniPort2,
                 usMeterId, uniTagInfoNoPcp,
                 true, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 3;
 
         // ensure upstream flows are not added if uniTagInfo is missing dhcp requirement
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfoNoDhcpNoIgmp,
                 true, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 3;
 
         // ensure downstream traps don't succeed without global config for nni ports
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(nniPort,
                 null, null,
                 true, false, Optional.empty());
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(nniPort,
                 null, null,
                 false, false, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 3;
         // do global config for nni ports and now it should succeed
         oltFlowService.enableDhcpOnNni = true;
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(nniPort,
                 null, null,
                 true, false, Optional.empty());
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(nniPort,
                 null, null,
                 false, false, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 5;
 
         // turn on DHCPv6 and we should get 2 flows
         oltFlowService.enableDhcpV6 = true;
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 7;
 
         // turn off DHCPv4 and it's only v6
         oltFlowService.enableDhcpV4 = false;
-        oltFlowService.processDhcpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processDhcpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true, Optional.empty());
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 8;
@@ -192,28 +203,28 @@
 
         // ensure pppoed traps are not added if global config is off.
         oltFlowService.enablePppoe = false;
-        oltFlowService.processPPPoEDFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processPPPoEDFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 0;
 
         // ensure upstream pppoed traps can be added and removed
         oltFlowService.enablePppoe = true;
-        oltFlowService.processPPPoEDFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processPPPoEDFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 1;
-        oltFlowService.processPPPoEDFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processPPPoEDFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 false, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 2;
 
         // ensure downstream pppoed traps can be added and removed
-        oltFlowService.processPPPoEDFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processPPPoEDFilteringObjectives(nniPort,
                 null, null,
                 true, false);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 3;
-        oltFlowService.processPPPoEDFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processPPPoEDFilteringObjectives(nniPort,
                 null, null,
                 false, false);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 4;
@@ -227,30 +238,30 @@
         oltFlowService.flowObjectiveService.clearQueue();
 
         // ensure igmp flows can be added and removed
-        oltFlowService.processIgmpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processIgmpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfo,
                 true, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 1;
-        oltFlowService.processIgmpFilteringObjectives(DEVICE_ID_1, uniPortNumber, usMeterId,
+        oltFlowService.processIgmpFilteringObjectives(uniPort1, usMeterId,
                 uniTagInfo,
                 false, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 2;
 
         // ensure igmp flow is not added if uniTag has no igmp requirement
-        oltFlowService.processIgmpFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processIgmpFilteringObjectives(uniPort1,
                 usMeterId, uniTagInfoNoDhcpNoIgmp,
                 true, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 2;
 
         //ensure igmp flow on NNI fails without global setting
-        oltFlowService.processIgmpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processIgmpFilteringObjectives(nniPort,
                 null, null,
                 true, false);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 2;
 
         // igmp trap on NNI should succeed with global config
         oltFlowService.enableIgmpOnNni = true;
-        oltFlowService.processIgmpFilteringObjectives(DEVICE_ID_1, nniPortNumber,
+        oltFlowService.processIgmpFilteringObjectives(nniPort,
                 null, null,
                 true, false);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives().size() == 3;
@@ -265,20 +276,20 @@
         oltFlowService.enableEapol = true;
 
         //will install
-        oltFlowService.processEapolFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processEapolFilteringObjectives(uniPort1,
                 uniTagInfo.getUpstreamBandwidthProfile(), new CompletableFuture<>(),
                 uniTagInfo.getUniTagMatch(), true);
 
         //bp profile doesn't exist
-        oltFlowService.processEapolFilteringObjectives(DEVICE_ID_1, uniPortNumber,
+        oltFlowService.processEapolFilteringObjectives(uniPort1,
                 uniTagInfo.getDownstreamBandwidthProfile(), new CompletableFuture<>(),
                 uniTagInfo.getUniTagMatch(), true);
     }
 
     @Test
     public void testLldpFiltering() {
-        oltFlowService.processLldpFilteringObjective(DEVICE_ID_1, nniPortNumber, true);
-        oltFlowService.processLldpFilteringObjective(DEVICE_ID_1, nniPortNumber, false);
+        oltFlowService.processLldpFilteringObjective(nniPort, true);
+        oltFlowService.processLldpFilteringObjective(nniPort, false);
     }
 
     @Test
@@ -286,10 +297,10 @@
         oltFlowService.flowObjectiveService.clearQueue();
         oltFlowService.enableDhcpOnNni = true;
         oltFlowService.enableIgmpOnNni = true;
-        oltFlowService.processNniFilteringObjectives(DEVICE_ID_1, nniPortNumber, true);
+        oltFlowService.processNniFilteringObjectives(nniPort, true);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives()
                 .size() == 3;
-        oltFlowService.processNniFilteringObjectives(DEVICE_ID_1, nniPortNumber, false);
+        oltFlowService.processNniFilteringObjectives(nniPort, false);
         assert oltFlowService.flowObjectiveService.getPendingFlowObjectives()
                 .size() == 6;
         oltFlowService.flowObjectiveService.clearQueue();
@@ -298,14 +309,14 @@
     @Test
     public void testUpBuilder() {
         ForwardingObjective objective =
-                oltFlowService.createUpBuilder(nniPortNumber, uniPortNumber, usMeterId, uniTagInfo).add();
+                oltFlowService.createUpBuilder(nniPort, uniPort1, usMeterId, uniTagInfo).add();
         checkObjective(objective, true);
     }
 
     @Test
     public void testDownBuilder() {
         ForwardingObjective objective =
-                oltFlowService.createDownBuilder(nniPortNumber, uniPortNumber, dsMeterId, uniTagInfo,
+                oltFlowService.createDownBuilder(nniPort, uniPort1, dsMeterId, uniTagInfo,
                         Optional.of(macAddress)).remove();
         checkObjective(objective, false);
     }
@@ -413,7 +424,7 @@
 
 
             if (ethType.ethType().equals(EthType.EtherType.LLDP.ethType()) ||
-                    portCriterion.port().equals(nniPortNumber)) {
+                    portCriterion.port().equals(nniPort.number())) {
                 assert meter == null;
                 assert writeMetadata == null;
                 assert vlanIdCriterion == null;
diff --git a/impl/src/test/java/org/opencord/olt/impl/TestBase.java b/impl/src/test/java/org/opencord/olt/impl/TestBase.java
index 9e14ee7..5153d10 100644
--- a/impl/src/test/java/org/opencord/olt/impl/TestBase.java
+++ b/impl/src/test/java/org/opencord/olt/impl/TestBase.java
@@ -18,9 +18,12 @@
 import com.google.common.collect.HashMultimap;
 import com.google.common.collect.Maps;
 import com.google.common.collect.Multiset;
+import org.onlab.packet.ChassisId;
 import org.onlab.packet.Ip4Address;
 import org.onlab.packet.MacAddress;
 import org.onosproject.core.DefaultApplicationId;
+import org.onosproject.net.DefaultDevice;
+import org.onosproject.net.Device;
 import org.onosproject.net.DeviceId;
 import org.onosproject.net.meter.MeterId;
 import org.onosproject.store.service.AsyncConsistentMultimap;
@@ -55,6 +58,9 @@
     protected String dsBpId = "HSIA-DS";
     protected DefaultApplicationId appId = new DefaultApplicationId(1, "OltServices");
 
+    protected static Device olt = new DefaultDevice(null, DeviceId.deviceId(OLT_DEV_ID), Device.Type.SWITCH,
+            "VOLTHA Project", "open_pon", "open_pon", "BBSIM_OLT_1", new ChassisId("a0a0a0a0a01"));
+
     Map<String, BandwidthProfileInformation> bpInformation = Maps.newConcurrentMap();
 
     protected void addBandwidthProfile(String id) {