diff options
author | Justin Klaassen <justinklaassen@google.com> | 2018-04-15 00:41:15 -0400 |
---|---|---|
committer | Justin Klaassen <justinklaassen@google.com> | 2018-04-15 00:41:15 -0400 |
commit | b8042fc9b036db0a6692ca853428fc6ab1e60892 (patch) | |
tree | 82669ea5d75238758e22d379a42baeada526219e /android/net | |
parent | 4d01eeaffaa720e4458a118baa137a11614f00f7 (diff) | |
download | android-28-b8042fc9b036db0a6692ca853428fc6ab1e60892.tar.gz |
Import Android SDK Platform P [4719250]HEADmastermainandroidx-work-releaseandroidx-webkit-releaseandroidx-viewpager2-releaseandroidx-versionedparcelable-releaseandroidx-vectordrawable-releaseandroidx-transition-releaseandroidx-sqlite-releaseandroidx-sharetarget-releaseandroidx-security-security-crypto-releaseandroidx-savedstate-releaseandroidx-room-releaseandroidx-recyclerview-releaseandroidx-recyclerview-recyclerview-selection-releaseandroidx-preference-releaseandroidx-paging-releaseandroidx-paging-legacy-releaseandroidx-navigation-releaseandroidx-mediarouter-releaseandroidx-media2-releaseandroidx-media2-media2-widget-releaseandroidx-media-releaseandroidx-master-releaseandroidx-localbroadcastmanager-releaseandroidx-loader-releaseandroidx-lifecycle-releaseandroidx-jetifier-releaseandroidx-g3-releaseandroidx-fragment-releaseandroidx-exifinterface-releaseandroidx-enterprise-releaseandroidx-core-releaseandroidx-core-core-role-releaseandroidx-coordinatorlayout-releaseandroidx-concurrent-releaseandroidx-compose-releaseandroidx-collection-releaseandroidx-camerax-releaseandroidx-browser-releaseandroidx-biometric-releaseandroidx-benchmark-releaseandroidx-autofill-releaseandroidx-arch-core-releaseandroidx-appcompat-releaseandroidx-annotation-releaseandroidx-annotation-annotation-experimental-releaseandroidx-activity-releaseandroid-arch-work-releaseandroid-arch-navigation-release
/google/data/ro/projects/android/fetch_artifact \
--bid 4719250 \
--target sdk_phone_armv7-win_sdk \
sdk-repo-linux-sources-4719250.zip
AndroidVersion.ApiLevel has been modified to appear as 28
Change-Id: I9ec0a12c9251b8449dba0d86b0cfdbcca16b0a7c
Diffstat (limited to 'android/net')
-rw-r--r-- | android/net/IpSecManager.java | 43 | ||||
-rw-r--r-- | android/net/IpSecTransform.java | 8 | ||||
-rw-r--r-- | android/net/NetworkCapabilities.java | 28 | ||||
-rw-r--r-- | android/net/NetworkPolicy.java | 4 | ||||
-rw-r--r-- | android/net/NetworkPolicyManager.java | 16 | ||||
-rw-r--r-- | android/net/NetworkRequest.java | 17 | ||||
-rw-r--r-- | android/net/NetworkState.java | 4 | ||||
-rw-r--r-- | android/net/apf/ApfFilter.java | 108 | ||||
-rw-r--r-- | android/net/dns/ResolvUtil.java | 65 | ||||
-rw-r--r-- | android/net/http/X509TrustManagerExtensions.java | 3 | ||||
-rw-r--r-- | android/net/ip/IpClient.java | 56 | ||||
-rw-r--r-- | android/net/ip/IpManager.java | 29 | ||||
-rw-r--r-- | android/net/metrics/ApfStats.java | 2 | ||||
-rw-r--r-- | android/net/util/NetworkConstants.java | 3 | ||||
-rw-r--r-- | android/net/wifi/WifiConfiguration.java | 82 | ||||
-rw-r--r-- | android/net/wifi/WifiManager.java | 6 |
16 files changed, 279 insertions, 195 deletions
diff --git a/android/net/IpSecManager.java b/android/net/IpSecManager.java index 15255083..a61ea50d 100644 --- a/android/net/IpSecManager.java +++ b/android/net/IpSecManager.java @@ -20,7 +20,6 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresPermission; -import android.annotation.SystemApi; import android.annotation.SystemService; import android.annotation.TestApi; import android.content.Context; @@ -140,6 +139,7 @@ public final class IpSecManager { } } + private final Context mContext; private final IIpSecService mService; /** @@ -336,6 +336,9 @@ public final class IpSecManager { */ public void applyTransportModeTransform(@NonNull Socket socket, @PolicyDirection int direction, @NonNull IpSecTransform transform) throws IOException { + // Ensure creation of FD. See b/77548890 for more details. + socket.getSoLinger(); + applyTransportModeTransform(socket.getFileDescriptor$(), direction, transform); } @@ -440,6 +443,9 @@ public final class IpSecManager { * @throws IOException indicating that the transform could not be removed from the socket */ public void removeTransportModeTransforms(@NonNull Socket socket) throws IOException { + // Ensure creation of FD. See b/77548890 for more details. + socket.getSoLinger(); + removeTransportModeTransforms(socket.getFileDescriptor$()); } @@ -659,8 +665,8 @@ public final class IpSecManager { * to create Network objects which are accessible to the Android system. * @hide */ - @SystemApi public static final class IpSecTunnelInterface implements AutoCloseable { + private final String mOpPackageName; private final IIpSecService mService; private final InetAddress mRemoteAddress; private final InetAddress mLocalAddress; @@ -682,13 +688,14 @@ public final class IpSecManager { * tunneled traffic. * * @param address the local address for traffic inside the tunnel + * @param prefixLen length of the InetAddress prefix * @hide */ - @SystemApi @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) - public void addAddress(@NonNull LinkAddress address) throws IOException { + public void addAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { - mService.addAddressToTunnelInterface(mResourceId, address); + mService.addAddressToTunnelInterface( + mResourceId, new LinkAddress(address, prefixLen), mOpPackageName); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } @@ -700,22 +707,24 @@ public final class IpSecManager { * <p>Remove an address which was previously added to the IpSecTunnelInterface * * @param address to be removed + * @param prefixLen length of the InetAddress prefix * @hide */ - @SystemApi @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) - public void removeAddress(@NonNull LinkAddress address) throws IOException { + public void removeAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { - mService.removeAddressFromTunnelInterface(mResourceId, address); + mService.removeAddressFromTunnelInterface( + mResourceId, new LinkAddress(address, prefixLen), mOpPackageName); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } - private IpSecTunnelInterface(@NonNull IIpSecService service, + private IpSecTunnelInterface(@NonNull Context ctx, @NonNull IIpSecService service, @NonNull InetAddress localAddress, @NonNull InetAddress remoteAddress, @NonNull Network underlyingNetwork) throws ResourceUnavailableException, IOException { + mOpPackageName = ctx.getOpPackageName(); mService = service; mLocalAddress = localAddress; mRemoteAddress = remoteAddress; @@ -727,7 +736,8 @@ public final class IpSecManager { localAddress.getHostAddress(), remoteAddress.getHostAddress(), underlyingNetwork, - new Binder()); + new Binder(), + mOpPackageName); switch (result.status) { case Status.OK: break; @@ -756,7 +766,7 @@ public final class IpSecManager { @Override public void close() { try { - mService.deleteTunnelInterface(mResourceId); + mService.deleteTunnelInterface(mResourceId, mOpPackageName); mResourceId = INVALID_RESOURCE_ID; } catch (RemoteException e) { throw e.rethrowFromSystemServer(); @@ -795,13 +805,13 @@ public final class IpSecManager { * @throws ResourceUnavailableException indicating that too many encapsulation sockets are open * @hide */ - @SystemApi @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTunnelInterface createIpSecTunnelInterface(@NonNull InetAddress localAddress, @NonNull InetAddress remoteAddress, @NonNull Network underlyingNetwork) throws ResourceUnavailableException, IOException { - return new IpSecTunnelInterface(mService, localAddress, remoteAddress, underlyingNetwork); + return new IpSecTunnelInterface( + mContext, mService, localAddress, remoteAddress, underlyingNetwork); } /** @@ -821,13 +831,13 @@ public final class IpSecManager { * layer failure. * @hide */ - @SystemApi @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void applyTunnelModeTransform(@NonNull IpSecTunnelInterface tunnel, @PolicyDirection int direction, @NonNull IpSecTransform transform) throws IOException { try { mService.applyTunnelModeTransform( - tunnel.getResourceId(), direction, transform.getResourceId()); + tunnel.getResourceId(), direction, + transform.getResourceId(), mContext.getOpPackageName()); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } @@ -839,7 +849,8 @@ public final class IpSecManager { * @param context the application context for this manager * @hide */ - public IpSecManager(IIpSecService service) { + public IpSecManager(Context ctx, IIpSecService service) { + mContext = ctx; mService = checkNotNull(service, "missing service"); } } diff --git a/android/net/IpSecTransform.java b/android/net/IpSecTransform.java index 099fe02f..62f79965 100644 --- a/android/net/IpSecTransform.java +++ b/android/net/IpSecTransform.java @@ -22,7 +22,6 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresPermission; -import android.annotation.SystemApi; import android.content.Context; import android.os.Binder; import android.os.Handler; @@ -130,7 +129,8 @@ public final class IpSecTransform implements AutoCloseable { synchronized (this) { try { IIpSecService svc = getIpSecService(); - IpSecTransformResponse result = svc.createTransform(mConfig, new Binder()); + IpSecTransformResponse result = svc.createTransform( + mConfig, new Binder(), mContext.getOpPackageName()); int status = result.status; checkResultStatus(status); mResourceId = result.resourceId; @@ -249,7 +249,6 @@ public final class IpSecTransform implements AutoCloseable { * * @hide */ - @SystemApi public static class NattKeepaliveCallback { /** The specified {@code Network} is not connected. */ public static final int ERROR_INVALID_NETWORK = 1; @@ -280,7 +279,6 @@ public final class IpSecTransform implements AutoCloseable { * * @hide */ - @SystemApi @RequiresPermission(anyOf = { android.Manifest.permission.MANAGE_IPSEC_TUNNELS, android.Manifest.permission.PACKET_KEEPALIVE_OFFLOAD @@ -323,7 +321,6 @@ public final class IpSecTransform implements AutoCloseable { * * @hide */ - @SystemApi @RequiresPermission(anyOf = { android.Manifest.permission.MANAGE_IPSEC_TUNNELS, android.Manifest.permission.PACKET_KEEPALIVE_OFFLOAD @@ -476,7 +473,6 @@ public final class IpSecTransform implements AutoCloseable { * @throws IOException indicating other errors * @hide */ - @SystemApi @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTransform buildTunnelModeTransform( diff --git a/android/net/NetworkCapabilities.java b/android/net/NetworkCapabilities.java index 374b3abc..a8e81791 100644 --- a/android/net/NetworkCapabilities.java +++ b/android/net/NetworkCapabilities.java @@ -254,9 +254,8 @@ public final class NetworkCapabilities implements Parcelable { /** * Indicates that this network is not congested. * <p> - * When a network is congested, the device should defer network traffic that - * can be done at a later time without breaking developer contracts. - * @hide + * When a network is congested, applications should defer network traffic + * that can be done at a later time, such as uploading analytics. */ public static final int NET_CAPABILITY_NOT_CONGESTED = 20; @@ -318,7 +317,7 @@ public final class NetworkCapabilities implements Parcelable { /** * Capabilities that suggest that a network is restricted. - * {@see #maybeMarkCapabilitiesRestricted}. + * {@see #maybeMarkCapabilitiesRestricted}, {@see #FORCE_RESTRICTED_CAPABILITIES} */ @VisibleForTesting /* package */ static final long RESTRICTED_CAPABILITIES = @@ -329,7 +328,13 @@ public final class NetworkCapabilities implements Parcelable { (1 << NET_CAPABILITY_IA) | (1 << NET_CAPABILITY_IMS) | (1 << NET_CAPABILITY_RCS) | - (1 << NET_CAPABILITY_XCAP) | + (1 << NET_CAPABILITY_XCAP); + + /** + * Capabilities that force network to be restricted. + * {@see #maybeMarkCapabilitiesRestricted}. + */ + private static final long FORCE_RESTRICTED_CAPABILITIES = (1 << NET_CAPABILITY_OEM_PAID); /** @@ -533,16 +538,21 @@ public final class NetworkCapabilities implements Parcelable { * @hide */ public void maybeMarkCapabilitiesRestricted() { + // Check if we have any capability that forces the network to be restricted. + final boolean forceRestrictedCapability = + (mNetworkCapabilities & FORCE_RESTRICTED_CAPABILITIES) != 0; + // Verify there aren't any unrestricted capabilities. If there are we say - // the whole thing is unrestricted. + // the whole thing is unrestricted unless it is forced to be restricted. final boolean hasUnrestrictedCapabilities = - ((mNetworkCapabilities & UNRESTRICTED_CAPABILITIES) != 0); + (mNetworkCapabilities & UNRESTRICTED_CAPABILITIES) != 0; // Must have at least some restricted capabilities. final boolean hasRestrictedCapabilities = - ((mNetworkCapabilities & RESTRICTED_CAPABILITIES) != 0); + (mNetworkCapabilities & RESTRICTED_CAPABILITIES) != 0; - if (hasRestrictedCapabilities && !hasUnrestrictedCapabilities) { + if (forceRestrictedCapability + || (hasRestrictedCapabilities && !hasUnrestrictedCapabilities)) { removeCapability(NET_CAPABILITY_NOT_RESTRICTED); } } diff --git a/android/net/NetworkPolicy.java b/android/net/NetworkPolicy.java index 1a28732e..e84c85ee 100644 --- a/android/net/NetworkPolicy.java +++ b/android/net/NetworkPolicy.java @@ -19,7 +19,7 @@ package android.net; import android.os.Parcel; import android.os.Parcelable; import android.util.BackupUtils; -import android.util.Pair; +import android.util.Range; import android.util.RecurrenceRule; import com.android.internal.util.Preconditions; @@ -136,7 +136,7 @@ public class NetworkPolicy implements Parcelable, Comparable<NetworkPolicy> { return 0; } - public Iterator<Pair<ZonedDateTime, ZonedDateTime>> cycleIterator() { + public Iterator<Range<ZonedDateTime>> cycleIterator() { return cycleRule.cycleIterator(); } diff --git a/android/net/NetworkPolicyManager.java b/android/net/NetworkPolicyManager.java index bf6b7e09..6546c391 100644 --- a/android/net/NetworkPolicyManager.java +++ b/android/net/NetworkPolicyManager.java @@ -31,6 +31,7 @@ import android.os.RemoteException; import android.os.UserHandle; import android.util.DebugUtils; import android.util.Pair; +import android.util.Range; import com.google.android.collect.Sets; @@ -258,8 +259,21 @@ public class NetworkPolicyManager { } /** {@hide} */ + @Deprecated public static Iterator<Pair<ZonedDateTime, ZonedDateTime>> cycleIterator(NetworkPolicy policy) { - return policy.cycleIterator(); + final Iterator<Range<ZonedDateTime>> it = policy.cycleIterator(); + return new Iterator<Pair<ZonedDateTime, ZonedDateTime>>() { + @Override + public boolean hasNext() { + return it.hasNext(); + } + + @Override + public Pair<ZonedDateTime, ZonedDateTime> next() { + final Range<ZonedDateTime> r = it.next(); + return Pair.create(r.getLower(), r.getUpper()); + } + }; } /** diff --git a/android/net/NetworkRequest.java b/android/net/NetworkRequest.java index 3d9d6e29..bd4a27c2 100644 --- a/android/net/NetworkRequest.java +++ b/android/net/NetworkRequest.java @@ -168,9 +168,6 @@ public class NetworkRequest implements Parcelable { * the requested network's required capabilities. Note that when searching * for a network to satisfy a request, all capabilities requested must be * satisfied. - * <p> - * If the given capability was previously added to the list of unwanted capabilities - * then the capability will also be removed from the list of unwanted capabilities. * * @param capability The capability to add. * @return The builder to facilitate chaining @@ -182,8 +179,7 @@ public class NetworkRequest implements Parcelable { } /** - * Removes (if found) the given capability from this builder instance from both required - * and unwanted capabilities lists. + * Removes (if found) the given capability from this builder instance. * * @param capability The capability to remove. * @return The builder to facilitate chaining. @@ -231,6 +227,8 @@ public class NetworkRequest implements Parcelable { * * @param capability The capability to add to unwanted capability list. * @return The builder to facilitate chaining. + * + * @removed */ public Builder addUnwantedCapability(@NetworkCapabilities.NetCapability int capability) { mNetworkCapabilities.addUnwantedCapability(capability); @@ -436,6 +434,15 @@ public class NetworkRequest implements Parcelable { } /** + * @see Builder#addUnwantedCapability(int) + * + * @removed + */ + public boolean hasUnwantedCapability(@NetCapability int capability) { + return networkCapabilities.hasUnwantedCapability(capability); + } + + /** * @see Builder#addTransportType(int) */ public boolean hasTransport(@Transport int transportType) { diff --git a/android/net/NetworkState.java b/android/net/NetworkState.java index b00cb482..321f9718 100644 --- a/android/net/NetworkState.java +++ b/android/net/NetworkState.java @@ -26,6 +26,8 @@ import android.util.Slog; * @hide */ public class NetworkState implements Parcelable { + private static final boolean SANITY_CHECK_ROAMING = false; + public static final NetworkState EMPTY = new NetworkState(null, null, null, null, null, null); public final NetworkInfo networkInfo; @@ -47,7 +49,7 @@ public class NetworkState implements Parcelable { // This object is an atomic view of a network, so the various components // should always agree on roaming state. - if (networkInfo != null && networkCapabilities != null) { + if (SANITY_CHECK_ROAMING && networkInfo != null && networkCapabilities != null) { if (networkInfo.isRoaming() == networkCapabilities .hasCapability(NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING)) { Slog.wtf("NetworkState", "Roaming state disagreement between " + networkInfo diff --git a/android/net/apf/ApfFilter.java b/android/net/apf/ApfFilter.java index d1904322..d5ff2dd6 100644 --- a/android/net/apf/ApfFilter.java +++ b/android/net/apf/ApfFilter.java @@ -16,21 +16,21 @@ package android.net.apf; +import static android.net.util.NetworkConstants.*; import static android.system.OsConstants.*; - import static com.android.internal.util.BitUtils.bytesToBEInt; import static com.android.internal.util.BitUtils.getUint16; import static com.android.internal.util.BitUtils.getUint32; import static com.android.internal.util.BitUtils.getUint8; -import static com.android.internal.util.BitUtils.uint16; import static com.android.internal.util.BitUtils.uint32; -import static com.android.internal.util.BitUtils.uint8; -import android.os.SystemClock; +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.content.IntentFilter; import android.net.LinkAddress; import android.net.LinkProperties; import android.net.NetworkUtils; -import android.net.apf.ApfGenerator; import android.net.apf.ApfGenerator.IllegalInstructionException; import android.net.apf.ApfGenerator.Register; import android.net.ip.IpClient; @@ -39,31 +39,29 @@ import android.net.metrics.ApfStats; import android.net.metrics.IpConnectivityLog; import android.net.metrics.RaEvent; import android.net.util.InterfaceParams; +import android.os.PowerManager; +import android.os.SystemClock; import android.system.ErrnoException; import android.system.Os; import android.system.PacketSocketAddress; import android.text.format.DateUtils; import android.util.Log; import android.util.Pair; - import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.util.HexDump; import com.android.internal.util.IndentingPrintWriter; - import java.io.FileDescriptor; import java.io.IOException; -import java.lang.Thread; import java.net.Inet4Address; import java.net.Inet6Address; import java.net.InetAddress; import java.net.SocketException; import java.net.UnknownHostException; -import java.nio.ByteBuffer; import java.nio.BufferUnderflowException; +import java.nio.ByteBuffer; import java.util.ArrayList; import java.util.Arrays; - import libcore.io.IoBridge; /** @@ -215,10 +213,6 @@ public class ApfFilter { { (byte) 0xff, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 }; private static final int ICMP6_TYPE_OFFSET = ETH_HEADER_LEN + IPV6_HEADER_LEN; - private static final int ICMP6_ROUTER_SOLICITATION = 133; - private static final int ICMP6_ROUTER_ADVERTISEMENT = 134; - private static final int ICMP6_NEIGHBOR_SOLICITATION = 135; - private static final int ICMP6_NEIGHBOR_ANNOUNCEMENT = 136; // NOTE: this must be added to the IPv4 header length in IPV4_HEADER_SIZE_MEMORY_SLOT private static final int UDP_DESTINATION_PORT_OFFSET = ETH_HEADER_LEN + 2; @@ -258,9 +252,26 @@ public class ApfFilter { private long mUniqueCounter; @GuardedBy("this") private boolean mMulticastFilter; + @GuardedBy("this") + private boolean mInDozeMode; private final boolean mDrop802_3Frames; private final int[] mEthTypeBlackList; + // Detects doze mode state transitions. + private final BroadcastReceiver mDeviceIdleReceiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + String action = intent.getAction(); + if (action.equals(PowerManager.ACTION_DEVICE_IDLE_MODE_CHANGED)) { + PowerManager powerManager = + (PowerManager) context.getSystemService(Context.POWER_SERVICE); + final boolean deviceIdle = powerManager.isDeviceIdleMode(); + setDozeMode(deviceIdle); + } + } + }; + private final Context mContext; + // Our IPv4 address, if we have just one, otherwise null. @GuardedBy("this") private byte[] mIPv4Address; @@ -269,13 +280,14 @@ public class ApfFilter { private int mIPv4PrefixLength; @VisibleForTesting - ApfFilter(ApfConfiguration config, InterfaceParams ifParams, + ApfFilter(Context context, ApfConfiguration config, InterfaceParams ifParams, IpClient.Callback ipClientCallback, IpConnectivityLog log) { mApfCapabilities = config.apfCapabilities; mIpClientCallback = ipClientCallback; mInterfaceParams = ifParams; mMulticastFilter = config.multicastFilter; mDrop802_3Frames = config.ieee802_3Filter; + mContext = context; // Now fill the black list from the passed array mEthTypeBlackList = filterEthTypeBlackList(config.ethTypeBlackList); @@ -284,6 +296,10 @@ public class ApfFilter { // TODO: ApfFilter should not generate programs until IpClient sends provisioning success. maybeStartFilter(); + + // Listen for doze-mode transition changes to enable/disable the IPv6 multicast filter. + mContext.registerReceiver(mDeviceIdleReceiver, + new IntentFilter(PowerManager.ACTION_DEVICE_IDLE_MODE_CHANGED)); } private void log(String s) { @@ -522,7 +538,7 @@ public class ApfFilter { // to our packet socket. b/29586253 if (getUint16(mPacket, ETH_ETHERTYPE_OFFSET) != ETH_P_IPV6 || getUint8(mPacket, IPV6_NEXT_HEADER_OFFSET) != IPPROTO_ICMPV6 || - getUint8(mPacket, ICMP6_TYPE_OFFSET) != ICMP6_ROUTER_ADVERTISEMENT) { + getUint8(mPacket, ICMP6_TYPE_OFFSET) != ICMPV6_ROUTER_ADVERTISEMENT) { throw new InvalidRaException("Not an ICMP6 router advertisement"); } @@ -889,10 +905,11 @@ public class ApfFilter { private void generateIPv6FilterLocked(ApfGenerator gen) throws IllegalInstructionException { // Here's a basic summary of what the IPv6 filter program does: // - // if it's not ICMPv6: - // if it's multicast and we're dropping multicast: - // drop - // pass + // if we're dropping multicast + // if it's not IPCMv6 or it's ICMPv6 but we're in doze mode: + // if it's multicast: + // drop + // pass // if it's ICMPv6 RS to any: // drop // if it's ICMPv6 NA to ff02::1: @@ -902,28 +919,44 @@ public class ApfFilter { // Drop multicast if the multicast filter is enabled. if (mMulticastFilter) { - // Don't touch ICMPv6 multicast here, we deal with it in more detail later. - String skipIpv6MulticastFilterLabel = "skipIPv6MulticastFilter"; - gen.addJumpIfR0Equals(IPPROTO_ICMPV6, skipIpv6MulticastFilterLabel); + final String skipIPv6MulticastFilterLabel = "skipIPv6MulticastFilter"; + final String dropAllIPv6MulticastsLabel = "dropAllIPv6Multicast"; + + // While in doze mode, drop ICMPv6 multicast pings, let the others pass. + // While awake, let all ICMPv6 multicasts through. + if (mInDozeMode) { + // Not ICMPv6? -> Proceed to multicast filtering + gen.addJumpIfR0NotEquals(IPPROTO_ICMPV6, dropAllIPv6MulticastsLabel); + + // ICMPv6 but not ECHO? -> Skip the multicast filter. + // (ICMPv6 ECHO requests will go through the multicast filter below). + gen.addLoad8(Register.R0, ICMP6_TYPE_OFFSET); + gen.addJumpIfR0NotEquals(ICMPV6_ECHO_REQUEST_TYPE, skipIPv6MulticastFilterLabel); + } else { + gen.addJumpIfR0Equals(IPPROTO_ICMPV6, skipIPv6MulticastFilterLabel); + } - // Drop all other packets sent to ff00::/8. + // Drop all other packets sent to ff00::/8 (multicast prefix). + gen.defineLabel(dropAllIPv6MulticastsLabel); gen.addLoad8(Register.R0, IPV6_DEST_ADDR_OFFSET); gen.addJumpIfR0Equals(0xff, gen.DROP_LABEL); - // Not multicast and not ICMPv6. Pass. + // Not multicast. Pass. gen.addJump(gen.PASS_LABEL); - gen.defineLabel(skipIpv6MulticastFilterLabel); + gen.defineLabel(skipIPv6MulticastFilterLabel); } else { // If not ICMPv6, pass. gen.addJumpIfR0NotEquals(IPPROTO_ICMPV6, gen.PASS_LABEL); } + // If we got this far, the packet is ICMPv6. Drop some specific types. + // Add unsolicited multicast neighbor announcements filter String skipUnsolicitedMulticastNALabel = "skipUnsolicitedMulticastNA"; gen.addLoad8(Register.R0, ICMP6_TYPE_OFFSET); // Drop all router solicitations (b/32833400) - gen.addJumpIfR0Equals(ICMP6_ROUTER_SOLICITATION, gen.DROP_LABEL); + gen.addJumpIfR0Equals(ICMPV6_ROUTER_SOLICITATION, gen.DROP_LABEL); // If not neighbor announcements, skip filter. - gen.addJumpIfR0NotEquals(ICMP6_NEIGHBOR_ANNOUNCEMENT, skipUnsolicitedMulticastNALabel); + gen.addJumpIfR0NotEquals(ICMPV6_NEIGHBOR_ADVERTISEMENT, skipUnsolicitedMulticastNALabel); // If to ff02::1, drop. // TODO: Drop only if they don't contain the address of on-link neighbours. gen.addLoadImmediate(Register.R0, IPV6_DEST_ADDR_OFFSET); @@ -1168,9 +1201,9 @@ public class ApfFilter { * Create an {@link ApfFilter} if {@code apfCapabilities} indicates support for packet * filtering using APF programs. */ - public static ApfFilter maybeCreate(ApfConfiguration config, + public static ApfFilter maybeCreate(Context context, ApfConfiguration config, InterfaceParams ifParams, IpClient.Callback ipClientCallback) { - if (config == null || ifParams == null) return null; + if (context == null || config == null || ifParams == null) return null; ApfCapabilities apfCapabilities = config.apfCapabilities; if (apfCapabilities == null) return null; if (apfCapabilities.apfVersionSupported == 0) return null; @@ -1187,7 +1220,8 @@ public class ApfFilter { Log.e(TAG, "Unsupported APF version: " + apfCapabilities.apfVersionSupported); return null; } - return new ApfFilter(config, ifParams, ipClientCallback, new IpConnectivityLog()); + + return new ApfFilter(context, config, ifParams, ipClientCallback, new IpConnectivityLog()); } public synchronized void shutdown() { @@ -1197,12 +1231,11 @@ public class ApfFilter { mReceiveThread = null; } mRas.clear(); + mContext.unregisterReceiver(mDeviceIdleReceiver); } public synchronized void setMulticastFilter(boolean isEnabled) { - if (mMulticastFilter == isEnabled) { - return; - } + if (mMulticastFilter == isEnabled) return; mMulticastFilter = isEnabled; if (!isEnabled) { mNumProgramUpdatesAllowingMulticast++; @@ -1210,6 +1243,13 @@ public class ApfFilter { installNewProgramLocked(); } + @VisibleForTesting + public synchronized void setDozeMode(boolean isEnabled) { + if (mInDozeMode == isEnabled) return; + mInDozeMode = isEnabled; + installNewProgramLocked(); + } + /** Find the single IPv4 LinkAddress if there is one, otherwise return null. */ private static LinkAddress findIPv4LinkAddress(LinkProperties lp) { LinkAddress ipv4Address = null; diff --git a/android/net/dns/ResolvUtil.java b/android/net/dns/ResolvUtil.java new file mode 100644 index 00000000..97d20f4b --- /dev/null +++ b/android/net/dns/ResolvUtil.java @@ -0,0 +1,65 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package android.net.dns; + +import android.net.Network; +import android.net.NetworkUtils; +import android.system.GaiException; +import android.system.OsConstants; +import android.system.StructAddrinfo; + +import libcore.io.Libcore; + +import java.net.InetAddress; +import java.net.UnknownHostException; + + +/** + * DNS resolution utility class. + * + * @hide + */ +public class ResolvUtil { + // Non-portable DNS resolution flag. + private static final long NETID_USE_LOCAL_NAMESERVERS = 0x80000000L; + + private ResolvUtil() {} + + public static InetAddress[] blockingResolveAllLocally(Network network, String name) + throws UnknownHostException { + final StructAddrinfo hints = new StructAddrinfo(); + // Unnecessary, but expressly no AI_ADDRCONFIG. + hints.ai_flags = 0; + // Fetch all IP addresses at once to minimize re-resolution. + hints.ai_family = OsConstants.AF_UNSPEC; + hints.ai_socktype = OsConstants.SOCK_DGRAM; + + final Network networkForResolv = getNetworkWithUseLocalNameserversFlag(network); + + try { + return Libcore.os.android_getaddrinfo(name, hints, (int) networkForResolv.netId); + } catch (GaiException gai) { + gai.rethrowAsUnknownHostException(name + ": TLS-bypass resolution failed"); + return null; // keep compiler quiet + } + } + + public static Network getNetworkWithUseLocalNameserversFlag(Network network) { + final long netidForResolv = NETID_USE_LOCAL_NAMESERVERS | (long) network.netId; + return new Network((int) netidForResolv); + } +} diff --git a/android/net/http/X509TrustManagerExtensions.java b/android/net/http/X509TrustManagerExtensions.java index e0fa63a5..f9b6dfce 100644 --- a/android/net/http/X509TrustManagerExtensions.java +++ b/android/net/http/X509TrustManagerExtensions.java @@ -21,7 +21,6 @@ import android.security.net.config.UserCertificateSource; import com.android.org.conscrypt.TrustManagerImpl; -import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.security.cert.CertificateException; @@ -133,8 +132,6 @@ public class X509TrustManagerExtensions { /** * Returns {@code true} if the TrustManager uses the same trust configuration for the provided * hostnames. - * - * @hide */ @SystemApi public boolean isSameTrustConfiguration(String hostname1, String hostname2) { diff --git a/android/net/ip/IpClient.java b/android/net/ip/IpClient.java index 9863370e..87249dfc 100644 --- a/android/net/ip/IpClient.java +++ b/android/net/ip/IpClient.java @@ -40,6 +40,7 @@ import android.net.util.MultinetworkPolicyTracker; import android.net.util.NetdService; import android.net.util.NetworkConstants; import android.net.util.SharedLog; +import android.os.ConditionVariable; import android.os.INetworkManagementService; import android.os.Message; import android.os.RemoteException; @@ -150,6 +151,28 @@ public class IpClient extends StateMachine { public void setNeighborDiscoveryOffload(boolean enable) {} } + public static class WaitForProvisioningCallback extends Callback { + private final ConditionVariable mCV = new ConditionVariable(); + private LinkProperties mCallbackLinkProperties; + + public LinkProperties waitForProvisioning() { + mCV.block(); + return mCallbackLinkProperties; + } + + @Override + public void onProvisioningSuccess(LinkProperties newLp) { + mCallbackLinkProperties = newLp; + mCV.open(); + } + + @Override + public void onProvisioningFailure(LinkProperties newLp) { + mCallbackLinkProperties = null; + mCV.open(); + } + } + // Use a wrapper class to log in order to ensure complete and detailed // logging. This method is lighter weight than annotations/reflection // and has the following benefits: @@ -281,6 +304,11 @@ public class IpClient extends StateMachine { return this; } + public Builder withoutMultinetworkPolicyTracker() { + mConfig.mUsingMultinetworkPolicyTracker = false; + return this; + } + public Builder withoutIpReachabilityMonitor() { mConfig.mUsingIpReachabilityMonitor = false; return this; @@ -343,6 +371,7 @@ public class IpClient extends StateMachine { /* package */ boolean mEnableIPv4 = true; /* package */ boolean mEnableIPv6 = true; + /* package */ boolean mUsingMultinetworkPolicyTracker = true; /* package */ boolean mUsingIpReachabilityMonitor = true; /* package */ int mRequestedPreDhcpActionMs; /* package */ InitialConfiguration mInitialConfig; @@ -374,6 +403,7 @@ public class IpClient extends StateMachine { return new StringJoiner(", ", getClass().getSimpleName() + "{", "}") .add("mEnableIPv4: " + mEnableIPv4) .add("mEnableIPv6: " + mEnableIPv6) + .add("mUsingMultinetworkPolicyTracker: " + mUsingMultinetworkPolicyTracker) .add("mUsingIpReachabilityMonitor: " + mUsingIpReachabilityMonitor) .add("mRequestedPreDhcpActionMs: " + mRequestedPreDhcpActionMs) .add("mInitialConfig: " + mInitialConfig) @@ -559,7 +589,6 @@ public class IpClient extends StateMachine { private final NetlinkTracker mNetlinkTracker; private final WakeupMessage mProvisioningTimeoutAlarm; private final WakeupMessage mDhcpActionTimeoutAlarm; - private final MultinetworkPolicyTracker mMultinetworkPolicyTracker; private final SharedLog mLog; private final LocalLog mConnectivityPacketLog; private final MessageHandlingLogger mMsgStateLogger; @@ -573,6 +602,7 @@ public class IpClient extends StateMachine { */ private LinkProperties mLinkProperties; private ProvisioningConfiguration mConfiguration; + private MultinetworkPolicyTracker mMultinetworkPolicyTracker; private IpReachabilityMonitor mIpReachabilityMonitor; private DhcpClient mDhcpClient; private DhcpResults mDhcpResults; @@ -685,9 +715,6 @@ public class IpClient extends StateMachine { mLinkProperties = new LinkProperties(); mLinkProperties.setInterfaceName(mInterfaceName); - mMultinetworkPolicyTracker = new MultinetworkPolicyTracker(mContext, getHandler(), - () -> { mLog.log("OBSERVED AvoidBadWifi changed"); }); - mProvisioningTimeoutAlarm = new WakeupMessage(mContext, getHandler(), mTag + ".EVENT_PROVISIONING_TIMEOUT", EVENT_PROVISIONING_TIMEOUT); mDhcpActionTimeoutAlarm = new WakeupMessage(mContext, getHandler(), @@ -719,8 +746,6 @@ public class IpClient extends StateMachine { } catch (RemoteException e) { logError("Couldn't register NetlinkTracker: %s", e); } - - mMultinetworkPolicyTracker.start(); } private void stopStateMachineUpdaters() { @@ -729,8 +754,6 @@ public class IpClient extends StateMachine { } catch (RemoteException e) { logError("Couldn't unregister NetlinkTracker: %s", e); } - - mMultinetworkPolicyTracker.shutdown(); } @Override @@ -1028,7 +1051,8 @@ public class IpClient extends StateMachine { // Note that we can still be disconnected by IpReachabilityMonitor // if the IPv6 default gateway (but not the IPv6 DNS servers; see // accompanying code in IpReachabilityMonitor) is unreachable. - final boolean ignoreIPv6ProvisioningLoss = !mMultinetworkPolicyTracker.getAvoidBadWifi(); + final boolean ignoreIPv6ProvisioningLoss = (mMultinetworkPolicyTracker != null) + && !mMultinetworkPolicyTracker.getAvoidBadWifi(); // Additionally: // @@ -1490,7 +1514,7 @@ public class IpClient extends StateMachine { mContext.getResources().getBoolean(R.bool.config_apfDrop802_3Frames); apfConfig.ethTypeBlackList = mContext.getResources().getIntArray(R.array.config_apfEthTypeBlackList); - mApfFilter = ApfFilter.maybeCreate(apfConfig, mInterfaceParams, mCallback); + mApfFilter = ApfFilter.maybeCreate(mContext, apfConfig, mInterfaceParams, mCallback); // TODO: investigate the effects of any multicast filtering racing/interfering with the // rest of this IP configuration startup. if (mApfFilter == null) { @@ -1520,6 +1544,13 @@ public class IpClient extends StateMachine { return; } + if (mConfiguration.mUsingMultinetworkPolicyTracker) { + mMultinetworkPolicyTracker = new MultinetworkPolicyTracker( + mContext, getHandler(), + () -> { mLog.log("OBSERVED AvoidBadWifi changed"); }); + mMultinetworkPolicyTracker.start(); + } + if (mConfiguration.mUsingIpReachabilityMonitor && !startIpReachabilityMonitor()) { doImmediateProvisioningFailure( IpManagerEvent.ERROR_STARTING_IPREACHABILITYMONITOR); @@ -1537,6 +1568,11 @@ public class IpClient extends StateMachine { mIpReachabilityMonitor = null; } + if (mMultinetworkPolicyTracker != null) { + mMultinetworkPolicyTracker.shutdown(); + mMultinetworkPolicyTracker = null; + } + if (mDhcpClient != null) { mDhcpClient.sendMessage(DhcpClient.CMD_STOP_DHCP); mDhcpClient.doQuit(); diff --git a/android/net/ip/IpManager.java b/android/net/ip/IpManager.java index 508a43d0..2eb36a22 100644 --- a/android/net/ip/IpManager.java +++ b/android/net/ip/IpManager.java @@ -114,35 +114,6 @@ public class IpManager extends IpClient { public static class Callback extends IpClient.Callback { } - public static class WaitForProvisioningCallback extends Callback { - private LinkProperties mCallbackLinkProperties; - - public LinkProperties waitForProvisioning() { - synchronized (this) { - try { - wait(); - } catch (InterruptedException e) {} - return mCallbackLinkProperties; - } - } - - @Override - public void onProvisioningSuccess(LinkProperties newLp) { - synchronized (this) { - mCallbackLinkProperties = newLp; - notify(); - } - } - - @Override - public void onProvisioningFailure(LinkProperties newLp) { - synchronized (this) { - mCallbackLinkProperties = null; - notify(); - } - } - } - public IpManager(Context context, String ifName, Callback callback) { super(context, ifName, callback); } diff --git a/android/net/metrics/ApfStats.java b/android/net/metrics/ApfStats.java index 3b0dc7ef..76a781dd 100644 --- a/android/net/metrics/ApfStats.java +++ b/android/net/metrics/ApfStats.java @@ -20,7 +20,7 @@ import android.os.Parcel; import android.os.Parcelable; /** - * An event logged for an interface with APF capabilities when its IpManager state machine exits. + * An event logged for an interface with APF capabilities when its IpClient state machine exits. * {@hide} */ public final class ApfStats implements Parcelable { diff --git a/android/net/util/NetworkConstants.java b/android/net/util/NetworkConstants.java index 984c9f81..53fd01f2 100644 --- a/android/net/util/NetworkConstants.java +++ b/android/net/util/NetworkConstants.java @@ -136,6 +136,8 @@ public final class NetworkConstants { * - https://tools.ietf.org/html/rfc4861 */ public static final int ICMPV6_HEADER_MIN_LEN = 4; + public static final int ICMPV6_ECHO_REQUEST_TYPE = 128; + public static final int ICMPV6_ECHO_REPLY_TYPE = 129; public static final int ICMPV6_ROUTER_SOLICITATION = 133; public static final int ICMPV6_ROUTER_ADVERTISEMENT = 134; public static final int ICMPV6_NEIGHBOR_SOLICITATION = 135; @@ -147,7 +149,6 @@ public final class NetworkConstants { public static final int ICMPV6_ND_OPTION_TLLA = 2; public static final int ICMPV6_ND_OPTION_MTU = 5; - public static final int ICMPV6_ECHO_REQUEST_TYPE = 128; /** * UDP constants. diff --git a/android/net/wifi/WifiConfiguration.java b/android/net/wifi/WifiConfiguration.java index b77b1ad5..f6c67c93 100644 --- a/android/net/wifi/WifiConfiguration.java +++ b/android/net/wifi/WifiConfiguration.java @@ -28,10 +28,12 @@ import android.net.Uri; import android.net.wifi.WifiInfo; import android.os.Parcel; import android.os.Parcelable; +import android.os.SystemClock; import android.os.UserHandle; import android.text.TextUtils; import android.util.BackupUtils; import android.util.Log; +import android.util.TimeUtils; import java.io.ByteArrayOutputStream; import java.io.DataInputStream; @@ -611,37 +613,6 @@ public class WifiConfiguration implements Parcelable { /** * @hide - * Last time the system tried to connect and failed. - */ - public long lastConnectionFailure; - - /** - * @hide - * Last time the system tried to roam and failed because of authentication failure or DHCP - * RENEW failure. - */ - public long lastRoamingFailure; - - /** @hide */ - public static int ROAMING_FAILURE_IP_CONFIG = 1; - /** @hide */ - public static int ROAMING_FAILURE_AUTH_FAILURE = 2; - - /** - * @hide - * Initial amount of time this Wifi configuration gets blacklisted for network switching - * because of roaming failure - */ - public long roamingFailureBlackListTimeMilli = 1000; - - /** - * @hide - * Last roaming failure reason code - */ - public int lastRoamingFailureReason; - - /** - * @hide * Last time the system was disconnected to this configuration. */ public long lastDisconnected; @@ -1620,8 +1591,9 @@ public class WifiConfiguration implements Parcelable { } if (mNetworkSelectionStatus.getConnectChoice() != null) { sbuf.append(" connect choice: ").append(mNetworkSelectionStatus.getConnectChoice()); - sbuf.append(" connect choice set time: ").append(mNetworkSelectionStatus - .getConnectChoiceTimestamp()); + sbuf.append(" connect choice set time: ") + .append(TimeUtils.logTimeOfDay( + mNetworkSelectionStatus.getConnectChoiceTimestamp())); } sbuf.append(" hasEverConnected: ") .append(mNetworkSelectionStatus.getHasEverConnected()).append("\n"); @@ -1724,7 +1696,7 @@ public class WifiConfiguration implements Parcelable { sbuf.append(" networkSelectionBSSID=" + mNetworkSelectionStatus.getNetworkSelectionBSSID()); } - long now_ms = System.currentTimeMillis(); + long now_ms = SystemClock.elapsedRealtime(); if (mNetworkSelectionStatus.getDisableTime() != NetworkSelectionStatus .INVALID_NETWORK_SELECTION_DISABLE_TIMESTAMP) { sbuf.append('\n'); @@ -1746,35 +1718,9 @@ public class WifiConfiguration implements Parcelable { if (this.lastConnected != 0) { sbuf.append('\n'); - long diff = now_ms - this.lastConnected; - if (diff <= 0) { - sbuf.append("lastConnected since <incorrect>"); - } else { - sbuf.append("lastConnected: ").append(Long.toString(diff / 1000)).append("sec "); - } - } - if (this.lastConnectionFailure != 0) { - sbuf.append('\n'); - long diff = now_ms - this.lastConnectionFailure; - if (diff <= 0) { - sbuf.append("lastConnectionFailure since <incorrect> "); - } else { - sbuf.append("lastConnectionFailure: ").append(Long.toString(diff / 1000)); - sbuf.append("sec "); - } - } - if (this.lastRoamingFailure != 0) { - sbuf.append('\n'); - long diff = now_ms - this.lastRoamingFailure; - if (diff <= 0) { - sbuf.append("lastRoamingFailure since <incorrect> "); - } else { - sbuf.append("lastRoamingFailure: ").append(Long.toString(diff / 1000)); - sbuf.append("sec "); - } + sbuf.append("lastConnected: ").append(TimeUtils.logTimeOfDay(this.lastConnected)); + sbuf.append(" "); } - sbuf.append("roamingFailureBlackListTimeMilli: "). - append(Long.toString(this.roamingFailureBlackListTimeMilli)); sbuf.append('\n'); if (this.linkedConfigurations != null) { for (String key : this.linkedConfigurations.keySet()) { @@ -2119,10 +2065,6 @@ public class WifiConfiguration implements Parcelable { lastConnected = source.lastConnected; lastDisconnected = source.lastDisconnected; - lastConnectionFailure = source.lastConnectionFailure; - lastRoamingFailure = source.lastRoamingFailure; - lastRoamingFailureReason = source.lastRoamingFailureReason; - roamingFailureBlackListTimeMilli = source.roamingFailureBlackListTimeMilli; numScorerOverride = source.numScorerOverride; numScorerOverrideAndSwitchedNetwork = source.numScorerOverrideAndSwitchedNetwork; numAssociation = source.numAssociation; @@ -2188,10 +2130,6 @@ public class WifiConfiguration implements Parcelable { dest.writeInt(lastUpdateUid); dest.writeString(creatorName); dest.writeString(lastUpdateName); - dest.writeLong(lastConnectionFailure); - dest.writeLong(lastRoamingFailure); - dest.writeInt(lastRoamingFailureReason); - dest.writeLong(roamingFailureBlackListTimeMilli); dest.writeInt(numScorerOverride); dest.writeInt(numScorerOverrideAndSwitchedNetwork); dest.writeInt(numAssociation); @@ -2257,10 +2195,6 @@ public class WifiConfiguration implements Parcelable { config.lastUpdateUid = in.readInt(); config.creatorName = in.readString(); config.lastUpdateName = in.readString(); - config.lastConnectionFailure = in.readLong(); - config.lastRoamingFailure = in.readLong(); - config.lastRoamingFailureReason = in.readInt(); - config.roamingFailureBlackListTimeMilli = in.readLong(); config.numScorerOverride = in.readInt(); config.numScorerOverrideAndSwitchedNetwork = in.readInt(); config.numAssociation = in.readInt(); diff --git a/android/net/wifi/WifiManager.java b/android/net/wifi/WifiManager.java index 433285bf..9c6c8a90 100644 --- a/android/net/wifi/WifiManager.java +++ b/android/net/wifi/WifiManager.java @@ -2141,7 +2141,8 @@ public class WifiManager { } /** - * Sets the Wi-Fi AP Configuration. + * Sets the Wi-Fi AP Configuration. The AP configuration must either be open or + * WPA2 PSK networks. * @return {@code true} if the operation succeeded, {@code false} otherwise * * @hide @@ -2150,8 +2151,7 @@ public class WifiManager { @RequiresPermission(android.Manifest.permission.CHANGE_WIFI_STATE) public boolean setWifiApConfiguration(WifiConfiguration wifiConfig) { try { - mService.setWifiApConfiguration(wifiConfig, mContext.getOpPackageName()); - return true; + return mService.setWifiApConfiguration(wifiConfig, mContext.getOpPackageName()); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } |