dxp 58 3 июня, 2010 Опубликовано 3 июня, 2010 · Жалоба Столкнулся с непоняткой. Вроде не первый раз использую структуры, но, видимо, прежние случаи были попроще. Итак. Есть непакованная структура (тип) с сигналами (коннект к модулям FIFO): typedef struct { bit flush; bit [ DATA_WIDTH-1:0] head; bit [ DATA_WIDTH-1:0] tail; bit push; bit pop; bit full; bit empty; bit [clog2(FRAME_SIZE)-1:0] count; } frame_buffer_t; Далее объявляется массив объектов данного типа (буферов несколько, поэтому и пачек сигналов тоже несколько): frame_buffer_t frame_buffer[FRAME_BUFFERS]; Далее, есть два разные блока (проблемые места выделены): always_comb begin for(int i = 0; i < FRAME_BUFFERS; i++) begin if( (i == sender.current_index) && (sender.fsm == sfsmSEND_DATA) ) begin frame_buffer[i].push = tx_channel_data_strobe; // <------------------------- frame_buffer[i].pop = tx_channel_data_strobe; ... always_comb begin for(int i = 0; i < FRAME_BUFFERS; i++) begin if( (check_frame_delivery.fsm == cpdfsmSUCCESS ) && ( i == sended_index_queue.head ) ) begin frame_buffer[i].flush = 1; // <------------------------- end else begin frame_buffer[i].flush = 0; end end end Квеста при компиляции выдает: Error: (vlog-7033) Src/swp.sv(559): Variable 'frame_buffer' driven in a combinatorial block, may not be driven by any other process. See Src/swp.sv(332). Т.е. что мы видим? Компилятор почему-то считает, что frame_buffer - это один цельный объект, и не позволяет писать в него из разных мест. Но на деле-то там разные "неделимые" объекты - члены структуры, которые в случае непакованных структур могут использоваться, насколько знаю, совершенно свободно без "привязок" к блокам. Там вообще (по Стандарту) можно одному члену структуры присваивать в continuos assignment, а другому члену этой же структуры - в поведенческом блоке. Аналогичная трабла возникла при генерации инстансов самих буферов: genvar i; generate for(i = 0; i < FRAME_BUFFERS; i++) begin : fdf fifo_sc_m #( .DATA_WIDTH ( DATA_WIDTH ), .CAPACITY ( FRAME_SIZE ) ) frame_data_fifo_inst ( .clk ( clk ), .sclr ( rst || frame_buffer[i].flush ), .data_in ( frame_buffer[i].tail ), .load ( frame_buffer[i].push ), .get ( frame_buffer[i].pop ), .empty ( frame_buffer[i].empty ), .full ( frame_buffer[i].full ), .data_out ( frame_buffer[i].head ), .usedw ( frame_buffer[i].count ) ); end endgenerate Ругается уже не компилятор, а симулятор: # ** Fatal: (vsim-3839) Src/swp.sv(704): Variable '/main_tb/test_swp_dut/swp_transceiver_a_inst/frame_buffer[0].empty', driven via a port connection, is multiply driven. See Src/swp.sv(332). # Region: /main_tb/test_swp_dut/swp_transceiver_a_inst/fdf[0]/frame_data_fifo_inst Таких мессаг он выдает пачку - на сигналы full, empty, count и head - т.е. на все сигналы, которые являются выходами модуля. А ссылается по-прежнему на вышеприведенный блок. Т.е. опять не "видит" разницы - отдельный объект и объект-непакованная структура. Скормил код Квартусу, тот проглотил без вопросов, не подавился. И даже на RTL viewer'е изобразил что-то похожее на правду (код пока сырой, там до нормального синтеза далеко). Вот и думаю, в чем засада и кто дурак - я или квеста? Рад услышать любые идеи. :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
des00 25 3 июня, 2010 Опубликовано 3 июня, 2010 · Жалоба Вот и думаю, в чем засада и кто дурак - я или квеста? квеста, начиная где то с 6.4d она стала параноидальной в этом вопросе %( Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Kuzmi4 0 3 июня, 2010 Опубликовано 3 июня, 2010 · Жалоба 2 des00 а можно поподробнее ?? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
des00 25 3 июня, 2010 Опубликовано 3 июня, 2010 · Жалоба а можно поподробнее ?? дык dxp же привел пример, попробуйте присвоить значения разным полям структуры или разным элементам неупакованного массива в разных процессах, до 6.4d квеста позволяла это сделать. После этого у нее появилась паранойя. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
dxp 58 3 июня, 2010 Опубликовано 3 июня, 2010 · Жалоба квеста, начиная где то с 6.4d она стала параноидальной в этом вопросе %( Да, забыл указать версию. Налетел на это на версии 6.4с, которой уже давно успешно пользовался. Установил 6.5d, результат ровно тот же. Вот думаю, как быть... Отказываться от структур?.. Не хочется. :( Работать на древней версии и не обновлять?.. Тоже не гуд - все развивается, а тут такой сознательный застой. Искать другой симулятор?.. Тоже не вариант. Выбора-то особо нет. Какие будут мнения? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Kuzmi4 0 6 июня, 2010 Опубликовано 6 июня, 2010 · Жалоба И всё же - как выходить с таких ситуаций кроме даунгрейда версии симулятора ? Если у кого есть рецептики - поделитесь :laughing: Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ViKo 1 7 июня, 2010 Опубликовано 7 июня, 2010 · Жалоба И всё же - как выходить с таких ситуаций кроме даунгрейда версии симулятора ? Может быть, в данном случае помогли бы интерфейсы вместо структур? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
des00 25 7 июня, 2010 Опубликовано 7 июня, 2010 · Жалоба Выбора-то особо нет. с массивами я по колхозному хачу always @(*) begin dat[0].re = idat_re; dat[0].im = idat_im; end generate if (pPRE_DELAY > 0) begin always @(posedge iclk) begin : data_delay int i; if (ival) begin for (i = 1; i <= pPRE_DELAY; i++) begin dat[i] <= dat[i-1]; end end end end endgenerate Со структурами сложнее, в упаковку их как с обычными векторами %) Но это хак, точнее затычка от кое чьих кривых рук %( Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться