题解 | #数据串转并电路#

数据串转并电路

https://www.nowcoder.com/practice/6134dc3c8d0741d08eb522542913583d

使用状态机可完成题目目标。

需要注意的是:

  1. ready_a信号并不是恒定为高,复位信号低电平期间需拉低。这点题目中未交代清楚。
  2. 最后一个状态向第一个状态切换时,将有效数据data_b送出。由于最后一位数据,即MSB位,在最后一个状态时输入,因此只需要使用5位移位寄存器暂存此前的有效数据,最后送出时将此时采样的数据与暂存数据位拼接后送出。
  3. 仅在ready-valid握手成功时,进行状态转换并采样输入的数据。

Talk is cheap, following is the code.

`timescale 1ns/1ns

module s_to_p(
	input 				clk 		,   
	input 				rst_n		,
	input				valid_a		,
	input	 			data_a		,
 
 	output	reg 		ready_a		,
 	output	reg			valid_b		,
	output  reg [5:0] 	data_b
);

parameter S0 = 3'h0;
parameter S1 = 3'h1;
parameter S2 = 3'h2;
parameter S3 = 3'h3;
parameter S4 = 3'h4;
parameter S5 = 3'h5;

reg [2:0] status;
reg [2:0] next_status;
reg [4:0] data_s;
wire      data_a_valid;

assign data_a_valid = ready_a && valid_a;

always @(posedge clk, negedge rst_n) begin
	if (~rst_n) begin
		ready_a <= 1'b0;
	end else begin
		ready_a <= 1'b1;
	end
end

always @(posedge clk, negedge rst_n) begin
	if (~rst_n) begin
		status <= S0;
	end else begin
		if (data_a_valid) begin
			status <= next_status;
		end else begin
			status <= status;
		end
	end
end

always @(*) begin
	case (status)
	S0: begin
		next_status = S1;
	end
	S1: begin
		next_status = S2;
	end
	S2: begin
		next_status = S3;
	end
	S3: begin
		next_status = S4;
	end
	S4: begin
		next_status = S5;
	end
	default: next_status = S0; 
	endcase
end

always @(posedge clk, negedge rst_n) begin
	if (~rst_n) begin
		data_s <= 5'h0;
	end else if (data_a_valid) begin
		data_s <= {data_a, data_s[4:1]};
	end
end

always @(posedge clk, negedge rst_n) begin
	if (~rst_n) begin
		data_b <= 6'h0;
		valid_b <= 1'b0;
	end else if (status == S5 && data_a_valid) begin
		data_b <= {data_a, data_s};
		valid_b <= 1'b1;
	end else begin
		data_b <= data_b;
		valid_b <= 1'b0;
	end
end

endmodule

全部评论

相关推荐

1 1 评论
分享
牛客网
牛客企业服务