getControllerActivityEnergyInfo() is an @hide API, migrate to getWifiActivityEnergyInfoAsync() which is an @SystemApi. Bug: 145244073 Test: m Development && adb install Development.apk, open Dev Tools app, go to Connectivity page, tap on Link Stats button, ensure link stats printed in text box below. Change-Id: I0a9edfff7d924a31c5a3470a89e03bd161f1a8fb
831 lines
32 KiB
Java
831 lines
32 KiB
Java
/**
|
|
**
|
|
** Copyright 2006, The Android Open Source Project
|
|
**
|
|
** Licensed under the Apache License, Version 2.0 (the "License");
|
|
** you may not use this file except in compliance with the License.
|
|
** You may obtain a copy of the License at
|
|
**
|
|
** http://www.apache.org/licenses/LICENSE-2.0
|
|
**
|
|
** Unless required by applicable law or agreed to in writing, software
|
|
** distributed under the License is distributed on an "AS IS" BASIS,
|
|
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
** See the License for the specific language governing permissions and
|
|
** limitations under the License.
|
|
*/
|
|
|
|
package com.android.development;
|
|
|
|
import android.app.Activity;
|
|
import android.app.AlarmManager;
|
|
import android.app.PendingIntent;
|
|
import android.content.BroadcastReceiver;
|
|
import android.content.Context;
|
|
import android.content.Intent;
|
|
import android.content.IntentFilter;
|
|
import android.content.SharedPreferences;
|
|
import android.content.pm.PackageManager.NameNotFoundException;
|
|
import android.net.ConnectivityManager;
|
|
import android.net.ConnectivityManager.NetworkCallback;
|
|
import android.net.LinkAddress;
|
|
import android.net.LinkProperties;
|
|
import android.net.Network;
|
|
import android.net.NetworkCapabilities;
|
|
import android.net.NetworkRequest;
|
|
import android.net.NetworkUtils;
|
|
import android.net.RouteInfo;
|
|
import android.net.wifi.ScanResult;
|
|
import android.net.wifi.WifiManager;
|
|
import android.os.RemoteException;
|
|
import android.os.Handler;
|
|
import android.os.Message;
|
|
import android.os.IBinder;
|
|
import android.os.INetworkManagementService;
|
|
import android.os.Parcel;
|
|
import android.os.PowerManager;
|
|
import android.os.PowerManager.WakeLock;
|
|
import android.os.ServiceManager;
|
|
import android.os.SystemClock;
|
|
import android.provider.Settings;
|
|
import android.os.Bundle;
|
|
import android.os.connectivity.WifiActivityEnergyInfo;
|
|
import android.text.TextUtils;
|
|
import android.util.Log;
|
|
import android.view.IWindowManager;
|
|
import android.view.View;
|
|
import android.widget.ArrayAdapter;
|
|
import android.widget.Button;
|
|
import android.widget.CheckBox;
|
|
import android.widget.CompoundButton;
|
|
import android.widget.EditText;
|
|
import android.widget.Spinner;
|
|
import android.widget.TextView;
|
|
import android.widget.Toast;
|
|
import android.widget.AdapterView.OnItemSelectedListener;
|
|
|
|
import com.android.internal.telephony.Phone;
|
|
import libcore.io.IoUtils;
|
|
|
|
import java.io.BufferedReader;
|
|
import java.io.FileInputStream;
|
|
import java.io.FileOutputStream;
|
|
import java.io.InputStreamReader;
|
|
import java.io.IOException;
|
|
import java.io.OutputStreamWriter;
|
|
import java.io.PrintWriter;
|
|
import java.net.HttpURLConnection;
|
|
import java.net.InetAddress;
|
|
import java.net.Proxy;
|
|
import java.net.Socket;
|
|
import java.net.URL;
|
|
import java.util.ArrayList;
|
|
import java.util.Enumeration;
|
|
import java.util.List;
|
|
import java.util.Random;
|
|
|
|
import static android.net.ConnectivityManager.CONNECTIVITY_ACTION;
|
|
import static android.net.ConnectivityManager.INET_CONDITION_ACTION;
|
|
import static android.net.NetworkCapabilities.*;
|
|
|
|
public class Connectivity extends Activity {
|
|
private static final String TAG = "DevToolsConnectivity";
|
|
private static final String GET_SCAN_RES = "Get Results";
|
|
private static final String START_SCAN = "Start Scan";
|
|
private static final String PROGRESS_SCAN = "In Progress";
|
|
|
|
private static final long SCAN_CYCLES = 15;
|
|
|
|
private static final int EVENT_TOGGLE_WIFI = 1;
|
|
private static final int EVENT_TOGGLE_SCREEN = 2;
|
|
|
|
private EditText mDCOnDurationEdit;
|
|
private EditText mDCOffDurationEdit;
|
|
private TextView mDCCycleCountView;
|
|
private long mDCOnDuration = 120000;
|
|
private long mDCOffDuration = 120000;
|
|
private int mDCCycleCount = 0;
|
|
|
|
private EditText mSCOnDurationEdit;
|
|
private EditText mSCOffDurationEdit;
|
|
private TextView mSCCycleCountView;
|
|
private long mSCOnDuration = 120000;
|
|
private long mSCOffDuration = 12000;
|
|
private int mSCCycleCount = 0;
|
|
|
|
private boolean mDelayedCycleStarted = false;
|
|
|
|
private Button mScanButton;
|
|
private TextView mScanResults;
|
|
private EditText mScanCyclesEdit;
|
|
private CheckBox mScanDisconnect;
|
|
private long mScanCycles = SCAN_CYCLES;
|
|
private long mScanCur = -1;
|
|
private long mStartTime = -1;
|
|
private long mStopTime;
|
|
private long mTotalScanTime = 0;
|
|
private long mTotalScanCount = 0;
|
|
|
|
private TextView mLinkStatsResults;
|
|
private TextView mHttpRequestResults;
|
|
|
|
private String mTdlsAddr = null;
|
|
|
|
private WifiManager mWm;
|
|
private WifiManager.MulticastLock mWml;
|
|
private PowerManager mPm;
|
|
private ConnectivityManager mCm;
|
|
private INetworkManagementService mNetd;
|
|
|
|
private WifiScanReceiver mScanRecv;
|
|
IntentFilter mIntentFilter;
|
|
|
|
private WakeLock mWakeLock = null;
|
|
private WakeLock mScreenonWakeLock = null;
|
|
|
|
private boolean mScreenOffToggleRunning = false;
|
|
private boolean mScreenOff = false;
|
|
|
|
private static final String CONNECTIVITY_TEST_ALARM =
|
|
"com.android.development.CONNECTIVITY_TEST_ALARM";
|
|
private static final String TEST_ALARM_EXTRA = "CONNECTIVITY_TEST_EXTRA";
|
|
private static final String TEST_ALARM_ON_EXTRA = "CONNECTIVITY_TEST_ON_EXTRA";
|
|
private static final String TEST_ALARM_OFF_EXTRA = "CONNECTIVITY_TEST_OFF_EXTRA";
|
|
private static final String TEST_ALARM_CYCLE_EXTRA = "CONNECTIVITY_TEST_CYCLE_EXTRA";
|
|
private static final String SCREEN_ON = "SCREEN_ON";
|
|
private static final String SCREEN_OFF = "SCREEN_OFF";
|
|
|
|
private static final String NETWORK_CONDITIONS_MEASURED =
|
|
"android.net.conn.NETWORK_CONDITIONS_MEASURED";
|
|
|
|
private void logBroadcast(Intent intent) {
|
|
StringBuilder sb = new StringBuilder();
|
|
Bundle b = intent.getExtras();
|
|
for (String key : b.keySet()) {
|
|
sb.append(String.format(" %s=%s", key, b.get(key)));
|
|
}
|
|
Log.d(TAG, "Got broadcast " + intent.getAction() + " extras:" + sb.toString());
|
|
}
|
|
|
|
public BroadcastReceiver mReceiver = new BroadcastReceiver() {
|
|
public void onReceive(Context context, Intent intent) {
|
|
logBroadcast(intent);
|
|
|
|
if (intent.getAction().equals(CONNECTIVITY_TEST_ALARM)) {
|
|
String extra = (String)intent.getExtra(TEST_ALARM_EXTRA);
|
|
PowerManager pm = (PowerManager)context.getSystemService(Context.POWER_SERVICE);
|
|
Long on = new Long(120000);
|
|
Long off = new Long(120000);
|
|
int cycle = 0;
|
|
try {
|
|
on = Long.parseLong((String)intent.getExtra(TEST_ALARM_ON_EXTRA));
|
|
off = Long.parseLong((String)intent.getExtra(TEST_ALARM_OFF_EXTRA));
|
|
cycle = Integer.parseInt((String)intent.getExtra(TEST_ALARM_CYCLE_EXTRA));
|
|
} catch (Exception e) {}
|
|
|
|
if (extra.equals(SCREEN_ON)) {
|
|
mScreenonWakeLock = mPm.newWakeLock(PowerManager.FULL_WAKE_LOCK |
|
|
PowerManager.ACQUIRE_CAUSES_WAKEUP,
|
|
"ConnectivityTest");
|
|
mScreenonWakeLock.acquire();
|
|
|
|
mSCCycleCount = cycle+1;
|
|
mSCOnDuration = on;
|
|
mSCOffDuration = off;
|
|
mSCCycleCountView.setText(Integer.toString(mSCCycleCount));
|
|
|
|
scheduleAlarm(mSCOnDuration, SCREEN_OFF);
|
|
} else if (extra.equals(SCREEN_OFF)) {
|
|
|
|
mSCCycleCount = cycle;
|
|
mSCOnDuration = on;
|
|
mSCOffDuration = off;
|
|
|
|
mScreenonWakeLock.release();
|
|
mScreenonWakeLock = null;
|
|
scheduleAlarm(mSCOffDuration, SCREEN_ON);
|
|
pm.goToSleep(SystemClock.uptimeMillis());
|
|
}
|
|
}
|
|
}
|
|
};
|
|
|
|
public Handler mHandler2 = new Handler() {
|
|
public void handleMessage(Message msg) {
|
|
switch(msg.what) {
|
|
case EVENT_TOGGLE_WIFI:
|
|
Log.e(TAG, "EVENT_TOGGLE_WIFI");
|
|
if (mDelayedCycleStarted && mWm != null) {
|
|
long delay;
|
|
switch (mWm.getWifiState()) {
|
|
case WifiManager.WIFI_STATE_ENABLED:
|
|
case WifiManager.WIFI_STATE_ENABLING:
|
|
mWm.setWifiEnabled(false);
|
|
delay = mDCOffDuration;
|
|
break;
|
|
default:
|
|
mWm.setWifiEnabled(true);
|
|
delay = mDCOnDuration;
|
|
mDCCycleCount++;
|
|
mDCCycleCountView.setText(Integer.toString(mDCCycleCount));
|
|
}
|
|
sendMessageDelayed(obtainMessage(EVENT_TOGGLE_WIFI),
|
|
delay);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Wifi Scan Listener
|
|
*/
|
|
private class WifiScanReceiver extends BroadcastReceiver {
|
|
@Override
|
|
public void onReceive(Context context, Intent intent) {
|
|
String action = intent.getAction();
|
|
|
|
if (action.equals(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION)) {
|
|
mStopTime = SystemClock.elapsedRealtime();
|
|
if (mStartTime != -1) {
|
|
mTotalScanTime += (mStopTime - mStartTime);
|
|
mStartTime = -1;
|
|
}
|
|
Log.d(TAG, "Scan: READY " + mScanCur);
|
|
mScanResults.setVisibility(View.INVISIBLE);
|
|
|
|
List<ScanResult> wifiScanResults = mWm.getScanResults();
|
|
if (wifiScanResults != null) {
|
|
mTotalScanCount += wifiScanResults.size();
|
|
mScanResults.setText("Current scan = " + Long.toString(wifiScanResults.size()));
|
|
mScanResults.setVisibility(View.VISIBLE);
|
|
Log.d(TAG, "Scan: Results = " + wifiScanResults.size());
|
|
}
|
|
|
|
mScanCur--;
|
|
mScanCyclesEdit.setText(Long.toString(mScanCur));
|
|
if (mScanCur == 0) {
|
|
unregisterReceiver(mScanRecv);
|
|
mScanButton.setText(GET_SCAN_RES);
|
|
mScanResults.setVisibility(View.INVISIBLE);
|
|
} else {
|
|
Log.d(TAG, "Scan: START " + mScanCur);
|
|
mStartTime = SystemClock.elapsedRealtime();
|
|
mWm.startScan();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
private static class DevToolsNetworkCallback extends NetworkCallback {
|
|
private static final String TAG = "DevToolsNetworkCallback";
|
|
|
|
public void onPreCheck(Network network) {
|
|
Log.d(TAG, "onPreCheck: " + network.netId);
|
|
}
|
|
|
|
public void onAvailable(Network network) {
|
|
Log.d(TAG, "onAvailable: " + network.netId);
|
|
}
|
|
|
|
public void onCapabilitiesChanged(Network network, NetworkCapabilities nc) {
|
|
Log.d(TAG, "onCapabilitiesChanged: " + network.netId + " " + nc.toString());
|
|
}
|
|
|
|
public void onLinkPropertiesChanged(Network network, LinkProperties lp) {
|
|
Log.d(TAG, "onLinkPropertiesChanged: " + network.netId + " " + lp.toString());
|
|
}
|
|
|
|
public void onLosing(Network network, int maxMsToLive) {
|
|
Log.d(TAG, "onLosing: " + network.netId + " " + maxMsToLive);
|
|
}
|
|
|
|
public void onLost(Network network) {
|
|
Log.d(TAG, "onLost: " + network.netId);
|
|
}
|
|
}
|
|
private DevToolsNetworkCallback mCallback;
|
|
|
|
private class RequestableNetwork {
|
|
private final NetworkRequest mRequest;
|
|
private final int mRequestButton, mReleaseButton, mProgressBar;
|
|
private NetworkCallback mCallback;
|
|
private Network mNetwork;
|
|
|
|
public RequestableNetwork(NetworkRequest request, int requestButton, int releaseButton,
|
|
int progressBar) {
|
|
mRequest = request;
|
|
mRequestButton = requestButton;
|
|
mReleaseButton = releaseButton;
|
|
mProgressBar = progressBar;
|
|
}
|
|
|
|
public RequestableNetwork(int capability, int requestButton, int releaseButton,
|
|
int progressBar) {
|
|
this(new NetworkRequest.Builder()
|
|
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR)
|
|
.addCapability(capability)
|
|
.build(),
|
|
requestButton, releaseButton, progressBar);
|
|
}
|
|
|
|
public void addOnClickListener() {
|
|
findViewById(mRequestButton).setOnClickListener(
|
|
new View.OnClickListener() { public void onClick(View v) { request(); }});
|
|
findViewById(mReleaseButton).setOnClickListener(
|
|
new View.OnClickListener() { public void onClick(View v) { release(); }});
|
|
}
|
|
|
|
public void setRequested(boolean requested) {
|
|
findViewById(mRequestButton).setEnabled(!requested);
|
|
findViewById(mReleaseButton).setEnabled(requested);
|
|
findViewById(mProgressBar).setVisibility(
|
|
requested ? View.VISIBLE : View.GONE);
|
|
}
|
|
|
|
public void request() {
|
|
if (mCallback == null) {
|
|
mCallback = new NetworkCallback() {
|
|
@Override
|
|
public void onAvailable(Network network) {
|
|
mNetwork = network;
|
|
onHttpRequestResults(null);
|
|
runOnUiThread(() -> findViewById(mProgressBar).setVisibility(View.GONE));
|
|
}
|
|
@Override
|
|
public void onLost(Network network) {
|
|
mNetwork = null;
|
|
onHttpRequestResults(null);
|
|
}
|
|
};
|
|
mCm.requestNetwork(mRequest, mCallback);
|
|
setRequested(true);
|
|
}
|
|
}
|
|
|
|
public void release() {
|
|
if (mCallback != null) {
|
|
mNetwork = null;
|
|
onHttpRequestResults(null);
|
|
mCm.unregisterNetworkCallback(mCallback);
|
|
mCallback = null;
|
|
setRequested(false);
|
|
}
|
|
}
|
|
|
|
public Network getNetwork() {
|
|
return mNetwork;
|
|
}
|
|
}
|
|
|
|
private final ArrayList<RequestableNetwork> mRequestableNetworks = new ArrayList<>();
|
|
private final RequestableNetwork mBoundTestNetwork;
|
|
private boolean mRequestRunning;
|
|
|
|
private void addRequestableNetwork(RequestableNetwork network) {
|
|
mRequestableNetworks.add(network);
|
|
}
|
|
|
|
private void addRequestableNetwork(int capability, int requestButton, int releaseButton,
|
|
int progressBar) {
|
|
mRequestableNetworks.add(new RequestableNetwork(capability, requestButton, releaseButton,
|
|
progressBar));
|
|
}
|
|
|
|
public Connectivity() {
|
|
super();
|
|
addRequestableNetwork(NET_CAPABILITY_MMS, R.id.request_mms, R.id.release_mms,
|
|
R.id.mms_progress);
|
|
addRequestableNetwork(NET_CAPABILITY_SUPL, R.id.request_supl, R.id.release_supl,
|
|
R.id.supl_progress);
|
|
addRequestableNetwork(NET_CAPABILITY_INTERNET, R.id.request_cell, R.id.release_cell,
|
|
R.id.cell_progress);
|
|
|
|
// Make bound requests use cell data.
|
|
mBoundTestNetwork = mRequestableNetworks.get(mRequestableNetworks.size() - 1);
|
|
|
|
NetworkRequest wifiRequest = new NetworkRequest.Builder()
|
|
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
|
.build();
|
|
addRequestableNetwork(new RequestableNetwork(wifiRequest,
|
|
R.id.request_wifi, R.id.release_wifi, R.id.wifi_progress));
|
|
}
|
|
|
|
final NetworkRequest mEmptyRequest = new NetworkRequest.Builder().clearCapabilities().build();
|
|
|
|
@Override
|
|
public void onCreate(Bundle icicle) {
|
|
super.onCreate(icicle);
|
|
|
|
setContentView(R.layout.connectivity);
|
|
|
|
mWm = (WifiManager)getSystemService(Context.WIFI_SERVICE);
|
|
mWml = mWm.createMulticastLock(TAG);
|
|
mWml.setReferenceCounted(false);
|
|
mPm = (PowerManager)getSystemService(Context.POWER_SERVICE);
|
|
mCm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
|
|
IBinder b = ServiceManager.getService(Context.NETWORKMANAGEMENT_SERVICE);
|
|
mNetd = INetworkManagementService.Stub.asInterface(b);
|
|
|
|
findViewById(R.id.enableWifi).setOnClickListener(mClickListener);
|
|
findViewById(R.id.disableWifi).setOnClickListener(mClickListener);
|
|
findViewById(R.id.acquireWifiMulticastLock).setOnClickListener(mClickListener);
|
|
findViewById(R.id.releaseWifiMulticastLock).setOnClickListener(mClickListener);
|
|
findViewById(R.id.releaseWifiMulticastLock).setEnabled(false);
|
|
|
|
findViewById(R.id.startDelayedCycle).setOnClickListener(mClickListener);
|
|
findViewById(R.id.stopDelayedCycle).setOnClickListener(mClickListener);
|
|
mDCOnDurationEdit = (EditText)findViewById(R.id.dc_wifi_on_duration);
|
|
mDCOnDurationEdit.setText(Long.toString(mDCOnDuration));
|
|
mDCOffDurationEdit = (EditText)findViewById(R.id.dc_wifi_off_duration);
|
|
mDCOffDurationEdit.setText(Long.toString(mDCOffDuration));
|
|
mDCCycleCountView = (TextView)findViewById(R.id.dc_wifi_cycles_done);
|
|
mDCCycleCountView.setText(Integer.toString(mDCCycleCount));
|
|
|
|
findViewById(R.id.startScreenCycle).setOnClickListener(mClickListener);
|
|
findViewById(R.id.stopScreenCycle).setOnClickListener(mClickListener);
|
|
mSCOnDurationEdit = (EditText)findViewById(R.id.sc_wifi_on_duration);
|
|
mSCOnDurationEdit.setText(Long.toString(mSCOnDuration));
|
|
mSCOffDurationEdit = (EditText)findViewById(R.id.sc_wifi_off_duration);
|
|
mSCOffDurationEdit.setText(Long.toString(mSCOffDuration));
|
|
mSCCycleCountView = (TextView)findViewById(R.id.sc_wifi_cycles_done);
|
|
mSCCycleCountView.setText(Integer.toString(mSCCycleCount));
|
|
|
|
mScanButton = (Button)findViewById(R.id.startScan);
|
|
mScanButton.setOnClickListener(mClickListener);
|
|
mScanCyclesEdit = (EditText)findViewById(R.id.sc_scan_cycles);
|
|
mScanCyclesEdit.setText(Long.toString(mScanCycles));
|
|
mScanDisconnect = (CheckBox)findViewById(R.id.scanDisconnect);
|
|
mScanDisconnect.setChecked(true);
|
|
mScanResults = (TextView)findViewById(R.id.sc_scan_results);
|
|
mScanResults.setVisibility(View.INVISIBLE);
|
|
|
|
mScanRecv = new WifiScanReceiver();
|
|
mIntentFilter = new IntentFilter();
|
|
mIntentFilter.addAction(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION);
|
|
|
|
findViewById(R.id.startTdls).setOnClickListener(mClickListener);
|
|
findViewById(R.id.stopTdls).setOnClickListener(mClickListener);
|
|
|
|
findViewById(R.id.report_all_bad).setOnClickListener(mClickListener);
|
|
|
|
findViewById(R.id.default_request).setOnClickListener(mClickListener);
|
|
findViewById(R.id.bound_http_request).setOnClickListener(mClickListener);
|
|
findViewById(R.id.bound_socket_request).setOnClickListener(mClickListener);
|
|
|
|
findViewById(R.id.link_stats).setOnClickListener(mClickListener);
|
|
|
|
for (RequestableNetwork network : mRequestableNetworks) {
|
|
network.setRequested(false);
|
|
network.addOnClickListener();
|
|
}
|
|
onHttpRequestResults(null);
|
|
|
|
IntentFilter broadcastFilter = new IntentFilter();
|
|
broadcastFilter.addAction(CONNECTIVITY_ACTION);
|
|
broadcastFilter.addAction(CONNECTIVITY_TEST_ALARM);
|
|
broadcastFilter.addAction(INET_CONDITION_ACTION);
|
|
broadcastFilter.addAction(NETWORK_CONDITIONS_MEASURED);
|
|
|
|
registerReceiver(mReceiver, broadcastFilter);
|
|
|
|
mLinkStatsResults = (TextView)findViewById(R.id.stats);
|
|
mLinkStatsResults.setVisibility(View.VISIBLE);
|
|
|
|
mHttpRequestResults = (TextView)findViewById(R.id.http_response);
|
|
mHttpRequestResults.setVisibility(View.VISIBLE);
|
|
|
|
mCallback = new DevToolsNetworkCallback();
|
|
mCm.registerNetworkCallback(mEmptyRequest, mCallback);
|
|
}
|
|
|
|
@Override
|
|
public void onDestroy() {
|
|
super.onDestroy();
|
|
for (RequestableNetwork network : mRequestableNetworks) {
|
|
network.release();
|
|
}
|
|
mCm.unregisterNetworkCallback(mCallback);
|
|
mCallback = null;
|
|
unregisterReceiver(mReceiver);
|
|
mWml.release();
|
|
}
|
|
|
|
@Override
|
|
public void onResume() {
|
|
super.onResume();
|
|
findViewById(R.id.connectivity_layout).requestFocus();
|
|
}
|
|
|
|
private View.OnClickListener mClickListener = new View.OnClickListener() {
|
|
public void onClick(View v) {
|
|
switch (v.getId()) {
|
|
case R.id.enableWifi:
|
|
mWm.setWifiEnabled(true);
|
|
break;
|
|
case R.id.disableWifi:
|
|
mWm.setWifiEnabled(false);
|
|
break;
|
|
case R.id.acquireWifiMulticastLock:
|
|
case R.id.releaseWifiMulticastLock:
|
|
onWifiMulticastLock(v.getId() == R.id.acquireWifiMulticastLock);
|
|
break;
|
|
case R.id.startDelayedCycle:
|
|
onStartDelayedCycle();
|
|
break;
|
|
case R.id.stopDelayedCycle:
|
|
onStopDelayedCycle();
|
|
break;
|
|
case R.id.startScreenCycle:
|
|
onStartScreenCycle();
|
|
break;
|
|
case R.id.stopScreenCycle:
|
|
onStopScreenCycle();
|
|
break;
|
|
case R.id.startScan:
|
|
onStartScanCycle();
|
|
break;
|
|
case R.id.startTdls:
|
|
onStartTdls();
|
|
break;
|
|
case R.id.stopTdls:
|
|
onStopTdls();
|
|
break;
|
|
case R.id.default_request:
|
|
onHttpRequest(DEFAULT);
|
|
break;
|
|
case R.id.bound_http_request:
|
|
onHttpRequest(HTTPS);
|
|
break;
|
|
case R.id.bound_socket_request:
|
|
onHttpRequest(SOCKET);
|
|
break;
|
|
case R.id.report_all_bad:
|
|
onReportAllBad();
|
|
break;
|
|
case R.id.link_stats:
|
|
onLinkStats();
|
|
break;
|
|
}
|
|
}
|
|
};
|
|
|
|
|
|
private void onStartDelayedCycle() {
|
|
if (!mDelayedCycleStarted) {
|
|
mDelayedCycleStarted = true;
|
|
try {
|
|
mDCOnDuration = Long.parseLong(mDCOnDurationEdit.getText().toString());
|
|
mDCOffDuration = Long.parseLong(mDCOffDurationEdit.getText().toString());
|
|
} catch (Exception e) { };
|
|
mDCCycleCount = 0;
|
|
|
|
mWakeLock = mPm.newWakeLock(PowerManager.FULL_WAKE_LOCK, "ConnectivityTest");
|
|
mWakeLock.acquire();
|
|
mHandler2.sendMessage(mHandler2.obtainMessage(EVENT_TOGGLE_WIFI));
|
|
}
|
|
}
|
|
|
|
private void onStopDelayedCycle() {
|
|
if (mDelayedCycleStarted) {
|
|
mDelayedCycleStarted = false;
|
|
mWakeLock.release();
|
|
mWakeLock = null;
|
|
if(mHandler2.hasMessages(EVENT_TOGGLE_WIFI)) {
|
|
mHandler2.removeMessages(EVENT_TOGGLE_WIFI);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void onStartScreenCycle() {
|
|
try {
|
|
mSCOnDuration = Long.parseLong(mSCOnDurationEdit.getText().toString());
|
|
mSCOffDuration = Long.parseLong(mSCOffDurationEdit.getText().toString());
|
|
} catch (Exception e) { };
|
|
mSCCycleCount = 0;
|
|
|
|
mScreenonWakeLock = mPm.newWakeLock(PowerManager.FULL_WAKE_LOCK,
|
|
"ConnectivityTest");
|
|
mScreenonWakeLock.acquire();
|
|
|
|
scheduleAlarm(10, SCREEN_OFF);
|
|
}
|
|
|
|
private void scheduleAlarm(long delayMs, String eventType) {
|
|
AlarmManager am = (AlarmManager)getSystemService(Context.ALARM_SERVICE);
|
|
Intent i = new Intent(CONNECTIVITY_TEST_ALARM);
|
|
|
|
i.putExtra(TEST_ALARM_EXTRA, eventType);
|
|
i.putExtra(TEST_ALARM_ON_EXTRA, Long.toString(mSCOnDuration));
|
|
i.putExtra(TEST_ALARM_OFF_EXTRA, Long.toString(mSCOffDuration));
|
|
i.putExtra(TEST_ALARM_CYCLE_EXTRA, Integer.toString(mSCCycleCount));
|
|
|
|
PendingIntent p = PendingIntent.getBroadcast(this, 0, i, PendingIntent.FLAG_UPDATE_CURRENT);
|
|
|
|
am.set(AlarmManager.ELAPSED_REALTIME_WAKEUP, SystemClock.elapsedRealtime() + delayMs, p);
|
|
}
|
|
|
|
private void onStopScreenCycle() {
|
|
}
|
|
|
|
private void onReportAllBad() {
|
|
Network[] networks = mCm.getAllNetworks();
|
|
for (Network network : networks) {
|
|
mCm.reportBadNetwork(network);
|
|
}
|
|
}
|
|
|
|
private void onStartScanCycle() {
|
|
if (mScanCur == -1) {
|
|
try {
|
|
mScanCur = Long.parseLong(mScanCyclesEdit.getText().toString());
|
|
mScanCycles = mScanCur;
|
|
} catch (Exception e) { };
|
|
if (mScanCur <= 0) {
|
|
mScanCur = -1;
|
|
mScanCycles = SCAN_CYCLES;
|
|
return;
|
|
}
|
|
}
|
|
if (mScanCur > 0) {
|
|
registerReceiver(mScanRecv, mIntentFilter);
|
|
mScanButton.setText(PROGRESS_SCAN);
|
|
mScanResults.setVisibility(View.INVISIBLE);
|
|
if (mScanDisconnect.isChecked())
|
|
mWm.disconnect();
|
|
mTotalScanTime = 0;
|
|
mTotalScanCount = 0;
|
|
Log.d(TAG, "Scan: START " + mScanCur);
|
|
mStartTime = SystemClock.elapsedRealtime();
|
|
mWm.startScan();
|
|
} else {
|
|
// Show results
|
|
mScanResults.setText("Average Scan Time = " +
|
|
Long.toString(mTotalScanTime / mScanCycles) + " ms ; Average Scan Amount = " +
|
|
Long.toString(mTotalScanCount / mScanCycles));
|
|
mScanResults.setVisibility(View.VISIBLE);
|
|
mScanButton.setText(START_SCAN);
|
|
mScanCur = -1;
|
|
mScanCyclesEdit.setText(Long.toString(mScanCycles));
|
|
if (mScanDisconnect.isChecked())
|
|
mWm.reassociate();
|
|
}
|
|
}
|
|
|
|
private void onStartTdls() {
|
|
mTdlsAddr = ((EditText)findViewById(R.id.sc_ip_mac)).getText().toString();
|
|
Log.d(TAG, "TDLS: START " + mTdlsAddr);
|
|
InetAddress inetAddress = null;
|
|
try {
|
|
inetAddress = InetAddress.getByName(mTdlsAddr);
|
|
mWm.setTdlsEnabled(inetAddress, true);
|
|
} catch (Exception e) {
|
|
mWm.setTdlsEnabledWithMacAddress(mTdlsAddr, true);
|
|
}
|
|
}
|
|
|
|
private void onStopTdls() {
|
|
if (mTdlsAddr == null) return;
|
|
Log.d(TAG, "TDLS: STOP " + mTdlsAddr);
|
|
InetAddress inetAddress = null;
|
|
try {
|
|
inetAddress = InetAddress.getByName(mTdlsAddr);
|
|
mWm.setTdlsEnabled(inetAddress, false);
|
|
} catch (Exception e) {
|
|
mWm.setTdlsEnabledWithMacAddress(mTdlsAddr, false);
|
|
}
|
|
}
|
|
|
|
private void onLinkStats() {
|
|
Log.e(TAG, "LINK STATS: ");
|
|
try {
|
|
mWm.getWifiActivityEnergyInfoAsync(getMainExecutor(), info -> {
|
|
if (info != null) {
|
|
mLinkStatsResults.setText(" power " + info.toString());
|
|
} else {
|
|
mLinkStatsResults.setText(" null! ");
|
|
}
|
|
});
|
|
} catch (Exception e) {
|
|
mLinkStatsResults.setText(" failed! " + e.toString());
|
|
}
|
|
}
|
|
|
|
|
|
private final static int DEFAULT = 0;
|
|
private final static int SOCKET = 1;
|
|
private final static int HTTPS = 2;
|
|
|
|
private void onHttpRequestResults(final String results) {
|
|
runOnUiThread(new Runnable() {
|
|
@Override
|
|
public void run() {
|
|
boolean enabled = !mRequestRunning;
|
|
findViewById(R.id.default_request).setEnabled(enabled);
|
|
|
|
enabled = !mRequestRunning && mBoundTestNetwork.getNetwork() != null;
|
|
findViewById(R.id.bound_http_request).setEnabled(enabled);
|
|
findViewById(R.id.bound_socket_request).setEnabled(enabled);
|
|
|
|
if (!TextUtils.isEmpty(results) || !mRequestRunning) {
|
|
((TextView) findViewById(R.id.http_response)).setText(results);
|
|
}
|
|
}
|
|
});
|
|
}
|
|
|
|
private String doSocketRequest(Network network, String host, String path) throws IOException {
|
|
Socket sock = network.getSocketFactory().createSocket(host, 80);
|
|
try {
|
|
sock.setSoTimeout(5000);
|
|
OutputStreamWriter writer = new OutputStreamWriter(sock.getOutputStream());
|
|
String request = String.format(
|
|
"GET %s HTTP/1.1\nHost: %s\nConnection: close\n\n", path, host);
|
|
writer.write(request);
|
|
writer.flush();
|
|
BufferedReader reader = new BufferedReader(new InputStreamReader(sock.getInputStream()));
|
|
String line = reader.readLine();
|
|
|
|
if (line == null || !line.startsWith("HTTP/1.1 200")) {
|
|
// Error.
|
|
return "Error: " + line;
|
|
}
|
|
|
|
do {
|
|
// Consume headers.
|
|
line = reader.readLine();
|
|
} while (!TextUtils.isEmpty(line));
|
|
|
|
// Return first line of body.
|
|
return reader.readLine();
|
|
} finally {
|
|
if (sock != null) {
|
|
IoUtils.closeQuietly(sock);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void onHttpRequest(final int type) {
|
|
mRequestRunning = true;
|
|
onHttpRequestResults(null);
|
|
|
|
Thread requestThread = new Thread() {
|
|
public void run() {
|
|
final String path = "/ip.js?fmt=text";
|
|
final String randomHost =
|
|
"h" + Integer.toString(new Random().nextInt()) + ".ds.ipv6test.google.com";
|
|
final String fixedHost = "google-ipv6test.appspot.com";
|
|
|
|
Network network = mBoundTestNetwork.getNetwork();
|
|
HttpURLConnection conn = null;
|
|
InputStreamReader in = null;
|
|
|
|
try {
|
|
final URL httpsUrl = new URL("https", fixedHost, path);
|
|
BufferedReader reader;
|
|
|
|
switch (type) {
|
|
case DEFAULT:
|
|
conn = (HttpURLConnection) httpsUrl.openConnection(Proxy.NO_PROXY);
|
|
in = new InputStreamReader(conn.getInputStream());
|
|
reader = new BufferedReader(in);
|
|
onHttpRequestResults(reader.readLine());
|
|
break;
|
|
case SOCKET:
|
|
String response = doSocketRequest(network, randomHost, path);
|
|
onHttpRequestResults(response);
|
|
break;
|
|
case HTTPS:
|
|
conn = (HttpURLConnection) network.openConnection(httpsUrl,
|
|
Proxy.NO_PROXY);
|
|
in = new InputStreamReader(conn.getInputStream());
|
|
reader = new BufferedReader(in);
|
|
onHttpRequestResults(reader.readLine());
|
|
break;
|
|
default:
|
|
throw new IllegalArgumentException("Cannot happen");
|
|
}
|
|
} catch(IOException e) {
|
|
onHttpRequestResults("Error! ");
|
|
} finally {
|
|
mRequestRunning = false;
|
|
if (in != null) IoUtils.closeQuietly(in);
|
|
if (conn != null) conn.disconnect();
|
|
}
|
|
}
|
|
};
|
|
requestThread.start();
|
|
}
|
|
|
|
private void onWifiMulticastLock(boolean enable) {
|
|
Log.d(TAG, (enable ? "Acquiring" : "Releasing") + " wifi multicast lock");
|
|
if (enable) {
|
|
mWml.acquire();
|
|
} else {
|
|
mWml.release();
|
|
}
|
|
findViewById(R.id.acquireWifiMulticastLock).setEnabled(!enable);
|
|
findViewById(R.id.releaseWifiMulticastLock).setEnabled(enable);
|
|
}
|
|
}
|