实验环境

硬件设备:GDK8

GDK8是我的主力开发机,可以非常方便的在ARM上编译代码,免去了交叉编译的苦恼,而它最大的特色就是可以进行JTAG调试。
相信现在非常多的领域都需要研究Linux内核,而传统的内核调试方法就是printk,而像kgdb这样的软件调试器又有调试不了的“盲区”,基于这种情况就只能使用JTAG技术,但市场上的芯片又不给你把JTAG引脚弄出来,于是想要使用JTAG进行调试是非常困难的,但是GDK8可以非常轻松的通过挥码枪与底层的Coresight协议进行交互,进行JTAG调试,大大提高了我解决问题的效率。

挥码枪上手指南
Nano Code下载链接

ATF与BL31的介绍

可信固件(Trusted Firmware)是ARM从ARM-v8时期开始引入的安全方案,主要作用在提高了启动过程的安全性和细化了运行过程的特权级区间,对于ARM而言,可信固件可以分成两类,分别是针对A核的TF-A和针对M核的TF-M。

当机器启动后,会从Boot Rom内启动bl1_entrypoint.S,bl1的主要目的是建立Trusted SRAM、exception vector、初始化串口等,bl1完成之后,会从Trusted Boot Firmware内运行bl2_main.c,在这里面会去初始化硬件和寻找bl3,当然bl3有很多,如bl31、bl32、bl33,bl31是通过SMC为Non-Secure持续提供设计安全的服务,并寻找bl32和bl33,其中bl32负责OPTee OS的运行,bl33则是不可信固件。

1. 下载ATF源代码

git clone https://github.com/ARM-software/arm-trusted-firmware.git

2. 编译ATF

编译ATF固件可以参照下面的命令进行编译。

make realcleanCFLAGS='-gdwarf-2' \
CROSS_COMPILE=aarch64-linux-gnu- \
make PLAT=rk3328 DEBUG=1 ERROR_DEPRECATED=1 bl31

其中PLAT=指对应芯片类型,由于GDK8的芯片是RK3328,所以指定PLAT=rk328,也可以根据具体的芯片型号指定不同的平台。
DEBUG=用于决定生成的二进制是否带有符号信息,比如设置DEBUG=1就会生成符号信息,而设置DEBUG=0就不会生成调试信息。
完成编译后,可以在build/rk3328/目录下找到编译出来的二进制文件,生成的固件位于bl31目录下,名字是bl31.elf

ls build/rk3328/debug/
bl31  lib  libc  libfdt  libwrapper  romlibls build/rk3328/debug/bl31/
16550_console.d         cache_helpers.o          errata_report.d        plat_gicv2.o        psci_on.d
16550_console.o         cci.d                    errata_report.o        plat_helpers.d      psci_on.o
aem_generic.d           cci.o                    generic_delay_timer.d  plat_helpers.o      psci_setup.d
aem_generic.o           context.d                generic_delay_timer.o  plat_log_common.d   psci_setup.o
arm_arch_svc_setup.d    context_mgmt.d           gicdv2_helpers.d       plat_log_common.o   psci_suspend.d
arm_arch_svc_setup.o    context_mgmt.o           gicdv2_helpers.o       plat_pm.d           psci_suspend.o
backtrace.d             context.o                gicv2_helpers.d        plat_pm.o           psci_system_off.d
backtrace.o             cortex_a53.d             gicv2_helpers.o        plat_psci_common.d  psci_system_off.o
bakery_lock_coherent.d  cortex_a53.o             gicv2_main.d           plat_psci_common.o  rockchip_gicv2.d
bakery_lock_coherent.o  cpu_data_array.d         gicv2_main.o           plat_topology.d     rockchip_gicv2.o
bl31_context_mgmt.d     cpu_data_array.o         interrupt_mgmt.d       plat_topology.o     runtime_exceptions.d
bl31_context_mgmt.o     cpu_data.d               interrupt_mgmt.o       pmu.d               runtime_exceptions.o
bl31.dump               cpu_data.o               misc_helpers.d         pmu.o               runtime_svc.d
bl31.elf                cpu_helpers.d            misc_helpers.o         pmu_sram_cpus_on.d  runtime_svc.o
bl31_entrypoint.d       cpu_helpers.o            multi_console.d        pmu_sram_cpus_on.o  soc.d
bl31_entrypoint.o       crash_console_helpers.d  multi_console.o        popcountdi2.d       soc.o
bl31.ld                 crash_console_helpers.o  params_setup.d         popcountdi2.o       spe.d
bl31.ld.d               crash_reporting.d        params_setup.o         popcountsi2.d       spe.o
bl31_main.d             crash_reporting.o        plat_bl_common.d       popcountsi2.o       spinlock.d
bl31_main.o             debug.d                  plat_bl_common.o       psci_common.d       spinlock.o
bl31.map                debug.o                  plat_common.d          psci_common.o       std_svc_setup.d
bl31_plat_setup.d       delay_timer.d            plat_common.o          psci_helpers.d      std_svc_setup.o
bl31_plat_setup.o       delay_timer.o            platform_common.d      psci_helpers.o      tf_log.d
bl_aux_params.d         desc_image_load.d        platform_common.o      psci_main.d         tf_log.o
bl_aux_params.o         desc_image_load.o        platform_helpers.d     psci_main.o         xlat_tables_common.d
bl_common.d             dsu_helpers.d            platform_helpers.o     psci_mem_protect.d  xlat_tables_common.o
bl_common.o             dsu_helpers.o            platform_mp_stack.d    psci_mem_protect.o  xlat_tables.d
build_message.o         ea_delegate.d            platform_mp_stack.o    psci_off.d          xlat_tables.o
cache_helpers.d         ea_delegate.o            plat_gicv2.d           psci_off.o

3. 替换固件

在GDK8中,机器启动的流程如下:

BOOTROM => TPL(ddr bin) => SPL(miniloader) => TRUST => U-BOOT => KERNELTPL(Tiny Program Loader)和 SPL(Secondary Program Loader)是比 U-Boot 更早阶段的bootloader。
TPL:运行在 sram 中,负责完成 ddr 初始化;
SPL:运行在 ddr 中,负责完成系统的 lowlevel 初始化、后级固件加载(trust.img 和
uboot.img);

在下图中可以看到,ATF固件位于trust.img内。

在uboot的编译脚本中通过pack_trust_image函数打包trust.img

function pack_trust_image()
{DRAM_BASE=`sed -n "/CONFIG_SYS_SDRAM_BASE=/s/CONFIG_SYS_SDRAM_BASE=//p" include/autoconf.mk|tr -d '\r'`rm trust*.img -fcd ${RKBIN}if [ "${ARM64_TRUSTZONE}" == "y" ]; then${SCRIPT_ATF} --ini ${INI_TRUST} ${PLAT_SHA} ${PLAT_RSA} ${PLAT_TRUST_SIZE}else${SCRIPT_TOS} --ini ${INI_TRUST} --base ${DRAM_BASE} ${PLAT_TRUST_SIZE}ficd -if [ -f ${RKBIN}/trust*.img ]; thenmv ${RKBIN}/trust*.img ./fi
}

进入到pack_trust_image后,会去调用script目录下的atf.sh脚本。
这个脚本回到rkbin/RKTRUST目录下查找配置文件,根据配置文件搜索固件,并将它们打包在一起。

COUNT=`cat ${INI} | wc -l`
if [ ${COUNT} -eq 1 ]; thenIMG=`sed -n "/PATH=/p" ${INI} | tr -d '\r' | cut -d '=' -f 2`cp ${IMG} ./trust.img
else./tools/trust_merger ${INI} ${SIZE} ${SHA} ${RSA}
fi

浏览rkbin下面的ini文件,可以看到文件内指定的二进制文件位置。

RK3328TRUST.ini
[VERSION]
MAJOR=1
MINOR=2
[BL30_OPTION]
SEC=0
[BL31_OPTION]
SEC=1
PATH=bin/rk33/rk322xh_bl31_v1.42.elf
ADDR=0x40000
[BL32_OPTION]
SEC=1
PATH=bin/rk33/rk322xh_bl32_v2.01.bin
ADDR=0x08400000
[BL33_OPTION]
SEC=0
[OUTPUT]
PATH=trust.img

此时将之前编译好的固件替换进来。

ls
px30_bl31_v1.21.elf                   rk3308_miniloader_wo_ftl_v1.23.bin       rk3368_usbplug_v2.58.bin
px30_bl32_v1.15.bin                   rk3308_usbplug_v1.25.bin                 rk3368_usbplug_v2.62.bin
px30_ddr_333MHz_v1.15.bin             rk3308_usbplug_wo_ftl_v1.25.bin          rk3368_usbplug_v2.68.bin
px30_miniloader_slc_v1.28.bin         rk3326_bl31_v1.21.elf                    rk3399_bl31_v1.35.elf
px30_miniloader_v1.31.bin             rk3326_bl32_v1.15.bin                    rk3399_bl32_v2.01.bin
px30_usbplug_slc_v1.28.bin            rk3326_ddr_333MHz_v1.15.bin              rk3399_ddr_666MHz_v1.24.bin
px30_usbplug_v1.31.bin                rk3326_miniloader_aarch32_slc_v1.29.bin  rk3399_ddr_800MHz_v1.24.bin
rk322xh_bl31_v1.42_bak.elf            rk3326_miniloader_aarch32_v1.16.bin      rk3399_ddr_933MHz_v1.24.bin
rk322xh_bl31_v1.42.elf                rk3326_miniloader_slc_v1.28.bin          rk3399_miniloader_spinor_v1.14.bin
rk322xh_bl31_v1.44.elf                rk3326_miniloader_v1.28.bin              rk3399_miniloader_v1.26.bin
rk322xh_bl31_v1.45.elf                rk3326_usbplug_slc_v1.28.bin             rk3399pro_bl31_v1.35.elf
rk322xh_bl32_v2.01.bin                rk3326_usbplug_v1.28.bin                 rk3399pro_bl32_v2.01.bin
rk322xh_ddr_333MHz_v1.16.bin          rk3328_ddr_333MHz_v1.16.bin              rk3399pro_ddr_666MHz_v1.24.bin
rk322xh_ddr_400MHz_v1.16.bin          rk3328_ddr_400MHz_v1.16.bin              rk3399pro_ddr_800MHz_v1.24.bin
rk322xh_miniloader_v2.50.bin          rk3366_ddr_800MHz_v1.00.bin              rk3399pro_ddr_933MHz_v1.24.bin
rk322xh_usbplug_v2.50.bin             rk3366_miniloader_v1.02.bin              rk3399pro_miniloader_v1.26.bin
rk3308_bl31_aarch32_v2.22.elf         rk3366_usbplug_v1.02.bin                 rk3399pro_usbplug_v1.26.bin
rk3308_bl31_v2.22.elf                 rk3368_bl30_v2.13.bin                    rk3399_usbplug_spinor_v1.14.bin
rk3308_bl32_v1.16.bin                 rk3368_bl30_v2.16.bin                    rk3399_usbplug_v1.26.bin
rk3308_ddr_393MHz_uart2_m1_v1.30.bin  rk3368_bl31_v1.91.bin                    rknpu_lion_bl31_v1.12.elf
rk3308_ddr_393MHz_uart4_m0_v1.30.bin  rk3368_bl32_v0.10.bin                    rknpu_lion_bl32_v1.13.bin
rk3308_ddr_451MHz_uart2_m1_v1.30.bin  rk3368_ddr_600MHz_v2.06.bin              rknpu_lion_ddr_933MHz_v1.04.bin
rk3308_ddr_451MHz_uart4_m0_v1.30.bin  rk3368h_bl31_v2.27.elf                   rknpu_lion_miniloader_usb_v1.03.bin
rk3308_ddr_589MHz_uart2_m1_v1.30.bin  rk3368h_bl32_v2.01.bin                   rkpx5_miniloader_v2.62.bin
rk3308_ddr_589MHz_uart4_m0_v1.30.bin  rk3368_miniloader_v2.58.bin
rk3308_miniloader_v1.25.bin           rk3368_miniloader_v2.68.bin

4. 打包固件

通过下面的命令重新生成trust.img文件,此时ATF固件就加载到里面了。

./make.sh trust

可以通过tools/trust_merger工具查看trust.img的信息。

./tools/trust_merger --unpack trust.img
File Size = 4194304
Header Tag:BL3X
Header version:258
Header flag:35
SrcFileNum:3
SignOffset:944
Component 0:
ComponentID:BL31
StorageAddr:0x4
ImageSize:0x11c
LoadAddr:0x10000
Component 1:
ComponentID:BL31
StorageAddr:0x120
ImageSize:0x20
LoadAddr:0xff091000
Component 2:
ComponentID:BL32
StorageAddr:0x140
ImageSize:0x2fc
LoadAddr:0x8400000
unpack success

该工具的基本用法如下所示:

Usage: trust_merger [options]... FILE
Merge or unpack Rockchip's trust image (Default action is to merge.)
Options:--pack                  Merge trust with specified config.--unpack                Unpack specified trust to current dir.--verbose               Display more runtime informations.--help                  Display this information.--version               Display version information.--subfix                Spec subfix.--replace               Replace some part of binary path.--prepath               Add prefix path of binary path.--rsa                   RSA mode."--rsa [mode]", [mode] can be: 0(none), 1(1024), 2(2048), 3(2048 pss).--sha                   SHA mode."--sha [mode]", [mode] can be: 0(none), 1(160), 2(256 RK big endian), 3(256 little endian).--size                  TrustImage size."--size [per image KB size] [copy count]", per image must be 64KB aligned

常见错误

tools/trust_merger不只可以查看trust.img的信息,同时也可以将trust.img进行打包,不可以将bl32.elf当作rk3328_loader_v1.16.250.bin或ini文件,打包进入trust.img内。

参考资料

  1. https://zhuanlan.zhihu.com/p/391101179
  2. https://zhuanlan.zhihu.com/p/520052961

基于RK3328平台构建ATF固件相关推荐

  1. web系统四层结构中服务器端,基于.NET平台构建四层B/S结构的动态网站

    摘要: Web是基于Internet技术的一种应用层服务,具有后台数据库支持的n层B/S结构已经成为动态Web应用的主流.虽然动态网站开发工作的主要是进行服务器端应用程序的开发,但是B/S结构动态We ...

  2. 云+X案例展 | 民生类:基于AWS PaaS构建基础集团企业级中台

    本案例由浪潮投递并参与评选,CSDN云计算独家全网首发:更多关于[云+X 案例征集]的相关信息,点击了解详情丨挖掘展现更多优秀案例,为不同行业领域带来启迪,进而推动整个"云+行业" ...

  3. grafana计算不同时间的差值_大数据时代!如何基于Spark Streaming构建实时计算平台...

    随着互联网技术的迅速发展,用户对于数据处理的时效性.准确性与稳定性要求越来越高,如何构建一个稳定易用并提供齐备的监控与预警功能的实时计算平台也成了很多公司一个很大的挑战. 自2015年携程实时计算平台 ...

  4. 基于Web SCADA平台构建实时数字化产线 - 初篇

           如各位对Web SCADA平台及技术感兴趣,欢迎转发或私信我,大家共同学习,相互交流共同进步:  构建数字化产线是近几年国家推出两化融化后.智能制造等相应政策后的产物,传统的信息化.工业 ...

  5. 基于Web SCADA平台构建数字化车间的MES系统

    数字化车间的MES系统与偏管理的信息化系统(如ERP.CRM.SRM等)最大的区别在于数据的"实时性",以传统的管理为主线的信息化系统因无法及时的将数据录入进系统,使得管理信息化中 ...

  6. 构建基于Linux平台的开源×××服务器

    实验名称:构建基于Linux平台的开源×××服务器 实验目标:一.基于Linux配置poptop ×××与管理 二.基于Linux配置Openswan ×××与管理 ×××的功能:加密数据 信息认证和 ...

  7. 基于Hadoop和Spark体系的大数据分析平台构建

    谢谢分享! 转载:http://www.sohu.com/a/249271561_481409 随着大数据.人工智能等技术的快速发展,企业对大数据平台的需求越来越强烈,通过大数据分析技术为企业提供经营 ...

  8. 恒丰银行基于大数据平台构建数据仓库的研究与实践

    恒丰银行原传统数据仓库是建立在IOE(IBM.ORACLE.EMC)传统架构体系上,已接入数据源系统有30多个,配套建立监管数据集市.数据分析集市,风险数据集市三个主要数据集市,负责十几个管理应用和监 ...

  9. 【Kubernetes 企业项目实战】06、基于 Jenkins+K8s 构建 DevOps 自动化运维管理平台(上)

    目录 一.k8s 助力 DevOps 在企业落地实践 1.1 传统方式部署项目为什么发布慢,效率低? 1.2 上线一个功能,有多少时间被浪费了? 1.3 如何解决发布慢,效率低的问题呢? 1.4 什么 ...

最新文章

  1. netty io.netty.buffer简介
  2. 向上取整的方法_瓷砖测量的方法有哪些?瓷砖尺寸一般是多少?
  3. 边缘计算架构_边缘计算架构梳理
  4. SOAR SQL进行优化和改写的自动化工具
  5. php 字符串与数字相加,注意!PHP中字符串与数字的比较
  6. 前端学习(2240):构造Vue的的利器-脚手架vue-cli3
  7. System verilog随机系统函数$randomize使用方法
  8. 用Windows 10自带的paint/画图 软件删除图片中的文字,并且添加新文字,适合学术应用,有截图
  9. re模块常用修饰符_re模块中常用功能函数
  10. .NET 文件相关的所有操作
  11. ToolScrip的设置与用法 (C#.NET Winform)
  12. uploadify3.1 php,Jquery上传插件 uploadify v3.1使用说明_jquery
  13. react 翻书效果_transition、class名称、React实现无限反复翻书效果
  14. php查看版本命令,如何查看php版本?查看php版本的详细步骤分享
  15. 【论文学习】《One-shot Voice Conversion by Separating Speaker and Content Representations with IN》
  16. Django(十二):django支付(微信支付宝)+项目部署(虚拟机、docker、云服务器)
  17. MSP430F149;一、TIMEA
  18. java unrar压缩_用java解压缩rar文件 de.innosystec.unrar解压缩rar文件
  19. Cadence改背景色
  20. PSTN PLMN ISDN

热门文章

  1. cve oracle,漏洞预警 | CVE-2018-3110 Oracle数据库服务器Java虚拟机漏洞
  2. 基于OV5640的FPGA-RAM HDMI显示
  3. Ardupilot固定翼无人机L1制导律原理及代码解读
  4. [前端]-- jquery学习1
  5. 写给两个月前的自己的一封信
  6. python编辑svg文件_使用Python创建SVG
  7. 生活随记-参观一大会址须知
  8. 逻辑运算符,if、swtch语句(java基础知识三)
  9. 让人又爱又恨的C语言
  10. 请帮我写一封情书,500字左右