Реализация нейронной сети на FPGA

advertisement
Реализация нейронной сети на FPGA
Автор: Ханов А.Р.<awengar@gmail.com>, СПбГУ, мат-мех,
аспирант
Руководитель: Баклановский М.В.
Нейронные сети широко применяются при решении задач
аппроксимации и распознавания образов. Эти задачи остро стоят и в
информационной безопасности, особенно в таких задачах как распознавание
CAPTCHA, анализ сетевого трафика, обнаружение DOS-атак, разработка
различных IDS и IPS -систем. Увеличение скорости работы нейронных сетей
является важной и актуальной проблемой. Одним из способов, позволяющих
ускорить их работу за счет использования параллелизма, который
свойственен самой нейронной сети, является ее реализация на кристалле.
Существуют различные варианты ее построения, включая реализации на
жестких и гибких кристаллах, с использованием различных типов
параллелизма [1]. В данной работе представлена реализация нейронной сети
на гибком кристалле.
Принципиально разными являются задачи реализации нейронных сетей
с обучением и без обучения. В первом случае нам известна структура сети и
веса синапсов нейронов, необходимо лишь реализовать саму эту сеть и
некоторый входной и выходной интерфейсы. При решении второй задачи
необходимо реализовывать некоторый алгоритм обучения. Нами решалась
первая задача. Необходимо реализовать генератор нейронной сети по ее
описанию на некотором псевдоязыке, в котором указана ее структура и
весовые коэффициенты. Было решено ограничиться структурами нейронной
сети с топологией типа персептрон.
При реализации нейронной сети возможно использование нескольких
типов параллелизма. При этом по-разному будут использованы ресурсы на
кристалле. Нами использовался параллелизм, при котором нейроны на
каждом такте накапливают взвешенную сумму, обрабатывая по одному
значению из предыдущего слоя за такт. Данные между слоями также
передаются последовательно, на каждом такте все нейроны слоя
обрабатывают одно и то же значение. При этом для каждого нейрона
потребуется лишь один умножитель и сумматор, весь слой будет вычислен за
число тактов, равное числу синапсов у каждого нейрона слоя, для всех слоев
кроме первого это число равно числу нейронов в предыдущем слое. В
результате вся нейронная сеть будет вычислена за число тактов, равное числу
нейронов во всех слоях.
Был реализован генератор нейронных сетей на языке Perl. В качестве
описания он принимает XML-файл, в результате получается программа на
языке VHDL, которая реализуют описанную нейронную сеть в виде
компонента.
В процессе реализации было несколько сложностей.
При реализации на процессоре обычно используются типы данных float
или double. Использование этих типов данных на кристалле осложнено тем,
что компоненты, которые проводят операции с этими типами данных,
занимают на кристалле большую площадь. Поэтому было решено
использовать числа с фиксированной точкой. Операции с числами с
фиксированной точкой следует проводить по следующим формулам:
a, p  g , q  ap * 2| p|  gq * 2|q|  (ap  gq) * 2| p| , | p || q |
a, p * g , q  ap * 2| p| * gq * 2|q|  ap * gq * 2| p||q|  ap * gq * 22| p|
Здесь a,g – целые части чисел, p,q – дробные части. При сложении
чисел с фиксированной точкой разрядность результата увеличивается на
единицу. При умножении двух чисел с фиксированной точкой удваивается
число бит в целой и дробной части. В случае переполнения мы записываем
наибольшее возможное число, при умножении мы отбрасываем половину
самых младших бит дробной части. При этом, работая с числами с
фиксированной точкой, мы фактически работаем с целыми числами. Более
подробно про потери точности при вычислениях с фиксированной точкой
можно узнать в [2].
Во-вторых, реализация непрерывной функции активации, сигмоидной
или биполярной, может быть различной. В нашей реализации эта функция
приближалась фиксированным числом значений на заранее определенном
отрезке. Все значения аргумента, лежащие за пределами отрезка,
приближались максимальным или минимальным значениями. Подробнее про
аппроксимацию функций активации можно узнать здесь [1].
Были проведены тесты, которые оценивают потерю точности
результата при различном числе бит в дробной части. Нейронная сеть из 5
нейронов в скрытом слое и одного входного и выходного нейрона была
обучена для приближения функции синуса на отрезке от 0 до 3 Пи по 50
произвольным точкам. Далее был сгенерирован код на VHDL, который
реализовывал данную структуру на кристалле. В таблице показана средняя
квадратическая ошибка вычисления значения функции по 25
последовательным точкам по сравнению с нейросетью, реализованной на
процессоре и использующей тип double для работы.
Таблица 1. Оценка средней квадратической ошибки вычисления по сравнению с реализацией на
процессоре.
Число бит в целой и
дробной части
12,4
12,8
Суммарная кв. ошибка
0,58760
0,38661
12,12
12,16
0,36965
0,36977
По данной таблице видно, что уже при 8 битах на дробную часть
ошибка начинает уменьшаться довольно незначительно.
Был проведен синтез данной нейронной сети при различном
количестве бит в дробной части для кристалла Spartan 3E 1200K. Синтез
проходил на Xilinx ISE 12.1. Результаты показаны в таблице. В первой строке
указано число бит для целой и дробной частей, во второй – период и частота
прошивки для данного кристалла.
Таблица 2. Результаты синтеза
Точность
Период,
частота
12, 4
10.957 нс
91.266 МГц
12, 8
14.401 нс
69.440 МГц
12,12
14.935 нс
66.957 МГц
12,16
15.815 нс
63.231 МГц
12, 20
15.944 нс
62.720 МГц
При точности 4 бита в дробной части нейронная сеть уже выдает
достаточно точные результаты, и при этом она занимает меньше ресурсов на
кристалле. Для тестирования генератора нейронных сетей были реализованы
различные топологии сетей с точностью 12 бит на целую и 4 на дробную
части. Была реализована нейронная сеть с 40 нейронами в скрытых слоях.
Результаты синтеза показаны в таблице. В первом столбце указано число
нейронов в каждом из слоев, первый является входным, последний –
выходным. В остальных столбцах – различные характеристики, получаемые
в результате синтеза.
Таблица 3. Результаты синтеза различных топологий
структура
Период,
частота
4 input LUT
Число умножителей
Slice Flip Flops
90 – 20 –
20 - 10
19.985ns
50.038MHz
8,631(49%)
28(100%)
1,021(5%)
90–10-1010-10 – 10
19.297ns
51.822MHz
5,533(31%)
28(100%)
1,149(6%)
90-40-10
20.493ns
48.797MHz
9,986(57%)
28(100%)
954(5%)
При одинаковом количестве нейронов увеличение числа слоев, по
которым они распределены, приводит к уменьшению занимаемых на
кристалле ресурсов из-за меньшего числа связей между нейронами. Самым
востребованным ресурсом оказываются умножители.
Оценим скорость работы нашей нейронной сети. Для структуры 90-2020-10 мы имеем частоту около 50 МГц, так как наша реализация сети
работает за число тактов, равное числу нейронов в сети, то входной вектор
вычисляется за (90+20+20+10)*20 = 2800 нс = 2,8 мкс. Реализация нейронной
сети из библиотеки AForge.NET вычисляла одно выходное значение за 7.6
мкс.
В результате был написан генератор нейронных сетей для кристалла.
Несмотря на то, что компонент был синтезирован для не самого
современного кристалла, был получен выигрыш в 2.7 раз по скорости по
сравнению с реализацией на С# в библиотеке AForge.NET. При
использовании нашего типа параллелизма возникает возможность
конвейерной обработки, при которой нейросеть вычисляет сразу несколько
значений одновременно. В будущем планируется соединение кристалла с ПК
через шину PCIe как внешнего вычислительного модуля для нейронных
сетей.
Список литературы
[1] FPGA NEUROCOMPUTERS , Amos R. Omondi, Jagath C. Rajapakse,
Mariusz Bajger, FPGA Implementations of Neural Networks, 2006, pp 1-36
[2] J. L. Holt and J. N. Hwang. 1993. Finite-precision error analysis of
neural network hardware implementations. IEEE IEEE Transactions on
Computers, 42(3):280–290
Download