INICIACIÓN AL LENGUAJE
ENSAMBLADOR
GRÁFICOS (2) 7.ª Parte
En esta segunda parte dedicada a los gráficos trataremos del BLITTER, es decir, un componente del Amiga que permite una serie de funciones a una gran velocidad, y con ella la posibilidad de trasladar bloques de memoria a 28 Mhz liberando así trabajo al microprocesador.
Por Fernando G. Terradillos |
|
Este chip, llamado Agnus (Fat Agnus para A-500 y A-2000b), además de contener el Blitter, realiza la tarea de suministrar memoria de exclusivo uso a los chips adicionales de gráficos, sonido, periféricos (coprocesadores), etc., con el consiguiente ahorro también de tiempo. Esta memoria exclusiva de utilización se llama CHIP MEMORY, porque es la que pueden manejar los coprocesadores. Esta es de sólo 512k, con el consiguiente problema para los gráficos de alta resolución, ya que se queda sin memoria al realizar algunos complicados procesos. En los últimos modelos de Amiga 2000 el Fat Agnus se ha cambiado por otro mejor para direccionar más memoria CHIP y así poder conseguir todas las resoluciones posibles y sus colores.
El Blitter comúnmente se utiliza para mover grandes bloques de memoria, pero además puede mover regiones rectangulares de memoria, permite otras funciones que aunque no se traten en este capítulo le pueden ser de gran ayuda, que es el poder realizar líneas en gráficos, rellenado de áreas, operaciones lógicas, etc., todas ellas a gran velocidad, siendo su programación muy complicada. Trataremos únicamente la primera opción, el traslado de bloques.
La utilización del blitter permite hacer scrolling limpio de una o varias líneas en pantalla, o incluso presentar una secuencia de fotogramas o pantallas para producir una animación. Para realizar esta tarea se han de llevar a cabo una serie de normas a la hora de la programación y el cuidado manejo de los registros de control de blitter que presentamos en el anterior capítulo. Volvamos a ver tales registros en el listado 1.
Recuerdo que estos valores se sumarán a $DFF000 para dar la posición de memoria exacta donde se insertará el valor.
Como podrás observar el Blitter maneja tres bloques cuente (Bloques A, B, C), es decir, los bloques de memoria a copiar y un destino (Destino D), eso quiere decir que distribuye cuatro canales de DMA (acceso directo a memoria). No es necesario utilizar todos los canales, solamente los que interese, en este caso la fuente A y el destino D. Si se pretende manejar por ejemplo cuatro bitplanos con 16 colores el proceso del blitter se ha de realizar cuatro veces en total, uno por bitplane, ya que ocupan páginas de memoria independientes.
Los requisitos necesarios para hacer un proceso de Blitter, es el insertar los valores correctos en los principales registros de control.
Estos son los registros:
| - BLTAPTH |
050 |
Blitter puntero para fuente A (high 3 bits) |
| - BLTAPTL |
052 |
Blitter puntero para fuente A (low 15 bits) |
Se utilizan dos registros para abarcar la totalidad de la CHIP MEMORY, situaremos la posición en memoria de nuestro bloque a copiar en el primer registro (el segundo se rellena automáticamente al utilizar una doble palabra, 32 bits).
| -BLTDPTH |
054 |
Blitter puntero para destino D (high 3 bits). |
| -BLTDPTL |
056 |
Blitter puntero para destino D (low 15 bits). |
Insertaremos el valor de la memoria donde irá destinado el bloque en el primer registro.
| -BLTAMOD |
064 |
Blitter módulo por fuente A |
El blitter usa módulos para manejar zonas o imágenes dentro de otras mucho mayores, es decir, manipula un bloque de memoria tal cual, pero con el módulo permite obtener una zona más pequeña o lo que es lo mismo, una ventana. Ya que no utilizaremos módulos insertaremos cero en el registro.
| -BLTCON0 |
040 |
Blitter control registro 0. |
| -BLTCON1 |
042 |
Blitter control registro 1. |
Este es un registro que siempre se utiliza en cualquier operación de Blitter. Contiene bits de control para las diferentes utilidades del Blitter, como líneas, rellenos de memoria, funciones lógicas, etc. Cada bit tiene una función específica, vamos a verlas:
| REGISTRO BLTCON0 040: |
| BITS 12 al 15: |
Valor Shift para fuente A |
| BIT 11: |
control de fuente A, poner a 1 si se utiliza fuente A |
| BIT 10: |
control de fuente B, poner a 1 si se utiliza fuente A |
| BIT 09: |
control de fuente C, poner a 1 si se utiliza fuente A. |
| BIT 08: |
control de destino D, poner a 1 si se utiliza destino D |
| BITS 00 al 07: |
función lógica de la operación generalmente BITS 4 al 7 a valor 1 |
| |
|
| REGISTRO BLTCON1 042: |
| BITS 12 al 15: |
valor Shift para fuente B |
| BIT 04: |
rellenado exclusivo |
| BIT 03: |
rellenado inclusivo |
| BIT 01: |
modo de mover bloque en decremento |
En nuestro caso pondremos a uno los bits 4, 5, 6, 7, 8, 11, 12, 13, 14, 15. Siendo el valor en sistema binario: 1111100111110000 dando en hexadecimal $F9F0. Mantenga este valor los más parecido, pues se encontrará con grandes sorpresas si pretendes hacer algún cambio crítico.
| -BLTAFWM |
044 |
Blitter máscara primera palabra para fuente A |
| -BLTALWM |
046 |
Blitter máscara última palabra para fuente A |
Este registro contiene la máscara para el proceso del Blitter. La máscara dejará el valor de la fuente si encuentra un bit a 0, actuando como un filtro. En este caso colocaremos el valor -1 o $FFFFFFFF.
| -BLTSIZE |
058 |
Blitter comienzo y tamaño (ventana ancho, alto). |
Este es el último registro para realizar un proceso de Blitter, y nos permite ajustar el alto y ancho de la imagen a mover. Automáticamente insertado el valor en el mismo se realizará la operación.
Para el Blitter las imágenes en un bitplane constan de posiciones de memoria cada 16 bits, en este caso pixels, uno más bajo que el siguiente. Las filas como es lógico irán por pixels. Como los registros en el Blitter sólo admite números de 16 bits (2 bytes) la distribución de la altura y la anchura para el registro BLTSIZE será de esta manera:
BIT# 15, 14, 13, 12, 11, 10, 09, 08, 07, 06, 05, 04, 03, 02, 01, 00, h9 h8 h7 h5 h4 h3 h1 h0 w5 w4 w3 w2 w1 w0
Los BITS 00 al 05 nos darán en total 64 combinaciones que multiplicados por 16 bits nos darán el total de pixels (=1.024) que se pueden utilizar por ancho en el proceso de una operación de Blitter. Por otro lado los BITS 06 al 15 nos da la posibilidad de manejar otros 1.024 píxel (10 bits permiten 1.024 combinaciones).
El ejemplo de hoy será de una gran utilidad, pues se podrá comprobar todo lo comentado anteriormente, además podrás observar cómo se escribe un texto en lenguaje ensamblador (que más tarde explicaré), así como poder cambiar algunos valores para que el scrolling aparezca en otra posición o incluso ajustar la separación entre las letras (ver listado 2).
Una vez hayas escrito el listado en tu editor de textos favorito has de ensamblarlo mediante las siguientes líneas desde CLI o salvadas a un fichero de texto para ejecutarlo:
c/assem aa.s -o LAST.asm
c/alink LAST.asm to p
A continuación pasemos a explicar paso a paso el funcionamiento del programa. Como de costumbre primero se abre la librería graphics.library, comprobando si ha habido algún error. A continuación se inicializan los bitmaps como explicamos en el anterior capítulo, es decir, primero reservando memoria para 2 bitplanes en la memoria CHIP (requerimiento $10002 = CHIP MEMORY) y escribe las posiciones que ocupan en memoria a la lista del COPPER o COPPERLIST que se encuentra al final del listado. Estas posiciones se escriben al COPPERLIST para que se mantengan constantemente insertándolas en los registros $Dff0E0 y $DFF0E4, así como de otros valores vistos igualmente en el anterior capítulo.
Luego el programa reserva $72 bytes también para el COPPERLIST, que luego copiará, y ahora es cuando realmente se inicializan los bitplanes, primero inicializando la estructura BITMAP, insertando previamente los valores correctos en los registros (número de bitplanes y alto y ancho). A continuación inicializan el RASPORT o parte visible de la pantalla utilizando la estructura correspondiente. Lo último que queda es juntar estas dos estructuras mediante un MOVE en Rasport.
Una vez inicializada nuestra pantalla colocaremos el COPPERLIST en el espacio de memoria reservado anteriormente, utilizando una simple rutina de copiado y luego desconecta la multitarea mediante la función Forbid (Offset -$84 de la librería exec) para más tarde volver a conectarlo.
Ahora damos un paso importante, que es el ajuste de cuáles son los procesos internos que van a funcionar, que en este caso serán el Copper y el Blitter. Además de estos procesos por supuesto se podrán incluir rutinas de sonido o Sprites, pero no hay espacio para incluirlas.
Primero salva la interrupción a nivel usuario para apuntar a lo que es el programa principal, que realiza funciones constantes de blitter. Las instrucciones tienen un funcionamiento parecido en el C-64, es decir, cada cierto tiempo el microprocesador para todas sus tareas y ejecuta un programa situado en el vector que ahora nos ocupamos de cambiar. También es importante saber que hay diferentes niveles de interrupción, según sea la importancia de la tarea; en este caso hemos utilizado la del nivel de usuario, de tipo medio bajo. EL vector a que nos hemos referido se encuentra en la posición de memoria $6C. Ya que es muy peligroso manejar interrupciones previamente deberemos desconectar la interrupción principal situada en el registro $DFF09A.
A continuación desactiva el actual Copper que hay en el momento de ejecutar el programa para insertar el nuevo; para ello desactiva el bit de control del registro de DMA, exactamente el $DFF096. Veamos el resto de los bits:
| BIT# |
DESCRIPCIÓN |
| 15 |
Control de lectura o escritura. Permite ajustar o borrar el resto de los bits. |
| 14 |
Blitter bit de estado del bus, sólo de lectura. Permite saber si ha acabado el proceso del Blitter. |
| 09 |
Permite todos los procesos de DMA que vienen a continuación. |
| 08 |
Permite Bitplane. |
| 07 |
Permite Copper. |
| 06 |
Permite Blitter. |
| 05 |
Permite Sprite. |
| 04 |
Permite Disco. |
| 00-03 |
Permite canales de Audio de 0 a 3. |
En el caso de este programa los bits que interesan ajustar son el Bitplane, Copper y Blitter dando como resultado el valor en binario 1000010111000000, en hexadecimal $85c0.
Queda sólo esperar a que pulsemos el botón izquierdo del ratón, mientras el único programa que se esta ejecutando se encuentra en una interrupción. Este programa situado en la etiqueta JUMP6 del listado maneja todos los procesos necesarios para hacer el Scrolling.
Primeramente calcula la mitad de la pantalla donde se va a efectuar el Scroll, en la posición #$16b0 a partir del comienzo de cada Bitplane, así como en el segundo Bitplane. Ahora sólo le queda insertar los valores exactos en los registros del Blitter que vimos anteriormente para producir nuestro efecto. Estos valores uno a uno son los siguientes:
| $DFF050 |
el registro A0 (comienzo bloque fuente, en mitad de pantalla) |
| $DFF054 |
el registro A1 (destino bloque, 2 pixels menos) |
| $DFF064 |
módulo fuente a del bloque a copiar |
| $DFF040 |
varios bits de control (número de fuentes con sus funciones lógicas) |
| $DFF044 |
máscara del bloque a copiar |
| $DFF058 |
ancho y alto del bloque y comienzo del Blitter |
Este mismo proceso se ha de hacer con el segundo Bitplane respetando sus posiciones. Asimismo, este proceso se repite 9 veces para que el carácter que se haya escrito al final de la línea se mueva hacia la izquierda. Para ajustar la separación entre letras se ha de aumentar o disminuir este valor.
El único cabo suelto es el de escritura en un Bitplane. Para escribir en una pantalla se han de ejecutar dos funciones de la librería gráfica:
| -$156(A6) |
que define el color del texto, y |
| -$3C(A6) |
que es la que realmente lo escribe. |
Como podrás observar estas dos funciones necesitan insertar valores en los correspondientes registros A0, A1 y D0 como son las estructuras Rasport, puntero del texto y número de caracteres. Para cambiar la posición de escritura de un texto se ha de cambiar dos valores de la estructura Rasport correspondiente a los Offset $24 y $26 (coordenadas X,Y del texto en la pantalla).
Queda sólo decir que en cuanto se haya pulsado el botón izquierdo del ratón el programa se ocupa de volver al estado anterior, volviendo a restaurar interrupciones, Copper, Sprite, y desocupar la memoria utilizada por los Bitplanes y estructuras.
Nada más. En el siguiente capítulo veremos la última parte en cuestión gráfica, como son los Sprites.
NOTA DE REDACCIÓN:
Los capítulos 1 a 6 de este cuadernillo se encuentran en la revista "Commodore World".
Listado 1
BLTCON0 040 Blitter control regístro 0
BLTCON1 042 Blitter control regístro 1
BLTAFWM 043 Blitter máscara primera palabra para fuente A
BLTALWM 046 Blitter máscara última palabra para fuente A
BLTCPTH 048 Blitter puntero para fuente C (high 3 bits)
BLTCPTL 04A Blitter puntero para fuente C (low 15 bits)
BLTDPTH 04C Blitter puntero para fuente B (high 3 bits)
BLTBPTL 04E Blitter puntero para fuente B (low 15 bits)
BLTAPTH 050 Blitter puntero para fuente A (high 3 bits)
BLTAPTL 052 Blitter puntero para fuente A (low 15 bits)
BLTDPTH 054 Blitter puntero para destinación D (high 3 bits)
BLTDPTL 056 Blitter puntero para destinación D (low 15 bits)
BLTSIZE 058 Blitter comienzo y tamaño (ventana ancho, alto)
BLTCMOD 060 Blitter módulo para fuente C
BLTBMOD 062 Blitter módulo para fuente B
BLTAMOD 064 Blitter módulo para fuente A
BLTDMOD 066 Blitter modulo para destinación D
BLTCDAT 070 Blitter fuente C para registro de datos
BLTBDAT 072 Blitter fuente B para registro de datos
BLTADAT 074 Blitter fuente A para registro de datos |
|
 |
 |
 |
Listado 2
****************************************************************************
* SCROLL BLITTER *
* *
* AUTOR FERNANDO G. TERRADILLOS *
****************************************************************************
BSR.L INIT ;VARIOS SETU
START LEA GFXNAME,A1 ;APUNTA NOMBRE LIBRERIA
JSR -$198(A6) ;ABRE LIBRERIA
MOVE.L D0,GFXBASE ;SALVA BASE LIBRERIA
BEQ.L ERROR1 ;ERROR?
MOVEA.L 4,A6 ;APUNTA EXEC
MOVE.L #$3A98.D0 ;BYTES POR BITPLANE
MULU #2,D0 ;POR 2 BITPLANES
MOVE.L #$10002,D1 ;PARAMETROS MEMORIA=CHIP
JSR -$C6(A6) ;ALLOCATE MEMORY
MOVE.L D0,MEM1 ;SALVA POSICION MEMORIA
BEQ.L ERROR2 ;ERROR?
MOVE.L MEM1,D0 ;CARGA POSICION MEMORIA
MOVE.L D0,D1 ;LA COPIA
ADDI.L #$3A98,D1 ;SEGUNDO BITPLANE
MOVE.W D0,POS1 ;ESCRIBE EN COPPERLIST
MOVE.W D1,POS2 ;BITPLANE 2
SWAP D0 ;CAMBIA REGISTRO
SWAP D1 ;IGUALMENTE
MOVE.W D0,POS3 ;ESCRIBE DE NUEVO EN COPPER
MOVE.W D1,POS4 ;TAMBIEN
MOVE.L #$72,D0 ;72 BYTES PARA COPPERLIST
MOVE.L #$10002,D1 ;PARAMETROS MEMORIA=CHIP
JSR -$C6(A6) ;ALLOCATE MEMORIA
MOVE.L D0,MEM2 ;SALVA LUGAR MEMORIA
BEQ.L ERROR3 ;ERROR?
MOVEA.L GFXBASE,A6 ;CARGA BASE
LEA BITMAP,A0 ;APUNTA STRUCTURA BITMAP
MOVE.B #2,D0 ;2 BITPLANES
MOVE.W #$190,D1 ;ANCHO
MOVE.W #$12C,D2 ;ALTO
JSR -$186(A6) ;INICIALIZA BITMAP
MOVEA.L MEM1,A0 ;APUNTA A MEMORIA 1
MOVEA.L A0,A1 ;CARGA EN A1
ADDA.L #$3A98,A1 ;+ $3A98=BITPLANE2
MOVE.L A0,BITMAP+8 ;POSICION BITPLANE1 EN BITMAP
MOVE.L A1,BITMAP+$C ;POSICION BITPLANE2 EN BITMAP
LEA RASPORT,A1 ;APUNTA ESTRUCTURA RASPORT
JSR -$C6(A6) ;INICIALIZA RASPORT
MOVE.L #BITMAP,RASPORT+4 ;JUNTA BITMAP CON RASPORT
MOVEA.L #COPPER,A0 ;APUNTA A COPPERLIST
MOVEA.L MEM2,A1 ;APUNTA A MEMORIA2=$72 BYTES
MOVE.W #$6f,D0 ;NUMERO DE BYTES A TRANSLADAR
LOOP1 MOVE.B (A0)+,(A1)+ ;LOS COPIA
DBF D0,LOOP1 ;HASTA $6F
MOVE.L #TEXT,TEXTPOS ;APUNTA AL TEXTO
MOVEA.L 4,A6 ;CARGA EXECBASE
JSR -$84(A6) ;QUITA MULTITASKING
MOVEA.L GFXBASE,A0 ;APUNTA GFXBASE
MOVE.W #$4000,$DFF09A ;QUITA INTERRUPCION PRINCIPAL
MOVE.W #$80,$DFF096 ;QUITA DMA COPPER
MOVE.L #6C,NEXIRQ+2 ;SALVA ANTERIOR INTERRUPCION
MOVE.L #NEWIRQ,$6C ;APUNTA A NUEVA INTERRUPCION
MOVE.L $32(A0),OLDCOPP ;SALVA ANTIGUO COPPERLIST
MOVE.L MEM2,$32(A0) ;APUNTA AL NUEVO COPPERLIST
MOVE.W #-$7940,$DFF096 ;PERMITE BLITTER,COPPER
MOVE.W #-$4000,$DFF09A ;HABILITA INTERRUPCION PRINC.
LOOP2 BTST #6,$BFE001 ;LEFT MOUSEBUTTON PULSADO
BEQ.S JUMP5 ;SI NO, DE NUEVO
BTST #$A,$DFF016 ;COMPRUEBA SI ES DEL MOUSE
BNE.S LOOP2
JUMP5 MOVEA.L GFXBASE,A0 ;CARGA GFXBASE
MOVE.W #$4000,$DFF09A ;QUITA INTERRUPCION PRINC.
MOVE.W #$80,$DFF096 ;QUITA DMA COPPER
MOVE.L NEXIRQ+2,$6C ;RESTABLECE INTERRUPCION
MOVE.L OLDCOPP,$32(A0) ;RESTABLECE ANTIGUO COPPER
MOVE.W #$80A0,$DFF096 ;PONE DMA COPPER
MOVE.W #-$4000,$DFF09A ;HABILITA INTERRUPCION PRINC.
MOVEA.L 4,A6 ;CARGA EXEC
JSR -$8A(A6) ;PERMITE MULTITASKING
MOVEA.L 4,A6 ;CARGA EXEC
MOVEA.L MEM2,A1 ;APUNTA MEMORIA2
MOVE.L #$72,D0 ;NUMERO DE BYTES
JSR -$D2(A6) ;DEALLOCATE MEMORIA
ERROR3 MOVEA.L 4,A6 ;CARGA EXEC
MOVEA.L MEM1,A1 ;APUNTA MEMORIA1
MOVE.L #$3A98,D0 ;NUMERO DE BYTES
MULU #2,D0 ;2 BITPLANES
JSR -$D2(A6) ;DEALLOCATE MEMORIA
ERROR2 MOVEA.L 4,A6 ;APUNTA EXEC
LEA GFXNAME,A1 ;APUNTA GFX LIBRARY
JSR -$19E(A6) ;CIERRA LIBRERIA
ERROR1 CLR.L D0 ;BORRA D0
RTS ;RETORNA CLI
NEWIRQ MOVE SR,-(A7) ;SALVA SR
MOVEM.L D0-D7/A0-A6,-(A7) ;sALVA REGISTROS
BSR.S JUMP6 ;RUTINA DE INTERRUPCION
MOVEM.L (A7)+,D0-D7/A0-A6 ;RESTABLECE REGISTROS
MOVE (A7)+,SR ;RESTABLECE SR
NEXIRC JMP $FC0CD8 ;SALTA RESTO INTERRUPCION
JUMP6 BTST #$E,$DFF002 ;COMPRUEBA BITS DE DMA
BNE.S JUMP6 ;SALTA
MOVEA.L MEM1,A0 ;APUNTA A BITPLANES
ADDA.L #$16B0,A0 ;MITAD DE PANTALLA
MOVEA.L A0,A1 ;DUPLICA
MOVEA.L A0,A2 ;DUPLICA
ADDA.L #$3A98,A2 ;BITPLANE 2, MITAD PANTALLA
MOVEA.L A2,A3 ;DUPLICA
SUBA.L #2,A1 ;RESTA 2
SUBA.L #2,A3 ;IGUAL BITPLANE 2
MOVE.L A0,$DFF050 ;FUENTE PARA BLITTER
MOVE.L A1,$DFF054 ;DESTINO
MOVE.L #0,$DFF064 ;MODULO FUENTE BLITTER
MOVE.L #$F9F00000,$DFF040 ;VARIOS BITS EN BLITTER REG.
MOVE.L #-1,$DFF044 ;MASCARA
MOVE.W #$512,$DFF058 ;TAMANO= 288 ANCHO,20 ALTO
MOVE.L A2,$DFF050 ;BITPLANE2 FUENTE
MOVE.L A3.$DFF054 ;DESTINO
MOVE.L #0,$DFF064 ;MODULO
MOVE.L #$F9F0000,$DFF040 ;VARIOS BITS
MOVE.L #-1,$DFF044 ;MASCARA
MOVE.W #$512,$DFF058 ;ANCHO,ALTO Y START
MOVE.W #0,RASPORT+$24 ;POSICION TEXTO X
MOVE.W #$7B,RASPORT+$26 ;POSICION TEXTO Y
MOVEA.L GFXBASE,A6 ;APUNTA GFXBASE
LEA RASPORT,A1 ;APUNTA RASPORT
LEA TEXT1,A0 ;APUNTA TEXTO
MOVE.W #3,D0 ;NUMERO DE CARACTERES=
JSR -$3C(A6) ;ESCRIBE TRES ESPACIOS
SUBI.B #1,CHARD ;COMPRUEBA EN ANCHO DE CARAC.
BNE.S JUMP7 ;SI NO SALTA PARA SUMAR 1
MOVE.W #$176,RASPORT+$24 ;POSICION DEL TEXTO X
MOVE.W #$7B,RASPORT+$26 ;POSICION DEL TEXTO Y
MOVEA.L GFXBASE,A6 ;APUNTA GFXBASE
LEA RASPORT,A1 ;APUNTA RASPORT
MOVE,B #1,D0 ;COLOR APEN
JSR -$156(A6) ;COLOR DEL TEXTO
LEA RASPORT.A1 ;APUNTA A RASPORT
MOVEA.L TEXTPOS.A0 ;APUNTA AL TEXTO
MOVE.W #1,D0 ;NUMERO DE CARACTERES=1
JSR -$3C(A6) ;ESCRIBE)
MOVE.B #9,CHARD ;PONE DE NUEVO ANCHO CARACTER
ADDI.L #1,TEXTPOS ;SUMA 1 A POSICION TEXTO
CMPI.L #TEXTEND,TEXTPOS ;COMPARA SI ES EL FIN
BNE.S JUMP7 ;SI NO, SALTA
MOVE.L #TEXT,TEXTPOS ;REINICIA COMIENZO DE TEXTO
JUMP7 ADDI.B #1,LOOPI ;LOOP
CMPI.B #3,LOOPI ;HASTA 3
BNE.L JUMP6 ;SALTA SI NO
CLR.B LOOPI ;BORRA BUCLE
RTS ;RETORNA
CNOP 0,2
GFXNAME DC.B 'graphics.library',0
CNOP 0,2
GFXBASE DC.L 0
MEM1 DC.L 0
MEM2 DC.L 0
TEXTPOS DC.L 0
OLDCOPP DC.L 0
CHARD DC.B 1
LOOPI DC.B 0
BITMAP DC.W $0032,$012C,$0002,$0000
DC.W $0002,$13C0,$0002,$4E58,$0000,$0000,$0000,$0000
DC.W $0000,$0000,$0000,$0000,$0000,$0000,$0000,$0000
RASPORT DC.W $0000,$0000,$0004,$0358,$0000,$0000,$0000,$0000
DC.W $0000,$0000,$0000,$0000,$FF01,$00FF,$0100,$000F
DC.W $0001,$FFFF,$0018,$007B,$CA0A,$0A0A,$0A0A,$0A0A
DC.W $0000,$0000,$00C0,$1FC8,$0000,$0008,$0008,$0006
DC.W $0000,$0000,$0000,$0000,$0000,$0000,$0000,$0000
DC.W $0000,$0000,$0000,$0000,$0000,$0000,$0000,$0000
DC.W $0000,$0000
COPPER DC.W $008E,$2C81,$0090,$74F1,$0092,$0028; VARIOS VALORES
DC.W $0094,$00D8,$00E0
POS3 DC.W $0002,$00E2 ;POSICION BITPLANE 1
POS1 DC.W $13C0,$00E4
POS4 DC.W $0002,$00E6 ;POSICION BITPLANE 2
POS2 DC.W $4E58,$0100,$2200,$0102,$0000,$0104,$0000
DC.W $0108,$0004,$010A,$0004
DC.W $0180,$0000,$0181,$0FFF,$FFFF,$FFFE
INIT BTST #5,$DFF01F
BEQ.S INIT
MOVE.W #$20,$DFF096
MOVEA.L 4,A6
RTS
TEXT DC.B 'ESTO ES UNA DEMOSTRACION DEL BLITTER'
TEXT1 DC.B ' '
TEXTEND DC.B 0 |
|
 |
 |
 |
|