Skip to content

[Feature Request / RFC] 配合 FontManagerService 将字体文件安装到 data 分区 #46

@dantmnf

Description

@dantmnf

背景

/proc/self/maps 中会显示通过 mmap 映射的文件名和对应的设备号,通过 VFS 机制(Magisk 的 bind mount 或 KernelSU 的 overlayfs)修改的字体文件会显示 data 分区的设备号,从而触发部分应用的风控策略。

TB320FC:/ # grep ' /system/' /proc/$(pidof com.android.systemui)/maps
...
707b39d000-707b39e000 r--p 00000000 fe:09 3813                           /system/lib64/libasyncio.so
707b39e000-707b39f000 r-xp 00001000 fe:09 3813                           /system/lib64/libasyncio.so
707b39f000-707b3a0000 r--p 00002000 fe:09 3813                           /system/lib64/libasyncio.so
707b3d2000-707b3e2000 r--p 00000000 fe:09 4097                           /system/lib64/libmediadrmmetrics_full.so
707b3e2000-707b3f4000 r-xp 00010000 fe:09 4097                           /system/lib64/libmediadrmmetrics_full.so
707b3f4000-707b3f6000 r--p 00022000 fe:09 4097                           /system/lib64/libmediadrmmetrics_full.so
707b3f6000-707b3f7000 rw-p 00023000 fe:09 4097                           /system/lib64/libmediadrmmetrics_full.so
707f05e000-708096d000 r--p 00000000 fe:0f 89819                          /system/fonts/NotoSerifCJK-Regular.ttc
708096d000-7081c00000 r--p 00000000 fe:0f 49003                          /system/fonts/NotoSansCJK-Regular.ttc
7081c00000-7085231000 r--p 00000000 fe:0f 89876                          /system/fonts/NotoSerifCJK-VF.otf.ttc
7085231000-708715d000 r--p 00000000 fe:0f 88918                          /system/fonts/NotoSansCJK-VF.otf.ttc
708715d000-70873a1000 r--p 00000000 fe:09 2730                           /system/fonts/Roboto-Regular.ttf
708aa58000-708aab3000 r--p 00000000 fe:09 3940                           /system/lib64/libcrypto.so
708aab3000-708ab2a000 r-xp 0005b000 fe:09 3940                           /system/lib64/libcrypto.so
708ab2a000-708ab7b000 --xp 000d2000 fe:09 3940                           /system/lib64/libcrypto.so
708ab7b000-708ab80000 r-xp 00123000 fe:09 3940                           /system/lib64/libcrypto.so
708ab80000-708ab90000 r--p 00128000 fe:09 3940                           /system/lib64/libcrypto.so
708ab90000-708ab91000 rw-p 00137000 fe:09 3940                           /system/lib64/libcrypto.so
...

要消除此类痕迹,需要 VFS 路径与对应设备号匹配(即路径显示 /data/xxxxxx),或将对应地址替换为 memfd 映射(Shamiko)。

PoC

Android 12 提供了通过 OTA 单独更新字体文件的方法:https://source.android.com/docs/core/fonts/custom-font-fallback

字体文件受 fs-verity 以及签名验证保护(Android 12-13 为 fs-verity 签名验证,Android 14 为用户态签名验证),FontManagerService 启动时会删除 /data/fonts 下验证失败的文件。

  • Android 12-13 需要禁用 fs-verity 签名验证:echo 0 > /proc/sys/fs/verity/require_signatures
  • Android 14 需要使用 RRO 向 config_fontManagerServiceCerts 追加自签名证书

以下步骤是以 Android 13 为例。

# # 安装字体
# echo 0 > /proc/sys/fs/verity/require_signatures
# touch /data/local/tmp/dummy
# # 由于禁用了签名验证,可以使用空文件作为签名文件
# # 此处两个路径都需要 system_server 进程可读
# cmd font update /system/fonts/NotoSansCJK-VF.otf.ttc /data/local/tmp/dummy
Success
#
# # 修改模块
# echo "echo 0 > /proc/sys/fs/verity/require_signatures" >> /data/adb/modules/notocjk/post-fs-data.sh
# rm /data/adb/modules/notocjk/system/fonts/NotoSansCJK-VF.otf.ttc
#
# # 重启验证
# reboot
# grep fonts /proc/$(pidof com.android.systemui)/maps
72cf22b000-72d1157000 r--p 00000000 fe:0f 97458                          /data/fonts/files/~~xbiOPHgakY7ty1i3IeKxog==/NotoSansCJKjp-Thin.otc
735a8aa000-735c1b9000 r--p 00000000 fe:0f 95862                          /system/fonts/NotoSerifCJK-Regular.ttc
735c1b9000-735d44c000 r--p 00000000 fe:0f 95828                          /system/fonts/NotoSansCJK-Regular.ttc
735d44c000-7360a7d000 r--p 00000000 fe:0f 95836                          /system/fonts/NotoSerifCJK-VF.otf.ttc
7360a7d000-7360cc1000 r--p 00000000 fe:09 2730                           /system/fonts/Roboto-Regular.ttf
7696ce8000-7696d33000 r--p 00000000 fe:09 2731                           /system/fonts/RobotoStatic-Regular.ttf

其他信息

  • FontManagerService 只能更新字体文件以及 named family,fallback family 依然需要通过修改 fonts.xml 实现
  • fonts.xml 中需要引用正确的 PostScript name
  • 需要更高的 fontRevision 才能覆盖 /system/fonts 下相同 PostScript name 的字体
    • PostScript name 和 fontRevision 相同时,会优先使用 /system/fonts 中的字体文件
    • 或许可以 patch 一下 fontRevision?
  • 用户可以通过 cmd font clear 主动删除所有热更新字体

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions