Randomize the prefix used by RouterAdvertisementResponder.

Currently RouterAdvertisementResponder always uses a prefix of
2001:db8::/64, even if there are multiple instances on different
interfaces. Randomize the prefix instead.

Test: TH
Bug: 240323229
Change-Id: I585ca804845f4278187602a6c9816470dcea04f8
diff --git a/staticlibs/testutils/devicetests/com/android/testutils/RouterAdvertisementResponder.java b/staticlibs/testutils/devicetests/com/android/testutils/RouterAdvertisementResponder.java
index 478161d..51d57bc 100644
--- a/staticlibs/testutils/devicetests/com/android/testutils/RouterAdvertisementResponder.java
+++ b/staticlibs/testutils/devicetests/com/android/testutils/RouterAdvertisementResponder.java
@@ -32,7 +32,6 @@
 
 import android.net.InetAddresses;
 import android.net.IpPrefix;
-import android.net.LinkAddress;
 import android.net.MacAddress;
 import android.util.ArrayMap;
 import android.util.Log;
@@ -52,6 +51,8 @@
 import java.net.Inet6Address;
 import java.nio.ByteBuffer;
 import java.util.Map;
+import java.util.Objects;
+import java.util.Random;
 
 /**
  * ND (RA & NA) responder class useful for tests that require a provisioned IPv6 interface.
@@ -59,16 +60,30 @@
  */
 public class RouterAdvertisementResponder extends PacketResponder {
     private static final String TAG = "RouterAdvertisementResponder";
-    private static final LinkAddress SLAAC_PREFIX = new LinkAddress("2001:db8::/64");
     private static final Inet6Address DNS_SERVER =
             (Inet6Address) InetAddresses.parseNumericAddress("2001:4860:4860::64");
     private final TapPacketReader mPacketReader;
     // Maps IPv6 address to MacAddress and isRouter boolean.
     private final Map<Inet6Address, Pair<MacAddress, Boolean>> mNeighborMap = new ArrayMap<>();
+    private final IpPrefix mPrefix;
 
-    public RouterAdvertisementResponder(TapPacketReader packetReader) {
+    public RouterAdvertisementResponder(TapPacketReader packetReader, IpPrefix prefix) {
         super(packetReader, RouterAdvertisementResponder::isRsOrNs, TAG);
         mPacketReader = packetReader;
+        mPrefix = Objects.requireNonNull(prefix);
+    }
+
+    public RouterAdvertisementResponder(TapPacketReader packetReader) {
+        this(packetReader, makeRandomPrefix());
+    }
+
+    private static IpPrefix makeRandomPrefix() {
+        final byte[] prefixBytes = new IpPrefix("2001:db8::/64").getAddress().getAddress();
+        final Random r = new Random();
+        for (int i = 4; i < 8; i++) {
+            prefixBytes[i] = (byte) r.nextInt();
+        }
+        return new IpPrefix(prefixBytes, 64);
     }
 
     /** Returns true if the packet is a router solicitation or neighbor solicitation message. */
@@ -105,11 +120,17 @@
         mNeighborMap.put(ip, new Pair<>(mac, false));
     }
 
+    /**
+     * @return the prefix that is announced in the Router Advertisements sent by this object.
+     */
+    public IpPrefix getPrefix() {
+        return mPrefix;
+    }
+
     private ByteBuffer buildPrefixOption() {
         return PrefixInformationOption.build(
-                new IpPrefix(SLAAC_PREFIX.getAddress(), SLAAC_PREFIX.getPrefixLength()),
-                (byte) (PIO_FLAG_ON_LINK | PIO_FLAG_AUTONOMOUS), 3600/*valid lifetime*/,
-                3600/*preferred lifetime*/);
+                mPrefix, (byte) (PIO_FLAG_ON_LINK | PIO_FLAG_AUTONOMOUS),
+                3600 /* valid lifetime */, 3600 /* preferred lifetime */);
     }
 
     private ByteBuffer buildRdnssOption() {