Instrucción AJMP y ACALL del AT89S52

El microcontrolador AT89S52 de ATMEL forma parte de la familia 8051 creada por Intel hace unas décadas. Éste es un microcontrolador de 8 bits, misma cantidad de bits que utiliza para definir sus instrucciones, o sea que cuenta con 255 instrucciones más una que no está definida. El 8051 cuenta con 8K bytes de memoria Flash para código. El 8051 es capaz de direccionar hasta 64K bytes de memoria para código en páginas de 2K bytes. Por lo que se deduce que puede usar HASTA 32 PAGINAS (desde la 0 a la 31).

Las instrucciones ACALL y AJMP (de 2 bytes) son las únicas que utilizan el direccionamiento absoluto. Este direccionamiento solo es posible realizarlo DENTRO DE LA MISMA PAGINA DE 2K. Por ejemplo:

image4.jpeg


En la imagen de arriba serían válidos los 2 primeros bloques como paginas de 2K. Puede verse que la primera página (página 0) va desde 0000H hasta 07FFH y la segunda desde 0800H hasta 0FFFH.

Las instrucciones ACALL y AJMP utilizan los primeros 5 bits más significativos de la dirección destino a "saltar" para definir la página sobre la que están trabajando. Por ejemplo, la etiqueta AQUI representa una instrucción en la dirección 0F46H.

AJMP AQUI

Podemos ver que la dirección destino en binario es 0000 1111 0100 0110.
Tomando los primeros 5 bits deducimos que la página en la que estamos trabajando es la página 1 (0000 1) cuyas direcciones van desde 0800H hasta 0FFFH.

La duda es que en el mapa de los códigos de operaciones del 8051, las instrucciones ACALL solo están definidas para la página 0 hasta la página 7 es decir sus códigos de operación son

AJMP(P0) 01H
ACALL(P0) 11H

AJMP(P1) 21H
ACALL(P1) 31H

AJMP(P2) 41H
ACALL(P2) 51H .... HASTA

AJMP(P7) E1H
ACALL(P7) F1H

De estos OP codes se utilizan solo los primeros 5 bits para armar los bytes de instrucción ACALL (O AJMP). De hecho el modo de direccionamiento absoluto es así:

aaa(+ 5 primeros bits del OP CODE)aaaaaaaa

se puede ver que son 16 bits (2 bytes) y las letras a' representan los primeros 11 bits de la dirección de destino, que en nuestro ejemplo serían: 111 0100 0110. Los 5 bits mas significativos están como implicitos porque se suponen estan en la misma página de la dirección origen desde donde se llamó la instrucción o de hecho, el mismo opcode (en nuestro ejemplo es 31H) nos indica en cual página se está trabajando.

entonces ¿No es válido utilizar una página superior a la 7 en un programa que yo escriba dado que no están definidas en el set de operaciones? Pero entonces ¿Por qué se da espacio para utilizar hasta 5 bits (justos los necesarios para combinarlos y usar hasta 32 paginas) en el direccionamiento absoluto para el 8051? :confused:
 
Última edición:
http://www.win.tue.nl/~aeb/comp/8051/set8051.html#51acall

Description: ACALL unconditionally calls a subroutine at the indicated code address. ACALL pushes the address of the instruction that follows ACALL onto the stack, least-significant-byte first, most-significant-byte second. The Program Counter is then updated so that program execution continues at the indicated address.

The new value for the Program Counter is calculated by replacing the least-significant-byte of the Program Counter with the second byte of the ACALL instruction, and replacing bits 0-2 of the most-significant-byte of the Program Counter with 3 bits that indicate the page. Bits 3-7 of the most-significant-byte of the Program Counter remain unchaged.

Since only 11 bits of the Program Counter are affected by ACALL, calls may only be made to routines located within the same 2k block as the first byte that follows ACALL.

En pocas palabras acall te permite hacer un llamado a subrutina dentro de los 2k siguientes.... si necesitas hacer un salto mas largo tienes que usar lcall (3 bytes)
 
Antes que nada muchas gracias chico3001 por tomarte la molestia de buscar información y responder mi pregunta. En realidad me hizo falta más claridad en mi pregunta y dar más información, pero no quería saturarla porque así daría pereza leerla. :LOL:

Lo que sucede es que este modo de direccionamiento absoluto en el at89s52 al principio parece revoltoso pero en realidad es fácil.

De hecho si te fijas:

ya había anotado que este modo solo permite dar saltos dentro de una misma página de 2KB y no a otra página.

:D Mi duda es:

¿Qué pasaría si mi código fuera muy extenso y llegara a necesitar dar un salto de la dirrección FA00H a la FF01H? Se puede ver que ESTAN DENTRO DE LA MISA PAGINA DE 2K, pero al parecer no están implementados los respectivos OP CODEs para trabajar en estas páginas tan altas. Me parece un poco mezquino que solo se permita llegar hasta la página 7. O quizá no estoy comprendiendo completamente este modo. El punto clave aquí son esos 5 bits que faltan para completar la instrucción de 16 bits; se insertan del OP CODE. Observa que en la información que me pegaste se toman primero 8 bits del program counter más otros 3 bits dando 11 bits en total.

De todos modos es muy útil tu respuesta (no es que me esté aferrando a utilizar la instrucción ACALL o AJMP cuya ventaja es que solo usan 2 bytes) ya que quizá puedo usar LCALL aunque usa 3 bytes lo cual podría hacer un poco más lenta su ejecución y tamaño de código, pero si esta instruccion LCALL sí la puedo usarla a lo largo de los 64KB de memoria entonces it is worth to use it.
 
Última edición:
ACALL solo afecta los primeros 11 bits de PC, pero no altera los mas significativos, asi que si estas en la direccion FA00H y haces un ACALL 7FF (el maximo) terminaras en la direccion FFFFH (la ultima direccionable)

Esto aplica para todo el rango de F800 a FFFF
 
Atrás
Arriba