题意整理

1、在硬件中进行乘除法运算是比较消耗资源的一种方法,想要在不影响延迟并尽量减少资源消耗,必须从硬件的特点上进行设计。根据寄存器的原理,由于是二进制,所以进位和退位为x2或者/2,同样除7可以使用进位3然后减去本身的做法,这样就将乘除法运算转化为位运算,这是一种比较简单的整数运算处理。

2、 需要给出一个计数器的状态机,注意d输入不是随时有效的,只有在cnt计数为0的那个时钟沿,d输入有效,因此需要设计一个寄存器din,在cnt为0时候锁存d的值

题解主体

根据题意分析,可以得到状态转换:

设输入为d,计数器为cnt

移位运算逻辑:

位运算

1

d

3

(din<<2)-din

7

(din<<3)-din

8

(din<<3)

状态机逻辑:

cnt

out

input_grant

0

直接输出d,并寄存d的值为din

1

1

(din<<2)-din

0

2

(din<<3)-din

0

3

(din<<3)

0

将电路转换成Verilog代码描述如下



reg [1:0]cnt;

reg [7:0]din;


always@(posedge clk or negedge rst) begin

       if(!rst) begin

              cnt <= 0;

              out <= 0;

              input_grant <= 0;

              din <= 0;

       end

       else begin

              cnt <= cnt+1;

              case (cnt)

                     0: begin

                            din <= d;

                            input_grant <= 1;

                            out <= d;

                     end

                     1: begin

                            input_grant <= 0;

                            out <= (din<<2)-din;

                     end       

                     2: begin

                            input_grant <= 0;

                            out <= (din<<3)-din;

                     end

                     3: begin

                            input_grant <= 0;

                            out <= (din<<3);

                     end

              endcase

       end




end


因此实现方式为如下的电路,综合得到:

参考答案

`timescale 1ns/1ns
module multi_sel(
input [7:0]d ,
input clk,
input rst,
output reg input_grant,
output reg [10:0]out
);

reg [1:0]cnt;
reg [7:0]din;

always@(posedge clk or negedge rst) begin
	if(!rst) begin
		cnt <= 0;
		out <= 0;
		input_grant <= 0;
		din <= 0;
	end
	else begin
		cnt <= cnt+1;
		case (cnt)
			0: begin
				din <= d;
				input_grant <= 1;
				out <= d;
			end
			1: begin
				input_grant <= 0;
				out <= (din<<2)-din;
			end		
			2: begin
				input_grant <= 0;
				out <= (din<<3)-din;
			end
			3: begin
				input_grant <= 0;
				out <= (din<<3);
			end	
		endcase
	end



end

endmodule