Bug 1330836 - Only send 'network config/status changed' events to Gecko if something actually changed r=jchen
MozReview-Commit-ID: CrlRDu8MbhY
--- a/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoNetworkManager.java
+++ b/mobile/android/geckoview/src/main/java/org/mozilla/gecko/GeckoNetworkManager.java
@@ -40,16 +40,19 @@ import android.util.Log;
* Specific mobile subtypes are mapped to general 2G, 3G and 4G buckets.
*
* Logic is implemented as a state machine, so see the transition matrix to figure out what happens when.
* This class depends on access to the context, so only use after GeckoAppShell has been initialized.
*/
public class GeckoNetworkManager extends BroadcastReceiver implements BundleEventListener {
private static final String LOGTAG = "GeckoNetworkManager";
+ // If network configuration and/or status changed, we send details of what changed.
+ // If we received a "check out new network state!" intent from the OS but nothing in it looks
+ // different, we ignore it. See Bug 1330836 for some relevant details.
private static final String LINK_DATA_CHANGED = "changed";
private static GeckoNetworkManager instance;
// We hackishly (yet harmlessly, in this case) keep a Context reference passed in via the start method.
// See context handling notes in handleManagerEvent, and Bug 1277333.
private Context context;
@@ -316,18 +319,19 @@ public class GeckoNetworkManager extends
@WrapForJNI(dispatchTo = "gecko")
private static native void onStatusChanged(String status);
/**
* Send current network state and connection type to whomever is listening.
*/
private void sendNetworkStateToListeners(final Context context) {
- if (currentConnectionType != previousConnectionType ||
- currentConnectionSubtype != previousConnectionSubtype) {
+ final boolean connectionTypeOrSubtypeChanged = currentConnectionType != previousConnectionType ||
+ currentConnectionSubtype != previousConnectionSubtype;
+ if (connectionTypeOrSubtypeChanged) {
previousConnectionType = currentConnectionType;
previousConnectionSubtype = currentConnectionSubtype;
final boolean isWifi = currentConnectionType == ConnectionType.WIFI;
final int gateway = !isWifi ? 0 :
wifiDhcpGatewayAddress(context);
if (GeckoThread.isRunning()) {
@@ -336,30 +340,36 @@ public class GeckoNetworkManager extends
} else {
GeckoThread.queueNativeCall(GeckoNetworkManager.class, "onConnectionChanged",
currentConnectionType.value,
String.class, currentConnectionSubtype.value,
isWifi, gateway);
}
}
- final String status;
+ // If neither network status nor network configuration changed, do nothing.
+ if (currentNetworkStatus == previousNetworkStatus && !connectionTypeOrSubtypeChanged) {
+ return;
+ }
- if (currentNetworkStatus != previousNetworkStatus) {
+ // If network status remains the same, send "changed". Otherwise, send new network status.
+ // See Bug 1330836 for relevant details.
+ final String status;
+ if (currentNetworkStatus == previousNetworkStatus) {
+ status = LINK_DATA_CHANGED;
+ } else {
previousNetworkStatus = currentNetworkStatus;
status = currentNetworkStatus.value;
- } else {
- status = LINK_DATA_CHANGED;
}
if (GeckoThread.isRunning()) {
onStatusChanged(status);
} else {
GeckoThread.queueNativeCall(GeckoNetworkManager.class, "onStatusChanged",
- String.class, status);
+ String.class, status);
}
}
/**
* Stop listening for network state updates.
*/
private static void unregisterBroadcastReceiver(final Context context, final BroadcastReceiver receiver) {
context.unregisterReceiver(receiver);