logotipo de intel

Arquitectura del controlador de dispositivo Intel OPAE FPGA Linux

Intel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-producto

Arquitectura del controlador de dispositivo Linux OPAE Intel FPGA

El controlador OPAE Intel FPGA proporciona interfaces para aplicaciones de espacio de usuario para configurar, enumerar, abrir y acceder a aceleradores FPGA en plataformas equipadas con soluciones Intel FPGA y permite funciones de administración a nivel de sistema como reconfiguración de FPGA, administración de energía y virtualización.

Arquitectura de hardware

Desde el punto de vista del sistema operativo view, el hardware FPGA aparece como un dispositivo PCIe normal. La memoria del dispositivo FPGA se organiza mediante una estructura de datos predefinida (Lista de funciones del dispositivo). Las características admitidas por el dispositivo FPGA se exponen a través de estas estructuras de datos, como se ilustra a continuación en la siguiente figura:

Dispositivo PCIe FPGA

Intel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-fig- (1)

El controlador admite PCIe SR-IOV para crear funciones virtuales (VF) que se pueden usar para asignar aceleradores individuales a máquinas virtuales.

Corporación Intel. Reservados todos los derechos. Intel, el logotipo de Intel y otras marcas de Intel son marcas comerciales de Intel Corporation o sus subsidiarias. Intel garantiza el rendimiento de sus productos FPGA y semiconductores según las especificaciones actuales de acuerdo con la garantía estándar de Intel, pero se reserva el derecho de realizar cambios en cualquier producto y servicio en cualquier momento sin previo aviso. Intel no asume ninguna responsabilidad u obligación que surja de la aplicación o el uso de cualquier información, producto o servicio descrito en este documento, excepto que Intel lo acuerde expresamente por escrito. Se recomienda a los clientes de Intel que obtengan la versión más reciente de las especificaciones del dispositivo antes de confiar en cualquier información publicada y antes de realizar pedidos de productos o servicios.

Otros nombres y marcas pueden ser reclamados como propiedad de terceros.

Dispositivo PCIe FPGA virtualizado

Intel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-fig- (2)

Motor de gestión FPGA (FME)
El motor de gestión FPGA realiza gestión térmica y de energía, informes de errores, reconfiguración, informes de rendimiento y otras funciones de infraestructura. Cada FPGA tiene una FME, a la que siempre se accede a través de la Función Física (PF). Las aplicaciones de espacio de usuario pueden adquirir acceso exclusivo a FME usando open() y liberarlo usando close() como usuario privilegiado (root).

Puerto
Un puerto representa la interfaz entre la estructura FPGA estática (el “Administrador de interfaz FPGA (FIM)”) y una región parcialmente reconfigurable que contiene una función de acelerador (AF). El Puerto controla la comunicación desde el software al acelerador y expone funciones como reinicio y depuración. Un dispositivo PCIe puede tener varios puertos y cada puerto puede exponerse a través de un VF asignándolo mediante FPGA_FME_PORT_ASSIGN ioctl en el dispositivo FME.

Unidad de función de acelerador (AF)

  • Se conecta una unidad de función de acelerador (AF) a un puerto y expone una región MMIO de 256 K que se utilizará para registros de control específicos del acelerador.
  • Las aplicaciones de espacio de usuario pueden adquirir acceso exclusivo a una AFU conectada a un puerto usando open() en el dispositivo del puerto y liberarlo usando close().
  • Las aplicaciones de espacio de usuario también pueden utilizar regiones MMIO del acelerador mmap().

Reconfiguración parcial
Como se mencionó anteriormente, los aceleradores se pueden reconfigurar mediante la reconfiguración parcial de una Función de Acelerador (AF) file. La Función de Acelerador (AF) debe haberse generado para el FIM exacto y la región estática objetivo (Puerto) de la FPGA; de lo contrario, la operación de reconfiguración fallará y posiblemente provocará inestabilidad en el sistema. Esta compatibilidad se puede verificar comparando la ID de la interfaz anotada en el encabezado AF con la ID de la interfaz expuesta por el FME a través de sysfs. Esta verificación generalmente la realiza el espacio del usuario antes de llamar al IOCTL de reconfiguración.

Nota:
Actualmente, cualquier programa de software que acceda a la FPGA, incluidos aquellos que se ejecutan en un host virtualizado, debe cerrarse antes de intentar una reconfiguración parcial. Los pasos serían:

  1. Descargar el controlador del invitado.
  2. Desenchufe el VF del huésped
  3. Deshabilitar SR-IOV
  4. Realizar una reconfiguración parcial
  5. Habilitar SR-IOV
  6. Conecte el VF al invitado
  7. Cargue el controlador en el invitado.

Virtualización FPGA
Para permitir el acceso a un acelerador desde aplicaciones que se ejecutan en una VM, el puerto de la AFU respectiva debe asignarse a un VF mediante los siguientes pasos:

  1. El PF posee todos los puertos AFU de forma predeterminada. Cualquier puerto que deba reasignarse a un VF primero debe liberarse del PF a través del ioctl FPGA_FME_PORT_RELEASE en el dispositivo FME.
  2. Una vez que se liberan N puertos del PF, el siguiente comando se puede usar para habilitar SRIOV y VF. Cada VF posee sólo un puerto con AFU. eco N > PCI_DEVICE_PATH/sriov_numvfs
  3. Pase los VF a las VM.
  4. Se puede acceder a la AFU en VF desde aplicaciones en VM (usando el mismo controlador dentro de VF).

Nota:
Una FME no puede asignarse a un VF, por lo tanto, PR y otras funciones de gestión sólo están disponibles a través del PF.

Organización del conductor

Controlador de dispositivo del módulo PCIe

Organización del conductor

Intel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-fig- (3)

Los dispositivos FPGA aparecen como dispositivos PCIe normales; por lo tanto, el controlador del dispositivo FPGA PCIe (intel-FPGA-PCI.ko) siempre se carga primero una vez que se detecta un FPGA PCIe PF o VF. Este controlador desempeña un papel infraestructural en la arquitectura del controlador. Él:

  • Crea un dispositivo contenedor FPGA como padre de los dispositivos de funciones.
  • Recorre la lista de funciones de dispositivos, que se implementa en la memoria BAR del dispositivo PCIe, para descubrir dispositivos de funciones y sus subcaracterísticas y crear dispositivos de plataforma para ellos bajo el dispositivo contenedor.
  • Soporta SR-IOV.
  • Presenta la infraestructura del dispositivo de funciones, que abstrae las operaciones de las subfunciones y expone funciones comunes a los controladores de dispositivos de funciones.

Funciones del controlador del dispositivo del módulo PCIe

  • Contiene descubrimiento de PCIe, enumeración de dispositivos y descubrimiento de funciones.
  • Crea directorios sysfs para el dispositivo principal, FPGA Management Engine (FME) y Puerto.
  • Crea las instancias del controlador de plataforma, lo que hace que el kernel de Linux cargue sus respectivos controladores de módulo de plataforma.

Controlador de dispositivo del módulo de plataforma FME

  • Gestión térmica y de energía, informes de errores, informes de rendimiento y otras funciones de infraestructura. Puede acceder a estas funciones a través de interfaces sysfs expuestas por el controlador FME.
  • Reconfiguración Parcial. El controlador FME registra un administrador FPGA durante la inicialización de la subfunción PR; una vez que recibe un ioctl FPGA_FME_PORT_PR de su parte, invoca la función de interfaz común de FPGA Manager para completar la reconfiguración parcial del flujo de bits al puerto dado.
  • Gestión de puertos para virtualización. El controlador FME introduce dos ioctls, FPGA_FME_PORT_RELEASE, que libera el puerto dado de PF; y FPGA_FME_PORT_ASSIGN, que asigna el puerto nuevamente a PF. Una vez que el puerto se libera del PF, se puede asignar al VF a través de las interfaces SR-IOV proporcionadas por el controlador PCIe. Para obtener más información, consulte "Virtualización FPGA".

Funciones del controlador de dispositivo del módulo de plataforma FME

  • Crea el nodo del dispositivo de caracteres FME.
  • Crea el sysfs FME files e implementa el sistema FME file accesores.
  • Implementa los subcontroladores de funciones privadas de FME.
  • Subcontroladores de funciones privadas de FME:
    • Encabezado FME
    • Gestión térmica
    • Gestión de energía
    • Error global
    • Reconfiguración parcial
    • Rendimiento mundial

Controlador de dispositivo del módulo de plataforma portuaria
De manera similar al controlador FME, el controlador del puerto FPGA (y AFU) (intel-fpga-afu.ko) se prueba una vez que se crea el dispositivo de plataforma del puerto. La función principal de este módulo es proporcionar una interfaz para que las aplicaciones del espacio de usuario accedan a los aceleradores individuales, incluido el control de reinicio básico en el puerto, la exportación de la región AFU MMIO, el servicio de mapeo del búfer DMA, la notificación UMsg(1) y funciones de depuración remota ( véase más arriba).

UMsg solo se admite a través de Acceleration Stack para el procesador Intel Xeon® con FPGA integrada.

Funciones del controlador de dispositivo del módulo de plataforma portuaria

  • Crea el nodo del dispositivo de carácter de puerto.
  • Crea el puerto sysfs files e implementa el Port sysfs file accesores.
  • Implementa los subcontroladores de funciones privadas del puerto.
  • Subcontroladores de funciones privadas de puerto:
    • Encabezado de puerto
    • AFU
    • Error de puerto
    • UMsg(2)
    • Grifo de señal

Aplicación Enumeración de dispositivos FPGA
Esta sección presenta cómo las aplicaciones enumeran el dispositivo FPGA de la jerarquía sysfs en /sys/class/fpga. en el exampEn el siguiente archivo, hay dos dispositivos Intel FPGA instalados en el host. Cada dispositivo FPGA tiene un FME y dos puertos (AFU). Para cada dispositivo FPGA, se crea un directorio de dispositivos en /sys/class/fpga:

/sys/class/fpga/intel-fpga-dev.0
/sys/class/fpga/intel-fpga-dev.1

Cada nodo tiene un FME y dos Puertos (AFU) como dispositivos secundarios:
/sys/class/fpga/intel-fpga-dev.0/intel-fpga-fme.0
/sys/class/fpga/intel-fpga-dev.0/intel-fpga-port.0
/sys/class/fpga/intel-fpga-dev.0/intel-fpga-port.1
/sys/class/fpga/intel-fpga-dev.1/intel-fpga-fme.1
/sys/class/fpga/intel-fpga-dev.1/intel-fpga-port.2
/sys/class/fpga/intel-fpga-dev.1/intel-fpga-port.3

En general, las interfaces FME/Port sysfs se denominan de la siguiente manera:
/sys/class/fpga/intel-fpga-dev.i/intel-fpga-fme.j/
/sys/class/fpga/intel-fpga-dev.i/intel-fpga-port.k/

con I numerando consecutivamente todos los dispositivos contenedores, j numerando consecutivamente las FME y k numerando consecutivamente todos los Puertos.

Se puede hacer referencia a los nodos de dispositivo utilizados para ioctl() y mmap() a través de:
/dev/intel-fpga-fme.j
/dev/intel-fpga-port.k

Enumeración de controladores PCIe
Esta sección da unview del flujo de código para la enumeración de dispositivos realizado por intel-fpga-pci.ko. Se resaltan las principales estructuras y funciones de datos. Es mejor seguir esta sección cuando viewusando el código fuente adjunto (pcie.c).

Estructuras de datos de enumeración

enumeración fpga_id_type {
IDENTIFICACIÓN DE LOS PADRES,
FME_ID,
PUERTO_ID,
FPGA_ID_MAX
};
estructura estática idr fpga_ids[FPGA_ID_MAX];
estructura fpga_chardev_info {
const char * nombre;
dev_t devt;
};
estructura fpga_chardev_info fpga_chrdevs[] = {
{ .nombre = FPGA_FEATURE_DEV_FME },
{ .nombre = FPGA_FEATURE_DEV_PORT },
};
clase de estructura estática *fpga_class;
estructura estática pci_device_id cci_pcie_id_tbl[] = {
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_RCiEP0_MCP),},
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_VF_MCP),},
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_RCiEP0_SKX_P),},
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_VF_SKX_P),},
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_RCiEP0_DCP),},
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCIe_DEVICE_ID_VF_DCP),},
{0,}
};
estructura estática pci_driver cci_pci_driver = {
.nombre = DRV_NAME,
.id_table = cci_pcie_id_tbl,
.sonda = cci_pci_probe,
.remove = cci_pci_remove,
.sriov_configure = cci_pci_sriov_configure
};
estructura cci_drvdata {
int dispositivo_id;
dispositivo de estructura *fme_dev;
estructura de bloqueo mutex;
estructura list_head port_dev_list;
int número_puerto_liberado;
struct list_head regiones;
};
estructura build_feature_devs_info {
estructura pci_dev *pdev;
void __iomem *ioaddr;
void __iomem *ioend;
int barra_actual;
vacío __iomem *pfme_hdr;
dispositivo de estructura *parent_dev;
estructura plataforma_dispositivo *feature_dev;
};

Flujo de enumeración

  • ccidrv_init()
    • Inicialice fpga_ids usando idr_init().
    • Inicialice fpga_chrdevs[i].devt usando alloc_chrdev_region().
    • Inicialice fpga_class usando class_create().
    • pci_register_driver(&cci_pci_driver);
  • cci_pci_probe()
    • Habilite el dispositivo PCI, solicite acceso a sus regiones, configure el modo maestro PCI y configure DMA.
  • cci_pci_create_feature_devs() build_info_alloc_and_init()
    • Asigne una estructura build_feature_devs_info, inicialícela.
      .parent_dev está configurado en un directorio sysfs principal (intel-fpga-dev.id) que contiene los directorios FME y Port sysfs.
  • parse_feature_list()
    • Recorra la lista de funciones del dispositivo BAR0 para descubrir el FME, el puerto y sus funciones privadas.
  • parse_feature() parse_feature_afus() parse_feature_fme()
    • Cuando se encuentra una FME:
  • build_info_create_dev()
    • Asigne un dispositivo de plataforma para FME y guárdelo en build_feature_devs_info.feature_dev.
    • feature_dev.id se inicializa con el resultado de idr_alloc(fpga_ids[FME_ID],
    • feature_dev.parent está configurado en build_feature_devs_info.parent_dev.
    • Asigne una variedad de recursos de estructura en feature_dev.resource.
  • Asigne una estructura feature_platform_data, inicialícela y almacene un puntero en feature_dev.dev.platform_data
    • create_feature_instance() build_info_add_sub_feature()
    • Inicialice feature_dev.resource[FME_FEATURE_ID_HEADER].
    • feature_platform_data_add()
    • Inicialice feature_platform_data.features[FME_FEATURE_ID_HEADER], todo menos .fops.
  • parse_feature() parse_feature_afus() parse_feature_port()
    • Cuando se encuentra un puerto:
  • build_info_create_dev()
    • Asigne un dispositivo de plataforma para el puerto y guárdelo en build_feature_devs_info.feature_dev.
    • feature_dev.id se inicializa con el resultado de idr_alloc(fpga_ids[PORT_ID],
    • feature_dev.parent está configurado en build_feature_devs_info.parent_dev.
    • Asigne una matriz de recursos de estructura en feature_dev.resource.
    • Asigne una estructura feature_platform_data, inicialícela y almacene un puntero en feature_dev.dev.platform_data
  • build_info_commit_dev()
    • Agregue la estructura feature_platform_data.node para el puerto a la lista de puertos en la estructura cci_drvdata.port_dev_list
  • create_feature_instance() build_info_add_sub_feature()
    • Inicialice feature_dev.resource[PORT_FEATURE_ID_HEADER].
  • feature_platform_data_add()
    • Inicialice feature_platform_data.features[PORT_FEATURE_ID_HEADER], todo menos .fops.
  • parse_feature() parse_feature_afus() parse_feature_port_uafu()
    • Cuando se encuentra una AFU:
  • create_feature_instance() build_info_add_sub_feature()
    • Inicialice feature_dev.resource[PORT_FEATURE_ID_UAFU].
  • feature_platform_data_add()
    • Inicialice feature_platform_data.features[PORT_FEATURE_ID_UAFU], todo menos .fops.
  • parse_feature() parse_feature_private() parse_feature_fme_private()
    • Cuando se encuentra una característica privada de FME:
  • create_feature_instance() build_info_add_sub_feature()
    • Inicialice feature_dev.resource[id].
  • feature_platform_data_add()
    • Inicialice feature_platform_data.features[id], todo menos .fops.
  • parse_feature() parse_feature_private() parse_feature_port_private()
  • Cuando se encuentra una característica privada de Puerto: * create_feature_instance() build_info_add_sub_feature() * Inicializa feature_dev.resource[id]. * feature_platform_data_add() Inicializa feature_platform_data.features[id], todo menos .fops.
  • parse_ports_from_fme()
    • Si el controlador está cargado en la función física (PF), entonces:
  • Ejecute el flujo parse_feature_list() en cada puerto descrito en el encabezado FME.
  • Utilice la BARRA mencionada en cada entrada de Puerto en el encabezado.

Inicialización del dispositivo de la plataforma FME
Esta sección da unview del flujo de código para la inicialización del dispositivo FME realizado por intel-fpga-fme.ko. Las principales estructuras y funciones de datos están resaltadas. Es mejor seguir esta sección cuando viewusando el código fuente adjunto (fme-main.c).

Estructuras de datos de dispositivos de la plataforma FME

estructura feature_ops {
int (*init)(struct platform_device *pdev, característica de estructura *característica);
int (*uinit)(struct platform_device *pdev, característica de estructura *característica);
long (*ioctl)(struct platform_device *pdev, característica de estructura *característica,
unsigned int cmd, unsigned long arg);
int (*prueba)(struct platform_device *pdev, característica de estructura *característica);
};
característica de estructura {
const char * nombre;
int índice_recurso;
void __iomem *ioaddr;
estructura feature_ops *ops;
};
estructura feature_platform_data {
struct list_head nodo;
estructura de bloqueo mutex;
dev_status largo sin firmar;
estructura cdev cdev;
estructura plataforma_dispositivo *dev;
unsigned int enable_count;
vacío *privado;
int num;
int (*config_port)(struct platform_device *, u32, bool);
estructura plataforma_dispositivo *(*fpga_for_each_port)(estructura plataforma_dispositivo *,
void *, int (*match)(struct platform_device *, void *)); estructura
características características[0];
};
estructura perf_object {
identificación interna;
const estructura atributo_group **attr_groups;
dispositivo de estructura *fme_dev;
struct list_head nodo;
struct list_head niños;
estructura kobject kobj;
};
estructura fpga_fme {
u8 puerto_id;
u64 pr_err;
dispositivo de estructura *dev_err;
estructura perf_object *perf_dev;
estructura feature_platform_data *pdata;
};

Flujo de inicialización del dispositivo de la plataforma FME

Flujo de inicialización de FMEIntel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-fig- (4)

  • fme_probe()fme_dev_init()
    • Inicialice una estructura fpga_fme y guárdela en el campo feature_platform_data.private.
  • fme_probe() fpga_dev_feature_init() característica_instancia_init()
    • Guarde una estructura feature_ops en feature_platform_data.features para cada característica completa.
    • Llame a la función de prueba, si corresponde, desde la estructura.
    • Llame a la función init desde la estructura.
  • fme_probe()fpga_register_dev_ops()
    • Cree el nodo del dispositivo de caracteres FME, registrando una estructura file_operaciones.

Inicialización del dispositivo de plataforma portuaria
Esta sección da unview del flujo de código para la inicialización del dispositivo portuario realizado por intel-fpga-afu.ko. Se resaltan las principales estructuras y funciones de datos. Es mejor seguir esta sección cuando viewusando el código fuente adjunto (afu.c).

Estructuras de datos de dispositivos de plataforma portuaria

estructura feature_ops {
int (*init)(struct platform_device *pdev, característica de estructura *característica);
int (*uinit)(struct platform_device *pdev, característica de estructura *característica);
long (*ioctl)(struct platform_device *pdev, característica de estructura *característica,
unsigned int cmd, unsigned long arg);
int (*prueba)(struct platform_device *pdev, característica de estructura *característica);
};
característica de estructura {
const char * nombre;
int índice_recurso;
void __iomem *ioaddr;
estructura feature_ops *ops;
};
estructura feature_platform_data {
struct list_head nodo;
estructura de bloqueo mutex;
dev_status largo sin firmar;
estructura cdev cdev;
estructura plataforma_dispositivo *dev;
unsigned int enable_count;
vacío *privado;
int num;
int (*config_port)(struct platform_device *, u32, bool);
estructura plataforma_dispositivo *(*fpga_for_each_port)(estructura plataforma_dispositivo *,
void *, int (*match)(struct platform_device *, void *));
características de estructura de estructura [0];
};
estructura fpga_afu_region {
índice u32;
banderas u32;
tamaño u64;
desplazamiento u64;
u64 físico;
struct list_head nodo;
};
estructura fpga_afu_dma_region {
u64 dirección_usuario;
longitud u64;
u64 iova;
página de estructura **páginas;
estructura rb_node nodo;
bool en uso;
};
estructura fpga_afu {
u64 región_cur_offset;
int núm_regiones;
u8 num_umsgs;
struct list_head regiones;
estructura rb_root dma_regions;
estructura feature_platform_data *pdata;
};

Flujo de inicialización del dispositivo de plataforma portuaria

Flujo de inicialización de puertoIntel-OPAE-FPGA-Linux-Device-Driver-Arquitectura-fig- (5)

  • afu_probe() afu_dev_init()
    • Inicialice una estructura fpga_afu y guárdela en el campo feature_platform_data.private.
  • afu_probe() fpga_dev_feature_init() característica_instancia_init()
    • Guarde una estructura feature_ops en feature_platform_data.features para cada característica completa.
    • Llame a la función de prueba, si corresponde, desde la estructura.
    • Llame a la función init desde la estructura.
  • afu_probe()fpga_register_dev_ops()
    • Cree el nodo del dispositivo de carácter de puerto, registrando una estructura file_operaciones.

FME IOCTL
IOCTL que se llaman en un abierto file descriptor para /dev/intel-fpga-fme.j FPGA_GET_API_VERSION: devuelve la versión actual como un número entero, comenzando desde 0.

FPGA_CHECK_EXTENSION: no compatible actualmente.

FPGA_FME_PORT_RELEASE: arg es un puntero a:

estructura fpga_fme_port_release {
__u32 argsz; // en: tamaño de (struct fpga_fme_port_release)
banderas __u32; // en: debe ser 0
__u32 puerto_id; // en: ID de puerto (de 0) a liberar.
};

FPGA_FME_PORT_ASSIGN—arg es un puntero a:

estructura fpga_fme_port_assign {
__u32 argsz; // en: tamaño de (struct fpga_fme_port_assign)
banderas __u32; // en: debe ser 0
__u32 puerto_id; // en: ID del puerto (desde 0) a asignar. (debe haber sido
publicado previamente por FPGA_FME_PORT_RELEASE)
};

FPGA_FME_PORT_PR—arg es un puntero a:

estructura fpga_fme_port_pr {
__u32 argsz; // en: tamaño de (struct fpga_fme_port_pr)
banderas __u32; // en: debe ser 0
__u32 puerto_id; // en: ID de puerto (desde 0)
__u32 tamaño_búfer; // en: tamaño del buffer de flujo de bits en bytes. Debe ser de 4 bytes
alineado.
__u64 dirección_búfer; // en: dirección de proceso del buffer de flujo de bits
estado __u64; // salida: estado de error (máscara de bits)
};

Puerto IOCTL
IOCTL que se llaman en un abierto file descriptor de /dev/intel-fpga-port.k FPGA_GET_API_VERSION: devuelve la versión actual como un número entero, comenzando desde 0. FPGA_CHECK_EXTENSION: no compatible actualmente.

FPGA_PORT_GET_INFO—arg es un puntero a:

estructura fpga_port_info {
__u32 argsz; // en: tamaño de (struct fpga_port_info)
banderas __u32; // salida: devuelve 0
__u32 num_regions; // salida: número de regiones MMIO, 2 (1 para AFU y 1 para
STP)
__u32 num_umsgs; // salida: número de UMsg admitidos por el hardware
};

FPGA_PORT_GET_REGION_INFO: arg es un puntero a:

estructura fpga_port_region_info {
__u32 argsz; // en: tamaño de (struct fpga_port_region_info)
banderas __u32; // salida: (máscara de bits) { FPGA_REGION_READ, FPGA_REGION_WRITE,
FPGA_REGION_MMAP}
índice __u32; // en: FPGA_PORT_INDEX_UAFU o FPGA_PORT_INDEX_STP
relleno __u32; // en: debe ser 0
tamaño __u64; // salida: tamaño de la región MMIO en bytes
__u64 compensado; // salida: desplazamiento de la región MMIO desde el inicio del dispositivo fd
};

FPGA_PORT_DMA_MAP—arg es un puntero a:
estructura fpga_port_dma_map {
__u32 argsz; // en: tamaño de (struct fpga_port_dma_map)
banderas __u32; // en: debe ser 0 __u64 user_addr; // en: proceso virtual
DIRECCIÓN. Debe estar alineado con la página.
__u64 longitud; // en: longitud del mapeo en bytes. Debe ser un múltiplo de la página.
tamaño.
__u64 iova; // salida: dirección virtual IO };

FPGA_PORT_DMA_UNMAP—arg es un puntero a:
estructura fpga_port_dma_unmap {
__u32 argsz; // en: tamaño de (struct fpga_port_dma_unmap)
banderas __u32; // en: debe ser 0
__u64 iova; // en: dirección virtual IO devuelta por un anterior
FPGA_PORT_DMA_MAP};

  • FPGA_PORT_RESET: el argumento debe ser NULL.
  • FPGA_PORT_UMSG_ENABLE: el argumento debe ser NULL.
  • FPGA_PORT_UMSG_DISABLE: los argumentos deben ser NULL.

FPGA_PORT_UMSG_SET_MODE—arg es un puntero a:

estructura fpga_port_umsg_cfg {
__u32 argsz; // en: tamaño de (struct fpga_port_umsg_cfg)
banderas __u32; // en: debe ser 0
__u32 sugerencia_bitmap; // en: mapa de bits del modo de sugerencia UMsg. Significa qué UMsg son
activado.
};

FPGA_PORT_UMSG_SET_BASE_ADDR—

  • UMsg debe desactivarse antes de emitir este ioctl.
  • El campo iova debe ser para un búfer lo suficientemente grande para todos los UMsg (num_umsgs * PAGE_SIZE).
    • La gestión del búfer del conductor marca el búfer como "en uso".
    • Si iova es NULL, cualquier región anterior se desmarca como "en uso".
  • arg es un puntero a:
    estructura fpga_port_umsg_base_addr {
    • u32 argsz; // en: tamaño de (struct fpga_port_umsg_base_addr)
    • banderas u32; // en: debe ser 0
    • u64 iova; // en: dirección virtual IO de FPGA_PORT_DMA_MAP. };

Nota:

  • Para borrar los errores del puerto, debe escribir la máscara de bits exacta de los errores actuales, por ejemploample, errores de gato > borrar
  • UMsg solo se admite a través de Acceleration Stack para el procesador Intel Xeon con FPGA integrada.

sistemas de archivos sysf Files

Sistemas de encabezado FME files
Intel-fpga-dev.i/intel-fpga-fme.j/

sistemas de archivos sysf file campo mmio tipo acceso
núm_puertos fme_header.capability.num_ports entero decimal Sólo lectura
tamaño de caché fme_header.capability.cache_size entero decimal Sólo lectura
versión fme_header.capability.fabric_verid entero decimal Sólo lectura
id_socket fme_header.capability.socket_id entero decimal Sólo lectura
bitstream_id fme_header.bitstream_id hexadecimal uint64_t Sólo lectura
bitstream_metadatos fme_header.bitstream_md hexadecimal uint64_t Sólo lectura

Sistemas de gestión térmica FME files
intel-fpga-dev.i/intel-fpga-fme.j/thermal_mgmt/

sistemas de archivos sysf file campo mmio tipo acceso
umbral1 umbral.térmico.tmp_thshold1 entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura
umbral2 umbral.térmico.tmp_thshold2 entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura
umbral_viaje umbral.térmico.therm_trip_thshold entero decimal Sólo lectura
umbral1_alcanzado umbral.térmico.thshold1_status entero decimal Sólo lectura
umbral2_alcanzado umbral.térmico.thshold2_status entero decimal Sólo lectura
umbral1_política térmico. umbral.thshold_policy entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura
temperatura termal.rdsensor_fm1.fpga_temp entero decimal Sólo lectura

Sistemas de administración de energía FME files
intel-fpga-dev.i/intel-fpga-fme.j/power_mgmt/

sistemas de archivos sysf file campo mmio tipo acceso
consumado potencia.status.pwr_consumed hexadecimal uint64_t Sólo lectura
umbral1 umbral.de.potencia.umbral1 hexadecimal uint64_t Usuario: Sólo lectura Raíz: Lectura-escritura
umbral2 umbral.de.potencia.umbral2 hexadecimal uint64_t Usuario: Sólo lectura Raíz: Lectura-escritura
umbral1_status potencia.umbral.umbral1_status decimal sin signo Sólo lectura
umbral2_status potencia.umbral.umbral2_status decimal sin signo Sólo lectura
derecho power.status.fpga_latency_report decimal sin signo Sólo lectura

Error global de FME sysfs files
intel-fpga-dev.i/intel-fpga-fme.j/errors/

sistemas de archivos sysf file campo mmio tipo acceso
pcie0_errores gerror.pcie0_err hexadecimal uint64_t Leer escribir
pcie1_errores gerror.pcie1_err hexadecimal uint64_t Leer escribir
inyectar_error gerror.ras_error_inj hexadecimal uint64_t Leer escribir

intel-fpga-dev.i/intel-fpga-fme.j/errors/fme-errors/

sistemas de archivos sysf file campo mmio tipo acceso
errores gerror.fme_err hexadecimal uint64_t Sólo lectura
primer_error gerror.fme_first_err.err_reg_status hexadecimal uint64_t Sólo lectura
siguiente_error gerror.fme_next_err.err_reg_status hexadecimal uint64_t Sólo lectura
claro Borra errores, first_error, next_error varios uint64_t Escribir solamente

Nota:
Para borrar los errores de FME, debe escribir la máscara de bits exacta de los errores actuales, por ejemploamperrores del gato > borrar.

Sistemas de reconfiguración parcial de FME files
intel-fpga-dev.i/intel-fpga-fme.j/pr/

sistemas de archivos sysf file campo mmio tipo acceso
id_interfaz pr.fme_pr_intfc_id0_h, pr.fme_pre_intfc_id0_l hexadecimal de 16 bytes Sólo lectura

Sistemas de rendimiento global de FME files
Intel-fpga-dev.i/intel-fpga-fme.j/dperf/clock

sistemas de archivos sysf file campo mmio tipo acceso
reloj gperf.clk.afu_interf_clock hexadecimal uint64_t Sólo lectura

intel-fpga-dev.i/intel-fpga-fme.j/dperf/cache/ (No válido para Acceleration Stack para CPU Intel Xeon con FPGA)

sistemas de archivos sysf file campo mmio tipo acceso
congelar gperf.ch_ctl.freeze entero decimal Leer escribir
leer_hit gperf.CACHE_RD_HIT hexadecimal uint64_t Sólo lectura
leer_miss gperf.CACHE_RD_MISS hexadecimal uint64_t Sólo lectura
escribir_hit gperf.CACHE_WR_HIT hexadecimal uint64_t Sólo lectura
escribir_miss gperf.CACHE_WR_MISS hexadecimal uint64_t Sólo lectura
solicitud_retención gperf.CACHE_HOLD_REQ hexadecimal uint64_t Sólo lectura
tx_req_stall gperf.CACHE_TX_REQ_STALL hexadecimal uint64_t Sólo lectura
sistemas de archivos sysf file campo mmio tipo acceso
rx_req_stall gperf.CACHE_RX_REQ_STALL hexadecimal uint64_t Sólo lectura
contención_puerto_escritura_datos gperf.CACHE_DATA_WR_PORT_CONTEN hexadecimal uint64_t Sólo lectura
tag_write_port_contention gperf.CACHE_TAG_WR_PORT_CONTEN hexadecimal uint64_t Sólo lectura

intel-fpga-dev.i/intel-fpga-fme.j/dperf/iommu/ (No válido para Acceleration Stack para CPU Intel Xeon con FPGA)

sistemas de archivos sysf file campo mmio tipo acceso
congelar gperf.vtd_ctl.freeze entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura

intel-fpga-dev.i/intel-fpga-fme.j/dperf/iommu/afuk/ (No válido para Acceleration Stack para CPU Intel Xeon con FPGA)

sistemas de archivos sysf file campo mmio tipo acceso
transacción_lectura gperf.VTD_AFU0_MEM_RD_TRANS hexadecimal uint64_t Sólo lectura
escritura_transacción gperf.VTD_AFU0_MEM_WR_TRANS hexadecimal uint64_t Sólo lectura
tlb_read_hit gperf.VTD_AFU0_TLB_RD_HIT hexadecimal uint64_t Sólo lectura
tlb_write_hit gperf.VTD_AFU0_TLB_WR_HIT hexadecimal uint64_t Sólo lectura

intel-fpga-dev.i/intel-fpga-fme.j/dperf/fabric/

sistemas de archivos sysf file campo mmio tipo acceso
permitir gperf.fab_ctl.(habilitado) entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura
congelar gperf.fab_ctl.freeze entero decimal Usuario: Sólo lectura Raíz: Lectura-escritura
pcie0_read gperf.FAB_PCIE0_RD hexadecimal uint64_t Sólo lectura
pcie0_write gperf.FAB_PCIE0_WR hexadecimal uint64_t Sólo lectura
pcie1_read gperf.FAB_PCIE1_RD hexadecimal uint64_t Sólo lectura
pcie1_write gperf.FAB_PCIE1_WR hexadecimal uint64_t Sólo lectura
upi_read gperf.FAB_UPI_RD hexadecimal uint64_t Sólo lectura
upi_write gperf.FAB_UPI_WR hexadecimal uint64_t Sólo lectura

intel-fpga-ev.i/intel-fpga/fme.j/dperf/fabric/portk/

sistemas de archivos sysf file campo mmio tipo acceso
pcie0_read gperf.FAB_PCIE0_RD hexadecimal uint64_t Sólo lectura
pcie0_write gperf.FAB_PCIE0_WR hexadecimal uint64_t Sólo lectura
pcie1_read gperf.FAB_PCIE1_RD hexadecimal uint64_t Sólo lectura
pcie1_write gperf.FAB_PCIE1_WR hexadecimal uint64_t Sólo lectura
upi_read gperf.FAB_UPI_RD hexadecimal uint64_t Sólo lectura
upi_write gperf.FAB_UPI_WR hexadecimal uint64_t Sólo lectura

Sistemas de encabezado de puerto files
intel-fpga-dev.i/intel-fpga-port.k/

sistemas de archivos sysf file campo mmio tipo acceso
id encabezado_puerto.capacidad.número_puerto entero decimal Sólo lectura
largo port_header.control.latency_tolerance entero decimal Sólo lectura

Puerto AFU encabezado sysfs files
intel-fpga-dev.i/intel-fpga-port.k/

sistemas de archivos sysf file campo mmio tipo acceso
afu_id afu_header.guid hexadecimal de 16 bytes Sólo lectura

Error de puerto sysfs files
intel-fpga-dev.i/intel-fpga-port.k/errors/

sistemas de archivos sysf file campo mmio tipo acceso
errores perror.port_error hexadecimal uint64_t Sólo lectura
primer_error perror.port_first_error hexadecimal uint64_t Sólo lectura
first_malformed_req perror.malreq hexadecimal de 16 bytes Sólo lectura
claro perror.(todos los errores) varios uint64_t Escribir solamente

Nota:
Para borrar los errores de puerto, debe escribir la máscara de bits exacta de los errores actuales, por ejemploamperrores del gato > borrar.

Historial de revisiones

Versión del documento Cambios
2017.10.02 Lanzamiento inicial.

Guía de arquitectura del controlador de dispositivo Linux OPAE Intel FPGA

Documentos / Recursos

Arquitectura del controlador de dispositivo Intel OPAE FPGA Linux [pdf] Guía del usuario
OPAE FPGA Arquitectura de controlador de dispositivo Linux, OPAE FPGA, Arquitectura de controlador de dispositivo Linux, Arquitectura de controlador, Arquitectura

Referencias

Deja un comentario

Su dirección de correo electrónico no será publicada. Los campos obligatorios están marcados *