• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.net.cts;
18 
19 import static android.net.NetworkCapabilities.NET_CAPABILITY_DUN;
20 import static android.net.NetworkCapabilities.NET_CAPABILITY_FOTA;
21 import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
22 import static android.net.NetworkCapabilities.NET_CAPABILITY_MMS;
23 import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING;
24 import static android.net.NetworkCapabilities.NET_CAPABILITY_SUPL;
25 import static android.net.NetworkCapabilities.NET_CAPABILITY_TEMPORARILY_NOT_METERED;
26 import static android.net.NetworkCapabilities.TRANSPORT_BLUETOOTH;
27 import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR;
28 import static android.net.NetworkCapabilities.TRANSPORT_VPN;
29 import static android.net.NetworkCapabilities.TRANSPORT_WIFI;
30 
31 import static junit.framework.Assert.fail;
32 
33 import static org.junit.Assert.assertArrayEquals;
34 import static org.junit.Assert.assertEquals;
35 import static org.junit.Assert.assertFalse;
36 import static org.junit.Assert.assertNotEquals;
37 import static org.junit.Assert.assertNull;
38 import static org.junit.Assert.assertTrue;
39 import static org.junit.Assume.assumeTrue;
40 
41 import android.annotation.NonNull;
42 import android.net.MacAddress;
43 import android.net.MatchAllNetworkSpecifier;
44 import android.net.NetworkCapabilities;
45 import android.net.NetworkRequest;
46 import android.net.NetworkSpecifier;
47 import android.net.wifi.WifiNetworkSpecifier;
48 import android.os.Build;
49 import android.os.PatternMatcher;
50 import android.os.Process;
51 import android.util.ArraySet;
52 import android.util.Range;
53 
54 import androidx.test.runner.AndroidJUnit4;
55 
56 import com.android.modules.utils.build.SdkLevel;
57 import com.android.networkstack.apishim.ConstantsShim;
58 import com.android.networkstack.apishim.NetworkRequestShimImpl;
59 import com.android.networkstack.apishim.common.NetworkRequestShim;
60 import com.android.networkstack.apishim.common.UnsupportedApiLevelException;
61 import com.android.testutils.DevSdkIgnoreRule;
62 import com.android.testutils.DevSdkIgnoreRule.IgnoreUpTo;
63 
64 import org.junit.Rule;
65 import org.junit.Test;
66 import org.junit.runner.RunWith;
67 
68 import java.util.Set;
69 
70 @RunWith(AndroidJUnit4.class)
71 public class NetworkRequestTest {
72     @Rule
73     public final DevSdkIgnoreRule ignoreRule = new DevSdkIgnoreRule();
74 
75     private static final String TEST_SSID = "TestSSID";
76     private static final String OTHER_SSID = "OtherSSID";
77     private static final int TEST_UID = 2097;
78     private static final String TEST_PACKAGE_NAME = "test.package.name";
79     private static final MacAddress ARBITRARY_ADDRESS = MacAddress.fromString("3:5:8:12:9:2");
80 
81     private class LocalNetworkSpecifier extends NetworkSpecifier {
82         private final int mId;
83 
LocalNetworkSpecifier(int id)84         LocalNetworkSpecifier(int id) {
85             mId = id;
86         }
87 
88         @Override
canBeSatisfiedBy(NetworkSpecifier other)89         public boolean canBeSatisfiedBy(NetworkSpecifier other) {
90             return other instanceof LocalNetworkSpecifier
91                 && mId == ((LocalNetworkSpecifier) other).mId;
92         }
93     }
94 
95     @Test
testCapabilities()96     public void testCapabilities() {
97         assertTrue(new NetworkRequest.Builder().addCapability(NET_CAPABILITY_MMS).build()
98                 .hasCapability(NET_CAPABILITY_MMS));
99         assertFalse(new NetworkRequest.Builder().removeCapability(NET_CAPABILITY_MMS).build()
100                 .hasCapability(NET_CAPABILITY_MMS));
101 
102         final NetworkRequest nr = new NetworkRequest.Builder().clearCapabilities().build();
103         // Verify request has no capabilities
104         verifyNoCapabilities(nr);
105     }
106 
107     @Test @IgnoreUpTo(Build.VERSION_CODES.Q)
testTemporarilyNotMeteredCapability()108     public void testTemporarilyNotMeteredCapability() {
109         assertTrue(new NetworkRequest.Builder()
110                 .addCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED).build()
111                 .hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED));
112         assertFalse(new NetworkRequest.Builder()
113                 .removeCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED).build()
114                 .hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED));
115     }
116 
verifyNoCapabilities(NetworkRequest nr)117     private void verifyNoCapabilities(NetworkRequest nr) {
118         // NetworkCapabilities.mNetworkCapabilities is defined as type long
119         final int MAX_POSSIBLE_CAPABILITY = Long.SIZE;
120         for(int bit = 0; bit < MAX_POSSIBLE_CAPABILITY; bit++) {
121             assertFalse(nr.hasCapability(bit));
122         }
123     }
124 
125     @Test
testTransports()126     public void testTransports() {
127         assertTrue(new NetworkRequest.Builder().addTransportType(TRANSPORT_BLUETOOTH).build()
128                 .hasTransport(TRANSPORT_BLUETOOTH));
129         assertFalse(new NetworkRequest.Builder().removeTransportType(TRANSPORT_BLUETOOTH).build()
130                 .hasTransport(TRANSPORT_BLUETOOTH));
131     }
132 
133     @Test
134     @IgnoreUpTo(Build.VERSION_CODES.Q)
testSpecifier()135     public void testSpecifier() {
136         assertNull(new NetworkRequest.Builder().build().getNetworkSpecifier());
137         final WifiNetworkSpecifier specifier = new WifiNetworkSpecifier.Builder()
138                 .setSsidPattern(new PatternMatcher(TEST_SSID, PatternMatcher.PATTERN_LITERAL))
139                 .setBssidPattern(ARBITRARY_ADDRESS, ARBITRARY_ADDRESS)
140                 .build();
141         final NetworkSpecifier obtainedSpecifier = new NetworkRequest.Builder()
142                 .addTransportType(TRANSPORT_WIFI)
143                 .setNetworkSpecifier(specifier)
144                 .build()
145                 .getNetworkSpecifier();
146         assertEquals(obtainedSpecifier, specifier);
147 
148         assertNull(new NetworkRequest.Builder()
149                 .clearCapabilities()
150                 .build()
151                 .getNetworkSpecifier());
152     }
153 
154     @Test
155     @IgnoreUpTo(Build.VERSION_CODES.Q)
testRequestorPackageName()156     public void testRequestorPackageName() {
157         assertNull(new NetworkRequest.Builder().build().getRequestorPackageName());
158         final String pkgName = "android.net.test";
159         final NetworkCapabilities nc = new NetworkCapabilities.Builder()
160                 .setRequestorPackageName(pkgName)
161                 .build();
162         final NetworkRequest nr = new NetworkRequest.Builder()
163                 .setCapabilities(nc)
164                 .build();
165         assertEquals(pkgName, nr.getRequestorPackageName());
166         assertNull(new NetworkRequest.Builder()
167                 .clearCapabilities()
168                 .build()
169                 .getRequestorPackageName());
170     }
171 
addNotVcnManagedCapability(@onNull NetworkCapabilities nc)172     private void addNotVcnManagedCapability(@NonNull NetworkCapabilities nc) {
173         if (SdkLevel.isAtLeastS()) {
174             nc.addCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED);
175         }
176     }
177 
178     @Test
179     @IgnoreUpTo(Build.VERSION_CODES.Q)
testCanBeSatisfiedBy()180     public void testCanBeSatisfiedBy() {
181         final LocalNetworkSpecifier specifier1 = new LocalNetworkSpecifier(1234 /* id */);
182         final LocalNetworkSpecifier specifier2 = new LocalNetworkSpecifier(5678 /* id */);
183 
184         // Some requests are adding NOT_VCN_MANAGED capability automatically. Add it to the
185         // capabilities below for bypassing the check.
186         final NetworkCapabilities capCellularMmsInternet = new NetworkCapabilities()
187                 .addTransportType(TRANSPORT_CELLULAR)
188                 .addCapability(NET_CAPABILITY_MMS)
189                 .addCapability(NET_CAPABILITY_INTERNET);
190         addNotVcnManagedCapability(capCellularMmsInternet);
191         final NetworkCapabilities capCellularVpnMmsInternet =
192                 new NetworkCapabilities(capCellularMmsInternet).addTransportType(TRANSPORT_VPN);
193         addNotVcnManagedCapability(capCellularVpnMmsInternet);
194         final NetworkCapabilities capCellularMmsInternetSpecifier1 =
195                 new NetworkCapabilities(capCellularMmsInternet).setNetworkSpecifier(specifier1);
196         addNotVcnManagedCapability(capCellularMmsInternetSpecifier1);
197         final NetworkCapabilities capVpnInternetSpecifier1 = new NetworkCapabilities()
198                 .addCapability(NET_CAPABILITY_INTERNET)
199                 .addTransportType(TRANSPORT_VPN)
200                 .setNetworkSpecifier(specifier1);
201         addNotVcnManagedCapability(capVpnInternetSpecifier1);
202         final NetworkCapabilities capCellularMmsInternetMatchallspecifier =
203                 new NetworkCapabilities(capCellularMmsInternet)
204                         .setNetworkSpecifier(new MatchAllNetworkSpecifier());
205         addNotVcnManagedCapability(capCellularMmsInternetMatchallspecifier);
206         final NetworkCapabilities capCellularMmsInternetSpecifier2 =
207                 new NetworkCapabilities(capCellularMmsInternet)
208                         .setNetworkSpecifier(specifier2);
209         addNotVcnManagedCapability(capCellularMmsInternetSpecifier2);
210 
211         final NetworkRequest requestCellularInternetSpecifier1 = new NetworkRequest.Builder()
212                 .addTransportType(TRANSPORT_CELLULAR)
213                 .addCapability(NET_CAPABILITY_INTERNET)
214                 .setNetworkSpecifier(specifier1)
215                 .build();
216         assertFalse(requestCellularInternetSpecifier1.canBeSatisfiedBy(null));
217         assertFalse(requestCellularInternetSpecifier1.canBeSatisfiedBy(new NetworkCapabilities()));
218         assertTrue(requestCellularInternetSpecifier1.canBeSatisfiedBy(
219                 capCellularMmsInternetMatchallspecifier));
220         assertFalse(requestCellularInternetSpecifier1.canBeSatisfiedBy(capCellularMmsInternet));
221         assertTrue(requestCellularInternetSpecifier1.canBeSatisfiedBy(
222                 capCellularMmsInternetSpecifier1));
223         assertFalse(requestCellularInternetSpecifier1.canBeSatisfiedBy(capCellularVpnMmsInternet));
224         assertFalse(requestCellularInternetSpecifier1.canBeSatisfiedBy(
225                 capCellularMmsInternetSpecifier2));
226 
227         final NetworkRequest requestCellularInternet = new NetworkRequest.Builder()
228                 .addTransportType(TRANSPORT_CELLULAR)
229                 .addCapability(NET_CAPABILITY_INTERNET)
230                 .build();
231         assertTrue(requestCellularInternet.canBeSatisfiedBy(capCellularMmsInternet));
232         assertTrue(requestCellularInternet.canBeSatisfiedBy(capCellularMmsInternetSpecifier1));
233         assertTrue(requestCellularInternet.canBeSatisfiedBy(capCellularMmsInternetSpecifier2));
234         assertFalse(requestCellularInternet.canBeSatisfiedBy(capVpnInternetSpecifier1));
235         assertTrue(requestCellularInternet.canBeSatisfiedBy(capCellularVpnMmsInternet));
236     }
237 
setUids(NetworkRequest.Builder builder, Set<Range<Integer>> ranges)238     private void setUids(NetworkRequest.Builder builder, Set<Range<Integer>> ranges)
239             throws UnsupportedApiLevelException {
240         if (SdkLevel.isAtLeastS()) {
241             final NetworkRequestShim networkRequestShim = NetworkRequestShimImpl.newInstance();
242             networkRequestShim.setUids(builder, ranges);
243         }
244     }
245 
246     @Test
247     @IgnoreUpTo(Build.VERSION_CODES.Q)
testInvariantInCanBeSatisfiedBy()248     public void testInvariantInCanBeSatisfiedBy() {
249         // Test invariant that result of NetworkRequest.canBeSatisfiedBy() should be the same with
250         // NetworkCapabilities.satisfiedByNetworkCapabilities().
251         final LocalNetworkSpecifier specifier1 = new LocalNetworkSpecifier(1234 /* id */);
252         final int uid = Process.myUid();
253         final NetworkRequest.Builder nrBuilder = new NetworkRequest.Builder()
254                 .addTransportType(TRANSPORT_CELLULAR)
255                 .addCapability(NET_CAPABILITY_INTERNET)
256                 .setLinkUpstreamBandwidthKbps(1000)
257                 .setNetworkSpecifier(specifier1)
258                 .setSignalStrength(-123);
259 
260         // The uid ranges should be set into the request, but setUids() takes a set of UidRange
261         // that is hidden and inaccessible from shims. Before, S setUids will be a no-op. But
262         // because NetworkRequest.Builder sets the UID of the request to the current UID, the
263         // request contains the current UID both on S and before S.
264         final Set<Range<Integer>> ranges = new ArraySet<>();
265         ranges.add(new Range<Integer>(uid, uid));
266         try {
267             setUids(nrBuilder, ranges);
268         } catch (UnsupportedApiLevelException e) {
269             // Not supported before API31.
270         }
271         final NetworkRequest requestCombination = nrBuilder.build();
272 
273         final NetworkCapabilities capCell = new NetworkCapabilities.Builder()
274                 .addTransportType(TRANSPORT_CELLULAR).build();
275         assertCorrectlySatisfies(false, requestCombination, capCell);
276 
277         final NetworkCapabilities capCellInternet = new NetworkCapabilities.Builder(capCell)
278                 .addCapability(NET_CAPABILITY_INTERNET).build();
279         assertCorrectlySatisfies(false, requestCombination, capCellInternet);
280 
281         final NetworkCapabilities capCellInternetBW =
282                 new NetworkCapabilities.Builder(capCellInternet)
283                     .setLinkUpstreamBandwidthKbps(1024).build();
284         assertCorrectlySatisfies(false, requestCombination, capCellInternetBW);
285 
286         final NetworkCapabilities capCellInternetBWSpecifier1 =
287                 new NetworkCapabilities.Builder(capCellInternetBW)
288                     .setNetworkSpecifier(specifier1).build();
289         assertCorrectlySatisfies(false, requestCombination, capCellInternetBWSpecifier1);
290 
291         final NetworkCapabilities capCellInternetBWSpecifier1Signal =
292                 new NetworkCapabilities.Builder(capCellInternetBWSpecifier1)
293                         .setSignalStrength(-123).build();
294         addNotVcnManagedCapability(capCellInternetBWSpecifier1Signal);
295         assertCorrectlySatisfies(true, requestCombination,
296                 capCellInternetBWSpecifier1Signal);
297 
298         final NetworkCapabilities capCellInternetBWSpecifier1SignalUid =
299                 new NetworkCapabilities.Builder(capCellInternetBWSpecifier1Signal)
300                     .setOwnerUid(uid)
301                     .setAdministratorUids(new int [] {uid}).build();
302         assertCorrectlySatisfies(true, requestCombination,
303                 capCellInternetBWSpecifier1SignalUid);
304     }
305 
assertCorrectlySatisfies(boolean expect, NetworkRequest request, NetworkCapabilities nc)306     private void assertCorrectlySatisfies(boolean expect, NetworkRequest request,
307             NetworkCapabilities nc) {
308         assertEquals(expect, request.canBeSatisfiedBy(nc));
309         assertEquals(
310                 request.canBeSatisfiedBy(nc),
311                 request.networkCapabilities.satisfiedByNetworkCapabilities(nc));
312     }
313 
uidRangesForUid(int uid)314     private static Set<Range<Integer>> uidRangesForUid(int uid) {
315         final Range<Integer> range = new Range<>(uid, uid);
316         return Set.of(range);
317     }
318 
319     @Test
testSetIncludeOtherUidNetworks()320     public void testSetIncludeOtherUidNetworks() throws Exception {
321         assumeTrue(TestUtils.shouldTestSApis());
322         final NetworkRequestShim shim = NetworkRequestShimImpl.newInstance();
323 
324         final NetworkRequest.Builder builder = new NetworkRequest.Builder();
325         // NetworkRequests have NET_CAPABILITY_NOT_VCN_MANAGED by default.
326         builder.removeCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED);
327         shim.setIncludeOtherUidNetworks(builder, false);
328         final NetworkRequest request = builder.build();
329 
330         final NetworkRequest.Builder otherUidsBuilder = new NetworkRequest.Builder();
331         otherUidsBuilder.removeCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED);
332         shim.setIncludeOtherUidNetworks(otherUidsBuilder, true);
333         final NetworkRequest otherUidsRequest = otherUidsBuilder.build();
334 
335         assertNotEquals(Process.SYSTEM_UID, Process.myUid());
336         final NetworkCapabilities ncWithMyUid = new NetworkCapabilities()
337                 .setUids(uidRangesForUid(Process.myUid()));
338         final NetworkCapabilities ncWithOtherUid = new NetworkCapabilities()
339                 .setUids(uidRangesForUid(Process.SYSTEM_UID));
340 
341         assertTrue(request + " should be satisfied by " + ncWithMyUid,
342                 request.canBeSatisfiedBy(ncWithMyUid));
343         assertTrue(otherUidsRequest + " should be satisfied by " + ncWithMyUid,
344                 otherUidsRequest.canBeSatisfiedBy(ncWithMyUid));
345         assertFalse(request + " should not be satisfied by " +  ncWithOtherUid,
346                 request.canBeSatisfiedBy(ncWithOtherUid));
347         assertTrue(otherUidsRequest + " should be satisfied by " + ncWithOtherUid,
348                 otherUidsRequest.canBeSatisfiedBy(ncWithOtherUid));
349     }
350 
351     @Test @IgnoreUpTo(Build.VERSION_CODES.Q)
testRequestorUid()352     public void testRequestorUid() {
353         final NetworkCapabilities nc = new NetworkCapabilities();
354         // Verify default value is INVALID_UID
355         assertEquals(Process.INVALID_UID, new NetworkRequest.Builder()
356                  .setCapabilities(nc).build().getRequestorUid());
357 
358         nc.setRequestorUid(1314);
359         final NetworkRequest nr = new NetworkRequest.Builder().setCapabilities(nc).build();
360         assertEquals(1314, nr.getRequestorUid());
361 
362         assertEquals(Process.INVALID_UID, new NetworkRequest.Builder()
363                 .clearCapabilities().build().getRequestorUid());
364     }
365 
366     // TODO: 1. Refactor test cases with helper method.
367     //       2. Test capability that does not yet exist.
368     @Test @IgnoreUpTo(Build.VERSION_CODES.R)
testBypassingVcn()369     public void testBypassingVcn() {
370         // Make an empty request. Verify the NOT_VCN_MANAGED is added.
371         final NetworkRequest emptyRequest = new NetworkRequest.Builder().build();
372         assertTrue(emptyRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
373 
374         // Make a request explicitly add NOT_VCN_MANAGED. Verify the NOT_VCN_MANAGED is preserved.
375         final NetworkRequest mmsAddNotVcnRequest = new NetworkRequest.Builder()
376                 .addCapability(NET_CAPABILITY_MMS)
377                 .addCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED)
378                 .build();
379         assertTrue(mmsAddNotVcnRequest.hasCapability(
380                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
381 
382         // Similar to above, but the opposite order.
383         final NetworkRequest mmsAddNotVcnRequest2 = new NetworkRequest.Builder()
384                 .addCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED)
385                 .addCapability(NET_CAPABILITY_MMS)
386                 .build();
387         assertTrue(mmsAddNotVcnRequest2.hasCapability(
388                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
389 
390         // Make a request explicitly remove NOT_VCN_MANAGED. Verify the NOT_VCN_MANAGED is removed.
391         final NetworkRequest removeNotVcnRequest = new NetworkRequest.Builder()
392                 .removeCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED).build();
393         assertFalse(removeNotVcnRequest.hasCapability(
394                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
395 
396         // Make a request add some capability inside VCN supported capabilities.
397         // Verify the NOT_VCN_MANAGED is added.
398         final NetworkRequest notRoamRequest = new NetworkRequest.Builder()
399                 .addCapability(NET_CAPABILITY_NOT_ROAMING).build();
400         assertTrue(notRoamRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
401 
402         // Make an internet request. Verify the NOT_VCN_MANAGED is added.
403         final NetworkRequest internetRequest = new NetworkRequest.Builder()
404                 .addCapability(NET_CAPABILITY_INTERNET).build();
405         assertTrue(internetRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
406 
407         // Make an internet request which explicitly removed NOT_VCN_MANAGED.
408         // Verify the NOT_VCN_MANAGED is removed.
409         final NetworkRequest internetRemoveNotVcnRequest = new NetworkRequest.Builder()
410                 .addCapability(NET_CAPABILITY_INTERNET)
411                 .removeCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED).build();
412         assertFalse(internetRemoveNotVcnRequest.hasCapability(
413                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
414 
415         // Make a normal MMS request. Verify the request could bypass VCN.
416         final NetworkRequest mmsRequest =
417                 new NetworkRequest.Builder().addCapability(NET_CAPABILITY_MMS).build();
418         assertFalse(mmsRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
419 
420         // Make a SUPL request along with internet. Verify NOT_VCN_MANAGED is not added since
421         // SUPL is not in the supported list.
422         final NetworkRequest suplWithInternetRequest = new NetworkRequest.Builder()
423                         .addCapability(NET_CAPABILITY_SUPL)
424                         .addCapability(NET_CAPABILITY_INTERNET).build();
425         assertFalse(suplWithInternetRequest.hasCapability(
426                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
427 
428         // Make a FOTA request with explicitly add NOT_VCN_MANAGED capability. Verify
429         // NOT_VCN_MANAGED is preserved.
430         final NetworkRequest fotaRequest = new NetworkRequest.Builder()
431                         .addCapability(NET_CAPABILITY_FOTA)
432                         .addCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED).build();
433         assertTrue(fotaRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
434 
435         // Make a DUN request, which is in {@code VCN_SUPPORTED_CAPABILITIES}.
436         // Verify NOT_VCN_MANAGED is preserved.
437         final NetworkRequest dunRequest = new NetworkRequest.Builder()
438                 .addCapability(NET_CAPABILITY_DUN).build();
439         assertTrue(dunRequest.hasCapability(ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
440 
441         // Make an internet request but with NetworkSpecifier. Verify the NOT_VCN_MANAGED is not
442         // added.
443         final NetworkRequest internetWithSpecifierRequest = new NetworkRequest.Builder()
444                 .addTransportType(TRANSPORT_WIFI).addCapability(NET_CAPABILITY_INTERNET)
445                 .setNetworkSpecifier(makeTestWifiSpecifier()).build();
446         assertFalse(internetWithSpecifierRequest.hasCapability(
447                 ConstantsShim.NET_CAPABILITY_NOT_VCN_MANAGED));
448     }
449 
verifyEqualRequestBuilt(NetworkRequest orig)450     private void verifyEqualRequestBuilt(NetworkRequest orig) {
451         try {
452             final NetworkRequestShim shim = NetworkRequestShimImpl.newInstance();
453             final NetworkRequest copy = shim.newBuilder(orig).build();
454             assertEquals(orig, copy);
455         } catch (UnsupportedApiLevelException e) {
456             fail("NetworkRequestShim.newBuilder should be supported in this SDK version");
457         }
458     }
459 
460     @Test @IgnoreUpTo(Build.VERSION_CODES.R)
testGetCapabilities()461     public void testGetCapabilities() {
462         final int[] netCapabilities = new int[] {
463                 NET_CAPABILITY_INTERNET,
464                 NET_CAPABILITY_NOT_ROAMING };
465         final NetworkCapabilities.Builder builder = NetworkCapabilities.Builder
466                 .withoutDefaultCapabilities();
467         for (int capability : netCapabilities) builder.addCapability(capability);
468         final NetworkRequest nr = new NetworkRequest.Builder()
469                 .clearCapabilities()
470                 .setCapabilities(builder.build())
471                 .build();
472         assertArrayEquals(netCapabilities, nr.getCapabilities());
473     }
474 
475     @Test
testBuildRequestFromExistingRequestWithBuilder()476     public void testBuildRequestFromExistingRequestWithBuilder() {
477         assumeTrue(TestUtils.shouldTestSApis());
478         final NetworkRequest.Builder builder = new NetworkRequest.Builder();
479 
480         final NetworkRequest baseRequest = builder.build();
481         verifyEqualRequestBuilt(baseRequest);
482 
483         final NetworkRequest requestCellMms = builder
484                 .addTransportType(TRANSPORT_CELLULAR)
485                 .addCapability(NET_CAPABILITY_MMS)
486                 .setSignalStrength(-99).build();
487         verifyEqualRequestBuilt(requestCellMms);
488 
489         final NetworkRequest requestWifi = builder
490                 .addTransportType(TRANSPORT_WIFI)
491                 .removeTransportType(TRANSPORT_CELLULAR)
492                 .addCapability(NET_CAPABILITY_INTERNET)
493                 .removeCapability(NET_CAPABILITY_MMS)
494                 .setNetworkSpecifier(makeTestWifiSpecifier())
495                 .setSignalStrength(-33).build();
496         verifyEqualRequestBuilt(requestWifi);
497     }
498 
makeTestWifiSpecifier()499     private WifiNetworkSpecifier makeTestWifiSpecifier() {
500         return new WifiNetworkSpecifier.Builder()
501                 .setSsidPattern(new PatternMatcher(TEST_SSID, PatternMatcher.PATTERN_LITERAL))
502                 .setBssidPattern(ARBITRARY_ADDRESS, ARBITRARY_ADDRESS)
503                 .build();
504     }
505 }
506