eris2206

Documentation: http://frombelow.net/projects/eris2206/
Clone: git clone https://git.frombelow.net/eris2206.git
Log | Files | Refs | Submodules | README | LICENSE

main.v (3156B)


      1 /*
      2  * Copyright 2022 Gerd Beuster (gerd@frombelow.net). This is free
      3  * soft-/hardware under the GNU GPL v3 license or any later
      4  * version. See COPYING in the root directory for details.
      5  */
      6 
      7 `include "ecpu.v"
      8 
      9 module main(input CLK_IN, // System clock (12 Mhz)
     10             // External clock generated by NE555; user can set frequency.
     11             // This clock is used by the CPU.
     12             input  USER_CLOCK,
     13             // Switch to choose between continously running clock and single stepping
     14             input  SWITCH_SINGLE_CONT,
     15             // Single step (exeuction mode) / write (programming mode) signal
     16             input  BUTTON_STEP,
     17             input  BUTTON_SKIP, // Skip memory cell (programming mode) signal
     18             input  BUTTON_RESET,
     19             input  SWITCH_PROGRAM, // Program or execute mode
     20             // Manual input to data bus
     21             input  SWITCH_D0, SWITCH_D1, SWITCH_D2, SWITCH_D3,
     22             input  SWITCH_D4, SWITCH_D5, SWITCH_D6, SWITCH_D7,
     23             output GREEN, output RED_N, output RED_E,
     24             output RED_S, output RED_W, input RX, output TX,
     25             output WS2811_DOUT);
     26 
     27    wire             button_step_debounced, button_skip_debounced;
     28    debouncer deb0(.clk(CLK_IN), .button(BUTTON_STEP), .debounced(button_step_debounced));
     29    debouncer deb1(.clk(CLK_IN), .button(BUTTON_SKIP), .debounced(button_skip_debounced));
     30 
     31    // The SOC uses two clocks: The internal 12 Mhz clock of the
     32    // iCEstick is used for updating the WS2811 LED matrix and for
     33    // timing serial communication. An external, user-supplied clock
     34    // generated by an NE555 is used for running the CPU. The speed of
     35    // this clock can be set via the speed dial. Since the high and low
     36    // phases of the external clock have different length, we use a prescaler
     37    // to "convert" some to same length phases.
     38    wire 	    slow_clk;
     39    prescaler #(.bits(1)) B1(.clk_in(USER_CLOCK), .clk_out(slow_clk));
     40 
     41    esoc s(.slow_clk(slow_clk), .fast_clk(CLK_IN),
     42           .reset_in(BUTTON_RESET),
     43           .program_mode(SWITCH_PROGRAM),
     44           .single_cont(SWITCH_SINGLE_CONT),
     45           .step(button_step_debounced),
     46           .skip(button_skip_debounced),
     47           .din({ !SWITCH_D7, !SWITCH_D6, !SWITCH_D5, !SWITCH_D4,
     48                  !SWITCH_D3, !SWITCH_D2, !SWITCH_D1, !SWITCH_D0 }),
     49 	  .green(GREEN), .red_n(RED_N), .red_e(RED_E), .red_s(RED_S),
     50           .red_w(RED_W),
     51           .tx(TX), .rx(RX), .ws2811_dout(WS2811_DOUT));
     52 
     53 endmodule
     54 
     55 module debouncer(input clk, input button, output reg debounced);
     56 
     57    parameter delay = 20;
     58 
     59    reg [delay:0]      debounce_timer;
     60    always @(posedge(clk))
     61      begin
     62         if (button && (debounce_timer == 0))
     63           begin
     64              debounced <= 1;
     65              debounce_timer <= -1;
     66           end
     67         else
     68           begin
     69              if (debounce_timer > 0)
     70                debounce_timer <= debounce_timer - 1;
     71              debounced <= 0;
     72           end
     73      end
     74 endmodule
     75 
     76 module prescaler(input clk_in, output clk_out);
     77 
     78    parameter bits = 24;
     79    reg [bits-1:0] c = 0;
     80 
     81    assign clk_out = c[bits-1];
     82 
     83    always @(posedge(clk_in))
     84      c <= c + 1;
     85 
     86 endmodule