Notify IP address changes to interface observers.
1. Add addressUpdated and addressRemoved methods to
INetworkManagementEventObserver. (The -Updated method is not
called -Added because it gets called for both adds and
changes.) Update all its callers in the tree.
2. Make NetworkManagementService parse IP address notifications
from NetlinkHandler and call the address{Removed,Updated} on
its observers.
Bug: 10232006
Change-Id: Ieb185dbba052bdbff03caafc0cf5397a7f04dc6d
diff --git a/core/java/android/net/INetworkManagementEventObserver.aidl b/core/java/android/net/INetworkManagementEventObserver.aidl
index 6f4dd5f..b76e4c2 100644
--- a/core/java/android/net/INetworkManagementEventObserver.aidl
+++ b/core/java/android/net/INetworkManagementEventObserver.aidl
@@ -53,6 +53,27 @@
*/
void interfaceRemoved(String iface);
+
+ /**
+ * An interface address has been added or updated
+ *
+ * @param address The address.
+ * @param iface The interface.
+ * @param flags The address flags.
+ * @param scope The address scope.
+ */
+ void addressUpdated(String address, String iface, int flags, int scope);
+
+ /**
+ * An interface address has been removed
+ *
+ * @param address The address.
+ * @param iface The interface.
+ * @param flags The address flags.
+ * @param scope The address scope.
+ */
+ void addressRemoved(String address, String iface, int flags, int scope);
+
/**
* A networking quota limit has been reached. The quota might not
* be specific to an interface.
diff --git a/core/java/com/android/server/net/BaseNetworkObserver.java b/core/java/com/android/server/net/BaseNetworkObserver.java
index 8b2aa5d..fa54c5f 100644
--- a/core/java/com/android/server/net/BaseNetworkObserver.java
+++ b/core/java/com/android/server/net/BaseNetworkObserver.java
@@ -36,6 +36,16 @@
}
@Override
+ public void addressUpdated(String address, String iface, int flags, int scope) {
+ // default no-op
+ }
+
+ @Override
+ public void addressRemoved(String address, String iface, int flags, int scope) {
+ // default no-op
+ }
+
+ @Override
public void interfaceLinkStateChanged(String iface, boolean up) {
// default no-op
}
diff --git a/services/java/com/android/server/NetworkManagementService.java b/services/java/com/android/server/NetworkManagementService.java
index 988b1f2..16cfa666 100644
--- a/services/java/com/android/server/NetworkManagementService.java
+++ b/services/java/com/android/server/NetworkManagementService.java
@@ -133,6 +133,7 @@
public static final int InterfaceChange = 600;
public static final int BandwidthControl = 601;
public static final int InterfaceClassActivity = 613;
+ public static final int InterfaceAddressChange = 614;
}
/**
@@ -393,6 +394,36 @@
setFirewallEnabled(mFirewallEnabled || LockdownVpnTracker.isEnabled());
}
+ /**
+ * Notify our observers of a new or updated interface address.
+ */
+ private void notifyAddressUpdated(String address, String iface, int flags, int scope) {
+ final int length = mObservers.beginBroadcast();
+ for (int i = 0; i < length; i++) {
+ try {
+ mObservers.getBroadcastItem(i).addressUpdated(address, iface, flags, scope);
+ } catch (RemoteException e) {
+ } catch (RuntimeException e) {
+ }
+ }
+ mObservers.finishBroadcast();
+ }
+
+ /**
+ * Notify our observers of a deleted interface address.
+ */
+ private void notifyAddressRemoved(String address, String iface, int flags, int scope) {
+ final int length = mObservers.beginBroadcast();
+ for (int i = 0; i < length; i++) {
+ try {
+ mObservers.getBroadcastItem(i).addressRemoved(address, iface, flags, scope);
+ } catch (RemoteException e) {
+ } catch (RuntimeException e) {
+ }
+ }
+ mObservers.finishBroadcast();
+ }
+
//
// Netd Callback handling
//
@@ -475,6 +506,32 @@
notifyInterfaceClassActivity(cooked[3], isActive);
return true;
// break;
+ case NetdResponseCode.InterfaceAddressChange:
+ /*
+ * A network address change occurred
+ * Format: "NNN Address updated <addr> <iface> <flags> <scope>"
+ * "NNN Address removed <addr> <iface> <flags> <scope>"
+ */
+ String msg = String.format("Invalid event from daemon (%s)", raw);
+ if (cooked.length < 6 || !cooked[1].equals("Address")) {
+ throw new IllegalStateException(msg);
+ }
+
+ int flags, scope;
+ try {
+ flags = Integer.parseInt(cooked[5]);
+ scope = Integer.parseInt(cooked[6]);
+ } catch(NumberFormatException e) {
+ throw new IllegalStateException(msg);
+ }
+
+ if (cooked[2].equals("updated")) {
+ notifyAddressUpdated(cooked[3], cooked[4], flags, scope);
+ } else {
+ notifyAddressRemoved(cooked[3], cooked[4], flags, scope);
+ }
+ return true;
+ // break;
default: break;
}
return false;
diff --git a/services/java/com/android/server/connectivity/Tethering.java b/services/java/com/android/server/connectivity/Tethering.java
index 22a7841..fb4c1cf 100644
--- a/services/java/com/android/server/connectivity/Tethering.java
+++ b/services/java/com/android/server/connectivity/Tethering.java
@@ -315,6 +315,10 @@
}
}
+ public void addressUpdated(String address, String iface, int flags, int scope) {}
+
+ public void addressRemoved(String address, String iface, int flags, int scope) {}
+
public void limitReached(String limitName, String iface) {}
public void interfaceClassDataActivityChanged(String label, boolean active) {}