@Test
public void testGetIPv4Addresses() {

	// Looks like Date is only 1s granularity
	ITopologyService mockTopology = createMock(ITopologyService.class);
	deviceManager.topology = mockTopology;
	expect(mockTopology.isAttachmentPointPort(DatapathId.of(anyLong()),
			OFPort.of(anyShort()))).
			andReturn(true).anyTimes();
	expect(mockTopology.getOpenflowDomainId(DatapathId.of(anyLong()))).andReturn(DatapathId.of(1L)).anyTimes();
	expect(mockTopology.isConsistent(DatapathId.of(EasyMock.anyLong()),
			OFPort.of(EasyMock.anyShort()),
			DatapathId.of(EasyMock.anyLong()),
			OFPort.of(EasyMock.anyShort())))
			.andReturn(false)
			.anyTimes();
	expect(mockTopology.isBroadcastDomainPort(DatapathId.of(EasyMock.anyLong()),
			OFPort.of(EasyMock.anyShort())))
			.andReturn(false)
			.anyTimes();
	expect(mockTopology.isInSameBroadcastDomain(DatapathId.of(EasyMock.anyLong()),
			OFPort.of(EasyMock.anyShort()),
			DatapathId.of(EasyMock.anyLong()),
			OFPort.of(EasyMock.anyShort()))).
			andReturn(false).anyTimes();
	replay(mockTopology);
	Entity e1 = new Entity(MacAddress.of(1L), VlanVid.ofVlan(1), IPv4Address.NONE, IPv6Address.NONE, DatapathId.NONE, OFPort.ZERO, new Date(2000));
	Device d1 = deviceManager.learnDeviceByEntity(e1);
	assertArrayEquals(new IPv4Address[0], d1.getIPv4Addresses());
	Entity e2 = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.of(2), IPv6Address.NONE, DatapathId.NONE, OFPort.ZERO, new Date(2000));
	Device d2 = deviceManager.learnDeviceByEntity(e2);
	d2 = deviceManager.learnDeviceByEntity(e2);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d2.getIPv4Addresses());
	// More than one entity
	Entity e2b = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.NONE, IPv6Address.NONE, DatapathId.of(2L), OFPort.of(2), new Date(3000));
	d2 = deviceManager.learnDeviceByEntity(e2b);
	assertEquals(2, d2.entities.length);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d2.getIPv4Addresses());
	// and now add an entity with an IP
	Entity e2c = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.of(2), IPv6Address.NONE, DatapathId.of(2L), OFPort.of(3), new Date(3000));
	d2 = deviceManager.learnDeviceByEntity(e2c);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d2.getIPv4Addresses());
	assertEquals(3, d2.entities.length);
	// Other devices with different IPs shouldn't interfere
	Entity e3 = new Entity(MacAddress.of(3L), VlanVid.ofVlan(3), IPv4Address.of(3), IPv6Address.NONE, DatapathId.NONE, OFPort.ZERO, new Date(4000));
	Entity e3b = new Entity(MacAddress.of(3L), VlanVid.ofVlan(3), IPv4Address.of(3), IPv6Address.NONE, DatapathId.of(3L), OFPort.of(3), new Date(4400));
	Device d3 = deviceManager.learnDeviceByEntity(e3);
	d3 = deviceManager.learnDeviceByEntity(e3b);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d2.getIPv4Addresses());
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(3) }, d3.getIPv4Addresses());
	// Add another IP to d3
	Entity e3c = new Entity(MacAddress.of(3L), VlanVid.ofVlan(3), IPv4Address.of(33), IPv6Address.NONE, DatapathId.of(3L), OFPort.of(3), new Date(4400));
	d3 = deviceManager.learnDeviceByEntity(e3c);
	IPv4Address[] ips = d3.getIPv4Addresses();
	Arrays.sort(ips);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(3), IPv4Address.of(33) }, ips);
	// Add another device that also claims IP2 but is older than e2
	Entity e4 = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.of(2), IPv6Address.NONE, DatapathId.NONE, OFPort.ZERO, new Date(1000));
	Entity e4b = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.NONE, IPv6Address.NONE, DatapathId.of(4L), OFPort.of(4), new Date(1000));
	Device d4 = deviceManager.learnDeviceByEntity(e4);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d2.getIPv4Addresses());
	assertArrayEquals(new IPv4Address[0],  d4.getIPv4Addresses());
	// add another entity to d4
	d4 = deviceManager.learnDeviceByEntity(e4b);
	assertArrayEquals(new IPv4Address[0], d4.getIPv4Addresses());
	// Make e4 and e4a newer
	Entity e4c = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.of(2), IPv6Address.NONE, DatapathId.NONE, OFPort.ZERO, new Date(5000));
	Entity e4d = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.NONE, IPv6Address.NONE, DatapathId.of(4L), OFPort.of(5), new Date(5000));
	d4 = deviceManager.learnDeviceByEntity(e4c);
	d4 = deviceManager.learnDeviceByEntity(e4d);
	assertArrayEquals(new IPv4Address[0], d2.getIPv4Addresses());
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d4.getIPv4Addresses());
	// Add another newer entity to d2 but with different IP
	Entity e2d = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.of(22), IPv6Address.NONE, DatapathId.of(4L), OFPort.of(6), new Date(6000));
	d2 = deviceManager.learnDeviceByEntity(e2d);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(22) }, d2.getIPv4Addresses());
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2) }, d4.getIPv4Addresses());
	// new IP for d2,d4 but with same timestamp. Both devices get the IP
	Entity e2e = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.of(42), IPv6Address.NONE, DatapathId.of(2L), OFPort.of(4), new Date(7000));
	d2 = deviceManager.learnDeviceByEntity(e2e);
	ips= d2.getIPv4Addresses();
	Arrays.sort(ips);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(22), IPv4Address.of(42) }, ips);
	Entity e4e = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.of(42), IPv6Address.NONE, DatapathId.of(4L), OFPort.of(7), new Date(7000));
	d4 = deviceManager.learnDeviceByEntity(e4e);
	ips= d4.getIPv4Addresses();
	Arrays.sort(ips);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2), IPv4Address.of(42) }, ips);
	// add a couple more IPs
	Entity e2f = new Entity(MacAddress.of(2L), VlanVid.ofVlan(2), IPv4Address.of(4242), IPv6Address.NONE, DatapathId.of(2L), OFPort.of(5), new Date(8000));
	d2 = deviceManager.learnDeviceByEntity(e2f);
	ips= d2.getIPv4Addresses();
	Arrays.sort(ips);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(22), IPv4Address.of(42), IPv4Address.of(4242) }, ips);
	Entity e4f = new Entity(MacAddress.of(4L), VlanVid.ofVlan(4), IPv4Address.of(4242), IPv6Address.NONE, DatapathId.of(4L), OFPort.of(8), new Date(9000));
	d4 = deviceManager.learnDeviceByEntity(e4f);
	ips= d4.getIPv4Addresses();
	Arrays.sort(ips);
	assertArrayEquals(new IPv4Address[] { IPv4Address.of(2), IPv4Address.of(42), IPv4Address.of(4242) }, ips);
}