第三方安装的应用全部自动允许授权权限:
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才有用,后面的应用安装了虽然能收到这个广播但无法加入白名单,后续有待研究!