当前位置: 首页 > article >正文

[问题记录] Android裁剪Provision应用后无法打开开发者选项

最近在做RK平台的内置应用裁剪,按照需求最终决定了裁剪列表,大概减少了系统img包100M的体积。裁剪的列表如下:

LOCAL_OVERRIDES_PACKAGES += \
    TelephonyProvider \
    CalendarProvider \
    WallpaperCropper \
    DocumentsUI \
    HTMLViewer \
    QuickSearchBox \
    MmsService \
    DownloadProvider \
    DownloadProviderUi \
    SimAppDialog \
    Contacts \
    EasterEgg \
    NfcNci \
    Launcher3QuickStep \
    Calendar \
    PrintSpooler \
    BasicDreams \
    BuiltInPrintService \
    MusicFX \
    Telecom \
    PrintRecommendationService \
    ManagedProvisioning \
    SoundPicker \
    PhotoTable \
    WAPPushManager \
    LiveWallpapersPicker \
    BookmarkProvider \
    ExactCalculator \
    TeleService \
    WallpaperBackup \
    BlockedNumberProvider \
    UserDictionaryProvider \
    DeskClock \
    WallpaperPicker \
    Provision

在后面几天的测试开发中,发现了一个问题:从原生设置中打开关于,点击版本号,无法打开开发者模式了。

解决方案

1.临时解决方案:查看 device_provisioned 的值。如果是0,则设置为1:

settings get global device_provisioned
settings put global device_provisioned 1

2. 根本解决方案:重新调整裁剪列表,不裁剪开机向导 Provision 这个应用。

解决过程

1.打开开发者选项有一个很明显的Toast,内容是“xxxx开发者xxxx”。于是直接在设置的源码中搜索 “开发者” 这个字段,应该可以找到对应的 string 资源和名称。

packages/apps/Settings# grep -nr "开发者"
res/values-zh-rCN/strings.xml:27:      <item quantity="other">现在只需再执行 <xliff:g id="STEP_COUNT_1">%1$d</xliff:g> 步操作即可进入开发者模式。</item>
res/values-zh-rCN/strings.xml:28:      <item quantity="one">现在只需再执行 <xliff:g id="STEP_COUNT_0">%1$d</xliff:g> 步操作即可进入开发者模式。</item>
res/values-zh-rCN/strings.xml:30:    <string name="show_dev_on" msgid="2840850085134853754">"您现在处于开发者模式!"</string>
res/values-zh-rCN/strings.xml:31:    <string name="show_dev_already" msgid="7041756429707644630">"您已处于开发者模式,无需进行此操作。"</string>
res/values-zh-rCN/strings.xml:32:    <string name="dev_settings_disabled_warning" msgid="6971867026249671244">"请先启用开发者选项。"</string>
res/values-zh-rCN/strings.xml:2721:    <string name="fullbackup_data_summary" msgid="971587401251601473">"自动远程备份设备数据(例如 WLAN 密码和通话记录)和应用数据(例如应用存储的设置和文件)。\n\n启用自动备份功能后,系统会定期远程保存设备和应用数据。应用数据可以是应用根据开发者设置保存的任何数据,包括可能比较敏感的数据(例如通讯录、邮件和照片)。"</string>
res/values-zh-rCN/strings.xml:4421:    <string name="quick_settings_developer_tiles" msgid="7336007844525766623">"快捷设置开发者图块"</string>
res/values-zh-rCN/strings.xml:4621:    <string name="autofill_reset_developer_options_complete" msgid="1276741935956594965">"已重置自动填充开发者选项"</string>
res/values-zh-rCN/strings.xml:4652:    <string name="graphics_driver_app_preference_prerelease_driver" msgid="7355929161805829480">"开发者驱动程序"</string>

2. 拿其中一个字段名称进行搜索:show_dev_on,查看哪个页面引用了这个字段,从而定位到具体的页面类。

packages/apps/Settings# grep -nr show_dev_on
……
src/com/android/settings/deviceinfo/BuildNumberPreferenceController.java:239:        mDevHitToast = Toast.makeText(mContext, R.string.show_dev_on,

 3.打开 BuildNumberPreferenceController.java 这个类,查找相关逻辑。有个和Click相关的方法,点进去看看有没有思路:

@Override
    public boolean handlePreferenceTreeClick(Preference preference) {
        ……
        // Don't enable developer options until device has been provisioned
        if (!WizardManagerHelper.isDeviceProvisioned(mContext)) {
            mMetricsFeatureProvider.action(
                    mContext, SettingsEnums.ACTION_SETTINGS_BUILD_NUMBER_PREF);
            return false;
        }

        ……
        // 有 countdown 计数和 Toast 处理,应该就是处理开发者模式的逻辑了
        if (mDevHitCountdown > 0) {
            mDevHitCountdown--;
            if (mDevHitCountdown == 0 && !mProcessingLastDevHit) {
                // Add 1 count back, then start password confirmation flow.
                mDevHitCountdown++;
                final ChooseLockSettingsHelper helper =
                        new ChooseLockSettingsHelper(mActivity, mFragment);
                mProcessingLastDevHit = helper.launchConfirmationActivity(
                        REQUEST_CONFIRM_PASSWORD_FOR_DEV_PREF,
                        mContext.getString(R.string.unlock_set_unlock_launch_picker_title));
                if (!mProcessingLastDevHit) {
                    enableDevelopmentSettings();
                }
                mMetricsFeatureProvider.action(
                        mMetricsFeatureProvider.getAttribution(mActivity),
                        MetricsEvent.FIELD_SETTINGS_BUILD_NUMBER_DEVELOPER_MODE_ENABLED,
                        mFragment.getMetricsCategory(),
                        null,
                        mProcessingLastDevHit ? 0 : 1);
            } else if (mDevHitCountdown > 0
                    && mDevHitCountdown < (TAPS_TO_BE_A_DEVELOPER - 2)) {
                if (mDevHitToast != null) {
                    mDevHitToast.cancel();
                }
                mDevHitToast = Toast.makeText(mContext,
                        mContext.getResources().getQuantityString(
                                R.plurals.show_dev_countdown, mDevHitCountdown,
                                mDevHitCountdown),
                        Toast.LENGTH_SHORT);
                mDevHitToast.show();
            }

            mMetricsFeatureProvider.action(
                    mMetricsFeatureProvider.getAttribution(mActivity),
                    MetricsEvent.FIELD_SETTINGS_BUILD_NUMBER_DEVELOPER_MODE_ENABLED,
                    mFragment.getMetricsCategory(),
                    null,
                    0);
        } else if (mDevHitCountdown < 0) {
            if (mDevHitToast != null) {
                mDevHitToast.cancel();
            }
            mDevHitToast = Toast.makeText(mContext, R.string.show_dev_already,
                    Toast.LENGTH_LONG);
            mDevHitToast.show();
            mMetricsFeatureProvider.action(
                    mMetricsFeatureProvider.getAttribution(mActivity),
                    MetricsEvent.FIELD_SETTINGS_BUILD_NUMBER_DEVELOPER_MODE_ENABLED,
                    mFragment.getMetricsCategory(),
                    null,
                    1);
        }
        return true;
    }

 在处理 click 计数前,看到注释中有一句:

// Don't enable developer options until device has been provisioned

即:在设备配置完成之前,不要启用开发者选项

看到 privisioned,马上反应过来原生的一个 Provision 应用,即开机向导。这个应用里做的一件非常重要的事情就是在用户完成配置之后,会设置数据库一个叫做 device_provisioned 的标记位。

4. 查看裁剪列表,确实把Provision这个应用裁剪掉了。查看数据库内的标记位,果然为0,表示设备设置仍未完成:

rk3568:/ # settings get global device_provisioned
0

手动设置一下这个标记位:

rk3568:/ # settings put global device_provisioned 1

重新尝试打开开发者模式,果然成功了。

问题复盘

这次的裁剪主要问题出在 Provision 开机向导上,有点太经验用事了。

之前在做另一个 Soc 预置 Launcher 的时候,替代 Soc 自己的 Launcher 时,在处理解锁环节(系统判断:是否拉起带 bootDirectAware 标记的 Launcher 和 Launcher 优先级)卡了很久,当时的解决方式是引入一个假 Launcher 负责解锁和设置 device_provisioned 标记,替代原生的 Provision 开机向导。

但是RK平台对替换 Launcher 的整体流程做的比较完善,因此不需要自行处理解锁之类的动作,自然就没有引入假 Launcher 这一套。加上我把 Provision 也裁剪掉了,导致没有流程设置 device_provision 的标记,自然引发了这个问题。

特地记录一下这个问题,继续努力。


http://www.kler.cn/a/415065.html

相关文章:

  • 【踩坑日记】【教程】如何在ubuntu服务器上配置公钥登录以及bug解决
  • TCP socket api详解 续
  • 简单好用的折线图绘制!
  • 【论文阅读】Federated learning backdoor attack detection with persistence diagram
  • 【Android+多线程】IntentService 知识总结:应用场景 / 使用步骤 / 源码分析
  • 05_JavaScript注释与常见输出方式
  • 基于Linux操作系统的DNS服务器实验
  • python网络爬虫进阶
  • 全面解析LLM业务落地:RAG技术的创新应用、ReAct的智能化实践及基于业务场景的评估框架设计
  • 开发一套ERP 第七弹 RUst 操作数据库
  • 全国1000米分辨率逐月植被覆盖度(FVC)数据集(2000-2024)
  • 网络安全——--网络安全的基本概念--病毒防护--入侵检测技术与防火墙--虚拟专用网
  • C#里怎么样使用继承实现不同的功能,以及调用基类函数?
  • 在Linux中备份msyql数据库和表的详细操作
  • 【ChatGPT大模型开发调用】如何获得 OpenAl API Key?
  • Linux系统管理基础指南--习题
  • Python3 爬虫 Scrapy的安装
  • Docker容器ping不通外网问题排查及解决
  • 【uniapp】轮播图
  • 力扣整理版十:动态规划(待更新)
  • 【CLIP】3: semantic-text2image-search允许局域网访问
  • 卷积神经网络实现图像分类
  • 【HF设计模式】01-策略模式
  • 【Linux | 计网】TCP协议详解:从定义到连接管理机制
  • 【Spring源码核心篇-04】spring中refresh刷新机制的流程和实现
  • FPGA工具链及功能介绍