|
| 1 | +// Copyright 2024 ETH Zurich and University of Bologna. |
| 2 | +// Solderpad Hardware License, Version 0.51, see LICENSE for details. |
| 3 | +// SPDX-License-Identifier: SHL-0.51 |
| 4 | +// |
| 5 | +// Authors: |
| 6 | +// - Hannah Pochert <hpochert@ethz.ch> |
| 7 | +// - Philippe Sauter <phsauter@iis.ee.ethz.ch> |
| 8 | + |
| 9 | +`include "common_cells/registers.svh" |
| 10 | + |
| 11 | +module uart #( |
| 12 | + /// The OBI configuration connected to this peripheral. |
| 13 | + parameter obi_pkg::obi_cfg_t ObiCfg = obi_pkg::ObiDefaultConfig, // SbrObiCfg |
| 14 | + /// OBI request type |
| 15 | + parameter type obi_req_t = logic, |
| 16 | + /// OBI response type |
| 17 | + parameter type obi_rsp_t = logic |
| 18 | +) ( |
| 19 | + input logic clk_i, // Primary input clock |
| 20 | + input logic rst_ni, // Asynchronous active-low reset |
| 21 | + |
| 22 | + // OBI request interface |
| 23 | + input obi_req_t obi_req_i, // a.addr, a.we, a.be, a.wdata, a.aid, a.a_optional | rready, req |
| 24 | + // OBI response interface |
| 25 | + output obi_rsp_t obi_rsp_o, // r.rdata, r.rid, r.err, r.r_optional | gnt, rvalid |
| 26 | + |
| 27 | + output logic irq_o, // Interrupt line |
| 28 | + output logic irq_no, // Negated Interrupt line |
| 29 | + |
| 30 | + input logic rxd_i, // Serial Input |
| 31 | + output logic txd_o, // Serial Output |
| 32 | + |
| 33 | + // Modem control pins are optional |
| 34 | + input logic cts_ni, // Modem Inp Clear To Send |
| 35 | + input logic dsr_ni, // Modem Inp Data Send Request |
| 36 | + input logic ri_ni, // Modem Inp Ring Indicator |
| 37 | + input logic cd_ni, // Modem Inp Carrier Detect |
| 38 | + output logic rts_no, // Modem Oup Ready To Send |
| 39 | + output logic dtr_no, // Modem Oup DaTa Ready |
| 40 | + output logic out1_no, // Modem Oup DaTa Ready, optional outputs |
| 41 | + output logic out2_no // Modem Oup DaTa Ready, optional outputs |
| 42 | +); |
| 43 | + // Import the UART package for definitions and parameters |
| 44 | + import uart_pkg::*; |
| 45 | + |
| 46 | + //--Receiver-and-Transmitter-Interface---------------------------------------------------------- |
| 47 | + logic rxd; |
| 48 | + logic txd; |
| 49 | + |
| 50 | + //--Receiver-Interrupt-Interface---------------------------------------------------------------- |
| 51 | + logic rx_fifo_trigger; |
| 52 | + logic rx_timeout; |
| 53 | + |
| 54 | + //--Register-Interface-Signals------------------------------------------------------------------ |
| 55 | + reg_read_t reg_read; // signals read from the registers |
| 56 | + reg_write_t reg_write; // new values being written to registers |
| 57 | + |
| 58 | + //--Baudenable-Interface-Signals---------------------------------------------------------------- |
| 59 | + logic oversample_rate_edge; |
| 60 | + logic double_rate_edge; |
| 61 | + logic baud_rate_edge; |
| 62 | + |
| 63 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 64 | + // REGISTER INTERFACE // |
| 65 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 66 | + |
| 67 | + uart_register #( |
| 68 | + .obi_req_t (obi_req_t), |
| 69 | + .obi_rsp_t (obi_rsp_t) |
| 70 | + ) i_uart_register ( |
| 71 | + .clk_i, |
| 72 | + .rst_ni, |
| 73 | + |
| 74 | + .obi_req_i, |
| 75 | + .obi_rsp_o, |
| 76 | + |
| 77 | + .reg_read_o (reg_read), |
| 78 | + .reg_write_i (reg_write) |
| 79 | + ); |
| 80 | + |
| 81 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 82 | + // MODEM CONTROL // |
| 83 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 84 | + |
| 85 | + uart_modem #( |
| 86 | + ) i_uart_modem ( |
| 87 | + .clk_i, |
| 88 | + .rst_ni, |
| 89 | + |
| 90 | + .cts_ni, |
| 91 | + .dsr_ni, |
| 92 | + .ri_ni, |
| 93 | + .cd_ni, |
| 94 | + .rts_no, |
| 95 | + .dtr_no, |
| 96 | + .out1_no, |
| 97 | + .out2_no, |
| 98 | + |
| 99 | + .reg_read_i (reg_read), |
| 100 | + .reg_write_o (reg_write.modem) |
| 101 | + ); |
| 102 | + |
| 103 | + //--Loopback-Mode------------------------------------------------------------------------------- |
| 104 | + assign txd_o = (reg_read.mcr.loopback == 1'b1) ? 1'b1 : txd; |
| 105 | + assign rxd = (reg_read.mcr.loopback == 1'b1) ? txd : rxd_i; |
| 106 | + |
| 107 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 108 | + // BAUDRATE GENERATION // |
| 109 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 110 | + |
| 111 | + uart_baudgeneration #( |
| 112 | + ) i_uart_baudgeneration ( |
| 113 | + .clk_i, |
| 114 | + .rst_ni, |
| 115 | + |
| 116 | + .oversample_rate_edge_o(oversample_rate_edge), |
| 117 | + .double_rate_edge_o (double_rate_edge), |
| 118 | + .baud_rate_edge_o (baud_rate_edge), |
| 119 | + |
| 120 | + .reg_read_i (reg_read) |
| 121 | + ); |
| 122 | + |
| 123 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 124 | + // RECEIVE // |
| 125 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 126 | + |
| 127 | + uart_rx # ( |
| 128 | + ) i_uart_rx ( |
| 129 | + .clk_i, |
| 130 | + .rst_ni, |
| 131 | + |
| 132 | + .oversample_rate_edge_i (oversample_rate_edge), |
| 133 | + .baud_rate_edge_i (baud_rate_edge), |
| 134 | + |
| 135 | + .rxd_i (rxd), |
| 136 | + |
| 137 | + .trigger_o (rx_fifo_trigger), |
| 138 | + .timeout_o (rx_timeout), |
| 139 | + |
| 140 | + .reg_read_i (reg_read), |
| 141 | + .reg_write_o (reg_write.rx) |
| 142 | + ); |
| 143 | + |
| 144 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 145 | + // TRANSMIT // |
| 146 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 147 | + |
| 148 | + uart_tx # ( |
| 149 | + ) i_uart_tx ( |
| 150 | + .clk_i, |
| 151 | + .rst_ni, |
| 152 | + |
| 153 | + .baud_rate_edge_i (baud_rate_edge), |
| 154 | + .double_rate_edge_i (double_rate_edge), |
| 155 | + |
| 156 | + .txd_o (txd), |
| 157 | + |
| 158 | + .reg_read_i (reg_read), |
| 159 | + .reg_write_o (reg_write.tx) |
| 160 | + ); |
| 161 | + |
| 162 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 163 | + // INTERRUPT CONTROL // |
| 164 | + //////////////////////////////////////////////////////////////////////////////////////////////// |
| 165 | + |
| 166 | + uart_interrupts #( |
| 167 | + ) i_uart_interrupts ( |
| 168 | + .clk_i, |
| 169 | + .rst_ni, |
| 170 | + |
| 171 | + .rx_fifo_trigger, |
| 172 | + .rx_timeout, |
| 173 | + |
| 174 | + .irq_o, |
| 175 | + .irq_no, |
| 176 | + |
| 177 | + .reg_read_i (reg_read), |
| 178 | + .reg_write_i (reg_write), |
| 179 | + .reg_write_o (reg_write.intrpt) |
| 180 | + ); |
| 181 | + |
| 182 | +endmodule |
0 commit comments