0% found this document useful (0 votes)
14 views13 pages

Uart

The document describes the architecture and implementation of a UART controller integrated with an LCD display using FPGA. It includes detailed entity definitions, signal declarations, and processes for UART communication, data handling, and LCD display management. The design aims to facilitate data transmission and display output through a structured VHDL code framework.

Uploaded by

hunghuyn244996
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
14 views13 pages

Uart

The document describes the architecture and implementation of a UART controller integrated with an LCD display using FPGA. It includes detailed entity definitions, signal declarations, and processes for UART communication, data handling, and LCD display management. The design aims to facilitate data transmission and display output through a structured VHDL code framework.

Uploaded by

hunghuyn244996
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd

8.

5
QUA UART

terminal

Project BAI_801_FPGA_LCD_DEM_PC_UART
FPGA_LCD_DEM_PC_UART
a.

FPGA_LCD_DEM_PC_UART
UART_CONTROLLER LCD_KHOITAO_HIENTHI
uart_rx uart_recv_data
uart_rx
fifo_uart_rx_data_rd LCD_HANG_1
uart_ena_rd LCD_DB
fifo_uart_rx_rd
ckht
uart_rx_empty ena_rx LCD_RS
fifo_uart_rx_empty
ckht LCD_E
rst LCD_CK
rst LCD_WR
ckht LCD_RST
uart_tx
uart_tx uart_trans_data
fifo_uart_tx_data_wr ena_db
uart_ena_tx
fifo_uart_tx_wr
uart_tx_full sw0
fifo_uart_tx_full dem BELL

DEM_8BIT HEXTOBCD_8BIT
CHIA_10ENA
ckht
ckht ena5hz ena_db donvi H2_15
ckht dem chuc H2_14
btn_n0 rst
rst
sw0 tram H2_13
ena_ss
LCD_GAN_DULIEU_HIENTHI_H2

Hình 8-10.
377
b.

entity FPGA_LCD_DEM_PC_UART is
Port( CKHT: in STD_LOGIC;
BTN_N0: in STD_LOGIC;
SW0: in STD_LOGIC;
BELL: OUT STD_LOGIC;
UART_RX: in STD_LOGIC;
UART_TX: out STD_LOGIC;
LCD_E: out STD_LOGIC;
LCD_RS: out STD_LOGIC;
LCD_RW: out STD_LOGIC;
LCD_DB: out STD_LOGIC_VECTOR (7 downto 0));
end FPGA_LCD_DEM_PC_UART;

architecture Behavioral of FPGA_LCD_DEM_PC_UART is


SIGNAL RST: STD_LOGIC;
SIGNAL LCD_HANG_1_R: STD_LOGIC_VECTOR(127 DOWNTO 0);
SIGNAL LCD_HANG_1_N: STD_LOGIC_VECTOR(127 DOWNTO 0);
SIGNAL LCD_HANG_2: STD_LOGIC_VECTOR(127 DOWNTO 0);

signal UART_TX_FULL: STD_LOGIC;


signal UART_RX_EMPTY: STD_LOGIC;

signal UART_RECV_DATA: STD_LOGIC_VECTOR(7 downto 0);


signal UART_TRANS_DATA: STD_LOGIC_VECTOR(7 downto 0);

signal UART_ENA_TX: STD_LOGIC;


signal UART_ENA_RD: STD_LOGIC;

signal ENA_DB: STD_LOGIC;


signal ENA_RX: STD_LOGIC;
signal DEM: STD_LOGIC_VECTOR(7 downto 0);
SIGNAL DONVI: STD_LOGIC_VECTOR (3 downto 0);
SIGNAL CHUC: STD_LOGIC_VECTOR (3 downto 0);
SIGNAL TRAM: STD_LOGIC_VECTOR (3 downto 0);

begin
RST <= NOT BTN_N0;
BELL <= '1';
LCD_RW <= '0';
ENA_RX <= CKHT;

CHIA_10ENA: ENTITY WORK.CHIA_10ENA


PORT MAP( CKHT => CKHT,
ENA5HZ => ENA_DB );

UART_UNIT:entity WORK.UART_CONTROLLER
port map( CKHT => CKHT,
RST => RST,
378
UART_RX => UART_RX,
UART_TX => UART_TX,
FIFO_UART_RX_ENA_RD => UART_ENA_RD,
FIFO_UART_RX_DATA_RD => UART_RECV_DATA,
FIFO_UART_RX_EMPTY => UART_RX_EMPTY,
FIFO_UART_TX_ENA_WR => UART_ENA_TX,
FIFO_UART_TX_DATA_WR => UART_TRANS_DATA,
FIFO_UART_TX_FULL => UART_TX_FULL);

PROCESS(UART_TX_FULL, ENA_DB, SW0, DEM)


BEGIN
UART_TRANS_DATA <= DEM; -
- GAN DL GOI DI
IF UART_TX_FULL = '0' THEN
UART_ENA_TX <= ENA_DB AND SW0; --
TAO XUNG PHAT
ELSE UART_ENA_TX <= '0';
END IF;
END PROCESS;

UART_ENA_RD <= ENA_RX AND (NOT UART_RX_EMPTY); --


TAO XUNG DOC
PROCESS(CKHT, RST)
BEGIN
IF RST = '1' THEN
LCD_HANG_1_R <= X"20202020202020202020202020202020";
ELSIF FALLING_EDGE(CKHT) THEN
LCD_HANG_1_R <= LCD_HANG_1_N;
END IF;
END PROCESS;
LCD_HANG_1_N <=
UART_RECV_DATA & LCD_HANG_1_R(127 DOWNTO 8)
WHEN UART_ENA_RD = '1'
ELSE LCD_HANG_1_R;

DEM_8BIT: ENTITY WORK.DEM_8BIT


PORT MAP ( CKHT => CKHT,
RST => RST,
ENA_SS => SW0,
ENA_DB => ENA_DB,
DEM => DEM);

HEXTOBCD: ENTITY WORK.HEXTOBCD_8BIT


PORT MAP ( SOHEX8BIT => DEM,
DONVI => DONVI,
CHUC => CHUC,
TRAM => TRAM);

LCD_GAN_DULIEU_HIENTHI: ENTITY WORK.


LCD_GAN_DULIEU_HIENTHI_H2
PORT MAP( H2_13 => TRAM,
379
H2_14 => CHUC,
H2_15 => DONVI,
LCD_HANG_2 => LCD_HANG_2);

LCD_KHOITAO_HIENTHI: ENTITY WORK.


LCD_KHOITAO_HIENTHI
PORT MAP( LCD_DB => LCD_DB,
LCD_RS => LCD_RS,
LCD_E => LCD_E,
LCD_RST => RST,
LCD_CK => CKHT,
LCD_HANG_1 => LCD_HANG_1_R,
LCD_HANG_2 => LCD_HANG_2);
end Behavioral;

entity UART_CONTROLLER is
GENERIC( DBIT: integer:=8;
SB_TICK: integer:=16;
DVSR: integer:=163;--326cho 100MHz
DVSR_BIT: integer:=9;
FIFO_W: integer:=2);

Port( CKHT: in STD_LOGIC;


RST: in STD_LOGIC;
UART_RX: in STD_LOGIC;
UART_TX: out STD_LOGIC;
FIFO_UART_RX_ENA_RD: in STD_LOGIC;
FIFO_UART_RX_DATA_RD: out
STD_LOGIC_VECTOR (7 downto 0);
FIFO_UART_RX_EMPTY: out STD_LOGIC;
FIFO_UART_TX_ENA_WR: in STD_LOGIC;
FIFO_UART_TX_DATA_WR: in
STD_LOGIC_VECTOR (7 downto 0);
FIFO_UART_TX_FULL: out STD_LOGIC);
end UART_CONTROLLER;

architecture Behavioral of UART_CONTROLLER is


signal s_tick: std_logic;
signal UART_RX_FIFO_IN: STD_LOGIC_VECTOR (7 downto 0);
signal UART_RX_DONE_TICK: std_logic;

signal UART_TX_FIFO_OUT:STD_LOGIC_VECTOR (7 downto 0);


signal UART_TX_DONE_TICK: std_logic;

signal UART_TX_FIFO_NOT_EMPRY: std_logic;


signal FIFO_UART_TX_EMPTY: std_logic;

begin
baud_gen_unit: entity work.mod_m_counter(arch)
generic map( M => DVSR,
380
N => DVSR_BIT)
port map( CKHT => CKHT,
RST => RST,
TICK => S_TICK);
UART_RX_UNIT:entity work.UART_CONTROLLER_RX(arch)
generic map( DBIT => DBIT,
SB_TICK => SB_TICK)
port map( CKHT => CKHT,
RST => RST,
S_TICK => S_TICK,
UART_RX => UART_RX,
UART_RX_DATA => UART_RX_FIFO_IN,
UART_RX_DONE_TICK => UART_RX_DONE_TICK);

FIFO_RX_UNIT: entity work.FIFO_RX(arch)


generic map ( B => DBIT,
W => FIFO_W)
port map( CKHT => CKHT,
RST => RST,
DATA_WR => UART_RX_FIFO_IN,
WR => UART_RX_DONE_TICK,
RD => FIFO_UART_RX_ENA_RD,
DATA_RD => FIFO_UART_RX_DATA_RD,
EMPTY => FIFO_UART_RX_EMPTY);

UART_TX_UNIT:entity work.UART_CONTROLLER_TX(arch)
generic map( DBIT => DBIT,
SB_TICK => SB_TICK)
port map( CKHT => CKHT,
RST => RST,
S_TICK => S_TICK,
UART_TX => UART_TX,
UART_TX_DATA => UART_TX_FIFO_OUT,
UART_TX_DONE_TICK => UART_TX_DONE_TICK,
UART_TX_FIFO_NOT_EMPRY =>
UART_TX_FIFO_NOT_EMPRY);
UART_TX_FIFO_NOT_EMPRY <= NOT FIFO_UART_TX_EMPTY;
FIFO_TX_UNIT: entity work. FIFO_TX(arch)
generic map( B => DBIT,
W => FIFO_W)
port map( CKHT => CKHT,
RST => RST,
RD => UART_TX_DONE_TICK,
DATA_RD => UART_TX_FIFO_OUT,
EMPTY => FIFO_UART_TX_EMPTY,
WR => FIFO_UART_TX_ENA_WR,
DATA_WR => FIFO_UART_TX_DATA_WR,
FULL => FIFO_UART_TX_FULL);
end Behavioral;

381
entity MOD_M_COUNTER is
generic ( N: integer := 4;
M: integer := 10);
Port ( CKHT: in STD_LOGIC;
RST: in STD_LOGIC;
TICK: out STD_LOGIC);
end MOD_M_COUNTER;
architecture arch of MOD_M_COUNTER is
SIGNAL R_REG: UNSIGNED(N-1 DOWNTO 0);
SIGNAL R_NEXT: UNSIGNED(N-1 downto 0);
begin
PROCESS(CKHT,RST)
BEGIN
IF RST = '1' THEN R_REG <= (OTHERS => '0');
ELSIF FALLING_EDGE(CKHT) THEN
R_REG <= R_NEXT;
END IF;
END PROCESS;
R_NEXT <= (OTHERS => '0') WHEN R_REG =(M-1)
ELSE R_REG+1;
TICK <= '1' WHEN R_REG = (M-1) ELSE '0';
end arch;

entity UART_CONTROLLER_RX is
generic ( DBIT: INTEGER:=8;
SB_TICK: INTEGER:=16);
Port ( CKHT: in STD_LOGIC;
RST: in STD_LOGIC;
UART_RX: in STD_LOGIC;
S_TICK: in STD_LOGIC;
UART_RX_DONE_TICK: out STD_LOGIC;
UART_RX_DATA: out STD_LOGIC_VECTOR (7 downto 0));
end UART_CONTROLLER_RX;

architecture arch of UART_CONTROLLER_RX is


TYPE state_type is (idle,start,data,stop);
signal state_reg: state_type;
signal state_next: state_type;
signal s_reg, s_next: unsigned(3 downto 0);
signal n_reg, n_next: unsigned(2 downto 0);
signal b_reg, b_next: std_logic_vector(7 downto 0);
begin
process(CKHT,RST)
begin
if RST = '1' then state_reg <= idle;
s_reg <= (others=> '0');
n_reg <= (others=> '0');
b_reg <= (others=> '0');

382
elsif falling_edge(CKHT) then
state_reg <= state_next;
s_reg <= s_next;
n_reg <= n_next;
b_reg <= b_next;
end if;
end process;

process(state_reg,s_reg,n_reg,b_reg,S_TICK,UART_RX)
begin
state_next <= state_reg;
s_next <= s_reg;
n_next <= n_reg;
b_next <= b_reg;
UART_RX_DONE_TICK <='0';
case state_reg is
when idle =>
if UART_RX = '0' then
state_next <= start;
s_next <= (others=>'0');
end if;

when start =>


if (S_TICK='1') then
if s_reg=7 then state_next <= data;
s_next <= (others=>'0');
n_next <= (others=>'0');
else s_next <= s_reg+1;
end if;
end if;

when data =>


if (S_TICK ='1') then
if s_reg=15 then
s_next <= (others=>'0');
b_next <= UART_RX & b_reg(7 downto 1);
if n_reg =(dbit-1) then
state_next <= stop;
else n_next <= n_reg+1;
end if;
else s_next <= s_reg+1;
end if;
end if;

when stop =>


if (S_TICK ='1') then
if (s_reg=(sb_tick-1)) THEN
state_next <= idle;
UART_RX_DONE_TICK <= '1';
else s_next <= s_reg+1;
end if;
383
end if;
end case;
end process;
UART_RX_DATA <= b_reg;
end arch;

entity FIFO_RX is
generic ( B: natural:=8;
W: natural:=2);
Port ( CKHT: in STD_LOGIC;
RST: in STD_LOGIC;
RD: in STD_LOGIC;
WR: in STD_LOGIC;
DATA_WR: in STD_LOGIC_VECTOR (B-1 downto 0);
EMPTY: out STD_LOGIC;
DATA_RD: out STD_LOGIC_VECTOR (B-1 downto 0));
end FIFO_RX;
architecture arch of FIFO_RX is
type reg_file_type is array (2**W-1 DOWNTO 0) of
std_logic_vector(B-1 downto 0);

SIGNAL array_reg: reg_file_type;


signal w_ptr_reg: std_logic_vector(W-1 downto 0);
signal w_ptr_next: std_logic_vector(W-1 downto 0);
signal w_ptr_succ: std_logic_vector(W-1 downto 0);
signal r_ptr_reg: std_logic_vector(W-1 downto 0);
signal r_ptr_next: std_logic_vector(W-1 downto 0);
signal r_ptr_succ: std_logic_vector(W-1 downto 0);

signal full_reg: std_logic;


signal full_next: std_logic;
signal empty_reg: std_logic;
signal empty_nex: std_logic;

signal wr_op: std_logic_vector(1 downto 0);


signal wr_en: std_logic;
begin
process(ckht, rst)
begin
if (RST='1') then
array_reg <= (others=>(others=>'0'));
elsif falling_edge(ckht) then
if wr_en='1' then
array_reg(conv_integer(unsigned(w_ptr_reg))) <=
DATA_WR;
end if;
end if;
end process;

DATA_RD <=
384
array_reg(conv_integer(unsigned(r_ptr_reg)));
wr_en <= wr and (not full_reg);

process(ckht,rst)
begin
if rst='1' then w_ptr_reg <= (others=> '0');
r_ptr_reg <= (others=> '0');
full_reg <= '0';
empty_reg <= '1';
elsif falling_edge(ckht) then
w_ptr_reg <= w_ptr_next;
r_ptr_reg <= r_ptr_next;
full_reg <= full_next;
empty_reg <= empty_next;
end if;
end process;

w_ptr_succ <= w_ptr_reg + 1;


r_ptr_succ <= r_ptr_reg + 1;
wr_op <= WR & RD;

process(w_ptr_reg,w_ptr_succ,r_ptr_reg,r_ptr_succ,wr_op,emp
ty_reg,full_reg)
begin
w_ptr_next <= w_ptr_reg;
r_ptr_next <= r_ptr_reg;
full_next <= full_reg;
empty_next <= empty_reg;
case wr_op is
when "00" =>
when "01" =>
if (empty_reg ='0') then
r_ptr_next <= r_ptr_succ;
full_next <='0';
if (r_ptr_succ = w_ptr_reg) then
empty_next <= '1';
end if;
end if;

when "10" =>


if (full_reg ='0') then
w_ptr_next <= w_ptr_succ;
empty_next <= '0';
if (w_ptr_succ = r_ptr_reg) then
full_next <= '1';
end if;
end if;

when others => w_ptr_next <= w_ptr_succ;


r_ptr_next <= r_ptr_succ;
end case;
385
end process;
EMPTY <= empty_reg;
end arch;

entity UART_CONTROLLER_TX is
generic ( DBIT: INTEGER:=8;
SB_TICK: INTEGER:=16);
Port ( CKHT: in STD_LOGIC;
RST: in STD_LOGIC;
UART_TX_FIFO_NOT_EMPRY: in STD_LOGIC;
S_TICK: in STD_LOGIC;
UART_TX_DATA:in
STD_LOGIC_VECTOR (7 downto 0);
UART_TX_DONE_TICK: out STD_LOGIC;
UART_TX: out STD_LOGIC);
end UART_CONTROLLER_TX;

architecture arch of UART_CONTROLLER_TX is


TYPE state_type is (idle, start, data, stop);
signal state_reg, state_next: state_type;
signal s_reg, s_next: unsigned(3 downto 0);
signal n_reg, n_next: unsigned(2 downto 0);
signal b_reg, b_next: std_logic_vector(7 downto 0);
signal tx_reg, tx_next: std_logic;
begin
process(CKHT, RST)
begin
if RST = '1' then state_reg <= idle;
s_reg <= (others=> '0');
n_reg <= (others=> '0');
b_reg <= (others=> '0');
tx_reg <= '1';
elsif falling_edge(CKHT) then
state_reg <= state_next;
s_reg <= s_next;
n_reg <= n_next;
b_reg <= b_next;
tx_reg <= tx_next;
end if;
end process;

process(state_reg,s_reg,n_reg,b_reg,s_tick,tx_reg,UART_TX_F
IFO_NOT_EMPRY,UART_TX_DATA)
begin
state_next <= state_reg;
s_next <= s_reg;
n_next <= n_reg;
b_next <= b_reg;
tx_next <= tx_reg;
UART_TX_DONE_TICK <= '0';
386
case state_reg is
when idle => tx_next <= '1';
if UART_TX_FIFO_NOT_EMPRY ='1' then
state_next <= start;
s_next <= (others=>'0');
b_next <= UART_TX_DATA;
end if;

when start => tx_next<= '0';


if (s_tick='1') then
if s_reg=15 then
state_next<= data;
s_next<=(others=>'0');
n_next<=(others=>'0');
else s_next<= s_reg+1;
end if;
end if;

when data => tx_next<= b_reg(0);


if (s_tick ='1') then
if s_reg=15 then
s_next<=(others=>'0');
b_next<='0'& b_reg(7 downto 1);
if n_reg=(DBIT-1) then
state_next<= stop;
else n_next<= n_reg+1;
end if;
else s_next<= s_reg+1;
end if;
end if;

when stop => tx_next<= '1';


if (s_tick ='1') then
if s_reg=(SB_TICK-1) then
state_next <= idle;
UART_TX_DONE_TICK<='1';
else s_next<=s_reg+1;
end if;
end if;
end case;
end process;
UART_TX <=tx_reg;
end arch;

entity fifo_tx is
generic (B: natural:=8;
W: natural:=2);
Port ( Ckht : in STD_LOGIC;
Rst: in STD_LOGIC;

387
RD: in STD_LOGIC;
WR: in STD_LOGIC;
DATA_WR: in STD_LOGIC_VECTOR (B-1 downto 0);
EMPTY: out STD_LOGIC;
FULL : out STD_LOGIC;
DATA_RD:out STD_LOGIC_VECTOR (B-1 downto 0));
end fifo_tx;

architecture arch of fifo_tx is


type reg_file_type is array (2**W-1 DOWNTO 0) of
std_logic_vector(B-1 downto 0);

SIGNAL array_reg: reg_file_type;


signal w_ptr_reg: std_logic_vector(W-1 downto 0);
signal w_ptr_next: std_logic_vector(W-1 downto 0);
signal w_ptr_succ: std_logic_vector(W-1 downto 0);

signal r_ptr_reg: std_logic_vector(W-1 downto 0);


signal r_ptr_next: std_logic_vector(W-1 downto 0);
signal r_ptr_succ: std_logic_vector(W-1 downto 0);

signal full_reg: std_logic;


signal full_next: std_logic;
signal empty_reg: std_logic;
signal empty_next: std_logic;
signal wr_op: std_logic_vector(1 downto 0);
signal wr_en: std_logic;
begin
process(ckht, rst)
begin
if (rst='1') then
array_reg <= (others=>(others=>'0'));
elsif falling_edge(ckht) then
if wr_en = '1' then
array_reg(conv_integer(unsigned(w_ptr_reg))) <=
DATA_WR;
end if;
end if;
end process;

DATA_RD <=
array_reg(conv_integer(unsigned(r_ptr_reg)));
wr_en <= wr and (not full_reg);

process(ckht, rst)
begin
if rst='1' then w_ptr_reg <= (others=> '0');
r_ptr_reg <= (others=> '0');
full_reg <= '0';
empty_reg <= '1';
elsif falling_edge(ckht) then
388
w_ptr_reg <= w_ptr_next;
r_ptr_reg <= r_ptr_next;
full_reg <= full_next;
empty_reg <= empty_next;
end if;
end process;
w_ptr_succ <= w_ptr_reg + 1;
r_ptr_succ <= r_ptr_reg + 1;
wr_op <= wr & rd;

process(w_ptr_reg,w_ptr_succ,r_ptr_reg,r_ptr_succ,wr_op,emp
ty_reg,full_reg)
begin
w_ptr_next <= w_ptr_reg;
r_ptr_next <= r_ptr_reg;
full_next <= full_reg;
empty_next <= empty_reg;

case wr_op is
when "00" =>
when "01" =>
if empty_reg ='0' then
r_ptr_next <= r_ptr_succ;
full_next <='0';
if r_ptr_succ = w_ptr_reg then
empty_next <= '1';
end if;
end if;

when "10" =>


if (full_reg ='0') then
w_ptr_next <= w_ptr_succ;
empty_next <= '0';
if (w_ptr_succ = r_ptr_reg) then
full_next <= '1';
end if;
end if;

when others => w_ptr_next <= w_ptr_succ;


r_ptr_next <= r_ptr_succ;
end case;
end process;
full <= full_reg;
empty <= empty_reg;
end arch;

389

You might also like