📄 mc8051_siu_rtl.vhd
字号:
--------------------------------------------------------------------------------- ---- X X XXXXXX XXXXXX XXXXXX XXXXXX X ---- XX XX X X X X X X X XX ---- X X X X X X X X X X X X ---- X X X X X X X X X X X X ---- X X X X XXXXXX X X XXXXXX X ---- X X X X X X X X X ---- X X X X X X X X X ---- X X X X X X X X X X ---- X X XXXXXX XXXXXX XXXXXX XXXXXX X ---- ---- ---- O R E G A N O S Y S T E M S ---- ---- Design & Consulting ---- ----------------------------------------------------------------------------------- ---- Web: http://www.oregano.at/ ---- ---- Contact: mc8051@oregano.at ---- ----------------------------------------------------------------------------------- ---- MC8051 - VHDL 8051 Microcontroller IP Core ---- Copyright (C) 2001 OREGANO SYSTEMS ---- ---- This library is free software; you can redistribute it and/or ---- modify it under the terms of the GNU Lesser General Public ---- License as published by the Free Software Foundation; either ---- version 2.1 of the License, or (at your option) any later version. ---- ---- This library is distributed in the hope that it will be useful, ---- but WITHOUT ANY WARRANTY; without even the implied warranty of ---- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ---- Lesser General Public License for more details. ---- ---- Full details of the license can be found in the file LGPL.TXT. ---- ---- You should have received a copy of the GNU Lesser General Public ---- License along with this library; if not, write to the Free Software ---- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA ---- --------------------------------------------------------------------------------------- Author: Roland H鰈ler---- Filename: mc8051_siu_rtl.vhd---- Date of Creation: Mon Aug 9 12:14:48 1999---- Version: $Revision: 1.8 $---- Date of Latest Version: $Date: 2002/09/05 11:16:08 $------ Description: Serial interface unit for the mc8051 microcontroller.---------------------------------------------------------------------------------------architecture rtl of mc8051_siu is signal s_rxpre_count : unsigned(5 downto 0); -- Receive prescaler signal s_txpre_count : unsigned(5 downto 0); -- Transmit prescaler signal s_m0_shift_en : std_logic; -- masks out every sixteenth -- rising edge of clk signal s_m2_rxshift_en : std_logic; -- mode 2 shift enable signal s_m13_rxshift_en : std_logic; -- mode 1 and 3 shift enable signal s_m2_txshift_en : std_logic; -- mode 2 shift enable signal s_m13_txshift_en : std_logic; -- mode 1 and 3 shift enable signal s_ff0 : std_logic; -- flipflop for edge dedection signal s_ff1 : std_logic; -- flipflop for edge dedection signal s_tf : std_logic; -- synchronised timer flag signal s_mode : unsigned(1 downto 0); -- mode signal s_sm2 : std_logic; -- multi processor comm. bit signal s_detect : std_logic; -- indicates start of recept. signal s_ren : std_logic; -- receive enable signal s_rxd_val : std_logic; -- received data bit signal s_txdm0 : std_logic; -- shift clock for m0 signal s_ri : std_logic; -- external receive interrupt signal s_trans : std_logic; -- enable transmission signal s_recv_done : std_logic; -- receive interrupt signal s_tran_done : std_logic; -- transmit interrupt signal s_rb8 : std_logic; -- 8th data bit signal s_tb8 : std_logic; -- 8th data bit signal s_recv_state : unsigned(3 downto 0); -- state reg. of receive unit signal s_tran_state : unsigned(3 downto 0); -- state reg. of transmit unit signal s_rxd_ff0 : std_logic; -- sample flip-flop signal s_rxd_ff1 : std_logic; -- sample flip-flop signal s_rxd_ff2 : std_logic; -- sample flip-flop signal s_det_ff0 : std_logic; -- rec. detect flip-flop signal s_det_ff1 : std_logic; -- rec. detect flip-flop signal s_tran_sh : unsigned(10 downto 0); -- transmission shift register signal s_recv_sh : unsigned(7 downto 0); -- reception shift register signal s_recv_buf : unsigned(7 downto 0); -- reception buffer register signal s_rxm13_ff0 : std_logic; -- generates an enable singal signal s_rxm13_ff1 : std_logic; -- generates an enable singal signal s_txm13_ff0 : std_logic; -- generates an enable singal signal s_txm13_ff1 : std_logic; -- generates an enable singal begin -- architecture rtl s_mode(1) <= scon_i(4); -- defines the 4 operating modes s_mode(0) <= scon_i(3); s_ren <= scon_i(1); -- receive enable s_sm2 <= scon_i(2); -- 1 time or half time baud rate s_tb8 <= scon_i(0); -- 9th data bit for transmission s_ri <= scon_i(5); -- the receive interrupt bit of the -- control unit sbuf_o <= std_logic_vector(s_recv_buf); -- the receive buffer output scon_o(0) <= s_recv_done; -- set when reception is completed scon_o(1) <= s_tran_done; -- set when transmission is completed scon_o(2) <= s_rb8; -- 9th data bit of reception ------------------------------------------------------------------------------- -- The two flip flops are updated every rising clock edge of clk. -- If a rising edge -- on the port tf_i is dedected the signal s_tf is set to 1 for one period. -- -- The transmission start signal s_trans is generated and held high till -- the statemachine has been launched with its first shift. -- -- The shift clock for mode0 is generated. It toggles with the half -- s_m0_shift_en rate. s_tf <= '1' when (s_ff0 = '1' and s_ff1 = '0') else '0'; p_sample_tf: process (clk, reset) begin if reset = '1' then s_ff0 <= '0'; s_ff1 <= '0'; s_trans <= '0'; else if clk'event and clk = '1' then s_ff0 <= tf_i; s_ff1 <= s_ff0; if trans_i = '1' then s_trans <= '1'; else case s_mode is when ("00") => if s_m0_shift_en = '1' then s_trans <= '0'; end if; when ("01") => if s_m13_txshift_en = '1' then s_trans <= '0'; end if; when ("10") => if s_m2_txshift_en = '1' then s_trans <= '0'; end if; when others => if s_m13_txshift_en = '1' then s_trans <= '0'; end if; end case; end if; end if; end if; end process p_sample_tf; ------------------------------------------------------------------------------- -- The register s_rxpre_count is driven with the system clock clk. So a -- good enable signal (which is stable when clk has its rising edge) can be -- derived to mask out every pulse of clk needed. -- s_m0_shift_en activates every sixteenth clock cycle -- s_m2_shift_en activates baud rates of 1/32 or 1/64 the clock frequenzy -- depending on signal smod_i -- s_m13_shift_en activates baud rates depending on timer/counter1 flag s_m0_shift_en <= '1' when s_txpre_count(3 downto 0) = conv_unsigned(15,5) else '0'; s_m2_rxshift_en <= '1' when (s_rxpre_count(4 downto 0) = conv_unsigned(31,5) and smod_i = '1') or (s_rxpre_count = conv_unsigned(63,6) and smod_i = '0') else '0'; s_m13_rxshift_en <= '1' when s_rxm13_ff0 = '1' and s_rxm13_ff1 = '0' else '0'; s_m2_txshift_en <= '1' when (s_txpre_count(4 downto 0) = conv_unsigned(31,5) and smod_i = '1') or (s_txpre_count = conv_unsigned(63,6) and smod_i = '0') else '0'; s_m13_txshift_en <= '1' when s_txm13_ff0 = '1' and s_txm13_ff1 = '0' else '0'; p_divide_clk: process (clk, reset) begin if reset = '1' then s_rxpre_count <= conv_unsigned(0,6); s_txpre_count <= conv_unsigned(0,6); s_rxm13_ff0 <= '0'; s_rxm13_ff1 <= '0'; s_txm13_ff0 <= '0'; s_txm13_ff1 <= '0'; else if clk'event and clk='1' then s_rxm13_ff1 <= s_rxm13_ff0; s_txm13_ff1 <= s_txm13_ff0; if smod_i = '1' then if s_rxpre_count(3 downto 0) = conv_unsigned(15,4) then s_rxm13_ff0 <= '1'; else s_rxm13_ff0 <= '0'; end if; else if s_rxpre_count(4 downto 0) = conv_unsigned(31,5) then s_rxm13_ff0 <= '1'; else s_rxm13_ff0 <= '0'; end if; end if; if smod_i = '1' then if s_txpre_count(3 downto 0) = conv_unsigned(15,4) then s_txm13_ff0 <= '1'; else s_txm13_ff0 <= '0'; end if; else if s_txpre_count(4 downto 0) = conv_unsigned(31,5) then s_txm13_ff0 <= '1'; else s_txm13_ff0 <= '0'; end if; end if; if trans_i = '1' then s_txpre_count <= conv_unsigned(0,6); else if s_mode=conv_unsigned(0,2) or s_mode=conv_unsigned(2,2) then s_txpre_count <= s_txpre_count + conv_unsigned(1,1); else if s_tf = '1' then s_txpre_count <= s_txpre_count + conv_unsigned(1,1); end if; end if; end if; if s_detect = '1' then s_rxpre_count <= conv_unsigned(0,6); else if s_mode=conv_unsigned(0,2) or s_mode=conv_unsigned(2,2) then s_rxpre_count <= s_rxpre_count + conv_unsigned(1,1); else if s_tf = '1' then s_rxpre_count <= s_rxpre_count + conv_unsigned(1,1); end if; end if; end if; end if; end if; end process p_divide_clk;------------------------------------------------------------------------------- -- This section samples the serial input for data detection, that is a -- 1-to-0 transition at rxd in state "0000". -- In all other states this unit reads the data bits depending on the baud -- rate. In mode0 this section is not active. s_detect <= '1' when s_det_ff0 = '0' and s_det_ff1 = '1' else '0'; s_rxd_val <= '1' when (s_rxd_ff0 = '1' and s_rxd_ff1 = '1') or (s_rxd_ff0 = '1' and s_rxd_ff2 = '1') or (s_rxd_ff1 = '1' and s_rxd_ff2 = '1') else '0'; p_sample_rx: process (clk, reset) begin if reset = '1' then s_rxd_ff0 <= '0'; s_rxd_ff1 <= '0'; s_rxd_ff2 <= '0'; s_det_ff0 <= '0'; s_det_ff1 <= '0'; else if clk'event and clk='1' then if s_recv_state = conv_unsigned(0,4) then -- state "0000" means if s_ren = '1' then -- to listen for a 1 to 0
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -