UART and Baud Rate Generator
UART Programming Interface
- Interface mimics ACIA software interface address/control/status contents
- Two addresses, Control/status and data access
Status Register (Read)
d0 = RDRF = Receive Data Register Full (1 = data is ready to read)
d1 = TDRE = Transmit Data Register Empty (1 = transmit is ready to send out data)
d2 = DCD = Data Carrier Detect (0 = carrier present - hardwired)
d3 = CTS = Clear to Send (0 = Clear to Send - ready to accept data - hardwired)
d7 = IRQ = Interrupt Request (1 = Interrupt present)
Control Register (Write)
d1,d0 = Control (11 = Master Reset)
d6,d5 = TC = Transmitter Control (RTS = Transmitter Interrupt Enable/Disable)
d7 = Interrupt Enable (1=enable interrupts)
Data Register (Read/Write)
- Register Select = 1
- Read = Read data from the data register (not implemented due to kbd removal)
- Write = Write data to the data register
Example Code
Read character from UART
- Returns character in Reg1
- Destroys Reg1
- Blocks until character is received
RDUART JSR WTUARTRXRDY WAIT FOR UART RX CHAR
IOR 0X01 0X09 READ UART CHAR
RTS RETURN KBD DATA IN REG1
WTUARTRXRDY IOR 0X00 0X08 READ UART STATUS
ARI 0X00 0X01 RX RDY BIT
BEZ WTUARTRXRDY LOOP UNTIL CHAR PRESENT
RTS
Write character to UART
- Pass character to write in Reg0
- Destroys Reg1
- Blocks until character can be written
WRUART JSR WTUARTTXBSY WRITE REG1 TO THE UART TX
IOW 0X01 0X09
RTS
WTUARTTXBSY IOR 0X00 0X08 WRITE REG1 OUT UART
ARI 0X00 0X02 TX EMPTY BIT
BEZ WTUARTTXBSY LOOP WHILE NOT EMPTY
RTS
Baud Rate Generator for buffered UART
- Assumes 50 MHz clock
- Pass Baud Rate in BAUD_RATE generic as integer value (300, 9600, 115,200)
- Legal values are 115200, 38400, 19200, 9600, 4800, 2400, 1200, 600, 300
UART and Baud Rate Generator VHDL Entities
- Code to add UART to the IOP16 top file
Pins
-- UART
rxd1 : in std_logic := '1'; -- Hardware Handshake needed
txd1 : out std_logic;
cts1 : in std_logic := '1';
rts1 : out std_logic;
serSelect : in std_logic := '1'; -- Jumper with pullup in FPGA for selecting serial between ACIA (installed) and VDU (removed)
Signals
- Add signals to architecture section
-- Decodes/Strobes
...
signal w_wrUart : std_logic;
signal w_rdUart : std_logic;
-- Interfaces
..
signal w_UartDataOut : std_logic_vector(7 downto 0);
-- Serial clock enable
signal W_serialEn : std_logic; -- 16x baud rate clock
UART Entity
-- 6850 style UART
UART: entity work.bufferedUART
port map (
clk => i_clk,
-- Strobes
n_wr => not w_wrUart,
n_rd => not w_rdUart,
-- CPU
regSel => w_periphAdr(0),
dataIn => w_periphOut,
dataOut => w_UartDataOut,
-- Clock strobes
rxClkEn => serialEn,
txClkEn => serialEn,
-- Serial I/F
rxd => rxd1,
txd => txd1,
n_rts => rts1,
n_cts => cts1
);
Baud Rate Generator Entity
-- ____________________________________________________________________________________
-- Baud Rate Generator as an entity with passed baud rate
-- Legal BAUD_RATE values are 115200, 38400, 19200, 9600, 4800, 2400, 1200, 600, 300
BaudRateGen : entity work.BaudRate6850
GENERIC map (
BAUD_RATE => 115200
)
PORT map (
i_CLOCK_50 => i_clk,
o_serialEn => w_serialEn
);
Add Code
-- Peripheral bus read mux
w_periphIn <= ...
...
w_UartDataOut when w_periphAdr(7 downto 1) = "0000100" else
---
-- Strobes/Selects
...
w_wrUart <= '1' when ((w_periphAdr(7 downto 1)="0000100") and (w_periphWr = '1')) else '0';
w_rdUart <= '1' when ((w_periphAdr(7 downto 1)="0000100") and (w_periphRd = '1')) else '0';
FPGA Resources (EP4CE15)
- UART
- Logic Cells: 183
- Registers: 94
- Memory Bits: 128
- M9Ks: 1
- Baud Rate Generator
- Logic Cells: 14
- Registers: 13
- Memory Bits: 0
- M9Ks: 0