library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

LIBRARY altera_mf;
USE altera_mf.altera_mf_components.all;

entity true_dual_port_ram is
        generic (
            ADDR_WIDTH      : natural := 8;
            DATA_WIDTH      : natural := 12;
            MEMORY_DEPTH    : natural := 256
        );
        port (
            clk         : in std_logic;
            addr_a      : in std_logic_vector(ADDR_WIDTH-1 downto 0);
            addr_b      : in std_logic_vector(ADDR_WIDTH-1 downto 0);
            wen_a       : in std_logic;
            wen_b       : in std_logic;
            ren_a       : in std_logic;
            ren_b       : in std_logic;
            wr_data_a   : in std_logic_vector(DATA_WIDTH-1 downto 0);
            wr_data_b   : in std_logic_vector(DATA_WIDTH-1 downto 0);
            rd_data_a   : out std_logic_vector(DATA_WIDTH-1 downto 0);
            rd_data_b   : out std_logic_vector(DATA_WIDTH-1 downto 0)
        );
end entity;

architecture arch of true_dual_port_ram is
    
begin

    altsyncram_component : altsyncram
        generic map (
            address_reg_b                       => "CLOCK0",
            clock_enable_input_a                => "BYPASS",
            clock_enable_input_b                => "BYPASS",
            clock_enable_output_a               => "BYPASS",
            clock_enable_output_b               => "BYPASS",
            indata_reg_b                        => "CLOCK0",
            intended_device_family              => "Cyclone V",
            lpm_type                            => "altsyncram",
            numwords_a                          => MEMORY_DEPTH,
            numwords_b                          => MEMORY_DEPTH,
            operation_mode                      => "BIDIR_DUAL_PORT",
            outdata_aclr_a                      => "NONE",
            outdata_aclr_b                      => "NONE",
            outdata_reg_a                       => "UNREGISTERED",
            outdata_reg_b                       => "UNREGISTERED",
            power_up_uninitialized              => "FALSE",
            read_during_write_mode_mixed_ports  => "OLD_DATA",
            read_during_write_mode_port_a       => "NEW_DATA_NO_NBE_READ",
            read_during_write_mode_port_b       => "NEW_DATA_NO_NBE_READ",
            widthad_a                           => ADDR_WIDTH,
            widthad_b                           => ADDR_WIDTH,
            width_a                             => DATA_WIDTH,
            width_b                             => DATA_WIDTH,
            width_byteena_a                     => 1,
            width_byteena_b                     => 1,
            wrcontrol_wraddress_reg_b           => "CLOCK0"
        )
        port map (
            address_a   => addr_a,
            address_b   => addr_b,
            clock0      => clk,
            data_a      => wr_data_a,
            data_b      => wr_data_b,
            rden_a      => ren_a,
            rden_b      => ren_b,
            wren_a      => wen_a,
            wren_b      => wen_b,
            q_a         => rd_data_a,
            q_b         => rd_data_b
        );

end architecture;
