URL
https://opencores.org/ocsvn/uart2bus_testbench/uart2bus_testbench/trunk
Subversion Repositories uart2bus_testbench
[/] [uart2bus_testbench/] [trunk/] [rtl/] [uart_rx.v] - Rev 13
Go to most recent revision | Compare with Previous | Blame | View Log
//--------------------------------------------------------------------------------------- // uart receive module // //--------------------------------------------------------------------------------------- module uart_rx ( clock, reset, ce_16, ser_in, rx_data, new_rx_data ); //--------------------------------------------------------------------------------------- // modules inputs and outputs input clock; // global clock input input reset; // global reset input input ce_16; // baud rate multiplyed by 16 - generated by baud module input ser_in; // serial data input output [7:0] rx_data; // data byte received output new_rx_data; // signs that a new byte was received // internal wires wire ce_1; // clock enable at bit rate wire ce_1_mid; // clock enable at the middle of each bit - used to sample data // internal registers reg [7:0] rx_data; reg new_rx_data; reg [1:0] in_sync; reg rx_busy; reg [3:0] count16; reg [3:0] bit_count; reg [7:0] data_buf; //--------------------------------------------------------------------------------------- // module implementation // input async input is sampled twice always @ (posedge clock or posedge reset) begin if (reset) in_sync <= 2'b11; else in_sync <= {in_sync[0], ser_in}; end // a counter to count 16 pulses of ce_16 to generate the ce_1 and ce_1_mid pulses. // this counter is used to detect the start bit while the receiver is not receiving and // signs the sampling cycle during reception. always @ (posedge clock or posedge reset) begin if (reset) count16 <= 4'b0; else if (ce_16) begin if (rx_busy | (in_sync[1] == 1'b0)) count16 <= count16 + 4'b1; else count16 <= 4'b0; end end // ce_1 pulse indicating expected end of current bit assign ce_1 = (count16 == 4'b1111) & ce_16; // ce_1_mid pulse indication the sampling clock cycle of the current data bit assign ce_1_mid = (count16 == 4'b0111) & ce_16; // receiving busy flag always @ (posedge clock or posedge reset) begin if (reset) rx_busy <= 1'b0; else if (~rx_busy & ce_1_mid) rx_busy <= 1'b1; else if (rx_busy & (bit_count == 4'h8) & ce_1_mid) rx_busy <= 1'b0; end // bit counter always @ (posedge clock or posedge reset) begin if (reset) bit_count <= 4'h0; else if (~rx_busy) bit_count <= 4'h0; else if (rx_busy & ce_1_mid) bit_count <= bit_count + 4'h1; end // data buffer shift register always @ (posedge clock or posedge reset) begin if (reset) data_buf <= 8'h0; else if (rx_busy & ce_1_mid) data_buf <= {in_sync[1], data_buf[7:1]}; end // data output and flag always @ (posedge clock or posedge reset) begin if (reset) begin rx_data <= 8'h0; new_rx_data <= 1'b0; end else if (rx_busy & (bit_count == 4'h8) & ce_1) begin rx_data <= data_buf; new_rx_data <= 1'b1; end else new_rx_data <= 1'b0; end endmodule //--------------------------------------------------------------------------------------- // Th.. Th.. Th.. Thats all folks !!! //---------------------------------------------------------------------------------------
Go to most recent revision | Compare with Previous | Blame | View Log