Apple IIc DLORES fixes
authorNick Downing <nick@ndcode.org>
Tue, 2 Aug 2022 03:01:43 +0000 (13:01 +1000)
committerNick Downing <nick@ndcode.org>
Tue, 2 Aug 2022 03:01:43 +0000 (13:01 +1000)
Makefile
dlores_viewer.asm
gr_to_ihx.py

index 5fa9027..5e39f9f 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -8,7 +8,7 @@ ASLINK=asxv5pxx/asxmak/linux/exe/aslink
 HEXMERGE=hexmerge.py
 
 LOAD_ADDR=0x800
-DATA_ADDR=0x880
+DATA_ADDR=0x900
 
 .PHONY: all
 all: \
index eb57e47..ff93700 100644 (file)
@@ -1,12 +1,15 @@
 ; read
 HW_KBD = 0xc000
+HW_IOUDIS = 0xc07e ; bit7 = IOUDIS state
 
 ; write
-HW_CLR80COL = 0xc000
-HW_SET80COL = 0xc001
+HW_CLR80COL = 0xc000 ; aka CLR80STORE, bankswitch by (RD|WR)(CARD|MAIN)RAM
+HW_SET80COL = 0xc001 ; aka SET80STORE, bankswitch by PAGE1/PAGE2, show page 1
 HW_CLR80VID = 0xc00c
 HW_SET80VID = 0xc00d
 HW_KBDSTRB = 0xc010
+HW_SETIOUDIS = 0xc07e ; IIc only, enable access to annunciators
+HW_CLRIOUDIS = 0xc07f ; IIc only, enable access to mouse
 
 ; read/write
 HW_CLRTEXT = 0xc050
@@ -17,35 +20,42 @@ HW_PAGE1 = 0xc054
 HW_PAGE2 = 0xc055
 HW_CLRHIRES = 0xc056
 HW_SETHIRES = 0xc057
-HW_SETDHIRES = 0xc05e
-HW_SETIOUDIS = 0xc07e
-HW_CLRIOUDIS = 0xc07f
+HW_SETAN3 = 0xc05e ; enable dhires
+HW_CLRAN3 = 0xc05f ; disable dhires
 
 TEXT_ADDR = 0x400
 TEXT_SIZE = 0x400
-DATA_ADDR = 0x880
+DATA_ADDR = 0x900
 DATA_FRAMES = 6
 
+WARM_START = 0x3d0
+ASOFT_GR = 0xf390
+MON_SETTXT = 0xfb39
+MON_HOME = 0xfc58
+
        .area   zpage
        .setdp
 
        .ds     0x80
 src:   .ds     2
 dest:  .ds     2
+count: .ds     1
 
        .area   text
 
-       sta     HW_CLR80COL
+       sta     HW_SET80COL
        sta     HW_SET80VID
+
+       lda     HW_IOUDIS
+       sta     HW_SETIOUDIS
+       sta     HW_SETAN3
+       bmi     0$
        sta     HW_CLRIOUDIS
+0$:
 
        sta     HW_CLRTEXT
        sta     HW_CLRMIXED
-       sta     HW_PAGE1
        sta     HW_CLRHIRES
-       sta     HW_SETDHIRES
-
-       sta     HW_SET80COL ; use HW_PAGE1/HW_PAGE2 for bank switching
 
        lda     #<DATA_ADDR
        sta     src
@@ -60,61 +70,99 @@ loop:       ; enter here with src pointing to current frame of animation
        sta     dest + 1
 
        ; copy one screen (there are 8 lines in 1/3 screen)
-       ldx     #8
-copy:
+       lda     #8
+       sta     count
+copy_screen:
 
-       ; copy 3 lines 8 lines apart to page 1, stop at screen hole
-       sta     HW_PAGE1
-       ldy     #119
-copy0: lda     [src],y
+       ; copy 3 lines 8 lines apart
+       ldx     #3
+       clc
+copy_line:
+
+       ldy     #39
+0$:    lda     [src],y
        sta     [dest],y
        dey
-       bpl     copy0
+       bpl     0$
 
-       ; src += 0x80
+       ; src += 40
        lda     src
-       eor     #0x80
+       adc     #40
        sta     src
-       bmi     0$
-       inc     src + 1
-0$:
 
-       ; copy 3 lines 8 lines apart to page 2, stop at screen hole
+       sei ; disable interrupts while screen holes are wrong
        sta     HW_PAGE2
-       ldy     #119
-copy1: lda     [src],y
+
+       ldy     #39
+1$:    lda     [src],y
        sta     [dest],y
        dey
-       bpl     copy1
+       bpl     1$
 
-       ; src += 0x80
+       sta     HW_PAGE1
+       cli
+
+       ; src += 40
        lda     src
-       eor     #0x80
+       adc     #40
+       sta     src
+
+       ; dest += 40
+       lda     dest
+       adc     #40
+       sta     dest
+
+       dex
+       bne     copy_line
+
+       ; src += 16 (always carries)
+       lda     #<DATA_ADDR ; always 0 in practice
        sta     src
-       bmi     0$
        inc     src + 1
-0$:
 
-       ; dest += 0x80
+       ; dest += 8 (might carry)
        lda     dest
-       eor     #0x80
+       adc     #8
        sta     dest
-       bmi     1$
+       bcc     2$
        inc     dest + 1
-1$:
+2$:
 
-       dex
-       bne     copy
+       dec     count
+       bne     copy_screen
 
        ; delay (assumes x == 0)
        ldy     #0x30
-2$:    dex
-       bne     2$
+delay: dex
+       bne     delay
+
+       lda     HW_KBD
+       bmi     quit
+
        dey
-       bne     2$
+       bne     delay
 
        ; wrap
        lda     src + 1
        cmp     #>(DATA_ADDR + DATA_FRAMES * TEXT_SIZE)
        bcc     loop
        bcs     reset
+
+quit:  sta     HW_KBDSTRB
+
+       sta     HW_CLR80VID
+       sta     HW_CLR80COL
+
+       lda     HW_IOUDIS
+       sta     HW_SETIOUDIS
+       sta     HW_CLRAN3
+       bmi     0$
+       sta     HW_CLRIOUDIS
+0$:
+
+       lda     HW_SETTEXT
+       lda     HW_PAGE1
+
+       jsr     MON_SETTXT
+       jsr     MON_HOME
+       jmp     WARM_START
index 4bdba3c..ac67053 100755 (executable)
@@ -36,17 +36,21 @@ assert xs == 80
 transparent_color = image_in[0, 0, 0] # temporary
 image_in[image_in == transparent_color] = 0
 
-# rotate colours in aux memory (required by the hardware)
-image_in[:, :, 0::2] = \
-  (image_in[:, :, 0::2] >> 1) | ((image_in[:, :, 0::2] << 3) & 8)
-
-image_out = numpy.zeros((ts, 8, 2, 0x80), numpy.uint8)
+image_out = numpy.zeros((ts, 8, 0x100), numpy.uint8)
 shifts = [0, 4]
 planes = [1, 0]
-for i in range(ys):
-  for j in range(2):
-    image_out[:, (i >> 1) & 7, j, (i >> 4) * 40:((i >> 4) + 1) * 40] |= \
-      image_in[:, i, planes[j]::2] << shifts[i & 1]
+for i in range(3):
+  for j in range(8):
+    for k in range(2):
+      # main memory
+      image_out[:, j, i * 80:i * 80 + 40] |= (
+        image_in[:, k | (j << 1) | (i << 4), 1::2]
+      ) << (k << 2)
+      # aux memory (colours are rotated by 1 bit)
+      image_out[:, j, i * 80 + 40:i * 80 + 80] |= (
+        (image_in[:, k | (j << 1) | (i << 4), 0::2] >> 1) |
+        ((image_in[:, k | (j << 1) | (i << 4), 0::2] << 3) & 8)
+      ) << (k << 2)
 image_out = image_out.reshape((ts * 0x800,))
 
 intelhex = IntelHex()