Потоковый интерфейс AXI4: как управлять массивом с плавающей точкой в HLS для генерации ускорителей HW и безопасно подключать их в проекте RTL?
В конце я хочу использовать потоковый интерфейс с массивами с плавающей запятой одинарной точности в Vivado Design Suite для создания аппаратных ускорителей. Руководство пользователя HLS UG902 показывает, что можно создавать ускорители HW (начиная с C, C++, SystemC, код OpenCL) с использованием различных интерфейсов.
Если вы хотите использовать потоковый интерфейс AXI4, HLS синтезирует сигналы TREADY и TVALID, но не синтезирует сигнал TLAST, необходимый для подключения интерфейса RTL, сгенерированного к системе обработки Zynq (в моем случае ядра ARM9). Чтобы решить эту проблему, Xilinx дает вам возможность использовать эту библиотеку
#include "ap_axi_sdata.h"
Внутри есть структура - шаблон:
#include "ap_int.h"
template<int D,int U,int TI,int TD>
struct ap_axis{
ap_int<D> data;
ap_uint<D/8> keep;
ap_uint<D/8> strb;
ap_uint<U> user;
ap_uint<1> last;
ap_uint<TI> id;
ap_uint<TD> dest;
};
У меня две проблемы:
- Если я хочу использовать только TLAST, а не другие, я пытаюсь установить U, TI и TD на ноль, но получаю ошибку.
- Если я хочу использовать "float", а не "ap_int", и я пытаюсь изменить его внутри шаблона, я получаю еще одну ошибку.
Вопрос:
Есть ли простой способ обработки и управления потоковым интерфейсом в HLS с данными с плавающей запятой?
1 ответ
Для меня самый простой способ решить это, это объявить свой собственный тип данных структуры без использования библиотеки, которую вы упомянули выше. По умолчанию VivadoHLS реализует интерфейсы AXIS с сигналами TDATA, TVALID и TREADY. Если вам также нужны TLAST и одноточечные данные одинарной точности, вы должны объявить свой собственный тип данных, который должен выглядеть примерно так:
struct my_data{
float data;
bool last;
};
Я могу привести пример того, как вы должны его использовать:
void my_function(my_data input[25], my_data output[25])
{
#pragma HLS INTERFACE axis port=output
#pragma HLS INTERFACE axis port=input
#pragma HLS INTERFACE s_axilite port=return
float tmp_data;
float tmp_last;
int k=0;
for(k=0;k<25;k++)
{
tmp_data[k] = input[k].data;
tmp_last[k] = input[k].last;
}
for(k=0;k<25;k++)
{
output[k].data = tmp_data[k];
output[k].last = tmp_last[k];
}
}
Если вы сделаете это, после синтеза вы получите такой результат:
Во избежание ошибок вы должны обратить внимание на следующее:всякий раз, когда вы используете данные ваших потоковых интерфейсов, вы должны быть осторожны в управлении остальными сигналами интерфейса.