Попытка реализовать шину spi в vhdl

Я пытался установить связь с ЦАП LTC2426 через SPI, но безуспешно. Сейчас ищу помощи. Может ли кто-нибудь сказать мне, почему мой код не работает. CSDAC работает правильно, генерируется SCLK и отправляются 32 бита, но, возможно, я ошибся с синхронизацией. Я был бы очень благодарен, если бы кто-нибудь помог мне исправить код.

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

entity DAC is
    port
        (
            CLK : in STD_LOGIC;         
            SCLK : out STD_LOGIC;
            MOSI : out STD_LOGIC;
            CSDAC : out STD_LOGIC := '1'        
        );  
end DAC;

architecture Behavioral of DAC is
Signal Counter : Integer range 0 to 32 := 0;
Signal CurrentBit : Integer range 0 to 32 := 0;
Signal DataSent : STD_LOGIC := '1';
Constant Data : STD_LOGIC_VECTOR(31 downto 0) := X"0030FFF0";
Signal Slope : STD_LOGIC := '0';
begin
Prescaler : process(CLK) 
begin
    if rising_edge(CLK) then
        if Counter = 5 then
            Slope <= not(Slope);
            Counter <= 0;
        else
            Counter <= Counter + 1;
        end if;
    end if; 
end process;
SCLK <= SLOPE;
WriteDac : process(CLK) 
begin
    if rising_edge(CLK) then
         if DataSent = '1' then
            if CurrentBit <= 31 then
                CSDAC <= '0';
                MOSI <= Data(CurrentBit);
                CurrentBit <= CurrentBit +1;
            else
                CSDAC <= '1';       
                DataSent <= '0';                
            end if;
         end if;
    end if;
end process;
end Behavioral;

РЕДАКТИРОВАТЬ: НОВЫЙ КОД

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

entity DAC is
    port
        (
            CLK : in STD_LOGIC;         
            SCLK : out STD_LOGIC;
            MOSI : out STD_LOGIC;
            DEBUG : out STD_LOGIC := '1';
            CSDAC : out STD_LOGIC := '1'        
        );  
end DAC;

architecture Behavioral of DAC is
Signal Counter : Integer range 0 to 6 := 0;
Signal Counter2 : Integer range 0 to 33 := 0;
Signal CurrentBit : Integer range 0 to 33 := 0;
Signal Fixed : STD_LOGIC := '0';
Signal DataSent : STD_LOGIC := '0';
Constant Data : STD_LOGIC_VECTOR(31 downto 0) := X"0FFF0C00";
Signal Slope_last : STD_LOGIC := '0'; 
Signal Slope : STD_LOGIC := '0';
Signal MSS : STD_LOGIC := '0';
begin

WriteDac : process(CLK) 
begin
    if rising_edge(CLK) then
        if Counter = 5 then
            Slope_last <= Slope;
            Slope <= not(Slope);
           if Slope_last = '1' and Slope = '0' then
                if Fixed = '1' then
                    if DataSent = '0' then
                        if CurrentBit <= 31 then
                            CSDAC <= '0';
                            DEBUG <= '0';
                            MOSI <= Data(CurrentBit);
                            CurrentBit <= CurrentBit +1;
                         else
                            MOSI <= '0';
                            CSDAC <= '1';
                            DEBUG <= '1';
                            DataSent <= '1';
                        end if;
                    end if;
                else
                  if Counter2 <= 31 then
                        CSDAC <= '1';
                        DEBUG <= '1';
                        Counter2 <= Counter2 + 1;
                        MSS <= not(MSS);
                        MOSI <= MSS;
                  else  
                        Fixed <= '1';
                        MOSI <= '0';
                  end if;
                end if;
            end if;
        else
            Counter <= Counter + 1;
        end if;
    end if;
end process;
SCLK <= SLOPE;

end Behavioral;

Я запускаю MOSI, потому что когда я посылаю пару битов, SCLK восстанавливается. Сначала SCLK работает на частоте около 1,4 МГц, когда я запускаю mosi, он восстанавливается до 4,167 МГц, обратите внимание, что 1,4 МГц или около того может быть 1,5 МГц, я не могу вспомнить это слишком хорошо.


person gv260ea    schedule 04.07.2013    source источник


Ответы (2)


Может быть, ваш второй процесс должен быть чувствителен к SCLK (или наклону) i.s.o. КЛК? Вы можете проверить opencores.org для некоторых примеров модуля SPI. Даже если он написан на Verilog, это не очень хороший пример того, как можно что-то сделать.

person vermaete    schedule 04.07.2013
comment
У @baldyHDL был лучший ответ. Помещение вашего кода в один процесс будет лучше. Вы также можете подумать о создании FSM. Немного излишне для ваших текущих потребностей, но решения всегда усложняются через некоторое время :-) - person vermaete; 05.07.2013

вы должны обновить свой счетчик битов (CurrentBit), связанный с SCK. например.:

...
WriteDac : process(CLK) 
begin
   if rising_edge(CLK) then
      slope_last<=slope;

      if slope_last='1' and slope='0' then -- e.g. falling edge!
          if DataSent = '1' then
 ...
person baldyHDL    schedule 05.07.2013
comment
Я основывал свой код на вашей рекомендации, мой логический анализатор декодирует шину spi, но lt2624 все еще не работает. Мой новый код будет готов через пару минут - person gv260ea; 05.07.2013
comment
вы используете симулятор? вы можете, например. используйте Xilinx WebPack (бесплатно), где включен облегченный симулятор. моделирование помогает найти очевидные ошибки; в вашем новом коде, например. вы должны сбросить счетчик на 0 после строки if counter=5 then . - person baldyHDL; 06.07.2013
comment
Я напрямую программирую плату и подключаю логический анализатор logic8 - person gv260ea; 06.07.2013
comment
Я также проверил это с помощью прицела - person gv260ea; 06.07.2013
comment
как упоминалось ранее... сбросить счетчик после строки if counter=5 then. Моделирование дает вам представление о вашем коде. проверка с помощью масштаба - это здорово... используйте его как второй шаг после симуляции! - person baldyHDL; 06.07.2013
comment
Я сбросил счетчик, но не повезло. - person gv260ea; 06.07.2013
comment
в вашей реализации вы также должны изменить активный край наклона (поскольку наклон сводится на нет прямо в то время, когда вы обнаруживаете край). должно быть, если Slope_last = '0' и Slope = '1' тогда. при этом вы должны увидеть правильные сигналы с помощью вашего прицела. теперь вы должны тщательно сравнить таблицу данных с тем, что вы делаете. Я ожидаю, что вы хотите записать значение во все цапы (CMD=0x0, Addr=0x0F)? однако сначала вы записываете младший бит DATA, а начинать следует со старшего бита. также вы должны написать команду обновления после записи ЦАПов... АААААИ... симуляция поможет вам увидеть все это ;-) - person baldyHDL; 06.07.2013
comment
Нет, я инвертировал данные вручную, чтобы сначала получить msb CMD=0x3 ADDR = 0x0 Value = 0xFFF, это равно 0x0030FFF0, когда его инвертирование равно 0x0FFF0C00. А в даташите написано, что 0x3 записывает данные и обновляет их. - person gv260ea; 06.07.2013
comment
Я также использую 32-битный режим. - person gv260ea; 06.07.2013
comment
так что еще не работает? дает ли ваш код vhdl результат (измеряемый с помощью области ;-)), который вы ожидаете, или нет? - person baldyHDL; 06.07.2013
comment
и когда я имитирую ваш код, он выглядит так, как будто cmd=0x0, addr=0x0, data=0x30f, манекены=0xff0. это отличается от того, что вы измеряете с помощью прицела? - person baldyHDL; 06.07.2013
comment
если инвертировать данные как вы говорите, то должно получиться 0x000FFF0C (сначала 4 бита cmd, потом 4 бита addr, потом 12 бит данных, потом пустышки) - person baldyHDL; 06.07.2013
comment
Моя область показывает, что все в порядке, но ЦАП ничего не выводит, подождите, мой CMD должен быть 0x3 addr = 0x0 data = 0xff0 - person gv260ea; 06.07.2013
comment
Вывод должен быть 0b00000000001100001111111111110000. - person gv260ea; 06.07.2013
comment
Я только что попробовал 0x000FFF0C, но ЦАП по-прежнему ничего не выводит. Я также ценю, что вы только что смоделировали код для меня. - person gv260ea; 06.07.2013
comment
Извините, только что увидел, что в 32-битном режиме 8 фиктивных битов должны быть первыми ... поэтому ваш 0x0FFF0C00 был правильным. может ли быть проблема с начальным таймингом? это выглядит так, как если бы вы написали значение сразу после включения питания... готов ли ЦАП в этот момент? однако, если код VHDL генерирует ожидаемый результат, то, вероятно, это больше не проблема, связанная с VHDL... - person baldyHDL; 06.07.2013
comment
Любые идеи. Может полярность часов - person gv260ea; 06.07.2013
comment
У меня есть вопрос, который я только что научился моделировать, но почему sclk выглядит странно и иногда имеет значение X - person gv260ea; 06.07.2013
comment
Я проверил sck, он выглядит очень странно. Имеет большое количество недолетов и перелетов, а также приличное количество шума и звона. - person gv260ea; 06.07.2013
comment
1. полярность часов: вы изменили активный наклон, как указано в предыдущем комментарии? 2. Моделирование: какие инструменты вы используете? Я смоделировал с помощью Xilinx ISE, и SCK кажется стабильным ... Я могу отправить тестовый стенд, если потребуется. 3. превышение/недостаток: проверьте соединение с землей (сделайте его как можно короче) и проверьте соединения с ЦАП. - person baldyHDL; 06.07.2013
comment
1. Да, я сделал 2-й, я переименовал sclk в sck, так как симулятор ise подумал, что это часы, но на цапе все еще ничего. - person gv260ea; 07.07.2013