From a2f4842e4a89095348f4110ace27c05eaa61f1db Mon Sep 17 00:00:00 2001
From: Kanzhe Jiang <kanzhe.jiang@bigswitch.com>
Date: Sun, 29 Apr 2012 10:06:22 -0700
Subject: [PATCH] Revert "Update device AP when necessary"

This reverts commit 0ae432f42f47f3d72fcc3034a97c335d1326b5e0.

Conflicts:

	src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java

Conflicts:

	src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java
---
 .../internal/DeviceManagerImpl.java           | 246 +++++++++---------
 .../internal/DeviceManagerImplTest.java       |  16 +-
 2 files changed, 130 insertions(+), 132 deletions(-)

diff --git a/src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java b/src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java
index 5e9053102..7f58f5b81 100755
--- a/src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java
+++ b/src/main/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImpl.java
@@ -304,22 +304,8 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         /**
          * Overall update, delete and clear methods for the set of maps
          * @param d the device to update
-         * @return true if successfully update the device
          */
-        private synchronized boolean updateMaps(Device d, Date lastTopoChangeTime) {
-        	/**
-        	 * If the device was last seen before the most recent topology change,
-        	 * the device might be outdated.
-        	 * Throw it away.
-        	 */
-        	if (lastTopoChangeTime.after(d.getLastSeen())) {
-        		if (log.isDebugEnabled()) {
-        			log.debug("Skip device update {}, which is seen before last topo change, {}",
-        					d, lastTopoChangeTime);
-        		}
-        		return false;
-        	}
-        	
+        private synchronized void updateMaps(Device d) {
             // Update dataLayerAddressDeviceMap
             updateDataLayerAddressDeviceMap(d);
             // Update ipv4AddressDeviceMap
@@ -328,7 +314,6 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             updateSwitchDeviceMap(d);
             // Update switchPortDeviceMap
             updateSwitchPortDeviceMap(d);
-            return true;
         }
 
         /** 
@@ -437,7 +422,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             if (na == null) { // this particular address is not in the device
                 na = new DeviceNetworkAddress(nwAddr, lastSeen);
                 dCopy.addNetworkAddress(na);
-                updateMaps(dCopy, lastTopoChangeTime);
+                updateMaps(dCopy);
             }
         }
 
@@ -456,8 +441,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             if (na != null) {
                 delFromIpv4AddressDeviceMap(nwAddr, d);
                 dCopy.removeNetworkAddress(na);
-                // Always update§
-                updateMaps(dCopy, new Date(0));
+                updateMaps(dCopy);
                 removeNetworkAddressFromStorage(d.getDlAddrString(), na);
             }
         }
@@ -505,8 +489,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             dCopy.addAttachmentPoint(dap);
             // Now add this updated device to the maps, which will replace
             // the old copy
-            updateMaps(dCopy, lastTopoChangeTime);
-            writeAttachmentPointToStorage(dCopy, dap, lastSeen);
+            updateMaps(dCopy);
             return true;
         }
 
@@ -550,9 +533,9 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             delFromSwitchPortDeviceMap(swPort, d);
             // Remove the original device from the Switch map
             delFromSwitchDeviceMap(sw, d);  
-            // Now always add this updated device to the maps, which will replace
+            // Now add this updated device to the maps, which will replace
             // the old copy
-            updateMaps(dCopy, new Date(0));
+            updateMaps(dCopy);
             if (log.isDebugEnabled()) {
                 log.debug("Remove AP {} post {} prev {} for Device {}", 
                           new Object[] {dap, dCopy.getAttachmentPoints().size(),
@@ -632,7 +615,6 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
     } // End of DevMgrMap class definition
 
     private DevMgrMaps devMgrMaps;
-    private Date lastTopoChangeTime;
 
     public DevMgrMaps getDevMgrMaps() {
         return devMgrMaps;
@@ -717,7 +699,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         
         @Override
         public String toString() {
-            String updateString = device.getDlAddrString();
+            String updateString = null;
             
             switch (updateType) {
             case ADDRESS_ADDED:
@@ -805,11 +787,8 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         evHistAttachmtPt(mac, swPort, EvAction.ADDED, "New device");
         device.addNetworkAddress(nwAddr, currentDate);
         device.setVlanId(vlan);
-        // Update the maps - insert the device in the maps only if
-        // it was learned after the most recent topology change
-        if (!devMgrMaps.updateMaps(device, lastTopoChangeTime)) {
-        	return;
-        }
+        // Update the maps - insert the device in the maps
+        devMgrMaps.updateMaps(device);
         writeDeviceToStorage(device, currentDate);
         updateStatus(device, true);
     }
@@ -918,17 +897,17 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         Short vlan = match.getDataLayerVirtualLan();
         if (vlan < 0) vlan = null;
         int nwSrc = getSrcNwAddr(eth, dlAddr);
-        Device srcDevice = devMgrMaps.getDeviceByDataLayerAddr(dlAddr);
+        Device device = devMgrMaps.getDeviceByDataLayerAddr(dlAddr);
         if (log.isTraceEnabled()) {
             long dstAddr = Ethernet.toLong(match.getDataLayerDestination());
-            Device dstDevice = devMgrMaps.getDeviceByDataLayerAddr(dstAddr);
-            if (srcDevice != null)
-                log.trace("    Src.AttachmentPts: {}", srcDevice.getAttachmentPointsMap().keySet());
-            if (dstDevice != null)
-                log.trace("    Dst.AttachmentPts: {}", dstDevice.getAttachmentPointsMap().keySet());
+            Device dstDev = devMgrMaps.getDeviceByDataLayerAddr(dstAddr);
+            if (device != null)
+                log.trace("    Src.AttachmentPts: {}", device.getAttachmentPointsMap().keySet());
+            if (dstDev != null)
+                log.trace("    Dst.AttachmentPts: {}", dstDev.getAttachmentPointsMap().keySet());
         }
         Date currentDate = new Date(); 
-        if (srcDevice != null) { 
+        if (device != null) { 
             // Write lock is expensive, check if we have an update first
             boolean newAttachmentPoint = false;
             boolean newNetworkAddress = false;
@@ -943,14 +922,14 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             DeviceNetworkAddress networkAddress = null;
 
             // Copy-replace of device would be too expensive here
-            srcDevice.setLastSeen(currentDate);
-            updateDevice = srcDevice.shouldWriteLastSeenToStorage();
+            device.setLastSeen(currentDate);
+            updateDevice = device.shouldWriteLastSeenToStorage();
             
             if (isGratArp(eth)) {
                 clearAttachmentPoints = true;
             }
 
-            attachmentPoint = srcDevice.getAttachmentPoint(switchPort);
+            attachmentPoint = device.getAttachmentPoint(switchPort);
             if (attachmentPoint != null) {
                 updateAttachmentPointLastSeen = true;
             } else {
@@ -966,7 +945,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             }
 
             if (nwSrc != 0) {
-                networkAddress = srcDevice.getNetworkAddress(nwSrc);
+                networkAddress = device.getNetworkAddress(nwSrc);
                 if (networkAddress != null) {
                     updateNetworkAddressLastSeen = true;
                 } else if (eth != null && (eth.getPayload() instanceof ARP)) {
@@ -994,7 +973,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                 Device deviceByNwaddr = this.getDeviceByIPv4Address(nwSrc);
                 if ((deviceByNwaddr != null) &&
                     (deviceByNwaddr.getDataLayerAddressAsLong() != 
-                                    srcDevice.getDataLayerAddressAsLong())) {
+                                    device.getDataLayerAddressAsLong())) {
                     updateNeworkAddressMap = true;
                     Device dCopy = new Device(deviceByNwaddr);
                     DeviceNetworkAddress naOld = dCopy.getNetworkAddress(nwSrc);
@@ -1002,20 +981,20 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                                                 dCopy.getNetworkAddressesMap();
                     if (namap.containsKey(nwSrc)) namap.remove(nwSrc);
                     dCopy.setNetworkAddresses(namap.values());
-                    this.devMgrMaps.updateMaps(dCopy, new Date(0));
+                    this.devMgrMaps.updateMaps(dCopy);
                     if (naOld !=null) 
                         removeNetworkAddressFromStorage(dCopy.getDlAddrString(), naOld);
                 }
 
             }
-            if ((vlan == null && srcDevice.getVlanId() != null) ||
-                    (vlan != null && !vlan.equals(srcDevice.getVlanId()))) {
+            if ((vlan == null && device.getVlanId() != null) ||
+                    (vlan != null && !vlan.equals(device.getVlanId()))) {
                 updateDeviceVlan = true;
             }
 
             if (newAttachmentPoint || newNetworkAddress || updateDeviceVlan || 
                                 updateNeworkAddressMap) {
-                Device nd = new Device(srcDevice);
+                Device nd = new Device(device);
 
                 try {
                     // Check if we have seen this attachmentPoint recently,
@@ -1027,10 +1006,10 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                         } else {
                             if (log.isDebugEnabled()) {
                                 log.debug("Learned new AP for device {} at {}",
-                                        nd, attachmentPoint);
+                                        HexString.toHexString(nd.getDataLayerAddressAsLong()),
+                                        attachmentPoint);
                             }
                             nd.addAttachmentPoint(attachmentPoint);
-                            updateDevice = true;
                             evHistAttachmtPt(nd.getDataLayerAddressAsLong(), 
                                              attachmentPoint.getSwitchPort(),
                                              EvAction.ADDED, 
@@ -1039,11 +1018,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                     }
 
                     if (clearAttachmentPoints) {
-                    	if (log.isDebugEnabled()) {
-                            log.debug("Grat ARP, clear all APs for device {}", nd);
-                        }
                         nd.clearAttachmentPoints();
-                        updateDevice = true;
                         evHistAttachmtPt(nd, 0L, (short)(-1),
                                 EvAction.CLEARED, "Grat. ARP from pkt-in");
                     }
@@ -1051,7 +1026,6 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                     if (newNetworkAddress) {
                         // add the address
                         nd.addNetworkAddress(networkAddress);
-                        updateDevice = true;
                         if (log.isTraceEnabled()) {
                             log.trace("Device {} added IP {}", 
                                       new Object[] {nd, IPv4.fromIPv4Address(nwSrc)});
@@ -1060,8 +1034,9 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
 
                     if (updateDeviceVlan) {
                         nd.setVlanId(vlan);
-                        updateDevice = true;
+                        writeDeviceToStorage(nd, currentDate);
                     }
+
                 } catch (APBlockedException e) {
                     assert(attachmentPoint == null);
                     ret = Command.STOP;
@@ -1071,13 +1046,8 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                     ForwardingBase.blockHost(floodlightProvider, switchPort,
                         dlAddr, ForwardingBase.FLOWMOD_DEFAULT_HARD_TIMEOUT);
                 }
-                
                 // Update the maps
-                if (!devMgrMaps.updateMaps(nd, lastTopoChangeTime)) {
-                	log.debug("Failed to update devMgrMap for device {}, lastSeen is before topoChange {}",
-                			nd, lastTopoChangeTime);
-                	return ret;
-                }
+                devMgrMaps.updateMaps(nd);
                 // publish the update after devMgrMaps is updated.
                 if (newNetworkAddress) {
                     updateAddress(nd, networkAddress, true);
@@ -1085,28 +1055,29 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                 if (updateDeviceVlan) {
                     updateVlan(nd);
                 }
-                srcDevice = nd;
+                device = nd;
             }
 
-            if (updateDevice) {
-                writeDeviceToStorage(srcDevice, currentDate);
-            } else {
-                if (updateAttachmentPointLastSeen) {
-                    attachmentPoint.setLastSeen(currentDate);
-                    if (attachmentPoint.shouldWriteLastSeenToStorage())
-                        writeAttachmentPointToStorage(
-                                srcDevice, attachmentPoint, currentDate);
-                }
+            if (updateAttachmentPointLastSeen) {
+                attachmentPoint.setLastSeen(currentDate);
+                if (attachmentPoint.shouldWriteLastSeenToStorage())
+                    writeAttachmentPointToStorage(
+                            device, attachmentPoint, currentDate);
+            }
 
-                if (updateNetworkAddressLastSeen || newNetworkAddress) {
-                    if (updateNetworkAddressLastSeen)
-                        networkAddress.setLastSeen(currentDate);
-                    if (newNetworkAddress || 
-                            networkAddress.shouldWriteLastSeenToStorage())
-                        writeNetworkAddressToStorage(
-                                srcDevice, networkAddress, currentDate);
-                }
+            if (updateNetworkAddressLastSeen || newNetworkAddress) {
+                if (updateNetworkAddressLastSeen)
+                    networkAddress.setLastSeen(currentDate);
+                if (newNetworkAddress || 
+                        networkAddress.shouldWriteLastSeenToStorage())
+                    writeNetworkAddressToStorage(
+                            device, networkAddress, currentDate);
+            }
+
+            if (updateDevice) {
+                writeDeviceToStorage(device, currentDate);
             }
+
         } else { // device is null 
             if (log.isTraceEnabled())
                 log.trace("   new device");
@@ -1665,6 +1636,8 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         // The long here is the SwitchCluster ID
         Map<Long, DeviceAttachmentPoint> tempAPMap =
                             new HashMap<Long, DeviceAttachmentPoint>();
+        Map<Long, DeviceAttachmentPoint> tempOldAPMap =
+            new HashMap<Long, DeviceAttachmentPoint>();
 
         // Get only the latest DAPs into a map
         for (DeviceAttachmentPoint dap : d.getAttachmentPoints()) {
@@ -1686,32 +1659,43 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                     // They are removed after deleting from storage.
                     if (isNewer(dap, existingDap)) {
                         tempAPMap.put(clusterId, dap);
+                        tempOldAPMap.put(clusterId, existingDap);
+                    } else {
+                        tempOldAPMap.put(clusterId, dap);
                     }
                 } else {
                     tempAPMap.put(clusterId, dap);
                 }
             }
         }
-        /**
-         * Also make sure the attachmentPoints are in non-blocked state
-         */
-        d.setAttachmentPoints(tempAPMap.values());
-        for (DeviceAttachmentPoint dap: tempAPMap.values()) {
-            boolean isblocked = dap.isBlocked();
-            dap.resetConflictState();
-            // only write to DB if the blocking state is reset.
-            if (isblocked) {
-            	writeAttachmentPointToStorage(d, dap, dap.getLastSeen());
+
+        synchronized (d) {
+            /**
+             * Since the update below is happening on a copy of the device it
+             * should not impact packetIn processing time due to lock contention
+             *
+             * Also make sure the attachmentPoints are in non-blocked state
+             */
+            for (DeviceAttachmentPoint dap: tempAPMap.values()) {
+                if (log.isDebugEnabled()) {
+                    log.debug("Reset AP {} for device {}", dap, d);
+                }
+            	//dap.setBlocked(false);
+                dap.resetConflictState();
+            }
+            d.setAttachmentPoints(tempAPMap.values());
+            for (DeviceAttachmentPoint dap : tempOldAPMap.values()) {
+                if (log.isDebugEnabled()) {
+                    log.debug("Reset Old AP {} for device {}", dap, d);
+                }
+            	//dap.setBlocked(false);
+                dap.resetConflictState();
+                d.addOldAttachmentPoint(dap);
+            }
+
+            if (log.isDebugEnabled()) {
+                log.debug("After cleanup, device {}", d);
             }
-        }
-        for (DeviceAttachmentPoint dap : d.getOldAttachmentPoints()) {
-            // Delete from memory after storage,
-            // otherwise an exception will
-            // leave stale attachment points on storage.
-            removeAttachmentPointFromStorage(d.getDlAddrString(),
-                HexString.toHexString(dap.getSwitchPort().getSw().getId()),
-                dap.getSwitchPort().getPort().toString());
-            d.removeOldAttachmentPoint(dap);
         }
     }
 
@@ -1901,7 +1885,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                     continue;
                 }
             }
-            devMgrMaps.updateMaps(d, lastTopoChangeTime);
+            devMgrMaps.updateMaps(d);
         }
     }
 
@@ -2058,7 +2042,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
             Date agedBoundary = ageBoundaryDifference(currentDate, expire);
             if (ap.getLastSeen().before(agedBoundary)) {
                 if (log.isDebugEnabled()) {
-                    log.debug("Remove aged AP {} from device {}", ap, HexString.toHexString(dlAddr));
+                    log.debug("Remove aged AP {} from device {}", ap, device);
                 }
                 devMgrMaps.delDevAttachmentPoint(dlAddr, ap.getSwitchPort());
                 evHistAttachmtPt(device.getDataLayerAddressAsLong(), 
@@ -2073,7 +2057,7 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
     /**
      * Age device entry based on an expiry associated with the device.
      */
-    protected void removeAgedDevices(Date currentDate) {
+    private void removeAgedDevices(Date currentDate) {
         Date deviceAgeBoundary = ageBoundaryDifference(currentDate, 
                                         DEVICE_MAX_AGE);
 
@@ -2139,28 +2123,45 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
                 readPortChannelConfigFromStorage();
             }
 
-            try {
-            	// serialize the devMgrMaps updates
-            	synchronized (devMgrMaps) {
-            		Collection<Device> devices = devMgrMaps.getDevices();
-	                for (Device d  : devices) {
-	                    try {
-	                        Device dCopy = new Device(d);
-	                        cleanupAttachmentPoints(dCopy);
-	                        
-	                        // Update the maps with the new device copy
-	                        devMgrMaps.updateMaps(dCopy, new Date(0));
-	                    }  catch (ConcurrentModificationException e) {
-	                    	log.error("DeviceUpdateWorker ConcurrentModificationException, ", e);
-	                    } catch (NullPointerException e) {
-	                    	log.error("DeviceUpdateWorker NPE, ", e);
-	                    }
-	                }
-	                lastTopoChangeTime = new Date();
-	                if (log.isDebugEnabled()) {
-	                    log.debug("Set lastTopoChangeTime {}", lastTopoChangeTime);
-	                }
-            	}
+            try { 
+                log.debug("DeviceUpdateWorker: cleaning up attachment points.");
+                for (IOFSwitch sw  : devMgrMaps.getSwitches()) {
+                    // If the set of devices connected to the switches we 
+                    // re-iterate a max of 3 times - WHY? TODO
+                    int maxIter = 3;
+                    while (maxIter > 0) {
+                        try {
+                            for (Device d: devMgrMaps.getDevicesOnASwitch(sw)) {
+                                Device dCopy = new Device(d);
+                                cleanupAttachmentPoints(dCopy);
+                                for (DeviceAttachmentPoint dap : 
+                                    dCopy.getOldAttachmentPoints()) {
+                                    // Don't remove conflict attachment points 
+                                    // with recent activities
+                                    if (dap.isInConflict() && !updatePortChannel)
+                                        continue;
+                                    // Delete from memory after storage,
+                                    // otherwise an exception will
+                                    // leave stale attachment points on storage.
+                                    log.debug("Remove AP {} from storage for device {}", dap, dCopy.getDlAddrString());
+                                    removeAttachmentPointFromStorage(dCopy.getDlAddrString(),
+                                        HexString.toHexString(dap.getSwitchPort().getSw().getId()),
+                                        dap.getSwitchPort().getPort().toString());
+                                    dCopy.removeOldAttachmentPoint(dap);
+                                }
+                                // Update the maps with the new device copy
+                                devMgrMaps.updateMaps(dCopy);
+                            }
+                            break;
+                        }  catch (ConcurrentModificationException e) {
+                            maxIter--;
+                        } catch (NullPointerException e) { }
+                    }
+                    if (maxIter == 0) {
+                        log.warn("Device attachment point clean up " +
+                                "attempted three times and failed.");
+                    }
+                }
             } catch (StorageException e) {
                 log.error("DeviceUpdateWorker had a storage exception, " +
                         "Floodlight exiting");
@@ -2297,7 +2298,6 @@ public class DeviceManagerImpl implements IDeviceManagerService, IOFMessageListe
         this.updates = new LinkedList<Update>();
         this.devMgrMaps = new DevMgrMaps();
         this.lock = new ReentrantReadWriteLock();
-        this.lastTopoChangeTime = new Date(0);
         
         this.evHistDevMgrAttachPt = 
                 new EventHistory<EventHistoryAttachmentPoint>("Attachment-Point");
diff --git a/src/test/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImplTest.java b/src/test/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImplTest.java
index 44a87c0d5..8d241604e 100644
--- a/src/test/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImplTest.java
+++ b/src/test/java/net/floodlightcontroller/devicemanager/internal/DeviceManagerImplTest.java
@@ -297,10 +297,11 @@ public class DeviceManagerImplTest extends FloodlightTestCase {
         expect(mockTopology.isInternal(1L, (short)1)).andReturn(false);
         deviceManager.setTopology(mockTopology);
 
-        // reduce the aging period to a few milliseconds
+        // reduce the aging period to a few seconds
+        DeviceManagerImpl.DEVICE_AGING_TIMER = 2;
         DeviceManagerImpl.DEVICE_AP_MAX_AGE = 1;
         DeviceManagerImpl.DEVICE_NA_MAX_AGE = 1;
-        DeviceManagerImpl.DEVICE_MAX_AGE = 2;
+        DeviceManagerImpl.DEVICE_MAX_AGE = 3;
 
         Date currentDate = new Date();
 
@@ -334,11 +335,10 @@ public class DeviceManagerImplTest extends FloodlightTestCase {
         assertEquals(2, rdevice.getNetworkAddresses().size());
 
         // Sleep to make sure the aging thread has run
-        Thread.sleep(Math.max(DeviceManagerImpl.DEVICE_NA_MAX_AGE, DeviceManagerImpl.DEVICE_AP_MAX_AGE)*1000);
-        deviceManager.removeAgedDevices(new Date());
+        Thread.sleep((DeviceManagerImpl.DEVICE_AGING_TIMER + DeviceManagerImpl.DEVICE_AGING_TIMER_INTERVAL)*1000);
 
         rdevice = deviceManager.getDeviceByDataLayerAddress(dataLayerSource);
-
+        assertEquals(0, rdevice.getAttachmentPoints().size());
         assertEquals(0, rdevice.getNetworkAddresses().size());
 
         // Make sure the device's AP and NA were removed from storage
@@ -347,10 +347,8 @@ public class DeviceManagerImplTest extends FloodlightTestCase {
         assertEquals(0, rdevice.getAttachmentPoints().size());
         assertEquals(0, rdevice.getNetworkAddresses().size());
 
-        // Sleep a bit longer seconds to allow device age
-        Thread.sleep((DeviceManagerImpl.DEVICE_MAX_AGE - 
-        		Math.max(DeviceManagerImpl.DEVICE_NA_MAX_AGE, DeviceManagerImpl.DEVICE_AP_MAX_AGE))*1000);
-        deviceManager.removeAgedDevices(new Date());
+        // Sleep 4 more seconds to allow device aging thread to run
+        Thread.sleep(DeviceManagerImpl.DEVICE_MAX_AGE*1000);
 
         assertNull(deviceManager.getDeviceByDataLayerAddress(dataLayerSource));
 
-- 
GitLab