Add address flags and scope to LinkAddress.

This is necessary so that the framework can know whether an IPv6
address is likely to be usable (i.e., if it's global scope and
preferred). Also, it will simplify the address notification
methods in INetworkManagementEventObserver, which currently take
the address, the flags, and the scope as separate arguments.

1. Add flags and scope to the class and update the unit test.
   Use the IFA_F_* and RT_SCOPE_* constants defined by libcore.
   Since most callers don't know about flags and scope, provide
   constructors that default the flags to zero and determine the
   scope from the address. Addresses notified by the kernel will
   have these properly set. Make multicast addresses invalid.
   Update the class documentation.
2. Provide an isSameAddressAs() method that compares only the
   address and prefix information between two LinkAddress
   objects. This is necessary because an interface can't have
   two addresses with the same address/prefix but different
   flags.
3. Update LinkProperties's addLinkAddress and removeLinkAddress
   to identify existing addresses to add/remove using
   isSameAddressAs instead of implicit equals(). Specifically:
   - If addLinkAddress is called with an address that is already
     present, the existing address's flags and scope are updated.
     This allows, for example, an address on an interface to go
     from preferred to deprecated when it expires, without it
     having to be removed and re-added.
   - If removeLinkAddress is called with an address that is
     present but with different flags, it deletes that address
     instead of failing to find a match.
4. Update the INetworkManagementEventObserver address
   notification methods to take just a LinkAddress instead of
   LinkAddress, flags, and scope. While I'm at it, change the
   order of the arguments for consistency with the other
   functions in the interface.

Change-Id: Id8fe0f09a7e8f6bee1ea3b52102178b689a9336e
diff --git a/core/tests/coretests/src/android/net/LinkPropertiesTest.java b/core/tests/coretests/src/android/net/LinkPropertiesTest.java
index e63f6b0..a602e07 100644
--- a/core/tests/coretests/src/android/net/LinkPropertiesTest.java
+++ b/core/tests/coretests/src/android/net/LinkPropertiesTest.java
@@ -24,6 +24,8 @@
 import java.net.InetAddress;
 import java.util.ArrayList;
 
+import libcore.io.OsConstants;
+
 public class LinkPropertiesTest extends TestCase {
     private static InetAddress ADDRV4 = NetworkUtils.numericToInetAddress("75.208.6.1");
     private static InetAddress ADDRV6 = NetworkUtils.numericToInetAddress(
@@ -341,6 +343,10 @@
         assertFalse(rmnet0.removeStackedLink(clat4));
     }
 
+    private LinkAddress getFirstLinkAddress(LinkProperties lp) {
+        return lp.getLinkAddresses().iterator().next();
+    }
+
     @SmallTest
     public void testAddressMethods() {
         LinkProperties lp = new LinkProperties();
@@ -366,26 +372,56 @@
         // Addresses on the base link.
         // Check the return values of hasIPvXAddress and ensure the add/remove methods return true
         // iff something changes.
+        assertEquals(0, lp.getLinkAddresses().size());
         assertTrue(lp.addLinkAddress(LINKADDRV6));
+        assertEquals(1, lp.getLinkAddresses().size());
         assertFalse(lp.hasIPv4Address());
         assertTrue(lp.hasIPv6Address());
 
         assertTrue(lp.removeLinkAddress(LINKADDRV6));
+        assertEquals(0, lp.getLinkAddresses().size());
         assertTrue(lp.addLinkAddress(LINKADDRV4));
+        assertEquals(1, lp.getLinkAddresses().size());
         assertTrue(lp.hasIPv4Address());
         assertFalse(lp.hasIPv6Address());
 
         assertTrue(lp.addLinkAddress(LINKADDRV6));
+        assertEquals(2, lp.getLinkAddresses().size());
         assertTrue(lp.hasIPv4Address());
         assertTrue(lp.hasIPv6Address());
 
         // Adding an address twice has no effect.
         // Removing an address that's not present has no effect.
         assertFalse(lp.addLinkAddress(LINKADDRV4));
+        assertEquals(2, lp.getLinkAddresses().size());
         assertTrue(lp.hasIPv4Address());
         assertTrue(lp.removeLinkAddress(LINKADDRV4));
+        assertEquals(1, lp.getLinkAddresses().size());
         assertFalse(lp.hasIPv4Address());
         assertFalse(lp.removeLinkAddress(LINKADDRV4));
+        assertEquals(1, lp.getLinkAddresses().size());
+
+        // Adding an address that's already present but with different properties causes the
+        // existing address to be updated and returns true.
+        // Start with only LINKADDRV6.
+        assertEquals(1, lp.getLinkAddresses().size());
+        assertEquals(LINKADDRV6, getFirstLinkAddress(lp));
+
+        // Create a LinkAddress object for the same address, but with different flags.
+        LinkAddress deprecated = new LinkAddress(ADDRV6, 128,
+                OsConstants.IFA_F_DEPRECATED, OsConstants.RT_SCOPE_UNIVERSE);
+        assertTrue(deprecated.isSameAddressAs(LINKADDRV6));
+        assertFalse(deprecated.equals(LINKADDRV6));
+
+        // Check that adding it updates the existing address instead of adding a new one.
+        assertTrue(lp.addLinkAddress(deprecated));
+        assertEquals(1, lp.getLinkAddresses().size());
+        assertEquals(deprecated, getFirstLinkAddress(lp));
+        assertFalse(LINKADDRV6.equals(getFirstLinkAddress(lp)));
+
+        // Removing LINKADDRV6 removes deprecated, because removing addresses ignores properties.
+        assertTrue(lp.removeLinkAddress(LINKADDRV6));
+        assertEquals(0, lp.getLinkAddresses().size());
     }
 
     @SmallTest