Así funciona la coherencia de memoria de los procesadores multinúcleo

Así funciona la coherencia de memoria de los procesadores multinúcleo

Josep Roca

La coherencia de memoria es uno de los elementos clave para los sistema multinúcleo que comparten una misma memoria y que utilizan una jerarquía de caches. Gracias a ella todos los núcleos tienen un acceso coherente a la memoria y tienen una visión común de la memoria que utilizan para ejecutar los programas. Os explicamos cómo funciona y cuál es su utilidad.

Imaginad por un momento que tenemos un sistema con varios núcleos, pero ninguno de ellos tiene una jerarquía de caches y por tanto tienen una visión compartida de la memoria.

El problema es que debido al abismo en velocidad entre la RAM y los procesadores se acabó por utilizar la memoria cache, la cual copia las páginas o las líneas de memoria más cercanas al código que está ejecutando el procesador en cada momento.

Distancia RAM Procesador

El uso de las caches que impide cuellos de botella en el rendimiento acaba creando problemas de coherencia ya que los procesadores no ejecutan las instrucciones sobre la RAM de manera directa sino sobre las caches, por lo que hace falta implementar un sistema de coherencia para asegurar que la información que almacenan las caches sea la correcta.

Consistencia de los datos y coherencia de la memoria

Consistencia Datos

La consistencia de los datos hace referencia al contrato entre los programas y la memoria RAM, es decir, como van a utilizar estos la memoria, pero especialmente como los diferentes hilos de ejecución se van a comunicar entre ellos. Por ejemplo, el hilo 1 necesita el dato B del hilo 2 y el hilo 2 el dato A, por lo que los datos sean los correctos es ideal para el correcto funcionamiento del programa que se está ejecutando.

La coherencia de memoria es en cambio el mecanismo a nivel de hardware que permite a los hilos de ejecución comunicarse correctamente, el cual es completamente transparente al software y funciona en segundo plano de manera automática asegurando que los diferentes núcleos tengan una visión de la memoria en común, es decir, totalmente coherente.

El problema de las información de las caches

Dual Core

Como hemos dicho antes las caches son lo que hace que sea necesaria un sistema de coherencia complejo, el motivo de ello es muy simple y tiene que ver con que existen dos tipos de caches:

  • Caches Privadas: Cercanas a los núcleos, mucho más pequeñas y completamente privadas de estas, cualquier cambio que se haga en las copias de las direcciones de memoria en las caches privadas sin un sistema de coherencia de caches no se reflejará en las copias.
  • Caches Compartidas: Están más alejadas de los núcleos, son mucho más grandes que las caches privadas.

Lo más fácil para los ingenieros de hardware sería conectar las diferentes caches privadas a la RAM, el problema con el que se enfrentan es que la memoria RAM tiene de media pocos canales de memoria, por lo que mientras un núcleo estaría accediendo a la RAM otros se quedarían en pausa. Es por eso que se utiliza una cache compartida siempre en el último nivel que es con la que esta conectada la RAM.

Jerarquia Caches

En la jerarquía de caches la única comunicación de cada nivel de cache es con los que está conectado, de tal manera que las caches privadas no están conectadas a la RAM de manera directa sino únicamente a la cache compartida o a los niveles posteriores o anteriores de la cache privada si los hubiese.

Mecanismo de husmeo para la coherencia de memoria

cache

La coherencia de cache no se implementa a través de ningún coprocesador, sino a través de una serie de mecanismos integrados en el hardware, los dos protocolos de coherencia más utilizados son los siguientes:

  • Escribir e invalidar: Cuando se realizar una operación de escritura a memoria, entonces todas las copias de esa línea de memoria en las diferentes caches son invalidadas. Lo que obliga a que los núcleos tengan que actualizar sus datos.
  • Escribir y actualizar: En este sistema cuando un procesador escribe sobre una línea de cache entonces todas las copias en las diferentes caches son actualizadas.

Para saber que líneas de cache se han cambiado se utiliza un «husmeador», el cual es un mecanismo por hardware que lo que hace monitorizar los accesos a memoria y a las caches por los diferentes núcleos de tal manera que el sistema de coherencia sabe que direcciones de memoria se modifican en cada momento. El problema de este método es que no escala muy bien con un gran número de núcleos.

Mecanismo de coherencia de memoria basado en directorio

Microscopio Circuito Electrónico

Este sistema de coherencia se basa en mantener un directorio de en que caches se encuentran las diferentes líneas de memoria. Este sistema es una implementación a nivel de hardware de la organización de directorios de un sistema operativo. El directorio no almacena los datos de las diferentes lineas de cache sino en que lineas de cache se encuentran copiadas las diferentes líneas de memoria.

Tiene la particularidad de que escala mucho mejor con el número de núcleos, que no el mecanismo de husmeo, pero no deja de ser un mecanismo de husmeo más avanzado, el cual deja constancia de todos los accesos que se han hecho a memoria, de tal manera que los diferentes núcleos saben que procesadores han accedido de antemano el dato de una línea de cache.