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

Subversion Repositories spi_master_slave

[/] [spi_master_slave/] [trunk/] [syn/] [spi_master.vhd] - Diff between revs 5 and 6

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 5 Rev 6
Line 58... Line 58...
--                      
--                      
--
--
--      PARALLEL READ INTERFACE
--      PARALLEL READ INTERFACE
--      =======================
--      =======================
--      An internal buffer is used to copy the internal shift register data to drive the 'do_o' port. When a complete word is received,
--      An internal buffer is used to copy the internal shift register data to drive the 'do_o' port. When a complete word is received,
--      the core shift register is transferred to the buffer, at the rising edge of the spi clock, 'spi_2x_clk_i'.
--      the core shift register is transferred to the buffer, at the rising edge of the spi clock, 'spi_clk'.
--      The signal 'do_valid_o' is set one 'spi_2x_clk_i' clock after, to directly drive a synchronous memory or fifo write enable.
--      The signal 'do_valid_o' is set one 'spi_clk' clock after, to directly drive a synchronous memory or fifo write enable.
--      'do_valid_o' is synchronous to the parallel interface clock, and changes only on rising edges of 'pclk_i'.
--      'do_valid_o' is synchronous to the parallel interface clock, and changes only on rising edges of 'pclk_i'.
--      When the interface is idle, data at the 'do_o' port holds the last word received.
--      When the interface is idle, data at the 'do_o' port holds the last word received.
--
--
--      PARALLEL READ SEQUENCE
--      PARALLEL READ SEQUENCE
--      ======================
--      ======================
--                      ______        ______        ______        ______   
--                      ______        ______        ______        ______   
--      spi_2x_clk_i     bit1 \______/ bitN \______/bitN-1\______/bitN-2\__...  -- spi 2x base clock
--      spi_clk          bit1 \______/ bitN \______/bitN-1\______/bitN-2\__...  -- spi 2x base clock
--                      _    __    __    __    __    __    __    __    __  
--                      _    __    __    __    __    __    __    __    __  
--      pclk_i           \__/  \__/  \__/  \__/  \__/  \__/  \__/  \__/  \_...  -- parallel interface clock (may be async to sclk_i)
--      pclk_i           \__/  \__/  \__/  \__/  \__/  \__/  \__/  \__/  \_...  -- parallel interface clock (may be async to sclk_i)
--                      _____________ _____________________________________...  -- 1) rx data is transferred to 'do_buffer_reg'
--                      _____________ _____________________________________...  -- 1) rx data is transferred to 'do_buffer_reg'
--      do_o            ___old_data__X__________new_data___________________...  --    after last rx bit, at rising 'spi_2x_clk_i'.
--      do_o            ___old_data__X__________new_data___________________...  --    after last rx bit, at rising 'spi_clk'.
--                                                   ____________               
--                                                   ____________               
--      do_valid_o      ____________________________/            \_________...  -- 2) 'do_valid_o' strobed for 2 'pclk_i' cycles
--      do_valid_o      ____________________________/            \_________...  -- 2) 'do_valid_o' strobed for 2 'pclk_i' cycles
--                                                                              --    on the 3rd 'pclk_i' rising edge.
--                                                                              --    on the 3rd 'pclk_i' rising edge.
--
--
--
--
Line 167... Line 167...
        spi_ssel_o : out std_logic;                                     -- spi bus slave select line
        spi_ssel_o : out std_logic;                                     -- spi bus slave select line
        spi_sck_o : out std_logic;                                      -- spi bus sck
        spi_sck_o : out std_logic;                                      -- spi bus sck
        spi_mosi_o : out std_logic;                                     -- spi bus mosi output
        spi_mosi_o : out std_logic;                                     -- spi bus mosi output
        spi_miso_i : in std_logic := 'X';                               -- spi bus spi_miso_i input
        spi_miso_i : in std_logic := 'X';                               -- spi bus spi_miso_i input
        di_req_o : out std_logic;                                       -- preload lookahead data request line
        di_req_o : out std_logic;                                       -- preload lookahead data request line
        di_i : in  std_logic_vector (N-1 downto 0) := (others => 'X');  -- parallel data in (clocked on rising spi_2x_clk_i after last bit)
        di_i : in  std_logic_vector (N-1 downto 0) := (others => 'X');  -- parallel data in (clocked on rising spi_clk after last bit)
        wren_i : in std_logic := 'X';                                   -- user data write enable, starts transmission when interface is idle
        wren_i : in std_logic := 'X';                                   -- user data write enable, starts transmission when interface is idle
        do_valid_o : out std_logic;                                     -- do_o data valid signal, valid during one spi_2x_clk_i rising edge.
        do_valid_o : out std_logic;                                     -- do_o data valid signal, valid during one spi_clk rising edge.
        do_o : out  std_logic_vector (N-1 downto 0);                    -- parallel output (clocked on rising spi_2x_clk_i after last bit)
        do_o : out  std_logic_vector (N-1 downto 0);                    -- parallel output (clocked on rising spi_clk after last bit)
        --- debug ports: can be removed for the application circuit ---
        --- debug ports: can be removed for the application circuit ---
        do_transfer_o : out std_logic;                                  -- debug: internal transfer driver
        do_transfer_o : out std_logic;                                  -- debug: internal transfer driver
        wren_o : out std_logic;                                         -- debug: internal state of the wren_i pulse stretcher
        wren_o : out std_logic;                                         -- debug: internal state of the wren_i pulse stretcher
        wren_ack_o : out std_logic;                                     -- debug: wren ack from state machine
        wren_ack_o : out std_logic;                                     -- debug: wren ack from state machine
        rx_bit_reg_o : out std_logic;                                   -- debug: internal rx bit
        rx_bit_reg_o : out std_logic;                                   -- debug: internal rx bit
Line 187... Line 187...
    );
    );
end spi_master;
end spi_master;
 
 
--================================================================================================================
--================================================================================================================
-- this architecture is a pipelined register-transfer description.
-- this architecture is a pipelined register-transfer description.
-- all signals are clocked at the rising edge of the system clock 'spi_2x_clk_i'.
-- all signals are clocked at the rising edge of the system clock 'sclk_i'.
--================================================================================================================
--================================================================================================================
architecture rtl of spi_master is
architecture rtl of spi_master is
    -- core clocks, generated from 'spi_2x_clk_i': initialized to differential values
    -- core clocks, generated from 'sclk_i': initialized to differential values
    signal core_clk : std_logic := '0';     -- continuous core clock, positive logic
    signal core_clk : std_logic := '0';     -- continuous core clock, positive logic
    signal core_n_clk : std_logic := '1';   -- continuous core clock, negative logic
    signal core_n_clk : std_logic := '1';   -- continuous core clock, negative logic
    signal core_ce : std_logic := '0';      -- core clock enable, positive logic
    signal core_ce : std_logic := '0';      -- core clock enable, positive logic
    signal core_n_ce : std_logic := '1';    -- core clock enable, negative logic
    signal core_n_ce : std_logic := '1';    -- core clock enable, negative logic
    -- spi bus clock, generated from the CPOL selected core clock polarity
    -- spi bus clock, generated from the CPOL selected core clock polarity
Line 293... Line 293...
    -- The clock enable phase is selected for serial input sampling, fsm clocking, and spi SCK output, 
    -- The clock enable phase is selected for serial input sampling, fsm clocking, and spi SCK output, 
    -- based on the configuration of CPOL and CPHA.
    -- based on the configuration of CPOL and CPHA.
    -- Each phase is selected so that all the registers can be clocked with a rising edge on all SPI
    -- Each phase is selected so that all the registers can be clocked with a rising edge on all SPI
    -- modes, by a single high-speed global clock, preserving clock resources.
    -- modes, by a single high-speed global clock, preserving clock resources.
    -----------------------------------------------------------------------------------------------
    -----------------------------------------------------------------------------------------------
    -- generate the core clock enables from the serial high-speed input clock
    -- generate the 2x spi base clock enable from the serial high-speed input clock
    spi_2x_ce_gen_proc: process (sclk_i) is
    spi_2x_ce_gen_proc: process (sclk_i) is
        variable clk_cnt : integer range SPI_2X_CLK_DIV-1 downto 0 := 0;
        variable clk_cnt : integer range SPI_2X_CLK_DIV-1 downto 0 := 0;
    begin
    begin
        if sclk_i'event and sclk_i = '1' then
        if sclk_i'event and sclk_i = '1' then
            if clk_cnt = SPI_2X_CLK_DIV-1 then
            if clk_cnt = SPI_2X_CLK_DIV-1 then
Line 308... Line 308...
                clk_cnt := clk_cnt + 1;
                clk_cnt := clk_cnt + 1;
            end if;
            end if;
        end if;
        end if;
    end process spi_2x_ce_gen_proc;
    end process spi_2x_ce_gen_proc;
    -----------------------------------------------------------------------------------------------
    -----------------------------------------------------------------------------------------------
    -- generate the core antiphase clocks and clock enables.
    -- generate the core antiphase clocks and clock enables from the 2x base CE.
    core_clock_gen_proc : process (sclk_i) is
    core_clock_gen_proc : process (sclk_i) is
    begin
    begin
        if sclk_i'event and sclk_i = '1' then
        if sclk_i'event and sclk_i = '1' then
            if spi_2x_ce = '1' then
            if spi_2x_ce = '1' then
                -- generate the 2 antiphase core clocks
                -- generate the 2 antiphase core clocks
Line 351... Line 351...
        if CPHA = '1' generate
        if CPHA = '1' generate
        begin
        begin
            samp_ce <= core_n_ce;
            samp_ce <= core_n_ce;
        end generate;
        end generate;
    -----------------------------------------------------------------------------------------------
    -----------------------------------------------------------------------------------------------
    -- FSM clock generation: generate 'fsm_ce' from core_ce or core_n_ce depending on CPHA
    -- FSM clock enable generation: generate 'fsm_ce' from core_ce or core_n_ce depending on CPHA
    fsm_ce_cpha_0_proc :
    fsm_ce_cpha_0_proc :
        if CPHA = '0' generate
        if CPHA = '0' generate
        begin
        begin
            fsm_ce <= core_n_ce;            -- for CPHA=0, latch registers at rising edge of negative core clock enable
            fsm_ce <= core_n_ce;            -- for CPHA=0, latch registers at rising edge of negative core clock enable
        end generate;
        end generate;

powered by: WebSVN 2.1.0

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