Parece que una instrucción de rama ARM parece tardar 6 ciclos en ejecutarse en un procesador ARM7TDMI. Parece que no debería estar sucediendo porque en todas las referencias que he encontrado, una instrucción de bifurcación ARM7TDMI debería tomar solo 3 ciclos. Pero:
La función C:
start_time = TC;
for (int i=0; i<120; i++) {
__asm("NOP");
}
end_time = TC;
El desmontaje muestra el bucle como: (Actualización: direcciones de instrucciones agregadas):
0x120 MOV R1, 0
0x124 B LOC0
start:
0x128 NOP
0x12C ADD R1, R1, 1
LOC0:
0x130 CMP R1, 120
0x134 BLT start
Ahora el resultado muestra que el bucle toma 1080 ciclos (convertido de un contador de temporizador colocado en TC), es decir, 9 ciclos por núcleo de bucle. Como NOP
, ADD
, CMP
son todas instrucciones de un solo ciclo, BLT
tiene que ser de 6 ciclos.
Una vez sospecho que mi método de sincronización tiene fallas. Pero si agrego 1 NOP
en el kernel de bucle, el aumento de tiempo equivaldría exactamente a 1 ciclo.
¿Qué está mal aquí?
(Actualización: solución: el código de desensamblado original se escribe incorrectamente ADD R1, R1, 1
como ADD R1, R1
)
Actualización: respuesta aceptada: el bloqueo de acceso Flash provoca los 3 ciclos adicionales
Gracias a todos por las respuestas y comentarios útiles, especialmente @supercat, @Dzarda, @DaveTweed, @IgorSkochinsky, @WoutervanOoijen. Estoy ejecutando el código de flash. La CPU es una LPC23xx. De acuerdo con el Manual del usuario, sí incluye un Módulo de aceleración de memoria (MAM) para el acceso de flash con buffer. Y los ciclos de captura de flash sugeridos bajo la velocidad de mi CPU son exactamente 3 ciclos.
El start
en el núcleo del ciclo penalizado anterior se está alineando con un límite de 8 bytes. Si cambio la alineación de start
al límite de 16 bytes, desaparecerá la penalización de 3 ciclos adicionales. Esto se puede explicar por el tamaño del búfer de captura previa de flash de 128 bits (16 bytes) de mi CPU.
(@WoutervanOoijen) Tenga en cuenta que el tiempo de recuperación instantánea de MAM de 3 ciclos no lo realiza la CPU ARM, sino el módulo MAM que realiza una búsqueda previa de los datos flash en paralelo con la CPU. Así que en mi código con start
alineado en el límite de 8 bytes, CMP
es la primera instrucción en el búfer de búsqueda previa de MAM de 128 bits (4 instrucciones). Cuando la CPU ARM ejecuta BLT
, el primer ciclo tarda en "entender" la instrucción. Luego intenta obtener la instrucción NOP
que no está en el búfer de búsqueda previa de MAM. Ese debería ser el momento en que los 3 ciclos adicionales ocurren cuando el MAM accede al flash. Cuando la instrucción NOP
está en el búfer (junto con otras 3 instrucciones en la línea flash de 32 bytes), la CPU ARM puede volver a llenar la tubería al obtener NOP
(quinto ciclo) y decodificar NOP
( 6º ciclo). De ahí provienen los 6 ciclos totales.
Entonces, la respuesta a mi pregunta es Sí, una instrucción de derivación de 6 ciclos es posible si hay un puesto de acceso flash.
Pregunta final sin resolver
Como señala @WoutervanOoijen, el razonamiento anterior tiene una falla. El módulo de aceleración de memoria de LPC23xx tiene un búfer de Branch Trail adicional que se supone que evita este tipo de ramas repetidas de bucle de recuperación. El LPC23XX User Manual indica:
El búfer de Branch Trail captura la línea en la que se produce una ruptura no secuencial. Si se vuelve a tomar la misma rama, la siguiente instrucción se toma del búfer de Trail Trail
Esta declaración no parece ser muy clara sobre lo que se está poniendo exactamente en el búfer de Branch Trail. Podría ser la última línea de flash precargada, o la última línea de flash de destino de rama. En cualquier caso, la penalización de acceso de flash no debería haber ocurrido porque la línea de flash (0x120 ~ 0x12F) que incluye la instrucción de destino de bifurcación ( NOP
) ya debería estar en el búfer Trail Trail cuando se está ejecutando BLT
a partir de la segunda vez).
(Por cierto, verifiqué que MAM se puso en modo Totalmente Habilitado, es decir, MAM_mode_control es 2)
Actualizaré esta pregunta cuando encuentre más información sobre esto. Y lo apreciaré si tiene algún comentario sobre lo que podría estar sucediendo aquí, o qué prueba se puede hacer para buscar pistas.