MTK 驱动(86)---更换CPU后,RPMB无法访问,必须同时更换eMMC

更换CPU后,RPMB无法访问,必须同时更换eMMC


   MTK平台的RPMB(Replay Protected Memory Block) solution中,rpmb key的生成是和CPU ID相绑定,如果遇到fail IC,或HW交叉实验中需要更换CPU(BB chip),那么就需要把eMMC一同做更换。原因是rpmb key具有OTP(One Time Programmable)特性,一旦被写入eMMC无法更改也无法擦除(JEDEC eMMC spec规定),eMMC vendor可能会有特殊方法清除。而不同的CPU计算出的rpmb key会不同,更换CPU后,就无法计算出和当前eMMC中对应的key了。
      具体的code是在vendor/mediatek/proprietary/bootable/bootloader/preloader/platform/<PLATFORM>/src/security/trustzone/tz_init.c的trustzone_post_init()函数中以下这段:
 #if CFG_TEE_SUPPORT
#if CFG_MICROTRUST_TEE_SUPPORT
 u8 rpmb_key[KEY_LEN];
 kdflib_get_msg_auth_key(teearg->hwuid, 16, rpmb_key, KEY_LEN);
 teei_key_param_prepare(TEE_PARAMETER_ADDR,(u8 *)teearg->hwuid,rpmb_key);
#else
 u8 rpmb_key[32];
 seclib_get_msg_auth_key(teearg->hwuid, 16, rpmb_key, 32);
#endif
 mmc_rpmb_set_key(rpmb_key);
 teearg->tee_rpmb_size = mmc_rpmb_get_size();
 DBG_MSG("%s TEE RPMB Size : 0x%x\n", MOD, teearg->tee_rpmb_size); 
#endif
  目前的solution是默认download后第一次开机就会生成并把rpmb key写入到eMMC。 
  对于分析问题需要HW交叉实验的场景,如果需要用到RPMB的话,则必须要同时更换eMMC。 
  对于产线遇到Fail IC的场景,我们提供以下的rpmb key延迟绑定的solution可以帮助客户有效减少Fail IC带来的eMMC额外成本损失。 
[SOLUTION]
   所谓rpmb key延迟绑定,就是产线依需求来决定何时触发绑定rpmb key(把rpmb key写入eMMC)的操作。建议是在产线比较靠后的工位,确认手机除rpmb之外的其他功能都正常后,再trigger programming rpmb key 到eMMC,之后再测试与rpmb相关的功能。建议的solution是可以利用sw reboot时在rtc寄存器中设置标记的方法作为判断标志。
1. 贵司可以在工模中新增一个按钮"Reboot for Set RPMB Key",点击按钮后(或者新增一个AT指令),执行以下操作:
property_set(“sys.powerctl”, “reboot,bootloader”);   
while(1) { pause(); }
  如果是用Java code来实做的话,可以参考上面的code对应改写即可。
  reboot命令参数可以根据需求客制化,这里是利用现成的bootloader参数,对应重启到fastboot mode。我们就是利用kernel在重启前向RTC寄存器写入的特殊flag作为preloader写rpmb key的判断标志位。

2. Preloader也需要做对应的修改。
2.1 vendor/mediatek/proprietary/bootable/bootloader/preloader/platform/<PLATFORM>/src/security/trustzone/tz_init.c
找到void trustzone_post_init(void)函数,在上面定义一个全局变量:
 U16 rpmb_key_set_flag = 0;
在这个函数中找到以下这段:
 #if CFG_TEE_SUPPORT
 u8 rpmb_key[32];
 seclib_get_msg_auth_key(teearg->hwuid, 16, rpmb_key, 32);
 mmc_rpmb_set_key(rpmb_key);
 teearg->tee_rpmb_size = mmc_rpmb_get_size();
 DBG_MSG("%s TEE RPMB Size : 0x%x\n", MOD, teearg->tee_rpmb_size); 
#endif
修改为:
 #if CFG_TEE_SUPPORT
    u8 rpmb_key[32];
    if (rpmb_key_set_flag != 0) {
        seclib_get_msg_auth_key(teearg->hwuid, 16, rpmb_key, 32);
        mmc_rpmb_set_key(rpmb_key);
    }
    teearg->tee_rpmb_size = mmc_rpmb_get_size();
    DBG_MSG("%s TEE RPMB Size : 0x%x\n", MOD, teearg->tee_rpmb_size); 
#endif
2.2  vendor/mediatek/proprietary/bootable/bootloader/preloader/platform/<PLATFORM>/src/drivers/rtc.c
找到bool rtc_boot_check(void)这个函数,在这个函数上面添加:
 extern U16 rpmb_key_set_flag;
在这个函数中找到以下这行:
 pdn1 = RTC_Read(RTC_PDN1);
在这行的后面添加以下的代码:
 if (pdn1 & RTC_PDN1_FAST_BOOT) {
    rpmb_key_set_flag = 1;
 }
贵司测试时,可以先修改Preloader,下adb reboot bootloader来做测试,测试通过后再客制化工模的按钮。
测试时可以再执行特殊重启前先测试看RPMB是否不能读写。特殊重启后RPMB即可正常读写。

3. RTC寄存器客制化
  上面我们提供的sample是直接利用了现有的fastboot mode的rtc register bit。如果贵司想要更换为其他的rtc bit来作为trigger rpmb key programming的flag的话,需要客制化kernel中相关的code。
3.1 kernel-3.18/drivers/watchdog/mediatek/wdk/wd_api.c
void arch_reset(char mode, const char *cmd) 函数中以下这段:
 if (cmd && !strcmp(cmd, "charger")) {
     /* do nothing */
 } else if (cmd && !strcmp(cmd, "recovery")) {
     rtc_mark_recovery();
 } else if (cmd && !strcmp(cmd, "bootloader")) {
     rtc_mark_fast();
 } else if (cmd && !strcmp(cmd, "kpoc")) {
#ifdef CONFIG_MTK_KERNEL_POWER_OFF_CHARGING
     rtc_mark_kpoc();
#endif
 } else {
     reboot = 1;
 }
  以上这段就是执行reboot命令时对传入的参数处理的部分,会set rtc对应bit。
  如果想换成其他rtc bit和reboot参数的话,可以模仿recovery或bootlooaer参数的处理方法自行添加。之后只需要对应修改preloader即可。
  • 2
    点赞
  • 28
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值