VL9 使用子模块实现三输入数的大小比较

文章讲述了在数字芯片设计中,如何通过创建子模块来比较8bit数值并找出最小值。两种方法被提出:一是使用时序逻辑的三个子模块分别进行两次比较;二是利用组合逻辑的两个子模块并在主模块中延迟一拍来完成三数比较。
摘要由CSDN通过智能技术生成

题目描述

在数字芯片设计中,通常把完成特定功能且相对独立的代码编写成子模块,在需要的时候再在主模块中例化使用,以提高代码的可复用性和设计的层次性,方便后续的修改。

请编写一个子模块,将输入两个8bit位宽的变量data_a,data_b,并输出data_a,data_b之中较小的数。并在主模块中例化,实现输出三个8bit输入信号的最小值的功能。

子模块的信号接口图如下:
在这里插入图片描述
主模块的信号接口图如下:
在这里插入图片描述
输入描述:
clk:系统时钟
rst_n:异步复位信号,低电平有效
a,b,c:8bit位宽的无符号数
输出描述:
d:8bit位宽的无符号数,表示a,b,c中的最小值

代码实现方式1

使用时序逻辑子模块
需要调用3个模块,其中:第一个模块:比较 T 时刻的 a 和 b,T+1 时刻出来 tmp1; 第二个模块:比较 T 时刻的 a 和 c,T+1 时刻出来 tmp2; 第三个模块:比较 T+1 时刻的 tmp1 和 tmp2,T+2 时刻出来 d;

如果只用2个子模块,那么 T 时刻比较 a 和 b 得到 tmp1,再比较 tmp1 和 c 的时候是 T+1 时刻的 c和 T+1 时刻的 tmp1,而 tmp1 代表的是 T 时刻 a 和 b 的较小值,所以这时候比较的 T 时刻的 a、b和 T+1 时刻的 c,显然不符合要求。

`timescale 1ns/1ns
module main_mod(
	input clk,
	input rst_n,
	input [7:0]a,
	input [7:0]b,
	input [7:0]c,
	
	output [7:0]d
);
//*************code***********//
// T 时刻的 a 和 b,T+1 时刻出来 tmp1
wire [7:0] tmp1; // a b 的最小值
child_mod U0(
 .clk ( clk ),
 .rst_n ( rst_n ),
 .a ( a ),
 .b ( b ),
 .d ( tmp1 )
);

// T 时刻的 a 和 c,T+1 时刻出来 tmp2
wire [7:0] tmp2; // a c 的最小值
child_mod U1(
 .clk ( clk ),
 .rst_n ( rst_n ),
 .a ( a ),
 .b ( c ),
 .d ( tmp2 )
);

// T+1 时刻的 tmp1 和 tmp2,T+2 时刻出来 d
child_mod U2(
 .clk ( clk ),
 .rst_n ( rst_n ),
 .a ( tmp1 ),
 .b ( tmp2 ),
 .d ( d )
);
endmodule

// 子模块
module child_mod(  //child_mod模块中包含时序逻辑
 input clk,
 input rst_n,
 input [7:0]a,
 input [7:0]b,
 output [7:0]d
);

reg [7:0] d_reg;
always @ (posedge clk or negedge rst_n)
begin
	if( ~rst_n ) begin
		d_reg<= 8'b0;
 	end
	else begin
 		if( a > b )
 			d_reg<= b;
 		else
 			d_reg<= a;
	 end
end
assign d = d_reg;
//*************code***********//
endmodule

代码实现方式2

使用组合逻辑子模块,需要打两拍。
组合逻辑的子模块,就不存在时序逻辑中的延时问题,所以调用的时候用2个子模块就可以完成3个数的比较,为了符合时序波形的要求,多打一拍

关于FPGA中“打一拍”的含义,我们可以理解为把某个信号延迟了一个时钟周期。“打两拍”就是延迟两个时钟周期,即打一拍就是系统时钟对外部信号采样一次,把采样的结果数据做为下一步的控制状态

如果是使用2个子模块

T时刻比较a、b,在T+1时刻输出最小值tmp1,在T+2时刻得到T+1时的c和T+1时的tmp1的最小值;
注意,这样比较完就是拿T时刻的a、b和T+1时刻的c比较
`timescale 1ns/1ns
module main_mod(
	input clk,
	input rst_n,
	input [7:0]a,
	input [7:0]b,
	input [7:0]c,
	
	output [7:0]d
);
//*************code***********//
wire [7:0] tmp1; // a b 的最小值
child_mod U0(
 .a ( a ),
 .b ( b ),
 .d ( tmp1 )
);
 
wire [7:0] tmp2; // a c 的最小值
child_mod U1(
 .a ( tmp1 ),
 .b ( c ),
 .d ( tmp2 )
);
 
reg [7:0] d_reg;
reg [7:0] d_reg2;
always @ (posedge clk or negedge rst_n)
begin
 	if( ~rst_n ) begin
 		d_reg  <= 8'b0;
 		d_reg2 <= 8'b0;
 		end
	 else begin
 		d_reg  <= tmp2; //为了符合时序波形的要求,多打一拍
 		d_reg2 <= d_reg;
 		end
 end
 
assign d = d_reg2;
endmodule

module child_mod(  //child_mod模块中只有组合逻辑
 input [7:0]a,
 input [7:0]b,
 output [7:0]d
);
assign d = (a>b) ? b : a;

//*************code***********//
endmodule
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

大西瓜的科研日记

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值