OpenCores
URL https://opencores.org/ocsvn/System09/System09/trunk

Subversion Repositories System09

[/] [System09/] [rev_86/] [rtl/] [VHDL/] [ACIA_TX.vhd] - Diff between revs 66 and 112

Go to most recent revision | Only display areas with differences | Details | Blame | View Log

Rev 66 Rev 112
--===========================================================================--
--===========================================================================--
--
--
--  S Y N T H E Z I A B L E    ACIA 6850   C O R E
--  S Y N T H E Z I A B L E    ACIA 6850   C O R E
--
--
--  www.OpenCores.Org - January 2007
--  www.OpenCores.Org - January 2007
--  This core adheres to the GNU public license  
--  This core adheres to the GNU public license  
--
--
-- Design units   : 6850 ACIA core for the System68/09
-- Design units   : 6850 ACIA core for the System68/09
--
--
-- File name      : ACIA_TX.vhd
-- File name      : ACIA_TX.vhd
--
--
-- Purpose        : Implements an ACIA device for communication purposes 
-- Purpose        : Implements an ACIA device for communication purposes 
--                  between the FPGA processor and the Host computer through
--                  between the FPGA processor and the Host computer through
--                  a RS-232 communication protocol.
--                  a RS-232 communication protocol.
--                  
--                  
-- Dependencies   : ieee.std_logic_1164
-- Dependencies   : ieee.std_logic_1164
--                  ieee.numeric_std
--                  ieee.numeric_std
--                  ieee.std_logic_unsigned
--                  ieee.std_logic_unsigned
--
--
--===========================================================================--
--===========================================================================--
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
-- Revision list
-- Revision list
-- Version  Author        Date                        Changes
-- Version  Author        Date                        Changes
--
--
-- 0.1      Ovidiu Lupas  15 January 2000    New model
-- 0.1      Ovidiu Lupas  15 January 2000    New model
-- 2.0      Ovidiu Lupas  17 April   2000    unnecessary variable removed
-- 2.0      Ovidiu Lupas  17 April   2000    unnecessary variable removed
--
--
-- 3.0      John Kent      5 January 2003    added 6850 word format control
-- 3.0      John Kent      5 January 2003    added 6850 word format control
-- 3.1      John Kent     12 January 2003    Rearranged state machine code
-- 3.1      John Kent     12 January 2003    Rearranged state machine code
-- 3.2      John Kent     30 March 2003      Revamped State machine
-- 3.2      John Kent     30 March 2003      Revamped State machine
-- 3.3      John Kent     16 January 2004    Major re-write - added baud rate gen
-- 3.3      John Kent     16 January 2004    Major re-write - added baud rate gen
--      4.0      John Kent      3 February 2007   renamed txunit to ACIA_TX
--      4.0      John Kent      3 February 2007   renamed txunit to ACIA_TX
-- 4.1      John Kent      4 February 2007   Cleaned up transmiter
-- 4.1      John Kent      4 February 2007   Cleaned up transmiter
-- 4.2      John Kent     25 Februauy 2007   Modify sensitivity lists and
-- 4.2      John Kent     25 Februauy 2007   Modify sensitivity lists and
--                                           split Tx Baud Clock select
--                                           split Tx Baud Clock select
--                                           and edge detection.
--                                           and edge detection.
--  dilbert57@opencores.org
--  dilbert57@opencores.org
--
--
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
library ieee;
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_unsigned.all;
 
 
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
-- Entity for the ACIA Transmitter
-- Entity for the ACIA Transmitter
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
entity ACIA_TX is
entity ACIA_TX is
  port (
  port (
     Clk    : in  Std_Logic;                    -- CPU Clock signal
     Clk    : in  Std_Logic;                    -- CPU Clock signal
     TxRst  : in  Std_Logic;                    -- Reset input
     TxRst  : in  Std_Logic;                    -- Reset input
     TxWr   : in  Std_Logic;                    -- Load transmit data
     TxWr   : in  Std_Logic;                    -- Load transmit data
     TxDin  : in  Std_Logic_Vector(7 downto 0);  -- Transmit data input.
     TxDin  : in  Std_Logic_Vector(7 downto 0);  -- Transmit data input.
     WdFmt  : in  Std_Logic_Vector(2 downto 0); -- word format
     WdFmt  : in  Std_Logic_Vector(2 downto 0); -- word format
     BdFmt  : in  Std_Logic_Vector(1 downto 0); -- baud format
     BdFmt  : in  Std_Logic_Vector(1 downto 0); -- baud format
     TxClk  : in  Std_Logic;                    -- Enable input
     TxClk  : in  Std_Logic;                    -- Enable input
     TxDat  : out Std_Logic;                    -- RS-232 data bit output
     TxDat  : out Std_Logic;                    -- RS-232 data bit output
     TxEmp  : out Std_Logic );                  -- Tx buffer empty
     TxEmp  : out Std_Logic );                  -- Tx buffer empty
end ACIA_TX; --================== End of entity ==============================--
end ACIA_TX; --================== End of entity ==============================--
 
 
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
-- Architecture for  ACIA_TX
-- Architecture for  ACIA_TX
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
 
 
architecture rtl of ACIA_TX is
architecture rtl of ACIA_TX is
 
 
  type TxStateType is ( Tx1Stop_State, TxStart_State,
  type TxStateType is ( Tx1Stop_State, TxStart_State,
                        TxData_State, TxParity_State, Tx2Stop_State );
                        TxData_State, TxParity_State, Tx2Stop_State );
 
 
  -----------------------------------------------------------------------------
  -----------------------------------------------------------------------------
  -- Signals
  -- Signals
  -----------------------------------------------------------------------------
  -----------------------------------------------------------------------------
 
 
  signal TxClkDel   : Std_Logic := '0';             -- Delayed Tx Input Clock
  signal TxClkDel   : Std_Logic := '0';             -- Delayed Tx Input Clock
  signal TxClkEdge  : Std_Logic := '0';             -- Tx Input Clock Edge pulse
  signal TxClkEdge  : Std_Logic := '0';             -- Tx Input Clock Edge pulse
  signal TxClkCnt   : Std_Logic_Vector(5 downto 0) := (others => '0'); -- Tx Baud Clock Counter
  signal TxClkCnt   : Std_Logic_Vector(5 downto 0) := (others => '0'); -- Tx Baud Clock Counter
  signal TxBdDel    : Std_Logic := '0';             -- Delayed Tx Baud Clock
  signal TxBdDel    : Std_Logic := '0';             -- Delayed Tx Baud Clock
  signal TxBdEdge   : Std_Logic := '0';             -- Tx Baud Clock Edge pulse
  signal TxBdEdge   : Std_Logic := '0';             -- Tx Baud Clock Edge pulse
  signal TxBdClk    : Std_Logic := '0';             -- Tx Baud Clock
  signal TxBdClk    : Std_Logic := '0';             -- Tx Baud Clock
  signal TxShiftReg : Std_Logic_Vector(7 downto 0) := (others => '0'); -- Transmit shift register
  signal TxShiftReg : Std_Logic_Vector(7 downto 0) := (others => '0'); -- Transmit shift register
  signal TxParity   : Std_logic := '0';             -- Parity Bit
  signal TxParity   : Std_logic := '0';             -- Parity Bit
  signal TxBitCount : Std_Logic_Vector(2 downto 0) := (others => '0'); -- Data Bit Counter
  signal TxBitCount : Std_Logic_Vector(2 downto 0) := (others => '0'); -- Data Bit Counter
  signal TxReq      : Std_Logic := '0';             -- Request Transmit
  signal TxReq      : Std_Logic := '0';             -- Request Transmit
  signal TxAck      : Std_Logic := '0';             -- Transmit Commenced
  signal TxAck      : Std_Logic := '0';             -- Transmit Commenced
  signal TxState    : TxStateType;                                               -- Transmitter state
  signal TxState    : TxStateType;                                               -- Transmitter state
 
 
begin
begin
 
 
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  -- Transmit Clock Edge Detection
  -- Transmit Clock Edge Detection
  -- A falling edge will produce a one clock cycle pulse
  -- A falling edge will produce a one clock cycle pulse
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
 
 
--  acia_tx_clock_edge : process(Clk, TxRst, TxClk, TxClkDel )
--  acia_tx_clock_edge : process(Clk, TxRst, TxClk, TxClkDel )
  acia_tx_clock_edge : process( TxRst, Clk )
  acia_tx_clock_edge : process( TxRst, Clk )
  begin
  begin
    if TxRst = '1' then
    if TxRst = '1' then
           TxClkDel  <= '0';
           TxClkDel  <= '0';
                TxClkEdge <= '0';
                TxClkEdge <= '0';
         elsif Clk'event and Clk = '0' then
         elsif Clk'event and Clk = '0' then
           TxClkDel  <= TxClk;
           TxClkDel  <= TxClk;
                TxClkEdge <= TxClkDel and (not TxClk);
                TxClkEdge <= TxClkDel and (not TxClk);
         end if;
         end if;
  end process;
  end process;
 
 
 
 
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  -- Transmit Clock Divider
  -- Transmit Clock Divider
  -- Advance the count only on an input clock pulse
  -- Advance the count only on an input clock pulse
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
 
 
--  acia_tx_clock_divide : process( Clk, TxRst, TxClkEdge, TxClkCnt )
--  acia_tx_clock_divide : process( Clk, TxRst, TxClkEdge, TxClkCnt )
  acia_tx_clock_divide : process( TxRst, Clk )
  acia_tx_clock_divide : process( TxRst, Clk )
  begin
  begin
    if TxRst = '1' then
    if TxRst = '1' then
           TxClkCnt <= "000000";
           TxClkCnt <= "000000";
         elsif Clk'event and Clk = '0' then
         elsif Clk'event and Clk = '0' then
           if TxClkEdge = '1' then
           if TxClkEdge = '1' then
                  TxClkCnt <= TxClkCnt + "000001";
                  TxClkCnt <= TxClkCnt + "000001";
      end if; -- TxClkEdge
      end if; -- TxClkEdge
         end if;        -- reset / clk
         end if;        -- reset / clk
  end process;
  end process;
 
 
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  -- Transmit Baud Clock Selector
  -- Transmit Baud Clock Selector
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  acia_tx_baud_clock_select : process( BdFmt, TxClk, TxClkCnt )
  acia_tx_baud_clock_select : process( BdFmt, TxClk, TxClkCnt )
  begin
  begin
  -- BdFmt
  -- BdFmt
  -- 0 0     - Baud Clk divide by 1
  -- 0 0     - Baud Clk divide by 1
  -- 0 1     - Baud Clk divide by 16
  -- 0 1     - Baud Clk divide by 16
  -- 1 0     - Baud Clk divide by 64
  -- 1 0     - Baud Clk divide by 64
  -- 1 1     - reset
  -- 1 1     - reset
    case BdFmt is
    case BdFmt is
         when "00" =>     -- Div by 1
         when "00" =>     -- Div by 1
           TxBdClk <= TxClk;
           TxBdClk <= TxClk;
         when "01" =>     -- Div by 16
         when "01" =>     -- Div by 16
           TxBdClk <= TxClkCnt(3);
           TxBdClk <= TxClkCnt(3);
         when "10" =>     -- Div by 64
         when "10" =>     -- Div by 64
           TxBdClk <= TxClkCnt(5);
           TxBdClk <= TxClkCnt(5);
         when others =>  -- reset
         when others =>  -- reset
           TxBdClk <= '0';
           TxBdClk <= '0';
    end case;
    end case;
  end process;
  end process;
 
 
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  -- Transmit Baud Clock Edge Detector
  -- Transmit Baud Clock Edge Detector
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  --
  --
  -- Generate one clock pulse strobe on falling edge of Tx Baud Clock
  -- Generate one clock pulse strobe on falling edge of Tx Baud Clock
  --
  --
--  acia_tx_baud_clock_edge : process(Clk, TxRst, TxBdClk, TxBdDel )
--  acia_tx_baud_clock_edge : process(Clk, TxRst, TxBdClk, TxBdDel )
  acia_tx_baud_clock_edge : process( TxRst, Clk )
  acia_tx_baud_clock_edge : process( TxRst, Clk )
  begin
  begin
    if TxRst = '1' then
    if TxRst = '1' then
           TxBdDel  <= '0';
           TxBdDel  <= '0';
                TxBdEdge <= '0';
                TxBdEdge <= '0';
         elsif Clk'event and Clk = '0' then
         elsif Clk'event and Clk = '0' then
           TxBdDel  <= TxBdClk;
           TxBdDel  <= TxBdClk;
                TxBdEdge <= (not TxBdClk) and TxBdDel;
                TxBdEdge <= (not TxBdClk) and TxBdDel;
         end if;
         end if;
  end process;
  end process;
 
 
 
 
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
  -- Transmitter activation process
  -- Transmitter activation process
  ---------------------------------------------------------------------
  ---------------------------------------------------------------------
--  acia_tx_write : process(Clk, TxRst, TxWr, TxReq, TxAck )
--  acia_tx_write : process(Clk, TxRst, TxWr, TxReq, TxAck )
  acia_tx_write : process( TxRst, Clk )
  acia_tx_write : process( TxRst, Clk )
  begin
  begin
     if TxRst = '1' then
     if TxRst = '1' then
       TxReq <= '0';
       TxReq <= '0';
       TxEmp <= '1';
       TxEmp <= '1';
     elsif Clk'event and Clk = '0' then
     elsif Clk'event and Clk = '0' then
                 if TxWr = '1' then
                 if TxWr = '1' then
         -- Write requests transmit
         -- Write requests transmit
                        -- and clears the Empty Flag 
                        -- and clears the Empty Flag 
                        TxReq <= '1';
                        TxReq <= '1';
              TxEmp <= '0';
              TxEmp <= '0';
            else
            else
         if (TxReq = '1') and (TxAck = '1') then
         if (TxReq = '1') and (TxAck = '1') then
                          -- Once the transmitter is started 
                          -- Once the transmitter is started 
                          -- We can clear request.
                          -- We can clear request.
           TxReq <= '0';
           TxReq <= '0';
                   elsif (TxReq = '0') and (TxAck = '0') then
                   elsif (TxReq = '0') and (TxAck = '0') then
                          -- When the transmitter is finished
                          -- When the transmitter is finished
                          -- We can flag transmit empty
                          -- We can flag transmit empty
                          TxEmp <= '1';
                          TxEmp <= '1';
                   end if;
                   end if;
                end if;
                end if;
    end if; -- clk / reset
    end if; -- clk / reset
  end process;
  end process;
 
 
  -----------------------------------------------------------------------------
  -----------------------------------------------------------------------------
  -- Implements the Tx unit
  -- Implements the Tx unit
  -----------------------------------------------------------------------------
  -----------------------------------------------------------------------------
  -- WdFmt - Bits[4..2]
  -- WdFmt - Bits[4..2]
  -- 0 0 0   - 7 data, even parity, 2 stop
  -- 0 0 0   - 7 data, even parity, 2 stop
  -- 0 0 1   - 7 data, odd  parity, 2 stop
  -- 0 0 1   - 7 data, odd  parity, 2 stop
  -- 0 1 0   - 7 data, even parity, 1 stop
  -- 0 1 0   - 7 data, even parity, 1 stop
  -- 0 1 1   - 7 data, odd  parity, 1 stop
  -- 0 1 1   - 7 data, odd  parity, 1 stop
  -- 1 0 0   - 8 data, no   parity, 2 stop
  -- 1 0 0   - 8 data, no   parity, 2 stop
  -- 1 0 1   - 8 data, no   parity, 1 stop
  -- 1 0 1   - 8 data, no   parity, 1 stop
  -- 1 1 0   - 8 data, even parity, 1 stop
  -- 1 1 0   - 8 data, even parity, 1 stop
  -- 1 1 1   - 8 data, odd  parity, 1 stop
  -- 1 1 1   - 8 data, odd  parity, 1 stop
--  acia_tx_transmit :  process(TxRst, Clk, TxState, TxDin, WdFmt,  
--  acia_tx_transmit :  process(TxRst, Clk, TxState, TxDin, WdFmt,  
--                              TxShiftReg, TxBdEdge, TxParity, TxBitCount,
--                              TxShiftReg, TxBdEdge, TxParity, TxBitCount,
--                                   TxReq, TxAck )
--                                   TxReq, TxAck )
  acia_tx_transmit :  process( TxRst, Clk )
  acia_tx_transmit :  process( TxRst, Clk )
  begin
  begin
         if TxRst = '1' then
         if TxRst = '1' then
          TxDat      <= '1';
          TxDat      <= '1';
               TxShiftReg <= "00000000";
               TxShiftReg <= "00000000";
                    TxParity   <= '0';
                    TxParity   <= '0';
                    TxBitCount <= "000";
                    TxBitCount <= "000";
          TxAck      <= '0';
          TxAck      <= '0';
                    TxState    <= Tx1Stop_State;
                    TxState    <= Tx1Stop_State;
    elsif Clk'event and Clk = '0' then
    elsif Clk'event and Clk = '0' then
      if TxBdEdge = '1' then
      if TxBdEdge = '1' then
        case TxState is
        case TxState is
        when Tx1Stop_State =>           -- Last Stop bit state
        when Tx1Stop_State =>           -- Last Stop bit state
          TxDat <= '1';
          TxDat <= '1';
          TxAck <= '0';                                 -- Transmitter halted
          TxAck <= '0';                                 -- Transmitter halted
                    if TxReq = '1' then
                    if TxReq = '1' then
             TxState <= TxStart_State;
             TxState <= TxStart_State;
                    end if;
                    end if;
 
 
        when TxStart_State =>
        when TxStart_State =>
          TxDat      <= '0';            -- Start bit
          TxDat      <= '0';            -- Start bit
               TxShiftReg <= TxDin;                 -- Load Shift reg with Tx Data
               TxShiftReg <= TxDin;                 -- Load Shift reg with Tx Data
                    TxParity   <= '0';
                    TxParity   <= '0';
                    if WdFmt(2) = '0' then
                    if WdFmt(2) = '0' then
                      TxBitCount <= "110";       -- 7 data + parity
                      TxBitCount <= "110";       -- 7 data + parity
               else
               else
            TxBitCount <= "111";       -- 8 data
            TxBitCount <= "111";       -- 8 data
               end if;
               end if;
          TxAck      <= '1';                             -- Flag transmit started
          TxAck      <= '1';                             -- Flag transmit started
          TxState    <= TxData_State;
          TxState    <= TxData_State;
 
 
        when TxData_State =>
        when TxData_State =>
          TxDat       <= TxShiftReg(0);
          TxDat       <= TxShiftReg(0);
          TxShiftReg  <= '1' & TxShiftReg(7 downto 1);
          TxShiftReg  <= '1' & TxShiftReg(7 downto 1);
          TxParity    <= TxParity xor TxShiftReg(0);
          TxParity    <= TxParity xor TxShiftReg(0);
                    TxBitCount  <= TxBitCount - "001";
                    TxBitCount  <= TxBitCount - "001";
                    if TxBitCount = "000" then
                    if TxBitCount = "000" then
                 if (WdFmt(2) = '1') and (WdFmt(1) = '0') then
                 if (WdFmt(2) = '1') and (WdFmt(1) = '0') then
                             if WdFmt(0) = '0' then          -- 8 data bits
                             if WdFmt(0) = '0' then          -- 8 data bits
                TxState <= Tx2Stop_State;     -- 2 stops
                TxState <= Tx2Stop_State;     -- 2 stops
                             else
                             else
                                    TxState <= Tx1Stop_State;     -- 1 stop
                                    TxState <= Tx1Stop_State;     -- 1 stop
                        end if;
                        end if;
                      else
                      else
                             TxState <= TxParity_State;      -- parity
                             TxState <= TxParity_State;      -- parity
                      end if;
                      end if;
                    end if;
                    end if;
 
 
        when TxParity_State =>                -- 7/8 data + parity bit
        when TxParity_State =>                -- 7/8 data + parity bit
               if WdFmt(0) = '0' then
               if WdFmt(0) = '0' then
                            TxDat <= not( TxParity );        -- even parity
                            TxDat <= not( TxParity );        -- even parity
                    else
                    else
                            TxDat <= TxParity;               -- odd parity
                            TxDat <= TxParity;               -- odd parity
               end if;
               end if;
                    if WdFmt(1) = '0' then
                    if WdFmt(1) = '0' then
                           TxState <= Tx2Stop_State;         -- 2 stops
                           TxState <= Tx2Stop_State;         -- 2 stops
                    else
                    else
                           TxState <= Tx1Stop_State;         -- 1 stop
                           TxState <= Tx1Stop_State;         -- 1 stop
                    end if;
                    end if;
 
 
        when Tx2Stop_State =>                 -- first of two stop bits
        when Tx2Stop_State =>                 -- first of two stop bits
          TxDat   <= '1';
          TxDat   <= '1';
                    TxState <= Tx1Stop_State;
                    TxState <= Tx1Stop_State;
 
 
        when others =>  -- Undefined
        when others =>  -- Undefined
          TxDat   <= '1';
          TxDat   <= '1';
          TxState <= Tx1Stop_State;
          TxState <= Tx1Stop_State;
 
 
        end case; -- TxState
        end case; -- TxState
 
 
                end if; -- TxBdEdge
                end if; -- TxBdEdge
         end if;         -- clk / reset
         end if;         -- clk / reset
 
 
  end process;
  end process;
 
 
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.