📄 sc_hdlc.vhd
字号:
Rx_fifo_RDn <= '1';
rx_cnt_fifo_rden <= '1';
when others => CPU_DATA_OUT <= (others => '1');
Rx_fifo_RDn <= '1';
rx_cnt_fifo_rden <= '1';
end case;
else
CPU_DATA_OUT <= "11111111";
Rx_fifo_RDn <= '1';
rx_cnt_fifo_rden <= '1';
end if;
end if;
end process;
TX_FIFO_valid <= TX_FIFO_EF;
RX_FIFO_valid <= RX_FIFO_EF;
RX_CNT_FIFO_valid <= RX_CNT_FIFO_EF;
WR_RD_TEST_REG_Gen :
process(RST, CPU_CS, CPU_WRn, CPU_ADD, CPU_clk) -- Read and clear signal generation
begin
if(RST = '0')then
WR_RD_test <= "11111111";
elsif CPU_DSn'event and CPU_DSn = '1' then
if (CPU_CS = '0' and CPU_WRn = '0' and CPU_ADD = "111") then
WR_RD_test <= CPU_DATA_In;
end if;
end if;
end process WR_RD_TEST_REG_Gen;
--============================ below logic is going to cancel =========================
Int_Clear_End_Gen :
process(RST, CPU_CS, CPU_WRn, CPU_ADD, rx_cnt_fifo_ef) -- Read and clear signal generation
begin
if(RST = '0' or rx_cnt_fifo_ef = '0')then
Int_Clr_end <= '1';
else
if (CPU_CS = '0' and CPU_ADD = "100") then
if(CPU_WRn = '1' ) then
Int_clr_end <= '0';
else
Int_clr_end <= '1';
end if;
else
Int_Clr_end <= '1';
end if;
end if;
end process Int_Clear_End_Gen;
Int_Clear_End_d_Gen :
process(RST, CPU_Clk) -- Read and clear signal generation
begin
if(RST = '0') then
Int_Clr_end_d <= (others => '1');
else
if CPU_clk'event and CPU_clk = '1' then
Int_Clr_end_d(0) <= Int_Clr_end;
Int_Clr_end_d(1) <= Int_Clr_end_d(0);
Int_Clr_end_d(2) <= Int_Clr_end_d(1);
Int_Clr_end_d(3) <= Int_Clr_end_d(2);
Int_Clr_end_d(4) <= Int_Clr_end_d(3);
Int_Clr_end_d(5) <= Int_Clr_end_d(4);
Int_Clr_end_d(6) <= Int_Clr_end_d(5);
Int_Clr_end_d(7) <= Int_Clr_end_d(6);
Int_Clr_end_d(8) <= Int_Clr_end_d(7);
Int_Clr_end_d(9) <= Int_Clr_end_d(8);
end if;
end if;
end process Int_Clear_End_d_Gen;
Int_tog_end <= Int_clr_end and Int_end_frame;
process(RST, Int_tog_end) -- Read and clear signal generation
begin
if(RST = '0')then
INTn_end <= '1';
elsif Int_tog_end'event and Int_tog_end = '1' then
INTn_end <= not INTn_end;
end if;
end process;
--=======================================================================================================
CPU_INTn <= not Sig_end_Frame;
FIFO_RST_gen :
process(RST, CPU_CS, CPU_WRn, CPU_ADD, CPU_DSn) -- Read and clear signal generation
begin
if(RST = '0')then
Rx_FIFO_RST <= '1';
Rx_CNT_FIFO_RST <= '1';
Tx_FIFO_RST <= '1';
Rx_sel <= '1';
elsif CPU_DSn'event and CPU_DSn = '1' then
if (CPU_CS = '0' and CPU_WRn = '0' and CPU_ADD = "110") then
if( CPU_DATA_In(0) = '0') then
Rx_FIFO_RST <= '0';
else
Rx_FIFO_RST <= '1';
end if;
if( CPU_DATA_In(1) = '0') then
Rx_CNT_FIFO_RST <= '0';
else
Rx_CNT_FIFO_RST <= '1';
end if;
if( CPU_DATA_In(2) = '0') then
Tx_FIFO_RST <= '0';
else
Tx_FIFO_RST <= '1';
end if;
if( CPU_DATA_In(3) = '0') then
Rx_sel <= '0';
else
Rx_sel <= '1';
end if;
end if;
end if;
end process FIFO_RST_Gen;
ST_REG1 : process(RST, RxClk, RxStatusWrite_n, Int_Clr_end_d(9))
begin
if(RST = '0' or Int_Clr_end_d(9) = '0')then
CRC_ERR <= '0';
Octet_ERR <= '0';
Abort_DET <= '0';
Sig_32B_frame <= '0';
Sig_end_Frame <= '0';
Rx_error <= '0';
elsif RxClk'event and RxClk = '1' then
if (RxStatusWrite_n = '0') then
CRC_ERR <= RxOutputData(0); -- CRC Error of Frame
Octet_ERR <= RxOutputData(1); -- Octet Error of Frame
Abort_DET <= RxOutputData(2); -- Abort Detected
Rx_error <= RxOutputData(0) or RxOutputData(1) or RxOutputData(2);
elsif (Int_32bytes = '0') then
Sig_32B_Frame <= '1'; -- Indicate 32 bytes
elsif (Int_latch2 = '0') then
Sig_end_Frame <= not Rx_cnt_fifo_EF;
else
null;
end if;
end if;
end process ST_REG1;
Int_end_latch : process(RST, RxClk) -- Generate interrupt latch signal
begin
if(RST = '0')then
Int_latch0 <= '1';
Int_latch1 <= '1';
Int_latch2 <= '1';
elsif RxClk'event and RxClk = '1' then
Int_latch0 <= Int_End_frame;
Int_latch1 <= Int_latch0;
Int_latch2 <= Int_latch1;
end if;
end process Int_end_latch;
--========================================================================
--======================== Rx Diagnostic logic =========================
-- When Rx HDLC Data is fail(CRC, Octet and Abort error), Rx FIFO and Rx HDLC Controller are restart
process(rst, rxclk, rx_error)
begin
if rst = '0' then
Diag_cnt <= 0;
elsif rxclk'event and rxclk = '1' then
if (rx_error = '1' and Diag_cnt < 500) then
Diag_cnt <= Diag_cnt + 1;
elsif (rx_error = '1' and Diag_cnt = 500) then
Diag_cnt <= 500;
else
Diag_cnt <= 0;
end if;
end if;
end process;
process(rst, Diag_cnt)
begin
if rst = '0' then
Rx_reset <= '1';
elsif (Diag_cnt >= 1 and Diag_cnt <= 499) then
Rx_reset <= '0';
else
Rx_reset <= '1';
end if;
end process;
--========================================================================
--========================= Rx state control =============================
process(Rxclk, rst)
begin
if (RST = '0') then
state_status <= idle;
byte_cnt <= "00000000";
bit_cnt <= "0000";
frame_cnt <= "00000000";
Int_32bytes <= '1';
Int_End_frame <= '1';
over_256 <= '0';
elsif (Rxclk'event and Rxclk = '1') then
case state_status is
when idle =>
byte_cnt <= "00000000";
bit_cnt <= "0000";
frame_cnt <= "00000000";
Int_32bytes <= '1';
Int_End_frame <= '1';
over_256 <= '0';
if ( RxDataWrite_n = '0') then
state_status <= start;
else
state_status <= idle;
end if;
when start =>
Int_32bytes <= '1';
Int_End_frame <= '1';
if (RxStatusWrite_n = '1') then
if (RxDataWrite_n = '0') then
if (byte_cnt = "11111101") then
over_256 <= '1';
state_status <= start;
byte_cnt <= byte_cnt + 1;
else
over_256 <= '0';
state_status <= start;
byte_cnt <= byte_cnt + 1;
end if;
else
state_status <= start;
over_256 <= '0';
end if;
else
if (byte_cnt = "11111101") then
over_256 <= '1';
state_status <= end_frame;
byte_cnt <= byte_cnt + 1;
else
over_256 <= '0';
state_status <= end_frame;
byte_cnt <= byte_cnt + 1;
end if;
end if;
when end_frame =>
Int_end_frame <= '0';
Frame_cnt <= byte_cnt + 1;
state_status <= idle;
over_256 <= '0';
when others =>
null;
end case;
end if;
end process;
--======================================================================
--====================== Tx Control Logic======= ===========================
Tx_CNTL : process(RST, CPU_CS, CPU_WRn, CPU_ADD) -- Tx control Register
begin
if(RST = '0')then
Tx_fifo_WRn <= '1';
else
if (CPU_CS = '0' and CPU_WRn = '0') then
case CPU_Add is
when "000" => Tx_fifo_WRn <= CPU_WR_DSn;
when others => Tx_fifo_WRn <= '1';
end case;
else
Tx_fifo_WRn <= '1';
end if;
end if;
end process Tx_CNTL;
Tx_End_Gen :
process(RST, Tx_Fifo_EF, CPU_CS, CPU_WRn, CPU_ADD) -- Tx control Register
begin
if(RST = '0' or Tx_fifo_ef = '1')then
Tx_End_Sig <= '0';
else
if (CPU_DSn'event and CPU_DSn = '1') then
if (CPU_CS = '0' and CPU_WRn = '0' and CPU_ADD = "001") then
Tx_End_Sig <= CPU_data_in(1);
end if;
end if;
end if;
end process Tx_End_Gen;
Tx_con_Gen :
process(RST, Tx_Fifo_EF, txclk) -- Tx control Register
begin
if(RST = '0' or Tx_fifo_ef = '1')then
TxStart_1 <= '0';
TxStart_2 <= '0';
TxStart_3 <= '0';
else
if (txclk'event and txclk ='1') then
TxStart_1 <= Tx_end_sig;
TxStart_2 <= TxStart_1;
TxStart_3 <= TxStart_2;
end if;
end if;
end process Tx_con_Gen;
Txstart <= (Txstart_1 xor Txstart_2) and txEmpty_n;
Tx_Empty_Gen :
process(RST, Tx_Fifo_EF, txclk) -- Tx control Register
begin
if(RST = '0' or Tx_fifo_ef = '1')then
TxEmpty_n <= '0';
else
if (txclk'event and txclk ='1') then
TxEmpty_n <= Tx_end_sig;
end if;
end if;
end process Tx_empty_Gen;
txcnt_Clear_Gen :
process(RST, CPU_CS, CPU_WRn, CPU_ADD)
begin
if(RST = '0')then
txcnt_clear <= '1';
else
if (CPU_CS = '0' and CPU_ADD = "000") then
if(CPU_WRn = '1' ) then
txcnt_clear <= '0';
else
txcnt_clear <= '1';
end if;
else
txcnt_clear <= '1';
end if;
end if;
end process txcnt_Clear_Gen;
Int_Clear_End_d_Gen :
process(RST, CPU_Clk) -- Read and clear signal generation
begin
if(RST = '0') then
txcnt_clear_d <= (others => '1');
else
if CPU_clk'event and CPU_clk = '1' then
txcnt_clear_d(0) <= txcnt_clear;
txcnt_clear_d(1) <= txcnt_clear_d(0);
txcnt_clear_d(2) <= txcnt_clear_d(1);
txcnt_clear_d(3) <= txcnt_clear_d(2);
txcnt_clear_d(4) <= txcnt_clear_d(3);
txcnt_clear_d(5) <= txcnt_clear_d(4);
txcnt_clear_d(6) <= txcnt_clear_d(5);
txcnt_clear_d(7) <= txcnt_clear_d(6);
txcnt_clear_d(8) <= txcnt_clear_d(7);
txcnt_clear_d(9) <= txcnt_clear_d(8);
end if;
end if;
end process Int_Clear_End_d_Gen;
Tx_Byte_CNT :
process(RST, Tx_Fifo_WRn, TxEmpty_n) -- Tx control Register
begin
if(RST = '0' or txcnt_clear_d(9) = '0')then
Tx_Byte_CNT <= (others => '0');
elsif Tx_Fifo_WRn'event and Tx_Fifo_WRn = '1' then
Tx_Byte_CNT <= Tx_Byte_CNT + 1;
end if;
end process Tx_Byte_CNT;
--====================== Tx HDLC controller ============================
TX: HDLC_TRANSMIT_CCITT port map(
-- Global Reset
Reset => Inv_Rst, -- Master reset
-- HDLC Transmit Serial Interface
TxC => TxClk, -- Transmit Serial Clock
TxD => TxDataa, -- Transmit Serial Data
-- HDLC Transmit External Memory Interface
TxInputData_B0 => TxInputData(0),
TxInputData_B1 => TxInputData(1),
TxInputData_B2 => TxInputData(2),
TxInputData_B3 => TxInputData(3),
TxInputData_B4 => TxInputData(4),
TxInputData_B5 => TxInputData(5),
TxInputData_B6 => TxInputData(6),
TxInputData_B7 => TxInputData(7),
TxRead_n => TxRead_n, -- Transmit Data Read
TxEmpty_n => TxEmpty_n, -- Transmit Data Empty
TxStart => TxStart, -- Transmit Start
TxAbort => '0', --TxAbort, -- Transmit Abort
TxEnable => '1'
);
--======================================================================
Tx_fifo_RD <= not TxRead_n;
Tx_fifo_WR <= not Tx_Fifo_WRn;
--======================= Tx FIFO Memory ===============================
TX_FIFO : TX_FIFO
port map(
Data =>CPU_Data_In,
WrClock =>CPU_clk,
RdClock =>TxClk,
WrEn => Tx_fifo_WR,
RdEn =>Tx_fifo_RD,
Reset =>TX_MEM_RST,
Q =>TxInputData,
Full =>Tx_FIFO_FF,
AlmostFull =>Tx_FIFO_AEF,
Empty =>Tx_FIFO_EF,
AlmostEmpty =>Tx_FIFO_AEF);
--=======================================================================
end SC_HDLC_a;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -