Skip to content
Snippets Groups Projects
Select Git revision
  • L2SDP-LIFT
  • L2SDP-1113
  • master default protected
  • HPR-158
4 results

ddrctrl_address_counter.vhd

Blame
  • Code owners
    Assign users and groups as approvers for specific file changes. Learn more.
    ddrctrl_address_counter.vhd 3.85 KiB
    -------------------------------------------------------------------------------
    --
    -- Copyright 2022
    -- ASTRON (Netherlands Institute for Radio Astronomy) <http://www.astron.nl/>
    -- P.O.Box 2, 7990 AA Dwingeloo, The Netherlands
    --
    -- Licensed under the Apache License, Version 2.0 (the "License");
    -- you may not use this file except in compliance with the License.
    -- You may obtain a copy of the License at
    --
    --     http://www.apache.org/licenses/LICENSE-2.0
    --
    -- Unless required by applicable law or agreed to in writing, software
    -- distributed under the License is distributed on an "AS IS" BASIS,
    -- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    -- See the License for the specific language governing permissions and
    -- limitations under the License.
    --
    -------------------------------------------------------------------------------
    -- Author: Job van Wee
    -- Purpose: Creates address by counting input valids
    --
    -- Description:
    --  The counter starts on the first valid = '1' clockcylce, the counter stops 
    --  when valid = '0'.
    --
    -- Remark:
    --  Use VHDL coding template from:
    --  https://support.astron.nl/confluence/display/SBe/VHDL+design+patterns+for+RTL+coding
    --  The maximum value of the address is determend by g_tech_ddr.
    
    LIBRARY IEEE, technology_lib, tech_ddr_lib, common_lib, dp_lib;
    USE IEEE.std_logic_1164.ALL;
    USE IEEE.numeric_std.ALL;
    USE technology_lib.technology_pkg.ALL;
    USE tech_ddr_lib.tech_ddr_pkg.ALL;
    USE common_lib.common_pkg.ALL;
    USE common_lib.common_mem_pkg.ALL;
    USE dp_lib.dp_stream_pkg.ALL;
    
    
    ENTITY ddrctrl_address_counter IS
      GENERIC (
        g_tech_ddr        : t_c_tech_ddr;                                                                                             -- type of memory
        g_sim_model       : BOOLEAN                           := TRUE                                                                 -- determens if this is a simulation
      );
      PORT (
        rst               : IN  STD_LOGIC;
        in_sosi           : IN  t_dp_sosi;                                                                                            -- input data
        out_mosi          : OUT t_mem_ctlr_mosi               := c_mem_ctlr_mosi_rst                                                  -- output data
      );
    END ddrctrl_address_counter;
    
    
    ARCHITECTURE rtl OF ddrctrl_address_counter IS
    
      -- constants for readability
      CONSTANT c_data_w   : NATURAL                           := func_tech_ddr_ctlr_data_w( g_tech_ddr );                             -- the with of the input data and output data, 576
      CONSTANT c_adr_w    : NATURAL                           := sel_a_b(g_sim_model, 4, func_tech_ddr_ctlr_address_w( g_tech_ddr )); -- the lengt of the address vector, for simulation this is smaller, otherwise the simulation would take to long, 27
      CONSTANT c_max_adr  : NATURAL                           := 2**(c_adr_w) - 1;                                                    -- the maximal address that is possible within the vector length of the address
    
      -- signal for storing address
      SIGNAL   s_adr      : NATURAL range 0 to 2**(c_adr_w)-1 := 0;                                                                   -- a signal that contains the address
    
    BEGIN
    
      -- The data is directly put through.
      out_mosi.wrdata(c_data_w - 1 DOWNTO 0) <= in_sosi.data(c_data_w - 1 DOWNTO 0);
      out_mosi.wr                            <= in_sosi.valid;
      out_mosi.address(c_adr_w -1 DOWNTO 0)  <= TO_UVEC(s_adr, c_adr_w);
    
      -- Increments the address each time in_sosi.valid = '1', if address = c_max_adr the address is reset to 0.
      p_adr : PROCESS(rst, in_sosi.valid)
      BEGIN
        IF rst = '1' THEN
          s_adr <= 0;
        ELSIF rising_edge(in_sosi.valid) THEN
          IF s_adr = c_max_adr THEN
            s_adr <= 0;
          ELSE
            s_adr <= s_adr + 1;
          END IF;
        END IF;
      END PROCESS;
    
    END rtl;