第三方安装的应用全部自动允许授权权限:

Q以下(可能也包括R)

方法一:

所有第三方应用给权限

frameworks/base/services/core/java/com/android/server/pm/PackageManagerService.java

在void doHandleMessage(Message msg) {

有个case

case POST_INSTALL: {

有个布尔值

final boolean grantPermissions = (args.installFlags

                                & PackageManager.INSTALL_GRANT_RUNTIME_PERMISSIONS) != 0;

改成true即可,

因为这个布尔值会传到handlePackagePostInstall这个方法里,以及final String[] grantedPermissions = args.installGrantPermissions;权限集合也会传进去

而s版本就没有这俩参数

然后方法里执行授予权限

if (grantPermissions) {

                final int callingUid = Binder.getCallingUid();

                mPermissionManager.grantRequestedRuntimePermissions(

                        res.pkg, res.newUsers, grantedPermissions, callingUid,

                        mPermissionCallback);

            }

S版本:

方法一:S上装完新应用第一次打开会进入所有请求权限的界面(如果权限比较多的都会进入一次性界面),只需要自动确认就可以,这样只是表面上改了,数据清掉重新打开还是没有,而且可能也不在一次性界面,需要与方法二 一起使用 ,优先使用方法二,不行再加上这个

vendor/mediatek/proprietary/packages/apps/PermissionController/src/com/android/permissioncontroller/permission/ui/handheld/ReviewPermissionsFragment.java

onCreate里

遍历权限

for (AppPermissionGroup group : mAppPermissions.getPermissionGroups()) {

            if (group.isReviewRequired() || (group.getBackgroundPermissions() != null

                    && group.getBackgroundPermissions().isReviewRequired())) {

之后加入

CtaManager manager = CtaManagerFactory.getInstance().makeCtaManager();

                    if (manager.isCtaSupported()) {

                            confirmPermissionsReviewforCTA();

                            SharedPreferences reviewConfirmSharedPreferences

                                    = getContext().getSharedPreferences("reviewConfirm", Context.MODE_PRIVATE);

                            String pkgName = reviewConfirmSharedPreferences.getString("package", "");



                            if (pkgName.equals("") || !pkgName.contains(packageInfo.packageName)) {

                                    String pkgNames = pkgName + packageInfo.packageName + ",";



                                    Log.d(LOG_TAG, "pkgNames: " + pkgNames);

                                    SharedPreferences.Editor editor = reviewConfirmSharedPreferences.edit();

                                    editor.putString("package", pkgNames);

                                    editor.commit();

                            }

                    } else {

                            confirmPermissionsReview();

                    }

                    executeCallback(true);

                    activity.finish();

注意!这个方法必须结合下面的方法二,才会走ReviewPermissionsActivity.java那不然就是单次授权GrantPermissionsActivity.java,主要是要把

mPackageManager.grantRuntimePermission(packageName,

                            permission, Process.myUserHandle());

这个异常抛出来就行,估计是如果要走ReviewPermissionsActivity,需要赋予什么权限才可以吧,然后这个权限是可以直接grantRuntimePermission,不会报异常

这个逻辑其实就是在这个界面点击所有都允许的点击事件逻辑 ,源码是

if (view == mContinueButton) {执行

实际上触发的activity是src/com/android/permissioncontroller/permission/ui/ReviewPermissionsActivity.java

里面可能走两个fragment,打log看具体走哪个。,另外一个是ReviewPermissionsWearFragment

如果是一个个允许的界面是src/com/android/permissioncontroller/permission/ui/GrantPermissionsActivity.java

但这里面不好改

方法二:

frameworks/base/apex/jobscheduler/service/java/com/android/server/DeviceIdleController.java

里面的广播接受中就是监听应用安装或者卸载或者连接usb的其他操作的一些的广播

private final BroadcastReceiver mReceiver = new BroadcastReceiver() {

源码有

Intent.ACTION_PACKAGE_REMOVED

我们需要加入

case Intent.ACTION_PACKAGE_ADDED:{

                Uri data = intent.getData();

                String packageName = data.getSchemeSpecificPart();

                android.util.Log.i("yantao","packageName add ="+ packageName);

                           if (packageName != null) {

                           PackageManager mPackageManager = context.getPackageManager();

                           try {

                PackageInfo mPackageInfo =   mPackageManager.getPackageInfo(packageName, PackageManager.GET_PERMISSIONS);

                 for (String permission : mPackageInfo.requestedPermissions){

int status = mPackageManager.checkPermission(permission,packageName );

                 if (status != PackageManager.PERMISSION_GRANTED) {

                    sGrantPermissionSet.add(permission);

                }

                     }

                 android.util.Log.d("yantao", "install need grantRuntimePermission size:"+sGrantPermissionSet.size());

                 for (String permission : sGrantPermissionSet) {

                    try{

                 mPackageManager.grantRuntimePermission(packageName,

                            permission, Process.myUserHandle());

                 }catch (Exception e) {

                 android.util.Log.i("yantao","grant error ="+ e);

                 }                 }

           } catch (Exception e) {



            }

sGrantPermissionSet这个就是一个hash集合用来存每个包应用的所需要的所有权限,

private static HashSet<String> sGrantPermissionSet = new HashSet<String>();

关键是这方法grantRuntimePermission

这个新加的action记得要放入过滤器里,在方法onBootPhase中

filter = new IntentFilter();

                filter.addAction(Intent.ACTION_PACKAGE_REMOVED);

                filter.addAction(Intent.ACTION_PACKAGE_ADDED);

                filter.addDataScheme("package");

                getContext().registerReceiver(mReceiver, filter);

第三方应用白名单:

还是在frameworks/base/apex/jobscheduler/service/java/com/android/server/DeviceIdleController.java

的Intent.ACTION_PACKAGE_ADDED加入

方法一:

           

addPowerSaveWhitelistAppInternal(“com.ruixun.rxinterphone”);

推荐使用第二种,第一种有时不生效

方法二:

try {

                                final PackageManager pm = getContext().getPackageManager();

                                ApplicationInfo ai = pm.getApplicationInfo("com.ruixun.rxinterphone",

                                        PackageManager.MATCH_ANY_USER);

                              

                                mPowerSaveWhitelistUserApps.put(ai.packageName,

                                        UserHandle.getAppId(ai.uid));

                            } catch (PackageManager.NameNotFoundException e) {

                            }

上面是指定应用添加白名单,那如果是全部第三方都加白名单

加入:

String packageName = intent.getData().getSchemeSpecificPart();

                addPowerSaveWhitelistAppInternal(packageName);

源码的

public boolean addPowerSaveWhitelistAppInternal(String name)

里面的操作就差不多是方法二了,所以本质是一样的

!!!只有第一次mPowerSaveWhitelistUserApps.put才有用,后面的应用安装了虽然能收到这个广播但无法加入白名单,后续有待研究!