Worldmaster 0 April 2, 2024 Posted April 2, 2024 · Report post Здравствуйте. Подскажите пожалуйста алгоритм правкеи вот этих проблем? Я так понял что нужно добавить констрейнт. Только мне не понятно какую линию надо брать из какого столбца?. Тут в некоторых строках указаны вообще внутренние сигналы. Подскажите пожалуйста как правильно это разрулить? Quote Share this post Link to post Share on other sites More sharing options...
Джеймс 5 April 2, 2024 Posted April 2, 2024 · Report post 3 hours ago, Worldmaster said: Я так понял что нужно добавить констрейнт. Только мне не понятно какую линию надо брать из какого столбца?. Тут в некоторых строках указаны вообще внутренние сигналы. Подскажите пожалуйста как правильно это разрулить? А Ваш существующий SDC файл можете опубликовать? Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 2, 2024 Posted April 2, 2024 · Report post В 02.04.2024 в 22:44, Джеймс сказал: А Ваш существующий SDC файл можете опубликовать? Конечно vhit_fpga.sdc Quote Share this post Link to post Share on other sites More sharing options...
pavlovconst 7 April 3, 2024 Posted April 3, 2024 · Report post Среда вам подсказывает, что в этих путях есть переход между тактовыми доменами. В тракт сигнала необходимо добавить синхронизаторы. Когда вы, как разработчик, будете уверены, что CDC сделаны корректно, можно будет написать констрейнт set_false_path. Если просто написать констрейнты, ничего не меняя в коде - вы только замаскируете проблему. Так лучше не делать ) Quote Share this post Link to post Share on other sites More sharing options...
Maverick_ 17 April 3, 2024 Posted April 3, 2024 · Report post применение IP core двухклоковое фифо между SDRAM и логикой - как решение проблеми IP core само пропишет ограничения для CDC в sdc файл Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 3, 2024 Posted April 3, 2024 · Report post В 03.04.2024 в 15:03, Maverick_ сказал: применение IP core двухклоковое фифо между SDRAM и логикой - как решение проблеми Так у меня так и есть. Данные пишутся в FIFO с одним клоком а считываются с другим. И ничего само не прописывается. В 03.04.2024 в 11:28, pavlovconst сказал: Среда вам подсказывает, что в этих путях есть переход между тактовыми доменами. В тракт сигнала необходимо добавить синхронизаторы. Когда вы, как разработчик, будете уверены, что CDC сделаны корректно, можно будет написать констрейнт set_false_path. Если просто написать констрейнты, ничего не меняя в коде - вы только замаскируете проблему. Так лучше не делать ) А можно предметно показать что сделать? Что то мне не совсем понятно. Как вот конкретно вот это утсранить? 2 -5.351 device_state_s0/Q SDRAM/RAM_ROW_ADDR_req_10_s0/CE InClock_50_net:[R] clk_160_clockout:[R] 1.250 2.316 4.216 где device_state это применяется в основом блоке от частоты InClock_50_net и вообще никак не связан с SDRAM. Тем более с линией RAM_ROW_ADDR_req. Это тактируется от clk_160_clockout = 160 мегагерц. Что конкретно изменить в коде то надо? Quote Share this post Link to post Share on other sites More sharing options...
Freibier 23 April 3, 2024 Posted April 3, 2024 · Report post 17 часов назад, Worldmaster сказал: Конечно А где констрейны input_delay output_delay? Не знаток говинов, но 600 MHz на вход и 160MHz на выход - это допустимо? Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 3, 2024 Posted April 3, 2024 · Report post В 03.04.2024 в 16:29, Freibier сказал: А где констрейны input_delay output_delay? Так я и прошу чтобы показали где и что надо записать то? В 03.04.2024 в 16:29, Freibier сказал: Не знаток говинов, но 600 MHz на вход и 160MHz на выход - это допустимо? по мануалу вообще указано до 1200 на MIPI Lane. Мне надо 600. Я так понимаю что при сборке компилятор будет оптимизировать так чтобы добрать до этой частоты? Quote Share this post Link to post Share on other sites More sharing options...
Freibier 23 April 3, 2024 Posted April 3, 2024 · Report post 1 час назад, Worldmaster сказал: от частоты InClock_50_net и вообще никак не связан с SDRAM а может нужен set_clock_groups? объявить частоты эксклюзивными, и тогда все обмены данными между клоковыми доменами на совести разработчика. Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 3, 2024 Posted April 3, 2024 · Report post В 03.04.2024 в 17:51, Freibier сказал: а может нужен set_clock_groups? А какие последствия? Ну а по сути мне бы кто нибудь простыми словами на примере показал в чем беда и я бы поправил. Вот например: Видим ошибку Вот два процесса где используется командный буфер. -- в конце цикла приемки проверим что там пришло cmd_chk_proc: process (InClock_50, FFT_OE_N) type cmd_states is (idle, send_data); variable cmd_state: cmd_states := idle; variable cnt: integer := 0; variable ptr: integer := 0; begin if rising_edge(InClock_50) then case cmd_state is when idle => if i2c_dev_IsEnable = '1' and i2c_IsComplete = '1' then i2c_dev_IsEnable <= '0'; end if; if FFT_OE_N = '1' and FFT_OE_D = '0' then case i2c_command_buffer(0) is when x"a1" => device_state <= command_mode; -- в каждом устрйостве i2c разместить фифо двухклоковый -- при получении данных фиксируем количество и переливаем их в модуль i2c -- затем запускаем обработку -- таким образом мы можм мередать для обработки любое количество байт подряд -- второй байт определяет номер шины i2c для отправки команды. -- гироскоп i2c_mode <= i2c_command_buffer(1)(1 downto 0); i2c_dev_Device_addr <= i2c_command_buffer(I2C_DEV_ADDR_BIT)(6 downto 0); i2c_dev_Reg_addr_HI <= i2c_command_buffer(I2C_REG_ADDR_HI); i2c_dev_Reg_addr_LOW <= i2c_command_buffer(I2C_REG_ADDR_LOW); i2c_dev_Reg_addr_16 <= i2c_command_buffer(I2C_REG_ADDR16_BIT)(0); i2c_dev_DataCount <= i2c_command_buffer(I2C_BYTES_COUNT_BIT); i2c_dev_Reg_RW <= i2c_command_buffer(I2C_RW_BIT)(0); i2c_dev_WriteEn <= '0'; i2c_dev_ReadEn <= '0'; i2c_dev_IsEnable <= '0'; i2c_dev_ResetBuffers <= '1'; cnt := to_integer(unsigned(i2c_command_buffer(I2C_BYTES_COUNT_BIT))); cmd_state := send_data; ptr := 0; when x"a2" => device_state <= command_mode; -- команда включения или отключения отладочного светодиода -- включим когда будет нормальная версия debug_led_drive <= i2c_command_buffer(1)(0); when x"a3" => device_state <= camera_mode; icam_index <= i2c_command_buffer(1)(0); -- команда переводит устройство в режим передачи кадров при каждом запросе на чтение when x"a4" => LaserOut_o <= i2c_command_buffer(1)(0); when others => end case; end if; when send_data => if cnt > 0 then i2c_dev_ResetBuffers <= '0'; if i2c_dev_Reg_RW = WRITE then i2c_dev_WriteEn <= '1'; i2c_dev_WriteData <= i2c_command_buffer(I2C_DATA_PTR_BIT + ptr); end if; ptr := ptr + 1; cnt := cnt - 1; else i2c_dev_ResetBuffers <= '1'; i2c_dev_IsEnable <= '1'; i2c_dev_WriteEn <= '0'; cmd_state := idle; end if; end case; end if; end process cmd_chk_proc; read_fft_proc: process (USB30_in_clk, FFT_rx_flag) variable read_ptr: integer :=0; variable counter: integer :=0; variable state: fft_io_states := idle; begin if rising_edge(USB30_in_clk) then if FFT_rx_flag = '0' then case state is when idle => i2c_command_buffer <= (others => (others => '0')); if counter >= 4 then state := oe_state; else counter := counter + 1; end if; when oe_state => FFT_OE_N <= '0'; state := rd_state; when rd_state => state := work_state; FFT_RD_N <= '0'; when work_state => if read_ptr < MAX_I2C_BUF_CNT then -- принимаем данные в командный буфер i2c_command_buffer(read_ptr) <= FFT_DATA_IN(7 downto 0); i2c_command_buffer(read_ptr+1) <= FFT_DATA_IN(15 downto 8); i2c_command_buffer(read_ptr+2) <= FFT_DATA_IN(23 downto 16); i2c_command_buffer(read_ptr+3) <= FFT_DATA_IN(31 downto 24); read_ptr := read_ptr + 4; else state := nop_state; end if; when others => FFT_RD_N <= '1'; FFT_OE_N <= '1'; end case; else counter := 0; state := idle; read_ptr := 0; FFT_RD_N <= '1'; FFT_OE_N <= '1'; end if; end if; end process read_fft_proc; Вот как конкретно тут исправить проблему? Quote Share this post Link to post Share on other sites More sharing options...
Maverick_ 17 April 3, 2024 Posted April 3, 2024 · Report post посмотрите Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 3, 2024 Posted April 3, 2024 (edited) · Report post В 03.04.2024 в 18:09, Maverick_ сказал: посмотрите У меня не такой богатый опыт в этой штуке. Можете показать как это будет выглядеть на моем примере?? По какому принципу надо выставлять set_max_delay и как определить нужные линии? Вот допустим линия: Добавляю задержку. Но какое ставить число? В итоге чего бы не ставил то все равно ничего не меняется. Edited April 3, 2024 by Worldmaster Quote Share this post Link to post Share on other sites More sharing options...
Maverick_ 17 April 3, 2024 Posted April 3, 2024 · Report post смотрели дизайн-пример https://www.gowinsemi.com/en/support/ip_detail/4/ и https://www.gowinsemi.com/en/support/database/2056/? пусть даже на другой плис... к каждой IP core среда должна генерировать файл констрейнов... во всяком случае у Intel, Xilinx так происходит... сгенерируйте пример и посмотрите что да как PS я с GOWIN не работал... Quote Share this post Link to post Share on other sites More sharing options...
Worldmaster 0 April 3, 2024 Posted April 3, 2024 · Report post В 03.04.2024 в 18:38, Maverick_ сказал: смотрели дизайн-пример https://www.gowinsemi.com/en/support/ip_detail/4/ https://www.gowinsemi.com/en/support/database/2056/? PS я с GOWIN не работал... Да смотрел конечно. Но тут даже не в МИПИ дело. Вот пример выше там просто буфер в одном процессе заполняется в другом обрабатывается. Добавил синхронизирующий процесс. process (InClock_50) begin if rising_edge(InClock_50) then i2c_command_buffer_sync <= i2c_command_buffer; end if; end process; -- в конце цикла приемки проверим что там пришло cmd_chk_proc: process (InClock_50, FFT_OE_N, FFT_OE_D, i2c_dev_IsEnable, i2c_IsComplete, i2c_command_buffer_sync) type cmd_states is (idle, send_data); variable cmd_state: cmd_states := idle; variable cnt: integer := 0; variable ptr: integer := 0; begin if rising_edge(InClock_50) then case cmd_state is when idle => if i2c_dev_IsEnable = '1' and i2c_IsComplete = '1' then i2c_dev_IsEnable <= '0'; end if; if FFT_OE_N = '1' and FFT_OE_D = '0' then case i2c_command_buffer_sync(0) is when x"a1" => device_state <= command_mode; -- в каждом устрйостве i2c разместить фифо двухклоковый -- при получении данных фиксируем количество и переливаем их в модуль i2c -- затем запускаем обработку -- таким образом мы можм мередать для обработки любое количество байт подряд -- второй байт определяет номер шины i2c для отправки команды. -- гироскоп i2c_mode <= i2c_command_buffer_sync(1)(1 downto 0); i2c_dev_Device_addr <= i2c_command_buffer_sync(I2C_DEV_ADDR_BIT)(6 downto 0); i2c_dev_Reg_addr_HI <= i2c_command_buffer_sync(I2C_REG_ADDR_HI); i2c_dev_Reg_addr_LOW <= i2c_command_buffer_sync(I2C_REG_ADDR_LOW); i2c_dev_Reg_addr_16 <= i2c_command_buffer_sync(I2C_REG_ADDR16_BIT)(0); i2c_dev_DataCount <= i2c_command_buffer_sync(I2C_BYTES_COUNT_BIT); i2c_dev_Reg_RW <= i2c_command_buffer_sync(I2C_RW_BIT)(0); i2c_dev_WriteEn <= '0'; i2c_dev_ReadEn <= '0'; i2c_dev_IsEnable <= '0'; i2c_dev_ResetBuffers <= '1'; cnt := to_integer(unsigned(i2c_command_buffer_sync(I2C_BYTES_COUNT_BIT))); cmd_state := send_data; ptr := 0; when x"a2" => device_state <= command_mode; -- команда включения или отключения отладочного светодиода -- включим когда будет нормальная версия debug_led_drive <= i2c_command_buffer_sync(1)(0); when x"a3" => device_state <= camera_mode; icam_index <= i2c_command_buffer_sync(1)(0); -- команда переводит устройство в режим передачи кадров при каждом запросе на чтение when x"a4" => LaserOut_o <= i2c_command_buffer_sync(1)(0); when others => end case; end if; when send_data => if cnt > 0 then i2c_dev_ResetBuffers <= '0'; if i2c_dev_Reg_RW = WRITE then i2c_dev_WriteEn <= '1'; i2c_dev_WriteData <= i2c_command_buffer_sync(I2C_DATA_PTR_BIT + ptr); end if; ptr := ptr + 1; cnt := cnt - 1; else i2c_dev_ResetBuffers <= '1'; i2c_dev_IsEnable <= '1'; i2c_dev_WriteEn <= '0'; cmd_state := idle; end if; end case; end if; end process cmd_chk_proc; Но он все равно ругается на задержку. Quote Share this post Link to post Share on other sites More sharing options...
sazh 11 April 3, 2024 Posted April 3, 2024 · Report post 6 часов назад, Worldmaster сказал: по мануалу вообще указано до 1200 на MIPI Lane. Мне надо 600. Я так понимаю что при сборке компилятор будет оптимизировать так чтобы добрать до этой частоты? И где Вы такие частоты взяли. Что такое 600. pixel clock? Total data rate? mipi bit clock? Должно быть четкое понятие что и на какой частоте гонит камера. И потянет ли это китайская плис. Например full hd: 1920x1080p@60Hz, 2-line total horizontal sample = 2200, total vertical line = 1125; pixel clock frequency = 2200x1125x60 = 148.5 MHz total data rate = 148.5MHz * 8bit = 1.188 Gbps line rate (data rate per line) 1.188 Gbps/2-line = 594 Mbps MIPI bit clock frequency = 594/2 = 297 MHz (ddr clk) Это китаец вряд ли потянет. Надо смотреть что его pll может. И можно ли камеру на него сажать. Получается , системная частота в районе 100МГц, не более. Вроде как. Quote Share this post Link to post Share on other sites More sharing options...