Android8.0 CtsVerifier Wifi Direct Test

Android8.0 CtsVerifier Wifi Direct Test

在测试8.0 CtsVerifier Wifi Direct Test时,总会测试失败,出现“ the target responder device was not found”的error

CTS的各版本的相关组件,及apk下载路径如下:
https://source.android.com/compatibility/cts/downloads
(ps: 以上链接需要翻墙网才可以打开)

测试办法:
Wifi Direct Test->Go Negotiation Requester/Service Discovery Requester Test->failed

正确的做法如下:
Settings –> Location –> Location status –> Use Wi-Fi estimate location
出现了”No location access”,有两个选项“CLOSE”、“TRUN ON LOCATION”

–>
测试时,要注意:
点击“TRUN ON LOCATION”即可,看到Use Wi-Fi estimate location还是为OFF状态,没关系,不用关注,直接退出,再去启动ctsVerifier.apk,再去测试即可pass
点击”CLOSE”的话,会去设置数据库为0,所以,点击这个是不成功的,测试也会failed


以下是这个测试整个debug过程

In Android8.0, using CtsVerifier.apk of Android 8.0, it version is 26. 
when test Go Negotiation Requester Test-> failed.

And I try test CtsVerifier.apk of Android 6.0, it's version is 23. it is test pass。

In android 8.0,using CtsVerifier.apk of Android 8.0. wifi direct test--> Go Negotiation Test

So, I find the root cause, the analysis is as follows:

1)
CtsVerifier.apk -> RequesterTestActivity.java

 private void searchTarget() {
。。。。。。。

 mTimer.schedule(new TimerTask() {
            @Override
            public void run() {
                mP2pMgr.requestPeers(mChannel, new PeerListListener() { 
                    @Override
                    public void onPeersAvailable(WifiP2pDeviceList _peers) {
                        final WifiP2pDeviceList peers = _peers;
                        /*
                         * Need to show dialog in GUI thread.
                         */
                        mHandler.post(new Runnable() {
                            @Override
                            public void run() {
                                mProgress.setVisibility(ProgressBar.INVISIBLE);
 // get list is null, so it test failed, show " the target responder device was not found"
                                if (peers.getDeviceList().size() == 0) { 
                                    mTextView.setText(
                                            R.string.p2p_target_not_found_error);
                                } else {
                                    showSelectTargetDialog(peers);
                                }
                            }
                        });
                    }
                }); 

。。。。。
 }


 2)
  in WifiP2pServiceImpl.java --> recivce REQUEST_PEERS
 --> getPeers((Bundle) message.obj, message.sendingUid))

 private WifiP2pDeviceList getPeers(Bundle pkg, int uid) {
........
 scanPermission = wifiPermissionsUtil.canAccessScanResults(pkgName, uid, Build.VERSION_CODES.O);
.................
// but this scanPermission is false, mPeers can not set.
// So CtsVerifier.apk get peers is null,it's size is 0, last it is test failed...
      if (scanPermission) { 
                return new WifiP2pDeviceList(mPeers);
            } else {
                return new WifiP2pDeviceList();
            } 
.......
 }

3)
 In  canAccessScanResults() of WifiPermissionsUtil.java

 public boolean canAccessScanResults(String pkgName, int uid,
                int minVersion) throws SecurityException {

            mAppOps.checkPackage(uid, pkgName);
        // Check if the calling Uid has CAN_READ_PEER_MAC_ADDRESS
        // permission or is an Active Nw scorer.
        boolean canCallingUidAccessLocation = checkCallerHasPeersMacAddressPermission(uid)
                || isCallerActiveNwScorer(uid);
        // LocationAccess by App: For AppVersion older than minVersion,
        // it is sufficient to check if the App is foreground.
        // Otherwise, Location Mode must be enabled and caller must have
        // Coarse Location permission to have access to location information.
        boolean canAppPackageUseLocation = isLegacyForeground(pkgName, minVersion)
                || (isLocationModeEnabled(pkgName)
                        && checkCallersLocationPermission(pkgName, uid));
        // If neither caller or app has location access, there is no need to check
        // any other permissions. Deny access to scan results.
            // pkgName=com.android.cts.verifier
            mLog.tC("icecream Denied: pkgName="+pkgName); 
            // uid=10063, minVersion=26
            mLog.tC("icecream Denied: uid="+uid+", minVersion="+minVersion); // false
            mLog.tC("icecream Denied: checkCallerHasPeersMacAddressPermission(uid)="
            +checkCallerHasPeersMacAddressPermission(uid)); // false
            mLog.tC("icecream Denied: isCallerActiveNwScorer(uid)="
            +isCallerActiveNwScorer(uid)); // false
            mLog.tC("icecream Denied: canCallingUidAccessLocation="
            +canCallingUidAccessLocation); // false
            mLog.tC("icecream Denied: isLegacyForeground(pkgName, minVersion)="
            +isLegacyForeground(pkgName, minVersion)); //false
            mLog.tC("icecream Denied: isLocationModeEnabled(pkgName)="
            +isLocationModeEnabled(pkgName)); // false
            mLog.tC("icecream Denied: checkCallersLocationPermission(pkgName, uid)=" 
            +checkCallersLocationPermission(pkgName, uid)); // true
            mLog.tC("icecream Denied: canAppPackageUseLocation="
            +canAppPackageUseLocation); // false
        if (!canCallingUidAccessLocation && !canAppPackageUseLocation) {
            mLog.tC("icecream Denied: no location permission");
            // here, it will return, so scanPermission had set false. 
            return false;
        }
.......
}

 4) I use CtsVerifier.apk of Android 6.0, it can test pass,
 but the CtsVerifier.apk of Android 8.0 is test failed.

 5) I check the isLegacyForeground(), it is

   private boolean isLegacyForeground(String pkgName, int version) {
        return isLegacyVersion(pkgName, version) && isForegroundApp(pkgName);
    }

    I add some log,
    isLegacyVersion(pkgName, version) is false
    isForegroundApp(pkgName) is true.

6) isLegacyVersion

  private boolean isLegacyVersion(String pkgName, int minVersion) {
            mLog.tC("icecream isLegacyVersion---------------- pkgName="+pkgName+",
             minVersion="+minVersion);
        try {
            mLog.tC("icecream isLegacyVersion
            mContext.getPackageManager().getApplicationInfo(pkgName, 0).targetSdkVersion=
            "+mContext.getPackageManager().getApplicationInfo(pkgName, 0).targetSdkVersion); 
            // targetSdkVersion is 26, and minVersion is 26,
            // so it return false. and then test failed,
            // So this is root case for CtsVerifier.apk of Android 6.0 test pass,
            // but Android 8.0 test failed 
            if (mContext.getPackageManager().getApplicationInfo(pkgName, 0)
                    .targetSdkVersion < minVersion) {
                return true;
            }
        } catch (PackageManager.NameNotFoundException e) {
            // In case of exception, assume known app (more strict checking)
            // Note: This case will never happen since checkPackage is
            // called to verify valididity before checking App's version.
        }
        return false;
    }

  7) isLocationModeEnabled(pkgName)
  this function will get database, Settings.Secure.LOCATION_MODE,
  and it's default is Settings.Secure.LOCATION_MODE_OFF,
  So if it is Settings.Secure.LOCATION_MODE_ON, this test will pass.

由以上可以看出,这个测试要pass,满足以下三个条件其中之一就可以了
1) 测试的CtsVerifier.apk版本低于android 8.0,即targetSdkVersion要小于26
2) 测试的CtsVerifier.apk要有android.permission.PEERS_MAC_ADDRESS权限才可以
3) 所测试的平台,要把Settings.Secure.LOCATION_MODE打开,让其设置成Settings.Secure.LOCATION_MODE_ON,而这个可以通过Settings去设置。
办法如下:

Settings –> Location –> Location status –> Use Wi-Fi estimate location
出现了”No location access”,有两个选项“CLOSE”、“TRUN ON LOCATION”

测试时,要注意:
点击“TRUN ON LOCATION”即可,看到Use Wi-Fi estimate location还是为OFF状态,没关系,不用关注,直接退出,再去启动ctsVerifier.apk,再去测试即可
点击”CLOSE”的话,会去设置数据库为0,所以,点击这个是不成功的,测试也会failed

猜你喜欢

转载自blog.csdn.net/gh201030460222/article/details/80559239