Почему для сигнала VHDL "inout" не будет присвоено значение при использовании в качестве выхода - PullRequest
3 голосов
/ 20 октября 2019

У меня есть описание VHDL для моста, и двунаправленному сигналу "mem_data_port0" не присваивается никакого значения независимо от того, что я пишу в него. Выводы на ПЛИС назначены соответственно, но нет выхода.

У меня есть код ниже (это для ПЛИС, входящей в более крупную систему, поэтому комментарии будут отражать другие компоненты системы, которые не являются ПЛИС)

К вашему сведению: FPGA представляет собой решетку LCMXO2-7000HC

Любые советы по назначению "mem_data_port0"?

library ieee;
use ieee.std_logic_1164.all; 
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;
--use ieee.std_logic_signed.all;
use ieee.std_logic_arith.all;
use ieee.numeric_std.all;


library machxo2;
use machxo2.all;

entity SinglePhasePowerAnalyzerBridge is
    port(
    output0 : out std_logic; -- dummy, unassigned outputs
    output1 : out std_logic;
    output2 : out std_logic;
    output3 : out std_logic;
    output4 : out std_logic;
    output5 : out std_logic;
    output6 : out std_logic;
    output7 : out std_logic;

    accq_data_in : in std_logic_vector (15 downto 0); -- accquisition data in
    accq_clk : in std_logic; -- accquisition clock in
    accq_data_ready : in std_logic; -- data ready in 0: sending voltage/current data, 1: sending frequency data
    accq_reset : in std_logic; -- accquisition reset (active low)
    accq_voltage_current : in std_logic; -- accquisition select for voltage and current 0: voltage, 1: current

    buffer_data_port0 : out std_logic_vector (15 downto 0); -- buffer data
    buffer_address_port0 : in std_logic_vector(12 downto 0); -- buffer address low bits
    buffer_address_high_port0 : in std_logic_vector(2 downto 0); -- buffer address high bits
    buffer_high_byte_en_port0 : in std_logic; -- high byte enable
    buffer_low_byte_en_port0 : in std_logic; -- low byte enable
    buffer_write_en_port0 : in std_logic; -- write enable
    buffer_output_en_port0 : in std_logic; -- output enable
    buffer_memory_en_port0 : in std_logic; -- memory enable

    buffer_interrupt_out : out std_logic; 

    -- pins going to external SRAM memory
    mem_data_port0 : inout std_logic_vector (15 downto 0);
    mem_address_port0 : out std_logic_vector(12 downto 0);
    mem_address_high_port0 : out std_logic_vector (3 downto 0);
    mem_memory_en_port0 : out std_logic := '1';
    mem_output_en_port0 : out std_logic := '1';
    mem_write_en_port0 : out std_logic := '1';
    mem_high_byte_en_port0 : out std_logic := '0';
    mem_low_byte_en_port0 : out std_logic := '0';

    debug_out : out std_logic -- debug output

    );

end SinglePhasePowerAnalyzerBridge;

architecture rtl of SinglePhasePowerAnalyzerBridge is

signal frequency_storage_buffer : std_logic_vector (15 downto 0); -- frequency buffer

signal voltage_storage_pointer : integer range 0 to 8191;
signal current_storage_pointer : integer range 0 to 8191;

signal signal_accq_data_in : std_logic_vector (15 downto 0);
signal signal_accq_clk : std_logic;
signal signal_inverse_accq_clk : std_logic;
signal signal_accq_data_ready : std_logic;
signal signal_accq_reset : std_logic;
signal signal_accq_voltage_current : std_logic;

signal signal_delayed_inverse_accq_clk : std_logic;

signal signal_buffer_data_port0 : std_logic_vector (15 downto 0);
signal signal_buffer_address_port0 : std_logic_vector(12 downto 0);
signal signal_buffer_address_high_port0 : std_logic_vector(2 downto 0);
signal signal_buffer_high_byte_en_port0 : std_logic;
signal signal_buffer_low_byte_en_port0 : std_logic;
signal signal_buffer_write_en_port0 : std_logic;
signal signal_buffer_output_en_port0 : std_logic;
signal signal_buffer_memory_en_port0 : std_logic;

begin

    signal_accq_data_in <= accq_data_in; -- connect all the pins to internal signals
    signal_accq_clk <= accq_clk;
    signal_accq_data_ready <= accq_data_ready;
    signal_accq_reset <= accq_reset;
    signal_accq_voltage_current <= accq_voltage_current;

    signal_inverse_accq_clk <= not signal_accq_clk;

    --debug_out <= signal_delayed_inverse_accq_clk;

    signal_buffer_address_port0 <= buffer_address_port0;
    signal_buffer_address_high_port0 <= buffer_address_high_port0;
    signal_buffer_high_byte_en_port0 <= buffer_high_byte_en_port0;
    signal_buffer_low_byte_en_port0 <= buffer_low_byte_en_port0;
    signal_buffer_write_en_port0 <= buffer_write_en_port0;
    signal_buffer_output_en_port0 <= buffer_output_en_port0;
    signal_buffer_memory_en_port0 <= buffer_memory_en_port0;

    buffer_interrupt_out <= not signal_accq_data_ready;

    output2 <= signal_accq_data_ready; -- dummy outputs, so the input pins are not left uncommected
    output3 <= signal_accq_clk;
    output4 <= signal_accq_reset;
    output5 <= signal_accq_voltage_current;


    general_event : process(signal_accq_clk, signal_accq_data_ready, signal_accq_data_in, signal_accq_voltage_current, signal_accq_reset, 
    signal_buffer_memory_en_port0, signal_buffer_output_en_port0, signal_buffer_write_en_port0, signal_buffer_address_high_port0, signal_buffer_address_port0, 
    signal_buffer_data_port0, frequency_storage_buffer, signal_accq_reset, signal_accq_data_ready, voltage_storage_pointer, current_storage_pointer)
    begin
        if(signal_accq_data_ready = '0') then -- when data from the acquisition controller comes in
            mem_output_en_port0 <= '1'; -- disable memory output
            mem_memory_en_port0 <= '0'; -- enable memory
            mem_write_en_port0 <= signal_inverse_accq_clk; -- send the acquisition clock to the memory write enable pin
            if(signal_accq_reset = '1') then -- if reset is not activated...
                accq_clk_edge : if(rising_edge(signal_accq_clk)) then -- process on clock rising edge
                    if(signal_accq_voltage_current = '1') then -- if sending current data
                        mem_data_port0 <= signal_accq_data_in; -- store the data in the current buffer
                        mem_address_port0 <= std_logic_vector(to_unsigned(current_storage_pointer, 13));
                        mem_address_high_port0 <= "0001"; -- sending current data to memory
                    current_storage_pointer <= (current_storage_pointer + 1); -- increment the counter
                    elsif (signal_accq_voltage_current = '0') then -- do the same if sending voltage data
                        --mem_data_port0 <= signal_accq_data_in; -- store the data in the voltage buffer
                        mem_data_port0 <= "1111111111111111";
                        mem_address_port0 <= std_logic_vector(to_unsigned(voltage_storage_pointer, 13));
                        mem_address_high_port0 <= "0000"; -- sending voltage data to memory
                        voltage_storage_pointer <= (voltage_storage_pointer + 1); -- increment the counter
                    end if;
                end if accq_clk_edge;
            else -- if reset is activated...
                voltage_storage_pointer <= 0; -- reset everything to 0
                current_storage_pointer <= 0; -- reset everything to 0
            end if;
        --end process accq_event;
        elsif (signal_accq_data_ready = '1') then -- if data ready is high, the buffer is in read mode
            mem_data_port0 <= "ZZZZZZZZZZZZZZZZ"; -- set memory data lines to input, or read mode
            mem_write_en_port0 <= '1'; -- disable writing to the memory
            mem_output_en_port0 <= '0'; -- enable memory output
            mem_address_port0 <= signal_buffer_address_port0; -- select the appropriate addreess
            mem_address_high_port0 (2 downto 0) <= signal_buffer_address_high_port0; -- do the same with the high bits

            if(rising_edge(signal_accq_clk) and signal_accq_reset = '1') then -- if the accquisition MCU is writing with the data ready pin high
                frequency_storage_buffer <= signal_accq_data_in; -- store the frequency value that it's sending
            end if;
            if(signal_accq_reset = '0') then -- reset as before if reset is enabled
                voltage_storage_pointer <= 0; -- reset everything to 0
                current_storage_pointer <= 0; -- reset everything to 0
            end if;

            if(signal_buffer_memory_en_port0 = '0' and signal_buffer_write_en_port0 = '1' and signal_accq_data_ready = '1' and signal_accq_reset = '1') then -- memory enabled and write enable high...
                case signal_buffer_address_high_port0 is
                    when "000" => signal_buffer_data_port0 <= mem_data_port0; -- output data to downstream MCUs as needed
                    when "001" => signal_buffer_data_port0 <= mem_data_port0;
                    when "010" => signal_buffer_data_port0 <= frequency_storage_buffer;
                    when "011" => signal_buffer_data_port0 <= std_logic_vector(to_unsigned(voltage_storage_pointer, 16));
                    when "100" => signal_buffer_data_port0 <= std_logic_vector(to_unsigned(current_storage_pointer, 16));
                    when "111" => signal_buffer_data_port0 <= "1010000001010110"; -- 0xA056
                    when others=>

                end case;
            end if; 
            if(signal_buffer_output_en_port0 = '0') then
                --buffer_data_port0(7 downto 0) <= signal_buffer_data_port0 (15 downto 8);
                --buffer_data_port0(15 downto 8) <= signal_buffer_data_port0 (7 downto 0);
                buffer_data_port0 <= signal_buffer_data_port0;
            else
                buffer_data_port0 <= "ZZZZZZZZZZZZZZZZ";
            end if;
        end if;
    end process general_event;

    output6 <= signal_buffer_high_byte_en_port0;
    output7 <= signal_buffer_low_byte_en_port0;



end rtl; 

1 Ответ

0 голосов
/ 20 октября 2019

Я пробовал ваш код на Modelsim. Хотя я не могу комментировать правильность поведения mem_data_port0, он получает назначенные значения в зависимости от других соответствующих сигналов, поэтому для направления выхода это работает.

VHDL Modelsim simulation

Если вы говорите о том, что вы не можете присвоить ему значения извне, все, о чем я могу подумать, это то, что вы забыли назначить ему высокий импеданс в режиме ввода, но вы это сделали, так что это не так.

Объяснение может состоять в том, что ваша сущность не является сущностью верхнего уровня, что может сделать входные порты непригодными (inout не имеет смысла внутри ПЛИС, только на верхнем уровне проекта).

...