module kbd_intf(mclk25, reset_in,PS2_Clk,PS2_Data,shift, ascii, kbd_available, read_kb); input mclk25, reset_in, read_kb; input PS2_Clk,PS2_Data; // input Scan_DAV; output shift, kbd_available; reg [2:0] kbd_state; reg [2:0] kbd_state_next; reg shift; reg ctrl; reg [7:0] code_latched; reg kbd_available; output [6:0] ascii; wire [6:0] decoded; wire [7:0] Scan_Code; PS2_Ctrl PS2_Ctrl ( .Clk(mclk25), .Reset(reset_in), .PS2_Clk(PS2_Clk), .PS2_Data(PS2_Data), .DoRead(DoRead), .Scan_Err(Scan_Err), .Scan_DAV(Scan_DAV), .Scan_Code(Scan_Code) ); assign DoRead = Scan_DAV; kbd_transl kbd_transl( .shift(shift), .incode(code_latched), .outcode(decoded)); assign ascii = ctrl? {2'b0, decoded[4:0]} : decoded; always @(posedge mclk25 ) begin if(reset_in) begin shift <= 0; ctrl <= 0; end else begin if( kbd_state == 1) begin if ((Scan_Code == 8'h12) | (Scan_Code == 8'h59)) shift <= 1; else if (Scan_Code == 8'h14) ctrl <= 1; end else if( kbd_state == 6) begin if((Scan_Code == 8'h12) | (Scan_Code == 8'h59)) shift <= 0; else if (Scan_Code == 8'h14) ctrl <= 0; end end end //always always @(posedge mclk25) begin if(reset_in) begin kbd_state <= 0; kbd_state <= 0; code_latched <= 0; kbd_available <= 0; end else begin kbd_state <= kbd_state_next; if(read_kb) kbd_available <= 0; if( kbd_state == 7) begin code_latched <= Scan_Code; kbd_available <= 1; end end end always @ (kbd_state or Scan_Code or Scan_DAV) begin case (kbd_state) 0: if( Scan_DAV) kbd_state_next <= 1; else kbd_state_next <= 0; 1: // have something, get it kbd_state_next <= 2; 2: if(Scan_Code == 8'hf0) kbd_state_next <= 3; else if(Scan_Code == 8'hE0) kbd_state_next <= 0; else if((Scan_Code == 8'h12) | (Scan_Code == 8'h14) | (Scan_Code == 8'h59)) begin kbd_state_next <= 0; end else kbd_state_next <= 7; 3: // was F0 wait a couple of states for Scan_DAV to go down kbd_state_next <= 4; 4: kbd_state_next <= 5; 5: if( Scan_DAV) // wait for more kbd_state_next <= 6; else kbd_state_next <= 5; 6: begin kbd_state_next <= 0; end 7: kbd_state_next <= 0; default: kbd_state_next <= 0; endcase end endmodule