2.9 INSTRUCCIONES ARITMÉTICAS Y LÓGICAS


2.9 INSTRUCCIONES ARITMÉTICAS Y LÓGICAS
El microprocesador Z-80 dispone de una unidad aritmética-lógica que le permite realizar una serie de operaciones, tanto aritméticas, como lógicas. Las aritméticas incluyen la suma y resta con o sin acarreo, incremento y decremento de un registro, comparaciones, ajuste decimal, complemento y negación. Las lógicas incluyen las operaciones que se realizan con los operadores "AND", "OR" y "XOR".
Antes de adentrarnos en el estudio de las instrucciones concretas, daremos una serie de definiciones útiles:
SUMA SIN ACARREO:
Consiste en sumar al contenido del registro "A" un número y obtener el resultado en el registro "A". El indicador de acarreo no se tiene en cuenta para esta operación. Su esquema sería:
 A+n
SUMA CON ACARREO:
Exactamente igual que la anterior, pero se suma también el indicador de acarreo del registro "F". De esta forma, sepuede incluir en la suma el acarreo procedente de una suma anterior. Su esquema sería:
 A+n+CF
RESTA SIN ACARREO:
Consiste en restar un número del contenido del registro "A", y obtener el resultado en este mismo registro. El indicador de acarreo no interviene en la operación. Se consideran números negativos los superiores a 127 (7Fh) de la forma que se explicó en el capítulo relativo a los sistemas de numeración; es decir, el número 255 (FFh) se considera "-1", el 254 (FEh) se considera "-2" y así sucesivamente, hasta 128 (80h) que se considera "-128". El paso de 127 a 128 o viceversa se indica poniendo a "1" el flag de "overflow" (P/V) del registro "F". Su esquema sería:
 A-n
RESTA CON ACARREO:
Igual que el anterior, salvo que también se resta el indicador de acarreo (CF) del registro "F". Su esquema sería:
 A-n-CF
INCREMENTO:
Consiste en sumar uno al contenido de un registro que se especifica en la instrucción. Su esquema es:
 R+1
Donde "R" representa un registro cualquiera de 8 a 16 bits. Si se trata de un registro doble (de 16 bits) se incrementa el registro de orden bajo (por ejemplo, en el "BC" se incrementa "C"), y si ello hace que este pase a valer "0", se incrementa también el de orden alto.
DECREMENTO:
Es la inversa de la anterior, consiste en restar uno al contenido de un registro. Su esquema es:
 R-1
Si se trata de un registro doble, se decrementa el de orden bajo y, si esto hace que pase a valer 255 (FFh), se decrementa también el de orden alto.
Si el registro incrementado o decrementado es de 8 bits, resultan afectados los indicadores del registro "F".
COMPARACIONES:
Estas instrucciones permiten comparar el contenido del acumulador con un número. Para ello, se resta el número del contenido del acumulador, pero el resultado no se almacena en ninguna parte, simplemente, se alteran determinados flags del registro "F", lo que nos indica si el número era menor, igual o mayor que el contenido del acumulador. Si era igual, se pone a "1" el flag "Z" (indicador de "cero"). Si el número era mayor, se pone a "1" el flag "S" (indicador de "signo").
AJUSTE DECIMAL:
Esta instrucción realiza un ajuste del contenido del acumulador para que, en vez de estar comprendido entre "00h" y "FFh", lo esté entre "00h" y "99h". Si se produce acarreo, se indica mediante el flag correspondiente. Para realizar esta operación se toma en cuenta el estado de los indicadores de "acarreo" (C) y "semi-acarreo" (H). Su finalidad es la de permitir realizar operaciones en "BCD" (Decimal Codificado en Binario).
COMPLEMENTO:
Consiste en realizar un "complemento a 1" del acumulador, es decir, cambiar los "unos" por "ceros" y los "ceros" por "unos".
NEGACIÓN:
Consiste en realizar un "complemento a 2" del acumulador, es decir, realizar un "complemento a 1" y, luego, sumarle "1". Lo que se obtiene es el "negativo" del número que teníamos en el acumulador. El efecto es el mismo que si restáramos el acumulador de "cero", es decir:
 0-A
EL FLAG DE ACARREO:
Existen dos instrucciones que afectan al indicador de acarreo del registro "F", es posible ponerlo a "1" o "complementarlo" (ponerlo a "1" si era "0" y viceversa). No se ha previsto una instrucción para poner a "0" el flag de acarreo, dado que esto se puede conseguir haciendo un "AND" o un "OR" del acumulador consigo mismo.
Veamos ya las instrucciones:
Grupo de instrucciones aritméticas para 8 bits
En este grupo de instrucciones los registros usados se indican con "r" según el siguiente código:
"r"
código
A
111
B
000
C
001
D
010
E
011
H
100
L
101
ADD, «sumar» en inglés: La función básica de esta instrucción es sumar sobre el registro acumulador el valor indicado por el operando. Ejecuta una suma binaria de ambos datos y no altera el contenido del operando.

ADD A,r
OBJETO:
Suma el registro acumulador "A" con el registro indicado por "r", dejando el resultado en el registro acumulador.
CODIGO MAQUINA:
1 0 0 0 0 <--- r --->
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
NOTA: Se entiende que hay acarreo desde el bit 3 cuando éste pasa de ser "1" a ser "0". Se entiende que hay desbordamiento si el resultado pasa de ser "positivo" a ser "negativo" o viceversa. Estas observaciones son válidas para todas las operaciones aritméticas.
CICLOS DE MEMORIA:
1
CICLOS DE RELOJ:
4
EJEMPLO:
ADD A,B
Valor del registro "A":
(A):
0 0 1 0 1 0 0 1
29h
Valor del registro "B":
(B):
0 1 0 0 1 0 1 0
4Ah
Ejecutamos la instrucción:
ADD A,B:
1 0 0 0 0 0 0 0
80h
Valor del registro "A" después de la ejecución:
(A):
0 1 1 1 0 0 1 1
73h
El valor del registro "B" después de la ejecución no varía.
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
0
0
x
1
x
0
0
0
Observe que hubo acarreo desde el bit 3.

ADD A,n
OBJETO:
Suma el registro acumulador "A" con el número entero de 8 bits "n", dejando el resultado en el registro acumulador.
CODIGO MAQUINA:
1 1 0 0 0 1 1 0
<-------- n -------->
C6h
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
CICLOS DE MEMORIA:
2
CICLOS DE RELOJ:
7
EJEMPLO:
ADD A,24
Valor del registro "A":
(A):
0 0 1 0 0 1 1 0
26h
Instrucción:
ADD A,24:
1 1 0 0 0 1 1 0
0 0 0 1 1 0 0 0
C6h
18h
Valor del registro "A" después de la ejecución:
(A):
0 0 1 1 1 1 1 0
3Eh
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
0
0
x
0
x
0
0
0

ADD A,(HL)
OBJETO:
Suma el registro acumulador "A" con el octeto de la posición de memoria direccionada por el contenido del par de registros "HL", y deja el resultado en el registro acumulador.
CODIGO MAQUINA:
1 0 0 0 0 1 1 0
86h
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
CICLOS DE MEMORIA:
2
CICLOS DE RELOJ:
7
EJEMPLO:
ADD A,(HL)
Valor del par de registros "HL":
(H):
(L):
0 1 0 0 1 1 0 0
1 1 1 1 0 0 1 1
4Ch
F3h
Valor de la posición de memoria 4CF3h:
(4CF3h):
1 0 0 1 1 1 0 0
9Ch
Valor del registro "A":
(A):
1 0 1 1 0 0 0 0
B0h
Instrucción:
ADD A,(HL):
1 0 0 0 0 1 1 0
86h
Valor del registro "A" después de la ejecución:
(A):
0 1 0 0 1 1 0 0
46h
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
0
0
x
0
x
0
0
1
Observe, que ha habido acarreo desde el bit 7.

ADD A,(IX+d)
OBJETO:
Suma el registro acumulador "A" con el octeto de la posición de memoria direccionada por el valor que resulta de: añadir al contenido del registro índice "IX" el entero de desplazamiento "d", el cual puede adquirir los valores desde -128 a +127. Deja el resultado en el registro acumulador.
CODIGO MAQUINA:
1 1 0 1 1 1 0 1
1 0 0 0 0 1 1 0
<-------- d -------->
DDh
86h
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
CICLOS DE MEMORIA:
5
CICLOS DE RELOJ:
19
EJEMPLO:
ADD A,(IX+7)
Suponemos que el registro "A" contiene el número 80h (128) y vamos a sumarle el contenido de la posición de memoria 9318h que suponemos que es también 80h (128). Para acceder a esta posición utilizamos direccionamiento indexado. El resultado deberá ser 256, es decir, 100h; pero como este número excede la capacidad del acumulador, obtendremos "00h" en el acumulador y "1" en el indicador de acarreo.
Esto ocurrirá con frecuencia. Cuando el resultado de una suma sea mayor de 255 (FFh), nos aparecerá el flag de acarreo a "1", y el acumulador contendrá ese número menos 256, para los matemáticos, lo que obtenemos en el acumulador es el "módulo 256" del resultado de la suma. Cuando, después de una suma, el indicador de acarreo sea "1", podemos saber el verdadero resultado si sumamos 256 al contenido del acumulador. Veamos ahora el ejemplo.
Valor del registro "IX":
(IX):
1 0 0 1 0 0 1 1
0 0 0 1 0 0 0 1
93h
11h
Valor de la posición de memoria 9318h:
(9318h):
1 0 0 0 0 0 0 0
80h
Valor del registro "A":
(A):
1 0 0 0 0 0 0 0
80h
Instrucción:
ADD A,(IX+7):
1 1 0 1 1 1 0 1
1 0 0 0 0 1 1 0
0 0 0 0 0 1 1 1
DDh
86h
07h
Valor del registro "A" después de la ejecución:
(A):
0 0 0 0 0 0 0 0
00h
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
0
1
x
0
x
1
0
1
Observe que se nos han puesto a "1" los indicadores de acarreo, cero y rebosamiento. El de acarreo, porque el resultado es mayor de 255; el de cero, porque el acumulador contiene "cero"; y el de rebosamiento, porque el bit 7 ha pasado de ser "1" a "0", lo que se interpreta como un cambio de signo; en este caso, el signo no nos interesa porque el numero no puede ser negativo, por lo que, simplemente, ignoramos el indicador "P/V".

ADD A,(IY+d)
OBJETO:
Suma el registro acumulador "A" con el octeto de la posición de memoria direccionada por el valor que resulta de: añadir al contenido del registro índice "IY" el entero de desplazamiento "d", el cual puede adquirir los valores desde -128 a +127. Deja el resultado en el registro acumulador.
CODIGO MAQUINA:
1 1 1 1 1 1 0 1
1 0 0 0 0 1 1 0
<-------- d -------->
FDh
86h
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
CICLOS DE MEMORIA:
5
CICLOS DE RELOJ:
19
EJEMPLO:
ADD A,(IY-6)
En esta ocasión vamos a usar, de nuevo, direccionamiento indexado para acceder al operando. Los dos números a sumar serán 7Fh y 03h, el resultado será 82h (F más 3 = 2 y nos llevamos una; 7 más 0 más 1 = 8). Como se vé, sumar en hexadecimal es lo mismo que hacerlo en decimal.
Valor del registro "IY":
(IY):
1 0 1 0 0 0 1 1
0 1 1 1 1 0 0 0
A3h
78h
Valor de la posición de memoria A372h:
(A372h):
0 1 1 1 1 1 1 1
7Fh
Valor del registro "A":
(A):
0 0 0 0 0 0 1 1
03h
Instrucción:
ADD A,(IY-6):
1 1 1 1 1 1 0 1
1 0 0 0 0 1 1 0
1 1 1 1 1 0 1 0
FDh
86h
FAh
Valor del registro "A" después de la ejecución:
(A):
1 0 0 0 0 0 1 0
82h
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
1
0
x
1
x
1
0
0
Observe, que el indicador de signo (S) se activa por estar activo el bit 7, el tratar este número como negativo o no, dependerá del programador. El indicador P/V se activa por superar el máximo valor del octeto en complemento a dos (el bit de signo ha pasado de "0" a "1"). Finalmente, el indicador H está a "1" porque hubo acarreo desde el bit 3.
Las instrucciones de sumar, como su nombre indica, suman; pero con lo visto hasta el momento sólo suman un octeto. Por lo tanto se limita la suma al número 255, considerando todos los positivos.
Este problema se soluciona con las instrucciones que se explican a continuación.
ADC (ADd with Carry), sumar con acarreo. Básicamente consiste en una suma binaria de dos octetos más el bit de acarreo. Esto quiere decir que si en una suma anterior el bit de acarreo está activo, "nos llevamos una", esa unidad hay que tenerla en cuenta en el octeto superior si existe.
Por ejemplo en una suma convencional en decimal.
7328 + 4256
al sumar las unidades 8 y 6 nos llevamos un 1 a las decenas; con las decenas y las centenas no hay acarreo, y de nuevo en las unidades de millar hay acarreo a las decenas de millar.
1
1
acarreo
7
3
2
8
+
4
2
5
6
1
1
5
8
4
Visto esto, se entenderá fácilmente, que sumando octetos se acarrea 1 al octeto superior cuando se supera el valor decimal 255 (FFh). Ver figura 6-1.
BINARIO

11000110
10011100
01001001
10000000
SUMANDO
00011000
10110000
00111010
10000000
SUMANDO
0
+
1
0
1
ACARREO

11011111
01001100
10000100
00000000
RESULTADO

HEXADECIMAL

C6
9C
49
80
SUMANDO
18
B0
3A
80
SUMANDO
+
1
0
1
ACARREO

DF
4C
84
00
RESULTADO

DECIMAL

190
156
73
128
SUMANDO
24
176
58
128
SUMANDO
+
1
0
1
ACARREO

223
76
132
0
RESULTADO
Fig 6-1. Suma de varios objetos con acarreo.
Esta es la manera de sumar, en binario, cantidades superiores a 255 decimal; usando las instrucciones que se describen a continuación.

ADC A,r
OBJETO:
Suma el registro acumulador "A", más el bit de acarreo, con el registro indicado por "r", dejando el resultado en el registro acumulador.
CODIGO MAQUINA:
1 0 0 0 1 <--- r --->
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
NOTA: Se entiende que hay acarreo desde el bit 3 cuando éste pasa de ser "1" a ser "0". Se entiende que hay desbordamiento si el resultado pasa de ser "positivo" a ser "negativo" o viceversa. Estas observaciones son válidas para todas las operaciones aritméticas.
CICLOS DE MEMORIA:
1
CICLOS DE RELOJ:
4
EJEMPLO:
ADC A,D
Suponemos que tenemos el flag de acarreo a "1", puede ser, por ejemplo, como resultado de una suma anterior. Por tanto, vamos a sumar 49h + 22h + 1. El resultado debe ser 6Ch.
Valor del registro "A":
(A):
0 1 0 0 1 0 0 1
49h
Valor del registro "D":
(D):
0 0 1 0 0 0 1 0
22h
Bit de acarreo = 1
Ejecutamos la instrucción:
ADC A,D:
1 0 0 0 1 0 1 0
8Ah
Valor del registro "A" después de la ejecución:
(A):
0 1 1 0 1 1 0 0
6Ch
Indicadores de condición después de la ejecución:
S
Z
H
P/V
N
C
0
0
x
0
x
0
0
0
Esta vez no ha habido acarreo, semi-acarreo ni cambio de signo.

ADC A,n
OBJETO:
Suma el registro acumulador "A", más el bit de acarreo, con el número entero de 8 bits "n", dejando el resultado en el registro acumulador.
CODIGO MAQUINA:
1 1 0 0 1 1 1 0
<-------- n -------->
CEh
INDICADORES DE CONDICIÓN A LOS QUE AFECTA:
S
;
pone 1 - si el resultado es negativo
pone 0 - en cualquier otro caso
Z
;
pone 1 - si el resultado es cero
pone 0 - en cualquier otro caso
H
;
pone 1 - si hay acarreo desde el bit 3
pone 0 - en cualquier otro caso
N
;
pone 0 - siempre
C
;
pone 1 - si hay acarreo desde el bit 7
pone 0 - en cualquier otro caso
P/V
;
pone 1 - si hay desbordamiento (overflow)
pone 0 - en cualquier otro caso
CICLOS DE MEMORIA:
2
CICLOS DE RELOJ:
7




VIDEOS


Comentarios

Entradas más populares de este blog

Tipos de Registro (lenguaje ensamblador)

2.5 Comparación y prueba Y 2.6 Saltos