紫光同创FPGA开发板LED流水灯实现教程

发布时间:2026/7/17 19:24:58
紫光同创FPGA开发板LED流水灯实现教程 1. 盘古PGX-MINI-4K开发板硬件概览紫光同创盘古PGX-MINI-4K开发板是一款基于国产FPGA芯片PGC4KD-6ILPG144设计的开发平台。作为国产FPGA生态中的重要组成部分这款开发板在硬件设计上充分考虑了初学者的使用需求。开发板采用Type-C接口供电真正实现了一根线搞定所有的便捷体验。板载资源包括两组20PIN扩展IO接口、四位八段数码管、四个机械按键以及八个可编程LED灯。开发板的核心芯片PGC4KD-6ILPG144属于紫光同创Compa系列FPGA具有4K逻辑单元规模采用LUT4架构工作电压范围为1.2V支持多种配置模式。特别值得一提的是该开发板集成了JTAG调试接口省去了外接下载器的麻烦大大降低了初学者的入门门槛。在LED硬件电路设计上开发板采用了经典的共阳极连接方式每个LED通过一个限流电阻连接到FPGA的IO口。当FPGA对应IO输出低电平时LED点亮输出高电平时LED熄灭。这种设计在保证安全性的同时也简化了程序控制逻辑。2. 开发环境搭建与项目创建2.1 软件工具准备要进行FPGA开发首先需要安装紫光同创官方提供的PDS开发环境。目前最新版本为PDS 2022.1可以从紫光同创官网下载。安装过程需要注意以下几点安装路径不要包含中文或特殊字符安装完成后需要手动添加License文件建议同时安装USB驱动确保开发板能够被正确识别安装完成后打开PDS软件界面布局与主流EDA工具类似主要包括工程管理窗口、设计输入窗口、综合报告窗口等几个主要区域。2.2 新建工程步骤点击File→New→Project创建新工程选择正确的设备型号PGC4KD-6ILPG144设置工程存放路径同样避免中文路径在Add Source步骤可以先跳过后续再添加设计文件完成工程创建后建议立即进行保存提示初次使用PDS时建议在工程设置中将Enable Message Suppression选项关闭这样可以获取更详细的编译和调试信息便于排查问题。2.3 硬件连接与检测将开发板通过Type-C接口连接到电脑后需要确认设备管理器能够正确识别开发板。正常情况下会显示Tang Primer USB-JTAG设备。如果出现黄色感叹号可能需要手动安装驱动。可以通过PDS软件的Programmer工具检测开发板连接状态。点击Auto Detect按钮如果一切正常应该能够看到检测到的FPGA设备信息。这一步非常重要确保后续的程序下载能够正常进行。3. LED流水灯设计原理3.1 硬件电路分析盘古PGX-MINI-4K开发板上的LED采用共阳极连接方式电路原理如下图所示FPGA IO口 → 220Ω限流电阻 → LED阳极 → LED阴极 → GND这种连接方式意味着当FPGA IO输出低电平(0)时形成电流通路LED点亮当FPGA IO输出高电平(1)时没有电势差LED熄灭开发板上的8个LED分别连接到FPGA的以下IO口LED编号FPGA管脚网络标号LED0P44LED[0]LED1P45LED[1]LED2P46LED[2]LED3P47LED[3]LED4P48LED[4]LED5P49LED[5]LED6P50LED[6]LED7P51LED[7]3.2 流水灯实现原理流水灯效果的本质是按照特定规律依次点亮和熄灭LED。要实现这一效果需要考虑以下几个关键点时序控制需要设计一个计数器来产生时间基准控制LED状态变化的节奏状态转换定义LED点亮的顺序和模式左移、右移、交替等消抖处理虽然LED控制不需要消抖但良好的设计习惯应该考虑信号的稳定性在FPGA中通常使用时钟分频产生的定时信号来控制流水速度。例如使用50MHz的系统时钟通过分频产生1Hz的信号就能实现每秒移动一次的流水效果。4. Verilog代码实现详解4.1 顶层模块设计首先创建顶层模块led_water_flow.v定义模块接口module led_water_flow( input wire clk, // 50MHz系统时钟 input wire rst_n, // 低电平复位信号 output reg [7:0] led // 8位LED输出 );顶层模块主要完成以下功能接收50MHz时钟和复位信号输出8位LED控制信号实例化定时器和LED控制逻辑4.2 时钟分频设计为了产生适合人眼观察的流水效果需要对50MHz系统时钟进行分频。设计一个32位计数器在计数值达到25,000,000时对应0.5秒产生一个脉冲信号reg [31:0] counter; reg timer_tick; always (posedge clk or negedge rst_n) begin if(!rst_n) begin counter 32d0; timer_tick 1b0; end else if(counter 32d24_999_999) begin counter 32d0; timer_tick 1b1; end else begin counter counter 32d1; timer_tick 1b0; end end这段代码实现了一个简单的分频器每0.5秒产生一个时钟周期的高电平脉冲timer_tick用于触发LED状态变化。4.3 LED状态机设计LED流水效果可以通过状态机来实现。这里设计一个8状态的状态机每个状态对应一个LED点亮的位置reg [2:0] state; always (posedge clk or negedge rst_n) begin if(!rst_n) begin state 3d0; led 8b1111_1110; // 初始状态LED0点亮 end else if(timer_tick) begin case(state) 3d0: begin led 8b1111_1101; state 3d1; end 3d1: begin led 8b1111_1011; state 3d2; end 3d2: begin led 8b1111_0111; state 3d3; end 3d3: begin led 8b1110_1111; state 3d4; end 3d4: begin led 8b1101_1111; state 3d5; end 3d5: begin led 8b1011_1111; state 3d6; end 3d6: begin led 8b0111_1111; state 3d7; end 3d7: begin led 8b1111_1110; state 3d0; end default: begin led 8b1111_1110; state 3d0; end endcase end end这种实现方式虽然代码量稍大但逻辑清晰便于理解和修改。每个时钟分频脉冲到来时LED点亮位置向右移动一位形成流水效果。4.4 移位寄存器实现方案除了状态机方案还可以使用移位寄存器来实现流水灯效果代码更加简洁reg [7:0] led_pattern; always (posedge clk or negedge rst_n) begin if(!rst_n) begin led_pattern 8b1111_1110; end else if(timer_tick) begin led_pattern {led_pattern[6:0], led_pattern[7]}; end end assign led led_pattern;这种实现方式利用Verilog的位拼接操作每次将最高位移到最低位实现循环移位效果。代码更加简洁但可能对初学者理解起来稍有难度。5. 约束文件配置与下载验证5.1 管脚约束文件配置在FPGA开发中约束文件用于指定模块端口与实际物理管脚的对应关系。创建led_water_flow.pdc文件添加以下内容# 系统时钟连接到开发板50MHz晶振 set_pin_assignment { clk } { LOCATION P23; } # 复位按键连接到开发板K4按键 set_pin_assignment { rst_n } { LOCATION P38; IOSTANDARD LVCMOS33; PULLTYPE PULLUP; } # LED输出管脚约束 set_pin_assignment { led[0] } { LOCATION P44; IOSTANDARD LVCMOS33; } set_pin_assignment { led[1] } { LOCATION P45; IOSTANDARD LVCMOS33; } set_pin_assignment { led[2] } { LOCATION P46; IOSTANDARD LVCMOS33; } set_pin_assignment { led[3] } { LOCATION P47; IOSTANDARD LVCMOS33; } set_pin_assignment { led[4] } { LOCATION P48; IOSTANDARD LVCMOS33; } set_pin_assignment { led[5] } { LOCATION P49; IOSTANDARD LVCMOS33; } set_pin_assignment { led[6] } { LOCATION P50; IOSTANDARD LVCMOS33; } set_pin_assignment { led[7] } { LOCATION P51; IOSTANDARD LVCMOS33; }5.2 综合与实现完成代码编写和约束文件配置后按照以下步骤进行综合与实现点击Flow菜单中的Synthesize进行综合综合完成后点击Implement进行布局布线实现过程完成后查看时序报告确保没有时序违例生成比特流文件(.fs)注意初次使用时可能会遇到一些警告信息如Net xxx has no load等这些通常与未使用的管脚或信号有关不影响基本功能但良好的设计习惯应该处理所有警告。5.3 程序下载与调试将生成的.fs文件下载到开发板的步骤如下确保开发板已正确连接电脑打开PDS Programmer工具点击Add File选择生成的.fs文件确保编程选项选择SRAM模式掉电后程序会丢失点击Program按钮开始下载下载完成后应该能看到开发板上的LED开始从右向左流动显示。如果按下K4按键复位键LED会恢复到初始状态。6. 功能扩展与进阶实验6.1 流水速度调节可以通过修改分频系数来调整流水速度。例如要加快流水速度可以减小分频系数else if(counter 32d12_499_999) begin // 0.25秒 counter 32d0; timer_tick 1b1; end也可以添加一个速度控制开关通过开发板上的拨码开关来选择不同的分频系数实现动态调速。6.2 流水方向控制扩展设计添加方向控制功能。使用开发板上的一个按键来控制流水方向input wire dir_key, // 方向控制按键 // 在状态机或移位寄存器逻辑中添加方向判断 if(dir_key) begin // 向右流动 led_pattern {led_pattern[0], led_pattern[7:1]}; end else begin // 向左流动 led_pattern {led_pattern[6:0], led_pattern[7]}; end6.3 多种流水模式实现通过状态机实现多种流水模式切换如单灯流水双灯追逐全亮全灭呼吸效果随机点亮模式可以使用开发板上的多个按键来切换不同模式每种模式对应不同的LED控制逻辑。6.4 使用PWM实现亮度渐变在简单的开关控制基础上可以引入PWM脉宽调制技术实现LED亮度的渐变效果reg [7:0] pwm_counter; reg [7:0] pwm_value; reg pwm_out; always (posedge clk) begin pwm_counter pwm_counter 8d1; pwm_out (pwm_counter pwm_value) ? 1b0 : 1b1; end // 将pwm_out连接到LED控制信号通过改变pwm_value的值可以调节LED的亮度实现呼吸灯等更丰富的视觉效果。7. 常见问题与调试技巧7.1 LED不亮或全部常亮这是最常见的现象可能原因包括管脚约束错误检查.pdc文件中的管脚分配是否正确极性理解错误确认LED是共阳极还是共阴极连接程序未正确下载检查下载过程和下载模式设置复位信号问题确保复位信号正常工作7.2 流水速度异常如果流水速度与预期不符检查时钟分频计算是否正确确认系统时钟频率是否为50MHz查看综合后的时序报告确认时钟网络延迟7.3 个别LED不工作如果大部分LED正常只有个别不工作检查对应LED的硬件电路包括电阻和LED本身测量FPGA对应管脚是否有信号输出确认约束文件中该管脚的配置正确7.4 调试技巧分享使用SignalTap逻辑分析仪PDS工具内置了SignalTap功能可以实时捕获内部信号非常有助于调试分模块验证先验证时钟分频模块是否正常工作再逐步添加其他功能简化测试可以先设计一个简单的LED闪烁程序确认基本功能正常后再实现复杂逻辑查阅官方文档紫光同创提供了详细的器件手册和开发板资料遇到问题时应该首先查阅相关文档8. 项目总结与进阶学习建议通过这个LED流水灯实验我们完成了FPGA开发的全流程实践包括开发环境搭建Verilog代码编写约束文件配置综合与实现程序下载与调试这个简单的项目涵盖了FPGA开发的基本要素是学习数字逻辑设计的良好起点。在实际操作中我发现紫光同创PDS工具链虽然界面友好但在一些细节处理上仍需注意比如约束文件的语法与其他厂商略有不同。对于想要进一步学习的开发者建议从以下几个方向深入学习更复杂的时序电路设计如FSM有限状态机研究FPGA的时钟管理和时序约束尝试外设接口开发如UART、SPI、I2C等探索基于FPGA的嵌入式系统设计如使用RISC-V软核国产FPGA生态正在快速发展掌握紫光同创FPGA开发技术将为未来的职业发展带来更多机会。这个流水灯项目虽然简单但已经包含了FPGA开发的核心思想希望读者能够通过这个入门实验开启自己的FPGA开发之旅。