Comparación del rendimiento del controlador de red en versiones en 10 lenguajes de programación

Un grupo de investigadores de universidades alemanas ha publicado resultados de un experimento, durante el cual se desarrollaron 10 versiones de un controlador típico para tarjetas de red Intel Ixgbe (X5xx) en diferentes lenguajes de programación. El controlador funciona en espacio de usuario y fue implementado en C, Rust, Go, C#, Java, OCaml, Haskell, Swift, JavaScript y Python. Al escribir el código, se prestó especial atención para alcanzar el máximo rendimiento posible, teniendo en cuenta las características de cada lenguaje. En funcionalidad, todas las versiones son idénticas y constan de aproximadamente 1000 líneas de código. Los avances del proyecto se distribuyen bajo licencia BSD.

La versión del controlador en Rust resultó ser muy cercana en rendimiento al controlador de referencia en C. Bajo una carga de envío simultáneo de bloques de 32 paquetes, el controlador en Rust quedó un poco rezagado, pero en pruebas con más de 32 paquetes por bloque, su velocidad prácticamente no difería del controlador en C y mostró un rendimiento de procesamiento de 28 millones de paquetes por segundo en un servidor con CPU Xeon E3-1230 v2 a 3.3 GHz.

Comparación del rendimiento del controlador de red en versiones en 10 lenguajes de programación

La siguiente categoría de rendimiento fue ocupada por los controladores en Go y C#, que mostraron resultados bastante cercanos (el controlador en Go llevó la delantera en pruebas con bloques de hasta 16 paquetes y comenzó a quedar algo rezagado en pruebas con más de 16 paquetes por bloque). Con bloques de 256 paquetes, el rendimiento máximo del controlador en C# fue de aproximadamente 28 millones de paquetes por segundo, mientras que el controlador en Go logró alrededor de 25 millones de paquetes por segundo.

A continuación, con resultados suficientemente cercanos, estaban los controladores en
Java, OCaml y Haskell, que ya quedaban notablemente rezagados respecto a las versiones consideradas anteriormente y no lograron superar la marca de 12 millones de paquetes por segundo. Un mayor rezago se observó en los controladores en Swift y JavaScript, que pudieron procesar flujos a un nivel de 5 millones de paquetes por segundo.

Cerrando la clasificación, el controlador en Python logró procesar solo 0.14 millones de paquetes por segundo. La implementación en Python se utilizó para evaluar la velocidad de funcionamiento de los intérpretes sin JIT y sin optimizaciones específicas (el código se ejecutó utilizando CPython 3.7 y no era compatible con PyPy, pero cabe mencionar que la optimización de las estructuras de almacenamiento de datos podría aumentar el rendimiento aproximadamente 10 veces).

Además, se realizaron pruebas de latencia que mostraron la efectividad del almacenamiento en búfer y el impacto del recolector de basura. Durante las pruebas, se midió la latencia tras la redirección de cada paquete por el controlador en comparación con el tiempo de envío conocido con precisión. Los líderes fueron, una vez más, los controladores en C y Rust, cuyos resultados fueron prácticamente indistinguibles para un flujo de 1 millón de paquetes por segundo (aproximadamente 20 µs). El controlador en Go también se desempeñó bien, quedando solo un poco detrás de los líderes y manteniéndose en torno a los 20 µs. El controlador en C# mostró latencias de aproximadamente 50 µs.
Los mayores retardos fueron mostrados por los controladores en JavaScript y Java (con latencias superiores a 300 µs).

Comparación del rendimiento del controlador de red en versiones en 10 lenguajes de programación

La investigación se llevó a cabo con el objetivo de evaluar la viabilidad del desarrollo de controladores y componentes del sistema operativo en lenguajes de nivel superior a C. Actualmente, 39 de 40 problemas al trabajar con memoria en Linux se deben a controladores, por lo que las cuestiones sobre el uso de un lenguaje más seguro y la extracción de controladores del núcleo al espacio de usuario siguen siendo relevantes y los fabricantes ya están experimentando activamente en esta dirección (por ejemplo, Google desarrolló una pila TCP para el sistema operativo Fuchsia en Go, la empresa CloudFlare implementó el protocolo QUIC en Rust, y Apple trasladó la pila TCP en dispositivos móviles al espacio de usuario). creó A partir del trabajo realizado, se concluyó que el lenguaje Rust es el mejor candidato para el desarrollo de controladores. Las capacidades proporcionadas por Rust permiten eludir los problemas que surgen de la manipulación de memoria de bajo nivel, a costa de una reducción en el rendimiento de aproximadamente el 2%-10% en comparación con los controladores en C. Los lenguajes Go y C# también se consideran adecuados para la creación de componentes del sistema en situaciones donde las latencias a nivel de fracciones de milisegundo, causadas por el uso de un recolector de basura, son aceptables.

Un grupo de investigadores de universidades alemanas publicó los resultados

Fuente: opennet.ru

Compra un hosting fiable para sitios web con protección contra DDoS, servidores VPS VDS 🔥 Compra un hosting fiable para sitios web con protección contra DDoS, servidores VPS VDS | ProHoster