El uso de sincronizadores de 2 ff ha sido un estándar para que una señal cruce los límites del reloj. Y hay muchos papeles / figuras que ilustran el mecanismo, como este:
Parece que bclk solo puede muestrear el pulso de adat una vez (en el segundo flanco ascendente de bclk ), lo que causa metaestabilidad de salida en bq1_dat . ¿Cómo se puede muestrear bq1_dat "alto" en el próximo borde de reloj activo?
Además de mi pregunta, me gustaría agregar lo que pienso para que una señal pase de manera segura a otro dominio de reloj (supongamos que 2-FF es suficiente para satisfacer el requisito de MTBF). Por favor corrígeme si hay algún error.
ps: el estado metaestable no muestra la forma de onda "deambulando", sino un nivel que no es ni '1' ni '0'. La siguiente figura muestra un ejemplo de salida metaestable.
La figura original provino de las notas de la Conferencia EE108A, Conferencia 13: Metaestabilidad y falla de sincronización (ow When Good Flip-Flops Bad) por WJ Dally.
fuente
Respuestas:
La respuesta simple es que no lo hacen solos. El sincronizador no está ahí para garantizar que los datos se transmitan, sino para garantizar que no termines con señales metaestables que alimenten muchas otras señales y causen problemas. El segundo FF como muestra el diagrama captura la primera salida de FF metaestable y evita que se propague aún más a través del diseño.
Hay varios tipos de señales, y la forma en que incluya sincronizadores depende de la señal de la que esté hablando. Pero veamos un par de tipos comunes:
Señales de activación - o cualquier señal que sea básicamente un impulso que debe iniciar algo más en funcionamiento. Por lo general, estos no contienen datos, y todo lo que le interesa es que haya, por ejemplo, un borde ascendente para comenzar a que algo vaya en otro dominio de reloj. Para que estos se crucen, necesitaría un sincronizador (esencialmente haciendo lo que se muestra en su diagrama), pero necesita un poco más.
La opción más simple es extender el pulso: esencialmente se asegura de que el pulso de entrada sea más de 1 período de reloj del reloj de destino (debe ser más largo que 1 ciclo por al menos el mayor tiempo de configuración y retención para el registro de destino) . Por ejemplo, si va de un reloj de 20MHz a un reloj de 15MHz, se asegurará de que su pulso sea de dos ciclos de reloj en la entrada, lo que garantizaría que se presente en el reloj de destino y no se pierda. Esto también responde a su pregunta sobre cómo se garantiza que la señal se transmita. Si el pulso es más ancho que un período de reloj de destino, significa que si se metaestable en el primer borde del reloj y termina siendo visto como un 0, entonces en el segundo borde del reloj definitivamente capturará el pulso.
Debido a que con este tipo de señal solo le interesa que el pulso se haya transmitido, no importa si la señal de salida termina con dos ciclos de reloj altos algunas veces y solo un ciclo el resto. Si necesita asegurarse de que sea un pulso de ciclo único, puede crear una instancia de un circuito detector de borde simple.
Buses de control , o posiblemente tipos de buses de datos. Podría decirse que son más difíciles porque si tiene un flujo de datos de varios bits que necesita estar sincronizado. En este caso, lo que haría es implementar algo llamado "apretón de manos". Básicamente carga sus datos en el reloj de origen y los mantiene. Luego, envía una señal de solicitud (como en 1) a través de un sincronizador. Una vez que la señal de solicitud está cruzada, sabe que el bus de datos también se estabilizará en el dominio de destino. Luego puede registrarlo en un banco de registro en el destino. El destino luego envía un pulso de confirmación nuevamente para informar a la fuente que puede cargar la siguiente palabra.
Usaría este tipo de bus si necesitara enviar una palabra de control al reloj de destino para el que necesita saber que llegó allí antes de enviar otro (por ejemplo, si envía un comando para hacer algo).
Buses de datos : para los datos donde tiene una fuente que escupe datos continuamente o en ráfagas, podría decirse que es mejor usar un FIFO que sincronizadores. El FIFO usa una memoria de reloj doble para guardar los datos, junto con contadores para realizar un seguimiento de la cantidad de datos que hay en el FIFO. Escribe los datos en el FIFO cuando hay espacio y luego incrementa la dirección de escritura. Esta dirección generalmente se codifica en un esquema de "codificación gris" que garantiza que cada incremento en la dirección cause solo unobit en el bus de direcciones para cambiar (lo que significa que no necesita sincronizar varios bits). Esta dirección se transfiere al dominio de destino (a través de una de sus cadenas de sincronizador), donde se compara con la dirección de lectura. Si hay datos en el FIFO, se pueden leer de la memoria utilizando el puerto del reloj de destino. La dirección de lectura tiene un código gris similar y se envía de vuelta a la fuente a través de otro sincronizador para que el puerto de escritura pueda calcular si hay espacio en la FIFO.
Señales de reinicio : por lo general, usan una versión modificada del sincronizador en lo que se conoce como "Afirmación asincrónica, Desassert sincrónico". En esta versión modificada, la entrada de datos al primer flip flop está vinculada a GND y, en cambio, la señal de reinicio entrante se conecta a las señales preestablecidas asincrónicas de cada flip-flop en el sincronizador. Esto da como resultado una señal de salida que es completamente asíncrona cuando sube, pero la cadena sincronizadora asegura que baja sincrónicamente con el reloj de destino marcando ceros en la cadena de registro.
Este tipo de sincronizador es terrible para los datos y el control, pero es perfecto para restablecer las señales. Si toda la lógica de destino alimenta la salida de esta cadena a las entradas de reinicio asíncrono de cualquier registro en el dominio, entonces hay poca preocupación por la metaestabilidad en el proceso de aserción (aunque sea asíncrono) ya que todos los registros se ven forzados a un estado conocido. Luego, cuando la señal de reinicio se desasiste en el dominio de origen, se desasocia sincrónicamente en el dominio de destino, lo que significa que todos los registros salen del reinicio en el mismo ciclo de reloj (en lugar de +/- 1 ciclo si fue un desassert asíncrono).
Como puede ver en lo anterior, es mucho más complejo hacer un cruce de dominio de reloj que simplemente pegar un sincronizador de 2 flip-flop en la señal. El método exacto utilizado depende de la aplicación.
fuente
sync_Bits
) para FPGA Xilinx y Altera para mejorar el comportamiento de la metaestabilidad. El sincronizador 2-FF se utiliza, por ejemplo,sync_Strobe
para construir sincronizadores más complejos para pulsos.1) Usando su dibujo como ejemplo, aclk y bclk son asíncronos entre sí. En otras palabras, tienen diferentes fuentes de reloj. Muestran adat como datos válidos pero sincronizados solo para aclk. Aquí es donde entra en juego el sincronizador bclk.
2) Este dibujo asume el peor de los casos, donde bq1_dat es una salida desordenada porque el bq1 FF capturó solo una parte del final de los datos, creando un estado metaestable en el que la salida generalmente es basura. Aquí está el truco. Bq2 tiene el mismo bclk que bq1, pero se necesitan 2 ciclos de reloj de bclk para que los datos pasen y aparezcan en bq2_dat.
3) El primer bclk capturó parte de los datos, lo que resultó en una salida desordenada, pero el segundo bclk es un ciclo de reloj más tarde, tiempo suficiente para que los datos ambiguos de bq1_dat se asienten en un estado alto o bajo. El desordenado pulso bq1_dat duró el tiempo suficiente para que bq2 capture una lógica válida '1' (lógica alta) y la pase a bq2_dat como datos válidos y ahora sincronizados (lógica alta).
4) En sentido descendente, cualquier reloj que use bclk tendrá datos sincronizados para trabajar. Tenga en cuenta que solo el primer bclk FF tuvo que lidiar con un estado metaestable . La salida podría haber sido un nivel lógico bajo si adat hubiera sido solo pico o nano segundos demasiado tarde. Recuerde que estos flip-flops muestrean la entrada de datos solo en el borde ascendente del reloj. Lo que sucede antes o después del borde ascendente se ignora.
fuente