1) 添加SSID名称后,WIFI列表仅能连接该设置的SSID AP
2) SSID并启用后,PDA只连接同名SSID的AP,其他连接不上;
3) MAC地址的应用场景和SSID类同,为避免非法AP设置成我们相同的SSID骗取连接,设置MAC
地址或范围并启用后,只有和预置MAC地址匹配的AP才能连接上;
以下就是实现添加SSID和MAC后限制wifi的连接:
package com.android.settings.wifi;
public class WifiSettings extends RestrictedSettingsFragmentimplements DialogInterface.OnClickListener, Indexable, WifiTracker.WifiListener,
AccessPointListener {
//定义访问数据库的一些变量
private static final String AUTHORITY="com.android.setting.wifi.provider.wifissidprovider";
private static final String AUTHORITY_MAC="com.android.setting.wifi.provider.wifimacprovider";
private static final Uri SSID_CONTENT_URI=Uri.parse("content://"+AUTHORITY);
private static final Uri MAC_CONTENT_URI=Uri.parse("content://"+AUTHORITY_MAC);
private List<WifiSsidMac> listSsidMacs;
@Override
public void onCreate(Bundle icicle) {
//初始化list
listSsidMacs=new ArrayList<WifiSettings.WifiSsidMac>();
}
//查询wifi ssid数据
private void getWifiSsidData(){
listSsidMacs.clear();
Cursor cursor = getContentResolver().query(SSID_CONTENT_URI, new String[]{"rowid as _id","name","status"}, null, null, null);
if(cursor!=null){
if(cursor.moveToFirst()){
WifiSsidMac bean=null;
do{
bean=new WifiSsidMac();
bean.setSsidid(cursor.getInt(0));
bean.setName(cursor.getString(1));
bean.setStatus(cursor.getInt(2));
listSsidMacs.add(bean);
} while(cursor.moveToNext());
}
cursor.close();
}
}
//查询wifi mac数据
private void getWifiMacData(){
Cursor cursor = getContentResolver().query(MAC_CONTENT_URI, new String[]{"rowid as _id","name","status"}, null, null, null);
if(cursor!=null){
if(cursor.moveToFirst()){
WifiSsidMac bean=null;
do{
bean=new WifiSsidMac();
bean.setMacid(cursor.getInt(0));
bean.setName(cursor.getString(1));
bean.setStatus(cursor.getInt(2));
listSsidMacs.add(bean);
} while(cursor.moveToNext());
}
cursor.close();
}
}
//声明ssid mac对象
private class WifiSsidMac{
private int ssidid;
private int macid;
private String name;
private int status;
public int getSsidid() {
return ssidid;
}
public void setSsidid(int ssidid) {
this.ssidid = ssidid;
}
public int getMacid() {
return macid;
}
public void setMacid(int macid) {
this.macid = macid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getStatus() {
return status;
}
public void setStatus(int status) {
this.status = status;
}
@Override
public String toString() {
return "WifiSsidMac [ssidid=" + ssidid + ", macid=" + macid + ", name=" + name + ", status=" + status + "]";
}
}
@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
//获取wifi管理器
mWifiTracker =
new WifiTracker(getActivity(), this, mBgThread.getLooper(), true, true, false);
mWifiManager = mWifiTracker.getManager();
。。。
//获取刷新wifi列表
if (intent.hasExtra(EXTRA_START_CONNECT_SSID)) {
onAccessPointsChanged();
}
}
//开始搜索wifi
@Override
public void onResume() {
mWifiTracker.startTracking();
}
//连接wifi
private void accessPointConnect(){
if (mSelectedAccessPoint.isSaved()) {
connect(mSelectedAccessPoint.getConfig());
} else if (mSelectedAccessPoint.getSecurity() == AccessPoint.SECURITY_NONE) {
/** Bypass dialog for unsecured networks */
mSelectedAccessPoint.generateOpenNetworkConfig();
connect(mSelectedAccessPoint.getConfig());
} else {
mDlgModify = false;
showDialog(mSelectedAccessPoint, true);
}
}
@Override
public boolean onContextItemSelected(MenuItem item) {
if (mSelectedAccessPoint == null) {
return super.onContextItemSelected(item);
}
switch (item.getItemId()) {
case MENU_ID_CONNECT: {
if(true){
if(mSelectedAccessPoint.isSsidBinding() ||mSelectedAccessPoint.isMacBinding()){
accessPointConnect();
} else{
Toast.makeText(getActivity(), getString(R.string.wifi_disconnected), Toast.LENGTH_SHORT).show();
}
} else{
accessPointConnect();
}
return true;
}
case MENU_ID_FORGET: {
forget();
return true;
}
}
return super.onContextItemSelected(item);
}
//点击项弹出框做连接操作
@Override
public boolean onPreferenceTreeClick(PreferenceScreen screen, Preference preference) {
if (preference instanceof AccessPointPreference) {
mSelectedAccessPoint = ((AccessPointPreference) preference).getAccessPoint();
if(true){
//如果ssid和mac绑定才可以点击
if(mSelectedAccessPoint.isSsidBinding() || mSelectedAccessPoint.isMacBinding()){
onPreferenceTreeClick();
} else{
Toast.makeText(getActivity(), getString(R.string.wifi_disconnected), Toast.LENGTH_SHORT).show();
}
} else{
onPreferenceTreeClick();
}
} else {
return super.onPreferenceTreeClick(screen, preference);
}
return true;
}
private void onPreferenceTreeClick(){
/** Bypass dialog for unsecured, unsaved, and inactive networks */
if (mSelectedAccessPoint.getSecurity() == AccessPoint.SECURITY_NONE &&
!mSelectedAccessPoint.isSaved() && !mSelectedAccessPoint.isActive()) {
/// M: support open ap wps test @{
if (FeatureOption.MTK_OPEN_AP_WPS_SUPPORT
&& mSelectedAccessPoint.getWpsAvailable()) {
showDialog(mSelectedAccessPoint, false);
} else {
/// @}
mSelectedAccessPoint.generateOpenNetworkConfig();
if (!savedNetworksExist) {
savedNetworksExist = true;
getActivity().invalidateOptionsMenu();
}
connect(mSelectedAccessPoint.getConfig());
}
} else if (mSelectedAccessPoint.isSaved()){
mDlgModify = false;
showDialog(mSelectedAccessPoint, false);
} else {
mDlgModify = false;
showDialog(mSelectedAccessPoint, true);
}
}
private void showDialog(AccessPoint accessPoint, boolean edit) {
if (accessPoint != null) {
WifiConfiguration config = accessPoint.getConfig();
if (isEditabilityLockedDown(getActivity(), config) && accessPoint.isActive()) {
final int userId = UserHandle.getUserId(config.creatorUid);
final PackageManager pm = getActivity().getPackageManager();
final IPackageManager ipm = AppGlobals.getPackageManager();
String appName = pm.getNameForUid(config.creatorUid);
try {
final ApplicationInfo appInfo = ipm.getApplicationInfo(appName, /* flags */ 0,
userId);
final CharSequence label = pm.getApplicationLabel(appInfo);
if (label != null) {
appName = label.toString();
}
} catch (RemoteException e) {
// leave appName as packageName
}
final AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setTitle(accessPoint.getSsid())
.setMessage(getString(R.string.wifi_alert_lockdown_by_device_owner,
appName))
.setPositiveButton(android.R.string.ok, null)
.show();
return;
}
}
if (mDialog != null) {
removeDialog(WIFI_DIALOG_ID);
mDialog = null;
}
// Save the access point and edit mode
mDlgAccessPoint = accessPoint;
mDlgEdit = edit;
showDialog(WIFI_DIALOG_ID);
}
@Override
public Dialog onCreateDialog(int dialogId) {
switch (dialogId) {
case WIFI_DIALOG_ID:
AccessPoint ap = mDlgAccessPoint; // For manual launch
if (ap == null) { // For re-launch from saved state
if (mAccessPointSavedState != null) {
ap = new AccessPoint(getActivity(), mAccessPointSavedState);
// For repeated orientation changes
mDlgAccessPoint = ap;
// Reset the saved access point data
mAccessPointSavedState = null;
}
}
// If it's null, fine, it's for Add Network
mSelectedAccessPoint = ap;
///M: add mtk feature
if (mSelectedAccessPoint != null) {
mWifiSettingsExt.recordPriority(mSelectedAccessPoint.getConfig());
}
final boolean hideForget = (ap == null || isEditabilityLockedDown(getActivity(),
ap.getConfig()));
mDialog = new WifiDialog(getActivity(), this, ap, mDlgEdit,
mDlgModify, /* no hide submit/connect */ false,
/* hide forget if config locked down */ hideForget);
return mDialog;
case WPS_PBC_DIALOG_ID:
return new WpsDialog(getActivity(), WpsInfo.PBC);
case WPS_PIN_DIALOG_ID:
return new WpsDialog(getActivity(), WpsInfo.DISPLAY);
case WRITE_NFC_DIALOG_ID:
if (mSelectedAccessPoint != null) {
mWifiToNfcDialog = new WriteWifiConfigToNfcDialog(
getActivity(), mSelectedAccessPoint.getConfig().networkId,
mSelectedAccessPoint.getSecurity(),
mWifiManager);
} else if (mWifiNfcDialogSavedState != null) {
mWifiToNfcDialog = new WriteWifiConfigToNfcDialog(
getActivity(), mWifiNfcDialogSavedState, mWifiManager);
}
return mWifiToNfcDialog;
}
return super.onCreateDialog(dialogId);
}
/**
* Shows the latest access points available with supplemental information like
* the strength of network and the security for it.
*/
@Override
public void onAccessPointsChanged() {
// Safeguard from some delayed event handling
if (getActivity() == null) return;
if (isUiRestricted()) {
addMessagePreference(R.string.wifi_empty_list_user_restricted);
return;
}
final int wifiState = mWifiManager.getWifiState();
switch (wifiState) {
case WifiManager.WIFI_STATE_ENABLED:
//获取wifi列表
List<ScanResult> listScanResult=null;
if(true){
getWifiSsidData();
getWifiMacData();
listScanResult= mWifiManager.getScanResults();
Log.i("chensenquan", "wifi listSsidMacs count:"+listSsidMacs.size());
Log.i("chensenquan", "wifi listScanResult count:"+listScanResult.size());
}
// AccessPoints are automatically sorted with TreeSet.
final Collection<AccessPoint> accessPoints =
mWifiTracker.getAccessPoints();
//getPreferenceScreen().removeAll();
mWifiSettingsExt.emptyCategory(getPreferenceScreen());
boolean hasAvailableAccessPoints = false;
/// M: add ap to screen @{
Log.d(TAG, "accessPoints.size() = " + accessPoints.size());
int index = 0;
for (AccessPoint accessPoint : accessPoints) {
// Ignore access points that are out of range.
if (accessPoint.getLevel() != -1) {
hasAvailableAccessPoints = true;
if (accessPoint.getTag() != null) {
final Preference pref = (Preference) accessPoint.getTag();
pref.setOrder(index++);
//getPreferenceScreen().addPreference(pref);
mWifiSettingsExt.addPreference(getPreferenceScreen(),
pref, accessPoint.getConfig() != null);
continue;
}
//设置上报的BSSID(mac地址)
//注意:当没有连接wifi时getBSSID()是有值的,连接之后上报的BSSID为空,
所有要通过mWifiManager.getScanResults()获取BSSID来设定accessPoint.setBSSID()
if(true){
for(ScanResult scanResult:listScanResult){
if(scanResult.SSID.equals(accessPoint.getSsid().toString())){
Log.i("chensenquan", "wifi scanResult ssid name:"+scanResult.SSID);
accessPoint.setBSSID(scanResult.BSSID);
}
}
setBindingSSIDMAC(accessPoint);
}
//这个类绑定wifi每项详细信息,利用它来做的连接AccessPointPreference preference = new AccessPointPreference(accessPoint,
getActivity(), mUserBadgeCache, false);
preference.setOrder(index++);
...
}
}
}
}
//绑定SSID和MAC
private void setBindingSSIDMAC(AccessPoint accessPoint){
String mac=accessPoint.getBSSID();
accessPoint.setWifiMacAddress(mac);
Log.i("chensenquan", "wifi mac:"+mac);
for(WifiSsidMac bean:listSsidMacs) {//listSsidMacs是通过添加ssid和mac从数据库中获取到的
//比较相同的ssid来绑定
if(bean.getName().equals(accessPoint.getSsid().toString())){
Log.i("chensenquan", "same wifi ssid:"+bean.getSsidid());
if(bean.getStatus()==1){
Log.i("chensenquan", "binding wifi ssid status:"+bean.getStatus());
accessPoint.setSsidBinding(true);
}
accessPoint.setWifiSsidid(bean.getSsidid());
} else {
if(bean.getName().equals(mac)){
//比较相同的mac来绑定
Log.i("chensenquan", "same wifi macid:"+bean.getMacid());
if(bean.getStatus()==1){
Log.i("chensenquan", "binding wifi mac status:"+bean.getStatus());
accessPoint.setMacBinding(true);
}
accessPoint.setWifiMacid(bean.getMacid());
}
}
}
//如果ssid和mac没有绑定,就端开连接
if(accessPoint.getNetworkInfo()!=null){
boolean isConnected=accessPoint.getNetworkInfo().isConnected();
Log.i("chensenquan", "is connected:"+isConnected);
if(isConnected && !accessPoint.isSsidBinding() && !accessPoint.isMacBinding()){
Log.i("chensenquan", "disConnected");
disconnectWifi(accessPoint);
}
}
}
/**
* 断开当前连接的网络
*/
public void disconnectWifi(AccessPoint accessPoint) {
int netId = accessPoint.getConfig().networkId;
mWifiManager.disableNetwork(netId);
mWifiManager.disconnect();
}
//输入密码后做连接
@Override
public void onClick(DialogInterface dialogInterface, int button) {
if (button == WifiDialog.BUTTON_FORGET && mSelectedAccessPoint != null) {
forget();
} else if (button == WifiDialog.BUTTON_SUBMIT) {
if (mDialog != null) {
submit(mDialog.getController());
}
}
}
/* package */ void submit(WifiConfigController configController) {
final WifiConfiguration config = configController.getConfig();
Log.d(TAG, "submit, config = " + config);
///M: add mtk feature
if (mSelectedAccessPoint != null) {
mWifiSettingsExt.submit(config, mSelectedAccessPoint,
mSelectedAccessPoint.getNetworkInfo() != null ?
mSelectedAccessPoint.getNetworkInfo().getDetailedState() : null);
}
if (config == null) {
if (mSelectedAccessPoint != null
&& mSelectedAccessPoint.isSaved()) {
connect(mSelectedAccessPoint.getConfig());
}
} else if (configController.isModify()) {
mWifiManager.save(config, mSaveListener);
} else {
mWifiManager.save(config, mSaveListener);
if (mSelectedAccessPoint != null) { // Not an "Add network"
connect(config);
}
}
mWifiTracker.resumeScanning();
}
/* package */ void forget() {
MetricsLogger.action(getActivity(), MetricsLogger.ACTION_WIFI_FORGET);
if (!mSelectedAccessPoint.isSaved()) {
if (mSelectedAccessPoint.getNetworkInfo() != null &&
mSelectedAccessPoint.getNetworkInfo().getState() != State.DISCONNECTED) {
// Network is active but has no network ID - must be ephemeral.
mWifiManager.disableEphemeralNetwork(
AccessPoint.convertToQuotedString(mSelectedAccessPoint.getSsidStr()));
} else {
// Should not happen, but a monkey seems to trigger it
Log.e(TAG, "Failed to forget invalid network " + mSelectedAccessPoint.getConfig());
return;
}
} else {
mWifiManager.forget(mSelectedAccessPoint.getConfig().networkId, mForgetListener);
}
mWifiTracker.resumeScanning();
// We need to rename/replace "Next" button in wifi setup context.
changeNextButtonState(false);
/// M: since we lost a configured AP, left ones priority need to be refreshed
mWifiSettingsExt.updatePriority();
}
//连接
protected void connect(final WifiConfiguration config) {
MetricsLogger.action(getActivity(), MetricsLogger.ACTION_WIFI_CONNECT);
mWifiManager.connect(config, mConnectListener);
}
protected void connect(final int networkId) {
MetricsLogger.action(getActivity(), MetricsLogger.ACTION_WIFI_CONNECT);
mWifiManager.connect(networkId, mConnectListener);
}
/**
* Refreshes acccess points and ask Wifi module to scan networks again.
*/
/* package */ void refreshAccessPoints() {
mWifiTracker.resumeScanning();
//getPreferenceScreen().removeAll();
mWifiSettingsExt.emptyCategory(getPreferenceScreen());
}
/**
* Called when "add network" button is pressed.
*/
/* package */ void onAddNetworkPressed() {
MetricsLogger.action(getActivity(), MetricsLogger.ACTION_WIFI_ADD_NETWORK);
// No exact access point is selected.
mSelectedAccessPoint = null;
showDialog(null, true);
}
/* package */ int getAccessPointsCount() {
final boolean wifiIsEnabled = mWifiTracker.isWifiEnabled();
if (wifiIsEnabled) {
return getPreferenceScreen().getPreferenceCount();
} else {
return 0;
}
}
/**
* Requests wifi module to pause wifi scan. May be ignored when the module is disabled.
*/
/* package */ void pauseWifiScan() {
mWifiTracker.pauseScanning();
}
/**
* Requests wifi module to resume wifi scan. May be ignored when the module is disabled.
*/
/* package */ void resumeWifiScan() {
mWifiTracker.resumeScanning();
}
/**
* Called when "add network" button in wifi gprs selected is pressed.
*/
public void addNetworkForSelector() {
MetricsLogger.action(getActivity(), MetricsLogger.ACTION_WIFI_ADD_NETWORK);
// No exact access point is selected.
mSelectedAccessPoint = null;
showDialog(null, true);
}
}
package com.android.settings.wifi;
import com.android.settings.R;
import com.android.settingslib.wifi.AccessPoint;
public class AccessPointPreference extends Preference {
public AccessPointPreference(AccessPoint accessPoint, Context context, UserBadgeCache cache,
boolean forSavedNetworks) {
super(context);
//如果ssid和mac绑定显示其绑定后的图标,加布局显示
setWidgetLayoutResource(R.layout.wifi_binding_image);
}
public AccessPoint getAccessPoint() {
return mAccessPoint;
}
@Override
protected void onBindView(View view) {
super.onBindView(view);
。。。。。。
view.setContentDescription(mContentDescription);
//控制其ssid和mac绑定的图标显示
ImageView iv_mac=(ImageView)view.findViewById(R.id.iv_mac);
ImageView iv_ssid=(ImageView)view.findViewById(R.id.iv_ssid);
if(mAccessPoint.isSsidBinding() && mAccessPoint.isMacBinding()){
iv_ssid.setVisibility(View.VISIBLE);
iv_mac.setVisibility(View.VISIBLE);
} else if(mAccessPoint.isSsidBinding()){
iv_mac.setVisibility(View.GONE);
} else if(mAccessPoint.isMacBinding()){
iv_ssid.setVisibility(View.GONE);
} else{
iv_ssid.setVisibility(View.GONE);
iv_mac.setVisibility(View.GONE);
}
}
。。。。。。
}
位置:MT6750M/frameworks/base/packages/SettingsLib/src/com/android/settingslib/wifi
/*
* Copyright (C) 2015 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.settingslib.wifi;
。。。。。。
import com.android.settingslib.R;
public class AccessPoint implements Comparable<AccessPoint>, Cloneable {
static final String TAG = "SettingsLib.AccessPoint";
。。。。。。
//定义变量
private String ssid;
private String bssid;
private boolean isSsidBinding=false;
private int wifiSsidid;
private boolean isMacBinding=false;
private int wifiMacid;
private String wifiMacAddress;
。。。。。。
public NetworkInfo getNetworkInfo() {
return mNetworkInfo;
}
public int getSecurity() {
return security;
}
public String getSsidStr() {
return ssid;
}
public CharSequence getSsid() {
SpannableString str = new SpannableString(ssid);
str.setSpan(new TtsSpan.VerbatimBuilder(ssid).build(), 0, ssid.length(),
Spannable.SPAN_INCLUSIVE_INCLUSIVE);
return str;
}
//定义绑定时用到的方法
public String getBSSID() {
return bssid;
}
public void setBSSID(String bssid) {
this.bssid=bssid;
}
public boolean isSsidBinding() {
return isSsidBinding;
}
public void setSsidBinding(boolean isSsidBinding) {
this.isSsidBinding = isSsidBinding;
}
public int getWifiSsidid() {
return wifiSsidid;
}
public void setWifiSsidid(int wifiSsidid) {
this.wifiSsidid = wifiSsidid;
}
public boolean isMacBinding() {
return isMacBinding;
}
public void setMacBinding(boolean isMacBinding) {
this.isMacBinding = isMacBinding;
}
public int getWifiMacid() {
return wifiMacid;
}
public void setWifiMacid(int wifiMacid) {
this.wifiMacid = wifiMacid;
}
public String getWifiMacAddress() {
return wifiMacAddress;
}
public void setWifiMacAddress(String wifiMacAddress) {
this.wifiMacAddress = wifiMacAddress;
}
/**
* Generate and save a default wifiConfiguration with common values.
* Can only be called for unsecured networks.
*/
public void generateOpenNetworkConfig() {
if (security != SECURITY_NONE)
throw new IllegalStateException();
if (mConfig != null)
return;
mConfig = new WifiConfiguration();
mConfig.SSID = AccessPoint.convertToQuotedString(ssid);
mConfig.allowedKeyManagement.set(KeyMgmt.NONE);
}
private void initWithScanResult(ScanResult result) {
ssid = result.SSID;
bssid = result.BSSID;
security = getSecurity(result);
/* OPEN AP test support */
mWpsAvailable = security != SECURITY_EAP && result.capabilities.contains("WPS");
if (security == SECURITY_PSK)
pskType = getPskType(result);
mRssi = result.level;
mSeen = result.timestamp;
}
public static String convertToQuotedString(String string) {
return "\"" + string + "\"";
}
private static int getSecurity(ScanResult result) {
///M: add mtk feature@{
int security = AccessPointExt.getSecurity(result);
if (security != -1) {
return security;
}
///@}
if (result.capabilities.contains("WEP")) {
return SECURITY_WEP;
} else if (result.capabilities.contains("PSK")) {
return SECURITY_PSK;
} else if (result.capabilities.contains("EAP")) {
return SECURITY_EAP;
}
return SECURITY_NONE;
}
static int getSecurity(WifiConfiguration config) {
if (config.allowedKeyManagement.get(KeyMgmt.WPA_PSK)) {
return SECURITY_PSK;
}
if (config.allowedKeyManagement.get(KeyMgmt.WPA_EAP) ||
config.allowedKeyManagement.get(KeyMgmt.IEEE8021X)) {
return SECURITY_EAP;
}
///M: add mtk feature@{
int security = AccessPointExt.getSecurity(config);
if (security != -1) {
return security;
}
///@}
return (config.wepKeys[0] != null) ? SECURITY_WEP : SECURITY_NONE;
}
public static String securityToString(int security, int pskType) {
if (security == SECURITY_WEP) {
return "WEP";
} else if (security == SECURITY_PSK) {
if (pskType == PSK_WPA) {
return "WPA";
} else if (pskType == PSK_WPA2) {
return "WPA2";
} else if (pskType == PSK_WPA_WPA2) {
return "WPA_WPA2";
}
return "PSK";
} else if (security == SECURITY_EAP) {
return "EAP";
}
return "NONE";
}
}
AccessPoint的整个类我没有贴完整,这个就是wifi的每项的详细信息都在这个类里面,大家有兴趣可以去看看