diff options
author | Erik Kline <ek@google.com> | 2015-05-15 18:49:17 +0900 |
---|---|---|
committer | Erik Kline <ek@google.com> | 2015-05-20 12:08:55 +0900 |
commit | abd3142dcae02026689b939c363329b822b7cc0a (patch) | |
tree | f880c9210be6b53d028608e82562fdda3e0efe99 | |
parent | f357c96273ad8c0f7acc0e15213cced2f0b21883 (diff) | |
download | frameworks_base-abd3142dcae02026689b939c363329b822b7cc0a.zip frameworks_base-abd3142dcae02026689b939c363329b822b7cc0a.tar.gz frameworks_base-abd3142dcae02026689b939c363329b822b7cc0a.tar.bz2 |
Close netlink socket when shutting down IpReachabilityMonitor
This forces the NetlinkSocketObserver thread to exit quickly, rather
than lingering until the next random netlink neighbor multicast message
arrives.
Additionally, add a small unittest to verify that multiple calls to
NetlinkSocket#close() are safe.
Change-Id: I101730fad7eee72f9c6e8a7e7bd10c634f2ceab4
-rw-r--r-- | core/java/android/net/IpReachabilityMonitor.java | 15 | ||||
-rw-r--r-- | core/tests/coretests/src/android/net/netlink/NetlinkSocketTest.java | 23 |
2 files changed, 31 insertions, 7 deletions
diff --git a/core/java/android/net/IpReachabilityMonitor.java b/core/java/android/net/IpReachabilityMonitor.java index add8774..cb8c866 100644 --- a/core/java/android/net/IpReachabilityMonitor.java +++ b/core/java/android/net/IpReachabilityMonitor.java @@ -73,7 +73,8 @@ public class IpReachabilityMonitor { private final Set<InetAddress> mIpWatchList; private int mIpWatchListVersion; private boolean mRunning; - final private Thread mObserverThread; + private final NetlinkSocketObserver mNetlinkSocketObserver; + private final Thread mObserverThread; public IpReachabilityMonitor(String ifName, Callback callback) throws IllegalArgumentException { mInterfaceName = ifName; @@ -88,15 +89,15 @@ public class IpReachabilityMonitor { mIpWatchList = new HashSet<InetAddress>(); mIpWatchListVersion = 0; mRunning = false; - mObserverThread = new Thread(new NetlinkSocketObserver()); + mNetlinkSocketObserver = new NetlinkSocketObserver(); + mObserverThread = new Thread(mNetlinkSocketObserver); mObserverThread.start(); } public void stop() { - synchronized (mLock) { - mRunning = false; - mIpWatchList.clear(); - } + synchronized (mLock) { mRunning = false; } + clearLinkProperties(); + mNetlinkSocketObserver.clearNetlinkSocket(); } // TODO: add a public dump() method that can be called during a bug report. @@ -251,6 +252,7 @@ public class IpReachabilityMonitor { } + // TODO: simply the number of objects by making this extend Thread. private final class NetlinkSocketObserver implements Runnable { private static final String TAG = "NetlinkSocketObserver"; private NetlinkSocket mSocket; @@ -292,7 +294,6 @@ public class IpReachabilityMonitor { if (mSocket != null) { mSocket.close(); } - mSocket = null; } // TODO: Refactor the main loop to recreate the socket upon recoverable errors. diff --git a/core/tests/coretests/src/android/net/netlink/NetlinkSocketTest.java b/core/tests/coretests/src/android/net/netlink/NetlinkSocketTest.java index b32de78..c599fe3 100644 --- a/core/tests/coretests/src/android/net/netlink/NetlinkSocketTest.java +++ b/core/tests/coretests/src/android/net/netlink/NetlinkSocketTest.java @@ -90,4 +90,27 @@ public class NetlinkSocketTest extends TestCase { s.close(); } + + public void testRepeatedCloseCallsAreQuiet() throws Exception { + // Create a working NetlinkSocket. + NetlinkSocket s = new NetlinkSocket(OsConstants.NETLINK_ROUTE); + assertNotNull(s); + s.connectToKernel(); + NetlinkSocketAddress localAddr = s.getLocalAddress(); + assertNotNull(localAddr); + assertEquals(0, localAddr.getGroupsMask()); + assertTrue(0 != localAddr.getPortId()); + // Close once. + s.close(); + // Test that it is closed. + boolean expectedErrorSeen = false; + try { + localAddr = s.getLocalAddress(); + } catch (ErrnoException e) { + expectedErrorSeen = true; + } + assertTrue(expectedErrorSeen); + // Close once more. + s.close(); + } } |