高通平台如何避免误入FFBM模式
前面两篇博客分别介绍了通过和qfil工具退出ffbm模式的方法。虽然售后的同学可以这么指导用户做恢复,但步骤多操作也麻烦,且属于事后处理,如果大面积高概率地出现,会严重影响用户体验。这个问题是高通引入ffbm模式导致的,采用高通芯片方案的android设备都可能会出现。google一下,友商pico的vr一体机用户在官方论坛反映《进入ffbm模式怎么退出》,一个多月前的帖子目前还没有回应。这里必须为我们售后的同学点赞,客户反馈问题24小时内就回应并解决了。android手机主要是联想的旗舰机zuk出现过,《the phone is blocking in mode ffbm》、《》、《help. test mode / ffbm mode》。看来必须从根上接决这个问题,否则售后同学的压力会很大,用户也会很烦。
进入ffbm模式是因为misc分区被修改了,谁修改的一时也弄不清楚。从售后同学那里了解到,用户并没有做root或unlock等特殊操作。考虑到可能有多个修改的源,没法都给堵上,所以打算从后端入手,修改init直接过滤掉该模式,无论misc分区被修改成什么样,都直接启动到android系统,而不进入ffbm。修改的代码很少,如下。
修改代码后,执行命令make systemimage -j8编译生成system.img,通过fastboot将新生成的system.img烧录到处于ffbm模式下的故障机器里,并重启。奇迹出现了,果然正常进入了android系统,如下图所示。
可以看到,kernel是老的,android是新的。再查看misc分区的内容及dmesg,如下图所示。
通过dd命令查看misc分区,内容为ffbm-00,kernel command line有androidboot.mode=ffbm-00的配置,在init中直接忽略了androidboot.mode的配置,android系统正常启动,相关log如下。
msm8998:/ # dd if=/dev/block/bootdevice/by-name/misc count=1 bs=128 ffbm-00 boot-factory 1+0 records in 1+0 records out 128 bytes transferred in 0.004 secs (32000 bytes/sec) msm8998:/ # dmesg | grep -ie "ffbm|androidboot" [ 0.000000] kernel command line: rcupdate.rcu_expedited=1 console=ttymsm0,115200,n8 androidboot.console=ttymsm0 earlycon=msm_serial_dm,0xc1b0000 androidboot.hardware=qcom androidboot.veritymode=enforcing androidboot.verifiedbootstate=orange androidboot.keymaster=1 androidboot.bootdevice=1da4000.ufshc androidboot.serialno=25f47d23 androidboot.mode=ffbm-00 quite dvt androidboot.baseband=apq skip_initramfs rootwait ro init=/init root=/dev/sda6 [ 1.172876] init: ignore androidboot.mode!
改动之前的log如下,init会根据kernel command line的配置进入ffbm模式,fs_mgr不挂载userdatafs_mgr,并且不启动android。
[ 0.000000] kernel command line: rcupdate.rcu_expedited=1 console=ttymsm0,115200,n8 androidboot.console=ttymsm0 earlycon=msm_serial_dm,0xc1b0000 androidboot.hardware=qcom androidboot.veritymode=enforcing androidboot.verifiedbootstate=orange androidboot.keymaster=1 androidboot.bootdevice=1da4000.ufshc androidboot.serialno=25f47d23 androidboot.mode=ffbm-00 quite dvt androidboot.baseband=apq skip_initramfs rootwait ro init=/init root=/dev/sda6 [ 1.355482] init: booting into ffbm mode [ 1.849985] fs_mgr: ffbm mode,skip mount userdatafs_mgr: __mount(source=/dev/block/bootdevice/by-name/modem_a,target=/firmware,type=vfat)=0
[ 1.869366] init: ffbm mode, not start class main