diff options
-rw-r--r-- | src/android/net/ip/IpClient.java | 19 | ||||
-rw-r--r-- | src/android/net/ip/IpClientLinkObserver.java | 39 |
2 files changed, 44 insertions, 14 deletions
diff --git a/src/android/net/ip/IpClient.java b/src/android/net/ip/IpClient.java index 1591f43..c4f46ae 100644 --- a/src/android/net/ip/IpClient.java +++ b/src/android/net/ip/IpClient.java @@ -389,6 +389,9 @@ public class IpClient extends StateMachine { private static final int CMD_COMPLETE_PRECONNECTION = 16; private static final int CMD_UPDATE_L2INFORMATION = 17; + private static final int ARG_LINKPROP_CHANGED_LINKSTATE_DOWN = 0; + private static final int ARG_LINKPROP_CHANGED_LINKSTATE_UP = 1; + // Internal commands to use instead of trying to call transitionTo() inside // a given State's enter() method. Calling transitionTo() from enter/exit // encounters a Log.wtf() that can cause trouble on eng builds. @@ -596,7 +599,9 @@ public class IpClient extends StateMachine { mLinkObserver = new IpClientLinkObserver( mContext, getHandler(), mInterfaceName, - () -> sendMessage(EVENT_NETLINK_LINKPROPERTIES_CHANGED), + (ifaceUp) -> sendMessage(EVENT_NETLINK_LINKPROPERTIES_CHANGED, ifaceUp + ? ARG_LINKPROP_CHANGED_LINKSTATE_UP + : ARG_LINKPROP_CHANGED_LINKSTATE_DOWN), config, mLog) { @Override public void onInterfaceAdded(String iface) { @@ -2053,12 +2058,14 @@ public class IpClient extends StateMachine { case EVENT_NETLINK_LINKPROPERTIES_CHANGED: // EVENT_NETLINK_LINKPROPERTIES_CHANGED message will be received in both of - // provisioning loss and normal user termination case (e.g. turn off wifi or - // switch to another wifi ssid), hence, checking current interface change - // status (down or up) would help distinguish. - final boolean ifUp = (msg.arg1 != 0); + // provisioning loss and normal user termination cases (e.g. turn off wifi or + // switch to another wifi ssid), hence, checking the current interface link + // state (down or up) helps distinguish the two cases: if the link state is + // down, provisioning is only lost because the link is being torn down (for + // example when turning off wifi), so treat it as a normal termination. if (!handleLinkPropertiesUpdate(SEND_CALLBACKS)) { - transitionToStoppingState(ifUp ? DisconnectCode.DC_PROVISIONING_FAIL + final boolean linkStateUp = (msg.arg1 == ARG_LINKPROP_CHANGED_LINKSTATE_UP); + transitionToStoppingState(linkStateUp ? DisconnectCode.DC_PROVISIONING_FAIL : DisconnectCode.DC_NORMAL_TERMINATION); } break; diff --git a/src/android/net/ip/IpClientLinkObserver.java b/src/android/net/ip/IpClientLinkObserver.java index dcbca94..46b3844 100644 --- a/src/android/net/ip/IpClientLinkObserver.java +++ b/src/android/net/ip/IpClientLinkObserver.java @@ -89,8 +89,13 @@ public class IpClientLinkObserver implements NetworkObserver { public interface Callback { /** * Called when some properties of the link were updated. + * + * @param linkState Whether the interface link state is up as per the latest + * {@link #onInterfaceLinkStateChanged(String, boolean)} callback. This + * should only be used for metrics purposes, as it could be inconsistent + * with {@link #getLinkProperties()} in particular. */ - void update(); + void update(boolean linkState); } /** Configuration parameters for IpClientLinkObserver. */ @@ -105,6 +110,7 @@ public class IpClientLinkObserver implements NetworkObserver { private final String mInterfaceName; private final Callback mCallback; private final LinkProperties mLinkProperties; + private boolean mInterfaceLinkState; private DnsServerRepository mDnsServerRepository; private final AlarmManager mAlarmManager; private final Configuration mConfig; @@ -121,6 +127,7 @@ public class IpClientLinkObserver implements NetworkObserver { mLinkProperties = new LinkProperties(); mLinkProperties.setInterfaceName(mInterfaceName); mConfig = config; + mInterfaceLinkState = true; // Assume up by default mDnsServerRepository = new DnsServerRepository(config.minRdnssLifetime); mAlarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE); mNetlinkMonitor = new MyNetlinkMonitor(h, log, mTag); @@ -149,7 +156,15 @@ public class IpClientLinkObserver implements NetworkObserver { // interface-specific messages (e.g., RTM_DELADDR) will not reach us, because the netd // code that parses them will not be able to resolve the ifindex to an interface name. clearLinkProperties(); - mCallback.update(); + mCallback.update(getInterfaceLinkState()); + } + } + + @Override + public void onInterfaceLinkStateChanged(String iface, boolean state) { + if (mInterfaceName.equals(iface)) { + maybeLog("interfaceLinkStateChanged", iface + (state ? " up" : " down")); + setInterfaceLinkState(state); } } @@ -162,7 +177,7 @@ public class IpClientLinkObserver implements NetworkObserver { changed = mLinkProperties.addLinkAddress(address); } if (changed) { - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } } } @@ -176,7 +191,7 @@ public class IpClientLinkObserver implements NetworkObserver { changed = mLinkProperties.removeLinkAddress(address); } if (changed) { - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } } } @@ -190,7 +205,7 @@ public class IpClientLinkObserver implements NetworkObserver { changed = mLinkProperties.addRoute(route); } if (changed) { - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } } } @@ -204,7 +219,7 @@ public class IpClientLinkObserver implements NetworkObserver { changed = mLinkProperties.removeRoute(route); } if (changed) { - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } } } @@ -218,7 +233,7 @@ public class IpClientLinkObserver implements NetworkObserver { synchronized (this) { mDnsServerRepository.setDnsServersOn(mLinkProperties); } - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } } } @@ -243,6 +258,14 @@ public class IpClientLinkObserver implements NetworkObserver { mLinkProperties.setInterfaceName(mInterfaceName); } + private synchronized boolean getInterfaceLinkState() { + return mInterfaceLinkState; + } + + private synchronized void setInterfaceLinkState(boolean state) { + mInterfaceLinkState = state; + } + /** Notifies this object of new interface parameters. */ public void setInterfaceParams(InterfaceParams params) { mNetlinkMonitor.setIfindex(params.index); @@ -355,7 +378,7 @@ public class IpClientLinkObserver implements NetworkObserver { cancelPref64Alarm(); } - mCallback.update(); + mCallback.update(getInterfaceLinkState()); } private void processPref64Option(StructNdOptPref64 opt, final long now) { |