浙江苏省城乡建设厅网站,找做网站的客户,wordpress 发布时间,学院网站怎么做的#x1f389;欢迎来到FPGA专栏~bin文件ram存取回环测试 ☆* o(≧▽≦)o *☆嗨~我是小夏与酒#x1f379; ✨博客主页#xff1a;小夏与酒的博客 #x1f388;该系列文章专栏#xff1a;FPGA学习之旅 文章作者技术和水平有限#xff0c;如果文中出现错误#xff0c;希望大… 欢迎来到FPGA专栏~bin文件ram存取回环测试 ☆* o(≧▽≦)o *☆嗨~我是小夏与酒 ✨博客主页小夏与酒的博客 该系列文章专栏FPGA学习之旅 文章作者技术和水平有限如果文中出现错误希望大家能指正 欢迎大家关注 ❤️ 目录-bin文件ram存取回环测试 一、效果演示演示视频结果分析 二、说明三、bin文件的生成bin文件介绍为什么使用bin文件作为数据载体发送给FPGAmatlab生成bin文件 四、串口收发模块五、回环系统搭建系统功能描述ram ip核设置RTL视图系统完整代码 一、效果演示
使用matlab生成100个1-100的32位随机整型数据并将数据保存为bin文件通过带有bin文件收发功能的串口调试助手发送给FPGA再接收FPGA的回环数据。
演示视频 演示视频-【FPGA】bin文件ram存取回环测试 结果分析
matlab生成的随机数
串口助手接收结果 分析 将串口助手接收框内的数据转换成10进制并与matlab生成的数据进行对比数值一致串口助手接收框内的有效数据个数为100个与matlab生成的数据个数一致接收框内最后出现了FF这个数据并不是bin文件中的数据而是串口助手最后发送给FPGA的发送指令该指令也被存入到了ram中为了避免该现象的出现可以在FPGA中对数据进行相关的判断处理或者使用vio进行控制即可解决。
二、说明
需要该项目中的串口助手软件或者项目工程文件的小伙伴直接加入QQ群在群文件中搜索下载即可QQ群862135231。 matlab版本R2020b vivado版本2020.2 开发板型号AXKU040 接口连接如下所示
三、bin文件的生成
bin文件介绍 bin文件是二进制文件的缩写通常用于存储计算机程序或数据。它们可以包含各种类型的信息例如操作系统、应用程序和媒体文件。bin文件是计算机系统中最基本的文件类型之一通常需要特定的软件才能打开和读取。 不同类型的bin文件可能需要不同的软件来打开例如图像bin文件可能需要图像查看器来打开而文档bin文件可能需要文本编辑器来打开。 重点在这 bin文件可以储存大量数据的二进制形式
为什么使用bin文件作为数据载体发送给FPGA
ChatGPT的回答 bin文件作为一种固定的二进制数据格式具有以下优点使其成为向FPGA发送数据的常用载体
紧凑性bin文件通常比其他格式更紧凑减少了数据传输的带宽和存储空间需求。高效性FPGA可以直接读取和处理二进制数据而不需要进行格式转换提高了数据处理的效率。准确性bin文件中的数据以精确的二进制形式表示确保了数据的准确性和完整性。通用性bin文件是一种广泛使用的格式可以在不同的系统和硬件平台之间进行传输和使用。
matlab生成bin文件
运行如下代码会在matlab脚本的根目录下生成bin文件
%% bin文件生成代码
%----------------------------------------------------
% 首先生成1-100的double类型随机整数
% 将double类型随机整数转换为32位数据
% 将转换后的数据保存为bin文件。
%----------------------------------------------------
clear;
clc;
close all;
% 生成1-100的double类型随机整数
random_numbers randi([1 100], 1, 100);% 将double类型数据转换为uint32类型
random_numbers_uint32 uint32(random_numbers);% 将数据保存为bin文件
fid fopen(random_numbers.bin, wb);
fwrite(fid, random_numbers_uint32, uint32);
fclose(fid);disp(随机数已生成并保存为 random_numbers.bin);
四、串口收发模块
关于串口收发模块的详细讲解请点击如下两篇文章进行学习 串口发送模块【FPGA零基础学习之旅#13】串口发送模块设计与验证 串口接收模块【FPGA零基础学习之旅#15】串口接收模块设计与验证工业环境。
在此附上模块代码 串口发送模块 //
//模块名称串口发送模块
//
module uart_byte_tx(input Clk,input Rst_n,input [7:0] data_byte,input send_en,input [2:0] baud_set,output reg uart_tx,output reg Tx_Done,output reg uart_state
);reg bps_clk;//波特率时钟reg [15:0]div_cnt;//分频计数器reg [15:0]bps_DR;//分频计数最大值reg [3:0]bps_cnt;//波特率计数时钟//定义数据的起始位和停止位localparam START_BIT 1b0;localparam STOP_BIT 1b1;reg [7:0]r_data_byte;//数据寄存器//--------uart状态模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)uart_state 1b0;else if(send_en)uart_state 1b1;else if(bps_cnt 4d11)//bps_cnt计数达到11次即发送结束uart_state 1b0;elseuart_state uart_state;end//--------使能分频计数模块-------
// assign en_cnt uart_state;//--------寄存待发送的数据使数据保持稳定--------always(posedge Clk or negedge Rst_n)beginif(!Rst_n)r_data_byte 8d0;else if(send_en)r_data_byte data_byte;elser_data_byte r_data_byte;end//--------波特率查找表-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_DR 16d5207;else begincase(baud_set)0:bps_DR 16d5207;1:bps_DR 16d2603;2:bps_DR 16d1301;3:bps_DR 16d867;4:bps_DR 16d433;default:bps_DR 16d5207;endcaseend end//--------Div_Cnt模块--------
//得到不同计数周期的计数器always(posedge Clk or negedge Rst_n)beginif(!Rst_n)div_cnt 16d0;else if(uart_state)begin // assign en_cnt uart_state;if(div_cnt bps_DR)div_cnt 16d0;elsediv_cnt div_cnt 1b1;endelsediv_cnt 16d0;end
//--------bps_clk信号的产生-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_clk 1b0;else if(div_cnt 16d1)bps_clk 1b1;elsebps_clk 1b0;end//--------bps_cnt计数模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_cnt 4d0;else if(bps_cnt 4d11)//clr信号bps_cnt 4d0;else if(bps_clk)bps_cnt bps_cnt 1b1;elsebps_cnt bps_cnt;end//--------Tx_Done模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)Tx_Done 1b0;else if(bps_cnt 4d11)Tx_Done 1b1;elseTx_Done 1b0;end//--------数据位输出模块-10选1多路器-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)uart_tx 1b1;else begincase(bps_cnt)0:uart_tx 1b1;1:uart_tx START_BIT;2:uart_tx r_data_byte[0];3:uart_tx r_data_byte[1];4:uart_tx r_data_byte[2];5:uart_tx r_data_byte[3];6:uart_tx r_data_byte[4];7:uart_tx r_data_byte[5];8:uart_tx r_data_byte[6];9:uart_tx r_data_byte[7];10:uart_tx STOP_BIT;default:uart_tx 1b1;endcaseendendendmodule 串口接收模块 //
//模块名称串口接收模块工业环境
//
module uart_byte_rx(input Clk,//50Minput Rst_n,input [2:0] baud_set,input data_rx,output reg [7:0] data_byte,output reg Rx_Done
);reg s0_Rx,s1_Rx;//同步寄存器reg tmp0_Rx,tmp1_Rx;//数据寄存器reg [15:0]bps_DR;//分频计数器计数最大值reg [15:0]div_cnt;//分频计数器reg bps_clk;//波特率时钟reg [7:0]bps_cnt;reg uart_state;reg [2:0] r_data_byte [7:0];reg [2:0]START_BIT;reg [2:0]STOP_BIT;wire nedge;//--------同步寄存器处理--------
//用于消除亚稳态always(posedge Clk or negedge Rst_n)beginif(!Rst_n)begins0_Rx 1b0;s1_Rx 1b0;endelse begins0_Rx data_rx;s1_Rx s0_Rx;endend//--------数据寄存器处理-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)begintmp0_Rx 1b0;tmp1_Rx 1b0;endelse begintmp0_Rx s1_Rx;tmp1_Rx tmp0_Rx;endend//--------下降沿检测-------- assign nedge !tmp0_Rx tmp1_Rx;//--------div_cnt模块--------
//得到不同计数周期的计数器always(posedge Clk or negedge Rst_n)beginif(!Rst_n)div_cnt 16d0;else if(uart_state)beginif(div_cnt bps_DR)div_cnt 16d0;elsediv_cnt div_cnt 1b1;endelsediv_cnt 16d0;end
//--------bps_clk信号的产生-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_clk 1b0;else if(div_cnt 16d1)bps_clk 1b1;elsebps_clk 1b0;end//--------bps_clk计数模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_cnt 8d0;else if(bps_cnt 8d159 || (bps_cnt 8d12 (START_BIT 2)))bps_cnt 8d0;else if(bps_clk)bps_cnt bps_cnt 1b1;elsebps_cnt bps_cnt;end//--------Rx_Done模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)Rx_Done 1b0;else if(bps_cnt 8d159)Rx_Done 1b1;elseRx_Done 1b0;end //--------波特率查找表-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)bps_DR 16d324;else begincase(baud_set)0:bps_DR 16d324;1:bps_DR 16d162;2:bps_DR 16d80;3:bps_DR 16d53;4:bps_DR 16d26;default:bps_DR 16d324;endcaseend end//--------采样数据接收模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)beginSTART_BIT 3d0;r_data_byte[0] 3d0; r_data_byte[1] 3d0;r_data_byte[2] 3d0; r_data_byte[3] 3d0;r_data_byte[4] 3d0; r_data_byte[5] 3d0;r_data_byte[6] 3d0; r_data_byte[7] 3d0;STOP_BIT 3d0;endelse if(bps_clk)begincase(bps_cnt)0:beginSTART_BIT 3d0;r_data_byte[0] 3d0;r_data_byte[1] 3d0;r_data_byte[2] 3d0;r_data_byte[3] 3d0;r_data_byte[4] 3d0;r_data_byte[5] 3d0;r_data_byte[6] 3d0;r_data_byte[7] 3d0;STOP_BIT 3d0; end6,7,8,9,10,11:START_BIT START_BIT s1_Rx;22,23,24,25,26,27:r_data_byte[0] r_data_byte[0] s1_Rx;38,39,40,41,42,43:r_data_byte[1] r_data_byte[1] s1_Rx;54,55,56,57,58,59:r_data_byte[2] r_data_byte[2] s1_Rx;70,71,72,73,74,75:r_data_byte[3] r_data_byte[3] s1_Rx;86,87,88,89,90,91:r_data_byte[4] r_data_byte[4] s1_Rx;102,103,104,105,106,107:r_data_byte[5] r_data_byte[5] s1_Rx;118,119,120,121,122,123:r_data_byte[6] r_data_byte[6] s1_Rx;134,135,136,137,138,139:r_data_byte[7] r_data_byte[7] s1_Rx;150,151,152,153,154,155:STOP_BIT STOP_BIT s1_Rx;default:beginSTART_BIT START_BIT;r_data_byte[0] r_data_byte[0];r_data_byte[1] r_data_byte[1];r_data_byte[2] r_data_byte[2];r_data_byte[3] r_data_byte[3];r_data_byte[4] r_data_byte[4];r_data_byte[5] r_data_byte[5];r_data_byte[6] r_data_byte[6];r_data_byte[7] r_data_byte[7];STOP_BIT STOP_BIT;endendcaseendend//--------数据状态判定模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)data_byte 8d0;else if(bps_cnt 8d159)begindata_byte[0] r_data_byte[0][2];data_byte[1] r_data_byte[1][2];data_byte[2] r_data_byte[2][2];data_byte[3] r_data_byte[3][2];data_byte[4] r_data_byte[4][2];data_byte[5] r_data_byte[5][2];data_byte[6] r_data_byte[6][2];data_byte[7] r_data_byte[7][2];endelse;end//--------uart_state模块-------- always(posedge Clk or negedge Rst_n)beginif(!Rst_n)uart_state 1b0;else if(nedge)uart_state 1b1;else if(Rx_Done || (bps_cnt 8d12 (START_BIT 2)))uart_state 1b0;elseuart_state uart_state;endendmodule
五、回环系统搭建
系统功能描述
系统串口波特率设置为115200
功能描述 为了避免使用按键等作为触发或者控制信号本项目使用串口指令控制整个系统的运行因此设置了十六进制的fe和ff指令。通过串口助手发送十六进制的fe指令使能ram的储存再通过发送十六进制的ff指令让FPGA将ram中的数据通过串口发送出来。
ram ip核设置
选择普通双端口类型 由于串口接收到的数据位宽都是8位将ram的输入端口设置为8位便于存储和控制深度选择为2048一直使能 ram中的数据也是直接通过串口输出因此输出端口的数据位宽也设置为8位便于控制和读取选择使用使能引脚控制ram读取数据 在Summary中可以看到每个端口访问数据的地址位宽
RTL视图 系统完整代码 uart_top.v timescale 1ns / 1psmodule uart_top(input sys_clk_p,input sys_clk_n,input rst_n,input uart_rx,output uart_tx
);localparam baud_set 3b100;wire locked;wire clk_r;wire clk;wire [7:0] data_byte;reg En;reg send_en;reg [11-1:0] data_in_cnt;wire Rx_Done;wire write_en;reg [10:0] addrb;wire read_en;wire [7:0] data_byte_tx;clk50MHz instance_name(// Clock out ports.clk_out1(clk_r), // output clk_out1// Status and control signals.reset(!rst_n), // input reset.locked(locked), // output locked// Clock in ports.clk_in1_p(sys_clk_p), // input clk_in1_p.clk_in1_n(sys_clk_n)); // input clk_in1_nassign clk (locked)?clk_r:1b0;uart_byte_rx inst_uart_byte_rx(.Clk (clk),.Rst_n (rst_n),.baud_set (baud_set),.data_rx (uart_rx),.data_byte (data_byte),.Rx_Done (Rx_Done));//--------------------system_ctrl--------------------------------always(posedge clk or negedge rst_n)beginif(!rst_n)En 1b0;else if(data_byte 8hfe)En 1b1;elseEn En;endalways(posedge clk or negedge rst_n)beginif(!rst_n)send_en 1b0;else if(data_byte 8hff addrb 11d2000)send_en 1b1;else if(addrb 11d2000)send_en 1b0;elsesend_en send_en;end
//-----------------------------------------------------------------//--------------------data_in_cnt--------------------------------always(posedge clk or negedge rst_n)beginif(!rst_n)data_in_cnt 11d0;else if((En) (data_in_cnt 11d2047) Rx_Done)data_in_cnt data_in_cnt 1b1;else if(data_in_cnt 11d2047)data_in_cnt 11d0;elsedata_in_cnt data_in_cnt;end
//-----------------------------------------------------------------assign write_en (En !(send_en))?1b1:1b0;ram_ip ram_8_2048_8(.clka (clk), // input wire clka.wea (write_en), // input wire [0 : 0] wea.addra (data_in_cnt), // input wire [10 : 0] addra.dina (data_byte), // input wire [7 : 0] dina.clkb (clk), // input wire clkb.enb (read_en), // input wire enb.addrb (addrb), // input wire [10 : 0] addrb.doutb (data_byte_tx) // output wire [7 : 0] doutb);assign read_en (send_en Tx_Done)?1b1:1b0;always(posedge clk or negedge rst_n)beginif(!rst_n)addrb 11d0;else if(Tx_Done)addrb addrb 1b1;elseaddrb addrb;enduart_byte_tx inst_uart_byte_tx(.Clk (clk),.Rst_n (rst_n),.data_byte (data_byte_tx),.send_en (send_en),.baud_set (baud_set),.uart_tx (uart_tx),.Tx_Done (Tx_Done),.uart_state ());endmodule 结尾 ❤️ 感谢您的支持和鼓励 您可能感兴趣的内容【FPGA零基础学习之旅#17】搭建串口收发与储存双口RAM系统【Python】串口通信-与FPGA、蓝牙模块实现串口通信PythonFPGA 【Arduino TinyGo】【最新】使用Go语言编写Arduino-环境搭建和点亮LED灯【全网首发开源教程】【Labview机器人仿真与控制】Labview与Solidworks多路支配关系-四足爬行机器人仿真与控制