am eeb291b7
: am 95e3cba1
: Merge "Reconnect/teardown proxy network connectivity." into klp-modular-dev
* commit 'eeb291b7f36d63c3db467cc7f4be61af09aa3171': Reconnect/teardown proxy network connectivity.
This commit is contained in:
@ -16,13 +16,24 @@
|
|||||||
|
|
||||||
package android.net;
|
package android.net;
|
||||||
|
|
||||||
|
import android.content.BroadcastReceiver;
|
||||||
|
import android.content.ComponentName;
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
|
import android.content.Intent;
|
||||||
|
import android.content.IntentFilter;
|
||||||
|
import android.content.ServiceConnection;
|
||||||
|
import android.os.Bundle;
|
||||||
import android.os.Handler;
|
import android.os.Handler;
|
||||||
|
import android.os.IBinder;
|
||||||
import android.os.Message;
|
import android.os.Message;
|
||||||
|
import android.os.Messenger;
|
||||||
|
import android.os.RemoteException;
|
||||||
|
import android.os.UserHandle;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
|
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
import java.net.UnknownHostException;
|
import java.net.UnknownHostException;
|
||||||
|
import java.util.concurrent.atomic.AtomicBoolean;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -31,27 +42,70 @@ import java.util.concurrent.atomic.AtomicInteger;
|
|||||||
* {@hide}
|
* {@hide}
|
||||||
*/
|
*/
|
||||||
public class ProxyDataTracker extends BaseNetworkStateTracker {
|
public class ProxyDataTracker extends BaseNetworkStateTracker {
|
||||||
private static final String NETWORK_TYPE = "PROXY";
|
|
||||||
private static final String TAG = "ProxyDataTracker";
|
private static final String TAG = "ProxyDataTracker";
|
||||||
|
private static final String NETWORK_TYPE = "PROXY";
|
||||||
|
|
||||||
// TODO: investigate how to get these DNS addresses from the system.
|
// TODO: investigate how to get these DNS addresses from the system.
|
||||||
private static final String DNS1 = "8.8.8.8";
|
private static final String DNS1 = "8.8.8.8";
|
||||||
private static final String DNS2 = "8.8.4.4";
|
private static final String DNS2 = "8.8.4.4";
|
||||||
private static final String REASON_ENABLED = "enabled";
|
private static final String REASON_ENABLED = "enabled";
|
||||||
|
private static final String REASON_DISABLED = "disabled";
|
||||||
|
private static final String REASON_PROXY_DOWN = "proxy_down";
|
||||||
|
|
||||||
|
private static final int MSG_TEAR_DOWN_REQUEST = 1;
|
||||||
|
private static final int MSG_SETUP_REQUEST = 2;
|
||||||
|
|
||||||
|
private static final String PERMISSION_PROXY_STATUS_SENDER =
|
||||||
|
"android.permission.ACCESS_NETWORK_CONDITIONS";
|
||||||
|
private static final String ACTION_PROXY_STATUS_CHANGE =
|
||||||
|
"com.android.net.PROXY_STATUS_CHANGE";
|
||||||
|
private static final String KEY_IS_PROXY_AVAILABLE = "is_proxy_available";
|
||||||
|
private static final String KEY_REPLY_TO_MESSENGER_BINDER = "reply_to_messenger_binder";
|
||||||
|
private static final String KEY_REPLY_TO_MESSENGER_BINDER_BUNDLE =
|
||||||
|
"reply_to_messenger_binder_bundle";
|
||||||
|
|
||||||
|
private Handler mTarget;
|
||||||
|
private Messenger mProxyStatusService;
|
||||||
|
private AtomicBoolean mReconnectRequested = new AtomicBoolean(false);
|
||||||
|
private AtomicBoolean mIsProxyAvailable = new AtomicBoolean(false);
|
||||||
private final AtomicInteger mDefaultGatewayAddr = new AtomicInteger(0);
|
private final AtomicInteger mDefaultGatewayAddr = new AtomicInteger(0);
|
||||||
private final AtomicInteger mReconnectGeneration = new AtomicInteger(0);
|
|
||||||
|
private final BroadcastReceiver mProxyStatusServiceListener = new BroadcastReceiver() {
|
||||||
|
@Override
|
||||||
|
public void onReceive(Context context, Intent intent) {
|
||||||
|
if (intent.getAction().equals(ACTION_PROXY_STATUS_CHANGE)) {
|
||||||
|
mIsProxyAvailable.set(intent.getBooleanExtra(KEY_IS_PROXY_AVAILABLE, false));
|
||||||
|
if (mIsProxyAvailable.get()) {
|
||||||
|
Bundle bundle = intent.getBundleExtra(KEY_REPLY_TO_MESSENGER_BINDER_BUNDLE);
|
||||||
|
if (bundle == null || bundle.getBinder(KEY_REPLY_TO_MESSENGER_BINDER) == null) {
|
||||||
|
Log.e(TAG, "no messenger binder in the intent to send future requests");
|
||||||
|
mIsProxyAvailable.set(false);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
mProxyStatusService =
|
||||||
|
new Messenger(bundle.getBinder(KEY_REPLY_TO_MESSENGER_BINDER));
|
||||||
|
// If there is a pending reconnect request, do it now.
|
||||||
|
if (mReconnectRequested.get()) {
|
||||||
|
reconnect();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
setDetailedState(NetworkInfo.DetailedState.DISCONNECTED,
|
||||||
|
REASON_PROXY_DOWN, null);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
Log.d(TAG, "Unrecognized broadcast intent");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a new ProxyDataTracker
|
* Create a new ProxyDataTracker
|
||||||
*/
|
*/
|
||||||
public ProxyDataTracker() {
|
public ProxyDataTracker() {
|
||||||
mNetworkInfo = new NetworkInfo(ConnectivityManager.TYPE_PROXY, 0, NETWORK_TYPE, "");
|
mNetworkInfo = new NetworkInfo(ConnectivityManager.TYPE_PROXY, 0, NETWORK_TYPE, "");
|
||||||
// TODO: update available state according to proxy state.
|
|
||||||
mNetworkInfo.setIsAvailable(true);
|
|
||||||
mLinkProperties = new LinkProperties();
|
mLinkProperties = new LinkProperties();
|
||||||
mLinkCapabilities = new LinkCapabilities();
|
mLinkCapabilities = new LinkCapabilities();
|
||||||
|
mNetworkInfo.setIsAvailable(true);
|
||||||
try {
|
try {
|
||||||
mLinkProperties.addDns(InetAddress.getByName(DNS1));
|
mLinkProperties.addDns(InetAddress.getByName(DNS1));
|
||||||
mLinkProperties.addDns(InetAddress.getByName(DNS2));
|
mLinkProperties.addDns(InetAddress.getByName(DNS2));
|
||||||
@ -64,11 +118,31 @@ public class ProxyDataTracker extends BaseNetworkStateTracker {
|
|||||||
throw new CloneNotSupportedException();
|
throw new CloneNotSupportedException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void startMonitoring(Context context, Handler target) {
|
||||||
|
mContext = context;
|
||||||
|
mTarget = target;
|
||||||
|
mContext.registerReceiver(mProxyStatusServiceListener,
|
||||||
|
new IntentFilter(ACTION_PROXY_STATUS_CHANGE),
|
||||||
|
PERMISSION_PROXY_STATUS_SENDER,
|
||||||
|
null);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Disable connectivity to the network.
|
* Disable connectivity to the network.
|
||||||
*/
|
*/
|
||||||
public boolean teardown() {
|
public boolean teardown() {
|
||||||
// TODO: tell relevant service to tear down proxy.
|
setTeardownRequested(true);
|
||||||
|
mReconnectRequested.set(false);
|
||||||
|
try {
|
||||||
|
if (mIsProxyAvailable.get() && mProxyStatusService != null) {
|
||||||
|
mProxyStatusService.send(Message.obtain(null, MSG_TEAR_DOWN_REQUEST));
|
||||||
|
}
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
Log.e(TAG, "Unable to connect to proxy status service", e);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
setDetailedState(NetworkInfo.DetailedState.DISCONNECTED, REASON_DISABLED, null);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -76,16 +150,24 @@ public class ProxyDataTracker extends BaseNetworkStateTracker {
|
|||||||
* Re-enable proxy data connectivity after a {@link #teardown()}.
|
* Re-enable proxy data connectivity after a {@link #teardown()}.
|
||||||
*/
|
*/
|
||||||
public boolean reconnect() {
|
public boolean reconnect() {
|
||||||
if (!isAvailable()) {
|
mReconnectRequested.set(true);
|
||||||
Log.w(TAG, "Reconnect requested even though network is disabled. Bailing.");
|
setTeardownRequested(false);
|
||||||
|
if (!mIsProxyAvailable.get()) {
|
||||||
|
Log.w(TAG, "Reconnect requested even though proxy service is not up. Bailing.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
setTeardownRequested(false);
|
setDetailedState(NetworkInfo.DetailedState.CONNECTING, REASON_ENABLED, null);
|
||||||
mReconnectGeneration.incrementAndGet();
|
|
||||||
// TODO: tell relevant service to setup proxy. Set state to connected only if setup
|
|
||||||
// succeeds.
|
|
||||||
setDetailedState(NetworkInfo.DetailedState.CONNECTED, REASON_ENABLED, null);
|
|
||||||
|
|
||||||
|
try {
|
||||||
|
mProxyStatusService.send(Message.obtain(null, MSG_SETUP_REQUEST));
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
Log.e(TAG, "Unable to connect to proxy status service", e);
|
||||||
|
setDetailedState(NetworkInfo.DetailedState.DISCONNECTED, REASON_PROXY_DOWN, null);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
// We'll assume proxy is set up successfully. If not, a status change broadcast will be
|
||||||
|
// received afterwards to indicate any failure.
|
||||||
|
setDetailedState(NetworkInfo.DetailedState.CONNECTED, REASON_ENABLED, null);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -116,7 +198,7 @@ public class ProxyDataTracker extends BaseNetworkStateTracker {
|
|||||||
private void setDetailedState(NetworkInfo.DetailedState state, String reason,
|
private void setDetailedState(NetworkInfo.DetailedState state, String reason,
|
||||||
String extraInfo) {
|
String extraInfo) {
|
||||||
mNetworkInfo.setDetailedState(state, reason, extraInfo);
|
mNetworkInfo.setDetailedState(state, reason, extraInfo);
|
||||||
Message msg = getTargetHandler().obtainMessage(EVENT_STATE_CHANGED, mNetworkInfo);
|
Message msg = mTarget.obtainMessage(EVENT_STATE_CHANGED, mNetworkInfo);
|
||||||
msg.sendToTarget();
|
msg.sendToTarget();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user