;->s.vxasm
;
;


R0 RN 0
R1 RN 1
R2 RN 2
R3 RN 3
R4 RN 4
R5 RN 5
R6 RN 6
R7 RN 7
R8 RN 8
R9 RN 9
R10 RN 10
R11 RN 11
R12 RN 12
R13 RN 13
R14 RN 14
R15 RN 15
PC  RN 15


a1 RN 0
a2 RN 1
a3 RN 2
a4 RN 3
v1 RN 4
v2 RN 5
v3 RN 6
v4 RN 7
v5 RN 8
v6 RN 9
sl RN 10
fp RN 11
ip RN 12
sp RN 13
lk RN 14
lr RN 14
pc RN 15

f0 FN 0
f1 FN 1
f2 FN 2
f3 FN 3
f4 FN 4
f5 FN 5
f6 FN 6
f7 FN 7







osbyte * 6
OS_Byte * 6
osvduv * 49
osword * 7
xoffch * 19
xonch  * 17
OS_EnterOS * &16
SVC_Mode * 3



 AREA  VTASM1, REL, CODE


 IMPORT vxchars00
 IMPORT vxchars18
 IMPORT extab



;****************************************************************************
; screen handling code commences at this point 


flashphase  DCD 0

vxflashflash       ; R0=flashphase 0x1000 or 0x0000
 
 STR R0,flashphase;
 MOV R15,R14



grid DCD 0

vxsetgrid          ; R0=yes/no

 STR R0,grid
 MOV R15,R14


; v3 points at char
; can use v2,v4,v5,v6
; v1 contains fancy bits
; v2 character code

; this can be optimised because on DHT chars only need half of bytes


vxfancyhires
fancyhires

 TST    v1,#&2000             ; lining ?
 BEQ    fancyh00
                              ; yes lining

 TST    v2,#&100
 BEQ    fancyh00              ; greater than 256

 AND    v2,v2,#&FF

 CMP    v2,#(353-256)
 BLT    fancyh00
 CMP    v2,#(506-256)
 BLE    fancyhsep


fancyh00
 MOV     v2,#10               ; nb bliting 2 rows at a time
 ADR     v5,fchar

fancyhnxt                     ; blit top 16 rows 

 LDR     v4,[v3],#4

 CMP     v2,#1
 BNE     fhnotul

                              ; now on last 2 rows
 TST     v1,#&2000

 ORRNE   v4,v4,#&FF0000
 ORRNE   v4,v4,#&FF000000
 ORRNE   v4,v4,#&FF00
 ORRNE   v4,v4,#&FF


fhnotul
 TST     v1,#&8000            ; DWL
 BEQ     fhnotl

 LDR     v6,lmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSL#6

 LDR     v6,lmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#2
 LDR     v6,lmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 LDR     v6,lmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 B       fhnotr


fhnotl
 TST     v1,#&4000            ; DWR
 BEQ     fhnotr

 LDR     v6,rmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSR#6

 LDR     v6,rmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#2
 LDR     v6,rmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1
 LDR     v6,rmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1


fhnotr
 STR     v4,[v5],#4


 SUBS    v2,v2,#1
 BNE     fancyhnxt


 ADR     v3,fchar
 MOV     pc,lk


                              ; know this is separated graphics
fancyhsep
 MOV     v2,#10                ; nb bliting 2 rows at a time
 ADR     v5,fchar

fancyhsepnxt                   ; blit 10 rows 


 LDR     v4,grid
 TST     v4,#1
 BEQ     fancyhnotgrid


 LDR     v4,[v3],#4

 CMP     v2,#8
 CMPNE   v2,#4
 CMPNE   v2,#1

; ORREQ   v4,v4,#&FF
; ORREQ   v4,v4,#&FF00

 ORREQ   v4,v4,#&0400
 ORREQ   v4,v4,#&41
 ORREQ   v4,v4,#&FF0000
 ORREQ   v4,v4,#&FF000000

 ORRNE   v4,v4,#&410000       ; C3
 ORRNE   v4,v4,#&04000000     ; C
 ORRNE   v4,v4,#&41           ; C3
 ORRNE   v4,v4,#&0400         ; C


 B       fhsepnotul



fancyhnotgrid
 LDR     v4,[v3],#4

 CMP     v2,#8
 CMPNE   v2,#4
 CMPNE   v2,#1

 BICEQ   v4,v4,#&FF
 BICEQ   v4,v4,#&FF00
 BICEQ   v4,v4,#&FF0000
 BICEQ   v4,v4,#&FF000000

 BICNE   v4,v4,#&C30000
 BICNE   v4,v4,#&0C000000
 BICNE   v4,v4,#&C3
 BICNE   v4,v4,#&0C00



fhsepnotul
 TST     v1,#&8000            ; DWL
 BEQ     fhsepnotl

 LDR     v6,lmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSL#6

 LDR     v6,lmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#2
 LDR     v6,lmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 LDR     v6,lmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 B       fhsepnotr


fhsepnotl
 TST     v1,#&4000            ; DWR
 BEQ     fhsepnotr

 LDR     v6,rmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSR#6

 LDR     v6,rmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#2
 LDR     v6,rmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1
 LDR     v6,rmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1


fhsepnotr
 STR     v4,[v5],#4


 SUBS    v2,v2,#1
 BNE     fancyhsepnxt


 ADR     v3,fchar
 MOV     pc,lk








lmaskx DCD &FFC0FFC0
lmask0 DCD &F0F0F0F0
lmask1 DCD &CCCCCCCC
lmask2 DCD &AAAAAAAA

rmaskx DCD &03FF03FF
rmask0 DCD &0F0F0F0F
rmask1 DCD &33333333
rmask2 DCD &55555555




fchar
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0


; v3 points at char
; can use v2,v4,v5,v6
; v1 contains fancy bits
; v2 character code


; we know this is only ever called on single height stuff

vxfancylores
fancylores

 TST    v1,#&2000             ; lining ?
 BEQ    fancy00
                              ; yes lining

 TST    v2,#&100
 BEQ    fancy00               ; greater than 256

 AND    v2,v2,#&FF

 CMP    v2,#(353-256)
 BLT    fancy00
 CMP    v2,#(506-256)
 BLE    fancysep


fancy00
 MOV     v2,#5                ; nb bliting 2 rows at a time
 ADR     v5,fchar

fancynxt                      ; blit top 8 rows 

 LDR     v4,[v3],#4

 CMP     v2,#1
 BNE     fnotul

                              ; now on last 2 rows
 TST     v1,#&2000            

 ORRNE   v4,v4,#&FF0000
 ORRNE   v4,v4,#&FF000000


fnotul
 TST     v1,#&8000            ; DWL
 BEQ     fnotl

 LDR     v6,lmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSL#6

 LDR     v6,lmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#2
 LDR     v6,lmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 LDR     v6,lmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 B       fnotr


fnotl
 TST     v1,#&4000            ; DWR
 BEQ     fnotr

 LDR     v6,rmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSR#6

 LDR     v6,rmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#2
 LDR     v6,rmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1
 LDR     v6,rmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1


fnotr
 STR     v4,[v5],#4


 SUBS    v2,v2,#1
 BNE     fancynxt


 ADR     v3,fchar
 MOV     pc,lk


                              ; know this is separated graphics
fancysep
 MOV     v2,#5                ; nb bliting 2 rows at a time
 ADR     v5,fchar

fancysepnxt                   ; blit 10 rows 


 LDR     v4,grid
 TST     v4,#1
 BEQ     fancynotgrid



 LDR     v4,[v3],#4

 ORR     v4,v4,#&C30000
 ORR     v4,v4,#&0C000000
 ORR     v4,v4,#&C3
 ORR     v4,v4,#&0C00


 CMP     v2,#4
 CMPNE   v2,#2

 ORREQ   v4,v4,#&FF
 ORREQ   v4,v4,#&FF00

 CMP     v2,#1
 ORREQ   v4,v4,#&FF0000
 ORREQ   v4,v4,#&FF000000
 
 B       fsepnotul


fancynotgrid                 ; sep graphics not grid 
 LDR     v4,[v3],#4

 BIC     v4,v4,#&C30000
 BIC     v4,v4,#&0C000000
 BIC     v4,v4,#&C3
 BIC     v4,v4,#&0C00


 CMP     v2,#4
 CMPNE   v2,#2

 BICEQ   v4,v4,#&FF
 BICEQ   v4,v4,#&FF00

 CMP     v2,#1
 BICEQ   v4,v4,#&FF0000
 BICEQ   v4,v4,#&FF000000


fsepnotul
 TST     v1,#&8000            ; DWL
 BEQ     fsepnotl

 LDR     v6,lmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSL#6

 LDR     v6,lmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#2
 LDR     v6,lmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 LDR     v6,lmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSL#1
 B       fsepnotr


fsepnotl
 TST     v1,#&4000            ; DWR
 BEQ     fsepnotr

 LDR     v6,rmaskx
 BIC     v4,v4,v6
 ORR     v4,v4,v4,LSR#6

 LDR     v6,rmask0
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#2
 LDR     v6,rmask1
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1
 LDR     v6,rmask2
 BIC     v4,v4,v6

 ORR     v4,v4,v4,LSR#1


fsepnotr
 STR     v4,[v5],#4


 SUBS    v2,v2,#1
 BNE     fancysepnxt


 ADR     v3,fchar
 MOV     pc,lk










; a1 pointer to data in memory
; a2 pointer to destination of bit map
; a3 number of characters to output
; a4 width  of sprite in bytes
;
; v1 char word
; v2 temp
; v3 character defn.
; v4 where we write output bytes
; v5 colour
; v6 colour


vxline00S
 MOV   ip,sp
 STMFD sp!,{v1-v6,sl,fp,ip,lk,pc}
 SUB   fp,ip,#4

 LDR   sl,=extab
 SUB   sp,a4,#2
 SUB   a4,a4,#5

linelp00S             ; for each character to print to sprite

; we set off with LH half of character on word boundary

 LDR   v1,[a1],#4

 AND   v2,v1,#&FF     ; get number of character in v2
 AND   v3,v1,#&100
 ORR   v2,v2,v3

 TST   v1,#&FE00      ; was FF
 BEQ   linenf00S

 LDR   v6,flashphase
 TST   v1,v6
 ADRNE v3,nullchar
 BNE   linerx00S

 TST   v1,#&C00
 BEQ   linenf00S

 LDR   v3,=vxchars18  ; 40 bytes per character
 ADD   v3,v3,v2,ASL#5 ; point v3 at char
 ADD   v3,v3,v2,ASL#3

 TST   v1,#&E000
 BLNE  fancyhires 

 TST   v1,#&800
 ADDNE v3,v3,#20
 B     linerx00S


linenf00S              ; come here if character not fancy
                       ; point v3 at start of char tab


 LDR   v3,=vxchars00   ; 20 bytes per character
 ADD   v3,v3,v2,ASL#4  ; point v3 at char
 ADD   v3,v3,v2,ASL#2

 TST   v1,#&E000
 BLNE  fancylores 

linerx00S


 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#5

linelp200S
 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&FF
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char word

 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],a4


 AND    v2,v1,#&FF0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char word

 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],a4

                         ; written two rows so loop

 SUBS   lk,lk,#1
 BNE    linelp200S

 ADD    a2,a2,#6         ; move right one posn

 SUBS   a3,a3,#1
 BLE    linexx00S


; now RH half of character not on word boundary

 LDR  v1,[a1],#4

 AND  v2,v1,#&FF     ; get number of character in v2
 AND  v3,v1,#&100
 ORR  v2,v2,v3

 TST  v1,#&FE00      ; was FF
 BEQ  linenf200S

 LDR   v6,flashphase
 TST   v1,v6
 ADRNE v3,nullchar
 BNE   linerx200S

 TST  v1,#&C00
 BEQ  linenf200S


 LDR  v3,=vxchars18  ; 40 bytes per character
 ADD  v3,v3,v2,ASL#5 ; point v3 at char
 ADD  v3,v3,v2,ASL#3

 TST   v1,#&E000
 BLNE  fancyhires 

 TST   v1,#&800
 ADDNE v3,v3,#20
 B     linerx200S


linenf200S            ; come here if character not fancy
                      ; point v3 at start of char tab
 LDR  v3,=vxchars00   ; 20 bytes per character
 ADD  v3,v3,v2,ASL#4  ; point v3 at char
 ADD  v3,v3,v2,ASL#2

 TST   v1,#&E000
 BLNE  fancylores 

linerx200S


 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#5

linelp300S
 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],#1


 AND    v2,v1,#&FF00
 LDR    v2,[sl,v2,LSR#6]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char word



 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],#1

 AND    v2,v1,#&FF000000
 LDR    v2,[sl,v2,LSR#22]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char word

                         ; written two rows so loop

 SUBS   lk,lk,#1
 BNE    linelp300S

 ADD    a2,a2,#6        ; move right one posn

 SUBS   a3,a3,#1

 BGT    linelp00S

linexx00S
 LDMEA fp,{v1-v6,sl,fp,sp,pc}








vxline18S
 MOV   ip,sp
 STMFD sp!,{v1-v6,sl,fp,ip,lk,pc}
 SUB   fp,ip,#4

 LDR   sl,=extab
 MOV   ip,a4
 SUB   sp,a4,#2
 SUB   a4,a4,#5



linelp18S            ; for each character to print to sprite

; we set off with LH half of character on word boundary

 LDR  v1,[a1],#4

 AND  v2,v1,#&FF     ; get number of character in v2
 AND  v3,v1,#&100
 ORR  v2,v2,v3

                     ; point v3 at start of char tab
 LDR  v3,=vxchars18  ; 20 bytes per character
 ADD  v3,v3,v2,ASL#5 ; point v3 at char
 ADD  v3,v3,v2,ASL#3

 LDR   v6,flashphase
 TST   v1,v6 
 ADRNE v3,nullchar
 BNE   linerx18S

 TST   v1,#&E000
 BLNE  fancyhires 

linerx18S

 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#10

 TST    v1,#&400
 BNE    linelp218ST
 TST    v1,#&800
 BNE    linelp218SB

 SUB   sp,ip,#2
 SUB   a4,ip,#5


linelp218S
 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&FF
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char word

 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],a4


 AND    v2,v1,#&FF0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char word

 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],a4

                         ; written two rows so loop

 SUBS   lk,lk,#1
 BNE    linelp218S

 ADD    a2,a2,#6         ; move right one posn

 SUBS   a3,a3,#1
 BLE    linexx18S


line18SMID

; now RH half of character not on word boundary

 LDR  v1,[a1],#4

 AND  v2,v1,#&FF      ; get number of character in v2
 AND  v3,v1,#&100
 ORR  v2,v2,v3

                      ; point v3 at start of char tab
 LDR  v3,=vxchars18   ; 20 bytes per character
 ADD  v3,v3,v2,ASL#5  ; point v3 at char
 ADD  v3,v3,v2,ASL#3


 LDR   v6,flashphase
 TST   v1,v6
 ADRNE v3,nullchar
 BNE   linerx218S

 TST   v1,#&E000
 BLNE  fancyhires 

linerx218S



 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#10


 TST    v1,#&400
 BNE    linelp318ST
 TST    v1,#&800
 BNE    linelp318SB

 SUB   sp,ip,#2
 SUB   a4,ip,#5



linelp318S
 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],#1


 AND    v2,v1,#&FF00
 LDR    v2,[sl,v2,LSR#6]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char word



 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],#1       ; write char word

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],#1

 AND    v2,v1,#&FF000000
 LDR    v2,[sl,v2,LSR#22]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char word


                         ; written two rows so loop

 SUBS   lk,lk,#1
 BNE    linelp318S

 ADD    a2,a2,#6        ; move right one posn

 SUBS   a3,a3,#1

 BGT    linelp18S

linexx18S
 LDMEA fp,{v1-v6,sl,fp,sp,pc}




nullchar
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0
 DCD 0




; this does LH Bottom half

linelp218SB
 ADD    v3,v3,#20

; this does LH Top half

linelp218ST

 SUB    sp,ip,#1
 SUB    a4,ip,#4

linelp2218ST

 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&FF
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],ip       ; write char word
 STR    v2,[v4],-a4

 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],ip       ; write char word
 STRB   v2,[v4],-sp

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],ip
 STRB   v2,[v4],ip

 SUB    v4,v4,#5         ; nb


 AND    v2,v1,#&FF0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],ip       ; write char word
 STR    v2,[v4],-a4


 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],ip       ; write char word
 STRB   v2,[v4],-sp

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],ip
 STRB   v2,[v4],ip

 SUB    v4,v4,#5         ; nb

                         ; written two rows so loop

 SUBS   lk,lk,#2
 BNE    linelp2218ST

 ADD    a2,a2,#6         ; move right one posn

 SUBS   a3,a3,#1

 BGT    line18SMID

 LDMEA fp,{v1-v6,sl,fp,sp,pc}
 



; this does RH bottom half

linelp318SB
 ADD    v3,v3,#20

; this does RH Top half

linelp318ST

 SUB    sp,ip,#1
 SUB    a4,ip,#2

linelp3218ST

 LDR    v1,[v3],#4     ; loaded 2 rows of character

 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],ip       ; write char word
 STRB   v2,[v4],-sp

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],ip
 STRB   v2,[v4],-sp


 AND    v2,v1,#&FF00
 LDR    v2,[sl,v2,LSR#6]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],ip       ; write char word
 STR    v2,[v4],a4


 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STRB   v2,[v4],ip       ; write char word
 STRB   v2,[v4],-sp

 MOV    v2,v2,LSR#8
 STRB   v2,[v4],ip
 STRB   v2,[v4],-sp

 AND    v2,v1,#&FF000000
 LDR    v2,[sl,v2,LSR#22]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],ip       ; write char word
 STR    v2,[v4],a4


 SUBS   lk,lk,#2
 BNE    linelp3218ST

 ADD    a2,a2,#6        ; move right one posn

 SUBS   a3,a3,#1

 BGT    linelp18S

 LDMEA fp,{v1-v6,sl,fp,sp,pc}
 








expltab
 DCD &00000000
 DCD &000000FF
 DCD &0000FF00
 DCD &0000FFFF
 DCD &00FF0000
 DCD &00FF00FF
 DCD &00FFFF00
 DCD &00FFFFFF
 DCD &FF000000
 DCD &FF0000FF
 DCD &FF00FF00
 DCD &FF00FFFF
 DCD &FFFF0000
 DCD &FFFF00FF
 DCD &FFFFFF00
 DCD &FFFFFFFF



; a1 pointer to data in memory
; a2 pointer to destination of bit map
; a3 number of characters to output
; a4 width  of sprite in bytes
;
; v1 char word
; v2 temp
; v3 character defn.
; v4 where we write output bytes
; v5 colour
; v6 colour

vxline15S
 MOV   ip,sp
 STMFD sp!,{v1-v6,sl,fp,ip,lk,pc}
 SUB   fp,ip,#4

 SUB   a4,a4,#8
 ADR   sl,expltab

linelp15S            ; for each character to print to sprite

 LDR  v1,[a1],#4

 AND  v2,v1,#&FF     ; get number of character in v2
 AND  v3,v1,#&100
 ORR  v2,v2,v3


 TST  v1,#&FE00      ; was FF
 BEQ  linenf15S


 LDR   v6,flashphase
 TST   v1,v6
 ADRNE v3,nullchar
 BNE   linerx15S

 TST  v1,#&C00
 BEQ  linenf15S


 LDR  v3,=vxchars18  ; 40 bytes per character
 ADD  v3,v3,v2,ASL#5 ; point v3 at char
 ADD  v3,v3,v2,ASL#3

 TST   v1,#&E000
 BLNE  fancyhires

 TST   v1,#&800
 ADDNE v3,v3,#20
 B     linerx15S

linenf15S            ; come here if character not fancy
                     ; point v3 at start of char tab
 LDR  v3,=vxchars00  ; 20 bytes per character
 ADD  v3,v3,v2,ASL#4 ; point v3 at char
 ADD  v3,v3,v2,ASL#2

 TST   v1,#&E000
 BLNE  fancylores 

linerx15S


 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#5

linelp215S
 LDR    v1,[v3],#4


 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F0
 LDR    v2,[sl,v2,LSR#2]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],a4       ; write char byte


 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F00000
 LDR    v2,[sl,v2,LSR#18]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],a4       ; write char byte


 SUBS   lk,lk,#1
 BNE    linelp215S

 ADD    a2,a2,#12        ; move right one posn
 SUBS   a3,a3,#2
 BGT    linelp15S

 LDMEA fp,{v1-v6,sl,fp,sp,pc}













; a1 pointer to data in memory
; a2 pointer to destination of bit map
; a3 number of characters to output
; a4 width  of sprite in bytes
;
; v1 char word
; v2 temp
; v3 character defn.
; v4 where we write output bytes
; v5 colour
; v6 colour

vxline23S
 MOV   ip,sp
 STMFD sp!,{v1-v6,sl,fp,ip,lk,pc}
 SUB   fp,ip,#4

 SUB   ip,a4,#4
 MOV   sp,a4
 SUB   a4,a4,#8

 ADR   sl,expltab

linelp23S            ; for each character to print to sprite

 LDR  v1,[a1],#4

 AND  v2,v1,#&FF     ; get number of character in v2
 AND  v3,v1,#&100
 ORR  v2,v2,v3

                     ; point v3 at start of char tab
 LDR  v3,=vxchars18  ; 40 bytes per character
 ADD  v3,v3,v2,ASL#5 ; point v3 at char
 ADD  v3,v3,v2,ASL#3

 LDR   v6,flashphase
 TST   v1,v6
 ADRNE v3,nullchar
 BNE   linerx23S

 TST   v1,#&E000
 BLNE  fancyhires 

linerx23S

 AND v5,v1,#&FF000000
 ORR v5,v5,v5,LSR#8
 ORR v5,v5,v5,LSR#16

 AND v6,v1,#&FF0000
 ORR v6,v6,v6,LSL#8
 ORR v6,v6,v6,LSR#16

 MOV    v4,a2

 MOV    lk,#10

 TST    v1,#&400
 BNE    linelp223ST
 TST    v1,#&800
 BNE    linelp223SB

linelp223S
 LDR    v1,[v3],#4

 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F0
 LDR    v2,[sl,v2,LSR#2]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],a4       ; write char byte


 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F00000
 LDR    v2,[sl,v2,LSR#18]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],#4       ; write char byte


 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],a4       ; write char byte


 SUBS   lk,lk,#1
 BNE    linelp223S

 ADD    a2,a2,#12        ; move right one posn
 SUBS   a3,a3,#2
 BGT    linelp23S

 LDMEA fp,{v1-v6,sl,fp,sp,pc}



linelp223SB               ; bottom of character

 ADD    v3,v3,#20


linelp223ST
 LDR    v1,[v3],#4

 AND    v2,v1,#&F
 LDR    v2,[sl,v2,LSL#2]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],-ip


 AND    v2,v1,#&F0
 LDR    v2,[sl,v2,LSR#2]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],-ip


 AND    v2,v1,#&F000
 LDR    v2,[sl,v2,LSR#10]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],a4

                         ; completed one row


 AND    v2,v1,#&F0000
 LDR    v2,[sl,v2,LSR#14]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],-ip


 AND    v2,v1,#&F00000
 LDR    v2,[sl,v2,LSR#18]


 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],-ip


 AND    v2,v1,#&F0000000
 LDR    v2,[sl,v2,LSR#26]

 AND    v2,v2,v5
 EOR    v2,v2,v6         ; mask with colours
 STR    v2,[v4],sp       ; write char byte
 STR    v2,[v4],a4


 SUBS   lk,lk,#2
 BNE    linelp223ST

 ADD    a2,a2,#12        ; move right one posn
 SUBS   a3,a3,#2
 BGT    linelp23S

 LDMEA fp,{v1-v6,sl,fp,sp,pc}


 EXPORT vxline00S
 EXPORT vxline18S

 EXPORT vxline15S
 EXPORT vxline23S

 EXPORT vxflashflash
 EXPORT vxsetgrid


 EXPORT vxfancylores
 EXPORT vxfancyhires

 END
