📄 send_core.vhd
字号:
-- 库声明
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use WORK.SEND_PACKAGE.all;
entity send_core is
generic (
DATA_BIT : integer := 64;-- 数据位个数
TOTAL_BIT : integer := 66;-- 总数据个数(1b起始位,64b数据,1b校验位,1b停止位)
PARITY_RULE:PARITY := ODD
);
port (
-- 时钟信号
clk : in std_logic;
rdclk:out std_logic; -- 读fifo的时钟
rdempty:in std_logic; --读空标志
rdreq:out std_logic;
-- 复位、使能子模块的信号
reset_parts : out std_logic;
reset_dt:out std_logic;
ce_parts : out std_logic;
new_data:in std_logic;
-- 和移位寄存器的接口信号
send_si : out std_logic;
-- 计数器时钟选择信号和计数器计数到达上阈的指示信号
overflow : in std_logic;
RxD:in std_logic;
-- 输出选择信号
sel_out : out std_logic;
parity:in std_logic;
-- dout:out std_logic_vector(5 downto 0);
-- 提供给CPU的接口信号
send_bus : in std_logic_vector(DATA_BIT-1 downto 0)
-- send_bus_2: out std_logic_vector(63 downto 0);
-- send_over : out std_logic
);
end send_core;
architecture send_core of send_core is
-- 内部信号
signal state : UART_STATE := UART_IDLE;
signal send_buf : std_logic_vector(67 downto 0);
signal si_count : integer range 0 to 100 := 0;
signal reg6:std_logic_vector(5 downto 0):= (others => '0');
signal rv_count: integer range 0 to 10 :=0;
--signal send_bus_2:std_logic_vector(63 downto 0);
begin
-- 主过程
main: process(clk)
begin
rdclk <= clk;
if rising_edge(clk) then
case state is
when UART_IDLE => -- 空闲状态
reset_parts <= '0';-- 复位子模块
reset_dt <= '0';
ce_parts <= '0'; -- 子模块使能无效
-- if new_data = '0' then
if (rdempty ='0')then
rdreq <= '1' ;
sel_out <= '0'; -- 使得输出保持为'1'
si_count <= TOTAL_BIT-1;-- 初始化串行加载序列的索引变量
state <= UART_LOAD;-- 改变状态为加载
else
state <= UART_IDLE;
end if;
-- else
-- state <= RECV_DETECT;
-- end if;
-------- 数据加载和发送状态--------
when UART_LOAD => -- 加载状态
-- send_bus_2 <=send_bus;
rdreq <= '0';
if overflow = '1' then -- 如果overflow信号为'1',表示数据加载完成
sel_out <= '0'; -- 使得输出保持为'1'
reset_parts <= '0';-- 复位子模块
ce_parts <= '0'; -- 子模块使能信号无效
state <= UART_SEND;-- 改变状态为发送
else
if not(si_count = TOTAL_BIT-1) then -- 通过增加si_count,
si_count <= si_count+1; --生成串行加载序列
else
si_count <= 0;
end if;
reset_parts <= '1'; -- 子模块复位信号无效
ce_parts <= '1'; -- 子模块使能信号有效
end if;
when UART_SEND => -- 发送状态
sel_out <= '1'; -- 选择输出为TxD
if overflow = '1' then -- 如果overflow为'1',表示发送完成
-- send_over <= '1'; -- 输出发送完成的指示信号
sel_out <= '0';
reset_dt <= '1';
state <= RECV_DETECT;-- 改变状态为发送完成
else
reset_parts <= '1'; -- 子模块复位信号无效
ce_parts <= '1'; -- 子模块使能信号有效
end if;
when RECV_DETECT =>
reset_dt <= '1';
-- send_over <= '0'; -- 恢复发送完成指示信号
reset_parts <= '1'; -- 子模块复位信号无效
ce_parts <= '1'; -- 子模块使能信号有效
if new_data = '1' then
rv_count <= 0;
reset_dt <= '0';
state <= RECV;
-- state <= UART_END_SEND;
else
state <= RECV_DETECT;
end if;
when RECV =>
reset_parts <= '1'; -- 子模块复位信号无效
ce_parts <= '1'; -- 子模块使能信号有效
if not(rv_count = 4) then
reg6(5 downto 1) <= reg6(4 downto 0) ;
reg6(0) <= RxD;
rv_count <= rv_count +1;
else
state <= CHECK;
end if;
when CHECK =>
reset_parts <= '1'; -- 子模块复位信号无效
ce_parts <= '1'; -- 子模块使能信号有效
case reg6 is
when "000000" => --接收正确
reg6 <= "000000";
-- dout <= reg6;
state <= UART_END_SEND;
when "000001" => --接收错误,重发
-- dout <= reg6;
reg6 <= "000000";
reset_parts <= '0';-- 复位子模块
reset_dt <= '0';
ce_parts <= '0'; -- 子模块使能无效
sel_out <= '0'; -- 使得输出保持为'1'
si_count <= TOTAL_BIT-1;-- 初始化串行加载序列的索引变量
state <= UART_LOAD;
when "000010" => --接收FIFO满,等待
-- dout <= reg6;
reg6 <= "000000";
reset_dt <= '1';
state <= RECV_DETECT;
when others =>
-- dout <= reg6;
reg6 <= "000000";
state <= UART_END_SEND;
end case;
when UART_END_SEND => -- 发送完成状态
ce_parts <= '0'; -- 子模块使能信号无效
-- send_over <= '0'; -- 恢复发送完成指示信号
state <= UART_IDLE; -- 改变状态为空闲
end case;
end if;
end process;
-- 生成串行加载序列 (奇偶校验)
send_buffer: process(send_bus,parity)
begin
send_buf(0) <= '0'; -- 存储起始位
send_buf(64 downto 1) <= send_bus(63 downto 0);-- 存储数据位
if PARITY_RULE = ODD or PARITY_RULE = EVEN then
send_buf(65) <= parity;
send_buf(67 DOWNTO 66) <= (others => '1');
else
send_buf(67 DOWNTO 65) <= (others => '1');
end if;
end process;
-- 串行输入选择
si_switch: process(si_count)
begin
if (si_count < TOTAL_BIT ) then
send_si <= send_buf(si_count);-- 将send_buf里面的数据送到send_si端口上
else
send_si <= '1';
end if;
end process;
end send_core;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -