1 /* 2 * Copyright (C) 2011 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; 18 19 import static android.system.OsConstants.AF_INET; 20 import static android.system.OsConstants.AF_INET6; 21 22 import android.annotation.NonNull; 23 import android.annotation.Nullable; 24 import android.annotation.RequiresPermission; 25 import android.annotation.SystemApi; 26 import android.app.Activity; 27 import android.app.PendingIntent; 28 import android.app.Service; 29 import android.app.admin.DevicePolicyManager; 30 import android.compat.annotation.UnsupportedAppUsage; 31 import android.content.ComponentName; 32 import android.content.Context; 33 import android.content.Intent; 34 import android.content.pm.IPackageManager; 35 import android.content.pm.PackageManager; 36 import android.os.Binder; 37 import android.os.IBinder; 38 import android.os.Parcel; 39 import android.os.ParcelFileDescriptor; 40 import android.os.RemoteException; 41 import android.os.ServiceManager; 42 import android.os.UserHandle; 43 44 import com.android.internal.net.NetworkUtilsInternal; 45 import com.android.internal.net.VpnConfig; 46 47 import java.net.DatagramSocket; 48 import java.net.Inet4Address; 49 import java.net.Inet6Address; 50 import java.net.InetAddress; 51 import java.net.Socket; 52 import java.util.ArrayList; 53 import java.util.List; 54 import java.util.Set; 55 56 /** 57 * VpnService is a base class for applications to extend and build their 58 * own VPN solutions. In general, it creates a virtual network interface, 59 * configures addresses and routing rules, and returns a file descriptor 60 * to the application. Each read from the descriptor retrieves an outgoing 61 * packet which was routed to the interface. Each write to the descriptor 62 * injects an incoming packet just like it was received from the interface. 63 * The interface is running on Internet Protocol (IP), so packets are 64 * always started with IP headers. The application then completes a VPN 65 * connection by processing and exchanging packets with the remote server 66 * over a tunnel. 67 * 68 * <p>Letting applications intercept packets raises huge security concerns. 69 * A VPN application can easily break the network. Besides, two of them may 70 * conflict with each other. The system takes several actions to address 71 * these issues. Here are some key points: 72 * <ul> 73 * <li>User action is required the first time an application creates a VPN 74 * connection.</li> 75 * <li>There can be only one VPN connection running at the same time. The 76 * existing interface is deactivated when a new one is created.</li> 77 * <li>A system-managed notification is shown during the lifetime of a 78 * VPN connection.</li> 79 * <li>A system-managed dialog gives the information of the current VPN 80 * connection. It also provides a button to disconnect.</li> 81 * <li>The network is restored automatically when the file descriptor is 82 * closed. It also covers the cases when a VPN application is crashed 83 * or killed by the system.</li> 84 * </ul> 85 * 86 * <p>There are two primary methods in this class: {@link #prepare} and 87 * {@link Builder#establish}. The former deals with user action and stops 88 * the VPN connection created by another application. The latter creates 89 * a VPN interface using the parameters supplied to the {@link Builder}. 90 * An application must call {@link #prepare} to grant the right to use 91 * other methods in this class, and the right can be revoked at any time. 92 * Here are the general steps to create a VPN connection: 93 * <ol> 94 * <li>When the user presses the button to connect, call {@link #prepare} 95 * and launch the returned intent, if non-null.</li> 96 * <li>When the application becomes prepared, start the service.</li> 97 * <li>Create a tunnel to the remote server and negotiate the network 98 * parameters for the VPN connection.</li> 99 * <li>Supply those parameters to a {@link Builder} and create a VPN 100 * interface by calling {@link Builder#establish}.</li> 101 * <li>Process and exchange packets between the tunnel and the returned 102 * file descriptor.</li> 103 * <li>When {@link #onRevoke} is invoked, close the file descriptor and 104 * shut down the tunnel gracefully.</li> 105 * </ol> 106 * 107 * <p>Services extending this class need to be declared with an appropriate 108 * permission and intent filter. Their access must be secured by 109 * {@link android.Manifest.permission#BIND_VPN_SERVICE} permission, and 110 * their intent filter must match {@link #SERVICE_INTERFACE} action. Here 111 * is an example of declaring a VPN service in {@code AndroidManifest.xml}: 112 * <pre> 113 * <service android:name=".ExampleVpnService" 114 * android:permission="android.permission.BIND_VPN_SERVICE"> 115 * <intent-filter> 116 * <action android:name="android.net.VpnService"/> 117 * </intent-filter> 118 * </service></pre> 119 * 120 * <p> The Android system starts a VPN in the background by calling 121 * {@link android.content.Context#startService startService()}. In Android 8.0 122 * (API level 26) and higher, the system places VPN apps on the temporary 123 * allowlist for a short period so the app can start in the background. The VPN 124 * app must promote itself to the foreground after it's launched or the system 125 * will shut down the app. 126 * 127 * <h3>Developer's guide</h3> 128 * 129 * <p>To learn more about developing VPN apps, read the 130 * <a href="{@docRoot}guide/topics/connectivity/vpn">VPN developer's guide</a>. 131 * 132 * @see Builder 133 */ 134 public class VpnService extends Service { 135 136 /** 137 * The action must be matched by the intent filter of this service. It also 138 * needs to require {@link android.Manifest.permission#BIND_VPN_SERVICE} 139 * permission so that other applications cannot abuse it. 140 */ 141 public static final String SERVICE_INTERFACE = VpnConfig.SERVICE_INTERFACE; 142 143 /** 144 * Key for boolean meta-data field indicating whether this VpnService supports always-on mode. 145 * 146 * <p>For a VPN app targeting {@link android.os.Build.VERSION_CODES#N API 24} or above, Android 147 * provides users with the ability to set it as always-on, so that VPN connection is 148 * persisted after device reboot and app upgrade. Always-on VPN can also be enabled by device 149 * owner and profile owner apps through 150 * {@link DevicePolicyManager#setAlwaysOnVpnPackage}. 151 * 152 * <p>VPN apps not supporting this feature should opt out by adding this meta-data field to the 153 * {@code VpnService} component of {@code AndroidManifest.xml}. In case there is more than one 154 * {@code VpnService} component defined in {@code AndroidManifest.xml}, opting out any one of 155 * them will opt out the entire app. For example, 156 * <pre> {@code 157 * <service android:name=".ExampleVpnService" 158 * android:permission="android.permission.BIND_VPN_SERVICE"> 159 * <intent-filter> 160 * <action android:name="android.net.VpnService"/> 161 * </intent-filter> 162 * <meta-data android:name="android.net.VpnService.SUPPORTS_ALWAYS_ON" 163 * android:value=false/> 164 * </service> 165 * } </pre> 166 * 167 * <p>This meta-data field defaults to {@code true} if absent. It will only have effect on 168 * {@link android.os.Build.VERSION_CODES#O_MR1} or higher. 169 */ 170 public static final String SERVICE_META_DATA_SUPPORTS_ALWAYS_ON = 171 "android.net.VpnService.SUPPORTS_ALWAYS_ON"; 172 173 /** 174 * Use IVpnManager since those methods are hidden and not available in VpnManager. 175 */ getService()176 private static IVpnManager getService() { 177 return IVpnManager.Stub.asInterface( 178 ServiceManager.getService(Context.VPN_MANAGEMENT_SERVICE)); 179 } 180 181 /** 182 * Prepare to establish a VPN connection. This method returns {@code null} 183 * if the VPN application is already prepared or if the user has previously 184 * consented to the VPN application. Otherwise, it returns an 185 * {@link Intent} to a system activity. The application should launch the 186 * activity using {@link Activity#startActivityForResult} to get itself 187 * prepared. The activity may pop up a dialog to require user action, and 188 * the result will come back via its {@link Activity#onActivityResult}. 189 * If the result is {@link Activity#RESULT_OK}, the application becomes 190 * prepared and is granted to use other methods in this class. 191 * 192 * <p>Only one application can be granted at the same time. The right 193 * is revoked when another application is granted. The application 194 * losing the right will be notified via its {@link #onRevoke}. Unless 195 * it becomes prepared again, subsequent calls to other methods in this 196 * class will fail. 197 * 198 * <p>The user may disable the VPN at any time while it is activated, in 199 * which case this method will return an intent the next time it is 200 * executed to obtain the user's consent again. 201 * 202 * @see #onRevoke 203 */ prepare(Context context)204 public static Intent prepare(Context context) { 205 try { 206 if (getService().prepareVpn(context.getPackageName(), null, context.getUserId())) { 207 return null; 208 } 209 } catch (RemoteException e) { 210 // ignore 211 } 212 return VpnConfig.getIntentForConfirmation(); 213 } 214 215 /** 216 * Version of {@link #prepare(Context)} which does not require user consent. 217 * 218 * <p>Requires {@link android.Manifest.permission#CONTROL_VPN} and should generally not be 219 * used. Only acceptable in situations where user consent has been obtained through other means. 220 * 221 * <p>Once this is run, future preparations may be done with the standard prepare method as this 222 * will authorize the package to prepare the VPN without consent in the future. 223 * 224 * @hide 225 */ 226 @SystemApi 227 @RequiresPermission(android.Manifest.permission.CONTROL_VPN) prepareAndAuthorize(Context context)228 public static void prepareAndAuthorize(Context context) { 229 IVpnManager vm = getService(); 230 String packageName = context.getPackageName(); 231 try { 232 // Only prepare if we're not already prepared. 233 int userId = context.getUserId(); 234 if (!vm.prepareVpn(packageName, null, userId)) { 235 vm.prepareVpn(null, packageName, userId); 236 } 237 vm.setVpnPackageAuthorization(packageName, userId, VpnManager.TYPE_VPN_SERVICE); 238 } catch (RemoteException e) { 239 // ignore 240 } 241 } 242 243 /** 244 * Protect a socket from VPN connections. After protecting, data sent 245 * through this socket will go directly to the underlying network, 246 * so its traffic will not be forwarded through the VPN. 247 * This method is useful if some connections need to be kept 248 * outside of VPN. For example, a VPN tunnel should protect itself if its 249 * destination is covered by VPN routes. Otherwise its outgoing packets 250 * will be sent back to the VPN interface and cause an infinite loop. This 251 * method will fail if the application is not prepared or is revoked. 252 * 253 * <p class="note">The socket is NOT closed by this method. 254 * 255 * @return {@code true} on success. 256 */ protect(int socket)257 public boolean protect(int socket) { 258 return NetworkUtilsInternal.protectFromVpn(socket); 259 } 260 261 /** 262 * Convenience method to protect a {@link Socket} from VPN connections. 263 * 264 * @return {@code true} on success. 265 * @see #protect(int) 266 */ protect(Socket socket)267 public boolean protect(Socket socket) { 268 return protect(socket.getFileDescriptor$().getInt$()); 269 } 270 271 /** 272 * Convenience method to protect a {@link DatagramSocket} from VPN 273 * connections. 274 * 275 * @return {@code true} on success. 276 * @see #protect(int) 277 */ protect(DatagramSocket socket)278 public boolean protect(DatagramSocket socket) { 279 return protect(socket.getFileDescriptor$().getInt$()); 280 } 281 282 /** 283 * Adds a network address to the VPN interface. 284 * 285 * Both IPv4 and IPv6 addresses are supported. The VPN must already be established. Fails if the 286 * address is already in use or cannot be assigned to the interface for any other reason. 287 * 288 * Adding an address implicitly allows traffic from that address family (i.e., IPv4 or IPv6) to 289 * be routed over the VPN. @see Builder#allowFamily 290 * 291 * @throws IllegalArgumentException if the address is invalid. 292 * 293 * @param address The IP address (IPv4 or IPv6) to assign to the VPN interface. 294 * @param prefixLength The prefix length of the address. 295 * 296 * @return {@code true} on success. 297 * @see Builder#addAddress 298 * 299 * @hide 300 */ addAddress(InetAddress address, int prefixLength)301 public boolean addAddress(InetAddress address, int prefixLength) { 302 check(address, prefixLength); 303 try { 304 return getService().addVpnAddress(address.getHostAddress(), prefixLength); 305 } catch (RemoteException e) { 306 throw new IllegalStateException(e); 307 } 308 } 309 310 /** 311 * Removes a network address from the VPN interface. 312 * 313 * Both IPv4 and IPv6 addresses are supported. The VPN must already be established. Fails if the 314 * address is not assigned to the VPN interface, or if it is the only address assigned (thus 315 * cannot be removed), or if the address cannot be removed for any other reason. 316 * 317 * After removing an address, if there are no addresses, routes or DNS servers of a particular 318 * address family (i.e., IPv4 or IPv6) configured on the VPN, that <b>DOES NOT</b> block that 319 * family from being routed. In other words, once an address family has been allowed, it stays 320 * allowed for the rest of the VPN's session. @see Builder#allowFamily 321 * 322 * @throws IllegalArgumentException if the address is invalid. 323 * 324 * @param address The IP address (IPv4 or IPv6) to assign to the VPN interface. 325 * @param prefixLength The prefix length of the address. 326 * 327 * @return {@code true} on success. 328 * 329 * @hide 330 */ removeAddress(InetAddress address, int prefixLength)331 public boolean removeAddress(InetAddress address, int prefixLength) { 332 check(address, prefixLength); 333 try { 334 return getService().removeVpnAddress(address.getHostAddress(), prefixLength); 335 } catch (RemoteException e) { 336 throw new IllegalStateException(e); 337 } 338 } 339 340 /** 341 * Sets the underlying networks used by the VPN for its upstream connections. 342 * 343 * <p>Used by the system to know the actual networks that carry traffic for apps affected by 344 * this VPN in order to present this information to the user (e.g., via status bar icons). 345 * 346 * <p>This method only needs to be called if the VPN has explicitly bound its underlying 347 * communications channels — such as the socket(s) passed to {@link #protect(int)} — 348 * to a {@code Network} using APIs such as {@link Network#bindSocket(Socket)} or 349 * {@link Network#bindSocket(DatagramSocket)}. The VPN should call this method every time 350 * the set of {@code Network}s it is using changes. 351 * 352 * <p>{@code networks} is one of the following: 353 * <ul> 354 * <li><strong>a non-empty array</strong>: an array of one or more {@link Network}s, in 355 * decreasing preference order. For example, if this VPN uses both wifi and mobile (cellular) 356 * networks to carry app traffic, but prefers or uses wifi more than mobile, wifi should appear 357 * first in the array.</li> 358 * <li><strong>an empty array</strong>: a zero-element array, meaning that the VPN has no 359 * underlying network connection, and thus, app traffic will not be sent or received.</li> 360 * <li><strong>null</strong>: (default) signifies that the VPN uses whatever is the system's 361 * default network. I.e., it doesn't use the {@code bindSocket} or {@code bindDatagramSocket} 362 * APIs mentioned above to send traffic over specific channels.</li> 363 * </ul> 364 * 365 * <p>This call will succeed only if the VPN is currently established. For setting this value 366 * when the VPN has not yet been established, see {@link Builder#setUnderlyingNetworks}. 367 * 368 * @param networks An array of networks the VPN uses to tunnel traffic to/from its servers. 369 * 370 * @return {@code true} on success. 371 */ setUnderlyingNetworks(Network[] networks)372 public boolean setUnderlyingNetworks(Network[] networks) { 373 try { 374 return getService().setUnderlyingNetworksForVpn(networks); 375 } catch (RemoteException e) { 376 throw new IllegalStateException(e); 377 } 378 } 379 380 /** 381 * Returns whether the service is running in always-on VPN mode. In this mode the system ensures 382 * that the service is always running by restarting it when necessary, e.g. after reboot. 383 * 384 * @see DevicePolicyManager#setAlwaysOnVpnPackage(ComponentName, String, boolean, Set) 385 */ isAlwaysOn()386 public final boolean isAlwaysOn() { 387 try { 388 return getService().isCallerCurrentAlwaysOnVpnApp(); 389 } catch (RemoteException e) { 390 throw e.rethrowFromSystemServer(); 391 } 392 } 393 394 /** 395 * Returns whether the service is running in always-on VPN lockdown mode. In this mode the 396 * system ensures that the service is always running and that the apps aren't allowed to bypass 397 * the VPN. 398 * 399 * @see DevicePolicyManager#setAlwaysOnVpnPackage(ComponentName, String, boolean, Set) 400 */ isLockdownEnabled()401 public final boolean isLockdownEnabled() { 402 try { 403 return getService().isCallerCurrentAlwaysOnVpnLockdownApp(); 404 } catch (RemoteException e) { 405 throw e.rethrowFromSystemServer(); 406 } 407 } 408 409 /** 410 * Return the communication interface to the service. This method returns 411 * {@code null} on {@link Intent}s other than {@link #SERVICE_INTERFACE} 412 * action. Applications overriding this method must identify the intent 413 * and return the corresponding interface accordingly. 414 * 415 * @see Service#onBind 416 */ 417 @Override onBind(Intent intent)418 public IBinder onBind(Intent intent) { 419 if (intent != null && SERVICE_INTERFACE.equals(intent.getAction())) { 420 return new Callback(); 421 } 422 return null; 423 } 424 425 /** 426 * Invoked when the application is revoked. At this moment, the VPN 427 * interface is already deactivated by the system. The application should 428 * close the file descriptor and shut down gracefully. The default 429 * implementation of this method is calling {@link Service#stopSelf()}. 430 * 431 * <p class="note">Calls to this method may not happen on the main thread 432 * of the process. 433 * 434 * @see #prepare 435 */ onRevoke()436 public void onRevoke() { 437 stopSelf(); 438 } 439 440 /** 441 * Use raw Binder instead of AIDL since now there is only one usage. 442 */ 443 private class Callback extends Binder { 444 @Override onTransact(int code, Parcel data, Parcel reply, int flags)445 protected boolean onTransact(int code, Parcel data, Parcel reply, int flags) { 446 if (code == IBinder.LAST_CALL_TRANSACTION) { 447 onRevoke(); 448 return true; 449 } 450 return false; 451 } 452 } 453 454 /** 455 * Private method to validate address and prefixLength. 456 */ check(InetAddress address, int prefixLength)457 private static void check(InetAddress address, int prefixLength) { 458 if (address.isLoopbackAddress()) { 459 throw new IllegalArgumentException("Bad address"); 460 } 461 if (address instanceof Inet4Address) { 462 if (prefixLength < 0 || prefixLength > 32) { 463 throw new IllegalArgumentException("Bad prefixLength"); 464 } 465 } else if (address instanceof Inet6Address) { 466 if (prefixLength < 0 || prefixLength > 128) { 467 throw new IllegalArgumentException("Bad prefixLength"); 468 } 469 } else { 470 throw new IllegalArgumentException("Unsupported family"); 471 } 472 } 473 474 /** 475 * Helper class to create a VPN interface. This class should be always 476 * used within the scope of the outer {@link VpnService}. 477 * 478 * @see VpnService 479 */ 480 public class Builder { 481 482 private final VpnConfig mConfig = new VpnConfig(); 483 @UnsupportedAppUsage 484 private final List<LinkAddress> mAddresses = new ArrayList<LinkAddress>(); 485 @UnsupportedAppUsage 486 private final List<RouteInfo> mRoutes = new ArrayList<RouteInfo>(); 487 Builder()488 public Builder() { 489 mConfig.user = VpnService.this.getClass().getName(); 490 } 491 492 /** 493 * Set the name of this session. It will be displayed in 494 * system-managed dialogs and notifications. This is recommended 495 * not required. 496 */ 497 @NonNull setSession(@onNull String session)498 public Builder setSession(@NonNull String session) { 499 mConfig.session = session; 500 return this; 501 } 502 503 /** 504 * Set the {@link PendingIntent} to an activity for users to 505 * configure the VPN connection. If it is not set, the button 506 * to configure will not be shown in system-managed dialogs. 507 */ 508 @NonNull setConfigureIntent(@onNull PendingIntent intent)509 public Builder setConfigureIntent(@NonNull PendingIntent intent) { 510 mConfig.configureIntent = intent; 511 return this; 512 } 513 514 /** 515 * Set the maximum transmission unit (MTU) of the VPN interface. If 516 * it is not set, the default value in the operating system will be 517 * used. 518 * 519 * @throws IllegalArgumentException if the value is not positive. 520 */ 521 @NonNull setMtu(int mtu)522 public Builder setMtu(int mtu) { 523 if (mtu <= 0) { 524 throw new IllegalArgumentException("Bad mtu"); 525 } 526 mConfig.mtu = mtu; 527 return this; 528 } 529 530 /** 531 * Sets an HTTP proxy for the VPN network. This proxy is only a recommendation 532 * and it is possible that some apps will ignore it. 533 */ 534 @NonNull setHttpProxy(@onNull ProxyInfo proxyInfo)535 public Builder setHttpProxy(@NonNull ProxyInfo proxyInfo) { 536 mConfig.proxyInfo = proxyInfo; 537 return this; 538 } 539 540 /** 541 * Add a network address to the VPN interface. Both IPv4 and IPv6 542 * addresses are supported. At least one address must be set before 543 * calling {@link #establish}. 544 * 545 * Adding an address implicitly allows traffic from that address family 546 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 547 * 548 * @throws IllegalArgumentException if the address is invalid. 549 */ 550 @NonNull addAddress(@onNull InetAddress address, int prefixLength)551 public Builder addAddress(@NonNull InetAddress address, int prefixLength) { 552 check(address, prefixLength); 553 554 if (address.isAnyLocalAddress()) { 555 throw new IllegalArgumentException("Bad address"); 556 } 557 mAddresses.add(new LinkAddress(address, prefixLength)); 558 mConfig.updateAllowedFamilies(address); 559 return this; 560 } 561 562 /** 563 * Convenience method to add a network address to the VPN interface 564 * using a numeric address string. See {@link InetAddress} for the 565 * definitions of numeric address formats. 566 * 567 * Adding an address implicitly allows traffic from that address family 568 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 569 * 570 * @throws IllegalArgumentException if the address is invalid. 571 * @see #addAddress(InetAddress, int) 572 */ 573 @NonNull addAddress(@onNull String address, int prefixLength)574 public Builder addAddress(@NonNull String address, int prefixLength) { 575 return addAddress(InetAddress.parseNumericAddress(address), prefixLength); 576 } 577 578 /** 579 * Add a network route to the VPN interface. Both IPv4 and IPv6 580 * routes are supported. 581 * 582 * Adding a route implicitly allows traffic from that address family 583 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 584 * 585 * @throws IllegalArgumentException if the route is invalid. 586 */ 587 @NonNull addRoute(@onNull InetAddress address, int prefixLength)588 public Builder addRoute(@NonNull InetAddress address, int prefixLength) { 589 check(address, prefixLength); 590 591 int offset = prefixLength / 8; 592 byte[] bytes = address.getAddress(); 593 if (offset < bytes.length) { 594 for (bytes[offset] <<= prefixLength % 8; offset < bytes.length; ++offset) { 595 if (bytes[offset] != 0) { 596 throw new IllegalArgumentException("Bad address"); 597 } 598 } 599 } 600 mRoutes.add(new RouteInfo(new IpPrefix(address, prefixLength), null, null, 601 RouteInfo.RTN_UNICAST)); 602 mConfig.updateAllowedFamilies(address); 603 return this; 604 } 605 606 /** 607 * Convenience method to add a network route to the VPN interface 608 * using a numeric address string. See {@link InetAddress} for the 609 * definitions of numeric address formats. 610 * 611 * Adding a route implicitly allows traffic from that address family 612 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 613 * 614 * @throws IllegalArgumentException if the route is invalid. 615 * @see #addRoute(InetAddress, int) 616 */ 617 @NonNull addRoute(@onNull String address, int prefixLength)618 public Builder addRoute(@NonNull String address, int prefixLength) { 619 return addRoute(InetAddress.parseNumericAddress(address), prefixLength); 620 } 621 622 /** 623 * Add a DNS server to the VPN connection. Both IPv4 and IPv6 624 * addresses are supported. If none is set, the DNS servers of 625 * the default network will be used. 626 * 627 * Adding a server implicitly allows traffic from that address family 628 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 629 * 630 * @throws IllegalArgumentException if the address is invalid. 631 */ 632 @NonNull addDnsServer(@onNull InetAddress address)633 public Builder addDnsServer(@NonNull InetAddress address) { 634 if (address.isLoopbackAddress() || address.isAnyLocalAddress()) { 635 throw new IllegalArgumentException("Bad address"); 636 } 637 if (mConfig.dnsServers == null) { 638 mConfig.dnsServers = new ArrayList<String>(); 639 } 640 mConfig.dnsServers.add(address.getHostAddress()); 641 return this; 642 } 643 644 /** 645 * Convenience method to add a DNS server to the VPN connection 646 * using a numeric address string. See {@link InetAddress} for the 647 * definitions of numeric address formats. 648 * 649 * Adding a server implicitly allows traffic from that address family 650 * (i.e., IPv4 or IPv6) to be routed over the VPN. @see #allowFamily 651 * 652 * @throws IllegalArgumentException if the address is invalid. 653 * @see #addDnsServer(InetAddress) 654 */ 655 @NonNull addDnsServer(@onNull String address)656 public Builder addDnsServer(@NonNull String address) { 657 return addDnsServer(InetAddress.parseNumericAddress(address)); 658 } 659 660 /** 661 * Add a search domain to the DNS resolver. 662 */ 663 @NonNull addSearchDomain(@onNull String domain)664 public Builder addSearchDomain(@NonNull String domain) { 665 if (mConfig.searchDomains == null) { 666 mConfig.searchDomains = new ArrayList<String>(); 667 } 668 mConfig.searchDomains.add(domain); 669 return this; 670 } 671 672 /** 673 * Allows traffic from the specified address family. 674 * 675 * By default, if no address, route or DNS server of a specific family (IPv4 or IPv6) is 676 * added to this VPN, then all outgoing traffic of that family is blocked. If any address, 677 * route or DNS server is added, that family is allowed. 678 * 679 * This method allows an address family to be unblocked even without adding an address, 680 * route or DNS server of that family. Traffic of that family will then typically 681 * fall-through to the underlying network if it's supported. 682 * 683 * {@code family} must be either {@code AF_INET} (for IPv4) or {@code AF_INET6} (for IPv6). 684 * {@link IllegalArgumentException} is thrown if it's neither. 685 * 686 * @param family The address family ({@code AF_INET} or {@code AF_INET6}) to allow. 687 * 688 * @return this {@link Builder} object to facilitate chaining of method calls. 689 */ 690 @NonNull allowFamily(int family)691 public Builder allowFamily(int family) { 692 if (family == AF_INET) { 693 mConfig.allowIPv4 = true; 694 } else if (family == AF_INET6) { 695 mConfig.allowIPv6 = true; 696 } else { 697 throw new IllegalArgumentException(family + " is neither " + AF_INET + " nor " + 698 AF_INET6); 699 } 700 return this; 701 } 702 verifyApp(String packageName)703 private void verifyApp(String packageName) throws PackageManager.NameNotFoundException { 704 IPackageManager pm = IPackageManager.Stub.asInterface( 705 ServiceManager.getService("package")); 706 try { 707 pm.getApplicationInfo(packageName, 0, UserHandle.getCallingUserId()); 708 } catch (RemoteException e) { 709 throw new IllegalStateException(e); 710 } 711 } 712 713 /** 714 * Adds an application that's allowed to access the VPN connection. 715 * 716 * If this method is called at least once, only applications added through this method (and 717 * no others) are allowed access. Else (if this method is never called), all applications 718 * are allowed by default. If some applications are added, other, un-added applications 719 * will use networking as if the VPN wasn't running. 720 * 721 * A {@link Builder} may have only a set of allowed applications OR a set of disallowed 722 * ones, but not both. Calling this method after {@link #addDisallowedApplication} has 723 * already been called, or vice versa, will throw an {@link UnsupportedOperationException}. 724 * 725 * {@code packageName} must be the canonical name of a currently installed application. 726 * {@link PackageManager.NameNotFoundException} is thrown if there's no such application. 727 * 728 * @throws PackageManager.NameNotFoundException If the application isn't installed. 729 * 730 * @param packageName The full name (e.g.: "com.google.apps.contacts") of an application. 731 * 732 * @return this {@link Builder} object to facilitate chaining method calls. 733 */ 734 @NonNull addAllowedApplication(@onNull String packageName)735 public Builder addAllowedApplication(@NonNull String packageName) 736 throws PackageManager.NameNotFoundException { 737 if (mConfig.disallowedApplications != null) { 738 throw new UnsupportedOperationException("addDisallowedApplication already called"); 739 } 740 verifyApp(packageName); 741 if (mConfig.allowedApplications == null) { 742 mConfig.allowedApplications = new ArrayList<String>(); 743 } 744 mConfig.allowedApplications.add(packageName); 745 return this; 746 } 747 748 /** 749 * Adds an application that's denied access to the VPN connection. 750 * 751 * By default, all applications are allowed access, except for those denied through this 752 * method. Denied applications will use networking as if the VPN wasn't running. 753 * 754 * A {@link Builder} may have only a set of allowed applications OR a set of disallowed 755 * ones, but not both. Calling this method after {@link #addAllowedApplication} has already 756 * been called, or vice versa, will throw an {@link UnsupportedOperationException}. 757 * 758 * {@code packageName} must be the canonical name of a currently installed application. 759 * {@link PackageManager.NameNotFoundException} is thrown if there's no such application. 760 * 761 * @throws PackageManager.NameNotFoundException If the application isn't installed. 762 * 763 * @param packageName The full name (e.g.: "com.google.apps.contacts") of an application. 764 * 765 * @return this {@link Builder} object to facilitate chaining method calls. 766 */ 767 @NonNull addDisallowedApplication(@onNull String packageName)768 public Builder addDisallowedApplication(@NonNull String packageName) 769 throws PackageManager.NameNotFoundException { 770 if (mConfig.allowedApplications != null) { 771 throw new UnsupportedOperationException("addAllowedApplication already called"); 772 } 773 verifyApp(packageName); 774 if (mConfig.disallowedApplications == null) { 775 mConfig.disallowedApplications = new ArrayList<String>(); 776 } 777 mConfig.disallowedApplications.add(packageName); 778 return this; 779 } 780 781 /** 782 * Allows all apps to bypass this VPN connection. 783 * 784 * By default, all traffic from apps is forwarded through the VPN interface and it is not 785 * possible for apps to side-step the VPN. If this method is called, apps may use methods 786 * such as {@link ConnectivityManager#bindProcessToNetwork} to instead send/receive 787 * directly over the underlying network or any other network they have permissions for. 788 * 789 * @return this {@link Builder} object to facilitate chaining of method calls. 790 */ 791 @NonNull allowBypass()792 public Builder allowBypass() { 793 mConfig.allowBypass = true; 794 return this; 795 } 796 797 /** 798 * Sets the VPN interface's file descriptor to be in blocking/non-blocking mode. 799 * 800 * By default, the file descriptor returned by {@link #establish} is non-blocking. 801 * 802 * @param blocking True to put the descriptor into blocking mode; false for non-blocking. 803 * 804 * @return this {@link Builder} object to facilitate chaining method calls. 805 */ 806 @NonNull setBlocking(boolean blocking)807 public Builder setBlocking(boolean blocking) { 808 mConfig.blocking = blocking; 809 return this; 810 } 811 812 /** 813 * Sets the underlying networks used by the VPN for its upstream connections. 814 * 815 * @see VpnService#setUnderlyingNetworks 816 * 817 * @param networks An array of networks the VPN uses to tunnel traffic to/from its servers. 818 * 819 * @return this {@link Builder} object to facilitate chaining method calls. 820 */ 821 @NonNull setUnderlyingNetworks(@ullable Network[] networks)822 public Builder setUnderlyingNetworks(@Nullable Network[] networks) { 823 mConfig.underlyingNetworks = networks != null ? networks.clone() : null; 824 return this; 825 } 826 827 /** 828 * Marks the VPN network as metered. A VPN network is classified as metered when the user is 829 * sensitive to heavy data usage due to monetary costs and/or data limitations. In such 830 * cases, you should set this to {@code true} so that apps on the system can avoid doing 831 * large data transfers. Otherwise, set this to {@code false}. Doing so would cause VPN 832 * network to inherit its meteredness from its underlying networks. 833 * 834 * <p>VPN apps targeting {@link android.os.Build.VERSION_CODES#Q} or above will be 835 * considered metered by default. 836 * 837 * @param isMetered {@code true} if VPN network should be treated as metered regardless of 838 * underlying network meteredness 839 * @return this {@link Builder} object to facilitate chaining method calls 840 * @see #setUnderlyingNetworks(Network[]) 841 * @see ConnectivityManager#isActiveNetworkMetered() 842 */ 843 @NonNull setMetered(boolean isMetered)844 public Builder setMetered(boolean isMetered) { 845 mConfig.isMetered = isMetered; 846 return this; 847 } 848 849 /** 850 * Create a VPN interface using the parameters supplied to this 851 * builder. The interface works on IP packets, and a file descriptor 852 * is returned for the application to access them. Each read 853 * retrieves an outgoing packet which was routed to the interface. 854 * Each write injects an incoming packet just like it was received 855 * from the interface. The file descriptor is put into non-blocking 856 * mode by default to avoid blocking Java threads. To use the file 857 * descriptor completely in native space, see 858 * {@link ParcelFileDescriptor#detachFd()}. The application MUST 859 * close the file descriptor when the VPN connection is terminated. 860 * The VPN interface will be removed and the network will be 861 * restored by the system automatically. 862 * 863 * <p>To avoid conflicts, there can be only one active VPN interface 864 * at the same time. Usually network parameters are never changed 865 * during the lifetime of a VPN connection. It is also common for an 866 * application to create a new file descriptor after closing the 867 * previous one. However, it is rare but not impossible to have two 868 * interfaces while performing a seamless handover. In this case, the 869 * old interface will be deactivated when the new one is created 870 * successfully. Both file descriptors are valid but now outgoing 871 * packets will be routed to the new interface. Therefore, after 872 * draining the old file descriptor, the application MUST close it 873 * and start using the new file descriptor. If the new interface 874 * cannot be created, the existing interface and its file descriptor 875 * remain untouched. 876 * 877 * <p>An exception will be thrown if the interface cannot be created 878 * for any reason. However, this method returns {@code null} if the 879 * application is not prepared or is revoked. This helps solve 880 * possible race conditions between other VPN applications. 881 * 882 * @return {@link ParcelFileDescriptor} of the VPN interface, or 883 * {@code null} if the application is not prepared. 884 * @throws IllegalArgumentException if a parameter is not accepted 885 * by the operating system. 886 * @throws IllegalStateException if a parameter cannot be applied 887 * by the operating system. 888 * @throws SecurityException if the service is not properly declared 889 * in {@code AndroidManifest.xml}. 890 * @see VpnService 891 */ 892 @Nullable establish()893 public ParcelFileDescriptor establish() { 894 mConfig.addresses = mAddresses; 895 mConfig.routes = mRoutes; 896 897 try { 898 return getService().establishVpn(mConfig); 899 } catch (RemoteException e) { 900 throw new IllegalStateException(e); 901 } 902 } 903 } 904 } 905