VHDL первые шаги или программируемая логика, как аппарат быстрого шифрования.

Не давно дошли наконец руки до программируемой логики. Потребовался быстрый брутфорс некоторого количества кодов, для изучения алгоритма построения ответов одной железки, контроллер которой пока не могу вычитать.
Для начала краткая предыстория.
Я написал алгоритм проверки в VHDL после большого количества исправлений (ругалось при компиляции, все-то им не нравится, то точка с запятой лишняя, то не хватает чего…) собрал, попытался запустить симуляцию… и результатом — какая-то белиберда…два дня мучений и переписывания алгоритма, обогатили меня знаниями в VHDL, но не сдвинули с места результат. тогда я решил пойти от простого к сложному. Уменьшил элементы алгоритма до 4-х бит и оставил всего несколько шагов от самого алгоритма.
И вот теперь мы перейдем к основной части, построение «вычислительной» системы на FPGA (field programmable gate array) или CPLD(Complex Programmable Logic Device), иными словами на программируемой логике.
По сути что у нас используется в алгоритмах шифрования? Сложение, вычитание, сдвиги, и набор логических операторов. Бывает еще табличный метод, но мы его рассматривать не будем. Все эти действия могут быть произведены процессором, а можно для них создать схему на «жесткой» логике. Ну или запрограммировать эту самую схему в кристалле ПЛИС(интегральная схема программируемой логики). И тогда у нас получится аппарат, который в идеале получив на входе исходный блок данных, на выходе тут же дает шифрованный или дешифрованный (смотря какой алгоритм и какой аппарат мы создавали). На самом деле, конечно, не тут же. Все элементы имеют задержку пропускания сигнала, и пока сигнал в цепях схемы не пройдет самый длинный из всех параллельных путей, результат будет не достоверным. Это будет так называемый переходный процесс, и его время будет зависеть от быстродействия ячеек FPGA и сложности алгоритма. Но в любом случае, кроме самых «гротескных» это будет быстрее, чем процессор бы выполнил последовательность всех действий.
для начала создаем элементы, из которых будем собирать нашу «функцию».

library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;

entity element1 is
port(
a,b,c,d : in std_logic_vector(3 downto 0 );
y : out std_logic_vector(3 downto 0 )
);
end entity element1;

architecture h_xor of element1 is
constant cn : unsigned := x"5"; -- cn <= x"5C4DD124"; begin y <= unsigned(a) + cn + unsigned( b xor c xor d ); end architecture h_xor; architecture h_major of element1 is begin y <= unsigned(a) + unsigned( ((b or c) and d) or ( b and c ) ); end architecture h_major;

в самом начале идет "шапка" библиотеки, она указывает какой тип библиотек и синтаксиса используется. Во всех источниках, что я читал, советуют просто скопировать все это, и добавить к use свои библиотеки, если нужно.
Далее мы объявляем что-то вроде интерфейса (entity). Наш интерфейс объявляет элементы с четырьмя, четырехразрядными входами (a,b,c,d) и одним четырехразрядным выходом (y).
После этого объявляем архитектуры требуемых элементов. Первый у нас реализует функцию xor со сложением: y = a + (b ^ c ^ d); А второй мажоритарное или со сложением y = a + maj_or(b, c, d);

Теперь переходим к основному файлу:

library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;

entity tut01 is
port(
x: in std_logic_vector(3 downto 0);
y: out std_logic_vector(3 downto 0)
);
end entity tut01;

architecture tutor of tut01 is
signal s0,s1,s2,s3,s4,s5,s6,s7,s8 : std_logic_vector(3 downto 0);
begin
e1: entity work.element1(h_major) port map( x"1", x"2", x"3", x, s0 );
e2: entity work.element1(h_xor) port map( x"4", x"5",x, s0, s1 );
e3: entity work.element1(h_major) port map( x"6", x, s0, s1, s2 );
e4: entity work.element1(h_xor) port map( x, s0, s1 , s2, s3 );
y <= s3; end architecture tutor;

Ну в области "шапки" и объявления интерфейса, ничего для нас нового нет, а вот в самой архитектуре объекта tutor. пожалуй, кое-что требует объяснения.
во-первых тут используются "переменные", точнее сигналы (s0..s8)
во-вторых тут объявляются "объекты" ранее определенных "типов" (e1..e4).
в третьих у объявленных элементов (объектов) используется порт маппинг (подключение портов, непосредственно при объявлении), причем некоторые порты, изначально "забиваются" шестнадцатиричными константами (x"4", x"6"...).

Далее, я думаю нужны некоторые объяснения. В VHDL, как и в любом языке описания аппаратуры, используется принцип "одновременности" действий. Т.е. все действия происходят одновременно, т.е. если мы пишем что-то вроде:

a <= b + c; b <= c + a;

где в начале a = 1, b = 2, c = 3, то у нас по выполнению этого буде a =5, b = 4; и только на втором проходе b станет равным 8, но при этом a уже будет равно 7...
Если же требуется произвести последовательность действий, то нужно обьявлять процесс, а внутри него вместо <= использовать присвоение, как в паскале :=, но об этом как нибудь в другой раз. Сейчас же, посмотрим что у нас получилось. Для начала схематическая диаграмма полученной функции (иногда помогает увидеть, как можно упростить всю систему в целом, кроме того она удобнее людям привыкшим не к программированию, а к сборке "в железе"). Схематическая диаграмма
Ну и смотрим на результат работы. В качестве параметров при симуляции были заданы случайные числа, подаваемые на вход X.
Симуляция процессов в ПЛИС
Здесь в районе 65 наносекунд, явно видны "всплески" значений вызванных, так называемым переходным процессом. Т.е. когда часть элементов, уже переключилась, на новые значения, а часть еще нет, и это вызывает кратковременные "паразитные" значения на выходе.

Для начала, я думаю будет достаточно. если кому это покажется интересным, то можно скачать с сайта altera.com программу Quartus (рекомендую поискать в сети или спросить у меня версию 9, потому как в более поздней, симуляцию уже исключили и рекомендуют для нее использовать стороннюю программу) и "поиграться". Реально мы смогли добиться при брутфорсе, быстродействия более чем в 100 раз превышающего вычисление той же крипто-функции, на процессоре с частотой 2800 Мгц (имейте ввиду что функция целиком умещается в кеше процессора).

Leave a Reply

Ваш e-mail не будет опубликован. Обязательные поля помечены *