通过代码分析一下WifiP2p discoverPeers流程:
//packages/modules/Wifi/framework/java/android/net/wifi/p2p/WifiP2pManager.java
public class WifiP2pManager {
@RequiresPermission(allOf = {
android.Manifest.permission.NEARBY_WIFI_DEVICES,
android.Manifest.permission.ACCESS_FINE_LOCATION
}, conditional = true)
public void discoverPeersOnSpecificFrequency(
@NonNull Channel channel, int frequencyMhz, @Nullable ActionListener listener) {
if (!isChannelConstrainedDiscoverySupported()) {
throw new UnsupportedOperationException();
}
checkChannel(channel);
if (frequencyMhz <= 0) {
throw new IllegalArgumentException("This frequency must be a positive value.");
}
Bundle extras = prepareExtrasBundle(channel);
extras.putInt(EXTRA_PARAM_KEY_PEER_DISCOVERY_FREQ, frequencyMhz);
channel.mAsyncChannel.sendMessage(DISCOVER_PEERS, WIFI_P2P_SCAN_SINGLE_FREQ,
channel.putListener(listener), extras); //发送DISCOVER_PEERS消息
}
}
DISCOVER_PEERS消息在ClientHandler的handleMessage方法中处理:
//packages/modules/Wifi/framework/java/android/net/wifi/p2p/WifiP2pServiceImpl .java
public class WifiP2pServiceImpl extends IWifiP2pManager.Stub {
private P2pStateMachine mP2pStateMachine;
private class ClientHandler extends Handler {
ClientHandler(String tag, android.os.Looper looper) {
super(looper);
}
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what) {
case WifiP2pManager.SET_DEVICE_NAME:
case WifiP2pManager.SET_WFD_INFO:
case WifiP2pManager.DISCOVER_PEERS:
case WifiP2pManager.STOP_DISCOVERY:
case WifiP2pManager.CONNECT:
case WifiP2pManager.CANCEL_CONNECT:
case WifiP2pManager.CREATE_GROUP:
case WifiP2pManager.REMOVE_GROUP:
case WifiP2pManager.START_LISTEN:
case WifiP2pManager.STOP_LISTEN:
case WifiP2pManager.SET_CHANNEL:
case WifiP2pManager.START_WPS:
case WifiP2pManager.ADD_LOCAL_SERVICE:
case WifiP2pManager.REMOVE_LOCAL_SERVICE:
case WifiP2pManager.CLEAR_LOCAL_SERVICES:
case WifiP2pManager.DISCOVER_SERVICES:
case WifiP2pManager.ADD_SERVICE_REQUEST:
case WifiP2pManager.REMOVE_SERVICE_REQUEST:
case WifiP2pManager.CLEAR_SERVICE_REQUESTS:
case WifiP2pManager.REQUEST_PEERS:
case WifiP2pManager.REQUEST_CONNECTION_INFO:
case WifiP2pManager.REQUEST_GROUP_INFO:
case WifiP2pManager.DELETE_PERSISTENT_GROUP:
case WifiP2pManager.REQUEST_PERSISTENT_GROUP_INFO:
case WifiP2pManager.FACTORY_RESET:
case WifiP2pManager.SET_ONGOING_PEER_CONFIG:
case WifiP2pManager.REQUEST_ONGOING_PEER_CONFIG:
case WifiP2pManager.REQUEST_P2P_STATE:
case WifiP2pManager.REQUEST_DISCOVERY_STATE:
case WifiP2pManager.REQUEST_NETWORK_INFO:
case WifiP2pManager.UPDATE_CHANNEL_INFO:
case WifiP2pManager.REQUEST_DEVICE_INFO:
case WifiP2pManager.REMOVE_CLIENT:
case WifiP2pManager.ADD_EXTERNAL_APPROVER:
case WifiP2pManager.REMOVE_EXTERNAL_APPROVER:
case WifiP2pManager.SET_CONNECTION_REQUEST_RESULT:
case WifiP2pManager.SET_VENDOR_ELEMENTS:
mP2pStateMachine.sendMessage(Message.obtain(msg)); //调用P2pStateMachine的sendMessage方法
break;
default:
Log.d(TAG, "ClientHandler.handleMessage ignoring msg=" + msg);
break;
}
}
}
}
在WifiP2pServiceImpl内部类P2pStateMachine的processMessage中处理消息:
//packages/modules/Wifi/framework/java/android/net/wifi/p2p/WifiP2pServiceImpl.java
public class WifiP2pServiceImpl extends IWifiP2pManager.Stub {
private WifiP2pNative mWifiNative;
private class P2pStateMachine extends StateMachine {
class P2pEnabledState extends State {
@Override
public boolean processMessage(Message message) {
if (isVerboseLoggingEnabled()) logd(getName() + message.toString());
switch (message.what) {
case WifiP2pManager.DISCOVER_PEERS: {
String packageName = getCallingPkgName(message.sendingUid, message.replyTo);
if (packageName == null) {
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_FAILED,
WifiP2pManager.ERROR);
break;
}
int scanType = message.arg1;
int uid = message.sendingUid;
Bundle extras = (Bundle) message.obj;
int freq = extras.getInt(
WifiP2pManager.EXTRA_PARAM_KEY_PEER_DISCOVERY_FREQ,
WifiP2pManager.WIFI_P2P_SCAN_FREQ_UNSPECIFIED);
boolean hasPermission = false;
if (scanType != WifiP2pManager.WIFI_P2P_SCAN_FULL
&& !isFeatureSupported(WifiP2pManager.FEATURE_FLEXIBLE_DISCOVERY)) {
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_FAILED,
WifiP2pManager.ERROR);
}
if (isPlatformOrTargetSdkLessThanT(packageName, uid)) {
hasPermission = mWifiPermissionsUtil.checkCanAccessWifiDirect(
packageName,
getCallingFeatureId(message.sendingUid, message.replyTo),
uid, true);
} else {
hasPermission = checkNearbyDevicesPermission(uid, packageName,
extras, "DISCOVER_PEERS");
}
if (!hasPermission) {
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_FAILED,
WifiP2pManager.ERROR);
// remain at this state.
break;
}
if (mDiscoveryBlocked) {
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_FAILED,
WifiP2pManager.BUSY);
break;
}
// do not send service discovery request while normal find operation.
// 在正常查找操作时不发送服务发现请求。
clearSupplicantServiceRequest();
Log.e(TAG, "-------discover_peers before p2pFind");
if (p2pFind(scanType, freq, DISCOVER_TIMEOUT_S)) { // 调用p2pFind方法
mWifiP2pMetrics.incrementPeerScans();
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_SUCCEEDED);
sendP2pDiscoveryChangedBroadcast(true);
} else {
replyToMessage(message, WifiP2pManager.DISCOVER_PEERS_FAILED,
WifiP2pManager.ERROR);
}
break;
......
}
return HANDLED;
}
}
......
private boolean p2pFind(@WifiP2pManager.WifiP2pScanType int scanType, int freq,
int timeout) {
if (isFeatureSupported(WifiP2pManager.FEATURE_SET_VENDOR_ELEMENTS)) {
Set<ScanResult.InformationElement> aggregatedVendorElements = new HashSet<>();
mVendorElements.forEach((k, v) -> aggregatedVendorElements.addAll(v));
if (!mWifiNative.setVendorElements(aggregatedVendorElements)) {
Log.w(TAG, "cannot set vendor elements to the native service.");
// Don't block p2p find or it might affect regular P2P functinalities.
mWifiNative.removeVendorElements();
}
}
if (scanType == WifiP2pManager.WIFI_P2P_SCAN_FULL) {
return mWifiNative.p2pFind(timeout); //调用WifiP2pNative的p2pFind方法
} else if (scanType == WifiP2pManager.WIFI_P2P_SCAN_SOCIAL
&& freq == WifiP2pManager.WIFI_P2P_SCAN_FREQ_UNSPECIFIED) {
return mWifiNative.p2pFind(scanType, freq, timeout);
} else if (scanType == WifiP2pManager.WIFI_P2P_SCAN_SINGLE_FREQ
&& freq != WifiP2pManager.WIFI_P2P_SCAN_FREQ_UNSPECIFIED) {
return mWifiNative.p2pFind(scanType, freq, timeout);
}
return false;
}
}
}
调用WifiP2pNative的p2pFind方法:
//packages/modules/Wifi/service/java/com/android/server/wifi/p2p/WifiP2pNative.java
public class WifiP2pNative {
private final SupplicantP2pIfaceHal mSupplicantP2pIfaceHal;
public boolean p2pFind(int timeout) {
return mSupplicantP2pIfaceHal.find(timeout); //调用SupplicantP2pIfaceHal的find方法
}
}
调用SupplicantP2pIfaceHal的find方法:
//packages/modules/Wifi/service/java/com/android/server/wifi/p2p/SupplicantP2pIfaceHal.java
public class SupplicantP2pIfaceHal {
private ISupplicantP2pIfaceHal mP2pIfaceHal;
public boolean find(int timeout) {
synchronized (mLock) {
String methodStr = "find";
if (mP2pIfaceHal == null) {
return handleNullHal(methodStr);
}
return mP2pIfaceHal.find(timeout); //调用ISupplicantP2pIfaceHal 的find方法
}
}
}
调用ISupplicantP2pIfaceHal的find方法,ISupplicantP2pIfaceHal是一个接口,由SupplicantP2pIfaceHalAidlImpl实现:
//packages/modules/Wifi/service/java/com/android/server/wifi/p2p/SupplicantP2pIfaceHalAidlImpl.java
public class SupplicantP2pIfaceHalAidlImpl implements ISupplicantP2pIfaceHal {
private ISupplicantP2pIface mISupplicantP2pIface = null;
public boolean find(int timeout) {
synchronized (mLock) {
if (!checkSupplicantP2pIfaceAndLogFailure("find")) return false;
if (timeout < 0) {
Log.e(TAG, "Invalid timeout value: " + timeout);
return false;
}
SupplicantResult<Void> result = new SupplicantResult("find(" + timeout + ")");
try {
result.setResult(mISupplicantP2pIface.find(timeout)); //调用ISupplicantP2pIface的find方法
} catch (RemoteException e) {
Log.e(TAG, "ISupplicantP2pIface exception: " + e);
supplicantServiceDiedHandler();
}
return result.isSuccess();
}
}
}
调用mISupplicantP2pIface的find方法,ISupplicantP2pIface是一个接口,由HAL层的Supplicant实现,到这就到HAL层了,这里就不再继续分析了。