Quartus RS232 UART IP核 使用 Verilog

本文将以 uart 发送为例,介绍 Quartus 的 RS232 UART IP 核的配置方法

一、UART 模块的配置及添加

1、调用 IP Catalog 界面

Tools —> IP Catalog
在这里插入图片描述

2、搜索找到并双击打开 RS232 UART

双击后会引导填写名称及存放路径,设置好后会自动打开 Platform Designer 页面
在这里插入图片描述

3、UART 参数配置

Parameters 这里的 Avalon Type 选择 Streaming,也就是数据流模式,我们将按字节传入和传出数据
其它配置项与常用 UART 无异
在这里插入图片描述

4、时钟配置

因为配置波特率的相关参数是该 IP 核自动实现的,所以需要加入时钟模块,告知系统输入时钟的频率
(1)View —> System Contents 打开 System Contents 配置界面
在这里插入图片描述
(2)View —> IP Catelog 打开 IP Catalog 搜索 clock 并双击添加 Clock Source
在这里插入图片描述
(3)配置将要为 UART 模块提供的数据频率,这里是 50 MHz
在这里插入图片描述
(4)连接时钟模块与 UART 模块的 clk 和 reset
在这里插入图片描述

5、Generate —> Generate HDL 生成模块

6、在 Quartus 中添加生成的模块

(1)先将 Project Navigator 设置为 Files,然后在 Files 处右键选择 Add
在这里插入图片描述
(2)添加刚刚生成的模块,然后点击 OK 保存
在这里插入图片描述

二、顶层文件的引用

1、实例化

从 Platform Designer 生成模块实例,将其拷贝到 Quartus 的顶层文件中
Generate —> Generate Instantiation Template 打开 Instantiation Template
HDL Language 选择 Verilog,Copy 该实例,粘贴到顶层文件中
在这里插入图片描述

2、网络连接

uart u0 (
	.clk_clk (clk), // clk.clk
	.reset_reset_n (rst_n), // reset.reset_n
//	.rs232_0_from_uart_ready (<connected-to-rs232_0_from_uart_ready>), // rs232_0_avalon_data_receive_source.ready
//	.rs232_0_from_uart_data (<connected-to-rs232_0_from_uart_data>), // .data
//	.rs232_0_from_uart_error (<connected-to-rs232_0_from_uart_error>), // .error
//	.rs232_0_from_uart_valid (<connected-to-rs232_0_from_uart_valid>), // .valid
	.rs232_0_to_uart_data (uart_send_data), // rs232_0_avalon_data_transmit_sink.data
//	.rs232_0_to_uart_error (<connected-to-rs232_0_to_uart_error>), // .error
	.rs232_0_to_uart_valid (uart_send_valid), // .valid
	.rs232_0_to_uart_ready (uart_send_ready), // .ready
	.rs232_0_UART_RXD (uart_rx), // rs232_0_external_interface.RXD
	.rs232_0_UART_TXD (uart_tx) // .TXD
);

将带有 from 的连线(UART 接收数据使用的)及不用的连线注释掉,只连接发送数据需要用到的连线

三、发送逻辑的实现

1、UART TX 不忙时 rs232_0_to_uart_ready 为1,表示已经准备好发送数据了
2、这时将 rs232_0_to_uart_valid 置1,UART 将开始对 rs232_0_to_uart_data 的端口的数据进行发送
3、对于发送的控制:如果想在发完一个字节后停止或者发送一个字节改变数据(紧接着发送第二个字节),控制时序需要与 UART 模块的 clk_clk 同步。
下面的代码实现的是:发送一个字节停止,等待1s后发送下一个字节

module FPGA_UART (
	input clk,
	input rst_n,
	input uart_rx,
	output uart_tx
);

reg [7:0] uart_send_data = 8'd0;
reg uart_send_valid;
wire uart_send_ready;

reg [31:0] counter = 32'd0;

parameter state_wait = 4'd0;
parameter state_send = 4'd1;
reg [3:0] state = state_wait;

reg send_flag = 0;

always@(posedge clk or negedge rst_n) begin
	if(!rst_n) begin
		uart_send_valid <= 0;
		counter <= 32'd0;
		uart_send_data <= 8'd0;
		state <= state_wait;
		send_flag = 0;
	end
	else begin
		case (state)
			state_wait: begin
				counter <= counter + 32'd1;
				if(counter >= 32'd49999999) begin
					counter <= 32'd0;
					state <= state_send;
				end
			end
			state_send: begin
				if(uart_send_ready && !send_flag) begin
					send_flag <= 1;
					uart_send_valid <= 1;
				end
				else begin
					uart_send_data <= uart_send_data + 8'd1;
					uart_send_valid <= 0;
					state <= state_wait;
					send_flag <= 0;
				end
			end
		endcase
	end
end

uart u0 (
	.clk_clk (clk), // clk.clk
	.reset_reset_n (rst_n), // reset.reset_n
//	.rs232_0_from_uart_ready (<connected-to-rs232_0_from_uart_ready>), // rs232_0_avalon_data_receive_source.ready
//	.rs232_0_from_uart_data (<connected-to-rs232_0_from_uart_data>), // .data
//	.rs232_0_from_uart_error (<connected-to-rs232_0_from_uart_error>), // .error
//	.rs232_0_from_uart_valid (<connected-to-rs232_0_from_uart_valid>), // .valid
	.rs232_0_to_uart_data (uart_send_data), // rs232_0_avalon_data_transmit_sink.data
//	.rs232_0_to_uart_error (<connected-to-rs232_0_to_uart_error>), // .error
	.rs232_0_to_uart_valid (uart_send_valid), // .valid
	.rs232_0_to_uart_ready (uart_send_ready), // .ready
	.rs232_0_UART_RXD (uart_rx), // rs232_0_external_interface.RXD
	.rs232_0_UART_TXD (uart_tx) // .TXD
);


endmodule

综合下载到开发板,用上位机观察数据,与预期结果一致,每秒发送一个字节:
在这里插入图片描述
如果想要实现,不停歇地将一组多个字节的数据依次发送,可以这样修改:

reg send_flag = 0; // 这个标志位的作用应该是表示移出数据标志位,这里懒得改了
reg end_flag = 0;
reg [15:0] data_buf = 16'h1236; // 测试数据

always@(posedge clk or negedge rst_n) begin
	if(!rst_n) begin
		uart_send_valid <= 0;
		counter <= 32'd0;
		uart_send_data <= 8'd0;
		state <= state_wait;
		send_flag = 0;
	end
	else begin
		case (state)
			state_wait: begin
				counter <= counter + 32'd1;
				if(counter >= 32'd49999999) begin
					counter <= 32'd0;
					state <= state_send;
					uart_send_data <= data_buf[7:0]; // 提前移出第一个字节
				end
			end
			state_send: begin
				if(end_flag) begin
					end_flag <= 0;
					uart_send_valid <= 0;
					send_flag <= 0;
					state <= state_wait;
				end
				else begin
					uart_send_valid <= 1;
					send_flag <= 1;
					if(send_flag) begin // 这里是为了让uart_send_valid维持一个周期后等第一个字节发送完成后移出后面的字节
						uart_send_data <= data_buf[15:8]; // 模拟字节移出
						end_flag = 1; // 强行退出发送状态,实际运用中会判断数据长度
					end
				end
			end
		endcase
	end
end

观察运行情况,每一秒发送两个字节,分别是 0x36,0x12:
在这里插入图片描述

  • 3
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
FPGA控制RS232串口通信实现verilog设计Quartus9.1工程源码 module ex5_rs232( clk_in,ext_rst_n, rs232_rx,rs232_tx ); input clk_in; // 25MHz主时钟 input ext_rst_n; //外部输入复位信号,低有效 input rs232_rx; // RS232接收数据信号 output rs232_tx; // RS232发送数据信号 //---------------------------------------------------- wire rst_n; //低电平复位信号 wire bps_start1,bps_start2; //接收到数据后,波特率时钟启动信号置位 wire clk_bps1,clk_bps2; // clk_bps_r高电平为接收数据位的中间采样点,同时也作为发送数据的数据改变点 wire[7:0] rx_data; //接收数据寄存器,保存直至下一个数据来到 wire rx_int; //接收数据中断信号,接收到数据期间始终为高电平 reg clk; always@(posedge clk_in) clk = ~clk; //--------------------------------------------------- //复位产生模块 sys_ctrl uut_sc( .clk(clk), .ext_rst_n(ext_rst_n), .rst_n(rst_n) ); //--------------------------------------------------- //下面的四个模块中,speed_rx和speed_tx是两个完全独立的硬件模块,可称之为逻辑复制 //(不是资源共享,和软件中的同一个子程序调用不能混为一谈) //////////////////////////////////////////// speed_select speed_rx( .clk(clk), //波特率选择模块 .rst_n(rst_n), .bps_start(bps_start1), .clk_bps(clk_bps1) ); uart_rx my_uart_rx( .clk(clk), //接收数据模块 .rst_n(rst_n), .rs232_rx(rs232_rx), .rx_data(rx_data), .rx_int(rx_int), .clk_bps(clk_bps1), .bps_start(bps_start1) ); /////////////////////////////////////////// speed_select speed_tx( .clk(clk), //波特率选择模块 .rst_n(rst_n), .bps_start(bps_start2), .clk_bps(clk_bps2) ); uart_tx my_uart_tx( .clk(clk), //发送数据模块 .rst_n(rst_n), .rx_data(rx_data), .rx_int(rx_int), .rs232_tx(rs232_tx), .clk_bps(clk_bps2), .bps_start(bps_start2) ); endmodule
### 回答1: Quartus FIR II IP核是一个数字信号处理器件,用于实现数字滤波器。它可以用于滤波、降噪、信号增强等应用。使用Quartus FIR II IP核,可以快速实现数字滤波器的设计和开发,提高开发效率和设计质量。在使用Quartus FIR II IP核时,需要根据实际需求进行配置和参数设置,以实现所需的滤波效果。同时,还需要进行仿真和验证,确保设计的正确性和稳定性。 ### 回答2: Quartus FIR II IP核是Altera Quartus软件的一部分,主要用于数字信号处理领域中的低通滤波、高通滤波和带通滤波等应用。Quartus FIR II IP核是一种现成的数字信号处理模块,基于FIR (Finite Impulse Response)滤波器的结构设计而成,能够快速有效地进行滤波处理。 使用Quartus FIR II IP核进行滤波处理非常简便,只需要在Altera Quartus软件中进行一些简单的配置,即可完成整个滤波处理过程。首先,需要在Quartus软件中打开IP Catalog(IP目录),选择FIR II Filter(FIR II滤波器),并将其添加到设计中。接下来,需要设置FIR II滤波器的参数,如滤波器的类型、阶数、采样率以及滤波器的系数等。然后将需要进行滤波处理的信号输入到滤波器中,进行滤波处理后,再将输出信号发送到下一级电路进行后续处理。 使用Quartus FIR II IP核的优点在于可以大大简化数字信号处理的设计流程,减轻设计人员的工作负担,同时也可以提高设计的效率和可靠性。此外,使用Quartus FIR II IP核所需的硬件资源也比较少,并且可以在FPGA芯片上实现,因此可以大大降低系统成本和功耗消耗。 总之,Quartus FIR II IP核是数字信号处理领域中常用的一种设计核心,可以用于实现低通滤波、高通滤波、带通滤波等各种滤波器,具有使用简便、性能稳定、资源消耗低等优点。在实际应用中,设计人员可以根据实际需求,灵活选择Quartus FIR II IP核的参数和配置,以便完成各种数字信号处理的任务。 ### 回答3: Quartus FIR II IP核是一个数字信号处理器件(DSP)的一部分,用于FIR(有限脉冲响应)滤波器的设计和实现。 使用Quartus FIR II IP核的第一步是打开Quartus软件,并创建一个新的项目。然后,用户需要在设计中添加一个FIR II IP核。在添加后,用户可以配置核的参数,如系数,滤波器类型和采样率等。 然后,基于定义的参数使用"IP Parametrization"功能生成基础模板。使用此模板,用户可以进行IP核设计的修改和代码生成。在设计阶段,用户可以按照特定的需求自定义参数。例如:修改系数值,改变滤波器类型等等。在定制完毕后,用户可以通过Quartus软件编译该设计,并下载到FPGA中进行测试。 在设计过程中,用户可以使用导出文件功能,将设计导出到其他数据格式。此外,用户可以根据需求在模板中添加自定义IP核供以后使用。 总的来说,使用Quartus FIR II IP核是一个相对简单的过程,但它需要用户具备一定的FPGA设计知识。Quartus FIR II IP核提供了一个可配置的平台与基础模板,使得该过程相对轻松,快捷,且高效。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值