《内置FIFO的UART设计与实现(共15页).doc》由会员分享,可在线阅读,更多相关《内置FIFO的UART设计与实现(共15页).doc(15页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。
1、精选优质文档-倾情为你奉上内置FIFO的UART设计与实现一、程序(加批注)library ieee; -U1:RSRuse ieee.std_logic_1164.all;use ieee.std_logic_unsigned.all;use ieee.std_logic_arith.all;entity RSR is port(reset:in std_logic; rx:in std_logic; clk:in std_logic; rx_data:out std_logic_vector(7 downto 0); rx_int:out std_logic);end entity; ar
2、chitecture arc of RSR issignal shifter:std_logic_vector(7 downto 0);signal bitstate:integer range 0 to 10:=0;beginprocess(clk,reset,rx) -接收进程begin if(reset=1) then -复位信号 bitstate=0; shifter=ZZZZZZZZ; elsif(rising_edge(clk) then if(bitstate=0) then -状态0 判断有没有数据输入 if(rx=0) then bitstate=bitstate+1; en
3、d if; elsif(bitstate=9) then -状态9 数据接收完成 bitstate=0; else -其他状态接收1-8为数据,停止位不检查 shifter(0)=rx; shifter(7 downto 1)=shifter(6 downto 0); bitstate=bitstate+1; end if; end if; end process;process(clk,reset) -输出进程begin if(reset=1) then rx_data=; rx_int=0; elsif(rising_edge(clk) then if(bitstate=9) then r
4、x_data=shifter; -数据输出 rx_int=1; else rx_int=0; rx_data=ZZZZZZZZ; end if; end if;end process; end arc; library ieee; -U2:FIFO ( 8 * 8 bit )use ieee.std_logic_1164.all;entity FIFO is port( clock : in std_logic; reset : in std_logic; wr_req : in std_logic; -写请求 rd_req : in std_logic; -读请求 data_in : in
5、std_logic_vector(7 downto 0); full : buffer std_logic; -满状态,1有效 empty : buffer std_logic; -空状态,1有效 data_out : out std_logic_vector(7 downto 0);end FIFO;architecture arch of FIFO is type type_2d_array is array(0 to 7) of std_logic_vector(7 downto 0); signal fifo_memory : type_2d_array; signal wr_addr
6、ess : integer range 0 to 7; signal rd_address : integer range 0 to 7; signal offset : integer range 0 to 7; signal data_buffer : std_logic_vector(7 downto 0);beginoffset rd_address)else (8 - (rd_address - wr_address)when (rd_address wr_address)else 0;empty = 1 when (offset = 0) else 0; full = 1 when
7、 (offset = 7) else 0; -实际存储空间7 * 8 bit,空出1*8bit以区分空和满process(clock,rd_req) -读进程begin if (clockevent and clock=1) then -同步清0 if reset = 1 then rd_address = 0; data_buffer 0); elsif (rd_req = 1 and empty = 0) then -读出数据 data_buffer rd_address rd_address = rd_address + 1 ; end case; end if; end if;end
8、process;data_out = data_buffer ;process(clock,wr_req) -写进程begin if (clockevent and clock=1) then -同步清0 if reset = 1 then wr_address = 0; elsif (wr_req = 1 and full = 0) then -写入数据 fifo_memory(wr_address) wr_address wr_address = wr_address + 1 ; end case; end if; end if;end process;end arch;library i
9、eee; -U3:TSRuse ieee.std_logic_1164.all;use ieee.std_logic_unsigned.all;use ieee.std_logic_arith.all;entity TSR is port(reset:in std_logic; tx_data:in std_logic_vector(7 downto 0); tx_int:in std_logic; - clk:in std_logic; tx:out std_logic; tx_req:out std_logic);end entity; architecture arc of TSR is
10、signal shifter:std_logic_vector(7 downto 0);type state is(s0,s1,s2);beginprocess(clk,reset) variable cnt:integer range 0 to 8:=0; variable present_state:state;begin if(reset=1) then tx=1; tx_req -判定有没有并行数据输入 if(tx_int=0) then shifter=tx_data; tx=1; tx_req=1; present_state:=s1; -一旦进入并串转换输出,TSR不再受empt
11、y的控制 else tx=1; tx_req -状态1,低电平起始位输出 tx=0; tx_req -状态2,8位数据移位输出 if(cnt8) then tx=shifter(7-cnt); cnt:=cnt+1; tx_req=0; present_state:=s2; else -状态2,高电平停止位输出 cnt:=0; tx=1; tx_reqRXD,clk=bps_clk,reset=rst,rx_data=data1,rx_int=req1);U2:FIFO port map(data_in=data1,wr_req=req1,clock=bps_clk,reset=rst,dat
12、a_out=data2,rd_req=req2,empty=req3);U3:TSR port map(tx_data=data2,tx_int=req3,clk=bps_clk,reset=rst,tx_req=req2,tx=TXD);end arc;二、功能仿真如图中若干蓝线的划分:输入RXD:0 0000 0100 1 0 0001 0000 1 0 0011 0000 1 0 0110 1001 1 (即以8421BCD码形式输入本人的学号:) 0 0000 0000 1 1 1111 1111 1(无效输入)对于第五行(即输入00)的说明:本程序设计 发送模块TSR 控制FIFO的
13、rd_req信号:只有当FIFO成功将其输出传送给TSR之后,才会产生tx_req信号控制rd_req信号并在下一个时钟上升沿下,FIFO进行读进程实现读取输出(只有这样才能实现FIFO输出的刷新)以及读指针的自增操作。而对于输入的数据69,尽管FIFO最终已经将其输出,但是由于读指针实现自增,empty变成1,无法将数据69传输到发送模块TSR。所以在输入的学号数据后面还要加上一个无用的8位数据将其写入FIFO以使写指针自增,实现empty=0,再在下一个时钟上升沿下将数据69传送到TSR,最终将输入的学号数据完整的输出。如图中若干蓝线的划分:输出TXD:1 0 0000 0000 1 1
14、0 0000 0100 1 1 0 0001 0000 1 1 0 0011 0000 1 1 0 0110 1001 1(学号的输出) 1 1 1111 1111 1(无效)对于第一行(即输出00)说明:由图可以看出是在第13个时钟周期开始输出的,因为开始清0后empty=1,直到第10个时钟上升沿下,rx_int=1(即wr_req=1)并且RSR输出数据,在第11个时钟上升沿下,向FIFO中写入数据04,empty=0(即tx_int=0),在第12个时钟上升沿下,FIFO的输出要送入TSR并且TSR输出1(此时tx_req=1)。而在此之前,因为tx_req=0(即rd_req=0),
15、尽管读指针为0不变并且所指向的数据变成04(即只执行了写进程而没有进行读进程),但是FIFO的输出一直保持着一开始复位清0时的输出00,在第13个时钟上升沿下TSR输出数据的起始位0(此时FIFO进行读进程,FIFO读取读指针所指向的数据04,输出变为04,但是读指针实现自增致使empty=1,不能将数据04送入TSR),接着依次输出00。说明:接收模块RSR:从输入数据到输出数据整个周期为 10 个时钟周期(数据格式:起始位0+8位有效数据+停止位1)。FIFO模块:对于发送模块TSR的设计:只要FIFO不为空(即empty=0),则在时钟上升沿的情况下,FIFO则将其输出(复位清0后输出为
16、00)传送给 TSR。TSR在每次输出10位数据(输出数据格式:8位数据开头加上起始位0,结尾加上停止位1)前,则在判断状态下输出1的同时产生tx_req信号请求FIFO输出下一个数据,在下一个时钟上升沿下,若empty=0则读指针自增指向下一个数据,并且FIFO将其输出实现输出的刷新;否则,读指针不变,并且FIFO输出不变。对于接收模块RSR的设计:只要RSR检验数据并接收完毕数据就会产生rx_int信号请求向FIFO中写入数据,如果full=0则在下一个时钟上升沿下数据写入;否则该数据相当于被丢弃不会再写入FIFO中,RSR再次进入检验状态,等待下一个有效数据。发送模块TSR:因为多了一个
17、判断状态(此时TXD输出1),再加上10位的数据,所以从数据输入到输出整个周期为 11 个时钟周期三、时序仿真四、耗用报告五、生成逻辑图附:对三个模块的设计与实现一、 接受模块U1:RSR1、 程序library ieee;use ieee.std_logic_1164.all;use ieee.std_logic_unsigned.all;use ieee.std_logic_arith.all;entity RSR is port(reset:in std_logic; rx:in std_logic; -串行数据接收端RXD clk:in std_logic; -时钟clk rx_dat
18、a:out std_logic_vector(7 downto 0); -FIFO中的data_in rx_int:out std_logic); -FIFO中的wr_reqend entity; architecture arc of RSR issignal shifter:std_logic_vector(7 downto 0);signal bitstate:integer range 0 to 10:=0;beginprocess(clk,reset,rx) -接收进程 begin if(reset=1) then -复位信号 -异步清0 bitstate=0; shifter=ZZ
19、ZZZZZZ; elsif(rising_edge(clk) then if(bitstate=0) then -状态0 判断有没有数据输入 if(rx=0) then bitstate=bitstate+1; end if; elsif(bitstate=9) then -状态9 数据接收完成 bitstate=0; else -其他状态接收1-8为数据,停止位不检查 shifter(0)=rx; shifter(7 downto 1)=shifter(6 downto 0); bitstate=bitstate+1; end if; end if; end process;process(
20、clk,reset) -输出进程begin if(reset=1) then rx_data=; -异步清0 rx_int=0; elsif(rising_edge(clk) then if(bitstate=9) then rx_data=shifter; -数据输出 rx_int=1; else rx_int=0; rx_data=ZZZZZZZZ; -不输出时呈高阻状态 end if; end if;end process; end arc;2、 功能仿真3、 时序仿真二、 U2:FIFO1、程序library ieee;use ieee.std_logic_1164.all;use i
21、eee.std_logic_unsigned.all;use ieee.std_logic_arith.all; entity FIFO is port( clock : in std_logic; reset : in std_logic; wr_req : in std_logic; rd_req : in std_logic; data_in : in std_logic_vector(7 downto 0); full : buffer std_logic; empty : buffer std_logic; data_out : out std_logic_vector(7 down
22、to 0);end FIFO;architecture arch of FIFO is type type_2d_array is array(0 to 7) of std_logic_vector(7 downto 0); signal fifo_memory : type_2d_array; signal wr_address : integer range 0 to 7; signal rd_address : integer range 0 to 7; signal offset : integer range 0 to 7; signal data_buffer : std_logi
23、c_vector(7 downto 0);beginoffset rd_address)else (8 - (rd_address - wr_address)when (rd_address wr_address)else 0;empty = 1 when (offset = 0) else 0;full = 1 when (offset = 7) else 0; -实际7*8bit容量(full=1)process(clock,rd_req)begin if (clockevent and clock=1) then if reset = 1 then rd_address = 0; dat
24、a_buffer 0); elsif (rd_req = 1 and empty = 0) then -empty=1则输出保持 data_buffer rd_address rd_address = rd_address + 1 ; end case; end if; end if;end process;data_out = data_buffer ;process(clock,wr_req)begin if (clockevent and clock=1) then -同步清0 clock时钟 if reset = 1 then wr_address = 0; elsif (wr_req
25、 = 1 and full = 0) then -full=1而wr_req=1则丢弃数据 fifo_memory(wr_address) wr_address wr_address = wr_address + 1 ; end case; end if; end if;end process;end arch;2、功能仿真3、时序仿真三、 发送模块U3:TSR1、 程序library ieee;use ieee.std_logic_1164.all;use ieee.std_logic_unsigned.all;use ieee.std_logic_arith.all;entity TSR
26、is port(reset:in std_logic; -复位信号 tx_data:in std_logic_vector(7 downto 0); -8位并行数据输入 tx_int:in std_logic; clk:in std_logic; tx:out std_logic; -串行数据发送端TXD tx_req:out std_logic);end entity; architecture arc of TSR issignal shifter:std_logic_vector(7 downto 0);type state is(s0,s1,s2);beginprocess(clk,r
27、eset) variable cnt:integer range 0 to 8:=0; variable present_state:state;begin if(reset=1) then tx=1; tx_req -判定有没有并行数据输入 if(tx_int=0) then shifter=tx_data; tx=1; tx_req=1; present_state:=s1; else tx=1; tx_req -状态1,低电平起始位输出 tx=0; tx_req -状态2, 8位数据移位输出 if(cnt8) then tx=shifter(7-cnt); cnt:=cnt+1; tx_req=0; present_state:=s2; else -状态2,高电平停止位输出 cnt:=0; tx=1; tx_req=0; present_state:=s0; end if; end case; end if;end process;end arc;2、 功能仿真3、 时序仿真专心-专注-专业