apilar caché en lugar de registros

6

¿Hay un procesador que realice operaciones aritméticas en una pila y no en registros? Por supuesto, para mantener el rendimiento, ese procesador debe almacenar en la caché el bloque superior de una pila en el mismo tipo de memoria que se usa para los registros.

Leí en un artículo (David R. Ditzel, HR McLellan. Registrar asignación de forma gratuita: La Caché de C Machine Stack. ) que un caché es más lento 2 veces que los registros debido a:

  • direccionamiento indirecto durante cada acceso al caché;
  • falta de caché cuando la pila crece.

El papel es viejo. Tal vez, ¿aparecieron mejoras en el diseño del procesador que hacen que la pila de caché sea viable? Creo que reducirá la complejidad de los compiladores y optimizará la copia entre los registros y el resto de la memoria.

Actualización 2012-10-18. Debido a que este concepto era conocido (no para mí), cambio la pregunta a "... ¿Procesadores modernos?"

Actualización 2012-10-18. Siento que debo decir explícitamente que no estoy hablando de "máquina de dirección cero". El almacenamiento en caché y la "dirección cero" son ortogonales. Mi hipotético procesador puede tener incluso una adición de 5 arias como "r3: = r0 + r2 + r11 + r5 + r8". “R n” significa la celda de memoria en sp + n, donde sp es un puntero de pila. sp cambia antes y después de un bloque de código. Un programa muy inusual cambia sp en cada operación aritmética.

    
pregunta beroal

5 respuestas

7

Sí, toda la línea de Burroughs a partir de 1961 con el B5000 utilizó una arquitectura de pila.

En esta arquitectura, administrar el flujo de datos hacia y desde la pila no es realmente un cuello de botella para el rendimiento. Un problema mayor es el hecho de que una máquina de "dirección cero" necesita muchas más instrucciones para completar una tarea determinada que una máquina de una, dos o tres direcciones. La decodificación de instrucciones y la tubería de ejecución se convierten en el principal cuello de botella.

Cuando trabajé allí a principios de la década de 1980, hubo un esfuerzo por construir una CPU que pudiera obtener secuencias relativamente grandes de instrucciones de dirección cero y traducirlas sobre la marcha a operaciones de tres direcciones que se enviarían a la tubería de ejecución. . (Piense en un compilador Java JIT implementado en hardware). Se volvió bastante complejo, especialmente para las tecnologías de implementación disponibles en ese momento, y no sé si esta estrategia finalmente tuvo éxito.

En caso de que se esté preguntando, la terminología de "dirección N" se refiere al número de operandos que se pueden especificar en una sola instrucción. Todas las operaciones en una máquina de pila están implícitamente en la primera o las dos ubicaciones superiores de la pila, por lo que hay cero operandos en las instrucciones. Una máquina que tiene un acumulador que se utiliza para todas las operaciones junto con otro registro o ubicación de memoria es una máquina de una sola dirección. Una máquina de dos direcciones puede especificar un operando de origen y destino arbitrario en una instrucción, y una máquina de tres direcciones puede especificar dos operandos de origen y colocar el resultado en un destino independiente.

    
respondido por el Dave Tweed
3

Recuerdo haber leído un artículo similar (quizás el mismo) hace unos 17 años. Tal enfoque podría ser bueno si uno estuviera desarrollando un procesador para ejecutar una instrucción a la vez rápidamente. Desafortunadamente, no funciona bien con la programación de instrucciones fuera de orden. Si uno tiene código como:

  ldr r1,[r0]
  ... do some stuff, not involving r1, r2, or [r2]
  str r1,[r2]

Un programador de instrucciones tiene la libertad de cambiar esas dos instrucciones como mejor le parezca. Si bien puede ser difícil para el programador de instrucciones saber si una escritura en alguna ubicación de memoria podría ser una escritura en [r2], muchos lenguajes compilados requieren que los programadores indiquen qué elementos pueden o no tener alias.

Por el contrario, las instrucciones eran más como:

  mov.l [r0],[--sp] ; Push [r0] onto stack
  ... do some stuff, which affects sp
  mov.l [sp++],[r2] ; Pop [r2] from stack

sería mucho más difícil para un motor de ejecución fuera de orden determinar si el operando de origen para la última instrucción sería siempre el mismo que el operando de destino del primero, y si alguna de las instrucciones de intervención podría afectarlo. p>     

respondido por el supercat
2

En el pasado trabajé con el Saab Ericsson Space Thor, un microprocesador para aplicaciones espaciales. Funcionó, pero tenía algunos inconvenientes graves. Solo uno: se expuso la línea de instrucciones: la instrucción que cargó una palabra de la memoria utilizada como dirección en la parte superior de la pila hace 2 instrucciones . Escribí una rutina rápida de copia de memoria para eso, pero Saab dijo que no se podía usar porque las interrupciones podrían causar problemas ...

    
respondido por el Wouter van Ooijen
0

Había procesadores Forth dedicados que solían usarse en el procesador de arranque para máquinas Sun / Sparc cuya arquitectura dedicada se asignaba al idioma. Pero generalmente no disponible.

    
respondido por el placeholder
0

El x86 es casi uno de esos :-) (y la parte de fp x87 aún más cerca)

Sin embargo, en los sistemas modernos, la pila es terrible, ya que puede tener un alias entre los núcleos o incluso los nodos NUMA, por lo que puede haber mucha señalización lenta y de larga distancia. O, como mínimo, más interbloqueos de los que obtiene con un archivo de registro y cambio de nombre de registro.

Tenga en cuenta que ni siquiera las CPU, pero otros dispositivos pueden tener datos DMA en su pila, ¡piense en leer los buffers!

    
respondido por el Jon Watte

Lea otras preguntas en las etiquetas