📄 decoding.vhd
字号:
----------------------------------------------------------------------------------
-- Company: Han'slaser
-- Engineer: Zhouj110624
-- Create Date: 08:53:15 09/22/2012
-- Design Name: decoding
-- Module Name: decoding - Behavioral
-- Project Name: decoding
-- Target Devices:
--功能说明:对输入的曼切斯特码进行解码,并将解码后的串行数据转换为并行数据
--其中同步头由4个高电平的编码时钟组成(32个解码时钟)
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use work.PCK_CRC8_D1.ALL;
entity decoding is
Port (
CLK : in STD_LOGIC; DECODE_EN : in STD_LOGIC; MANCHESTER_WITHOUT_HEADER : in STD_LOGIC; --输入的曼切斯特码
DECODE_ERROR : out STD_LOGIC; DECODE_OUT : out std_logic_vector( 20 downto 0) --解码后的串行编码 );
end decoding;
architecture Behavioral of decoding is
----------------------------------------------------------------------------------
signal crc8_data_reg : std_logic_vector( 7 downto 0 ) := (others => '0');
signal crc8_data : std_logic_vector( 7 downto 0 ) := (others => '0');
signal manchester_data : std_logic_vector( 28 downto 0) := (others => '0');
signal decode_reg1 : std_logic := '0';
signal decode_reg2 : std_logic := '0';
signal decode_coder : std_logic := '0';--输出串行码元内部信号
signal coder_cnt : std_logic_vector( 2 downto 0 ) := (others => '0');--时钟计数
-- signal coder_high_cnt : std_logic_vector( 2 downto 0 ) := (others => '0');--时钟计数,用于判断码的‘0’‘1’状态
signal manchester_cnt : std_logic_vector( 4 downto 0 ) := (others => '0');--串转并
signal decoder_end : std_logic := '0';
signal decoder_end_reg : std_logic := '0';
signal decod_end_reg_cnt1 : std_logic_vector(10 downto 0) := (others => '0');
begin
----------------------------------------------------------------------------------
--组合运算
----------------------------------------------------------------------------------
-- DECODE_OUT <= manchester_data(28 downto 8);
-- Pod_crc <= crc8_data;
----------------------------------------------------------------------------------
--曼切斯特码解码进程,通过计数器实现:整个曼切斯特码为8个解码时钟周期,而其高电平仅为4个时钟周期,
--码元‘1’:高电平在前,码元‘0’:低电平在前,所以在整个码前6个周期中,对码元高电平计数,若记得的数值
--小于3 则此码为:‘0’,若记得的数值大于等于3,则此码为:‘1’。
----------------------------------------------------------------------------------
----------------------------------------------------------------------------------
--对解码时钟计数,最大计数值为7
----------------------------------------------------------------------------------
Pr_cnt_CLK :
process(CLK)
begin
if rising_edge(CLK) then
if DECODE_EN = '0' then
coder_cnt <= (others => '0');
else
if coder_cnt < "111" then--7
coder_cnt <= coder_cnt + 1;
else
coder_cnt <= (others => '0');
end if;
end if;
end if;
end process;
----------------------------------------------------------------------------------
--判断电平
----------------------------------------------------------------------------------
-- Pr_cnt_hgih :
-- process(CLK)
-- begin
-- if rising_edge(CLK) then
-- if DECODE_EN = '0' then
-- coder_high_cnt <= (others => '0');
-- DECODE_ERROR <= '0';
-- else
-- if coder_cnt < "101" then--6
-- DECODE_ERROR <= '0';
-- if MANCHESTER_WITHOUT_HEADER = '1' then
-- coder_high_cnt <= coder_high_cnt + 1;
-- else
-- coder_high_cnt <= coder_high_cnt;
-- end if;
-- elsif coder_cnt = "100" then--5
-- --小于3,即前4个时钟为低电平
-- if coder_high_cnt < "010" then--4
-- DECODE_ERROR <= '0';
-- decode_coder <= '0';
-- --大于等于,即前4个时钟为高电平
-- elsif coder_high_cnt < "100" then--5
-- DECODE_ERROR <= '0';
-- decode_coder <= '1';
-- else
-- DECODE_ERROR <= '1';
-- end if;
-- else
-- DECODE_ERROR <= '0';
-- coder_high_cnt <= (others => '0');
-- end if;
-- end if;
-- end if;
-- end process;
-- decode_reg1 <= '0' when coder_cnt = "010" and MANCHESTER_WITHOUT_HEADER = '0' else
-- '1' when coder_cnt = "010" and MANCHESTER_WITHOUT_HEADER = '1' else
-- decode_reg1;
-- decode_reg2 <= '0' when coder_cnt = "101" and MANCHESTER_WITHOUT_HEADER = '0' else
-- '1' when coder_cnt = "101" and MANCHESTER_WITHOUT_HEADER = '1' else
-- decode_reg2;
Pr_just : process(CLK)
begin
if rising_edge(CLK) then
if DECODE_EN = '0' then
decode_reg1 <= '0';
decode_reg2 <= '0';
else
if (coder_cnt > "001") and (coder_cnt < "011") then--1-3
if MANCHESTER_WITHOUT_HEADER = '0' then
decode_reg1 <= '0';
else
decode_reg1 <= '1';
end if;
elsif (coder_cnt > "100") and (coder_cnt < "110") then--4-6
if MANCHESTER_WITHOUT_HEADER = '0' then
decode_reg2 <= '0';
else
decode_reg2 <= '1';
end if;
else
null;
end if;
end if;
end if;
end process;
Pr_decode : process(CLK)
begin
if rising_edge(CLK) then
if DECODE_EN = '0' then
DECODE_ERROR <= '0';
decode_coder <= '0';
else
if coder_cnt = "110" then
if decode_reg1 = '0' and decode_reg2 = '1' then
decode_coder <= '0';
DECODE_ERROR <= '0';
elsif decode_reg1 = '1' and decode_reg2 = '0' then
decode_coder <= '1';
DECODE_ERROR <= '0';
else
DECODE_ERROR <= '1';
end if;
else
DECODE_ERROR <= '0';
end if;
end if;
end if;
end process;
----------------------------------------------------------------------------------
--串转并处理和CRC8校验
----------------------------------------------------------------------------------
Pr_tran :
process(CLK)
begin
if rising_edge(CLK) then
if DECODE_EN = '0' then
manchester_cnt <= (others => '0');
crc8_data_reg <= (others => '0');
decoder_end <= '0';
else
if coder_cnt < "111" then--7
manchester_cnt <= manchester_cnt;
else
manchester_cnt <= manchester_cnt + 1;
manchester_data ( 28 - conv_integer( manchester_cnt ) ) <= decode_coder;--以串行码开头作为高位
if manchester_cnt < "10101" then--21
decoder_end <= '0';
crc8_data_reg <= nextCRC8_D1( decode_coder, crc8_data_reg);
elsif manchester_cnt < "11100" then--28
decoder_end <= '0';
else
decoder_end <= '1';
-- DECODE_OUT <= manchester_data(28 downto 8);
crc8_data <= crc8_data_reg;
end if;
end if;
end if;
end if;
end process;
----------------------------------------------------------------------------------
--输出标志位
----------------------------------------------------------------------------------
Pr_d : process(CLK) begin if rising_edge(CLK) then decod_end_reg_cnt1(0) <= decoder_end; decod_end_reg_cnt1(10 downto 1) <= decod_end_reg_cnt1(9 downto 0); decoder_end_reg <= decod_end_reg_cnt1(10); end if; end process;
Pr_mark :
process(CLK)
begin
if rising_edge(CLK) then
if ( crc8_data = manchester_data(7 downto 0) )and ( decoder_end_reg = '1' ) then
DECODE_OUT <= manchester_data(28 downto 8);
else
null;
end if;
end if;
end process;
end Behavioral;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -