提示: 熟悉MTK平台开发者选项开关和USB调试模式开关
文章目录
实现效果
- 默认开发者模式打开-USB调试模式打开
- 系统应用开发可以自己实现开发者和USB模式开关,方便定制业务
一、修改内容
修改要源码路径
\vendor\mediatek\proprietary\packages\apps\SettingsProvider\src\com\android\providers\settings\DatabaseHelper.java
实现方案
loadSecureSettings 方法里面:设置adb 相关属性、 设置usb 模式
属性 | 值 |
---|---|
Settings.Secure.ADB_ENABLED | 1 |
Settings.Global.DEVELOPMENT | 1 |
persist.sys.usb.config | adb |
具体修改如下
private void loadSecureSettings(SQLiteDatabase db) {
SQLiteStatement stmt = null;
try {
stmt = db.compileStatement("INSERT OR IGNORE INTO secure(name,value)"
+ " VALUES(?,?);");
...............................
loadSetting(stmt, Settings.Secure.ADB_ENABLED, 1);
loadSetting(stmt, Settings.Global.DEVELOPMENT_SETTINGS_ENABLED,1);
SystemProperties.set("persist.sys.usb.config","adb");
...................
}
二、实现方案分析
思路
先找到具体代码,看看逻辑是怎样处理的
找到开发者选项的代码
进入系统设置->系统->开发者选项,会看到如下日志
D Switching to fragment com.android.settings.development.DevelopmentSettingsDashboardFragment
D Launching fragment com.android.settings.development.DevelopmentSettingsDashboardFragment
那么接下来就是分析 开发者选项 对应的源码 DevelopmentSettingsDashboardFragment
DevelopmentSettingsDashboardFragment 源码分析
使用开发者选项开关
肉眼可见的代码,见名知意的方法 enableDeveloperOptions disableDeveloperOptions
private void enableDeveloperOptions() {
if (Utils.isMonkeyRunning()) {
return;
}
DevelopmentSettingsEnabler.setDevelopmentSettingsEnabled(getContext(), true);
for (AbstractPreferenceController controller : mPreferenceControllers) {
if (controller instanceof DeveloperOptionsPreferenceController) {
((DeveloperOptionsPreferenceController) controller).onDeveloperOptionsEnabled();
}
}
}
private void disableDeveloperOptions() {
if (Utils.isMonkeyRunning()) {
return;
}
DevelopmentSettingsEnabler.setDevelopmentSettingsEnabled(getContext(), false);
final SystemPropPoker poker = SystemPropPoker.getInstance();
poker.blockPokes();
for (AbstractPreferenceController controller : mPreferenceControllers) {
if (controller instanceof DeveloperOptionsPreferenceController) {
((DeveloperOptionsPreferenceController) controller)
.onDeveloperOptionsDisabled();
}
}
poker.unblockPokes();
poker.poke();
}
核心逻辑就是 setDevelopmentSettingsEnabled 控制
DevelopmentSettingsEnabler.setDevelopmentSettingsEnabled(getContext(), true);
DevelopmentSettingsEnabler.setDevelopmentSettingsEnabled(getContext(), false);
DevelopmentSettingsEnabler
DevelopmentSettingsEnabler 源码路径:\frameworks\base\packages\SettingsLib\src\com\android\settingslib\development\DevelopmentSettingsEnabler.java
setDevelopmentSettingsEnabled 方法
public static void setDevelopmentSettingsEnabled(Context context, boolean enable) {
Settings.Global.putInt(context.getContentResolver(),
Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, enable ? 1 : 0);
LocalBroadcastManager.getInstance(context)
.sendBroadcast(new Intent(DEVELOPMENT_SETTINGS_CHANGED_ACTION));
}
哈哈,不就是设置一次 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED 属性的嘛
其实在这里就可以如何默认打开开发者模式了,就是设置DEVELOPMENT_SETTINGS_ENABLED 属性,具体方案两种:
- 找到默认的配置,在配置里面设置值
- 在数据库或者配置文件加载的时候,设置一次值
DEVELOPMENT_SETTINGS_ENABLED
追根溯源 ,找到相关的 DEVELOPMENT_SETTINGS_ENABLED 配置逻辑
Framework 层Settings.System, Settings.Secure和Settings.Global存储及应用 可以看一下以前的笔记:
Settings.System-Secure-Global
主要看一下字段DEVELOPMENT_SETTINGS_ENABLED 对应的value 值是什么,通过官网去查看一下。
比如:Settings.Global.DEVELOPMENT_SETTINGS_ENABLED 值是什么,因为如果我们在系统配置里面配置字段默认值,肯定需要知道常量的value 值是什么,也就是默认配置的字段值是什么。
如下:找到 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED 的值value 为:development_settings_enabled
我们也可以通过源码来查询一次,配置的值是什么。
无论从官网上面查询这个常量还是源码查询常量对应的value 值是一致的:development_settings_enabled
就此打住,分析到这里暂不往下分析,那么就在 DatabaseHelper.java 类中,初始化地方,给于DEVELOPMENT_SETTINGS_ENABLED 一个默认的值1 就可以,代表true.
USB 调试开关
回到 DevelopmentSettingsDashboardFragment 源码,找到对应的adb control ,理论上 adb 开关设置应该在control,查看以下源码:
找到 AdbPreferenceController
AdbPreferenceController
onAdbDialogConfirmed onDeveloperOptionsSwitchDisabled 方法,调用的就是 writeAdbSetting 方法
发现MTKSetting 应用中,并没有 writeAdbSetting 方法,那么就查找一次
fise4@ubuntu-PowerEdge-R730:~/Android2/mt6769-alps-release-s0.mp1.rc/alps-release-s0.mp1.rc$ grep -rn writeAdbSetting
frameworks/base/packages/SettingsLib/src/com/android/settingslib/development/AbstractEnableAdbPreferenceController.java:125: writeAdbSetting(false);
frameworks/base/packages/SettingsLib/src/com/android/settingslib/development/AbstractEnableAdbPreferenceController.java:133: protected void writeAdbSetting(boolean enabled) {
frameworks/base/packages/SettingsLib/tests/robotests/src/com/android/settingslib/development/EnableAdbPreferenceControllerTest.java:179: writeAdbSetting(true);
packages/apps/Settings/src/com/android/settings/development/AdbPreferenceController.java:39: writeAdbSetting(true);
packages/apps/Settings/src/com/android/settings/development/AdbPreferenceController.java:65: writeAdbSetting(false);
AbstractEnableAdbPreferenceController
源码路径:
frameworks/base/packages/SettingsLib/src/com/android/settingslib/development/AbstractEnableAdbPreferenceController.java
AbstractEnableAdbPreferenceController.java writeAdbSetting 方法
protected void writeAdbSetting(boolean enabled) {
Settings.Global.putInt(mContext.getContentResolver(),
Settings.Global.ADB_ENABLED, enabled ? ADB_SETTING_ON : ADB_SETTING_OFF);
notifyStateChanged();
}
就是设置了一次 ADB_ENABLED 值呗
关于 ADB_ENABLED 值,我们查看以下官网配置,如下:
那还是在数据初始化的时候,设置一次Global.ADB_ENABLED 的值 即可。
adb 查看修改值
三、其它
- 为什么不在配置的地方去修改配置,或者定义配置值:
配置地方找不到;跟user-debug 版本有关联;部分属性并不是在配置文件中定义的,直接在内核和编译文件定义的,比如.py 脚本定义,在数据库定义地方直接赋值一次。
- ADB_ENABLED 的一些思考
在开发者模式开关地方,源码分析的明明是 Settings.Global 关联的 development_settings_enabled,但是实际上发现这个属性并不在Global 里面,而是在 Secure 里面,即使在数据库初始化默认值给Global,实际上生效的值还是Secure, 可能跟平台规则相关。
- 开发者模式、USB调试模式、USB 模式
在一些定制的产品中,会有各种定制需求,根据需求结合系统应用实现各种需求。