Although Lemmings can walk, fall, and dig, Lemmings aren't invulnerable. If a Lemming falls for too long then hits the ground, it can splatter. In particular, if a Lemming falls for more than 20 clock cycles then hits the ground, it will splatter and cease walking, falling, or digging (all 4 outputs become 0), forever (Or until the FSM gets reset). There is no upper limit on how far a Lemming can fall before hitting the ground. Lemmings only splatter when hitting the ground; they do not splatter in mid-air.
Extend your finite state machine to model this behaviour.
Falling for 20 cycles is survivable:
Falling for 21 cycles causes splatter:
module top_module( input clk, input areset, // Freshly brainwashed Lemmings walk left. input bump_left, input bump_right, input ground, input dig, output walk_left, output walk_right, output aaah, output digging );
module top_module(
input clk,
input areset, // Freshly brainwashed Lemmings walk left.
input bump_left,
input bump_right,
input ground,
input dig,
output walk_left,
output walk_right,
output aaah,
output digging );
localparam left = 0;
localparam right = 1;
localparam left_dig = 2;
localparam right_dig = 3;
localparam left_fall = 4;
localparam right_fall = 5;
localparam over = 6;
reg[2:0] state, next_state;
reg[3:0] out;
reg[7:0] cnt;
always@(posedge clk or posedge areset) begin
if(areset)
state <= left;
else
state <= next_state;
end
always@(*) begin
case(state)
left:next_state=ground?(dig?left_dig:(bump_left?right:left)):left_fall;
right:next_state=ground?(dig?right_dig:(bump_right?left:right)):right_fall;
left_dig:next_state=ground?left_dig:left_fall;
right_dig:next_state=ground?right_dig:right_fall;
left_fall:next_state=ground?((cnt>=5'd21)?over:left):left_fall;
right_fall:next_state=ground?((cnt>=5'd21)?over:right):right_fall;
over:next_state=over;
endcase
end
always@(posedge clk or posedge areset) begin
if(areset) begin
out <= 4'b1000;
end
else
case(next_state)
left:begin
out <= 4'b1000;
cnt <= 0;
end
right:begin
out <= 4'b0100;
cnt <= 0;
end
left_dig:begin
out <= 4'b0001;
cnt <= 0;
end
right_dig:begin
out <= 4'b0001;
cnt <= 0;
end
left_fall:begin
out <= 4'b0010;
cnt = cnt + 1;
end
right_fall:begin
out <= 4'b0010;
cnt = cnt + 1;
end
over:out <= 4'b0000;
endcase
end
assign {walk_left, walk_right, aaah, digging} = out;
endmodule
建立了一个微信公众号“Andy的ICer之路”,此公众号主要分享数字IC相关的学习经验,做公众号的目的就是记录自己的学习过程,很多东西回过头来可能就忘记了,为了记住知识和分享知识,希望自己可以保持更新,有兴趣的朋友可以关注一下!