
msk:	equ	00CC9H
wy:	equ	00CCAH	;wy,ex form a double byte in this order
ex:	equ	00CCBH
wye:	equ	00CCCH
eks:	equ	00CCDH
ssiz:	equ	02000H
rsiz:	equ	040H
sorg:	equ	04000H

	org	0100H
	jmp gdem


;	point mode: move cursor right

pxpl:	lxi h,msk
	mov a,m
	ani 0AAH
	jz  pxp1
	rrc
	mov m,a
	ret
pxp1:	mov a,m
	rrc
	rrc
	rrc
	mov m,a
	ani 0A0H
	rz
	lda ex
	adi 004H
	sta ex
	ret

;	point mode: move cursor left

pxmi:	lxi h,msk
	mov a,m
	ani 055H
	jz  pxm1
	rlc
	mov m,a
	ret
pxm1:	mov a,m
	rlc
	rlc
	rlc
	mov m,a
	ani 005H
	rz
	lda ex
	sui 004H
	sta ex
	ret

;	point mode: move cursor up

pypl:	lxi h,msk
	mov a,m
	ani 033H
	jz  pyp1
	rlc
	rlc
	mov m,a
	ret
pyp1:	mov a,m
	rrc
	rrc
	mov m,a
	lda wy
	sui 002H
	sta wy
	ret

;	point mode: move cursor down

pymi:	lxi h,msk
	mov a,m
	ani 0CCH
	jz  pym1
	rrc
	rrc
	mov m,a
	ret
pym1	mov a,m
	rlc
	rlc
	mov m,a
	lda wy
	adi 002H
	sta wy
	ret

;	load acc with mask, HL with byte address from
;	(msk,wy,ex)

dot:	lhld wy
	mov a,h
	mvi h,sorg/02000H
	dad h
	dad h
	dad h
	dad h
	dad h
	rrc
	rrc
	ora l
	mov l,a
	lda msk
	ret

;	point mode: home cursor

phom:	lxi h,08080H
	shld wy
	mvi a,040H
	sta msk
	ret

;	point mode: make white dot at cursor

pwhit:	call dot
	ora m
	mov m,a
	ret

;	point mode: make black dot at cursor

pblak:	call dot
	cma
	ana m
	mov m,a
	ret

;	point mode: reverse dot under cursor

prev:	call dot
	xra m
	mov m,a
	ret

;	point mode: test dot under cursor

ptest:	call dot
	ana m
	ret

;	both modes: clear screen to white

whit:	lxi d,ssiz
	lxi h,sorg
whi1:	mvi m,0FFH
	inx h
	dcr e
	jnz whi1
	dcr d
	jnz whi1
	ret

;	both modes: clear screen to black

blak:	lxi d,ssiz
	lxi h,sorg
bla1:	mvi m,000H
	inx h
	dcr e
	jnz bla1
	dcr d
	jnz bla1
	ret

;	both modes: reverse entire screen

reve:	lxi d,ssiz
	lxi h,sorg
rev1:	mov a,m
	xri 0FFH
	mov m,a
	inx h
	dcr e
	jnz rev1
	dcr d
	jnz rev1
	ret

;	point mode:	given a cartesian address, form a bit
;	mask and byte address for the cursor

pcar:	lhld wye
	mvi b,001H
	mov a,h
	rrc
	jnc pca1
	mov h,a
	mov a,b
	rlc
	mov b,a
	mov a,h
pca1:	rrc
	jnc pca2
	mov a,b
	rlc
	rlc
	rlc
	rlc
	mov b,a
pca2:	mov a,l
	rrc
	mov b,a
	jnc pca3
	rlc
	rlc
pca3:	sta msk
	lda wye
	ani 0FCH
	sta wy
	lda eks
	ani 0FEH
	sta wy
	ret

;	point mode:  draw a line between two points
;	given the increments (B,C)=(dx,dy)

plin:	lxi h,pxpl
	mov a,b
	ora a
	jp  pli1
	cma
	inr a
	mov b,a
	lxi h,pxmi
pli1:	lxi d,pypl
	mov a,c
	ora a
	jp  pli2
	cma
	inr a
	mov c,a
	lxi d,pymi
pli2:	cmp b
	jnc pli3
	xchg
	mov c,b
	mov b,a
pli3:	mov a,c
	sta eks
	mov a,b
	add a
	mov b,a
	sub c
	push psw
	sub c
	mov c,a
pli4:	pop psw
	push h
	lxi h,prev
	xthl
	cpi 001H
	jm  pli5
	push h
	add c
	jmp pli6
pli5:	add b
pli6:	push d
	push psw
	lda eks
	dcr a
	sta eks
	jnz pli4
	pop psw
	ret

;	point mode: shift within one byte to scroll the
;	screen right one pixel

pexpl:	mov a,m
	rrc
	mov b,a
	ani 055H
	ora c
	mov c,a
	mov a,b
	rrc
	rrc
	mov b,a
	ani 00AH
	ora c
	mov c,a
	mov a,b
	ani 0A0H
	mov b,c
	mov c,a
	ret

;	point mode: intra-byte shift to scroll left one pixel

pexmi:	mov a,m
	rlc
	mov b,a
	ani 0AAH
	ora c
	mov c,a
	mov a,b
	rlc
	rlc
	mov b,a
	ani 050H
	ora c
	mov c,a
	mov a,b
	ani 005H
	mov b,c
	mov c,a
	ret

;	point mode: intrabyte shift to scroll up one pixel

pwypl:	mov a,m
	mov b,a
	rlc
	rlc
	ani 0CCH
	ora c
	mov c,a
	mov a,b
	ani 0CCH
	rrc
	rrc
	mov b,c
	mov c,a
	ret

;	point mode: intrabyte shift to scroll down one pixel

pwymi:	mov a,m
	mov b,a
	rrc
	rrc
	ani 033H
	ora c
	mov c,a
	mov a,b
	ani 033H
	rlc
	rlc
	mov b,c
	mov c,a
	ret

;	point mode: move entire screen right one pixel

pekspl:	lxi h,sorg
	lxi d,rsiz-1
peksp1:	push h
	dad d
	call pexpl
	pop h
peksp2:	call pexpl
	mov m,b
	inx h
	mov a,l
	ani 03FH
	jnz peksp2
	mov a,h
	cpi (sorg+ssiz)/0100H
	jnz peksp1
	ret

;	point mode: shift entire screen left one pixel

peksmi:	lxi h,sorg+ssiz-1
	lxi d,-rsiz+1
peksm1:	push h
	dad d
	call pexmi
	pop h
peksm2:	call pexmi
	mov m,b
	mov a,l
	ani 03FH
	dcx h
	jnz peksm2
	mov a,h
	cpi sorg/0100H-1
	jnz peksm1
	ret

;	point mode: shift entire screen up one pixel

pwyepl:	lxi h,sorg+ssiz-1
pwyep1:	lxi d,-ssiz+rsiz
	push h
	dad d
	call pwypl
	pop h
	push h
	lxi d,-rsiz
pwyep2:	call pwypl
	mov m,b
	dad d
	mov a,h
	cpi sorg/0100H-1
	jnz pwyep2
	pop h
	mov a,l
	ani 03FH
	dcx h
	jnz pwyep1
	ret

;	point mode: move entire screen down one pixel

pwyemi:	lxi h,sorg
pwyem1:	lxi d,ssiz-rsiz
	push h
	dad d
	call pwymi
	pop h
	push h
	lxi d,rsiz
pwyem2:	call pwymi
	mov m,b
	dad d
	mov a,h
	cpi (sorg+ssiz)/0100H
	jnz pwyem2
	pop h
	inx h
	mov a,l
	ani 03FH
	jnz pwyem1
	ret

;	fast right shift of 4 pixels= 1 byte

fxpl:	lxi h,sorg
	lxi d,rsiz-1
fxp1:	push h
	dad d
	mov b,m
	pop h
fxp2:	mov a,m
	mov m,b
	mov b,a
	inx h
	mov a,l
	ani 03FH
	jnz fxp2
	mov a,h
	cpi (sorg+ssiz)/0100H
	jnz fxp1
	ret

;	fast left shift of 4 pixels which is one byte

fxmi:	lxi h,sorg+ssiz-1
	lxi d,-rsiz+1
fxm1:	push h
	dad d
	mov b,m
	pop h
fxm2:	mov a,m
	mov m,b
	mov b,a
	mov a,l
	ani 03FH
	dcx h
	jnz fxm2
	mov a,h
	cpi sorg/0100H-1
	jnz fxm1
	ret

;	fast shift up by 2 pixels = 1 byte

fypl:	lxi h,sorg+ssiz-1
fyp1:	lxi d,-ssiz+rsiz
	push h
	dad d
	mov b,m
	pop h
	push h
	lxi d,-rsiz
fyp2:	mov a,m
	mov m,b
	mov b,a
	dad d
	mov a,h
	cpi sorg/0100H-1
	jnz fyp2
	pop h
	mov a,l
	ani 03FH
	dcx h
	jnz fyp1
	ret

;	fast down shift of entire screen by 2 pixels = 1 byte

fymi:	lxi h,sorg
fym1:	lxi d,ssiz-rsiz
	push h
	dad d
	mov b,m
	pop h
	push h
	lxi d,rsiz
fym2:	mov a,m
	mov m,b
	mov b,a
	dad d
	mov a,h
	cpi (sorg+ssiz)/0100H
	jnz fym2
	pop h
	inx h
	mov a,l
	ani 03FH
	jnz fym1
	ret

;	gray mode: in-byte right shift

gexpl:	mov a,m
	rrc
	rrc
	rrc
	rrc
	mov b,a
	ani 00FH
	ora c
	mov c,a
	mov a,b
	ani 0F0H
	mov b,c
	mov c,a
	ret

;	gray mode: intrabyte left shift of one pixel

gexmi:	mov a,m
	rlc
	rlc
	rlc
	rlc
	mov b,a
	ani 0E0H
	ora c
	mov c,a
	mov a,b
	ani 00FH
	mov b,c
	mov c,a
	ret

;	gray mode: shift whole screen 1 pixel right

gekspl:	lxi h,sorg
	lxi d,rsiz-1
geksp1:	push h
	dad d
	call gexpl
	pop h
geksp2:	call gexpl
	mov m,b
	inx h
	mov a,l
	ani 03FH
	jnz geksp2
	mov a,h
	cpi (sorg+ssiz)/0100H
	jnz geksp1
	ret

;	gray mode: shift entire screen left one pixel

geksmi:	lxi h,sorg+ssiz-1
	lxi d,-rsiz+1
geksm1:	push h
	dad d
	call gexmi
	pop h
geksm2:	call gexmi
	mov m,b
	mov a,l
	ani 03FH
	dcx h
	jnz geksm2
	mov a,h
	cpi sorg/0100H-1
	jnz geksm1
	ret

;	gray mode: move cursor right one pixel

gxpl:	lxi h,msk
	mov a,m
	ani 0F0H
	jz  gxp1
	mvi m,00FH
	ret
gxp1:	mvi m,0F0H
	lda ex
	adi 004H
	sta ex
	ret

;	gray mode: shift cursor left one pixel

gxmi:	lxi h,msk
	mov a,m
	ani 00FH
	jz  gxm1
	mvi m,0F0H
	ret
gxm1:	mvi m,00FH
	lda ex
	sui 004H
	sta ex
	ret

;	gray mode: move cursor up one pixel

gypl:	lda wy
	sui 002H
	sta wy
	ret

;	gray mode: move cursor down one pixel

gymi:	lda wy
	adi 002H
	sta wy
	ret

;	gray mode: home cursor

ghom:	lxi h,08080H
	shld wy
	mvi a,00FH
	sta msk
	ret

;	gray mode: make cursor pixel white

gwhi:	call dot
	ora m
	mov m,a
	ret

;	gray mode: make cursor pixel black

gbla:	call dot
	cma
	ana m
	mov m,a
	ret

;	gray mode: reverse cursor pixel

grev:	call dot
	xra m
	mov m,a
	ret

;	gray mode: sense cursor pixel

gsen:	call dot
	ana m
	rz
	push psw
	ani 0F0H
	pop psw
	rz
	rrc
	rrc
	rrc
	rrc
	ret

;	gray mode: raise gray level of cursor pixel

gzpl:	call dot
	mov b,a
	cma
	ana m
	mov c,a
	mov a,b
	ana m
	adi 011H
	ana b
	ora c
	mov m,a
	ret

;	gray mode: lower pixel under cursor one gray level

gzmi:	call dot
	mov b,a
	cma
	ana m
	mov c,a
	mov a,b
	ana m
	adi 0FFH
	ana b
	ora c
	mov m,a
	ret

;	gray mode: cartesian coordinates to mask, byte address

gcart:	lhld wye
	mov a,l
	ani 03FH
	rlc
	sta wy
	mov a,h
	ani 03FH
	rrc
	push psw
	rlc
	rlc
	rlc
	sta ex
	pop psw
	mvi a,00FH
	jc  gcar1
	xri 0FFH
gcar1:	sta msk
	ret

;	form decimal number from digit string

nure:	mvi b,000H
nur1:	call read
	cpi '-'
	jz  numi
	cpi '0'
	rc
	cpi ':'
	rnc
	sui '0'
	mov c,a
	mov a,b
	rlc
	rlc
	add b
	rlc
	add c
	mov b,a
	jmp nur1
numi:	lxi h,minu
	push h
	jmp nur1
minu:	push psw
	mov a,b
	cma
	inr a
	mov b,a
	pop psw
	ret

;	get (B,C)=(count, operation)

coop:	call nure
	mov c,a
	mov a,b
	ora a
	rnz
	mvi b,001H
	ret

;	get (B,C)=(x,y)

coor:	call nure
	push b
	call nure
	pop psw
	mov c,b
	mov b,a
	ret

;	repeat the subroutine in (HL) (B) times

iter:	push b
	mov a,c
	push h
	lxi d,ite1
	push d
	pchl
ite1:	pop h
	pop b
	dcr b
	rz
	jmp iter

	nop
	nop

;	block of combined cursor movements and cursor
;	inversions in the point mode - for demonstration

pn:	call prev
	call pypl
	jmp  prev

ps:	call prev
	call pymi
	jmp  prev

pe:	call prev
	call pxpl
	jmp  prev

pw:	call prev
	call pxmi
	jmp  prev

;	place the individual negatives of the bytes B,C in H,L

negl:	mov a,c
	cma
	inr a
	mov l,a
	mov a,b
	cma
	inr a
	mov h,a
	ret

;	add D,E to H,L as two separate bytes, sum in H,L

addl:	mov a,e
	add l
	mov l,a
	mov a,d
	add h
	mov h,a
	ret

;	command i reads increment pair, plots line

pii:	call coor
	jmp  plin

;	command t reads two adjacent edges, plots triangle

tt:	call coor
	call negl
	push h
	push b
	call coor
	call negl
	pop d
	call addl
	push h
	call plin
	pop b
	call plin
	pop b
	jmp  plin

;	command p reads cartesian coordinates, plots point

pp:	call coor
	mov a,b
	adi 080H
	sta eks
	mov a,c
	cma
	adi 081H
	sta wye
	call pcar
	jmp  prev

;	block of combined screen-cursor shifts

pea:	call pekspl
	jmp  pxpl

pwe:	call peksmi
	jmp  pxmi

pno:	call pwyepl
	jmp  pypl

pso:	call pwyemi
	jmp  pymi

;	similar block for grey mode

gea:	call gekspl
	jmp  gxpl

gwe:	call geksmi
	jmp  gxmi

gno:	call fypl
	jmp  gypl

gso:	call fymi
	jmp  gymi

;	combined cursor movement and 8-level gray shift

ge:	call gzeh
	call gxpl
	jmp  gzeh

gw:	call gzeh
	call gxmi
	jmp  gzeh

gn:	call gzeh
	call gypl
	jmp  gzeh

gs:	call gzeh
	call gymi
	jmp  gzeh

;	move whole screen through 8 gray points

gzeeh:	lxi d,ssiz
	lxi h,sorg
gzee1:	mov b,m
	mov a,b
	ani 0F0H
	mov c,a
	mov a,b
	adi 008H
	ani 00FH
	ora c
	adi 080H
	mov m,a
	inx h
	dcr e
	jnz gzee1
	dcr d
	jnz gzee1
	ret

;	lighten the whole screen by one grey point

gzeepl:	lxi d,ssiz
	lxi h,sorg
gzeep1:	mov b,m
	mov a,b
	ani 0F0H
	mov c,a
	mov a,b
	adi 001H
	ani 00FH
	ora c
	adi 010H
	mov m,a
	inx h
	dcr e
	jnz gzeep1
	dcr d
	jnz gzeep1
	ret

;	darken whole screen by one gray point

gzeemi:	lxi d,ssiz
	lxi h,sorg
gzeem1:	mov b,m
	mov a,b
	ani 0F0H
	mov c,a
	mov a,b
	adi 00FH
	ani 00FH
	ora c
	adi 0F0H
	mov m,a
	inx h
	dcr e
	jnz gzeem1
	dcr d
	jnz gzeem1
	ret

;	lighten the pixel under the cursor by 8 points

gzeh:	call dot
gzed:	mov c,a
	cma
	ana m
	mov b,a
	mov a,m
	ana c
	adi 088H
	ana c
	ora b
	mov m,a
	ret

;	lighten all pixels from here to left margin 8 points

edge:	call dot
	ora a
	jp edg1
	call gzed
edg1:	mov a,l
	ani 03FH
	rz
	dcx h
	mov b,m
	mov a,b
	ani 0F0H
	mov c,a
	mov a,b
	sui 008H
	ani 00FH
	ora c
	sui 080H
	mov m,a
	jmp edg1

;	block of combined cursor movements and pixel reverses

gee:	call gxpl
	jmp  gzeh

gww:	call gxmi
	jmp  gzeh

gnn:	call gypl
	jmp  gzeh

gss:	call gymi
	jmp  gzeh

;	draw a line with given increments in grey mode

glin:	lxi h,gxpl
	mov a,b
	ora a
	jp gli1
	cma
	inr a
	mov b,a
	lxi h,gxmi
gli1:	lxi d,gypl
	mov a,c
	ora a
	jp gli2
	cma
	inr a
	mov c,a
	lxi d,gymi
gli2:	cmp b
	jnc gli3
	xchg
	mov c,b
	mov b,a
gli3:	mov a,c
	sta eks
	mov a,b
	add a
	mov b,a
	sub c
	push psw
	sub c
	mov c,a
gli4:	pop psw
	push h
	lxi h,gzeh
	xthl
	cpi 001H
	jm gli5
	push h
	add c
	jmp gli6
gli5:	add b
gli6:	push d
	push psw
	lda eks
	dcr a
	sta eks
	jnz gli4
	pop psw
	ret

;	draw a shaded triangle

shat:	call coor
	call negl
	push h
	push b
	call coor
	call negl
	pop d
	call addl
	push h
	call glin
	call edge
	pop b
	call glin
	call edge
	pop b
	jmp  glin

;	- - -  LIFE in the gray mode - - -



;	ordinary cycle for neighbors of left pixel

olep:	push h
	push h
	dad d
	mov a,m
	adi 011H
	mov m,a
	dcx h
	inr m
	pop h
	dcx h
	inr m
	dad b
	inr m
	inx h
	mov a,m
	adi 011H
	mov m,a
	pop h
	ret

;	ordinary cycle for neighbors of right pixel

orip:	push h
	push h
	dad d
	mov a,m
	adi 011H
	mov m,a
	inx h
	mov a,m
	adi 010H
	mov m,a
	pop h
	inx h
	mov a,m
	adi 010H
	mov m,a
	dad b
	mov a,m
	adi 010H
	mov m,a
	dcx h
	mov a,m
	adi 011H
	mov m,a
	pop h
	ret

;	count neighbors of ordinary cells

onec:	lxi b,rsiz
	lxi d,-rsiz
	lxi h,sorg+rsiz
one1:	mov a,m
	ani 080H
	cnz rnom
	mov a,m
	ani 008H
	cnz lnom
	inx h
	mov a,l
	cpi 0C0H
	jnz one1
	mov a,h
	cpi (sorg+ssiz)/0100H-1
	jnz one1
	ret

;	update to next generation once neighbor count done

next:	lxi d,ssiz
	lxi h,sorg
nex1:	mov a,m
	ora a
	jz nex8
	mov c,a
	ani 077H
	mov b,a
	mov a,c
	ani 088H
	mov c,a
	rlc
	add b
	mov b,a
	push h
	lxi h,nex4
	xthl
	mov a,b
	ani 0F0H
	cpi 020H
	jz nex2
	cpi 030H
	jz nex3
	xra a
	ret
nex2:	mov a,c
	ani 080H
	ret
nex3:	mvi a,080H
	ret
nex4:	push psw
	push h
	lxi h,nex7
	xthl
	mov a,b
	ani 00FH
	cpi 002H
	jz nex5
	cpi 003H
	jz nex6
	xra a
	ret
nex5:	mov a,c
	ani 008H
	ret
nex6:	mvi a,008H
	ret
nex7:	pop b
	ora b
	mov m,a
nex8:	inx h
	dcr e
	jnz nex1
	dcr d
	jnz nex1
	ret

;	cycle for left pixel on left margin

llep:	push h
	push h
	push h
	dad d
	mov a,m
	adi 011H
	mov m,a
	mov a,l
	ori 03FH
	mov l,a
	inr m
	pop h
	mov a,l
	ori 03FH
	mov l,a
	inr m
	dad b
	inr m
	pop h
	dad b
	mov a,m
	adi 011H
	mov m,a
	pop h
	ret

;	cycle for right pixel on right margin

rrip:	push h
	push h
	push h
	dad d
	mov a,m
	adi 011H
	mov m,a
	mov a,l
	ani 0C0H
	mov l,a
	mov a,m
	adi 010H
	mov m,a
	pop h
	mov a,l
	ani 0C0H
	mov l,a
	mov a,m
	adi 010H
	mov m,a
	dad b
	mov a,m
	adi 010H
	mov m,a
	pop h
	dad b
	mov a,m
	adi 011H
	mov m,a
	pop h
	ret

;	left pixel: choose between normal or margin cycle

rnom:	mov a,l
	ani 03FH
	jz  llep
	jmp olep

;	right pixel: chose normal or margin cycle

lnom:	mov a,l
	ani 03FH
	cpi 03FH
	jz  rrip
	jmp orip

;	count neighbors along top margin

ncto:	lxi b,rsiz
	lxi d,ssiz-rsiz
	lxi h,sorg
ncti:	mov a,m
	ani 080H
	cnz rnom
	mov a,m
	ani 008H
	cnz lnom
	inx h
	mov a,l
	ani 03FH
	jnz ncti
	ret

;	count neighbors along bottom margin

ncbo:	lxi b,-ssiz+rsiz
	lxi d,-rsiz
	lxi h,sorg+ssiz-rsiz
	jmp ncti

;	execute one cycle of LIFE

life:	call onec
	call ncto
	call ncbo
	jmp next

;	demonstration for point mode graphics

pdem:	call phom
pden:	call coop
	lxi h,pvec
	call iter
	jmp pden

;	menu for point mode graphics

pvec:	cpi 06EH
	jz  pn
	cpi 073H
	jz  ps
	cpi 065H
	jz  pe
	cpi 077H
	jz  pw
	cpi 'N'
	jz  pno
	cpi 'S'
	jz pso
	cpi 'E'
	jz  pea
	cpi 'W'
	jz  pwe
	cpi 'C'
	jz  blak
	cpi 'R'
	jz  reve
	cpi '.'
	jz prev
	cpi 069H
	jz  pii
	cpi 074H
	jz  tt
	cpi 070H
	jz  pp
	cpi ';'
	jz  0000H
	cpi 'G'
	jz  gdem
	ret

;	demonstration for gray mode graphics

gdem:	call ghom
gden:	call coop
	lxi h,gvec
	call iter
	jmp gden


;	vector for gray mode graphic demonstration

gvec:	cpi 06EH
	jz  gn
	cpi 073H
	jz  gs
	cpi 065H
	jz  ge
	cpi 077H
	jz gw
	cpi 'N'
	jz  gno
	cpi 'S'
	jz  gso
	cpi 'E'
	jz  gea
	cpi 'W'
	jz  gwe
	cpi 'B'
	jz  whit
	cpi 07FH
	jz blak
	cpi 'C'
	jz  blak
	cpi 072H
	jz  grev
	cpi 068H
	jz  gzeh
	cpi 06BH
	jz  gzmi
	cpi 06CH
	jz  gzpl
	cpi 'R'
	jz reve
	cpi 'H'
	jz  gzeeh
	cpi 'K'
	jz  gzeemi
	cpi 'L'
	jz  gzeepl
	cpi 069H
	jz gii
	cpi 067H
	jz  life
	cpi '.'
	jz  gzeh
	cpi ';'
	jz  0000H
	cpi 'P'
	jz  pdem
	ret

;	i (= line) in gray mode

gii:	call coor
	jmp  glin

;	- - - read routine - - -

read:	in  0EDH
	ani 040H
	jz  read
	in  0EFH
	ani 07FH
	ret
	end
