题解 | #根据状态转移图实现时序电路#
根据状态转移图实现时序电路
https://www.nowcoder.com/practice/e405fe8975e844c3ab843d72f168f9f4
`timescale 1ns/1ns
module seq_circuit(
input C ,
input clk ,
input rst_n,
output wire Y // Y 是 wire 型变量,不受时钟信号的约束改变
);
//===========================================//
// 逻辑表达式解法
//===========================================//
/*根据状态机的描述,从原始的状态函数定义出发,分别求出两位nxt_st和一位输出的表达式*/
// 定位两位状态
// reg [1:0] state
reg st1, st0;
always @(posedge clk or negedge rst_n)
begin
if(~rst_n) begin
st1 <= 1'b0;
st0 <= 1'b0;
end
else begin
st1 <= (st0&(~C))|(st1&C);
st0 <= (st0&(~C))|(~st1&C);
end
end
assign Y = (st1&st0)|(st1&(~st0)&C);
//===========================================//
// 状态机解法
//===========================================//
// localparam
// s0 = 3'b000,
// s1 = 3'b001,
// s2 = 3'b010,
// s3 = 3'b100;
// reg [2:0] cur_st, nxt_st;
/*======三段式FSM 最后一段描述输出逻辑======*/
/*
always @(posedge clk or negedge rst_n)
begin
if(~rst_n)
cur_st <= s0;
else
cur_st <= nxt_st;
end
always @( *) begin
case(cur_st)
s0: nxt_st = C? s1 : s0;
s1: nxt_st = C? s1 : s2;
s2: nxt_st = C? s3 : s2;
s3: nxt_st = C? s3 : s0;
default :
nxt_st = s0;
endcase
end
// Y在定义中为wire信号,其值的改变不应当受限于时钟的上升沿、
// 根据本体的报错,也是如此
// 故,这里的第三段状态机使用组合逻辑
reg y_r;
assign Y = y_r;
always @( *) begin
if(~rst_n)
y_r = 1'b0;
else if(cur_st==s2 || (cur_st==s3 && C==1'b1))
y_r = 1'b1;
else
y_r = 1'b0;
end
*/
/*======两段FSM 含输出======*/
/*
always @(posedge clk or negedge rst_n)
begin
if(~rst_n)
cur_st <= s0;
else
cur_st <= nxt_st;
end
reg y_r;
assign Y = y_r;
always @( *) begin
case (cur_st)
s0: begin
nxt_st = C? s1 : s0;
y_r = 1'b0;
end
s1: begin
nxt_st = C? s1 : s2;
y_r = 1'b0;
end
s2: begin
nxt_st = C? s3 : s2;
y_r = 1'b1;
end
s3: begin
nxt_st = C? s3 : s0;
y_r = C? 1'b1 : 1'b0;
end
default : begin
nxt_st = s0;
y_r = 1'b0;
end
endcase
end
*/
/*======两段FSM 不含输出======*/
/*
always @(posedge clk or negedge rst_n)
begin
if(~rst_n)
cur_st <= s0;
else
cur_st <= nxt_st;
end
always @( *) begin
case(cur_st)
s0: nxt_st = C? s1 : s0;
s1: nxt_st = C? s1 : s2;
s2: nxt_st = C? s3 : s2;
s3: nxt_st = C? s3 : s0;
default :
nxt_st = s0;
endcase
end
assign Y = (cur_st==s2) | (cur_st==s3 && C==1'b1);
*/
endmodule

