суббота, 3 июня 2017 г.

Странности в Verilog-2001


Немного истории или появление ПЛИС и HDL
Ха-ха, здравствуйте-здравствуйте, дорогие читатели. Недавно я писал про странности, связанные с софтом, а именно - Vivado, но дело дошло до самого языка.Вообще для программирования FPGA/PLD/ПЛИС используют языки программирования, позволяющие описать прохождение цифровых электрических сигналов и реакцию цифровых схем на эти сигналы. В данной статье я не буду затрагивать вопросы, связанные с цифровой схемотехникой, булевой алгеброй (алгеброй логики и т.п.). Прообразом ПЛИС стали Программируемые логические матрицы (ПЛМ/PLM), построенные на основе N-в-1 логических элементах (ИЛИ/И), к которым подведены от 1 до N сигналов. Программирование осуществляется с помощью плавления перемычек между входами логических элементов:
Любая логическая функция и любые последовательностные схемы могут быть реализованы на базисных элементах. 

После ПЛМ появились ПЛИС представляющие собой несколько десятков слоев ПЛМ (например, семейство MAX7000). Далее ПЛИС стали сохранять конфигурацию во внутреннюю оперативную память, а конфигурация при старте загружалась с Flash-памяти.

Для описания связей между  логическими элементами (задания какие перемычки нужно включить, а какие убрать) были придуманы языки для описания аппаратуры (HDL): AHDL, VHDL и Verilog.  Наиболее востребованными являются 2 последних, лично я предпочитаю Verilog, т.к. он отдаленно напоминает классику - язык С, а VHDL - Pascal.

Этот странный Verilog

В этом разделе я опишу, пожалуй лишь несколько из странностей Verilog.

1. Доступ к параметрам модуля из функции

Доступ к параметрам  модуля невозможен из функции, например есть модуль:

module my_module #
(
      parameter PARAM_1 = 1
)
(
    // ports defenitions
);

localparam _PARAM_1_LOC = PARAM_1;

function[1:0] some_func();
// local variables defined here ...
      // <!!!!! в этой функции мне недоступен PARAM_1, но доступен PARAM_1_LOC
endfunction;

endmodule

Несмотря на то, что функция some_func принадлежит модулю my_module у нее нет доступа к параметрам модуля, но есть доступ к локальным параметрам.

2. Инверсия порядка бит в байте

Иногда необходимо изменить порядок следования бит в векторе на обратный, очень бы хотелось сделать так:

reg[7:0] byte_vector;

reg[7:0] inversed_byte_vector;
 // где-то внутри always
inversed_byte_vector = byte_vector[0:7]; // ОШИБКА КОМПИЛЯЦИИ

 К сожалению, это не работает, приходится использовать конкатенацию или цикл:

inversed_byte_vector = {byte_vector[0], byte_vector[1], ....byte_vector[7]}


3. Доступ к вектору по индексам

 Известно, что чтобы получить доступ к произвольной части вектора достаточно обратиться к нему указав индексы, по которым необходимо сделать срез:

reg [31:0] my_vector;
reg [7:0] vector_part;

// где-то внутри always блока
vector_part = my_vector[29:22];

Но доступ по индексам возможен только тогда, когда передаются константы, поэтому приходится городить такие конструкции.

// присвоение внутри функции
reg[7:0] shift;
begin
shift = `MAX_DATA_WIDTH - NUMBER_OF_BYTES * 8;
// потом я не могу вырезать данные так:
result = data[MAX_DATA_WIDTH : shift]; // ошибка

для того, чтобы получить то, что я хочу, я должен сделать так:
result = data[`MAX_DATA_WIDTH - 1 : `MAX_DATA_WIDTH - NUMBER_OF_BYTES * 8];

 4. Чудесный мир литералов

Данная вещь куда как более тривиальна, но менее очевидна, для того, чтобы присвоить двоичное значение какому-нибудь регистру можно его записать как:

my_reg  = 8'b10001111; // Разрядность в битах, одинарная кавычка, латинская "бэ" и бит за битом (старшие биты идут вперед).

Но, что делать если нужно записать значение в 16-ричной системе счисления, т.к. 64 бита писать нереально утомительно, даже если пользоваться конкатом, для этих целей существует представление hex-литералов:

my_reg = 64'hAABBCCDDEEFF0011;
Хоть синтаксис и С подобный, но никаких тебе 0x и т.п.

Это не баги, это фичи
Verilog, конечно же, неплох, для описания HDL, но хочется, чтобы таких неудобств в нем было как можно меньше, учитывая, что последний раз стандарт выходил в 2001 г., а сам язык является наиболее популярным для программирования ПЛИС. Поэтому ждем перемен (с).

Комментариев нет:

Отправить комментарий

Распространение Windows-приложений (Chocolatey)

Менеджеры пакетов для ОС Windows В большинстве дистрибутивов Linux есть свои менеджеры пакетов: в Ubuntu/Mint это apt и deb, в OpenSuse э...