????????针对不同的应用领域,Xilinx 公司设计开发了各种逻辑资源规模和集成各 种外设功能的Zynq SOC器件,包括专为成本优化的Zynq-7000平台,面向高性 能实时计算应用领域的 Zynq UltraScale+ MPSoC,面向射频通信的 ZynqUltraScale+ RFSoC,以及具备高度可扩展特性的自适应加速平台ACAP。 具体相关知识大家可以下去查询。
????????Zynq-7000 系列是赛灵思公司推出的一系列全可编程片上系统,基于 Xilinx SoC 架构。这些产品在单个设备上集成了功能丰富的双核 ARM CortexTM-A9 MPCore 处理系统(PS)和 Xilinx 可编程逻辑(PL),实现了灵活性,可配置性和性 能的完美结合。双核ARM Cortex-A9 MPCore 处理器是PS的核心,它还包括片 内存储器、外部存储器接口和一组丰富的I/O外设。Zynq-7000系列通过将ARM CPU和外设集成在一个芯片内,使得其兼具处理器和FPGA的双重特性。 作为 SoC FPGA 家族中功耗和成本最具优势的系列,掌握 Zynq 7000 SoC FPGA的开发方法,不仅可以熟悉整个SoC FPGA系列器件的开发流程,还可以学有所用。
????????GPIO(General Purpose I/O),通用输入输出,是ZYNQ的外设之一。GPIO 包括MIO 与EMIO,是 ZYNQ 上最常用的硬件资源。MIO分配在GPIO的Bank0和 Bank1,属于ZYNQ的PS部分, 而EMIO也是PS上GPIO的一部分,但连接到了PL, 分配在GPIO的Bank2和Bank3。MIO在芯片外部有54个引脚,这些引脚可以用 于GPIO、SPI、UART、USB 等功能上,每个引脚都同时具有多种功能。因为 MIO 是PS部分的引脚且其操作对于PL端不可见,所以对MIO的操作可以视为纯PS 端的操作。EMIO有64个引脚, EMIO与MIO的不同在于,EMIO连接到了PL, 再从PL输出信号,而MIO直接从PS端输出。
????????ZYNQ PS 中包含一组丰富的外设,用于和外部设备进行通信。ZYNQ的IO 包括对外连接的GPIO和内部PS与PL通信的AXIO。其中对外的GPIO又分为 两种:MIO和EMIO。MIO和 EMIO只是 GPIO信号的两种接口,MIO直连到 PS,EMIO则是 PS扩展到PL,从PL接出的I/O。EMIO依然属于PS,只是连 接到了PL,再从PL输出信号。所以MIO不需要管脚约束,而EMIO需要管脚 约束。 ????????
????????当GPIO 用作输出时,一般用于控制一些简单的外设,如LED 和蜂鸣器。 也可以用于观测一些简单外设的状态,如按键,此时 GPIO 用作输入。GPIO 可 以通过 MIO 连接到 PS 端的引脚,也可以通过 EMIO 连接到 PL。
????????MIO 是 I/O外设连接的基础,软件程序将I/O信号路由到MIO引脚。由于 MIO 引脚数量有限,I/O外围信号也可以通过EMIO接口路由到PL(包括PL设 备引脚),用于访问更多的设备引脚(PL引脚)和允许I/O外设控制器接口到PL中 的用户逻辑,
Vivado v2018.3 (64-bit)
双击打开Vivado软件,界面如下图所示
首先点击Quick Start 下的 Create Project 创建新工程,也可点击工具栏中的 File->Project->New...进行创建。
进入新建工程向导后next,编辑工程名称和工程目录
对需要的工程类型进行选择,将光标放置在对应的选项上即可出现对应的中文翻译。这里我们勾选“RTL Project”,因为我们是完全新建工程,所以勾选下方的现在不指定资源,接着点击“next”进行下一步。
截接下来选择对应的开发板型号
接下来会弹出工程摘要界面,该界面会对工程的类型以及所选用芯片的器件型号进行总结,用户可通过该界面检查是否有创建错误。确认无误后点击 Finish 完成工程创建
创建完成后Vivado工程后软件界面及对应功能如下图
接下来点击“Create Block Design”创建一个模块设计,在弹出的窗口中对设计命名。
接下来对其命名 注意:不能使用中文以及空格命名。
创建完成后软件界面如图所示,可以看到此时Design栏中出现了我们刚创建好的“system”模块设计。此时我们的设计内没有任何内容,需要点击 “+”为设计添加IP核。
添加IP核
在弹出的搜索栏中输入 zynq,可以看到下方出现了“ZYNQ7 Processing System”, 如图所示。该IP核为ZYNQ7 处理系统IP核,双击该IP核添加。 添加完成后的zynq IP核如图所
?
?大部分IP核在添加完成后,并不能直接满足用户的需求,我们还需对IP核 的接口信号以及一些相关参数进行配置
双击IP核 进入配置
Zynq 中的外设接口由对应控制器控制,使用时需要先进行使能。点击图形化向导界面的I/O Peripherals中对应的外设接口便可以跳转到相应的配置界面, 或者从左侧导航栏的MIO Configuration手动进入到配置界面。
本次设计通过PS与PL侧的按键控制另一侧的led灯,每个按键和led 灯都需要一个GPIO信号。在前面的原理部分我们有讲过,GPIO连接到PS部分使用的是MIO接口,连接到PL部分使用的则是EMIO接口,所以本次设计我们需要使能这两个外设接口。PS 端的引脚是固定的,我们不需要分配, PL端的按键和led灯都需要一个EMIO信号,因此我们将EMIO的位宽设置为2。设置完成后检查电平状态,将Bank1的电平设置为1.8V。
使能完外设接口后我们返回图形化向导界面,如图所示。可以看到在GPIO外设后面已经打上了√,代表此时我们已经使能该接口。在进行硬件逻辑系统搭建时,我们可以通过该界面快速一览使用到了哪些zynq资源。
接下来开始配置 DDR 型号,DDR 全名为双速率同步动态随机存储器 (Double Data Rate Synchronous Dynamic Random Access Memory),也就是我们常说的内存。基于PS端的应用,大部分都需要基于片外存储外设DDR上运行。 因此在使用时,我们需要配置DDR型号。 DDR 的配置同样可以通过图像化向导界面跳转,如所示,点击 DDR 控制 器,软件便会快速跳转。
?
配置完 DDR后即完成了本次 zynq IP 核的配置,点击 OK,可以看到此时 zynq IP 核如图 2-31所示,因为我们配置了GPIO外设,相较于配置前,此时多 了一个GPIO_0端口。?
然后导出引脚
导出完成后可以看到软件帮我们导出了zynq的两个引脚,但是 GPIO_0还 未导出,因此我们需要将其手动导出。?
?
端口连接
本次设计中zynq IP核在配置时,有几个端口信号是没有被使用到的,这几 个信号具体如下:
? FCLK_RESET0_N:全局复位信号,低电平有效。
? M_AXI_GPIO:通用AXI接口信号,M代表其作为主机信号。
? M_AXI_GPIO_ACLK:M_AXI_GPIO的输入时钟信号。
? FCLK_CLK0:PS输出时钟信号。 其中,M_AXI_GPIO_ACLK 虽然本次设计并未使用到,但是如果不给其一 个输入信号,软件便会报错。为了防止出现该现象,我们只需将 FCLK_CLK0 和M_AXI_GPIO_ACLK连接即可。连接时只需选中其中一个引脚按住鼠标左键 拖动到对应的引脚即可。如图所示
在涉及到的模块较多的场合,系统会出现自动连接(Run Connection Automation)的选项,如图? 所示。点击该项并设置需要连接的模块后,软件便会自动生成 AXI 互联 IP 核(AXI Interconnect)和处理器系统复位 IP 核 (Processor System Reset),并自动连接 AXI信号,部分时钟信号和复位信号。 但是软件在连接时,有时会将信号连接到用户期望之外的端口上。因此,连线复杂的设计通常需要手动对部分端口信号进行连接。?
验证设计
端口连接完成后使用快捷键 Ctrl+S 或者点击左上方的保存按钮保存设计, 随后点击上方的√来对设计进行验证。
?
?系统开始对设计进行验证,当出现以下弹窗时,证明设计无误。如果出现 警告,则需要重新检查系统。
点击sources资源栏下我们创建的system模块设计,单击右键,在展开的功 能中选择“Generate Output Products...”生成输出。
接下来软件会弹出生成输出前的设置界面,如图所示。在合成选项栏 直接选择“Out Of context per IP”即可,下方的“Number of jobs”选项选择最 大值。该值会影响生成输出时的速度,该值越大,生成输出的速度就越快,最 大值与电脑配置有关,设置完成后点击“Generate”开始生成。
?输出的生成比较慢需要等待一段时间,生成完成后软件会弹出如图 所 示弹窗,点击OK即可。
接着我们还是点击sources资源栏下我们创建的system模块设计,单击右键, 在展开的功能中选择“Create HDL Wrapper...”创建HDL封装。
在弹出的窗口中选择让 vivado管理封装和自动更新,随后点击 OK开始创 建封装。
当Sources栏出现蓝色名为system_wrapper的 设计文件时,则代表封装已经创建和更新完成,如图所示。
这里需要注意的是,system_wrapper.v 文件为顶层例化文件,在用户修改设 计并生成输出后,只要更新 Wrapper,system_wrapper.v 中的内容便会被覆盖。 若用户需要在顶层中手动加入一些语句,在修改硬件生成输出后只要更新 Wrapper这些语句便会被覆盖。如果您的设计中需要加入自己的逻辑代码,建议用户手动创建一个顶层文件,在文件中例化system_wrapper.v文件,并添加自己 的逻辑代码。
对于使用过PL端的设计,在完成封装后,我们需要对涉及到的管脚进行分 配和约束。点击左侧导航栏的“Open Elaborated Design”进行约束和分配。
打开后管脚约束界面如图所示,如果软件没有正确显示该界面,可以 将右上角的下拉栏展开,打开I/O Planning皆可切换到该页面。
在管脚约束界面中,我们需要做的是对使用到的PL端的管脚进行分配并对 管脚电平进行约束,本次设计所涉及到的为PL端的按键和PL端的LED灯。
具体管脚查询自己所用到的开发板型号说明文件 查询完成管脚分配
完成分配后使用快捷键 Ctrl+S 对约束文件进行保存,此时软件会弹出弹窗 让用户进行命名,将光标停在英文上即可出现对应翻译。在下方File name中对文件进行命名,这里读者可自行命名,只要符合命名规范即可。
完成了管脚约束后即可开始比特流的生成,比特流中包含着对PL端的配置信息,其中就包括对引脚的分配以及电平的约束,因此生成比特流需要在进行管脚分配和约束之后。当然如果设计并未使用到PL部分资源,可以直接跳过该 环节。 点击“Generate Bitstream”开始生成比特流,如图所示。此时软件会提示没有可用的实现结果,是否先进行综合实现再自动生成比特流,我们直接 点击Yes即可。
?
比特流生成的时间较长,需要耐心等待,在生成比特流时,vivado 软件右 上角会显示此时的运行状态,如图所示。
当比特流生成完成时,右上角会出现√的标识,?
首先点击 File,然后在展开的功能栏中选择 Export,最后在 Export 的多个 选择项中选择“ExportHardware...”将硬件描述文件导出。
此时软件会弹出弹窗询问我们是否包含比特流,对于本次设计,我们涉及到了 PL 端的资源使用,因此需要勾选比特流,如图 所示。勾选比特流后 点击OK开始导出。
比特流中包含有PL端的配置信息,因此对于涉及到PL端资源的设计,导 出硬件描述文件时我们需要包含比特流,以配置 PL。而对于纯 PS 端的设计, 用户在导出时无论是否勾选包含比特流都是可以的
硬件导出完成后 vivado 部分的设计已经完成,接下来打开 SDK开始 CPU 软件程序设计。点击File,在展开的功能栏中选择“Launch SDK”
接下来软件会弹出弹窗让我们设置硬件描述文件和工作空间的路径,这里我们保持默认即可,点击OK运行SDK。
2.9CPU软件程序设计
打开SDK软件界面如图 所示,其中“system_wrapper_hw_platform_0” 为从vivado中导出的硬件资源描述文件。
创建SDK工程
接下来会进入工程创建界面,如图所示。此时需要为工程命名, 其余部分软件已经帮我们设置好了,例如工程所支持的硬件平台,处理器型号 等。这里我们保持默认,点击Next进行下一步。?
这里我们需要为工程选择模板,选择 Empty Application,此时右边窗口便 会出现当前工程模板的描述,点击Finish完成工程创建。
创建完成可以看到工程资源中多了两个文件夹
?
?添加用户代码
如图所示,将工程下拉展开,右键单击 src 文件夹,在弹出的功能栏 中选择New/Source File。
接下来我们需要对该源文件命名,这里必须命名为 main.c,其余部分保持 默认即可。点击Finish完成创建。
完成创建后软件的编辑器自动帮我们打开了 main.c 文件,同时还打开了一 个system.mss的文件,如图所示。?
在写入用户代码前,我们先跳转到系统为我们打开的 system.mss 文件查看。 可以看到该文件除了对板级支持包进行了相关说明外,还提供了许多相关的驱 动例程和相关文档供开发者参考。
接下来返回main.c,向其中添加以下代码:
/*
* 使用PS_GPIO实现了按键控制LED功能:
* PS端按键按下→PL端的灯亮起,松开熄灭
* PL端按键按下→PS端的灯亮起,松开熄灭
*/
#include "COMMON.h"
int main(void)
{
u8 State; //存放按键(MIO47)的电平状态,0为低电平,1为高电平
PS_GPIO_Init(); //初始化PS端MIO和EMIO
//设置PS_LED(MIO7)为输出并且初始为低电平
PS_GPIO_SetMode(PS_LED, OUTPUT, 0);
//设置PL_LED(EMIO0)为输出并且初始为低电平
PS_GPIO_SetMode(PL_LED, OUTPUT, 0);
PS_GPIO_SetMode(PS_KEY, INPUT, 0); //设置PS_KEY(MIO47)方向为输入
PS_GPIO_SetMode(PL_KEY, INPUT, 0); //设置PL_KEY(EMIO1)方向为输入
while(1)
{
//读取PS_KEY的电平值并存储到State变量里
State = PS_GPIO_GetPort(PS_KEY);
//将State变量的值取非赋予PL_LED来输出
PS_GPIO_SetPort(PL_LED,!State);
//读取PL_KEY的电平值并存储到State变量里
State = PS_GPIO_GetPort(PL_KEY);
//将State变量的值取非赋予PS_LED来输出
PS_GPIO_SetPort(PS_LED,!State);
}
return 0;
}
Ctrl+S 保存设计,SDK 会自动编译,在确认编译无误后,接下来便可以开 始进行板级验证了。
点击我们创建的led工程,随后点击上方菜单栏的Run,在展开的功能选项 中选择“Run Configurations...”。软件会打开如图所示界面。
接下来我们要新建一个任务,将烧录文件下载到开发板中具体步骤如下:
① 双击GDB或System Debugger新建配置任务?
② 在右侧检查是否添加比特流文件和 PS初始化脚本,通常软件会自动添 加,如果没有,用户可以关闭并重新打开该界面或自己手动添加。比特 流只在使用到PL资源时需要,在纯PS的设计中不需要添加比特流。
③ 确认下方四个选项都被勾选,这四个选项分别是系统复位、配置 FPGA、 PS 初始化和 PL-PS 电平转换。后两个选项通常是默认勾选的,用户需 要手动勾选前两项以确保PL部分能够被正确配置。
④ 点击上方的Application切换到应用界面。
⑤ 检查.elf文件是否添加且烧录任务是否被选中。这里.elf文件由软件编译 产生,参与用户程序的运行。SDK默认情况下设置了自动编译,用户保 存设计后软件便会编译并生成.elf文件,所以当搜索不到.elf文件时检查 设计是否保存。
⑥ 点击“Run”开始烧录
下载完成后 即可观察板级结果