Fix crash and duplicated ethernet tethering request

This change fix two things:
1. Handle ethernet callback in internal thread to avoid crash. IpServer
should be created from tethering thread, otherwise mIpNeighborMonitor of
IpServer would throw
   IllegalStateException("start() called from off-thread")
2. Ethernet tethering request may be duplicated if multiple
startTethering is called but no stopTethering

Bug: 130840861
Bug: 148824036
Test: ON/OFF ethernet tehtering manually
      atest TetheringTests

Change-Id: I7c5127e96d80d077735010d2e62c7227805ccb10
This commit is contained in:
markchien
2020-02-26 20:54:55 +08:00
parent a429d3b551
commit 3849d89111
2 changed files with 34 additions and 9 deletions

View File

@@ -220,6 +220,7 @@ public class Tethering {
private final UserRestrictionActionListener mTetheringRestriction;
private final ActiveDataSubIdListener mActiveDataSubIdListener;
private final ConnectedClientsTracker mConnectedClientsTracker;
private final TetheringThreadExecutor mExecutor;
private int mActiveDataSubId = INVALID_SUBSCRIPTION_ID;
// All the usage of mTetheringEventCallback should run in the same thread.
private ITetheringEventCallback mTetheringEventCallback = null;
@@ -296,8 +297,8 @@ public class Tethering {
final UserManager userManager = (UserManager) mContext.getSystemService(
Context.USER_SERVICE);
mTetheringRestriction = new UserRestrictionActionListener(userManager, this);
final TetheringThreadExecutor executor = new TetheringThreadExecutor(mHandler);
mActiveDataSubIdListener = new ActiveDataSubIdListener(executor);
mExecutor = new TetheringThreadExecutor(mHandler);
mActiveDataSubIdListener = new ActiveDataSubIdListener(mExecutor);
// Load tethering configuration.
updateConfiguration();
@@ -315,9 +316,7 @@ public class Tethering {
final WifiManager wifiManager = getWifiManager();
if (wifiManager != null) {
wifiManager.registerSoftApCallback(
mHandler::post /* executor */,
new TetheringSoftApCallback());
wifiManager.registerSoftApCallback(mExecutor, new TetheringSoftApCallback());
}
}
@@ -606,14 +605,17 @@ public class Tethering {
Context.ETHERNET_SERVICE);
synchronized (mPublicSync) {
if (enable) {
if (mEthernetCallback != null) return TETHER_ERROR_NO_ERROR;
mEthernetCallback = new EthernetCallback();
mEthernetIfaceRequest = em.requestTetheredInterface(mEthernetCallback);
mEthernetIfaceRequest = em.requestTetheredInterface(mExecutor, mEthernetCallback);
} else {
if (mConfiguredEthernetIface != null) {
stopEthernetTetheringLocked();
stopEthernetTetheringLocked();
if (mEthernetCallback != null) {
mEthernetIfaceRequest.release();
mEthernetCallback = null;
mEthernetIfaceRequest = null;
}
mEthernetCallback = null;
}
}
return TETHER_ERROR_NO_ERROR;