Как мне указать функцию сравнения табло в Cocotb?
Я хочу расширить пример Cocian Endan Swapper, чтобы он также проверял содержимое пакетов, выводимых тестируемым устройством (DUT). В приведенном примере кодаmodel
Функция, которая генерирует ожидаемый результат, добавляет неизмененную входную транзакцию в список ожидаемых результатов. Этот список предоставляется в качестве параметра на табло.
Чтобы понять, как работает табло и почему model
Функция не добавляла транзакции с заменой байтов, я внес ошибку проектирования в DUT. В следующем блоке кода endian_swapper.vhdl
if (byteswapping = '0') then
stream_out_data <= stream_in_data;
else
stream_out_data <= byteswap(stream_in_data);
end if;
Я просто перевернул if
условие в первой строке: (byteswapping /= '0')
,
После повторного запуска тестового стенда я ожидал, что тест не пройден, но он все равно проходит:
# 62345.03ns INFO cocotb.regression regression.py:209 in handle_result Test Passed: wavedrom_test
# 62345.03ns INFO cocotb.regression regression.py:170 in tear_down Passed 33 tests (0 skipped)
# 62345.03ns INFO cocotb.regression regression.py:176 in tear_down Shutting down...
Похоже, что при создании табло отсутствует функция сравнения:
self.scoreboard = Scoreboard(dut)
self.scoreboard.add_interface(self.stream_out, self.expected_output)
Он должен иметь третий параметр в вызове add_interface
, но этот параметр недокументирован.
Итак, как мне указать эту функцию сравнения, чтобы также проверялось содержимое пакета?
Я использую QuestaSim для моделирования и выполнил тестовый стенд с make SIM=questa
, Я также очистил каталог сборки между запусками.
2 ответа
Если я использую следующий diff при использовании Icarus, тесты не пройдут, как ожидалось:
diff --git a/examples/endian_swapper/hdl/endian_swapper.sv b/examples/endian_swapper/hdl/endian_swapper.sv
index 810d3b7..a85db0d 100644
--- a/examples/endian_swapper/hdl/endian_swapper.sv
+++ b/examples/endian_swapper/hdl/endian_swapper.sv
@@ -119,7 +119,7 @@ always @(posedge clk or negedge reset_n) begin
stream_out_startofpacket <= stream_in_startofpacket;
stream_out_endofpacket <= stream_in_endofpacket;
- if (!byteswapping)
+ if (byteswapping)
stream_out_data <= stream_in_data;
else
stream_out_data <= byteswap(stream_in_data);
У меня нет доступа к Questa, но я посмотрю, что происходит на симуляторе VHDL. Мой инстинкт должен был бы перепроверить, что ты бежал make clean
после внесения изменений и проверки того, что Questa каким-то образом не кэширует встроенные библиотеки RTL.
Вы правы, что есть некоторые недокументированные ключевые аргументы add_interface
метод табло:
compare_fn
может быть любой вызываемой функциейreorder_depth
целое число, разрешающее изменение порядка транзакций
Если вы поставите compare_fn
он будет вызван с транзакцией, когда он будет получен монитором, однако это довольно примитивный механизм. Он не масштабируется и существует только по историческим причинам (следовательно, не документирован).
Лучший способ - создать подкласс класса Scoreboard и определить пользовательский compare
Способ по следующему прототипу:
def compare(self, got, exp, log, strict_type=True):
"""
Common function for comparing two transactions.
Can be re-implemented by a subclass.
"""
где got
а также exp
полученные и ожидаемые транзакции и log
это ссылка на logger
экземпляр монитора (для предоставления более значимых сообщений).
Верхний уровень примера Endian Swapper предоставляется как код SystemVerilog, а также код VHDL. Код verilog используется по умолчанию, если иное не указано опциями компиляции.
Если я бегу:
make SIM=questa TOPLEVEL_LANG=vhdl
как указано в кратком руководстве, все работает как положено. В этом случае нет необходимости указывать функцию сравнения.