Initialize TetheringManager lazily
Many applications use ConnectivityManager without needing
TetheringManager (or without calling legacy ConnectivityManager methods
that delegate to TetheringManager), so initializing TetheringManager
when ConnectivityManager is created wastes resources.
This is especially true considering that TetheringManager is not trivial
to initialize (worst case scenario it starts a thread and does multiple
Binder requests), and ConnectivityManager is created in ActivityThread
when setting up the app proxy on startup.
Bug: 190556328
Test: atest FrameworksNetTests CtsNetTestCases TetheringTests
Original-Change: https://android-review.googlesource.com/1736505
Merged-In: I2ba7b8f2b9e1c934cfb082776b8d643f2f2c17e5
Change-Id: I2ba7b8f2b9e1c934cfb082776b8d643f2f2c17e5
diff --git a/framework/src/android/net/ConnectivityManager.java b/framework/src/android/net/ConnectivityManager.java
index a3fc621..e496966 100644
--- a/framework/src/android/net/ConnectivityManager.java
+++ b/framework/src/android/net/ConnectivityManager.java
@@ -936,7 +936,17 @@
private final Context mContext;
- private final TetheringManager mTetheringManager;
+ @GuardedBy("mTetheringEventCallbacks")
+ private TetheringManager mTetheringManager;
+
+ private TetheringManager getTetheringManager() {
+ synchronized (mTetheringEventCallbacks) {
+ if (mTetheringManager == null) {
+ mTetheringManager = mContext.getSystemService(TetheringManager.class);
+ }
+ return mTetheringManager;
+ }
+ }
/**
* Tests if a given integer represents a valid network type.
@@ -2395,7 +2405,6 @@
public ConnectivityManager(Context context, IConnectivityManager service) {
mContext = Objects.requireNonNull(context, "missing context");
mService = Objects.requireNonNull(service, "missing IConnectivityManager");
- mTetheringManager = (TetheringManager) mContext.getSystemService(Context.TETHERING_SERVICE);
sInstance = this;
}
@@ -2466,7 +2475,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetherableIfaces() {
- return mTetheringManager.getTetherableIfaces();
+ return getTetheringManager().getTetherableIfaces();
}
/**
@@ -2481,7 +2490,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetheredIfaces() {
- return mTetheringManager.getTetheredIfaces();
+ return getTetheringManager().getTetheredIfaces();
}
/**
@@ -2502,7 +2511,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetheringErroredIfaces() {
- return mTetheringManager.getTetheringErroredIfaces();
+ return getTetheringManager().getTetheringErroredIfaces();
}
/**
@@ -2546,7 +2555,7 @@
@UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
@Deprecated
public int tether(String iface) {
- return mTetheringManager.tether(iface);
+ return getTetheringManager().tether(iface);
}
/**
@@ -2570,7 +2579,7 @@
@UnsupportedAppUsage
@Deprecated
public int untether(String iface) {
- return mTetheringManager.untether(iface);
+ return getTetheringManager().untether(iface);
}
/**
@@ -2596,7 +2605,7 @@
@RequiresPermission(anyOf = {android.Manifest.permission.TETHER_PRIVILEGED,
android.Manifest.permission.WRITE_SETTINGS})
public boolean isTetheringSupported() {
- return mTetheringManager.isTetheringSupported();
+ return getTetheringManager().isTetheringSupported();
}
/**
@@ -2689,7 +2698,7 @@
final TetheringRequest request = new TetheringRequest.Builder(type)
.setShouldShowEntitlementUi(showProvisioningUi).build();
- mTetheringManager.startTethering(request, executor, tetheringCallback);
+ getTetheringManager().startTethering(request, executor, tetheringCallback);
}
/**
@@ -2708,7 +2717,7 @@
@Deprecated
@RequiresPermission(android.Manifest.permission.TETHER_PRIVILEGED)
public void stopTethering(int type) {
- mTetheringManager.stopTethering(type);
+ getTetheringManager().stopTethering(type);
}
/**
@@ -2766,7 +2775,7 @@
synchronized (mTetheringEventCallbacks) {
mTetheringEventCallbacks.put(callback, tetherCallback);
- mTetheringManager.registerTetheringEventCallback(executor, tetherCallback);
+ getTetheringManager().registerTetheringEventCallback(executor, tetherCallback);
}
}
@@ -2788,7 +2797,7 @@
synchronized (mTetheringEventCallbacks) {
final TetheringEventCallback tetherCallback =
mTetheringEventCallbacks.remove(callback);
- mTetheringManager.unregisterTetheringEventCallback(tetherCallback);
+ getTetheringManager().unregisterTetheringEventCallback(tetherCallback);
}
}
@@ -2808,7 +2817,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetherableUsbRegexs() {
- return mTetheringManager.getTetherableUsbRegexs();
+ return getTetheringManager().getTetherableUsbRegexs();
}
/**
@@ -2826,7 +2835,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetherableWifiRegexs() {
- return mTetheringManager.getTetherableWifiRegexs();
+ return getTetheringManager().getTetherableWifiRegexs();
}
/**
@@ -2845,7 +2854,7 @@
@UnsupportedAppUsage
@Deprecated
public String[] getTetherableBluetoothRegexs() {
- return mTetheringManager.getTetherableBluetoothRegexs();
+ return getTetheringManager().getTetherableBluetoothRegexs();
}
/**
@@ -2869,7 +2878,7 @@
@UnsupportedAppUsage
@Deprecated
public int setUsbTethering(boolean enable) {
- return mTetheringManager.setUsbTethering(enable);
+ return getTetheringManager().setUsbTethering(enable);
}
/**
@@ -2985,7 +2994,7 @@
@UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
@Deprecated
public int getLastTetherError(String iface) {
- int error = mTetheringManager.getLastTetherError(iface);
+ int error = getTetheringManager().getLastTetherError(iface);
if (error == TetheringManager.TETHER_ERROR_UNKNOWN_TYPE) {
// TETHER_ERROR_UNKNOWN_TYPE was introduced with TetheringManager and has never been
// returned by ConnectivityManager. Convert it to the legacy TETHER_ERROR_UNKNOWN_IFACE
@@ -3067,7 +3076,7 @@
}
};
- mTetheringManager.requestLatestTetheringEntitlementResult(type, wrappedListener,
+ getTetheringManager().requestLatestTetheringEntitlementResult(type, wrappedListener,
showEntitlementUi);
}
@@ -4849,7 +4858,7 @@
public void factoryReset() {
try {
mService.factoryReset();
- mTetheringManager.stopAllTethering();
+ getTetheringManager().stopAllTethering();
} catch (RemoteException e) {
throw e.rethrowFromSystemServer();
}