Páginas vistas en total

viernes, 31 de julio de 2015

Programar en android TRS-80 y ensamblador Z80 - Pz2

VER VIDEO PZ2
En el blog anterior vimos el programa PZ1 para hacer una simple suma y resta con mensajes desplegamos los resultados ahora completaremos el programa PZ2 con introducir los datos por el teclado de la pantalla.

1.Ejecutamos TRS-80 y aparecen 4 modelos y seleccionamos el último TRS80 III con NEWDOS80 presionamos el menu izquierdo y presionamos START o RESUME y aparece una pantalla del sistema operativo NEWDOS80 con el mensaje NewDos/80 Ready está listo para recibir comandos del sistema operativo. Hay varios comandos como:
FREE indica la cantidad de espacio libre en granules, cada granulo equivale a dos sectores de 256 bytes.
Drive0  NEWDOS80  06/00/00  40 tracks  13 Fdes  51 Grans
Tiene 40 tracks con 51 Gránulos  libres en el Drive 0
LIST archivo Despliega el contenido de un archivo de texto.
KILL archivo Elimina un archivo almacenado en el disco.
RENAME Cambia el nombre de un archivo.
COPY archivo1 archivo2 Copia el archivo1 a un nuevo archivo2 en el disco.
DIR Despliega el directorio de todos los archivos almacenados en el disco.
Ahora  introducimos DIR y aparece el directorio de programas y archivos SRC o ASM y CMD. Vemos el programa EDTASM/CMD es el editor y ensamblador que utilizaremos.
2.Introducimos EDTASM y aparece la pantalla del editor ensamblador TRS-80 EDITOR/ASSEMBLER 1.1 y un * asterisco. Si ya tenemos el programa en disco lo cargamos en memoria con L D=PZ2/SRC o ASM y aparece el mensaje APPARAT ASSEMBLER APPENDAGE, VERSION 3 y * asterisco, listo para recibir comandos. Hay varios comandos como Pnl1:nl2 para desplegar líneas, Dnl1:nl2 de eliminar líneas y se aplican a una sola línea o a un rango de líneas, el carácter # indica el inicio y * el final, es oportuno indicar que con la tecla SHIFT aparecen más caracteres como # * / y otros. con P#:* desplegara todas las líneas. Rnl para reemplazar una línea. Enl para editar una línea una vez introducido acepta subcomandos como X para desplegar la línea y el cursor aparece al final y se puede retroceder con <- para corregir la línea. Inl para insertar líneas a partir de una línea y se va incrementando en 10. Para introducir el programa usamos I insert y aparece la primera línea con 100 ahora línea por línea introducimos el programa y se va incrementando en 10. Como ejemplo cuando aparece 100 presionamos el tabulador -> y salta 8 posiciones escribimos ORG volvemos  a presionar -> salta 8 posiciones y escribimos 7000H y ahora presionamos ENTER  y aparece la siguiente línea de 110 así continuamos introduciendo todas las líneas hasta la última línea  ponemos END.
El lenguaje ensamblador del Z80 tiene un formato para las instrucciones, como una línea de texto siguiente.
ETIQUETA  CODIGO DE OPERACION   OPERANDOS  ;COMENTARIOS
ETIQUETA Indica una dirección a una instrucción y se usa para de alguna parte del programa de regresar a esta dirección.
CODIGO DE OPERACION Cada instrucción tiene un código para las operaciones de trasferencia, aritmética, lógicas, desplazamiento, rotación, saltos incondicionales y condicionales, llamadas de subrutinas, entrada y salida de dispositivos periféricos y de control.
OPERANDOS o DATOS Cada instrución tiene un código de operación y sus correspondientes operandos o datos para ejecutar la instrucción.
COMENTARIOS Sirven para comentar la instrucción con una descripción sencilla y corta iniciando con ; punto y coma. Cuando es larga se utiliza toda la línea iniciando con ; punto y coma y todo el comentario.
Instrucciones del lenguaje ensamblador o pseudo instrucciones no tiene un código de operación, pero son importantes conocerlas tal como:
ORG Indica la dirección de inicio del programa.
EQU  Define o iguala el nombre de una variable un valor.
DEFB Define con un nombre un byte de memoria.
DEFW Define con un nombre una palabra de 2 bytes de memoria.
DEFM Define con un nombre una área de memoria para mensajes.
DEFS N Define un número N de bytes de memoria con un nombre una área de trabajo.
END Indica el fin del programa.
Programa PZ2
Ahora introducimos el siguiente programa PZ2 pide se introduzca DATO1 y DATO2 como 4 num hexadec se suma y resta y despliega los resultados.
                 ORG       7000H
DESP1     EQU    33H
;DATO1    EQU    02
;DATO2    EQU    02
INICIO     LD       HL,MSG1   ;DESPL DATO1
DMSG1   LD       A,(HL)         ;A=CARACTER
                 CALL   DESP         ;DESPL CARACT
                 INC      HL              ;INCR A SIG
                 CP       '='                ;ES FIN DE MSG1
                 JR     NZ,DMSG1 ;NO, OTRO CARAC
                 CALL  E4HEX
                 LD      (DATO1),HL                
                 LD      (DATO3),HL ;DATO3=DATO1
                 LD        A,' '
                 CALL   DESP         ;DESPL ESPACIO
                 CALL   D4HEX       ;DESPL HEXAD
                 LD        A,' '
                 CALL   DESP         ;DESPL ESPACIO
                 LD        HL,(DATO1)
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP         ;SIG LINEA
                 LD        HL,MSG2
DMSG2   LD        A,(HL)        ;DESPL DATO2=
                CALL    DESP
                 INC      HL
                 CP        '='
                 JR        NZ,DMSG2
                 CALL  E4HEX
                 LD      (DATO2),HL
                 LD        A,' '
                 CALL    DESP         ;DESPL ESPACIO
                 CALL    D4HEX       ;DESPL HEXADEC
                 LD        A,' '
                 CALL    DESP         ;DESPL ESPACIO
                 LD        HL,(DATO2)
                 CALL   DENT          ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP          ;SIG LINEA
;SUMA 2 BYTES DE DATO1 Y DATO2
;RESULTADO QUEDA EN DATO1
;DATO1-X1X2-2 BYTES
;DATO2-Y1Y2-2 BYTES
;X1=X1+Y1  X2=X2+Y2
                 LD       IX,DATO1+1 ;1ER BYTE DER
                 LD       IY,DATO2+1
                 LD       A,(IX)             ;CARGA EN A
                 ADD    A,(IY)            ;SUMA 1ER BYTE
                 LD       (IX),A      ;GUARDA EN DATO1
                 LD       A,(IX-1)         ;SEG BYTE
                ADC    A,(IY-1)      ;SUMA 2BYTE Y C
                 LD       (IX-1),A     ;GUADA EN DATO1
                 CALL  C,DMSG5     ;DESBORDE
                 LD       HL,MSG3
DMSG3   LD        A,(HL)         ;DESPL SUMA=
                 CALL   DESP
                 INC      HL
                 CP       '='
                 JR       NZ,DMSG3
                 LD       HL,(DATO1)
                 CALL   D4HEX       ;DESPL HEXAD
                 LD        A,' '
                 CALL    DESP
                 LD        HL,(DATO1)
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP
;RESTA DATO2 DE DATO3 RESULTADO EN
;DATO3 RECORDAR QUE DATO3=DATO1
;DATO3-X1X2-2 BYTES
;DATO2-Y1Y2-2 BYTES
;X1=X1-Y1  X2=X2-Y2
                 LD       IX,DATO3+1
                 LD       IY,DATO2+1
                 LD       B,1           ;B=2 BYTES
                 XOR    A              ;LIMPIA CARRY
OTRO      LD       AE,(IX)     ;CARGA BYTE
                SBC     A,(IY)       ;RESTA BYTE
                 LD       (IX),A      ; GUARDA BYTE
                 DEC    IX
                 DEC    IY
                 DEC    B               ;DECREM B
                JR       NZ,OTRO  ;RESTA OTRO BYTE
;
;RESTA BINARIA
;0000 0010-A=02
;0000 0010-B=02
;0000 0000-A=00 X
;
;0000 0010-ACAR
;1111 1101-B'
;0000 0001-+1
;1111 1110-B''
;
;1111 1100-ACAR
;0000 0010-A=02
;1111 1110-B''
;0000 0000-A=00 CY=1
;
                 LD       HL,MSG4
DMSG4   LD        A,(HL)         ;DESPL RESTA=
                 CALL   DESP
                 INC      HL
                 CP       '='
                 JR       NZ,DMSG4
                 LD       HL,(DATO3)
                 CALL   D4HEX       ;DESPL HEXAD
                 LD        A,' '
                 CALL   DESP
                 LD       HL,(DATO3)
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP
                 RET                         ; REGRESA SO
;SUBRUTINA PARA DESPLEGAR MSG5
;DESBORDE DE SUMA
DMSG5    LD        LD,MSG5
DMSG51  LD        A,(HL)
                  CALL   DESP
                  INC      HL
                  CP       13
                  JR        NZ,DMSG51
                  RET
;
;CODIGO ASCII
;30=0 31=1 32=2 33=3 34=4 35=5 36=6 37=7
38=8 39=9...41=A 42=B 43=C 44=D 45=E 46=F
;SUMA BINARIA    RESTA BINARIA
;0+0=0                     0-0=0
;0+1=1                     0-1=1  CY=1
;1+0=1                     1-0=1
;1+1=0 CY=1           1-1=0
;
;SUBRUTINA PARA INTRODUCIR POR
;TECLADO CUATRO NUM HEXAD  A HL
E4HEX     LD          HL,0       ;HL=0
E4HEX1  CALL     TECLA    ;A=DIGITO HEXAD
                 CP         13           ;ES FIN
                 RET        Z            ;SI REGRESA
                 CALL     DESP       ;DESP A
                 CP          '0'               ;ES < 30(0)
                 JR          C,E4HEX1   ;SI IGNORA
                 CP         3AH             ;ES =< 39(9)
                 JR          C,ROTAR    ;SI 0-9
                 CP         'A'                 ;ES <41(A)
                 JR          C,E4HEX1   ;SI IGNORA
                 CP         'G'                 ;ES >=47(G)
                 JR          NC,E4HEX1 ;SI IGNORA
                SUB        7                   ;ES A-F
ROTAR   AND        15                ;A=0FH
                ADD       HL,HL
                ADD       HL,HL          ;DESPLAZA HL
                ADD       HL,HL          ;4 BITS A LA IZQ
                ADD       HL,HL          ;
                LD          D,0               ;D=0
                LD          E,A               ;E=A
                ADD       HL,DE          ;
                JR          E4HEX1        ;SIG DIGITO
TECLA    CALL     49H
                RET             
;SUBRUTINA PARA CONVERTIR HEXADEC DEL REG A Y DESPLEGARLO EN ASCII
D2HEX    PUSH   AF              ;GUARDA AF
                 RRCA                      ;A=02
                 RRCA
                 RRCA
                 RRCA                     ;A=20
                 CALL    D2HEX1
                 POP     AF              ;A=02
D2HEX1  AND    0FH            ;A=00  A=02
                 ADD   30H             ;A=30  A=32
                 CP      3AH             ;ES 30-39(0-9)
                 JR      C,DESP       ;SI, DESPL 30-39(0-9)
                 ADD   A,7              ;NO, ES 41-46(A-F)
DESP       CALL DESP1        ;DESPL CARACTER
                 RET
;SUBRUTINA PARA DESPLEGAR DE HL 
;CUATRO NUM HEXAD
D4HEX     LD          A,H          ;NUM SUPERIOR
                 CALL     D2HEX
                 LD          A,L           ;NUM INFERIOR
                JR          D2HEX
;SUBRUTINA PARA DESPLEGAR  EN
;ENTEROS EL REG  A QUE ESTA EN HL
DENT      LD          BC,-10000  ;BC=D8F0
                 CALL     DDEC1
                 LD          BC,-1000    ;BC=FC18
                 CALL     DDEC1
                 LD         BC,-100        ;BC=FF9C
;
-100D -64H
;
;0000 0000 0110 0100-64
;
;0000 0000 0000 0110-ACARREO
;1111 1111 1001 1011-64'
;0000 0000 0000 0001-+1
;1111 1111 1001 1100-BC=FF9C
;
                 CALL    DENT1
                 LD         BC,-10     ;BC=FFF6
;-10=-A
;0000 0000 0000 1010-A
;
;0000 0000 0000 0010-ACARREO
;1111 1111 1111 0101-A'
;0000 0000 0000 0001-+1
;1111 1111 1111 0110-BC=FFF6
;
                 CALL    DENT1
                 LD         BC,-1      ;BC=FFFF
;-1
;0000 0000 0000 0001-1
;
;1111 1111 1111 1110-1'
;0000 0000 0000 0001-+1
;1111 1111 1111 1111-BC=FFFF
;
DENT1     LD         A,'0'-1     ;A=30-1=29
DENT2     INC       A              ;A=30
                 ADD     HL,BC       ;HL=FFF8
;
;BC=-100 BC=FF9C PARA HL=0002
;0000 0000 0000 0000-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1001 1100-BC
;1111 1111 1001 1110-HL=FF9D CY=0
;
;BC=-10 BC=FFF6 HL=0002
;0000 0000 0000 1100-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1111 0110-BC
;1111 1111 1111 1000-HL=FFF8 CARRY=0
;
;BC=-1 BC=FFFF HL=0002
;1111 1111 1111 1100-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1111 1111-BC
;0000 0000 0000 0001-HL=0001 CY=1 A=31
;
:1111 1111 1111 1110-ACARREO
;0000 0000 0000 0001-HL
;1111 1111 1111 1111-BC
;0000 0000 0000 0000-HL=0000 CY=1 A=32
;
;0000 0000 0000 0000-ACARREO
;0000 0000 0000 0000-HL
;1111 1111 1111 1111-BC
;1111 1111 1111 1111-HL=FFFF CY=0 A=32
;        
                 JR        C,DENT2
                 SBC      HL,BC
;
;BC=-100 BC=FF9C HL=FF9D
;1111 1111 1001 1110-HL=FF9D
;1111 1111 1001 1100-BC=FF9C
;
;0000 0000 0000 0110-ACAR
;0000 0000 0110 0011-BC'
;0000 0000 0000 0001-+1
;0000 0000 0110 0100-BC''
;
;1111 1111 1111 1000-ACAR
;1111 1111 1001 1110-HL
;0000 0000 0110 0100-BC''
;0000 0000 0000 0010-HL=0002 A=30->0
;
;BC=-10 BC=FFF6 HL=FFF8
;0000 0000 0000 0100-ACARREO
;1111 1111 1111 1000-HL=FFF8
;1111 1111 1111 0110-BC=FFF6
;
;0000 0000 0000 0010-ACAR
;0000 0000 0000 1001-BC'
;0000 0000 0000 0001-+1
;0000 0000 0000 1010-BC''
;
;1111 1111 1111 0000-ACAR
;1111 1111 1111 1000-HL=FFF8
;0000 0000 0000 1010-BC''
;0000 0000 0000 0010-HL A=30->0
;
;BC=-1 BC=FFFF HL=0000
;0000 0000 0000 0000-HL
;1111 1111 1111 1111-BC
;
;0000 0000 0000 0000-B'
;0000 0000 0000 0001-+1
;0000 0000 0000 0001-B''
;
;0000 0000 0000 0000-HL
;0000 0000 0000 0001-B''
;0000 0000 0000 0001-HL  A=32->2
;
                 CALL    DESP        ;A=CARACTER
                 RET
;
MSG1      DEFM 'DATO1='
MSG2      DEFM 'DATO2='
MSG3      DEFM 'SUMA ='
MSG4      DEFM 'RESTA='
MSG5      DEFM 'DESBORDE SUMA...'
                 DEFB  13
DATO1    DEFW  0000H
DATO2    DEFW  0000H
DATO3    DEFW  0000H
;                CALL   440DH
                 END     INICIO
Cuando se termina de introducir todo el programa, para salir de Insert presionamos BREAK y salimos a EDTASM apareciendo * listo para recibir más comandos.
3.Ahora ensamblamos el programa con: A /NO/WE indicando /NO no se genere el programa objeto CMD y con /WE se pare en la línea que tenga errores. Al ensamblar el programa y encuentra errores, se para en el número de línea con error. Se puede corregir con replace Rnl reemplace número de línea, aparece el número de línea e introducimos la línea correcta con ENTER termina y  reemplaza toda la línea. Con edit Enl presionamos ENTER  después introducimos X y despliega  toda línea colocando el cursor al final de la línea y con backspace <- retroceder hasta corregir el error.
Observamos que en la parte izquierda aparece el código de operación y sus operandos de cada instrucción de lenguaje ensamblador de la derecha. El total de errores y la cantidad en bytes del área de memoria que queda. Una tabla de símbolos o etiquetas usadas en el programa indicando el número de línea donde aparecen.
4.Cuando ya no hay errores se procede a guardar el programa fuente SRC o ASM con W D=PZ2/ASM y la primera vez  aparece el mensaje de FILE NO EXISTENT ...REPLAY C TO CREATE IT  dar C para crearlo. Si ya existe aparece FILE ALREADY EXISTS...USE IT...(Y OR NO) dar Y si va sobre escribir el archivo,  para tenerlo en disco y volver a llamarlo en cualquier momento.
5.Ahora generamos el programa objeto, introduciendo solo A y aparece el mensaje  OBJECT FILESPEC? introducimos el nombre PZ2/CMD y la primera vez  aparece el mensaje de FILE NO EXISTENT ...REPLAY C TO CREATE IT  dar C para crearlo. Si ya existe aparece FILE ALREADY EXISTS...USE IT...(Y OR NO) dar Y si va sobre escribir el archivo.
6.Ahora está listo para ejecutarse, salimos a NEWDOS80 con B y aparece NewDos/80 Ready, introducimos DIR y vemos que esten los archivos PZ2/ASM y PZ2/CMD. Para ejecutarlo introducimos el programa objeto PZ2/CMD o solo PZ2.
7.Ejecutamos el programa y nos pide se introduzca DATO1= tecleamos 4 dígitos hexadecimales y van apareciendo en la pantalla damos ENTER y despliega el DATO1  en hexadec y entero decimal. Ahora DATO2= tecleamos 4 dígitos hexadecimales y van apareciendo en la pantalla damos ENTER y despliega el DATO2  en hexadec y entero decimal. Se ejecuta y aparece SUMA= la suma de DATO1 y DATO2 en hexadec y en entero decimal. Aparece RESTA= la resta de DATO1 menos DATO2 en hexadec y entero decimal.
Las computadoras incluyendo los microprocesadores como el Z80 funcionan con bits de 1 y 0. La operación básica de sumar la realiza siguiendo la tabla de suma binaria.
0+0=0
0+1=1
1+0=1
1+1=0 Cy=1 Acarreo de 1
Sea el caso de sumar dos bytes, DATO1=2 y DATO2=2 en binario es:
0000 0100-Acarreo
0000 0010-Dato1=02
0000 0010-Dato2=02
0000 0100-Suma=04
Ejecutar el programa e introducir DATO1=2 DATO2=2  y ver los resultados.

En un byte de 8 bits se puede almacenar un binario de 00000000 hasta un máximo de 11111111 y para obtener el equivalente del máximo valor entero, aplicamos la siguiente formula de 2^n-1, tenemos 2 elevado a n-1, donde n es el número de bits, para un byte n=8-1=7 para cada posición de izquierda a derecha.
1x2^7+1x2^6+1x2^5+1x2^4+1x2^3+1x2x^2+1x2^1+1x2^0=1x128+1x64+1x32+1x16+1x8+1x4+1x2+1x1=128+64+32+16+8+4+2+1=255
Para 2 bytes el máximo número que puede almacenar es FFFF hexadecimal y es 65535 en enteros, cuando se pasa hay un desborde o carry.
Introducir DATO1=FFFF DAT2=0  y observar que sucede. Ahora introducir DATO1=FFFF DAT2=1 que sucede, hay un desborde en la suma.

Si tenemos un byte de 01001010 el valor entero es:
0x2^7+1x2^6+0x2^5+0x2^4+1x2^3+0x2x^2+1x2^1+0x2^0=0x128+1x64+0x32+0x16+1x8+0x4+1x2+0x1=0+64+0+0+8+0+2+0=64+8+2=74
Es muy importante indicar que el byte de 01001010 se puede representar en hexadecimal como 4A y es igual al valor como entero de 74. Pero muy diferente 74 como hexadecimal, su valor como entero es 117.
Si introducimos en nuestro programa:74 o 74D     Lo considera como entero pero lo convierte a hexadecimal  y equivale a 4A. Lo concidera como hexadecimal y equivale a
74 de valor entero y sin la H dará un error.
Entonces las operaciones aritméticas solo acepta EDTASM en hexadecimales de valores enteros y al ejecutarse el programa objeto convierte de hexadecimal a binario y hace las operaciones en binario y los resultados los convierte y quedan en hexadecimal. Es muy pero muy importante entender estas representaciones de los números enteros como hexadecimal y binario. Pero también se pueden hacer operaciones con decimales  + y - utilizando aritmética de punto flotante.

sábado, 13 de junio de 2015

Programar en android TRS-80 y ensamblador Z80 - pz1

VER VIDEO PZ1
En el blog PZ anterior vimos este programita:
                 ORG   7000H
DATO1    EQU    02
DATO2    EQU    02
                 LD       A,DATO1
                 LD       B,DATO2
                 ADD    A,B
                 CALL   440DH
                 END
Simplemente SUMA=DATO1+DATO2=2+2=4 pero analicemos todo lo que se necesita para realizar la suma con una microcomputadora TRS80 III con el microprocesador Z80 el sistema operativo NEWDOS80 y el editor ensamblador EDTASM.
Resumiendo hicimos lo siguiente
1.Buscamos TRS-80 en Google Play al encontrarlo, lo instalamos en el teléfono con android4.






















2.Una vez instalado ejecutamos TRS-80 y aparecen 4 modelos y seleccionamos el último TRS80 III con NEWDOS80 presionamos el menu izquierdo y presionamos START o RESUME y aparece una pantalla del sistema operativo NEWDOS80 con el mensaje NewDos/80 Ready está listo para recibir comandos del sistema operativo. Hay varios comandos como:
FREE indica la cantidad de espacio libre en granules, cada granulo equivale a dos sectores de 256 bytes.
Drive0  NEWDOS80  06/00/00  40 tracks  13 Fdes  51 Grans
Tiene 40 tracks con 51 Granulos  libres en el Drive 0
LIST archivo Despliega el contenido de un archivo de texto.
KILL archivo Elimina un archivo almacenado en el disco.
RENAME Cambia el nombre de un archivo.
COPY archivo1 archivo2 Copia el archivo1 a un nuevo archivo2 en el disco.
DIR Despliega el directorio de todos los archivos almacenados en el disco.
Ahora  introducimos DIR y aparece el directorio de programas y archivos SRC o ASM y CMD. Vemos el programa EDTASM/CMD es el editor y ensamblador que utilizaremos.






















3.Introducimos EDTASM y aparece la pantalla del editor ensamblador TRS-80 EDITOR/ASSEMBLER 1.1 y un * asterisco. Si ya tenemos el programa en disco lo cargamos en memoria con L D=PZ/SRC o ASM y aparece el mensaje APPARAT ASSEMBLER APPENDAGE, VERSION 3 y * asterisco, listo para recibir comandos. Hay varios comandos como Pnl1:nl2 para desplegar líneas, Dnl1:nl2 de eliminar líneas y se aplican a una sola línea o a un rango de líneas, el carácter # indica el inicio y * el final, es oportuno indicar que con la tecla SHIFT aparecen más caracteres como # * / y otros. con P#:* desplegara todas las líneas. Rnl para reemplazar una línea. Enl para editar una línea una vez introducido acepta subcomandos como X para desplegar la línea y el cursor aparece al final y se puede retroceder con <- para corregir la línea. Inl para insertar líneas a partir de una línea y se va incrementando en 10. Para introducir el programa usamos I insert y aparece la primera línea con 100 ahora línea por línea introducimos el programa y se va incrementando en 10. Como ejemplo cuando aparece 100 presionamos el tabulador -> y salta 8 posiciones escribimos ORG volvemos  a presionar -> salta 8 posiciones y escribimos 7000H y ahora presionamos ENTER  y aparece la siguiente línea de 110 así continuamos introduciendo todas las líneas hasta la 170 con END.






















100                  ORG   7000H
110 DATO1    EQU    02
120 DATO2    EQU    02
130                  LD       A,DATO1
140                  LD       B,DATO3
150                 ADG    A,B
160                 CALL   440DH
170                 END    
El lenguaje ensamblador del Z80 tiene un formato para las instrucciones, como una línea de texto siguiente.
ETIQUETA  CODIGO DE OPERACION   OPERANDOS  ;COMENTARIOS
ETIQUETA Indica una dirección a una instrucción y se usa para de alguna parte del programa de regresar a esta dirección.
CODIGO DE OPERACION Cada instrucción tiene un código para las operaciones de trasferencia, aritmética, lógicas, desplazamiento, rotación, saltos incondicionales y condicionales, llamadas de subrutinas, entrada y salida de dispositivos periféricos y de control.
OPERANDOS o DATOS Cada intrución tiene un código de operación y sus correspondientes operandos o datos para ejecutar la instrucción.
COMENTARIOS Sirven para comentar la instrucción con una descripción sencilla y corta iniciando con ; punto y coma. Cuando es larga se utiliza toda la línea iniciando con ; punto y coma y todo el comentario.
Instrucciones del lenguaje ensamblador o pseudo instrucciones no tiene un código de operación, pero son importantes conocerlas tal como:
ORG Indica la dirección de inicio del programa.
EQU  Define o iguala el nombre de una variable un valor.
DEFB Define con un nombre un byte de memoria.
DEFW Define con un nombre una palabra de 2 bytes de memoria.
DEFM Define con un nombre una área de memoria para mensajes.
DEFS N Define un número N de bytes de memoria con un nombre una área de trabajo.
END Indica el fin del programa.
Cuando se termina de introducir todo el programa, para salir de Insert presionamos BREAK y salimos a EDTASM apareciendo * listo para recibir más comandos.






















4.Ahora ensamblamos el programa con: A /NO/WE indicando /NO no se genere el programa objeto CMD y con /WE se pare en la línea que tenga errores. Al ensamblar el programa y encuentra errores, se para en el número de línea con error. Se puede corregir con replace Rnl reemplace número de línea, aparece el número de línea e introducimos la línea correcta con ENTER termina y  reemplaza toda la línea. Con edit Enl presionamos ENTER  después introducimos X y despliega  toda línea colocando el cursor al final de la línea y con backspace <- retroceder hasta corregir el error.
Ensablamos el programa con A /NO/WE y detecta el siguiente error.
UNDEFINED SYMBOL
7002 0600        140              LD     B,DATO3
Damos break y aparece * y corregimos la línea introduciendo E140 y aparece la línea 140 presionamos X y se despliega la línea y aparece al final el cursor, retrocedemos con <- una posición y se borra el 3 ahora introducimos 2 y damos ENTER.
Volvemos a ensamblar el programa con A /NO/WE y detecta otro error.
ILLEGAL OPCODE
0150        ADG      A,B
Damos BREAK  e introducimos R150 y aparece la línea 0150 e introducimos la línea, presionamos tabulador -> y salta 8 posiciones introducimos ADD y otra vez -> salta 8 posiciones e introducimos A,B presionamos ENTER aparece NO ROOM BETWEEN LINES ignorarlo. Introducimos P#:* para desplegar todo el programa y ver que los cambios  realizados.
Volver a ensamblarlo con A /NO/WE y sin errores el programa ensamblado es:
7000                  100     ORG       7000H
02                      110    DATO1   EQU    02
02                      120    DATO2   EQU    02
7000 3E02        130                   LD    A,DATO1
7002 0602        140                   LD    B,DATO3
7004 80            150                  ADE  A,B
7005 CD0D44  160                  CALL 440DH
0000                  170                  END   INICIO
0000   TOTAL ERRORS
34932 TEXT AREA BYTES LEFT
DATO1 0002 110 130
DATO2 0002 120 140
INICIO  7000 130 170
Observamos que en la parte izquierda aparece el código de operación y sus operandos de cada instrucción de lenguaje ensamblador de la derecha. El total de errores y la cantidad en bytes del área de memoria que queda. Una tabla de símbolos o etiquetas usadas en el programa indicando el número de línea donde aparecen.
5.Cuando ya no hay errores se procede a guardar el programa fuente SRC o ASM con W D=PZ/ASM y la primera vez  aparece el mensaje de FILE NO EXISTENT ...REPLAY C TO CREATE IT  dar C para crearlo. Si ya existe aparece FILE ALREADY EXISTS...USE IT...(Y OR NO) dar Y si va sobre escribir el archivo,  para tenerlo en disco y volver a llamarlo en cualquier momento.
7.Ahora generamos el programa objeto, introduciendo solo A y aparece el mensaje  OBJECT FILESPEC? introducimos el nombre PZ/CMD y la primera vez  aparece el mensaje de FILE NO EXISTENT ...REPLAY C TO CREATE IT  dar C para crearlo. Si ya existe aparece FILE ALREADY EXISTS...USE IT...(Y OR NO) dar Y si va sobre escribir el archivo.
8.Ahora esta listo para ejecutarse, salimos a NEWDOS80 con B y aparece NewDos/80 Ready, introducimos DIR y vemos que esten los archivos PZ/SRC o ASM y PZ/CMD. Para ejecutarlo introducimos el programa objeto PZ/CMD o solo PZ en este caso no aparece nada en la pantalla. Pero internamente podemos analizar lo que sucede. En la memoria tenemos:
1)7000 3E02        
2)7002 0602       
3)7004 80            
4)7005 CD0D44 
1) LD A,02
7000-3E
7001-02
Todo programa inicia en alguna dirección de memoria, en este caso la dirección es 7000. Toda instrucción realiza varios ciclos de máquina y cada ciclo tiene varios estados o tiempos. Primero realiza un ciclo de operación o fetch de ir a memoria y obtener el código de operación 3E a la dirección de memoria que indica el contador de programa PC=7000. En T1 se activa el ciclo de máquina M1' también MEMREQ' en el bus de direcciones se activa la dirección de PC=7000 y en T2  se activa la señal de lectura a memoria RD' y activa el bus de datos con 3E leído de memoria y es recibido el codigo por el registro de instrucción IR=3E en la CPU decodifica el código en T3 y sabe que debe cargar el registro A con 02 que esta en memoria y debe de hacer un ciclo de lectura a memoria, se incrementa el contador de programa PC=7001 Inicia el ciclo de lectura se activa en T1 MEMREQ' y en T2 está activo el bus de direcciones con PC=7001 y también en T2 la señal de lectura RD' activa el bus de datos con 02 y en T3 es recibido por el registro A=02 completandose la intrucción de LD A,02.
2) LD B,02
7002-06
7003-02
Realiza un ciclo de operación o fetch de ir a memoria y obtener el código de operación 06 a la dirección de memoria que indica el contador de programa PC=7002. En T1 se activa el ciclo de máquina M1' también MEMREQ' en el bus de direcciones se activa la dirección de PC=7002 y en T2  se activa la señal de lectura a memoria RD' y activa el bus de datos con 06 leido de memoria y es recibido el codigo por el registro de instrucción IR=06 en la CPU decodifica el código en T3 y sabe que debe cargar el registro B con 02 que esta en memoria y debe de hacer un ciclo de lectura a memoria, se incrementa el contador de programa PC=7003 e inicia el ciclo de lectura,  se activa en T1 MEMREQ' y en T2 está activo el bus de direcciones con PC=7003 y también en T2 la señal de lectura RD' activa el bus de datos con 02 y en T3 es recibido por el registro B=02 completandose la intrucción de LD B,02.
3) ADD A,B
7004-80
Primero realiza un ciclo de operación o fetch de ir a memoria y obtener el código de operación 80 a la dirección de memoria que indica el contador de programa PC=7004. En T1 se activa el ciclo de máquina M1' también MEMREQ' en el bus de direcciones se activa la dirección de PC=7004 y en T2  se activa la señal de lectura a memoria RD' y activa el bus de datos con 80 leído de memoria y es recibido el código por el registro de instrucción IR=80 en la CPU decodifica el código en T3 y sabe que es una suma y en T4 suma B=02 a A=02 y el resultado queda en A=04 completando la instrucción ADD A, B.
4) CALL 440DH
7005-CD
7006-0D
7007-44
Realiza un ciclo de operación o fetch de ir a memoria y obtener el código de operación CD a la dirección de memoria que indica el contador de programa PC=7005. En T1 se activa el ciclo de máquina M1' también MEMREQ' en el bus de direcciones se activa la dirección de PC=7005 y en T2  se activa la señal de lectura a memoria RD' y activa el bus de datos con CD leído de memoria y es recibido el codigo por el registro de instrucción IR=CD en la CPU decodifica el código en T3 y sabe que debe de llamar a una subrutina y debe cargar el contador de programa PC=440D de dos bytes continuos de memoria por lo tanto dos ciclos de lectura a memoria, se incrementa el contador de progra PC=7006 e inicia el ciclo de lectura se activa en T1 MEMREQ' y en T2 está activo el bus de direcciones con PC=7006 y también en T2 la señal de lectura RD' activa el bus de datos con 0D y en T3 es recibido por el registro PC=000D Inicia otro ciclo de lectura se activa en T1 MEMREQ' y en T2 está activo el bus de direcciones con PC=7007 y también en T2 la señal de lectura RD' activa el bus de datos con 44 y en T3 es recibido por el registro PC=440D y se ejecuta la llamada saltando a PC=440D a ejecutar las instrucciones hasta encontrar un retorno RET y regrese a continuar con la siguiente instrucción después de la llamada completando la instrucción CALL 440DH.






















9.Para ver internamente la memoria y registros usamos DEBUG o depurador, el programa debe contener la lamada CALL 440DH. Salimos del emulador TRS-80 y con TASK MANAGER damos KILL a TRS-80 salimos y volvemos a entra a TRS-80 y aparece NewDos/80 Ready introducimos DEBUG y vuelve aparecer NewDos/80 Ready introducimos el programa objeto PZ/CMD o PZ y aparece la pantalla X  con tres áreas de memoria y entre ella los registros.























Introducimos  D7000 y aparece la memoria a partir de 7000.






















Ahora con G7000 se ejecuta el programa y podemos observar el contenido del registro A=04 y es el resultado de la suma.






















Con G0000 regresamos al sistema operativo y aparece NewDos/80 Ready.
El programa con DEBUG nos permite observar el contenido de los registros y memoria al ejecutarse el programa objeto. Sin DEBUG este programa al ejecutarse no envía ningún mensaje.
Ahora modificaremos el programa PZ y obtenemos el programa PZ1 para incluir mensajes de la suma y resta de enteros positivos.
                 ORG       7000H
DESP1     EQU    33H
DATO1    EQU    02
DATO2    EQU    02
INICIO     LD       HL,MSG1   ;DESPL DATO1
DMSG1   LD       A,(HL)         ;A=CARACTER
                 CALL   DESP         ;DESPL CARACT
                 INC      HL              ;INCR A SIG
                 CP       '='                ;ES FIN DE MSG1
                 JR     NZ,DMSG1 ;NO, OTRO CARAC
                 LD       A,DATO1    ;SI, A=02
                 CALL  D2HEX        ;DESPL HEXAD
                 LD        A,' '
                 CALL   DESP         ;DESPL ESPACIO
                 LD        HL,DATO1
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP         ;SIG LINEA
                 LD        HL,MSG2
DMSG2   LD        A,(HL)        ;DESPL DATO2=
                CALL    DESP
                 INC      HL
                 CP        '='
                 JR        NZ,DMSG2
                 LD        A,DATO2
                 CALL   D2HEX       ;DESPL HEXADEC
                 LD        A,' '
                 CALL    DESP         ;DESPL ESPACIO
                 LD        HL,DATO2
                 CALL   DENT          ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP          ;SIG LINEA
                 LD       A,DATO1     ;A=02
                 LD       B,DATO2     ;B=02
                 ADD    A,B               ;A=02+02=04
;SUMA
;0000 0010-A=02
;0000 0010-B=02
;0000 0100-A=04
;
                 LD       C,A
                 LD       B,0                ;BC=0002
                 LD       HL,MSG3
DMSG3   LD        A,(HL)         ;DESPL SUMA=
                 CALL   DESP
                 INC      HL
                 CP       '='
                 JR       NZ,DMSG3
                 LD       A,C              ;A=02
                 CALL   D2HEX       ;DESPL HEXAD
                 LD        HL,0
                 ADD     HL,BC        ;HL=0002
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP
                 LD       A,DATO1     ;A=02
                 LD       B,DATO2     ;B=02
                 SUB    B               ;A=02-02=00
;RESTA BINARIA
;0000 0010-A=02
;0000 0010-B=02
;0000 0000-A=00 X
;
;0000 0010-ACAR
;1111 1101-B'
;0000 0001-+1
;1111 1110-B''
;
;1111 1100-ACAR
;0000 0010-A=02
;1111 1110-B''
;0000 0000-A=00 CY=1
;
                 LD       C,A
                 LD       B,0                ;BC=0000
                 LD       HL,MSG4
DMSG4   LD        A,(HL)         ;DESPL RESTA=
                 CALL   DESP
                 INC      HL
                 CP       '='
                 JR       NZ,DMSG4
                 LD       A,C              ;A=00
                 CALL   D2HEX       ;DESPL HEXAD
                 LD        HL,0
                 ADD     HL,BC        ;HL=0000
                 CALL   DENT         ;DESPL ENTERO
                 LD        A,13
                 CALL   DESP
                 RET                         ; REGRESA SO
;
;CODIGO ASCII
;30=0 31=1 32=2 33=3 34=4 35=5 36=6 37=7
38=8 39=9...41=A 42=B 43=C 44=D 45=E 46=F
;SUMA BINARIA    RESTA BINARIA
;0+0=0                     0-0=0
;0+1=1                     0-1=1  CY=1
;1+0=1                     1-0=1
;1+1=0 CY=1           1-1=0
;
;SUBRUTINA PARA CONVERTIR HEXADEC DEL REG A=02 Y DESPLEGARLO EN ASCII
D2HEX    PUSH   AF              ;GUARDA AF
                 RRCA                      ;A=02
                 RRCA
                 RRCA
                 RRCA                     ;A=20
                 CALL    D2HEX1
                 POP     AF              ;A=02
D2HEX1  AND    0FH            ;A=00  A=02
                 ADD   30H             ;A=30  A=32
                 CP      3AH             ;ES 30-39(0-9)
                 JR      C,DESP       ;SI, DESPL 30-39(0-9)
                 ADD   A,7              ;NO, ES 41-46(A-F)
DESP       CALL DESP1        ;DESPL CARACTER
                 RET
;SUBRUTINA PARA DESPLEGAR  EN ENTEROS EL REG  A=02 QUE ESTA EN HL=0002
DENT       LD         BC,-100        ;BC=FF9C
;
-100D -64H
;
;0000 0000 0110 0100-64
;
;0000 0000 0000 0110-ACARREO
;1111 1111 1001 1011-64'
;0000 0000 0000 0001-+1
;1111 1111 1001 1100-BC=FF9C
;
                 CALL    DENT1
                 LD         BC,-10     ;BC=FFF6
;-10=-A
;0000 0000 0000 1010-A
;
;0000 0000 0000 0010-ACARREO
;1111 1111 1111 0101-A'
;0000 0000 0000 0001-+1
;1111 1111 1111 0110-BC=FFF6
;
                 CALL    DENT1
                 LD         BC,-1      ;BC=FFFF
;-1
;0000 0000 0000 0001-1
;
;1111 1111 1111 1110-1'
;0000 0000 0000 0001-+1
;1111 1111 1111 1111-BC=FFFF
;
DENT1     LD         A,'0'-1     ;A=30-1=29
DENT2     INC       A              ;A=30
                 ADD     HL,BC       ;HL=FFF8
;
;BC=-100 BC=FF9C HL=0002
;0000 0000 0000 0000-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1001 1100-BC
;1111 1111 1001 1110-HL=FF9D CY=0
;
;BC=-10 BC=FFF6 HL=0002
;0000 0000 0000 1100-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1111 0110-BC
;1111 1111 1111 1000-HL=FFF8 CARRY=0
;
;BC=-1 BC=FFFF HL=0002
;1111 1111 1111 1100-ACARREO
;0000 0000 0000 0010-HL
;1111 1111 1111 1111-BC
;0000 0000 0000 0001-HL=0001 CY=1 A=31
;
:1111 1111 1111 1110-ACARREO
;0000 0000 0000 0001-HL
;1111 1111 1111 1111-BC
;0000 0000 0000 0000-HL=0000 CY=1 A=32
;
;0000 0000 0000 0000-ACARREO
;0000 0000 0000 0000-HL
;1111 1111 1111 1111-BC
;1111 1111 1111 1111-HL=FFFF CY=0 A=32
;        
                 JR        C,DENT2
                 SBC      HL,BC
;
;BC=-100 BC=FF9C HL=FF9D
;1111 1111 1001 1110-HL=FF9D
;1111 1111 1001 1100-BC=FF9C
;
;0000 0000 0000 0110-ACAR
;0000 0000 0110 0011-BC'
;0000 0000 0000 0001-+1
;0000 0000 0110 0100-BC''
;
;1111 1111 1111 1000-ACAR
;1111 1111 1001 1110-HL
;0000 0000 0110 0100-BC''
;0000 0000 0000 0010-HL=0002 A=30->0
;
;BC=-10 BC=FFF6 HL=FFF8
;0000 0000 0000 0100-ACARREO
;1111 1111 1111 1000-HL=FFF8
;1111 1111 1111 0110-BC=FFF6
;
;0000 0000 0000 0010-ACAR
;0000 0000 0000 1001-BC'
;0000 0000 0000 0001-+1
;0000 0000 0000 1010-BC''
;
;1111 1111 1111 0000-ACAR
;1111 1111 1111 1000-HL=FFF8
;0000 0000 0000 1010-BC''
;0000 0000 0000 0010-HL A=30->0
;
;BC=-1 BC=FFFF HL=0000
;0000 0000 0000 0000-HL
;1111 1111 1111 1111-BC
;
;0000 0000 0000 0000-B'
;0000 0000 0000 0001-+1
;0000 0000 0000 0001-B''
;
;0000 0000 0000 0000-HL
;0000 0000 0000 0001-B''
;0000 0000 0000 0001-HL  A=32->2
;
                 CALL    DESP        ;A=CARACTER
                 RET
;
MSG1      DEFM 'DATO1='
MSG2      DEFM 'DATO2='
MSG3      DEFM 'SUMA ='
MSG4      DEFM 'RESTA='
;                CALL   440DH
                 END     INICIO
Utilizamos los pasos del 2 al 8 para introducir el programa, ensamblarlo y ejecutarlo obteniendo los resultados deseados.























Una vez que se ejecute correctamente podemos hacer dos cambios al programa.
1.Cambiar DATO2 de 2  a DATO2 con 270  Vemos  la línea:
130 DATO2    EQU   2
Editamos con E130 y después introducimos X aparece el cursor, escribir 70 y dar ENTER y queda
130 DATO2    EQU   270
Ensamblar con A /NO/WE y observar que sucede. Al ensamblar nos da este mensaje.
FIELD OVERFLOW
702D    3E0E   00340    LD    A,DATO2
Al ensamblar el programa checa que los operandos no pasen de 255.
2.Cambiar DATO2   2 a DATO2  -2 y también ver que pasa. Al ensamblar con A /NO/WE nos da este mensaje.
FIELD OVERFLOW
702D    3E0E   00340    LD    A,DATO2
El programa no acepta enteros negativos.
Las computadoras incluyendo los microprocesadores como el Z80 funcionan con bits de 1 y 0. La operación básica de sumar la realiza siguiendo la tabla de suma binaria.
0+0=0
0+1=1
1+0=1
1+1=0 Cy=1 Acarreo de 1
Sea el caso de sumar dos bytes, Dato1=02 y Dato2=02 en binario es:
0000 0100-Acarreo
0000 0010-Dato1=02
0000 0010-Dato2=02
0000 0100-Suma=04
En un byte de 8 bits se puede almacenar un binario de 00000000 hasta un máximo de 11111111 y para obtener el equivalente del máximo valor entero, aplicamos la siguiente formula de 2^n-1, tenemos 2 elevado a n-1, donde n es el número de bits, para un byte n=8-1=7 para cada posición de izquierda a derecha.
1x2^7+1x2^6+1x2^5+1x2^4+1x2^3+1x2x^2+1x2^1+1x2^0=1x128+1x64+1x32+1x16+1x8+1x4+1x2+1x1=128+64+32+16+8+4+2+1=255
Si tenemos un byte de 01001010 el valor entero es
0x2^7+1x2^6+0x2^5+0x2^4+1x2^3+0x2x^2+1x2^1+0x2^0=0x128+1x64+0x32+0x16+1x8+0x4+1x2+0x1=0+64+0+0+8+0+2+0=64+8+2=74
Es muy importante indicar que el byte de 01001010 se puede representar en hexadecimal como 4A y es igual al valor como entero de 74. Pero muy diferente 74 como hexadecimal, su valor como entero es 117. Si tenemos en nuestro programa:
DATO1     EQU     74 o 74D    
Lo considera como entero pero lo convierte a hexadecimal  y equivale a 4A.
DATO1     EQU     4AH
Lo considera como hexadecimal y equivale a
74 de valor entero y sin la H dará un error.
Cambiar los datos del programa como
120 DATO1     EQU      4AH
130 DATO2     EQU      74
Ensamblar con A /NO/WE y si resulta sin errores guarda el archivo con W D=PZ1/ASM y ahora se crea el programa objeto PZ1/CMD Se ejecuta y obtenemos los resultados deseados.






















Ahora cambiar los datos como:
120 DATO1     EQU      94
130 DATO2     EQU      53
Ensamblar con A /NO/WE y si resulta sin errores guarda el archivo con W D=PZ1/ASM y ahora se crea el programa objeto PZ1/CMD Se ejecuta y obtemos los resultados deseados.





















Entonces las operaciones aritméticas solo aceptan hexadecimales de valores enteros y al ejecutarse el programa objeto convierte de hexadecimal a binario y hace las operaciones en binario y los resultados los convierte y quedan en hexadecimal. Es muy pero muy importante entender estas representaciones de los números enteros como hexadecimal y binario. Pero también se pueden hacer operaciones con decimales  + y - utilizando aritmética de punto flotante.

sábado, 9 de mayo de 2015

Programar en android TRS-80 y ensamblador Z80 - Pz

Programar el emulador TRS-80 en android el microprocesador Z80 de la microcomputadora TRS80 III con el editor ensamblador EDTASM del sistema operativo NEWDOS80.
VER VIDEO PZ
El TRS-80 emula una línea de microcomputadoras de la compañía TRS de fin de los años de 1970. Inicio con el modelo trs80 I continuo con el trs80 III y terminino con el trs80 IV y después salieron  otros modelos. Los tres modelos utilizaron el microprocesador Z80 de 8 bits. Internamente tiene varios registros, contadores y apuntadores, un sumador y buses para comunicarse internamente.                 
Para comunicarse externamente también utiliza buses de Datos, Direcciones y de Control, con las memorias RAM ROM y los puertos de los dispositivos de entrada y salida I/O como Leds de salida, Switches de entrada y una grabadora de Cassets. Los buses tiene tres estados uno de señal baja activa, otro de señal alta activa y el estado de alta impedancia que no conduce señales.

                                                                  
Señales y Buses del Z80
El chip del Z80 tiene 40 pines con:
1.El bus de direcciones de 16 bits unidireccional
2.El bus de datos de 8 bits bidireccional
3.El bus de control con 16 bits con las siguientes señales:
Control del sistema
M1' Señal de salida negativa, activa indica inicio ciclo de máquina fetch o de operación para obtener una instrucción de memoria.
MREQ' Señal de salida negativa, activa indica un requerimiento de acceso a memoria
IOREQ' Señal de salida negativa, activa indica un requerimiento de entrada-salida
RD' Señal de salida negativa, activa indica una lectura de memoria o de un dispositivo.
WR' Señal de salida negativa, activa indica una escritura a memoria o un dispositivo.
RFSH' Señal de salida negativa, activa indica un refresco de memoria.
Control del CPU
HALT' Señal de salida negativa, activa fue generada por una introducción HALT e indica el alto del cpu.
WAIT' Señal de entrada negativa, activa indica tiempo de espera para memorias lentas
INT' Señal de entrada negativa, activa indica una interrupción enmascarable
NMI' Señal de entrada negativa, activa indica una interrupción no enmascarable
RESET' Señal de entrada negativa, activa inicia el funcionamiento del CPU y genera la dirección 0000 y la envía a la memoria para ejecutar la primera instrucción.
Control del Bus
BUSRQ' Señal de entrada negativa, activa indica el requerimiento de los buses para una transferencia de acceso a memoria directo DMA
BUSACK' Señal de salida negativa, activa indica el reconocimiento del uso de los buses para una transferencia de acceso a memoria directo DMA.
Otras señales
CLK Señal que indica la entrada del reloj externo generado por un oscilador.
+5V Voltaje positivo
GND Tierra
       

Registros del Z80
El Z80 tiene  los siguientes registros principales de 8 bits que puede manipular el programador.
A, F, B, C, D, E, H, L
Algunos se pueden combinar en pares de 16 bits: BC, DE, HL
El registro F indica el estado de los bits banderas o Flags resultado de las operaciones
       7    6   5   4    3     2     1    0
F= | S | Z | X | H | X | P/V | N | C |
S Bandera Signo o Sign Flag 1:negativo
Z Bandera Cero o Zero Flag 1:cero
H Bandera Medio Acarreo o Half Carry Flag 1: acarreo del bit 3 al 4
P Bandera de Paridad o Parity Flag 1: par
V Bandera de Sobre flujo o Overflow Flag 1:sobreflujo
N Bandera de Operación o Operation Flag 1:operación anterior resta
C Bandera de Acarreo o Carry Flag 1: acarreo 
Los registros alternos de ocho bits para intercambio de los registros en las interrupciones:
A', F', B', C', D', E', H', L'
IX, IY Registros index, para indexar tablas de datos y buscar algún valor.
Adder o Sumador de 8 y 16 bits una entrada es el registro o el acumulador y la salida o resultado de la operación regresa al acumulador A. La otra entrada es de otro registro, memoria o puertos de entrada-salida.
SP Registro apuntador stack o de pila, para guardar valores de rutinas y operaciones de expresiones matemáticas.
PC Contador de programa, lleva el control de la dirección de la siguiente instrucción a ejecutar
INC Es un incrementador o decrementador en  1, lo usa el contador de programa PC y otras instrucciones.
RF Registro refresh o de refresco de la memoria dinámica, solo utiliza 7 bits, las memorias dinámica son hechas de transistores MOS de carga capacitiva y necesitan refrescarse cada determinado tiempo en  milisegs para no perder su valor.
IV Registro de vectores de interrupciones,  se usa para completar el vector de interrupción con la parte enviada por los dispositivos de entrada salida y forman la dirección completa de las rutinas o drivers del servicio de cada dispositivo.
IR Registro de instrucción de 2 bytes o 16 bits, Para instrucciones de un byte su contenido de  un byte de IR se obtiene de memoria con un ciclo fetch o de operación e identifica el codigo de opereración de un byte y en T3 y T4 realiza la operación y si requiere datos realiza un ciclo de memoria o de entrada-salida. Para instrucciones de dos bytes realiza otro ciclo fetch y completa los dos bytes de IR e identifica el código de operación de los dos bytes y en T3 y T4 ejecuta la operación  y si requiere datos realiza un ciclo de memoria.

Sistemas Numéricos
Hay muchos sistemas numéricos, como el decimal que utilizamos, pero el que nos interesa es el binario y hexadécimal para programar en lenguaje ensamblador del Z80.
El sistema binario tiene solo dos digitos de 1 y 0 físicamente se representan el 1 con 5 volts y el 0 con 0 volts. El lenguaje binario es el que entiende las computadoras y está limitado a la  cantidad de bits que pueden manipular  organizados en bytes de 8 bits. 
Un byte con números binarios se escribe como:
11011001B
Con una B al final.
La razón principal del sistema hexadecimal es facilitar la representación binaria en grupos de 4 bits por dígitos parecidos al sistema decimal:
0000-0
0001-1
0010-2
0011-3
0100-4
0101-5
0110-6
0111-7
1000-8
1001-9
1010-A
1011-B
1100-C
1101-D
1110-E
1111-F
El ejemplo anterior binario de un byte de 8 bits:
11011001B
En hexadecimal queda como:
D9H
Colocandose una H al final
Veamos un programita en hexadecimal en memoria:
Dir     Op
7000-3E
7001-02
7002-06
7003-02
7004-80
7005-CD
7006-0D
7007-44
7008-00
Identificamos las instrucciones:
3E02-LD A,2H
0602-LD B,2H
80-    ADD A,B
CD0D44-CALL 440DH
Ahora lo convertimos en Binario
    7       0      0       0        3      E       0      2
0111 0000 0000 0000-0011 1110 0000 0010
    0       6       0       2       8      0       C     D
0000 0110 0000 0010 1000 0000 1100 1101
    0       D      4       4   
0000 1101 0100 0100
Las instrucciones que entiende el Z80 estan en  lenguaje binario de unos 1 de 5 volts y ceros 0 de 0 volts, organizados como bytes de ocho bits almacenados en alguna memoria RAM o ROM. Cada instrucción es de un byte a cuatro bytes, tiene una parte de operación de un byte a dos bytes y la otra parte es la dirección a operandos o datos y puede ser de uno a dos bytes están en la propia instrucción, en los registros, en la memoria o llegan de los puertos de entrada o salen para los puertos de salida.

Direccionamiento del Z80
Las instrucciones para obtener sus datos u operandos utilizan varios modos de direccionamiento.
1.Inmediato de un byte y dos bytes. El dato de un byte o dos bytes esta en la propia instrucción pero almacenados en la memoria.
11)LD C,FFH  ;Carga el registro C con el número FFH.
7500H-LD C,FFH
7501H-FFH
C=33H -> C=FFH
12)LD HL,3456h  ;Carga el par HL con el dato 3456h.
7600H-LD HL,3456H
7601H-56H
7602H-34H
HL=6723 -> HL=3456H
2.Directo a memoria o directo extendido y a la página cero de la memoria, especifica una dirección de memoria donde esta el dato. La primera página 0 contiene los vectores de interrupciones.
21)LD A,(7000H) ;Carga el acumulador con el dato contenido en la dirección 7000H en memoria
7000H=55 -> A=55
22)LD HL,(2345H)  ;Carga el registro L con el  contenido de la dirección 2345H y el registro H con el contenido de la dirección 2346H.
2345H=34
2346H=07 -> HL=0734
Para la página 0 solo se utiliza en la instrucción RST, que salta y continua ejecutando la instrucción contenida en la dirección en página cero cuya dirección se incluye  en la instrucción, que puede ser 0, 8, 10H, 18H, 20H, 28H,  30H y 38H.
23)RST 10H   ;Carga el PC con el valor 0010h, con lo que se ejecutará la instrucción contenida en esa dirección.
10H -> PC -> Salta a ejecutar la instrucción en 10H
3.Relativo. Especifica una dirección relativa al  contador de programa PC o la dirección de la  instrucción actual y se suma el desplazamiento de un rango de -127 posiciones hacia atras y +128 hacia adelante.
31)JR Z,02H  ;Salta, si el resultado anterior fue cero, a la dirección que resulta de sumar al PC actual el número 02H
00FFF-SUB
1000H-JR,02H (-02H)
1001H-LD
1002H-ADD
4.Indexado. Utiliza los registros indexados IX e IY que contienen un dato de 16 bits más  el desplazamiento para obtener la dirección efectiva del dato.
41)SUB (IX+44H)  ;Resta al acumulador el contenido de la dirección de memoria que se obtiene al sumar 44H al contenido del registro IX.
A=43H
IX=1000H
DS=0044H
PC=1044H
1044H=33H -> A=43H-33H=10H
5.Registro y Registro extendido. La  dirección  específica el contenido de un registro y un registro doble.
51)ADD A,B  ;Suma el contenido del registro B en el  acumulador (A) y el resultado queda en el acumulador.
B=22H A=33H -> A=33H+22H=55H
6.Implicado. La instrucción asume un registro, normalmente el registro A o F sin indicarlo.
SCF   ;Activa o coloca a 1 el flag C.
61)F=00H -> F=01H
7.Bit. Las instrucciones afectan a un solo bit de un registro.
71)SET 6, B  ; Activa bit 6 del registro B
B=04H=00000100 -> B=44H

Instrucciones del Z80
Las instrucciones del Z80 contienen un código de operación y los operandos que pueden obtenerse con varios modos de direccionamiento de algún registro, memoria o de dispositivos de entrada-salida. Las instrucciones son:
1.Transferencia
Transferencia o movimiento de 8 bits de un byte, o de 16 bits de dos bytes, del stack y blocks de bytes. El movimiento es entre registros, entre registros y memoria, entre registros y el stack y   movimientos de blocks en memoria. Las trasferencias o movimientos es del segundo operando al primero y no afectan el contenido ni las banderas de estado.
11) LD A, B   ;Mueve el contenido de B en A
A=07H B=02H -> A=02H
LD B, 32H  ;Mueve 32H en B
1000H-LD B,32H
1001H-32H -> B=32H
12) LD HL , 2270H  ;Mueve 2270H de mem en HL
2270H-70H
2271H-22H -> HL=2270H
13) LD A , (2311H)  ; Mueve de mem de la dirección 2311H su contenido al registro A
2311H-66H -> A=66H
14)PUSH BC  ;Coloca o empuja el contenido del par BC en la pila o stack
9008H-11H
9007H-22H
SP=9006H
BC=3344H
PUSH
9008H-11H
9007H-22H
9006H-44H
9005H-33H
SP=9004H
BC=3344H
15)EXX  BC, DE  ;Intercambia el contenido de DE y de BC
BC=2222H DE=3333H -> BC=3333H DE=2222H
2.Arirméticas Lógicas Rotación y Desplazamiento
Aritméticas de un byte y dos bytes. Realiza operaciones aritméticas de suma y resta, incrementos y decrementos entre registros, el resultado siempre queda en el registro A y para registros dobles el resultado queda en el registro par HL. Las operaciones aritméticas son del segundo operando al primero y afectan los contenidos del primer operando y las banderas de estado.
21)ADD A, B ;Suma el contenido de B al acumulador A
B=54H A=34H -> A=34H+54H=84H
22)ADD A, 41H  ;Suma el valor 41H al acumulador
2000H-ADD A,41H-CO
2001H-41H
A=56 -> A=56+41H=97H
23)SUB C   ;Resta el valor de C del valor de A
C=35H A=66H -> A=66H-35H=31H
24)INC B  ;Incrementa en 1 el valor de B
B=77 -> B=77+1=78
25)DEC BC  ;Decrementa en 1 el valor del contenido par de BC
BC=4444H -> BC=4444H-1=4443H
Logicas
Realiza las operaciones lógicas de AND OR XOR entre registros y el resultado queda en el registro A.
26)AND B ; Al valor de B y A se aplica la función Y o AND
B=88H=10001000B
A=28H=00101000B
A=08H=00001000B
Rotación y desplazamientos
Realizan movimientos a la izquierda o derecha de los bits de un registro y afectan el contenido del operando.
27)RLC A ; Rotación a la izquierda de A una posición, el bit 7 pasa al acarreo C y este pasa al bit 0.
C=0 A=88H=10001000B -> C=1 A=00010000=10H
3.Salto
Salto incondicional y condicional. Cambian la secuencia del programa de forma incondicional y condicional a otra dirección para continuar la secuencia del programa.
31)JP 7000H  ; Salto incondicional a la dirección 7000H de la memoria
7000H-ADD
7001H-Instr1
7002H-Instr2
....
7FFFH-InstrN
8000H-JP 7000H  ;7000H -> PC
8001H-SUB
32)JP C, 7000H  ;Salto condicional si la bandera de acarreo C está activa, ve a la dirección 7000H de la memoria
7000H-ADD
7001H-Instr1
7002H-Instr2
....
7FFFH-ADD
8000H-JP C,7000H  ;7000H -> PC
8001H-SUB
Comparación
33)CP 13  ;Compara el valor de 13 con el de A el resultado afecta las banderas de estado y la siguiente instrucción checa las banderas para saltar a otra dirección.
7000H-ADD
7001H-Instr1
7002H-Instr2
....
7FFDH-LD A,13
7FFEH-CP 13
8000H-JP Z,7000H  ;7000H -> PC
8001H-SUB
Instruccioes de Bits
SET 7, B  ;Activa el bit 7 del registro B
RES 2, B  ;Desactiva el bit 2 del registro B
BIT 7, B   ;Checa el bit 7 de B y si esta puesto activa la bandera Z y la siguiente instrucción checa las banderas para saltar a otra dirección.
4.Rutinas
Rutinas del programa o de interrupciones. Las rutinas o subrutinas son secuencia de instrucciones que pueden ser llamadas por el programa varias veces y cuando terminan regresan a continuar la secuencia del programa.
41)CALL 8000H  ;Llama la subrutina localizada en la dirección 8000H
7000H-CALL 8000H
7001H-LD
7002H-Instr2
....
7FFFH-InstrN
8000H-LD
8001H-ADD
.....
8030H-RET
5.Entrada y Salida.
Realizan la transferencia  con los dispositivos de entrada-salida.
51)IN A, (01H) ;Mueve  el dato de un byte del puerto de entrada  01 al registro A
PTO01=33H
A=56H -> A=33H
52)OUT (03H) , A ;Mueve el contenido de A un dato de un byte al puerto de salida 07
PTO07=33H
A=44H -> A=44H PTO07=44H
6.Control.
Realizan operaciones de control como parar el cpu con HALT, NOP no operación y activar o desactivar las interrupciones.

Ejecución de las Instrucciones
El proceso de ejecutar las instrucciones de un programa es un ciclo de instrucción que contiene varios ciclos de máquina con hasta tres o cuatro estados de tiempos por cada instrucción. Un ciclo de instrucción consiste de:
1.Obtener la instrucción de memoria.
2.Decodificación o identificación de la instrucción.
3.Ejecución de la instrucción.
Una instrucción puede ser de uno a cuatro bytes, en algunas el primer byte y en otras también el segundo byte tienen un codigo de operación y los restantes una dirección de los operandos o datos. Podemos identificar para ejecutar las instrucciones los ciclos siguientes:

Ciclo Fetch o de Operación
   
El ciclo de operación inicia al activar la señal ciclo de máquina M1' en T1 con cuatro tiempos para obtener la siguiente instrucción indicada por el contador de programa PC que es colocada en el bus de direcciones al inicio de M1, medio ciclo después de T1 se activa MREQ' y es usada como una señal de chip enable clock para la memoria dinámica RAM. Se activa RD' para permitir al cpu en T2 leer la memoria del bus de datos en el registro de instrucción IR y desactivar MREQ' y RD' en la subida del pulso T3. En T3 y T4 se activa la señal refresh RFSH y junto con el registro R envía 7 bits inferiores al bus de direcciones para refrescar toda la memoria dinámica, también se vuelve activar MREQ' pero no se activa RD'. Debido a la respuesta de memorias lentas se introducen tiempos de espera Tw si es necesario.
Esta parte es la más importante del ciclo de operación pués al mismo tiempo en T3 y T4 se decodifica la instrucción contenida en el registro de instrucción IR y se ejecuta para instrucciones de un byte de operación. Para instrucciones de dos bytes de operación hace otro ciclo de operación para completar e identificar la instruccion de dos bytes de operación. Para las instrucciones de un byte o dos bytes de operación si necesita operandos debe hacer ciclos de memoria o ciclos de entrada-salida para obtener los datos.

Ciclos Memoria de Lectura y Escritura
      
El ciclo de lectura usa tres tiempos, inicia con la señal activa MREQ' en la bajada del pulso  T1 y se utiliza como una señal chip select en la memoria y se desactiva a la bajada del pulso T3, también se activa  RD' a la bajada del pulso T1 y se desactiva a la bajada del pulso T3.  En T2 con MREQ', RD' y el bus de direcciones, los tres activos, lee de memoria un byte y se envía por el bus de datos al cpu.
      
El ciclo de escritura activa MREQ' en la bajada del pulso T1 y se desactiva en baja del pulso  T3 y la señal WR' se activa en la bajada del pulso T2 y se desactiva en bajada del pulso  T3. En T2 con MREQ', WR', el bus de direcciones activos y se escribe en memoria un byte del bus de datos. Para memorias de respuesta lenta el cpu utiliza tiempos de espera Tw en T2 para recibir los datos. La señal WR' se desactiva medio ciclo antes de que la dirección y datos cambien para  satisfacer el traslape de algunas memorias.

Ciclos de Entrada y Salida
      
El ciclo de entrada usa tres tiempos, inicia con la señal activa IORQ' en la bajada del pulso T1 y se desactiva a la bajada del pulso T3, también se activa  RD' a la bajada del pulso T1  y se desactiva a la bajada del pulso T3.  En T2 se introduce un tiempo de espera WAIT para asegurar la respuesta  del dispositivo de salida. También en T2 con IORQ', RD' y el bus de direcciones, los tres activos, lee de memoria un byte y se envía por el bus de datos al puerto de salida. Tiene 256 puertos de entrada.
      
El ciclo de escritura activa IORQ' en la bajada del pulso T1 y se desactiva en baja del pulso T3 y la señal WR' se activa en la bajada del pulso T1 y se desactiva en bajada del pulso T3. En T2 se introduce un tiempo de espera WAIT para asegurar la respuesta del dispositivo de entrada. También en T2 con IORQ', WR', el bus de direcciones, los tres activos,  escribe en memoria un byte del bus de datos que vienen de un puerto de entrada. La señal WR' a veces se utiliza como una señal de reloj para los dispositivos. Tiene 256 puertos de salida.

Ciclo de Interrupción Enmascarable
                  
La cpu reconoce una interrupción  INT' de algún dispositivo, en la subida del último tiempo de la instrucción que se esta ejecutando, la señal no es aceptada si el flip flop IE no está activo o si la señal BUSREQ esta activa. Si la interrupción es acepta se activa un ciclo especial M1 en T1 hasta T3, también se activan MREQ' y IORQ' en el primer tiempo de espera Tw permite que el dispositivo coloque un vector de 8 bits en el bus de datos y dos estados de espera son agregados para facilitar una interrupción de prioridad ripple e identificar el dispositivo que envió el vector de interrupción, MREQ' y IORQ' se desactivan en T3.

Ciclo de Interrupción no Enmascarable                
Es una interrupción de la más alta prioridad y no puede desactivarse por softwate y necesita una respuesta inmediata, por ejemplo la falla de la fuente de alimentación. Es parecido a un ciclo de lectura de memoria, excepto que el bus de datos es ignorado y almacena el contador del programa en un stack externo y salta a la dirección 006H dónde ejecuta una rutina de servicio de interrupciones no enmascarables.
En T1 el contador del programa se envía al bus de direcciones hasta T2 y en T3 inicia un refresh de la memoria y termina en T4. M1 inicia en la subida del pulso T1 y termina en la subida del pulso T3. MREQ' y RD' inician en la bajada del pulso T1 y terminan en la subida del pulso T3. RFSH inicia en la subida del pulso T3 y termina en la bajada del pulso T4.

Ciclo de Acceso a Memoria Directo DMA
                   
La señal BUSREQ' es aceptada en la subida del último tiempo de la ejecución de una instrucción o ciclo de máquina. Cuando es reconocida pone en alta impedancia los buses de direcciones, datos y desactiva las señales RMEM', IOREQ', RD', WR' y RFSH y no puede ser interrumpido por INT o NMI. El cpu envía la señal BUSACK' para reconocimiento de la solcitud aceptada a un dispositivo controlado por acceso a memoria directo DMA, que llevará el control de los buses, así como el refresco de la memoría dinámica si es necesario, hasta que el dispositivo envie otra interrupción del fin de la transferencia de datos.
Ciclo de la Instrucción HALT
Cuando se ejecuta la instrucción HALT también ejecuta instrucciones NOPs hasta que una interrupción INT o NMI llega al cpu y son aceptadas si esta activo el flip flop IE. las interrupciones son capturadas en la subida del pulso T4 y en el siguiente ciclo da un reconocimiento a la interrupción y NMI tiene mayor prioridad que INT. El propósito de ejecutar NOP es mantener activa la señal RFSH. Cada ciclo de HALT es un ciclo M1' excepto que el dato recibido de memoria es ignorado y la instrucción NOP es forzada en el cpu.

Lenguaje Ensamblador Z80
Un programa está constituido por una secuencia de instrucciones para resolver algún problema. El ciclo de instrucción se repite hasta que se encuentre la última instrucción del programa.
El emulador TRS-80 contiene la computadora TRS80 III con un sistema operativo Newdos80,  debe cargarse en la memoria RAM para iniciar su operación y tiene muchos programas y rutinas, al final uno de ellos es el programa de comandos que  entra en un loop o de repetición de una secuencia de instrucciones esperando algún comando que llama otro programa para ejecutarse, por ejemplo el interprete de Basic, el programa editor y ensamblador EDTASM o el programa Debug como veremos más adelante.
Programar en lenguaje binario de unos 1 y ceros 0, sería muy complicado y engorroso, para evitarlo se utilaza un lenguaje ensamblador para codificar el programa y un traductor ensamblador para convertir el programa al lenguaje binario que entiende el Z80.
El lenguaje ensamblador del Z80 tiene un formato en una línea de texto:
Etiqueta          Código de Operación          Operandos o Datos          ;Comentario
Una etiqueta con un nombre, la operación con un nombre o mnemónico, los operandos o datos algunas veces con nombre de los operandos y al final un comentario que inicia con ; punto y coma, pero también se pone al inicio de la línea de texto cuando toda la línea es un comentario.
El lenguaje ensamblador también tiene pseudo instrucciones que no tiene equivalente a una instrucción del Z80. El punto y coma ; indica un comentario. ORG dir Indica la dirección de inicio del programa. EQU define variables del programa, con hasta 6 letras, por facilidad se definen al inicio  del programa, otras como DEFB define una constante de un byte, DEFW define una constante de una palabra de dos bytes, DEFM define una área de memoria para mensajes y DEFS define áreas de trabajo.
END indica el final del programa y siempre debe ser la última instrucción.

 
                      

Microcomputadora TRS80 III
La microcomputadora trs80 III  que utilizaremos para programar en lenguaje ensamblador. Tiene un microprocesador Z80, memoria de hasta 64 Kbytes, la memoria de tipo solo lectura es el ROM II de 12 Kbyte que contiene el interprete Basic. La memoria de escritura y lectura RAM de 4 Kbytes hasta 48 Kbytes. Un teclado o Keyboard como dispositivo de entrada. Un monitor o Video como dispositivo visual de salida. De uno a cuatro unidades de disco flexible o Floppy Disks como dispositivos de entrada y salida, la unidad cero siempre tiene el disco del sistema operativo Newdos80 u otro sistema, los otros tres puden usarse para guardar archivos de  datos y programas.
El disco floppy o flexible puede tener 35 o 40 tracks, cada uno tiene 10 sectores y cada sector tiene 256 bytes. Lógicamente se organizan como granulos de cinco sectores. Los primeros tracks 1 y 2 contiene el sistema operativo, el track 0 y sector 0 contiene el boot del sistema y los demas los módulos sys0, sys1 hasta el sys13. El track 17 contiene el control del asignamiento del espacio utilizado por los archivos, en el sector 0 está la tabla de asignación de granulos GAT para los archivos y en el sector 1 la tabla index hash HIT para la seguridad de los archivos. El sector 2 al 9 contiene la entrada al directorio de archivos primarios FPDE y si es necesaria la entrada a la extensión del directorio de archivos FXDE  cuando es grande el archivo. Cada entrada tiene 32 bytes para cada archivo  hasta un total de 64 archivos. Para utilizar el disco en un programa se debe abrir y asignar un nombre al archivo en un block de control de datos DCB de 32 bytes que tiene varios parámetros. Ahora se pueden hacer operaciones de búsqueda, lectura y escritura al disco, cuando se termina de usar hay que cerrar el archivo. También puede conectarse una impresora y un modem para comunicaciones no incluido en el emulador. Cuando usamos el sistema operativo Newdos80 del disco floppy de la unidad 0 que lo contiene, se carga con el programa boot en la memoria de escritura y lectura RAM usa 16 Kbytes todos los programas, pero solo se cargan sys0 hasta sys6 y todos los demás se cargan cuando se necesiten, en una área de traslape u overlay. Las rutinas son para utilizar los discos flexibles para escribir y leer archivos de programas y datos desde el Basic ROM II o del editor y ensamblador EDTASM que  está incluido en Newdos80.

Usaremos un teléfono inteligente con Android4 para instalar el emulador TRS-80 del  microcomputador TRS80 III que contiene el sistema operativo Newdos80 y tiene el interprete Basic ROM II, también el lenguaje ensamblador EDTASM y este lo usaremos para programar en lenguaje ensamblador del Z80.
Los pasos para instalar y usar el emulador TRS-80 son los siguientes.
1.Buscar en google play el emulador TRS-80 e instalarlo.
2.Presionar el ícono de TRS-80 y aparecen cuatro Modelos del TRS-80 usaremos el último que corresponde a TRS80 III y el sistema operativo Newdos80.

3.Presionamos el menú izquierdo y aparecen  varias opciones, seleccionamos Resume o Start y aparece una pantalla con NEWDOS/80 la fecha y hora, el mensaje Newdos/80 y READY
.
4.El sistema está listo para recibir comandos del sistema operativo, como DIR para ver el directorio de archivos texto y programas. LIST archivo, para desplegar un archivo de texto. FREE para ver los granulos o espacio libre del disco flexible. COPY archivo1 archivo2  para copiar un archivo. RENAME archivo1 archivo2 para cambiar el nombre de un archivo. KILL archivo para eliminar un archivo. Hay muchos más comandos, pero primero introducimos el comando DIR para ver el contenido del disco flexible de la unidad 0  y vemos a EDTASM.

5.Introducimos EDTASM y aparece la pantalla del editor con un asterisco * indicando que puede aceptar comandos de edición: I- Insertar lineas D- Eliminar línea R-Remplazar líneas P-Desplegar líneas. Los comandos utiliza una línea o un rango de líneas, indicado por dos puntos: como D120:150 elimina las líneas 120 hasta la 150. El símbolo gato # significa la primera línea y el asterisco * la última línea.  Por ejemplo P#:* significa desplegar todas las líneas de texto.

6.Crearemos un programa de varias instrucciones. Escribimos solo I para introducir líneas de texto, aparece la línea 100  y se va  incrementando en 10. Ahora introducir el  siguiente programa que hará una simple suma.
100                  ORG       7000H
110 DATO1    EQU    2
120 DATO2    EQU    2
130                  LD          A,DATO1
140                  LD          B,DATO2
150                  ADD       A,B
160                  CALL      440DH
170                  END
ORG es una pseudoinstrucción que indica la dirección 7000H de inicio del programa. EQU asigna valores a las variables DATO1 y DATO2. Las pseudoinstrucciones no generan código.
LD carga el registro A y B con 2.
ADD Suma el registro B a A.
CALL 440DH llama a DEBUGER, programa para ver la memoria y registros del programa.
END termina el programa.
Para salir de insertar instrucciones  presionamos la tecla BREAK.

7.Ahora ensamblaremos el programa con A /NO/WE indicando con NO de no generar el programa objeto y WE que pare en error. Si salen errores de ensamblado se despliegan en la pantalla, hay que corregirlos utilizando R línea  para reemplazar la línea por una  corregida y repetir el paso 7 hasta eliminar todos los errores.
8.Guardamos nuestro archivo de programa fuente sin errores con: W D=PZ/SRC
9.Cuando el programa está sin errores introducir solo A y pide el nombre del archivo del programa objeto PZ/CMD y ahora sale un mensaje de crear el archivo y se pone C.
10.Ahora salimos del EDTASM introduciendo B para regresar al sistema operativo Newdos80 y aparece ready listo para recibir comandos.
11.Introducimos DIR y aparece el directorio con PZ/SRC el programa fuente y PZ/CMD el programa objeto listo para ejecutarse.
12.Introducimos PZ/CMD y se ejecuta el programa objeto, no aparece nada en la pantalla solamente usamos la instrucción load  LD de cargar el registro A y B con 2H y ADD A,B sumando registro B a A e indica una ejecución correcta de otro modo desplegaría un error. Ahora usaremos DEBUG para ver la memoria y los registros del programa.
13.Salimos del sistema y con task manager damos kill al programa TRS-80. Volvemos a entrar a TRS-80 y damos RESUME.

14.Aparece READY e introducimos DEBUG aparece READY e introducimos PZ/CMD ahora aparece la pantalla X de DEBUG con tres areas de  memoria desde la dirección 0000 separadas por los registros.

15.Introducimos el comando D7000 y despliega la memoria desde la dirección 7000 y observamos nuestro programa en hexadécimal:
7000-3E02 0602 80CD 0D44 0000
Identificamos las instrucciones:
3E02-LD A,2H
0602-LD B,2H
80-    ADD A,B
CD0D44-CALL 440DH
Ahora lo convertimos en Binario
    7       0      0        0       3       E      0      2
0111 0000 0000 0000-0011 1110 0000 0010
    0      6        0       2       8      0       C      D
0000 0110 0000 0010 1000 0000 1100 1101
    0      D      4       4   
0000 1101 0100 0100
Es increíble y sorprendente que un programa de una computadora se represente y entienda un lenguaje binario de solo 1 y 0 y físicamente de voltajes de 5 volts y 0 Volts y por lo tanto de corrientes muy pequeñas.

16.Ahora introducimos G7000 y se ejecuta el programa, observamos el registro A con un valor de 4, comprobamos que se realizo la suma de 2+2.
AF=0400

17.Para regresar al sistema operativo introducimos G0000 con esto damos un RESET iniciando la carga del sistema operativo Newdos80.

Es increible y maravilloso que en nuestro teléfono inteligente con Android  que cabe en la palma de la mano, estamos emulando una microcomputadora TRS80 III que fué una de las primeras microcomputadoras, antes que apareciera la PC de IBM, pero no cualquiera podía tener una, era cara y nada fácil de usar, se necesitaban conocimientos de computación. Ahora tenemos la oportunidad de usarla en nuestro teléfono inteligente con el emulador TRS-80. Con esto iniciamos un curso usando el emulador  y veremos en detalle todas las instrucciones del microprocesador Z80 y con el editor ensamblador EDTASM haremos varios programas. También usaremos el programa DEBUG para ver la memoria y registros de los programas. Estudiaremos el funcionamiento interno de la TRS80 III y del sistema operativo Newdos80,  esto es simplemente por gusto e interés de saber cómo funciona el microprocesador Z80 en la microcomputadora TRS80 III con el emulador TRS-80. Todo esto como una base para posteriormente estudiar algo más complejo, el microprocesador ARM que la mayoría de los teléfonos inteligentes lo usan junto con el sistema operativo Android.