;; This program will only run on a Plus
;; 
;; This program writes colours using the old CPC
;; method and reads back the data in the ASIC ram.
;;
;; This then compares the value read against the values expected 
;; (these were retreived from a real Plus).
;; 
;; This code builds with Pasmo assembler.
org &8000
;;nolist

txt_output equ &bb5a
scr_set_mode equ &bc0e
km_wait_char equ &bb06

start:
ld a,2
call scr_set_mode 

;; unlock asic
call asic_enable

;; disable ints, because the OS sets colours every
;; VSYNC and I don`t want this to affect the program

di

;; enable asic ram
ld bc,&7fb8
out (c),c


ld ix,read_rgb_colours
ld b,32

ld a,&40
cc:
push bc
;; write colour using CPC method
ld bc,&7f00
;; write pen
out (c),c
;; write colour
out (c),a
inc a

;; read colour 0 from ASIC ram
ld hl,(&6400)
;; store in array
ld (ix+0),l
ld (ix+1),h
inc ix
inc ix
pop bc
djnz cc

;; disable asic ram
ld bc,&7fa0
out (c),c
ei

call check_colours
call km_wait_char
ret


;;-----------------------------------------------------------------------------------------------------

print_hex:
push af
srl a
srl a
srl a
srl a
call print_nibble
pop af
print_nibble:
and &f
cp 9+1
jr c,number_digit
sub 10
add a,"A"
call txt_output
ret
number_digit:
add a,"0"
call txt_output
ret

;;-----------------------------------------------------------------------------------------------------

print_msg:
ld a,(hl)
inc hl
or a
ret z
call txt_output
jr print_msg

;;-----------------------------------------------------------------------------------------------------

check_colours:
;; check values read
ld b,32
ld ix,read_rgb_colours
ld iy,expected_rgb_colours
chkloop:
push ix
push iy
ld hl,pen1_txt
call print_msg

ld a,'&'
call txt_output

ld a,32
sub b
call print_hex
pop ix
pop iy

ld l,(ix+0)
ld h,(ix+1)
ld e,(iy+0)
ld d,(iy+1)
inc ix
inc ix
inc iy
inc iy
push ix
push iy

or a
sbc hl,de
jr z,chkloop2
add hl,de

push hl
ld hl,pen2_txt
call print_msg

ld a,'&'
call txt_output

pop hl
ld a,h
call print_hex
ld a,l
call print_hex

ld hl,pen3_txt
call print_msg

ld a,'&'
call txt_output

ld a,d
call print_hex
ld a,e
call print_hex

ld a,13
call txt_output
ld a,10
call txt_output
jr chkloop3

chkloop2:
ld hl,pen4_txt
call print_msg
chkloop3:

;; wait when we have showed most numbers
ld a,32
sub b
cp 24
call z,km_wait_char

pop iy
pop ix
djnz chkloop
ret

;;-----------------------------------------------------------------------------------------------------

pen1_txt:
defb "Ink ",0

pen2_txt:
defb " is wrong. Got ",0

pen3_txt:
defb " should be ",0

pen4_txt:
defb " is correct.",13,10,0

;;-----------------------------------------------------------------------------------------------------

;; stores rgb colours in ASIC form
read_rgb_colours:
defs 32*2

;;-----------------------------------------------------------------------------------------------------

asic_enable:
push af
push hl
push bc
push de
ld hl,asic_sequence
ld bc,&bc00
ld d,16

ae1:
ld      a,(hl)
out     (c),a
inc     hl
dec     d
jr      nz,ae1
 
ld a,&ee
out (c),a
pop de
pop bc
pop hl
pop af 
ret

 ;;-----------------------------------------------------------------------------------------------------

asic_sequence:
defb &ff,&00  ;; synchronisation
defb &ff,&77,&b3,&51,&a8,&d4,&62,&39,&9c,&46,&2b,&15,&8a,&cd

;;-----------------------------------------------------------------------------------------------------

;; f00 = bright green
;; 9:3:1 weighting
;; 0, 1
;; RB G

;; green is brighter than red, which is brighter than blue

asic_colour macro _r,_g,_b
	defw (_g*256)+(_r*16)+_b
endm

;; GRB
expected_rgb_colours:
asic_colour &06,&06,&06                     ;; White 
asic_colour &06,&06,&06                     ;; White 
asic_colour &00,&0f,&06                     ;; Sea Green 
asic_colour &0f,&0f,&06                     ;; Pastel yellow 
asic_colour &00,&00,&06                     ;; Blue 
asic_colour &0f,&00,&06                     ;; Purple 
asic_colour &00,&06,&06                     ;; Cyan 
asic_colour &0f,&06,&06                     ;; Pink 
asic_colour &0f,&00,&06                     ;; Purple 
asic_colour &0f,&0f,&06                    ;; Pastel yellow 
asic_colour &0f,&0f,&00                     ;; Bright Yellow 
asic_colour &0f,&0f,&0f                     ;; Bright White 
asic_colour &0f,&00,&00                     ;; Bright Red 
asic_colour &0f,&00,&0f                     ;; Bright Magenta 
asic_colour &0f,&06,&00                     ;; Orange 
asic_colour &0f,&06,&0f                     ;; Pastel Magenta 
asic_colour &00,&00,&06                     ;; Blue 
asic_colour &00,&0f,&06                     ;; Sea Green 
asic_colour &00,&0f,&00                     ;; Bright green 
asic_colour &00,&0f,&0f                     ;; Bright Cyan 
asic_colour &00,&00,&00                     ;; Black 
asic_colour &00,&00,&0f                     ;; Bright Blue 
asic_colour &00,&06,&00                     ;; Green 
asic_colour &00,&06,&0f                     ;; Sky Blue 
asic_colour &06,&00,&06                     ;; Magenta 
asic_colour &06,&0f,&06                     ;; Pastel green 
asic_colour &06,&0f,&00                     ;; Lime 
asic_colour &06,&0f,&0f                     ;; Pastel cyan 
asic_colour &06,&00,&00                     ;; Red 
asic_colour &06,&00,&0f                     ;; Mauve 
asic_colour &06,&06,&00                     ;; Yellow 
asic_colour &06,&06,&0f                      ;; Pastel blue 

end start