Discrepancia entre el análisis de tiempo estático posterior al lugar y la ruta y los resultados de la simulación ISIM

Descripción general

Estoy implementando una CPU simple de estilo Harvard usando Xilinx ISE versión 14.1. Estoy usando configuraciones compatibles con una placa Digilent Nexys3, pero por el momento todo el proyecto se realiza solo en simulación.

Tengo la siguiente entrada en mi archivo UCF que especifica la ubicación (pin) del reloj en la placa Nexys3, junto con una restricción de período de 100 MHz. Esto significa un período de 10ns.

Net "clk" LOC=V10 | IOSTANDARD=LVCMOS33;
Net "clk" TNM_NET = sys_clk_pin;
TIMESPEC TS_sys_clk_pin = PERIOD sys_clk_pin 100000 kHz;

Estoy cronometrando toda la lógica síncrona usando el borde positivo de este reloj.

El análisis de tiempo estático posterior a Place-and-Route sugiere que todo está bien:

Timing constraint: TS_sys_clk_pin = PERIOD TIMEGRP "sys_clk_pin" 100 MHz HIGH 
50%;
For more information, see Period Analysis in the Timing Closure User Guide (UG612).

 12987 paths analyzed, 961 endpoints analyzed, 0 failing endpoints
 0 timing errors detected. (0 setup errors, 0 hold errors, 0 component switching limit errors)
 Minimum period is   4.003ns.

El período mínimo está dentro del objetivo de 10 ns. No hay rutas sin restricciones en el informe.

El informe luego menciona este camino primero. Dado que el tiempo coincide, asumo que es el camino más lento en el diseño (el camino con la menor holgura). Es la ruta desde el registro de instrucciones hasta el bit más alto del puntero de la pila. La ruta (a través de la ALU y el bus 3) parece sana para mi diseño cuando el registro se carga con un valor inmediato. La ruta push/pop toma una ruta diferente.

Slack (setup path):     5.997ns (requirement - (data path - clock path skew + uncertainty))
  Source:               CONTROL/IR_15_2 (FF)
  Destination:          SP/VALUE_31 (FF)
  Requirement:          10.000ns
  Data Path Delay:      3.951ns (Levels of Logic = 9)
  Clock Path Skew:      -0.017ns (0.252 - 0.269)
  Source Clock:         clk_BUFGP rising at 0.000ns
  Destination Clock:    clk_BUFGP rising at 10.000ns
  Clock Uncertainty:    0.035ns

  Clock Uncertainty:          0.035ns  ((TSJ^2 + TIJ^2)^1/2 + DJ) / 2 + PE
    Total System Jitter (TSJ):  0.070ns
    Total Input Jitter (TIJ):   0.000ns
    Discrete Jitter (DJ):       0.000ns
    Phase Error (PE):           0.000ns

  Maximum Data Path at Slow Process Corner: CONTROL/IR_15_2 to SP/VALUE_31
    Location             Delay type         Delay(ns)  Physical Resource
                                                       Logical Resource(s)
    -------------------------------------------------  -------------------
    SLICE_X13Y30.BQ      Tcko                  0.391   CONTROL/IR_15_3
                                                       CONTROL/IR_15_2
    SLICE_X5Y31.D3       net (fanout=12)       0.847   CONTROL/IR_15_2
    SLICE_X5Y31.D        Tilo                  0.259   RAM/read_address<1>
                                                       ALU1/Mmux_RR11241
    SLICE_X14Y24.B3      net (fanout=4)        1.283   bus3_1_OBUF
    SLICE_X14Y24.COUT    Topcyb                0.380   SP/VALUE<3>
                                                       SP/Mcount_VALUE_lut<1>
                                                       SP/Mcount_VALUE_cy<3>
    SLICE_X14Y25.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<3>
    SLICE_X14Y25.COUT    Tbyp                  0.076   SP/VALUE<7>
                                                       SP/Mcount_VALUE_cy<7>
    SLICE_X14Y26.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<7>
    SLICE_X14Y26.COUT    Tbyp                  0.076   SP/VALUE<11>
                                                       SP/Mcount_VALUE_cy<11>
    SLICE_X14Y27.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<11>
    SLICE_X14Y27.COUT    Tbyp                  0.076   SP/VALUE<15>
                                                       SP/Mcount_VALUE_cy<15>
    SLICE_X14Y28.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<15>
    SLICE_X14Y28.COUT    Tbyp                  0.076   SP/VALUE<19>
                                                       SP/Mcount_VALUE_cy<19>
    SLICE_X14Y29.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<19>
    SLICE_X14Y29.COUT    Tbyp                  0.076   SP/VALUE<23>
                                                       SP/Mcount_VALUE_cy<23>
    SLICE_X14Y30.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<23>
    SLICE_X14Y30.COUT    Tbyp                  0.076   SP/VALUE<27>
                                                       SP/Mcount_VALUE_cy<27>
    SLICE_X14Y31.CIN     net (fanout=1)        0.003   SP/Mcount_VALUE_cy<27>
    SLICE_X14Y31.CLK     Tcinck                0.314   SP/VALUE<31>
                                                       SP/Mcount_VALUE_xor<31>
                                                       SP/VALUE_31
    -------------------------------------------------  ---------------------------
    Total                                      3.951ns (1.800ns logic, 2.151ns route)
                                                       (45.6% logic, 54.4% route)

Armado con este conocimiento, ejecuto una simulación posterior a Place-and-Route con un período de reloj de 10 ns pensando que todo estará bien. Sin embargo, no lo es. Las señales no se asientan a tiempo para el siguiente borde del reloj y todo es un desastre. Relajar el reloj a 50 ns (20 Mhz) permite mucho tiempo para que todo se asiente.

tiempos

A los 425ns obtenemos el pulso de reloj que señala el inicio del ciclo en el que ejecutaremos la instrucción SP <- 0xFFFFFFFF. IR_15_2es la señal del informe de tiempo. SP_valuees un registro, por lo que solo asume el valor que se le presenta en el siguiente flanco ascendente. SP se carga desde bus3, así que lo usamos como proxy.

En el gráfico vemos que se necesitan aproximadamente 3 ns para IR_15_2que se afirme. Luego, toma más de 10 ns más para que el bus1 tome el control de la señal. A los 451 ns, 26 ns más tarde, la señal está disponible en el bus 3 y podemos empezar a pensar en cargar SP con ella.

Pregunta

El tiempo estático me dice que la ruta más larga de registro a registro en el diseño debería tomar alrededor de 4 ns, mientras que la simulación muestra que las señales tardan alrededor de 26 ns en establecerse. ¿Que esta pasando aqui? ¿El análisis de tiempo estático no encuentra todas las rutas relevantes? ¿Usé/configuré mal el simulador? ¿Leí mal el análisis de tiempo estático?

Estoy bien ejecutando el diseño a 20Mhz, esto no es una competencia de velocidad. Solo tengo la sensación de que me falta algo importante.

información adicional

El proyecto completo (archivos VHDL, proyecto XISE) está disponible en bitbucket .

Avíseme si me perdí algunos datos cruciales en mi pregunta. Estas son herramientas complicadas y no pretenderé que entiendo todos (¡o incluso la mayoría!) de los aspectos.
¿Por qué bus3 indica UUUUUUUU? ¿Es esta la primera instrucción que ejecuta, o hay algo más que hace Uque se propague? No estoy seguro de cómo maneja STA U, y eso puede ser parte de su problema.
Es la primera instrucción real que estamos ejecutando. Después del pulso de reinicio (no se muestra), ejecuto tres nops (tristate todo) para asegurarme de que los efectos del reinicio se han calmado y luego ejecuto esta instrucción (para inicializar el puntero de la pila). El UUUUUUUU en bus3 es el resultado de realizar la operación ALU 0 (y, creo) en dos entradas ZZZZZZZZ.
Por cierto, los tiempos que se muestran en el gráfico son típicos para todos los ciclos de registro->bus1->bus3->registro. Esto también es válido cuando no hay UUUUUUUU a la vista. Elegí esta instrucción porque aparece como la ruta más lenta en STA.
Parece que está leyendo el informe de tiempo correctamente, por lo que se reduce (muy probablemente) a que la configuración de su STA no coincide con sus condiciones de funcionamiento. Por ejemplo, una suposición predeterminada de STA puede ser que todas las entradas sean estables (definidas como 1 o 0) en el flanco ascendente del reloj. ¿Hay un circuito de retroalimentación que solo aparece cuando algunos autobuses son Zo U?
Por cierto, ¿estás realmente seguro de que necesitas tri-state? Eso por sí solo puede causar mucho dolor en STA.
Ah, claro. Quiere decir que el decodificador asigne las señales directamente en HDL ("if sel=x"1" then bus1<=register1; end if;") y que la síntesis se preocupe por los cables en lugar de perder el tiempo con "cableado falso" que es explícitamente poner a "Z". Ni siquiera se me pasó por la cabeza. Le echaré un vistazo.
En mi experiencia, los internos Zdeben tratarse como un martillo, útil en casos específicos, pero no una solución milagrosa o incluso una solución preferida.
Cambié mi código para nunca generar una Z (llegué a examinar todos los caracteres Z en mis archivos fuente). Esto tuvo un pequeño impacto en la salida de STA (3 ns de holgura en lugar de 6 ns) y un gran impacto en la salida de la simulación. Ahora puedo ejecutarlo con un reloj de 10ns y la salida es consistente. ¡Parece que resolviste el problema! Si lo agrega como respuesta, lo aceptaré.

Respuestas (1)

Mirando a través de su informe de tiempo, no hay nada que indique un problema potencial. Dado que tiene un problema, esto significa que los escenarios que está comprobando el análisis de tiempo estático (STA) no cubren el uso real de su circuito.

Sin una configuración seria de STA, algunas suposiciones comunes son que todas las entradas son válidas en el momento en que sube el reloj y que se conocen todos los estados (es decir, una lógica 1o 0). Inmediatamente, el UUUUUUUUencendido bus3parece muy sospechoso y es un posible problema con la inicialización. En simulaciones lógicas, Uimplica que la línea es a 1o 0, pero un registro que la controla no se inicializó correctamente. Esto podría hacer que el simulador dé respuestas extrañas hasta que todos los registros se carguen o se restablezcan. Sin embargo, este problema se manifiesta en ciclos posteriores después de inicializar todos los registros.

El otro problema potencial es que se bus1inicia en un estado de alta impedancia ( ZZZZZZZZ). Teniendo en cuenta que los tres estados generalmente no se asumen en el análisis de tiempo, esta es la fuente más probable de la discrepancia de tiempo. Las condiciones tri-estatales deben codificarse cuidadosamente en su herramienta STA para que puedan ser consideradas. Esta puede ser una tarea muy difícil y es propensa a errores (programación incorrecta, casos perdidos, etc.). Creo que la programación en retrasos de tres estados probablemente le daría un resultado STA preciso que debería coincidir con su simulación.

Sin embargo, tri-state suele ser una mala elección para la comunicación en chip tanto para ASIC como para FPGA. Esta ambigüedad de la confiabilidad de STA, el potencial de contención del bus y la incertidumbre de los requisitos de potencia de la unidad hacen que sea más probable que los sistemas tri-state causen problemas en lugar de solucionarlos. El método más seguro es usar un multiplexor para seleccionar qué fuente "habla" con el bus, o dividir el diseño de manera diferente. Solo usaría tri-state cuando sé que resolverá más problemas de los que puede causar.

Cambié mi código para nunca generar una Z (llegué a examinar todos los caracteres Z en mis archivos fuente). Esto tuvo un pequeño impacto en la salida de STA (3 ns de holgura en lugar de 6 ns) y un gran impacto en la salida de la simulación. Ahora puedo ejecutarlo con un reloj de 10ns y la salida es consistente.