Browse Source

Reset via BREAK on physical TTY or GPIO

It is really, really useful to be able to do an external reset. The
USB one has the problem that USB itself depends on the FPGA; use a
BREAK on the physical TTY (possibly a GPIO) for a more robust solution
(can even be connected to a plain old switch.)
H. Peter Anvin 3 years ago
parent
commit
90f0cc21b5
1 changed files with 29 additions and 1 deletions
  1. 29 1
      fpga/max80.sv

+ 29 - 1
fpga/max80.sv

@@ -593,6 +593,7 @@ module max80
 
    // System reset
    wire	       usb_rxd_break_rst; // Break due to USB serial port BREAK
+   reg 	       tty_rxd_break_rst; // Break due to TTY serial port BREAK
 
    // Reset control. Note that CPU reset command 0 is intentionally ignored.
    wire [3:0] cpu_reset_cmd =
@@ -607,7 +608,8 @@ module max80
    //  - CPU entering TRAP state (irrecoverable error)
    //  - BREAK received on USB console
    //
-   assign reset_cmd[1] = cpu_reset_cmd[1] | cpu_trap | usb_rxd_break_rst;
+   assign reset_cmd[1] = cpu_reset_cmd[1] | cpu_trap |
+			 usb_rxd_break_rst | tty_rxd_break_rst;
 
    //
    // Hard system reset: FPGA not reloaded, PLLs reset, all hw units reset
@@ -709,6 +711,32 @@ module max80
 	    .tty_txd ( tty_data_out ) // DTE -> DCE
 	    );
 
+   // Detect BREAK on the hardware tty input and generate a reset,
+   // regardless of any other control signals.
+   reg [19:0]  tty_break_ctr;
+   always @(posedge sys_clk)
+     begin
+	if (~hard_rst_n)
+	  begin
+	     tty_break_ctr     <= ~'b0;
+	     tty_rxd_break_rst <= ~tty_rxd;
+	  end
+	else
+	  begin
+	     if (tty_rxd)
+	       begin
+		  tty_break_ctr     <= 'b0;
+		  tty_rxd_break_rst <= 1'b0;
+	       end
+	     else
+	       begin
+		  tty_break_ctr <= tty_break_ctr + 1'b1;
+		  if (&tty_break_ctr)
+		    tty_rxd_break_rst <= 1'b1;
+	       end // else: !if(tty_rxd)
+	  end // else: !if(~hard_rst_n)
+     end // always @ (posedge sys_clk)
+
    max80_usb #( .channels( TTY_CHANNELS ) ) usb (
 		  .hard_rst_n         ( hard_rst_n ),
 		  .clock48            ( usb_clk ),