Merge changes from topic "ethernet-move-tm-dev" into tm-dev

* changes:
  Remove connectivity-tiramisu-updatable-sources
  Merge history of opt/net/ethernet
diff --git a/Tethering/src/com/android/networkstack/tethering/BpfCoordinator.java b/Tethering/src/com/android/networkstack/tethering/BpfCoordinator.java
index 225bd58..f8a1094 100644
--- a/Tethering/src/com/android/networkstack/tethering/BpfCoordinator.java
+++ b/Tethering/src/com/android/networkstack/tethering/BpfCoordinator.java
@@ -2033,5 +2033,13 @@
         return mBpfConntrackEventConsumer;
     }
 
+    // Return tethering client information. This is used for testing only.
+    @NonNull
+    @VisibleForTesting
+    final HashMap<IpServer, HashMap<Inet4Address, ClientInfo>>
+            getTetherClientsForTesting() {
+        return mTetherClients;
+    }
+
     private static native String[] getBpfCounterNames();
 }
diff --git a/Tethering/tests/unit/src/com/android/networkstack/tethering/BpfCoordinatorTest.java b/Tethering/tests/unit/src/com/android/networkstack/tethering/BpfCoordinatorTest.java
index 179fc8a..4967d27 100644
--- a/Tethering/tests/unit/src/com/android/networkstack/tethering/BpfCoordinatorTest.java
+++ b/Tethering/tests/unit/src/com/android/networkstack/tethering/BpfCoordinatorTest.java
@@ -224,8 +224,6 @@
             private int mSrcPort = PRIVATE_PORT;
             private int mDstPort = REMOTE_PORT;
 
-            Builder() {}
-
             public Builder setProto(int proto) {
                 if (proto != IPPROTO_TCP && proto != IPPROTO_UDP) {
                     fail("Not support protocol " + proto);
@@ -250,8 +248,6 @@
             private int mSrcPort = REMOTE_PORT;
             private int mDstPort = PUBLIC_PORT;
 
-            Builder() {}
-
             public Builder setProto(int proto) {
                 if (proto != IPPROTO_TCP && proto != IPPROTO_UDP) {
                     fail("Not support protocol " + proto);
@@ -279,8 +275,6 @@
             private int mDstPort = REMOTE_PORT;
             private long mLastUsed = 0;
 
-            Builder() {}
-
             public Tether4Value build() {
                 return new Tether4Value(mOif, mEthDstMac, mEthSrcMac, mEthProto, mPmtu,
                         mSrc46, mDst46, mSrcPort, mDstPort, mLastUsed);
@@ -301,8 +295,6 @@
             private int mDstPort = PRIVATE_PORT;
             private long mLastUsed = 0;
 
-            Builder() {}
-
             public Tether4Value build() {
                 return new Tether4Value(mOif, mEthDstMac, mEthSrcMac, mEthProto, mPmtu,
                         mSrc46, mDst46, mSrcPort, mDstPort, mLastUsed);
@@ -321,8 +313,6 @@
             private short mPublicPort = PUBLIC_PORT;
             private short mRemotePort = REMOTE_PORT;
 
-            Builder() {}
-
             public Builder setMsgType(short msgType) {
                 if (msgType != IPCTNL_MSG_CT_NEW && msgType != IPCTNL_MSG_CT_DELETE) {
                     fail("Not support message type " + msgType);
@@ -377,6 +367,7 @@
     // Late init since the object must be initialized by the BPF coordinator instance because
     // it has to access the non-static function of BPF coordinator.
     private BpfConntrackEventConsumer mConsumer;
+    private HashMap<IpServer, HashMap<Inet4Address, ClientInfo>> mTetherClients;
 
     private long mElapsedRealtimeNanos = 0;
     private final ArgumentCaptor<ArrayList> mStringArrayCaptor =
@@ -482,6 +473,8 @@
         final BpfCoordinator coordinator = new BpfCoordinator(mDeps);
 
         mConsumer = coordinator.getBpfConntrackEventConsumerForTesting();
+        mTetherClients = coordinator.getTetherClientsForTesting();
+
         final ArgumentCaptor<BpfCoordinator.BpfTetherStatsProvider>
                 tetherStatsProviderCaptor =
                 ArgumentCaptor.forClass(BpfCoordinator.BpfTetherStatsProvider.class);
@@ -1793,4 +1786,280 @@
             clearInvocations(mBpfUpstream4Map, mBpfDownstream4Map);
         }
     }
+
+    // Test network topology:
+    //
+    //            public network                UE                private network
+    //                  |                     /     \                    |
+    // +------------+   V  +-------------+             +--------------+  V  +------------+
+    // |   Sever    +------+  Upstream   |+------+-----+ Downstream 1 +-----+  Client A  |
+    // +------------+      +-------------+|      |     +--------------+     +------------+
+    // remote ip            +-------------+      |                          private ip
+    // 140.112.8.116:443   public ip             |                          192.168.80.12:62449
+    //                     (upstream 1, rawip)   |
+    //                     1.0.0.1:62449         |
+    //                     1.0.0.1:62450         |     +--------------+     +------------+
+    //                            - or -         +-----+ Downstream 2 +-----+  Client B  |
+    //                     (upstream 2, ether)         +--------------+     +------------+
+    //                                                                      private ip
+    //                                                                      192.168.90.12:62450
+    //
+    // Build two test rule sets which include BPF upstream and downstream rules.
+    //
+    // Rule set A: a socket connection from client A to remote server via the first upstream
+    //             (UPSTREAM_IFINDEX).
+    //             192.168.80.12:62449 -> 1.0.0.1:62449 -> 140.112.8.116:443
+    // Rule set B: a socket connection from client B to remote server via the first upstream
+    //             (UPSTREAM_IFINDEX).
+    //             192.168.80.12:62450 -> 1.0.0.1:62450 -> 140.112.8.116:443
+    //
+    // The second upstream (UPSTREAM_IFINDEX2) is an ethernet interface which is not supported by
+    // BPF. Used for testing the rule adding and removing on an unsupported upstream interface.
+    //
+    private static final Tether4Key UPSTREAM4_RULE_KEY_A = makeUpstream4Key(
+            DOWNSTREAM_IFINDEX, DOWNSTREAM_MAC, PRIVATE_ADDR, PRIVATE_PORT);
+    private static final Tether4Value UPSTREAM4_RULE_VALUE_A = makeUpstream4Value(PUBLIC_PORT);
+    private static final Tether4Key DOWNSTREAM4_RULE_KEY_A = makeDownstream4Key(PUBLIC_PORT);
+    private static final Tether4Value DOWNSTREAM4_RULE_VALUE_A = makeDownstream4Value(
+            DOWNSTREAM_IFINDEX, MAC_A, DOWNSTREAM_MAC, PRIVATE_ADDR, PRIVATE_PORT);
+
+    private static final Tether4Key UPSTREAM4_RULE_KEY_B = makeUpstream4Key(
+            DOWNSTREAM_IFINDEX2, DOWNSTREAM_MAC2, PRIVATE_ADDR2, PRIVATE_PORT2);
+    private static final Tether4Value UPSTREAM4_RULE_VALUE_B = makeUpstream4Value(PUBLIC_PORT2);
+    private static final Tether4Key DOWNSTREAM4_RULE_KEY_B = makeDownstream4Key(PUBLIC_PORT2);
+    private static final Tether4Value DOWNSTREAM4_RULE_VALUE_B = makeDownstream4Value(
+            DOWNSTREAM_IFINDEX2, MAC_B, DOWNSTREAM_MAC2, PRIVATE_ADDR2, PRIVATE_PORT2);
+
+    private static final ConntrackEvent CONNTRACK_EVENT_A = makeTestConntrackEvent(
+            PUBLIC_PORT, PRIVATE_ADDR, PRIVATE_PORT);
+
+    private static final ConntrackEvent CONNTRACK_EVENT_B = makeTestConntrackEvent(
+            PUBLIC_PORT2, PRIVATE_ADDR2, PRIVATE_PORT2);
+
+    @NonNull
+    private static Tether4Key makeUpstream4Key(final int downstreamIfindex,
+            @NonNull final MacAddress downstreamMac, @NonNull final Inet4Address privateAddr,
+            final short privatePort) {
+        return new Tether4Key(downstreamIfindex, downstreamMac, (short) IPPROTO_TCP,
+            privateAddr.getAddress(), REMOTE_ADDR.getAddress(), privatePort, REMOTE_PORT);
+    }
+
+    @NonNull
+    private static Tether4Key makeDownstream4Key(final short publicPort) {
+        return new Tether4Key(UPSTREAM_IFINDEX, MacAddress.ALL_ZEROS_ADDRESS /* dstMac (rawip) */,
+                (short) IPPROTO_TCP, REMOTE_ADDR.getAddress(), PUBLIC_ADDR.getAddress(),
+                REMOTE_PORT, publicPort);
+    }
+
+    @NonNull
+    private static Tether4Value makeUpstream4Value(final short publicPort) {
+        return new Tether4Value(UPSTREAM_IFINDEX,
+                MacAddress.ALL_ZEROS_ADDRESS /* ethDstMac (rawip) */,
+                MacAddress.ALL_ZEROS_ADDRESS /* ethSrcMac (rawip) */, ETH_P_IP,
+                NetworkStackConstants.ETHER_MTU, toIpv4MappedAddressBytes(PUBLIC_ADDR),
+                toIpv4MappedAddressBytes(REMOTE_ADDR), publicPort, REMOTE_PORT,
+                0 /* lastUsed */);
+    }
+
+    @NonNull
+    private static Tether4Value makeDownstream4Value(final int downstreamIfindex,
+            @NonNull final MacAddress clientMac, @NonNull final MacAddress downstreamMac,
+            @NonNull final Inet4Address privateAddr, final short privatePort) {
+        return new Tether4Value(downstreamIfindex, clientMac, downstreamMac,
+                ETH_P_IP, NetworkStackConstants.ETHER_MTU, toIpv4MappedAddressBytes(REMOTE_ADDR),
+                toIpv4MappedAddressBytes(privateAddr), REMOTE_PORT, privatePort, 0 /* lastUsed */);
+    }
+
+    @NonNull
+    private static ConntrackEvent makeTestConntrackEvent(final short publicPort,
+                @NonNull final Inet4Address privateAddr, final short privatePort) {
+        return new ConntrackEvent(
+                (short) (NetlinkConstants.NFNL_SUBSYS_CTNETLINK << 8 | IPCTNL_MSG_CT_NEW),
+                new Tuple(new TupleIpv4(privateAddr, REMOTE_ADDR),
+                        new TupleProto((byte) IPPROTO_TCP, privatePort, REMOTE_PORT)),
+                new Tuple(new TupleIpv4(REMOTE_ADDR, PUBLIC_ADDR),
+                        new TupleProto((byte) IPPROTO_TCP, REMOTE_PORT, publicPort)),
+                ESTABLISHED_MASK,
+                100 /* nonzero, CT_NEW */);
+    }
+
+    void checkRule4ExistInUpstreamDownstreamMap() throws Exception {
+        assertEquals(UPSTREAM4_RULE_VALUE_A, mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_A));
+        assertEquals(DOWNSTREAM4_RULE_VALUE_A, mBpfDownstream4Map.getValue(
+                DOWNSTREAM4_RULE_KEY_A));
+        assertEquals(UPSTREAM4_RULE_VALUE_B, mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_B));
+        assertEquals(DOWNSTREAM4_RULE_VALUE_B, mBpfDownstream4Map.getValue(
+                DOWNSTREAM4_RULE_KEY_B));
+    }
+
+    void checkRule4NotExistInUpstreamDownstreamMap() throws Exception {
+        assertNull(mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_A));
+        assertNull(mBpfDownstream4Map.getValue(DOWNSTREAM4_RULE_KEY_A));
+        assertNull(mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_B));
+        assertNull(mBpfDownstream4Map.getValue(DOWNSTREAM4_RULE_KEY_B));
+    }
+
+    // Both #addDownstreamAndClientInformationTo and #setUpstreamInformationTo need to be called
+    // before this function because upstream and downstream information are required to build
+    // the rules while conntrack event is received.
+    void addAndCheckRule4ForDownstreams() throws Exception {
+        // Add rule set A which is on the first downstream and rule set B which is on the second
+        // downstream.
+        mConsumer.accept(CONNTRACK_EVENT_A);
+        mConsumer.accept(CONNTRACK_EVENT_B);
+
+        // Check that both rule set A and B were added.
+        checkRule4ExistInUpstreamDownstreamMap();
+    }
+
+    @Test
+    @IgnoreUpTo(Build.VERSION_CODES.R)
+    public void testTetherOffloadRule4Clear_RemoveDownstream() throws Exception {
+        final BpfCoordinator coordinator = makeBpfCoordinator();
+
+        // Initialize upstream and downstream information manually but calling the setup helper
+        // #initBpfCoordinatorForRule4 because this test needs to {update, remove} upstream and
+        // downstream manually for testing.
+        addDownstreamAndClientInformationTo(coordinator, DOWNSTREAM_IFINDEX);
+        addDownstreamAndClientInformationTo(coordinator, DOWNSTREAM_IFINDEX2);
+
+        setUpstreamInformationTo(coordinator, UPSTREAM_IFINDEX);
+        addAndCheckRule4ForDownstreams();
+
+        // [1] Remove the first downstream. Remove only the rule set A which is on the first
+        // downstream.
+        coordinator.tetherOffloadClientClear(mIpServer);
+        assertNull(mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_A));
+        assertNull(mBpfDownstream4Map.getValue(DOWNSTREAM4_RULE_KEY_A));
+        assertEquals(UPSTREAM4_RULE_VALUE_B, mBpfUpstream4Map.getValue(
+                UPSTREAM4_RULE_KEY_B));
+        assertEquals(DOWNSTREAM4_RULE_VALUE_B, mBpfDownstream4Map.getValue(
+                DOWNSTREAM4_RULE_KEY_B));
+
+        // Clear client information for the first downstream only.
+        assertNull(mTetherClients.get(mIpServer));
+        assertNotNull(mTetherClients.get(mIpServer2));
+
+        // [2] Remove the second downstream. Remove the rule set B which is on the second
+        // downstream.
+        coordinator.tetherOffloadClientClear(mIpServer2);
+        assertNull(mBpfUpstream4Map.getValue(UPSTREAM4_RULE_KEY_B));
+        assertNull(mBpfDownstream4Map.getValue(DOWNSTREAM4_RULE_KEY_B));
+
+        // Clear client information for the second downstream.
+        assertNull(mTetherClients.get(mIpServer2));
+    }
+
+    private void asseertClientInfoExist(@NonNull IpServer ipServer,
+            @NonNull ClientInfo clientInfo) {
+        HashMap<Inet4Address, ClientInfo> clients = mTetherClients.get(ipServer);
+        assertNotNull(clients);
+        assertEquals(clientInfo, clients.get(clientInfo.clientAddress));
+    }
+
+    // Although either ClientInfo for a given downstream (IpServer) is not found or a given
+    // client address is not found on a given downstream can be treated "ClientInfo not
+    // exist", we still want to know the real reason exactly. For example, we don't the
+    // exact reason in the following:
+    //   assertNull(clients == null ? clients : clients.get(clientInfo.clientAddress));
+    // This helper only verifies the case that the downstream still has at least one client.
+    // In other words, ClientInfo for a given IpServer has not been removed yet.
+    private void asseertClientInfoNotExist(@NonNull IpServer ipServer,
+            @NonNull ClientInfo clientInfo) {
+        HashMap<Inet4Address, ClientInfo> clients = mTetherClients.get(ipServer);
+        assertNotNull(clients);
+        assertNull(clients.get(clientInfo.clientAddress));
+    }
+
+    @Test
+    @IgnoreUpTo(Build.VERSION_CODES.R)
+    public void testTetherOffloadRule4Clear_ChangeOrRemoveUpstream() throws Exception {
+        final BpfCoordinator coordinator = makeBpfCoordinator();
+
+        // Initialize upstream and downstream information manually but calling the helper
+        // #initBpfCoordinatorForRule4 because this test needs to {update, remove} upstream and
+        // downstream.
+        addDownstreamAndClientInformationTo(coordinator, DOWNSTREAM_IFINDEX);
+        addDownstreamAndClientInformationTo(coordinator, DOWNSTREAM_IFINDEX2);
+
+        setUpstreamInformationTo(coordinator, UPSTREAM_IFINDEX);
+        addAndCheckRule4ForDownstreams();
+
+        // [1] Update the same upstream state. Nothing happens.
+        setUpstreamInformationTo(coordinator, UPSTREAM_IFINDEX);
+        checkRule4ExistInUpstreamDownstreamMap();
+
+        // [2] Switch upstream interface from the first upstream (rawip, bpf supported) to
+        // the second upstream (ethernet, bpf not supported). Clear all rules.
+        setUpstreamInformationTo(coordinator, UPSTREAM_IFINDEX2);
+        checkRule4NotExistInUpstreamDownstreamMap();
+
+        // Setup the upstream interface information and the rules for next test.
+        setUpstreamInformationTo(coordinator, UPSTREAM_IFINDEX);
+        addAndCheckRule4ForDownstreams();
+
+        // [3] Switch upstream from the first upstream (rawip, bpf supported) to no upstream. Clear
+        // all rules.
+        setUpstreamInformationTo(coordinator, INVALID_IFINDEX);
+        checkRule4NotExistInUpstreamDownstreamMap();
+
+        // Client information should be not deleted.
+        asseertClientInfoExist(mIpServer, CLIENT_INFO_A);
+        asseertClientInfoExist(mIpServer2, CLIENT_INFO_B);
+    }
+
+    @Test
+    @IgnoreUpTo(Build.VERSION_CODES.R)
+    public void testTetherOffloadClientAddRemove() throws Exception {
+        final BpfCoordinator coordinator = makeBpfCoordinator();
+
+        // [1] Add client information A and B on on the same downstream.
+        final ClientInfo clientA = new ClientInfo(DOWNSTREAM_IFINDEX, DOWNSTREAM_MAC,
+                PRIVATE_ADDR, MAC_A);
+        final ClientInfo clientB = new ClientInfo(DOWNSTREAM_IFINDEX, DOWNSTREAM_MAC,
+                PRIVATE_ADDR2, MAC_B);
+        coordinator.tetherOffloadClientAdd(mIpServer, clientA);
+        coordinator.tetherOffloadClientAdd(mIpServer, clientB);
+        asseertClientInfoExist(mIpServer, clientA);
+        asseertClientInfoExist(mIpServer, clientB);
+
+        // Add the rules for client A and client B.
+        final Tether4Key upstream4KeyA = makeUpstream4Key(
+                DOWNSTREAM_IFINDEX, DOWNSTREAM_MAC, PRIVATE_ADDR, PRIVATE_PORT);
+        final Tether4Value upstream4ValueA = makeUpstream4Value(PUBLIC_PORT);
+        final Tether4Key downstream4KeyA = makeDownstream4Key(PUBLIC_PORT);
+        final Tether4Value downstream4ValueA = makeDownstream4Value(
+                DOWNSTREAM_IFINDEX, MAC_A, DOWNSTREAM_MAC, PRIVATE_ADDR, PRIVATE_PORT);
+        final Tether4Key upstream4KeyB = makeUpstream4Key(
+                DOWNSTREAM_IFINDEX, DOWNSTREAM_MAC2, PRIVATE_ADDR2, PRIVATE_PORT2);
+        final Tether4Value upstream4ValueB = makeUpstream4Value(PUBLIC_PORT2);
+        final Tether4Key downstream4KeyB = makeDownstream4Key(PUBLIC_PORT2);
+        final Tether4Value downstream4ValueB = makeDownstream4Value(
+                DOWNSTREAM_IFINDEX, MAC_B, DOWNSTREAM_MAC2, PRIVATE_ADDR2, PRIVATE_PORT2);
+
+        mBpfUpstream4Map.insertEntry(upstream4KeyA, upstream4ValueA);
+        mBpfDownstream4Map.insertEntry(downstream4KeyA, downstream4ValueA);
+        mBpfUpstream4Map.insertEntry(upstream4KeyB, upstream4ValueB);
+        mBpfDownstream4Map.insertEntry(downstream4KeyB, downstream4ValueB);
+
+        // [2] Remove client information A. Only the rules on client A should be removed and
+        // the rules on client B should exist.
+        coordinator.tetherOffloadClientRemove(mIpServer, clientA);
+        asseertClientInfoNotExist(mIpServer, clientA);
+        asseertClientInfoExist(mIpServer, clientB);
+        assertNull(mBpfUpstream4Map.getValue(upstream4KeyA));
+        assertNull(mBpfDownstream4Map.getValue(downstream4KeyA));
+        assertEquals(upstream4ValueB, mBpfUpstream4Map.getValue(upstream4KeyB));
+        assertEquals(downstream4ValueB, mBpfDownstream4Map.getValue(downstream4KeyB));
+
+        // [3] Remove client information B. The rules on client B should be removed.
+        // Exactly, ClientInfo for a given IpServer is removed because the last client B
+        // has been removed from the downstream. Can't use the helper #asseertClientInfoExist
+        // to check because the container ClientInfo for a given downstream has been removed.
+        // See #asseertClientInfoExist.
+        coordinator.tetherOffloadClientRemove(mIpServer, clientB);
+        assertNull(mTetherClients.get(mIpServer));
+        assertNull(mBpfUpstream4Map.getValue(upstream4KeyB));
+        assertNull(mBpfDownstream4Map.getValue(downstream4KeyB));
+    }
 }
diff --git a/framework-t/api/module-lib-current.txt b/framework-t/api/module-lib-current.txt
index 216081a..5a8d47b 100644
--- a/framework-t/api/module-lib-current.txt
+++ b/framework-t/api/module-lib-current.txt
@@ -112,24 +112,6 @@
     field @NonNull public static final android.os.Parcelable.Creator<android.net.NetworkStateSnapshot> CREATOR;
   }
 
-  public final class NetworkStats implements java.lang.Iterable<android.net.NetworkStats.Entry> android.os.Parcelable {
-    method @NonNull public java.util.Iterator<android.net.NetworkStats.Entry> iterator();
-  }
-
-  public static class NetworkStats.Entry {
-    method public int getDefaultNetwork();
-    method public int getMetered();
-    method public long getOperations();
-    method public int getRoaming();
-    method public long getRxBytes();
-    method public long getRxPackets();
-    method public int getSet();
-    method public int getTag();
-    method public long getTxBytes();
-    method public long getTxPackets();
-    method public int getUid();
-  }
-
   public class NetworkStatsCollection {
     method @NonNull public java.util.Map<android.net.NetworkStatsCollection.Key,android.net.NetworkStatsHistory> getEntries();
   }
diff --git a/framework-t/api/system-current.txt b/framework-t/api/system-current.txt
index 9fe55ce..c59fb68 100644
--- a/framework-t/api/system-current.txt
+++ b/framework-t/api/system-current.txt
@@ -26,6 +26,7 @@
     method public int getVersion();
     field public static final int BROADCAST_TYPE_NEARBY_PRESENCE = 3; // 0x3
     field public static final int BROADCAST_TYPE_UNKNOWN = -1; // 0xffffffff
+    field public static final int MEDIUM_BLE = 1; // 0x1
     field public static final int PRESENCE_VERSION_UNKNOWN = -1; // 0xffffffff
     field public static final int PRESENCE_VERSION_V0 = 0; // 0x0
     field public static final int PRESENCE_VERSION_V1 = 1; // 0x1
@@ -297,7 +298,6 @@
     field public static final int CREDENTIAL_TYPE_PUBLIC = 1; // 0x1
     field public static final int IDENTITY_TYPE_PRIVATE = 1; // 0x1
     field public static final int IDENTITY_TYPE_PROVISIONED = 2; // 0x2
-    field public static final int IDENTITY_TYPE_PUBLIC = 4; // 0x4
     field public static final int IDENTITY_TYPE_TRUSTED = 3; // 0x3
     field public static final int IDENTITY_TYPE_UNKNOWN = 0; // 0x0
   }
@@ -483,6 +483,7 @@
     method @NonNull public android.net.NetworkStats add(@NonNull android.net.NetworkStats);
     method @NonNull public android.net.NetworkStats addEntry(@NonNull android.net.NetworkStats.Entry);
     method public int describeContents();
+    method @NonNull public java.util.Iterator<android.net.NetworkStats.Entry> iterator();
     method @NonNull public android.net.NetworkStats subtract(@NonNull android.net.NetworkStats);
     method public void writeToParcel(@NonNull android.os.Parcel, int);
     field @NonNull public static final android.os.Parcelable.Creator<android.net.NetworkStats> CREATOR;
@@ -506,6 +507,17 @@
 
   public static class NetworkStats.Entry {
     ctor public NetworkStats.Entry(@Nullable String, int, int, int, int, int, int, long, long, long, long, long);
+    method public int getDefaultNetwork();
+    method public int getMetered();
+    method public long getOperations();
+    method public int getRoaming();
+    method public long getRxBytes();
+    method public long getRxPackets();
+    method public int getSet();
+    method public int getTag();
+    method public long getTxBytes();
+    method public long getTxPackets();
+    method public int getUid();
   }
 
   public class TrafficStats {
diff --git a/framework-t/src/android/net/NetworkStats.java b/framework-t/src/android/net/NetworkStats.java
index bcfeab9..51ff5ec 100644
--- a/framework-t/src/android/net/NetworkStats.java
+++ b/framework-t/src/android/net/NetworkStats.java
@@ -16,8 +16,6 @@
 
 package android.net;
 
-import static android.annotation.SystemApi.Client.MODULE_LIBRARIES;
-
 import static com.android.net.module.util.NetworkStatsUtils.multiplySafeByRational;
 
 import android.annotation.IntDef;
@@ -391,102 +389,80 @@
 
         /**
          * @return the uid of this entry.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public int getUid() {
             return uid;
         }
 
         /**
          * @return the set state of this entry.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         @State public int getSet() {
             return set;
         }
 
         /**
          * @return the tag value of this entry.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public int getTag() {
             return tag;
         }
 
         /**
          * @return the metered state.
-         * @hide
          */
         @Meteredness
-        @SystemApi(client = MODULE_LIBRARIES)
         public int getMetered() {
             return metered;
         }
 
         /**
          * @return the roaming state.
-         * @hide
          */
         @Roaming
-        @SystemApi(client = MODULE_LIBRARIES)
         public int getRoaming() {
             return roaming;
         }
 
         /**
          * @return the default network state.
-         * @hide
          */
         @DefaultNetwork
-        @SystemApi(client = MODULE_LIBRARIES)
         public int getDefaultNetwork() {
             return defaultNetwork;
         }
 
         /**
          * @return the number of received bytes.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public long getRxBytes() {
             return rxBytes;
         }
 
         /**
          * @return the number of received packets.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public long getRxPackets() {
             return rxPackets;
         }
 
         /**
          * @return the number of transmitted bytes.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public long getTxBytes() {
             return txBytes;
         }
 
         /**
          * @return the number of transmitted packets.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public long getTxPackets() {
             return txPackets;
         }
 
         /**
          * @return the count of network operations performed for this entry.
-         * @hide
          */
-        @SystemApi(client = MODULE_LIBRARIES)
         public long getOperations() {
             return operations;
         }
@@ -708,7 +684,7 @@
      * The remove() method is not implemented and will throw UnsupportedOperationException.
      * @hide
      */
-    @SystemApi(client = MODULE_LIBRARIES)
+    @SystemApi
     @NonNull public Iterator<Entry> iterator() {
         return new Iterator<Entry>() {
             int mIndex = 0;
diff --git a/framework/src/android/net/QosSocketInfo.java b/framework/src/android/net/QosSocketInfo.java
index a45d507..39c2f33 100644
--- a/framework/src/android/net/QosSocketInfo.java
+++ b/framework/src/android/net/QosSocketInfo.java
@@ -16,6 +16,9 @@
 
 package android.net;
 
+import static android.system.OsConstants.SOCK_DGRAM;
+import static android.system.OsConstants.SOCK_STREAM;
+
 import android.annotation.NonNull;
 import android.annotation.Nullable;
 import android.annotation.SystemApi;
@@ -24,6 +27,7 @@
 import android.os.Parcelable;
 
 import java.io.IOException;
+import java.net.DatagramSocket;
 import java.net.InetAddress;
 import java.net.InetSocketAddress;
 import java.net.Socket;
@@ -53,6 +57,8 @@
     @Nullable
     private final InetSocketAddress mRemoteSocketAddress;
 
+    private final int mSocketType;
+
     /**
      * The {@link Network} the socket is on.
      *
@@ -98,6 +104,16 @@
     }
 
     /**
+     * The socket type of the socket passed in when this QosSocketInfo object was constructed.
+     *
+     * @return the socket type of the socket.
+     * @hide
+     */
+    public int getSocketType()  {
+        return mSocketType;
+    }
+
+    /**
      * Creates a {@link QosSocketInfo} given a {@link Network} and bound {@link Socket}.  The
      * {@link Socket} must remain bound in order to receive {@link QosSession}s.
      *
@@ -112,6 +128,32 @@
         mParcelFileDescriptor = ParcelFileDescriptor.fromSocket(socket);
         mLocalSocketAddress =
                 new InetSocketAddress(socket.getLocalAddress(), socket.getLocalPort());
+        mSocketType = SOCK_STREAM;
+
+        if (socket.isConnected()) {
+            mRemoteSocketAddress = (InetSocketAddress) socket.getRemoteSocketAddress();
+        } else {
+            mRemoteSocketAddress = null;
+        }
+    }
+
+    /**
+     * Creates a {@link QosSocketInfo} given a {@link Network} and bound {@link DatagramSocket}. The
+     * {@link DatagramSocket} must remain bound in order to receive {@link QosSession}s.
+     *
+     * @param network the network
+     * @param socket the bound {@link DatagramSocket}
+     * @hide
+     */
+    public QosSocketInfo(@NonNull final Network network, @NonNull final DatagramSocket socket)
+            throws IOException {
+        Objects.requireNonNull(socket, "socket cannot be null");
+
+        mNetwork = Objects.requireNonNull(network, "network cannot be null");
+        mParcelFileDescriptor = ParcelFileDescriptor.fromDatagramSocket(socket);
+        mLocalSocketAddress =
+                new InetSocketAddress(socket.getLocalAddress(), socket.getLocalPort());
+        mSocketType = SOCK_DGRAM;
 
         if (socket.isConnected()) {
             mRemoteSocketAddress = (InetSocketAddress) socket.getRemoteSocketAddress();
@@ -131,6 +173,8 @@
         final int remoteAddressLength = in.readInt();
         mRemoteSocketAddress = remoteAddressLength == 0 ? null
                 : readSocketAddress(in, remoteAddressLength);
+
+        mSocketType = in.readInt();
     }
 
     private @NonNull InetSocketAddress readSocketAddress(final Parcel in, final int addressLength) {
@@ -170,6 +214,7 @@
             dest.writeByteArray(remoteAddress);
             dest.writeInt(mRemoteSocketAddress.getPort());
         }
+        dest.writeInt(mSocketType);
     }
 
     @NonNull
diff --git a/nearby/framework/java/android/nearby/BroadcastRequest.java b/nearby/framework/java/android/nearby/BroadcastRequest.java
index 3273ea1..90f4d0f 100644
--- a/nearby/framework/java/android/nearby/BroadcastRequest.java
+++ b/nearby/framework/java/android/nearby/BroadcastRequest.java
@@ -78,15 +78,17 @@
     }
 
     /**
+     * Broadcast the request using the Bluetooth Low Energy (BLE) medium.
+     */
+    public static final int MEDIUM_BLE = 1;
+
+    /**
      * The medium where the broadcast request should be sent.
      *
      * @hide
      */
-    @IntDef({Medium.BLE, Medium.MDNS})
-    public @interface Medium {
-        int BLE = 1;
-        int MDNS = 2;
-    }
+    @IntDef({MEDIUM_BLE})
+    public @interface Medium {}
 
     /**
      * Creates a {@link BroadcastRequest} from parcel.
@@ -149,7 +151,8 @@
     }
 
     /**
-     * Returns the list of broadcast mediums.
+     * Returns the list of broadcast mediums. A medium represents the channel on which the broadcast
+     * request is sent.
      */
     @NonNull
     @Medium
diff --git a/nearby/framework/java/android/nearby/PresenceCredential.java b/nearby/framework/java/android/nearby/PresenceCredential.java
index 1e851d6..0a3cc1d 100644
--- a/nearby/framework/java/android/nearby/PresenceCredential.java
+++ b/nearby/framework/java/android/nearby/PresenceCredential.java
@@ -57,8 +57,6 @@
     public static final int IDENTITY_TYPE_PROVISIONED = 2;
     /** Trusted identity type. */
     public static final int IDENTITY_TYPE_TRUSTED = 3;
-    /** Public identity type. */
-    public static final int IDENTITY_TYPE_PUBLIC = 4;
 
     /**
      * @hide *
@@ -68,8 +66,7 @@
         IDENTITY_TYPE_UNKNOWN,
         IDENTITY_TYPE_PRIVATE,
         IDENTITY_TYPE_PROVISIONED,
-        IDENTITY_TYPE_TRUSTED,
-        IDENTITY_TYPE_PUBLIC
+        IDENTITY_TYPE_TRUSTED
     })
     public @interface IdentityType {}
 
diff --git a/nearby/service/Android.bp b/nearby/service/Android.bp
index 802e2c8..7112bb1 100644
--- a/nearby/service/Android.bp
+++ b/nearby/service/Android.bp
@@ -41,6 +41,39 @@
     sdk_version: "module_current",
 }
 
+// Common lib for nearby end-to-end testing.
+java_library {
+    name: "nearby-common-lib",
+    srcs: [
+        "java/com/android/server/nearby/common/bloomfilter/*.java",
+        "java/com/android/server/nearby/common/bluetooth/*.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/AesCtrMultipleBlockEncryption.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/AesEcbSingleBlockEncryption.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/BluetoothAddress.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/BluetoothUuids.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/Bytes.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/Constants.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/EllipticCurveDiffieHellmanExchange.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/HmacSha256.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/Ltv.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/MessageStreamHmacEncoder.java",
+        "java/com/android/server/nearby/common/bluetooth/fastpair/NamingEncoder.java",
+        "java/com/android/server/nearby/common/bluetooth/testability/**/*.java",
+        "java/com/android/server/nearby/common/bluetooth/gatt/*.java",
+        "java/com/android/server/nearby/common/bluetooth/util/*.java",
+    ],
+    libs: [
+        "androidx.annotation_annotation",
+        "androidx.core_core",
+        "error_prone_annotations",
+        "framework-bluetooth",
+        "guava",
+    ],
+    sdk_version: "module_current",
+    visibility: [
+        "//packages/modules/Connectivity/nearby/tests/multidevices/clients/test_support/fastpair_provider",
+    ],
+}
 
 // Main lib for nearby services.
 java_library {
diff --git a/nearby/service/java/com/android/server/nearby/fastpair/FastPairAdvHandler.java b/nearby/service/java/com/android/server/nearby/fastpair/FastPairAdvHandler.java
index 4de4cee..2ecce47 100644
--- a/nearby/service/java/com/android/server/nearby/fastpair/FastPairAdvHandler.java
+++ b/nearby/service/java/com/android/server/nearby/fastpair/FastPairAdvHandler.java
@@ -91,12 +91,13 @@
         if (mPairDataProvider == null) {
             return;
         }
-        List<Account> accountList = mPairDataProvider.loadFastPairEligibleAccounts();
+
         if (FastPairDecoder.checkModelId(fastPairDevice.getData())) {
             byte[] model = FastPairDecoder.getModelId(fastPairDevice.getData());
             Log.d(TAG, "On discovery model id " + Hex.bytesToStringLowercase(model));
             // Use api to get anti spoofing key from model id.
             try {
+                List<Account> accountList = mPairDataProvider.loadFastPairEligibleAccounts();
                 Rpcs.GetObservedDeviceResponse response =
                         mPairDataProvider.loadFastPairAntispoofKeyDeviceMetadata(model);
                 if (response == null) {
@@ -121,6 +122,7 @@
         } else {
             // Start to process bloom filter
             try {
+                List<Account> accountList = mPairDataProvider.loadFastPairEligibleAccounts();
                 byte[] bloomFilterByteArray = FastPairDecoder
                         .getBloomFilter(fastPairDevice.getData());
                 byte[] bloomFilterSalt = FastPairDecoder
diff --git a/nearby/service/java/com/android/server/nearby/fastpair/FastPairManager.java b/nearby/service/java/com/android/server/nearby/fastpair/FastPairManager.java
index 2d7cba9..f368080 100644
--- a/nearby/service/java/com/android/server/nearby/fastpair/FastPairManager.java
+++ b/nearby/service/java/com/android/server/nearby/fastpair/FastPairManager.java
@@ -418,11 +418,13 @@
             return;
         }
         if (mScanEnabled) {
+            Log.v(TAG, "invalidateScan: scan is enabled");
             nearbyManager.startScan(new ScanRequest.Builder()
                             .setScanType(ScanRequest.SCAN_TYPE_FAST_PAIR).build(),
                     ForegroundThread.getExecutor(),
                     mScanCallback);
         } else {
+            Log.v(TAG, "invalidateScan: scan is disabled");
             nearbyManager.stopScan(mScanCallback);
         }
     }
diff --git a/nearby/service/java/com/android/server/nearby/provider/BleDiscoveryProvider.java b/nearby/service/java/com/android/server/nearby/provider/BleDiscoveryProvider.java
index db58476..4cb6d8d 100644
--- a/nearby/service/java/com/android/server/nearby/provider/BleDiscoveryProvider.java
+++ b/nearby/service/java/com/android/server/nearby/provider/BleDiscoveryProvider.java
@@ -144,6 +144,7 @@
                     + "because BluetoothLeScanner is null.");
             return;
         }
+        Log.v(TAG, "Ble scan stopped.");
         bluetoothLeScanner.stopScan(mScanCallback);
     }
 
diff --git a/nearby/service/java/com/android/server/nearby/provider/DiscoveryProviderManager.java b/nearby/service/java/com/android/server/nearby/provider/DiscoveryProviderManager.java
index af1c0b5..9003499 100644
--- a/nearby/service/java/com/android/server/nearby/provider/DiscoveryProviderManager.java
+++ b/nearby/service/java/com/android/server/nearby/provider/DiscoveryProviderManager.java
@@ -152,8 +152,11 @@
 
             ScanListenerRecord removedRecord =
                     mScanTypeScanListenerRecordMap.remove(listenerBinder);
+            Log.v(TAG, "DiscoveryProviderManager unregistered scan listener.");
             NearbyMetrics.logScanStopped(removedRecord.hashCode(), removedRecord.getScanRequest());
             if (mScanTypeScanListenerRecordMap.isEmpty()) {
+                Log.v(TAG, "DiscoveryProviderManager stops provider because there is no "
+                        + "scan listener registered.");
                 stopProviders();
                 return;
             }
@@ -162,6 +165,8 @@
 
             // Removes current highest scan mode requested and sets the next highest scan mode.
             if (removedRecord.getScanRequest().getScanMode() == mScanMode) {
+                Log.v(TAG, "DiscoveryProviderManager starts to find the new highest scan mode "
+                        + "because the highest scan mode listener was unregistered.");
                 @ScanRequest.ScanMode int highestScanModeRequested = ScanRequest.SCAN_MODE_NO_POWER;
                 // find the next highest scan mode;
                 for (ScanListenerRecord record : mScanTypeScanListenerRecordMap.values()) {
diff --git a/nearby/tests/multidevices/clients/test_support/fastpair_provider/Android.bp b/nearby/tests/multidevices/clients/test_support/fastpair_provider/Android.bp
index e01c436..298c9dc 100644
--- a/nearby/tests/multidevices/clients/test_support/fastpair_provider/Android.bp
+++ b/nearby/tests/multidevices/clients/test_support/fastpair_provider/Android.bp
@@ -34,11 +34,13 @@
     ],
     static_libs: [
         "NearbyFastPairProviderLiteProtos",
+        "androidx.core_core",
         "androidx.test.core",
         "error_prone_annotations",
         "fast-pair-lite-protos",
         "framework-annotations-lib",
+        "guava",
         "kotlin-stdlib",
-        "service-nearby-pre-jarjar",
+        "nearby-common-lib",
     ],
 }
diff --git a/nearby/tests/multidevices/clients/test_support/fastpair_provider/simulator_app/Android.bp b/nearby/tests/multidevices/clients/test_support/fastpair_provider/simulator_app/Android.bp
index 87d352f..125c34e 100644
--- a/nearby/tests/multidevices/clients/test_support/fastpair_provider/simulator_app/Android.bp
+++ b/nearby/tests/multidevices/clients/test_support/fastpair_provider/simulator_app/Android.bp
@@ -25,6 +25,7 @@
 // adb remount
 // adb push ${ANDROID_PRODUCT_OUT}/system/app/NearbyFastPairProviderSimulatorApp /system/app/
 // adb reboot
+// Grant all permissions requested to NearbyFastPairProviderSimulatorApp before launching it.
 android_app {
     name: "NearbyFastPairProviderSimulatorApp",
     sdk_version: "test_current",
diff --git a/nearby/tests/multidevices/host/AndroidTest.xml b/nearby/tests/multidevices/host/AndroidTest.xml
index a5f6839..5926cc1 100644
--- a/nearby/tests/multidevices/host/AndroidTest.xml
+++ b/nearby/tests/multidevices/host/AndroidTest.xml
@@ -21,11 +21,13 @@
         <!-- For coverage to work, the APK should not be uninstalled until after coverage is pulled.
              So it's a lot easier to install APKs outside the python code.
         -->
-        <target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
-            <option name="test-file-name" value="NearbyMultiDevicesClientsSnippets.apk" />
-            <option name="test-file-name" value="NearbyFastPairSeekerDataProvider.apk" />
-            <option name="check-min-sdk" value="true" />
+        <target_preparer class="com.android.tradefed.targetprep.RootTargetPreparer" />
+        <target_preparer class="com.android.compatibility.common.tradefed.targetprep.FilePusher">
+            <option name="remount-system" value="true" />
+            <option name="push" value="NearbyMultiDevicesClientsSnippets.apk->/system/app/NearbyMultiDevicesClientsSnippets/NearbyMultiDevicesClientsSnippets.apk" />
+            <option name="push" value="NearbyFastPairSeekerDataProvider.apk->/system/app/NearbyFastPairSeekerDataProvider/NearbyFastPairSeekerDataProvider.apk" />
         </target_preparer>
+        <target_preparer class="com.android.tradefed.targetprep.RebootTargetPreparer" />
         <target_preparer class="com.android.tradefed.targetprep.RunCommandTargetPreparer">
             <option name="run-command" value="input keyevent KEYCODE_WAKEUP" />
             <option name="run-command" value="wm dismiss-keyguard" />
@@ -39,14 +41,47 @@
         <target_preparer class="com.android.tradefed.targetprep.DeviceSetup">
             <option name="force-skip-system-props" value="true" /> <!-- avoid restarting device -->
             <option name="screen-always-on" value="on" />
+            <!-- List permissions requested by the APK: aapt d permissions <PATH_TO_YOUR_APK> -->
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_ADMIN" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_ADVERTISE" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_CONNECT" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_PRIVILEGED" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_SCAN" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.INTERNET" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.GET_ACCOUNTS" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.WRITE_SECURE_SETTINGS" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.REORDER_TASKS" />
         </target_preparer>
     </device>
     <device name="device2">
-        <target_preparer class="com.android.tradefed.targetprep.suite.SuiteApkInstaller">
-            <option name="test-file-name" value="NearbyMultiDevicesClientsSnippets.apk" />
-            <option name="test-file-name" value="NearbyFastPairSeekerDataProvider.apk" />
-            <option name="check-min-sdk" value="true" />
+        <target_preparer class="com.android.tradefed.targetprep.RootTargetPreparer" />
+        <target_preparer class="com.android.compatibility.common.tradefed.targetprep.FilePusher">
+            <option name="remount-system" value="true" />
+            <option name="push" value="NearbyMultiDevicesClientsSnippets.apk->/system/app/NearbyMultiDevicesClientsSnippets/NearbyMultiDevicesClientsSnippets.apk" />
+            <option name="push" value="NearbyFastPairSeekerDataProvider.apk->/system/app/NearbyFastPairSeekerDataProvider/NearbyFastPairSeekerDataProvider.apk" />
         </target_preparer>
+        <target_preparer class="com.android.tradefed.targetprep.RebootTargetPreparer" />
         <target_preparer class="com.android.tradefed.targetprep.RunCommandTargetPreparer">
             <option name="run-command" value="input keyevent KEYCODE_WAKEUP" />
             <option name="run-command" value="wm dismiss-keyguard" />
@@ -54,6 +89,37 @@
         <target_preparer class="com.android.tradefed.targetprep.DeviceSetup">
             <option name="force-skip-system-props" value="true" /> <!-- avoid restarting device -->
             <option name="screen-always-on" value="on" />
+            <!-- List permissions requested by the APK: aapt d permissions <PATH_TO_YOUR_APK> -->
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_ADMIN" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_ADVERTISE" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_CONNECT" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_PRIVILEGED" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.BLUETOOTH_SCAN" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.INTERNET" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.GET_ACCOUNTS" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.WRITE_SECURE_SETTINGS" />
+            <option
+                name="run-command"
+                value="pm grant android.nearby.multidevices android.permission.REORDER_TASKS" />
         </target_preparer>
     </device>
 
diff --git a/service/src/com/android/server/connectivity/CarrierPrivilegeAuthenticator.java b/service/src/com/android/server/connectivity/CarrierPrivilegeAuthenticator.java
index b761762..ce955fd 100644
--- a/service/src/com/android/server/connectivity/CarrierPrivilegeAuthenticator.java
+++ b/service/src/com/android/server/connectivity/CarrierPrivilegeAuthenticator.java
@@ -19,8 +19,6 @@
 import static android.net.NetworkCapabilities.NET_CAPABILITY_CBS;
 import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR;
 
-import static com.android.networkstack.apishim.ConstantsShim.RECEIVER_NOT_EXPORTED;
-
 import android.annotation.NonNull;
 import android.content.BroadcastReceiver;
 import android.content.Context;
@@ -160,7 +158,7 @@
     private void registerForCarrierChanges() {
         final IntentFilter filter = new IntentFilter();
         filter.addAction(TelephonyManager.ACTION_MULTI_SIM_CONFIG_CHANGED);
-        mContext.registerReceiver(this, filter, null, mHandler, RECEIVER_NOT_EXPORTED /* flags */);
+        mContext.registerReceiver(this, filter, null, mHandler);
         registerCarrierPrivilegesListeners();
     }
 
diff --git a/tests/unit/java/com/android/server/connectivity/CarrierPrivilegeAuthenticatorTest.java b/tests/unit/java/com/android/server/connectivity/CarrierPrivilegeAuthenticatorTest.java
index 553cb83..157507b 100644
--- a/tests/unit/java/com/android/server/connectivity/CarrierPrivilegeAuthenticatorTest.java
+++ b/tests/unit/java/com/android/server/connectivity/CarrierPrivilegeAuthenticatorTest.java
@@ -69,8 +69,6 @@
 @RunWith(DevSdkIgnoreRunner.class)
 @IgnoreUpTo(SC_V2) // TODO: Use to Build.VERSION_CODES.SC_V2 when available
 public class CarrierPrivilegeAuthenticatorTest {
-    // TODO : use ConstantsShim.RECEIVER_NOT_EXPORTED when it's available in tests.
-    private static final int RECEIVER_NOT_EXPORTED = 4;
     private static final int SUBSCRIPTION_COUNT = 2;
     private static final int TEST_SUBSCRIPTION_ID = 1;
 
@@ -117,7 +115,7 @@
 
     private IntentFilter getIntentFilter() {
         final ArgumentCaptor<IntentFilter> captor = ArgumentCaptor.forClass(IntentFilter.class);
-        verify(mContext).registerReceiver(any(), captor.capture(), any(), any(), anyInt());
+        verify(mContext).registerReceiver(any(), captor.capture(), any(), any());
         return captor.getValue();
     }
 
@@ -140,11 +138,10 @@
     @Test
     public void testConstructor() throws Exception {
         verify(mContext).registerReceiver(
-                eq(mCarrierPrivilegeAuthenticator),
-                any(IntentFilter.class),
-                any(),
-                any(),
-                eq(RECEIVER_NOT_EXPORTED));
+                        eq(mCarrierPrivilegeAuthenticator),
+                        any(IntentFilter.class),
+                        any(),
+                        any());
         final IntentFilter filter = getIntentFilter();
         assertEquals(1, filter.countActions());
         assertTrue(filter.hasAction(ACTION_MULTI_SIM_CONFIG_CHANGED));