作者:Bill,来源:易灵思官微
eMMC全称为 embedded Multi Media Card,主要用于非易失性存储,它弥补了 FPGA 芯片自身存储能力的不足,为 FPGA 提供一个高集成度、大容量、低成本、且易于使用的“硬盘”或“固态硬盘”解决方案。
eMMC简介
eMMC 在 FPGA 系统中的作用可以概括为:
系统启动:可存储OS镜像
大容量数据存储:记录采集数据、视频、日志
运行操作系统和应用程序
eMMC并非一个单纯的存储芯片,内部主要可以分为 Flash Memory、Flash Controller 以及Interface 三大部分:

Flash Memory:负责数据存储。
Flash Controller:负责管理NAND Flash的读写、擦除、坏块管理、磨损均衡、错误校正等复杂操作。
Interface:提供了一个标准化的主机接口,让主处理器可以像访问一个标准设备一样轻松访问存储。
易灵思eMMC IP
易灵思为用户提供了eMMC Host Controller IP (基于eMMC5.1协议)和配套的Linux驱动。为了方便用户在系统中使用eMMC,易灵思还提供了eMMC Demo工程(基于TJ375N529 / TJ375N1156X开发板),实现了将Linux系统写入eMMC并从eMMC中加载Linux系统的功能。
eMMC5.1协议中定义的速率模式如下表所示,易灵思eMMC Host Controller IP V1.0最高实现HS400模式。

eMMC Demo
3.1 写入Linux系统
在将Linux系统写入eMMC之前,需要进行以下操作:① 用以太网口从服务器下载Linux系统文件。② 使用工具对eMMC进行分区。为了方便上述操作,RISC-V需要先从SD卡启动系统。
将Linux系统写入eMMC的具体流程如下图所示:

通过Balena Etcher工具将sdcard.img(包括Linux kernel、device tree、file system)烧写进SD卡。
用Efinity Programmer擦除SPI flash,并将emmc_linux.hex(包含FPGA bitstream、OpenSBI、U-Boot)文件烧写进flash,其中FPGA bitstream包含bootloader(FSBL)文件。
重新上电加载程序后,运行bootloader读取flash里面的OpenSBI和U-Boot文件,输入run sd_bootcmd命令引导U-Boot读取SD卡内的Linux kernel和device tree并将其写入到DDR内存里,然后RISC-V会依次加载Linux kernel和device tree,加载成功后,再读取SD卡内的file system并挂载在Linux系统内。
通过开发板上的以太网口连接至服务器,下载服务器里的uImage(Linux kernel image)、linux.dtb(device tree blob)、rootfs.tar(tarball of the root filesystem)文件并写入到SD卡里。
通过emmc_programmer脚本把uImage、linux.dtb、rootfs.tar从SD卡读出并写入eMMC里。

3.2 加载Linux系统
从eMMC中加载Linux系统的流程如下图所示:

开发板上电加载程序后,运行bootloader读取flash里面的OpenSBI和U-Boot文件。
引导U-Boot读取eMMC卡内的Linux kernel和device tree。
将读出的Linux kernel和device tree写入到DDR内存里。
RISC-V依次加载DDR内存里的Linux kernel和device tree,加载成功后,再读取eMMC卡内的file system并挂载在Linux系统内。
如下图所示,Linux系统加载完成后,进入系统内,执行lsblk命令,显示根系统是挂载在eMMC第二分区上。

在FPGA上成功加载Linux系统后,将获得一个功能完整的嵌入式开发环境,能够运行多种应用程序并利用丰富的工具链进行开发,支持从基础开发到高性能计算的广泛需求。
总结
易灵思提供了基于eMMC的Linux系统加载方案,完善了易灵思RISC-V生态系统,更加便于用户在RISC-V上使用Linux系统。同时eMMC作为Linux系统加载介质,兼具高可靠性、易用性及性能优势,其集成化设计简化了存储管理,通过标准化接口与RISC-V架构协同,支撑了Linux系统的稳定运行 。