2017-02-28 32 views
0

2つの3ビットアドレスレジスタと2つの3to8デコーダを使用する3ビットレジスタのクロスバーを使用して64バイトのRAMを作成します。 VHDLコードは次のとおりです。複数出力の8ビットレジスタを同じ出力(VHDL)に接続

library ieee; 
use ieee.std_logic_1164.all; 

entity ram88 is 
    port(a : in std_logic_vector (2 downto 0); 
     s0: in std_logic; 
     s1: in std_logic; 
     s: in std_logic; 
     e: in std_logic; 
     io_in: in std_logic_vector (7 downto 0); 
     io_out:out std_logic_vector (7 downto 0)); 

end ram88; 

architecture behavior of ram88 is 

    component reg3 is 
    port(a : in std_logic_vector (2 downto 0); 
      ss,e : in std_logic; --st and enable 
      b : out std_logic_vector (2 downto 0)); 
    end component; 

    component reg8 is 
    port(a : in std_logic_vector (7 downto 0); 
      ss,e : in std_logic; --st and enable 
      b : out std_logic_vector (7 downto 0)); 
    end component; 

    component decod8 is 
    port(a : in std_logic_vector (2 downto 0); 
      b : out std_logic_vector (7 downto 0)); 
    end component; 

    signal e1 : std_logic := '1'; 
    signal l0, l1 : std_logic_vector (2 downto 0); 
    signal ll0, ll1 : std_logic_vector (7 downto 0); 
    type arr2d is array (7 downto 0, 7 downto 0) of std_logic; 
    signal andij, fin_s, fin_e : arr2d; 

begin 

    e1 <= '1'; 

    reg0: reg3 port map (a => a, ss => s0, e => e1, b => l0); 
    reg1: reg3 port map (a => a, ss => s1, e => e1, b => l1); 
    decod0: decod8 port map(a => l0, b => ll0); 
    decod1: decod8 port map(a => l1, b => ll1); 

    mem_blks_ii: 
    for ii in 0 to 7 generate 
    mem_blks_jj: 
    for jj in 0 to 7 generate 
     andij(ii,jj) <= ll0(ii) and ll1(jj); 
     fin_s(ii,jj) <= andij(ii,jj) and s; 
     fin_e(ii,jj) <= andij(ii,jj) and e; 
     regij: reg8 port map(a=> io_in, ss=> fin_s(ii,jj), e => fin_e(ii,jj), b => io_out); 
    end generate mem_blks_jj; 
    end generate mem_blks_ii; 


end behavior; 

次に、シミュレーション用に次のテストユニットを使用します。メモリアドレス000x000に値00000001を設定します。終わりに、それはイネーブル信号を設定することにより、値を取得します。

library ieee; 
use ieee.std_logic_1164.all; 

entity ram88_bench is 

end ram88_bench; 

architecture behavior of ram88_bench is 

    component ram88 
    port(a : in std_logic_vector (2 downto 0); 
     s0: in std_logic; 
     s1: in std_logic; 
     s: in std_logic; 
     e: in std_logic; 
     io_in: in std_logic_vector (7 downto 0); 
     io_out:out std_logic_vector (7 downto 0)); 
    end component; 

    signal abar : std_logic_vector (2 downto 0); 
    signal s0bar, s1bar, sbar, ebar: std_logic; 
    signal io_in_bar, io_out_bar: std_logic_vector (7 downto 0); 

begin 

    ram0: ram88 port map(a=>abar, s0=> s0bar, s1=> s1bar 
         , s=> sbar, e=> ebar 
         , io_in => io_in_bar, io_out=> io_out_bar); 

    process 
    begin 

    -- set (0,1) for access point in memory 
    abar <= "000"; 
    s0bar <= '1'; 
    s1bar <= '0'; 
    wait for 2 fs; 
    s0bar <= '0'; 

    abar <= "000"; 
    s1bar <= '1'; 
    wait for 2 fs; 
    s1bar <= '0'; 

    -- store the value ... 
    ebar <= '1'; 
    sbar <= '1'; 
    io_in_bar <= "00000001"; 
    wait for 2 fs; 
    sbar <= '0'; 

    ---- temporary clear the value before retrieval 
    --sbar <= '0'; 
    --ebar <= '0'; 
    ---- io_in_bar <= "00000000";  
    --wait for 2 fs; 

    --retrieve the value ???? 
    ebar <= '1'; 
    sbar <= '0'; 
    wait for 6 fs; 

    wait; 

    end process; 

end behavior; 

問題がio_out_barの値はシミュレーションの最後に00000001予想未知数の「0X」の代わりに強制されたということです!私は理由を理解できませんでしたが、8ビットのRAMレジスタがすべて同じ出力に接続されているため、どちらを実際に検索する必要があるのか​​判断できませんでした。この問題を解決するにはどうすればよいですか?

+2

マルチプレクサを使用して1つを選択します。代わりに、トライステートロジックを使用することですが、それは私が知っている最新のFPGAでは有効ではありません。 –

答えて

3

質問はMinimal, Complete and Verifiable exampleではありません。解決策を実証するのに役立ちます。インスタンス化のためのいくつかの迅速かつ汚いエンティティ:

library ieee; 
use ieee.std_logic_1164.all; 

entity reg3 is 
    port (
     a:  in std_logic_vector (2 downto 0); 
     ss,e: in std_logic; 
     b:  out std_logic_vector (2 downto 0) 
    ); 
end entity; 

architecture foo of reg3 is 
begin 
    b <= a when ss = '1' and e = '1'; 
end architecture; 

library ieee; 
use ieee.std_logic_1164.all; 

entity decod8 is 
    port (
     a:  in std_logic_vector (2 downto 0); 
     b:  out std_logic_vector (7 downto 0) 
    ); 
end entity; 

architecture foo of decod8 is 
    use ieee.numeric_std.all; 
begin 
    process (a) 
     variable idx: natural range 0 to 7; 
    begin 
     idx := to_integer(unsigned(a)); 
     b <= (others => '0'); 
     b(idx) <= '1'; 
    end process; 
end architecture; 

library ieee; 
use ieee.std_logic_1164.all; 

entity reg8 is 
    port (
     a:  in std_logic_vector (7 downto 0); 
     ss,e: in std_logic; 
     b:  out std_logic_vector (7 downto 0) 
    ); 
end entity; 

architecture foo of reg8 is 
begin 
    b <= a when ss = '1' and e = '1'; 
end architecture;  

...私はすべての8ビットのRAMレジスタは同じ出力に接続されているので、我々が取得する必要があり、実際の値である1を決定することはできないと思います。この問題を解決するにはどうすればよいですか?あなたが正しく推測

、すべて 8ビット・レジスタは、io_outを駆動します。

ここでの考え方は、RAMに供給されるインデックスに従って一度に1つだけを選択することです。この例では、l0l1のラッチと同じ書き込みアドレスを使用し、出力のために64個の8ビットレジスタのうちの1つを選択します。

それは行動的にここに純粋に行われていますが、インスタンス化されたマルチプレクサ(セレクタ)で行うことができます。

architecture behavior of ram88 is 

    component reg3 is 
    port(a : in std_logic_vector (2 downto 0); 
      ss,e : in std_logic; --st and enable 
      b : out std_logic_vector (2 downto 0)); 
    end component; 

    component reg8 is 
    port(a : in std_logic_vector (7 downto 0); 
      ss,e : in std_logic; --st and enable 
      b : out std_logic_vector (7 downto 0)); 
    end component; 

    component decod8 is 
    port(a : in std_logic_vector (2 downto 0); 
      b : out std_logic_vector (7 downto 0)); 
    end component; 

    signal e1 : std_logic := '1'; 
    signal l0, l1 : std_logic_vector (2 downto 0); 
    signal ll0, ll1 : std_logic_vector (7 downto 0); 
    type arr2d is array (7 downto 0, 7 downto 0) of std_logic; 
    signal andij, fin_s, fin_e : arr2d; 
    type mux is array (7 downto 0, 7 downto 0) of -- ADDED 
       std_logic_vector (7 downto 0); 
    signal mux88: mux;        -- ADDED 
    signal idxii, idxjj: natural range 0 to 7;  -- ADDED 
    use ieee.numeric_std.all;      -- ADDED 

begin 

    e1 <= '1'; 

    idxii <= to_integer(unsigned(l0));    -- ADDED 
    idxjj <= to_integer(unsigned(l1));    -- ADDED 

    reg0: reg3 port map (a => a, ss => s0, e => e1, b => l0); 
    reg1: reg3 port map (a => a, ss => s1, e => e1, b => l1); 
    decod0: decod8 port map(a => l0, b => ll0); 
    decod1: decod8 port map(a => l1, b => ll1); 

    mem_blks_ii: 
    for ii in 0 to 7 generate 
    mem_blks_jj: 
    for jj in 0 to 7 generate 
     andij(ii,jj) <= ll0(ii) and ll1(jj); 
     fin_s(ii,jj) <= andij(ii,jj) and s; 
     fin_e(ii,jj) <= andij(ii,jj) and e; 
    -- regij: reg8 port map(a=> io_in, ss=> fin_s(ii,jj), e => fin_e(ii,jj), b => io_out); -- CHANGED 
    regij: reg8 port map(a=> io_in, ss=> fin_s(ii,jj), e => fin_e(ii,jj), b => mux88(ii,jj));  -- CHANGED 
    end generate mem_blks_jj; 
    end generate mem_blks_ii; 

    io_out <= mux88(idxii, idxjj); -- ADDED READBACK MUX 

end behavior; 

そして、それは与える:RAMがリードバック

ram88_bench_fixed.png

8バイト×8ビットのstd_logic_vector値には、2つの追加インデックスで選択された64ビットの値のうちの1つがあります。インスタンシエートされたコンポーネントから構築する場合は、すべての論理ゲートがどこにあるのかを合成してカウントすると、RAMとそのファンインバッファに使用されるラッチとほぼ同じサイズになり、書き込みステアリングよりもかなり大きくなります論理。

+0

ありがとう!非常に包括的な答え! – argasm

関連する問題