4 Diseño del sistema desarrollado
4.2 Estructura del target BMv2 implementado
Para facilitar la integración con ARP-Path se ha diseñado un target personalizado mediante el framework BMv2. Como ya se señaló en el apartado 3.6.1, un target BMv2 sobre el que se carga un programa P4 implementa exclusivamente un plano de datos. Es decir, el proceso correspondiente a la ejecución de un switch BMv2 no es capaz por sí mismo de conmutar paquetes. Para ello, es preciso ejecutar un proceso paralelo que implemente el plano de control, ya sea una interfaz de comandos como la que incluye BMv2, o un controlador SDN.
El switch BMv2 podrá encaminar tráfico una vez que el plano de control haya provisionado un estado de reenvío, lo que incluye no sólo la instalación de entradas en tablas, sino también la configuración de sesiones Multicast en el Packet Replication Engine. Tal como se ilustró en el apartado 3.3.1, el PRE es el componente encargado de implementar Multicast mediante la configuración de sesiones que asocian un identificador de grupo Multicast a un conjunto de
55 puertos. Broadcast puede entenderse como una sesión Multicast que tiene asociados todos los puertos del switch (excluyendo, evidentemente el puerto de entrada del paquete).
Por tanto, dado que ARP-Path está basado en la difusión controlada de paquetes, es preciso configurar una sesión Multicast para implementar Broadcast. Sin embargo, se desea que el switch ARP-Path BMv2 pueda funcionar autónomamente en ausencia de plano de control externo, es decir, que no sea necesario lanzar otro proceso distinto al del switch para poder encaminar paquetes. Por ello, el propio target BMv2 debe configurar el PRE al inicializarse, siendo ésta una de las razones que han justificado el uso de un target personalizado.
De forma general, las razones por las que se ha desarrollado un target propio son: La configuración de una sesión Broadcast en el PRE por defecto.
Incluir el extern ARP-Path como un componente disponible para su instanciación en programas P4.
Mejorar la eficiencia en la difusión de paquetes Multicast respecto a otros targets BMv2. Desechar funcionalidades no utilizadas (soporte para colas por prioridad).
Recoger medidas estadísticas (véase el apartado 4.6.1).
De los puntos anteriores, se debe resaltar la implementación de la difusión de paquetes Multicast. BMv2 implementa la difusión de paquetes mediante la transmisión secuencial de cada una de las copias del paquete por puerto. En un sistema hardware, la transmisión se podría realizar en paralelo. El problema en este punto no es la limitación técnica en sí, sino que por defecto el orden de transmisión es estático y está definido por el identificador de puerto. Así, la copia Multicast que primero se envía se corresponde con el puerto cuyo identificador sea menor. En ARP-Path esto implicaría que, a menor identificador de puerto, mayor probabilidad de que el camino se establezca a través de dicho puerto, ya que las copias de un ARP-Request se transmitirían en orden creciente de identificador de puerto. Por ello, se ha implementado un sistema de difusión en el que la transmisión sigue siendo secuencial, pero el orden de transmisión de las copias pasa a ser aleatorio, de tal forma que se facilite la variabilidad de caminos en ARP-Path.
El target desarrollado es un switch BMv2 multihilo, escrito en C++. El target se ha denominado ARP-P4. La arquitectura de ARP-P4 tiene mucho en común con el target l2_switch de BMv2, pero incluye algunas funcionalidades del target simple_switch.
Un target BMv2 es una clase derivada de bm::SwitchWContexts o bien bm::Switch, que a su vez deriva de la primera. bm::SwitchWContexts permitiría crear un target capaz de ejecutar varios programas P4 excluyentes en paralelo , como por ejemplo, un programa P4 para IPv4 y otro para IPv6. En este caso el paquete atravesaría un programa u otro en base su versión de IP. Sin embargo, esta funcionalidad no está implementada todavía, por lo que todos los targets desarrollados hasta el momento derivan de bm::Switch.
Para implementar un target, se requiere, como ya se ha dicho, crear una clase derivada de alguna de las dos referenciadas, e implementar los métodos receive_() y start_and_return_(). El primer método es llamado automáticamente por el componente DevMgr cada vez que se recibe un paquete. Start_and_return_() está pensado para iniciar el procesamiento de paquetes, si bien es opcional implementar esta operación en este método.
56 Tres hilos de procesamiento paralelos para el plano de datos.
Cuatro bloques programables con P4: Parser, Ingreso, Egreso y Deparser Soporte para multicast mediante el componente PRE.
Sesión Multicast para broadcast implementada por defecto.
Soporte para clonación de paquetes en el bloque de control de Ingreso. Compatibilidad con P4Runtime.
La arquitectura P4 empleada es V1Switch, la única disponible para targets P4 a día de hoy, heredando por tanto, el conjunto de metadatos estándar definidos para esta arquitectura, standard_metadata. Existen dos bloques de control, Ingreso y Egreso. Ingreso tiene la funcionalidad genérica de determinar el destino del paquete, mientras que Egreso está pensado para realizar un procesado posterior del paquete una vez ya se ha fijado su destino. Es por ello que el puerto de salida -el metadato standard_metadata.egress_port- únicamente puede modificarse en el bloque de Ingreso, debiendo permanecer inalterado en el de egreso.
En la inicialización de ARP-P4 se configura una sesión multicast en el PRE asociada a todos los puertos a través de la cual se implementa Broadcast. Esto no excluye que el PRE también pueda soportar otras sesiones configuradas mediante P4Runtime.
Se han seguido algunas de las recomendaciones para mejorar el rendimiento expuestas en [26]. Específicamente, se ha balanceado a la distribución de los bloques de control entre los tres hilos asignados al plano de datos. La funcionalidad de los 3 hilos es la siguiente:
El hilo de recepción se encarga de recibir un paquete, llamar al bloque Parser, e introducir el paquete en la cola de entrada, que comunica con el hilo de procesado. El hilo de procesado recoge paquetes de la cola de entrada, y llama a los bloques Ingreso
y Egreso. Si el paquete tiene que ser difundido por varios puertos, mediante el PRE se realizarán tantas copias del paquete como puertos existan para la sesión multicast y cada uno de los paquetes clonados atravesará el bloque de Egreso. Tras atravesar el bloque de Egreso, el paquete se depositará en la cola de salida.
El hilo de transmisión recoge paquetes de la cola de salida, llama al Deparser y lo reenvía por el puerto correspondiente.
Por último, ARP-P4 tiene soporte para P4Runtime, para lo cual se ha adaptado la clase switch_runner disponible en el target simple_switch_grpc. Switch_runner inicializa el servidor P4Runtime, y dispone de soporte para la gestión de mensajes Packet-In y Packet-Out mediante la especificación de un número de puerto que identifica al plano de control P4Runtime. Es habitual emplear el número 255 como identificador de puerto del plano de control, de forma que todos los paquetes dirigidos a este puerto serán interceptados e inyectados al servidor P4Runtime para su envío en un mensaje Packet-In.
La Figura 25 representa la estructura del target ARP-P4, mostrándose la secuencia que siguen los paquetes recibidos, las operaciones Packet-In y Packet-Out, y la localización de los bloques programables mediante P4.
57 Figura 25 Estructura del target BMv2 desarrollado