En noviembre del 2022, la Agencia de Seguridad Nacional de EE. UU. emitió un informe sobre la seguridad en la gestión de la memoria RAM. Si te fijas en otros informes de la NSA sobre el tema, notarás que se centran en el cifrado de datos o la protección del ciclo de producción y otros problemas organizativos, por lo que dirigirse directamente a los desarrolladores de software es un movimiento bastante inusual para la agencia. Esto podría dar a pensar que se trata de algo particularmente importante. Básicamente, la NSA está instando a los desarrolladores de software a cambiar a lenguajes de programación cuya arquitectura implique una mayor seguridad a la hora de trabajar con la memoria; y dejar de usar C y C++. De lo contrario, se recomienda implementar un conjunto de medidas para probar el software en busca de vulnerabilidades y evitar su explotación.
Para los programadores, esto es algo bastante obvio, por lo que la llamada de la NSA no está dirigida directamente a ellos, sino a la gerencia o representantes comerciales. De hecho, la redacción está claramente centrada en las empresas. A continuación, trataremos de analizar los argumentos presentados sin ser demasiado técnicos.
La seguridad de la memoria
Abramos nuestro último Informe sobre la evolución de las amenazas en el tercer trimestre del 2022 y echemos un vistazo a las vulnerabilidades más utilizadas en los ciberataques.
En primera línea, sigue estando la vulnerabilidad CVE-2018-0802 en el componente Editor de ecuaciones del paquete Microsoft Office, descubierta en el 2018. Un procesamiento de datos incorrecto en la RAM, da como resultado la apertura de un documento malicioso de Microsoft Word que podría llevar al lanzamiento de código arbitrario.
Otra vulnerabilidad popular entre los delincuentes es la CVE-2022-2294 en el componente WebRTC del navegador Google Chrome que conduce a la ejecución de código arbitrario como resultado de un error de desbordamiento de búfer.
Otra vulnerabilidad, la CVE-2022-2624, ubicada en la herramienta de visualización de PDF de Chrome, también puede provocar un desbordamiento de búfer.
Por supuesto, no todas las vulnerabilidades de software se producen por causa de una gestión insegura de la RAM, pero muchas de ellas sí. El informe de la NSA cita las estadísticas de Microsoft de que los errores en la gestión de la memoria causan el 70 % de las vulnerabilidades descubiertas.
¿Por qué pasa esto? Si el problema de las filtraciones de memoria es tan grave, ¿por qué no podemos unirnos de alguna forma y dejar de escribir código vulnerable?
La raíz del problema es el uso de los lenguajes de programación C y C++. Su arquitectura brinda a los desarrolladores mucha libertad para trabajar con la RAM. Pero junto con la libertad viene la responsabilidad.
Los programadores de C/C++ tienen que implementar mecanismos para escribir y leer datos de forma segura. A su vez, los lenguajes de programación de alto nivel como C#, Rust, Go y otros se encargan de eso. La cuestión es que al compilar el código fuente del programa, los medios de gestión segura de la memoria se introducen automáticamente, y los desarrolladores no necesitan dedicar su tiempo a eso. Rust utiliza aún más medios para mejorar la seguridad, hasta restringir la compilación de código potencialmente peligroso mientras muestra el error al programador.
Por supuesto, dejar de usar C/C++ no es factible mientras estos lenguajes sigan siendo indispensables para ciertas tareas, como cuando se necesita código para el MCU u otros dispositivos con serias limitaciones en el poder de cómputo y el tamaño de la memoria.
En igualdad de condiciones, los lenguajes de programación de alto nivel pueden conducir a la creación de programas que requieren más recursos. Pero las estadísticas de amenazas comunes nos muestran que los ataques se dirigen con mayor frecuencia al software de usuarios domésticos (como navegadores y editores de texto), que se ejecutan en ordenadores muy potentes (en comparación con los MCU, por supuesto).
No se puede cambiar el lenguaje de programación sin más
Y la NSA lo sabe. Una enorme base de datos de software escrita en lenguajes de programación “inseguros” no se puede trasladar a otro lenguaje de la noche a la mañana. Aunque hablemos de escribir un producto de software desde cero, puede haber un equipo establecido, una infraestructura y métodos de desarrollo en torno a un lenguaje de programación en particular.
Como ejemplo, imagínate que te piden que te mudes de tu casa solo porque fue construida hace mucho tiempo. Sabes que la estructura está perfectamente y que solo se derrumbaría a causa de un gran terremoto y, además, estás acostumbrado a vivir allí. El equipo de desarrolladores de Google Chrome tiene una publicación en la que establece explícitamente que en este momento no pueden cambiar a otro lenguaje de programación (en este caso, Rust) en el que la seguridad esté integrada en la arquitectura. Podría ser posible en el futuro, pero ahora mismo necesitan otras soluciones.
Esta misma publicación de los desarrolladores de Google Chrome también explica por qué no se puede cambiar fundamentalmente la seguridad del código C/C++. Estos lenguajes de programación simplemente no fueron diseñados para resolver todos los problemas de compilación de golpe. Por ello, el informe de la NSA menciona dos conjuntos de medidas como alternativa:
- La prueba de código para vulnerabilidades potenciales con técnicas de análisis dinámico y estático.
- Usar características que eviten la explotación de un error de código, aunque ya esté allí.
Los desafíos del cambio
Los expertos coinciden en general con la opinión de la NSA, pero pueden tener diferentes opiniones sobre cómo podemos cambiar exactamente a lenguajes de programación de alto nivel en los casos en que la necesidad surja, entre otras cosas, de los requisitos de seguridad.
En primer lugar, es importante comprender que, si se produce tal movimiento, llevará muchos años. En segundo lugar, una evolución como esta tiene un precio, uno que no todas las empresas están dispuestas a pagar. El problema de la gestión insegura de la memoria en los lenguajes de programación con un bajo nivel de abstracción es un problema sistémico. Se necesita una solución radical, pero no esperes que todos comiencen mañana mismo a desarrollar en C#, Go, Java, Ruby, Rust o Swift. Esta situación presenta las mismas complicaciones que si se intentara obligar a toda una ciudad o país a pasarse al vegetarianismo o cualquier otro cambio extremo de la noche a la mañana.
Por último, el problema de la gestión insegura de la memoria puede ser muy importante, pero está lejos de ser el único problema relacionado con la seguridad del software.
En las varias décadas de existencia de la industria TI, nunca ha sido posible crear un sistema universal y completamente seguro para todas las tareas (excepto soluciones altamente especializadas). Desde un punto de vista empresarial, tiene sentido tanto invertir en nuevas tecnologías (desarrollando las habilidades correspondientes y contratando especialistas con experiencia) como en la máxima protección de las tecnologías existentes. Para el desarrollo de software, podemos hablar de nuevos lenguajes de programación y tecnologías para probar el código existente. Para cualquier otro negocio, puede ser invertir en nuevas tecnologías para protegerse contra los ciberataques, así como probar constantemente la solidez de la infraestructura existente. En otras palabras, una estrategia integral de la seguridad es lo más óptimo y seguirá siéndolo durante mucho tiempo.