Verilog进阶挑战(3)—— 输入序列不连续的序列检测

Verilog进阶挑战


输入序列不连续的序列检测


一、题目描述

请编写一个序列检测模块,输入信号端口为data,表示数据有效的指示信号端口为data_valid。当data_valid信号为高时,表示此刻的输入信号data有效,参与序列检测;当data_valid为低时,data无效,抛弃该时刻的输入。当输入序列的有效信号满足0110时,拉高序列匹配信号match。

模块的接口信号图如下:
在这里插入图片描述
在这里插入图片描述
输入描述:
clk:系统时钟信号
rst_n:异步复位信号,低电平有效
data:单比特信号,待检测的数据
data_valid:输入信号有效标志,当该信号为1时,表示输入信号有效

输出描述:
match:当输入信号data满足目标序列,该信号为1,其余时刻该信号为0

二、解析与代码

`timescale 1ns/1ns
module sequence_detect(
	input clk,
	input rst_n,
	input data,
	input data_valid,
	output reg match
	);

reg [3:0]data_reg=0;
always@(posedge clk or negedge rst_n)begin
	if(!rst_n)
		data_reg <= 0;
	else if(data_valid)
		data_reg <= {data_reg[2:0],data};
	else
		data_reg <= data_reg;
end 
//计数器 避免那个0110的开头是数据无效时的
reg [2:0] cnt=0;
always@(posedge clk or negedge rst_n)begin
	if(!rst_n)
		cnt <= 0;
	else if(data_valid==1)
		cnt <= cnt +1;
	else
		cnt <= 0;
end
//match更新
//错的原因:原本是always@(posedge clk or negedge rst_n)时序逻辑,data_reg比实际data慢一拍
always@(*)begin
	if(!rst_n)
		match <= 0;
	else if(data_reg==4'b0110  && cnt>=3'd4)
		match <= 1;
	else
	 	match <= 0;
end
endmodule

状态机的写法:
状态空间定义:S0:0000; S1:0001; … S15:1111
状态转移图:
在这里插入图片描述

module sequence_detect(
	input clk,
	input rst_n,
	input data,
	input data_valid,
	output reg match=0
	);
//三段式状态机方法
reg [3:0]current_state,next_state;
//状态更新
always@(posedge clk or negedge rst_n)begin
	if(!rst_n)
		current_state <= 4'b0000;
	else if(data_valid)
		current_state <= next_state;
	else
		current_state <= current_state;
end
//状态转移
//状态定义
parameter  S0   = 4'b0000;  
parameter  S1   = 4'b0001;  
parameter  S2   = 4'b0010;  
parameter  S3   = 4'b0011;  
parameter  S4   = 4'b0100;  
parameter  S5   = 4'b0101;  
parameter  S6   = 4'b0110;  
parameter  S7   = 4'b0111;  
parameter  S8   = 4'b1000;  
parameter  S9   = 4'b1001;  
parameter  S10   = 4'b1010;  
parameter  S11   = 4'b1011;  
parameter  S12   = 4'b1100;  
parameter  S13   = 4'b1101;  
parameter  S14   = 4'b1110; 
parameter  S15   = 4'b1111;   
always@(*)begin
	if(data_valid)
		case(current_state)
			S0:begin
				if(data) next_state <= S1;
				else next_state <= S0;
			end
			S1:begin
				if(data) next_state <= S3;
				else next_state <= S2;
			end
			S2:begin
				if(data) next_state <= S3;
				else next_state <= S4;
			end
			S3:begin
				if(data) next_state <= S7;
				else next_state <= S6;
			end
			S4:begin
				if(data) next_state <= S5;
				else next_state <= S8;
			end
			S5:begin
				if(data) next_state <= S11;
				else next_state <= S10;
			end
			S6:begin
				if(data) next_state <= S13;
				else next_state <= S12;
			end
			S7:begin
				if(data) next_state <= S15;
				else next_state <= S14;
			end
			S8:begin
				if(data) next_state <= S9;
				else next_state <= S0;
			end
			S9:begin
				if(data) next_state <= S3;
				else next_state <= S2;
			end
			S10:begin
				if(data) next_state <= S11;
				else next_state <= S5;
			end
			S11:begin
				if(data) next_state <= S7;
				else next_state <= S6;
			end
			S12:begin
				if(data) next_state <= S9;
				else next_state <= S8;
			end
			S13:begin
				if(data) next_state <= S11;
				else next_state <= S10;
			end
			S14:begin
				if(data) next_state <= S15;
				else next_state <= S12;
			end
			S15:begin
				if(data) next_state <= S15;
				else next_state <= S14;
			end
		endcase
	else
		next_state <= S0;
end
//输出
always@(*)begin
	 match <= (next_state==S6)?1:0;
end
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值