home *** CD-ROM | disk | FTP | other *** search
/ CP/M / CPM_CDROM.iso / mbug / mbug097.arc / CON512T.MAC < prev    next >
Text File  |  1979-12-31  |  16KB  |  873 lines

  1. ; *************************************************************
  2. ;    Console (and other) I/O drivers for 512k BIOS
  3. ; *************************************************************
  4.  
  5. ; location of keyboard driver program in system page
  6. keyboard_driver    equ    bios_sys_start
  7.  
  8. ; Function keys:
  9.  
  10. fn_key_1    equ    81h    ; value returned by scn_in
  11.  
  12. fn_str_end    equ    0FFh    ; end function char
  13. fn_str_pause    equ    0FEh    ; pause char
  14. fn_str_wait    equ    0FDh    ; wait for fkey char
  15.  
  16. window_char    equ    0A0h    ; value returned by scn_in to get window
  17.  
  18. user_char    equ    0A1h    ; value returned by scn_in to get user program
  19.  
  20. ;
  21. ; language options ..
  22. ENGLISH    equ    1        ;=1 if english version
  23. DANISH    equ    0        ;=1 if danish version
  24. SWEDISH    equ    0        ;=1 if swedish version
  25. ;
  26. VDUH    equ    24
  27. VDUW    equ    80
  28. ;
  29. ; PIO B bits of interest
  30. BEEP_BIT    equ    6
  31. SER_OUT        equ    5    ;serial comm. lines
  32. SER_IN        equ    4
  33. SER_CTS        equ    3    ;printer busy line= clear to send
  34. SER_DTR        equ    2    ;DTR output
  35. CASS_OUT    equ    1
  36. CASS_IN        equ    0    ;cassette bits
  37. ;
  38. ; SEE ALSO RS232 routines for other timing changes
  39. ;
  40. ; software dependent timing for 3.375 Mhz
  41. ; dump values calculated for "cycle" loop
  42. ; formula reqd. is #T states for cycle = 26n + 97
  43. ; with video waiting OFF
  44. LONG    equ    104        ;1200 Hz
  45. SHORT    equ    50        ;2400 Hz
  46. ; load value taken for freq. of (1200+2400)/2
  47. ; n = ( f/3400 - 141 ) / 36   for GETBIT II
  48. CUTOFF    equ    28        ;receive half-way point (redundancy)
  49. ;BELL_T    equ    164        ;G two above mid C (784hz)
  50. bell_t    equ    165
  51. MILLISEC    equ    122        ;disk timing parameter (vwait ON)
  52. ;
  53. BELL_Z    equ    100        ;fairly short (number of cycles)
  54. ; the following two are 100Hz multiples (CPU speed independent)
  55. REPT_START    equ    100        ;gives 1 second repeat delay
  56. RP_SPEED    equ    10        ;gives 10 Hz repeat rate
  57. ;
  58. ; 6545 register definitions
  59. H_LPEN    equ    16
  60. L_LPEN    equ    17
  61. H_UPDATE    equ    18
  62. L_UPDATE    equ    19
  63. DUMMY    equ    31
  64. ; status bit definitions
  65. RETRACE    equ    5
  66. LPEN_FULL    equ    6
  67. UPDATE_RDY    equ    7
  68.  
  69.  
  70. ; initialize 6545 crt controller - no int disabling
  71. ; but wait for 50 ms to allow font selection to take place
  72. crtc_fill:    
  73.     push    bc
  74.     push    hl
  75. ;
  76.     ld    b,16
  77. cz_a    defl    $
  78.     ld    a,b
  79.     dec    a
  80.     out    (crtc),a
  81.     ld    a,(hl)
  82.     out    (crtc+1),a
  83.     dec    hl
  84.     djnz    cz_a
  85. cz_aabc:
  86.     ld    b,75        ;also works at 3.375 Mhz
  87.     call    dely1
  88.     pop    hl
  89.     pop    bc
  90.     ret
  91. ;
  92. ; Console status. This routine actually gets a key from the keyboard if no key
  93. ; is already pending.
  94. ;
  95. ; return a=FF and nz if there would be a key to get,
  96. ;        a=0  and z if nothing there
  97. const:    
  98. ; Must call status update as mchinw sits in a loop calling const
  99.     call    display_time
  100.     xor    a
  101. disable_kbd:
  102.     ret
  103. ;    ld    a,(fn_active)    ; Disables keyboard also (for testing)
  104. ;    or    a
  105. ;    ret    z
  106.     map    sys_vdr
  107.     push    hl
  108.     ld    hl,save_key
  109.     ld    a,(hl)
  110.     inc    a
  111.     jr    nz,still_got
  112.     jr    try
  113. got_key:
  114.     pop    bc
  115.     pop    hl
  116.     ld    (hl),a
  117. still_got:
  118.     or    0FFh
  119. common_ret:
  120.     ld    h,a
  121.     map    bios_map
  122.     ld    a,h
  123.     pop    hl
  124.     ret
  125. not_got_key:
  126.     pop    bc
  127.     pop    hl
  128.     ld    a,0FFh
  129.     ld    (hl),a
  130.     xor    a
  131.     jr    common_ret
  132.  
  133. ; Try to get key from keyboard or from function string.
  134. ; It is here that the function keys and code conversions are handled.
  135. try:
  136.     push    hl
  137.     push    bc
  138.     ld    a,(in_fnstr)
  139.     or    a
  140.     jr    z,not_fn
  141.     ld    hl,pause_count
  142.     ld    a,(hl)
  143.     dec    a
  144.     jp    m,not_pse
  145.     ld    (hl),a        ; if in pause then decr count and no key
  146.     jr    not_got_key
  147. not_pse:
  148.     ld    hl,(fn_ptr)
  149. start_fn:
  150. ; if <ESC> is pressed then stop reading function string
  151.     call    scn_in
  152. ;    jr    nz,esc_not_pr
  153.     cp    '['-40h
  154.     jr    nz,esc_not_pr
  155. end_fn:
  156.     xor    a        ; and quit function string
  157.     ld    (in_fnstr),a
  158.     jr    not_got_key
  159. esc_not_pr:
  160.     ld    a,(hl)        ; get next 'key'
  161.     inc    hl
  162.     ld    (fn_ptr),hl
  163.     cp    fn_str_end    ; quit
  164.     jr    z,end_fn
  165.     ld    b,a
  166.     ld    a,l        ; quit next time if reached end
  167.     and    7Fh
  168.     ld    a,b
  169.     jr    nz,not_end_fn
  170.     ld    hl,in_fnstr
  171.     ld    (hl),false
  172. not_end_fn:
  173.     cp    fn_str_pause
  174.     jr    nz,not_pse1
  175.     ld    hl,pause_count    ; if pause then wait 20 calls (or 50)
  176.     ld    (hl),30        ; or 30? Pick a number, any number.
  177.     jr    z,not_got_key
  178. not_pse1:
  179.     cp    fn_str_wait
  180.     jr    nz,not_wait
  181.     ld    hl,in_fnstr
  182.     ld    a,(hl)        ; Wait until this function key is pressed again
  183.     ld    (fn_waiting),a
  184.     ld    (hl),0
  185.     jr    not_got_key
  186. not_wait:
  187.     cp    fn_key_1    ; if function number then chain to new fn key
  188.     jr    c,got_key
  189.     cp    fn_key_1+num_fn_keys
  190.     jr    nc,got_key
  191.     jr    chain_fk
  192.  
  193. ; Get key from keyboard, if function key pressed and fn keys enabled
  194. ; then start reading from function string.
  195. not_fn:
  196. ;    ld    a,(fn_active)    ;%%%%%
  197. ;    or    a
  198. ;    jr    z,not_got_key
  199.     call    scn_in
  200.     jr    nz,not_got_key
  201.     cp    fn_key_1
  202.     jp    c,got_key
  203.     cp    fn_key_1+num_fn_keys
  204.     jr    c,chain_fk
  205.     cp    window_char
  206.     jr    z,control_window
  207.     cp    user_char
  208.     jr    z,link_user_kbd
  209. ; now must convert cursor keys (90h..9Fh) to correct value
  210.     cp    90h
  211.     jp    c,got_key
  212.     cp    0A0h
  213.     jp    nc,got_key
  214.     ld    hl,curs_key_tab-90h
  215.     ld    c,a
  216.     ld    b,0
  217.     add    hl,bc
  218.     ld    a,(hl)
  219.     or    a        ; if 0 then no char for this key
  220.     jp    z,not_got_key
  221.     jp    got_key
  222.     
  223.  
  224. chain_fk:
  225.     ld    h,a
  226.     ld    a,(fn_active)
  227.     or    a
  228.     jp    z,not_got_key
  229.     ld    a,h
  230.     ld    (in_fnstr),a
  231.     ld    hl,fn_waiting
  232.     cp    (hl)
  233.     ld    (hl),0
  234.     jp    z,not_pse
  235.     sub    fn_key_1    ; convert to 0..11
  236.     ld    hl,fn_store    ; start of stored strings
  237.     rr    a
  238.     rr    l        ; 128 bytes each, -> LS bit to L
  239.     add    a,h        ; MS bits to H
  240.     ld    h,a
  241.     ld    a,(hl)
  242.     cp    fn_str_end
  243.     jp    z,not_got_key
  244.     jp    start_fn
  245.  
  246. control_window:
  247.     xor    a
  248.     ld    (fn_waiting),a
  249.     ld    a,(window_loaded)
  250.     or    a
  251.     jr    z,no_w
  252.     ld    hl,not_got_key    ; return from subr to not_got_key routine
  253.     push    hl
  254.     ld    hl,(window_addr)
  255.     jp    (hl)
  256.  
  257. ; WINDOW.SYS not loaded so toggle fn keys on/off
  258. no_w:
  259.     ld    hl,fn_active
  260.     ld    a,(hl)
  261.     cpl
  262.     ld    (hl),a
  263.     jp    not_got_key
  264.  
  265. ; link to user program
  266. link_user_kbd:
  267.     ld    a,(user_page)
  268.     or    a
  269.     jp    z,not_got_key
  270.     ld    hl,not_got_key    ; return to this address
  271.     push    hl
  272.     call    mem_page    ; Enable user's page (+ screen at 8000h ??)
  273.     ld    hl,(user_addr)    ; 'Call' program at offset of 0
  274.     jp    (hl)
  275.  
  276. mchinw:    
  277.     call    mchinl
  278.     jr    z,mchinw
  279.     ret
  280.  
  281. ; DGOS type (and CP/M CONIN) keyboard routines
  282. ; return Z if no key available (and a=0)
  283. ;       NZ and a=char if there is one there
  284. mchinl:
  285.     call    const
  286.     ret    z        ;no new key available
  287. ; CONST returned nz, so there must be a key at (save_key) ..
  288.     push    hl
  289.     ld    hl,save_key
  290.     ld    a,(hl)
  291.     ld    (hl),-1        ;reset save_key
  292.     pop    hl
  293.     ret            ;(status is nz)
  294.  
  295.  
  296. ;
  297. ; calls to keyboard driver program in system page
  298. ;
  299. scn_in:
  300.     map    sys_vdr
  301.     jp    keyboard_driver
  302.  
  303. ; XBIOS call 15
  304. key_pressed:
  305.     ld    a,c
  306. is_closed:
  307.     push    af
  308.     map    sys_vdr
  309.     pop    af
  310.     call    keyboard_driver+3
  311.     jp    recover_bmap
  312.  
  313. ; call scn_in and return with other page (in A) enabled ( for FLASH routine )
  314. scn_in_m:
  315.     ld    (temp_2),a
  316.     map    sys_vdr
  317.     call    keyboard_driver
  318.     push    af
  319.     ld    a,(temp_2)
  320.     out    (map_port),a
  321.     pop    af
  322.     ret
  323.  
  324.  
  325.  
  326. ; Character to be output is in C
  327. ; (conout)
  328. ; ADM-3A emulator plus some functions from the TVI-912C terminal
  329. ; i.e. line insert, delete, clear to eol and eop
  330. ; ### put in char insert and delete from BETI
  331. INV_SET:    
  332.     rrca                ;get bit 7=1 if char was ')' = 029H
  333.     and    080H
  334.     ld    (inv_byte),a
  335.     jp    kilseq
  336. ;
  337. LINE_INS:    
  338.     call    do_cret
  339.     push    hl            ;save posn. at start of curr. line
  340.     ex    de,hl            ;de=start of line
  341.     ld    hl,vdu+vduw*vduh-1    ;end of last line
  342.     push    hl
  343.     and    a
  344.     sbc    hl,de
  345.     ld    b,h            ;enough bytes?
  346.     ld    c,l
  347.     pop    de
  348.     ld    hl,vdu+vduw*(vduh-1)-1
  349.     lddr
  350. ;
  351. ; due to lddr
  352.     pop    hl            ;get start of curr. line
  353. EOL_CLR:    
  354.     call    bclr_tel        ;clear line at (hl) for vduw-b
  355.     jp    kilseq
  356. ;
  357. ; delete the line underneath the cursor
  358. LINE_DEL:    
  359.     call    do_cret
  360.     push    hl
  361.     push    hl            ;initial dst is start of curr line
  362.     ld    bc,vduw
  363.     add    hl,bc
  364.     push    hl            ;save start of line under curr line
  365.     ex    de,hl            ;de=start of line under curr. line
  366.     ld    hl,vdu+vduh*vduw+1
  367.     and    a
  368.     sbc    hl,de
  369.     ld    b,h            ;enough bytes to move and >0
  370.     ld    c,l
  371.     pop    hl            ;initial src = line under curr. line
  372.     pop    de            ;initial dst = curr line
  373.     ldir
  374. ; also b=0 (column position)
  375.     call    bclr_bot        ;clear bottom line (if b=0)
  376.     pop    hl
  377.     jr    kilseq
  378.  
  379. CURS_SET:    
  380.     sub    '{'            ;'{' turns cursor off -> a=0
  381.     ld    (curs_flag),a
  382.     jr    kilseq
  383.  
  384. ESCSEQ:    
  385.     dec    a
  386.     jr    z,final
  387.     dec    a
  388.     ld    a,c
  389.     jr    z,second
  390. FIRST:    
  391.     cp    '}'
  392.     jr    z,curs_set
  393.     cp    '{'
  394.     jr    z,curs_set
  395.     cp    ')'        ;half intensity for 912C
  396.     jr    z,inv_set
  397.     cp    '('        ;hi off for 912C
  398.     jr    z,inv_set
  399.     cp    '='
  400.     jr    z,cur_pos    ;cursor positioning
  401.     res    5,a        ;lower case -> upper case
  402.     cp    'E'        ;line insert
  403.     jr    z,line_ins
  404.     cp    'R'
  405.     jr    z,line_del    ;line delete
  406.     cp    'T'
  407.     jr    z,eol_clr    ;clear to end of line
  408.     cp    'Y'        ;page erase
  409.     jr    z,cls_entry
  410.     xor    a
  411.     ld    (esctrp),a    ; kill ESC sequence anyway
  412.     ld    a,c
  413.     cp    'Z'        ; if >= Z then attribute, so do space instead
  414.     jr    c,kilseq
  415.     ld    c,' '
  416.     jr    put_c
  417. CLS_ENTRY:    
  418.     call    z,clr_tep
  419.     jr    kilseq    ; kill sequence
  420. ;
  421. CUR_POS:    
  422.     ld    a,2
  423.     jr    rst_esc        ; was esc =
  424. ;
  425. FINAL:    
  426.     ld    a,c
  427.     sub    020H
  428.     ld    b,a            ;column position
  429.     ld    hl,(linpos)        ;really ld l,(linpos)
  430.     ld    h,0
  431.     ld    d,h
  432.     ld    e,l
  433.     add    hl,hl
  434.     add    hl,hl
  435.     add    hl,de
  436.     add    hl,hl
  437.     add    hl,hl
  438.     add    hl,hl
  439.     add    hl,hl        ; mult by 80 decimal
  440.     ld    e,a
  441.     add    hl,de        ; add col pos
  442. ; keep it within bounds of 2048 (columns get confused anyway)
  443.     ld    a,h
  444.     and    07H
  445.     ld    h,a
  446.     ld    de,vdu
  447.     add    hl,de        ; add base
  448. KILSEQ:    
  449.     xor    a
  450.     jr    rst_esc
  451. ;
  452. SECOND:    
  453.     sub    020H
  454.     ld    (linpos),a
  455.     ld    a,1
  456.     jr    rst_esc
  457. ;
  458. SETESC:    
  459.     ld    a,3
  460. RST_ESC:    
  461.     ld    (esctrp),a
  462.     jr    vrecovr
  463. ;
  464. ; home and clear screen, entered with Z flag set
  465. CLRVDU:    
  466.     ld    hl,vdu
  467.     ld    b,0        ;first column
  468.     jr    cls_entry
  469. ;
  470. VDUOUT:    
  471.     push    af
  472.     push    bc
  473.     push    de
  474.     push    hl
  475. ;
  476.     ld    hl,(cursor)
  477.     call    csr_flip    ; invert (hl)
  478.     ld    a,(colpos)    ; get column position in b ..
  479.     ld    b,a
  480.     ld    a,(esctrp)    ; is esc sequence in progress?
  481.     or    a
  482.     jp    nz,escseq
  483. PUT_C:    
  484.     ld    a,c
  485.     cp    020H
  486.     jr    c,try_ctrl    ;ctrl char ?
  487.     ld    a,(inv_byte)
  488.     or    c
  489.     ld    (hl),a
  490. CSRIGHT:    
  491.     inc    hl
  492.     inc    b
  493. EOL_CHECK:    
  494.     ld    a,b
  495.     sub    vduw
  496.     jr    nz,chkscr
  497.     ld    b,a
  498. CHKSCR:    
  499.     ex    de,hl
  500.     ld    hl,vdu+vduw*vduh-1
  501.     or    a
  502.     sbc    hl,de
  503.     ex    de,hl
  504.     jr    nc,vrecovr
  505. ; scroll the screen ...
  506.     push    bc        ; save old column posn.
  507.     push    hl
  508.     ld    bc,vduw*vduh-vduw
  509.     ld    hl,vdu+vduw
  510.     ld    de,vdu
  511.     ldir
  512. ; .. b=0 from ldir
  513.     call    bclr_bot    ; clear bottom line (if b=0)
  514.     pop    hl
  515.     pop    bc        ; get old column posn.
  516.     ld    de,-vduw
  517.     add    hl,de
  518.     jr    vrecovr
  519. ;
  520. TRY_CTRL:    
  521.     cp    01EH
  522.     jr    z,vhome
  523.     cp    01BH        ; escape
  524.     jr    z,setesc
  525.     cp    01AH
  526.     jr    z,clrvdu
  527.     cp    09H        ; tab function to '8' boundaries only
  528.     jr    z,tab
  529.     cp    08H        ; backspace
  530.     jr    z,bspc
  531.     cp    0AH
  532.     jr    z,lfeed
  533.     cp    0BH        ; cursor up a line
  534.     jr    z,csup
  535.     cp    0CH        ; cursor to right (not CLS)
  536.     jr    z,csright
  537.     cp    07H        ; bell code
  538.     jr    z,beep
  539.     cp    0DH        ; carriage return
  540.     call    z,do_cret
  541. VRECOVR:    
  542.     ld    a,b
  543. RECOV1:    
  544.     ld    (colpos),a
  545. RECOV2:    
  546.     ld    (cursor),hl
  547.     call    csr_flip
  548.     pop    hl
  549.     pop    de
  550.     pop    bc
  551.     pop    af
  552.     jp    retvdu        ; switch VDU to F000, return
  553. ;
  554. CSUP:    
  555.     ld    de,-vduw
  556.     add    hl,de
  557.     ld    a,h
  558.     cp    +(vdu shr 8)
  559.     jr    nc,recov2
  560. LFEED:    
  561.     ld    de,vduw
  562.     add    hl,de
  563.     jr    chkscr
  564. ;
  565. VHOME:    
  566.     ld    hl,vdu
  567.     xor    a
  568.     jr    recov1
  569. ;
  570. BSPC:    
  571.     dec    hl
  572.     dec    b
  573.     ld    a,h
  574.     cp    +(vdu shr 8)-1
  575.     jr    z,vhome
  576.     bit    7,b
  577.     jr    z,vrecovr
  578.     ld    b,vduw-1
  579.     jr    vrecovr
  580. ;
  581. TAB:    
  582.     ld    a,(inv_byte)
  583.     or    ' '
  584.     ld    (hl),a
  585.     inc    hl
  586.     inc    b
  587.     ld    a,b
  588.     and    07H            ; are we at tab stop yet ?
  589.     jr    nz,tab
  590.     jp    eol_check
  591. ;
  592. BEEP:    
  593.     push    de
  594.     ld    a,(fast_cpu)
  595.     or    a
  596.     ld    d,bell_t        ; 6.75 MHz
  597.     jr    nz,b_1
  598.     ld    d,+(bell_t shr 1)    ; 3.375 MHz
  599. b_1:
  600.     out    (vwait_off),a
  601.     ld    c,2*bell_z        ; 100 cycles of tone
  602.     in    a,(beep_port)
  603. B_LOOP:    
  604.     xor    40h
  605.     out    (beep_port),a
  606.     ld    b,d
  607. DJ1:
  608.     ld    a,a
  609.     ld    a,a
  610.     ld    a,a
  611.     djnz    dj1
  612.     dec    c
  613.     jr    nz,b_loop
  614.     pop    de
  615.     jr    recov2
  616. ;
  617. ; subroutine to do "carriage return"
  618. ; (also used by delete line, insert line)
  619. DO_CRET:    
  620.     ld    a,b
  621.     or    a
  622.     ret    z
  623. CRLOOP:    
  624.     dec    hl
  625.     djnz    crloop
  626.     ret
  627. ;
  628. ; clear bottom line, assuming b=0 ..
  629. BCLR_BOT:    
  630.     ld    hl,vdu+(vduh-1)*vduw    ;start of last line
  631. ; clear to end of line at (hl) for vduw-b bytes
  632. BCLR_TEL:    
  633.     ld    a,vduw
  634.     sub    b
  635.     push    hl
  636. CLRT_1:    
  637.     ld    (hl),' '
  638.     inc    hl
  639.     dec    a
  640.     jr    nz,clrt_1
  641.     pop    hl
  642.     ret
  643. ;
  644. ; clear to end of page from (hl)
  645. CLR_TEP:    
  646.     push    hl
  647.     ex    de,hl
  648.     ld    a,' '
  649. CLRTP:    
  650.     ld    (de),a
  651.     inc    de
  652.     ld    hl,-(vdu+vduh*vduw+1)    ;clear one past end of vdu
  653.     add    hl,de
  654.     jr    nc,clrtp
  655.     pop    hl
  656.     ret
  657. ;
  658. CSR_FLIP:    
  659.     ld    a,(curs_flag)
  660.     or    a
  661.     ret    z
  662.     ld    a,(hl)
  663.     xor    80h
  664.     ld    (hl),a
  665.     ret
  666.  
  667.  
  668.  
  669. ; Software UART routines which do not need to live below
  670. ; 0F000H ..
  671.  
  672. SET_BAUD:    
  673. ; look up delay routine in table and place in simult
  674.     push    hl
  675.     push    de
  676.     ld    l,a
  677.     ld    h,0
  678.     add    hl,hl        ;*2
  679.     ld    de,baud_tab
  680.     add    hl,de
  681.     ld    e,(hl)
  682.     inc    hl
  683.     ld    d,(hl)
  684.     ld    (simult),de
  685.     pop    de
  686.     pop    hl
  687.     ret
  688.  
  689. BAUD_TAB:    
  690.     defw    l300
  691.     defw    l600
  692.     defw    l1200
  693.     defw    l2400
  694.     defw    l4800
  695.     defw    l1200        ;provision for 110 baud
  696.  
  697.  
  698. RS_OUT:    
  699.     push    af
  700.     push    bc
  701.     push    de
  702.     push    hl
  703.     push    ix
  704.     ld    ix,num_data    ;start of RS scratchpads
  705.     ld    l,0        ;start bit
  706.     ld    b,(ix+num_data-num_data)
  707.     bit    3,b
  708.     jr    z,eight        ;if eight data bits
  709.     res    7,a
  710. EIGHT:    
  711.     rrca            ;rotating does not affect parity
  712.     adc    hl,hl
  713.     djnz    eight
  714. ; now calculate parity if reqd. to do so
  715.     ld    b,(ix+parity-num_data)
  716.     dec    b
  717.     jr    z,no_par    ;no parity at all
  718.     dec    b
  719.     jr    z,odd_par    ;odd parity is set
  720. ; even parity is selected ..
  721.     or    a        ;set P flag
  722.     jp    pe,send_par    ;parity is already even
  723. ; parity of data is odd, so add a bit to make it even
  724. W_PAR:    
  725.     scf            ;turn on extra parity bit
  726.     jr    send_par
  727. ODD_PAR:    
  728.     or    a
  729.     jp    pe,w_par    ;turn on P bit to make it odd
  730. SEND_PAR:    
  731.     adc    hl,hl
  732. NO_PAR:    
  733.     ld    b,(ix+adj_fact-num_data) ;must rotate hl to starting posn.
  734. ALIGN:    
  735.     scf
  736.     adc    hl,hl
  737.     djnz    align
  738.     ld    d,(ix+totalq-num_data)    ;tx control
  739.     ld    e,0
  740. ;
  741. ; now wait for modem ready i.e. CTS to go high
  742. W_CTS:    
  743.     in    a,(piob_data)
  744.     bit    ser_cts,a
  745.     jr    z,w_cts
  746. ;
  747.     di            ;stop int_rtn during this
  748.     call    jp_simul
  749.     ld    a,(flag)    ;z -> we  got a char in
  750.     or    a
  751.     call    z,chk_break    ;store character, wait for mark
  752. ;
  753.     ei
  754.     pop    ix
  755.     pop    hl
  756.     pop    de
  757.     pop    bc
  758.     pop    af
  759.     ret
  760.  
  761.  
  762. ; return char in A and Z, or NZ if no char available from q
  763. RS_IN:    
  764.     push    de
  765.     push    hl
  766.     push    ix
  767.     ld    hl,(w_ptr)
  768.     ld    de,(r_ptr)
  769.     or    a
  770.     sbc    hl,de
  771.     jr    nz,got_RS
  772. ; buffer empty, so allow it to be refilled
  773.     in    a,(piob_data)
  774.     set    ser_dtr,a
  775.     out    (piob_data),a
  776.     or    -1        ;nz => got nothing
  777. RS_EX:    
  778.     pop    ix
  779.     pop    hl
  780.     pop    de
  781.     ret
  782. GOT_RS:    
  783.     call    next_RS
  784. ; update count of "safe" space remaining in buffer
  785.     di
  786.     ld    hl,(dtr_limit)
  787.     inc    hl
  788.     ld    (dtr_limit),hl
  789.     ei
  790.     ld    a,(ix+0)    ;get data first
  791.     ld    (r_ptr),de    ;and acknowledge
  792.     cp    a
  793.     jr    RS_ex
  794.  
  795.  
  796.  
  797.  
  798. ; return 0 if busy, FF if ready for serial printer
  799. ; used by DESPOOL (can also be used by WordStar)
  800. S_LISTST:    
  801.     in    a,(piob_data)
  802.     bit    ser_cts,a
  803.     jr    nz,prnt_ready
  804.     xor    a
  805.     ret
  806. PRNT_READY:    
  807.     ld    a,0FFH
  808.     ret
  809.  
  810.  
  811.  
  812. flash_max    equ    60    ;number of bytes to flash
  813.  
  814. ; flash inverse message to top of screen
  815. flash:
  816.     map    vdr_map
  817.     push    hl        ;save message location
  818.     ld    hl,vdu
  819.     ld    de,save_p
  820.     ld    bc,flash_max
  821.     ldir
  822.     pop    hl
  823. ;
  824.     ld    de,vdu
  825. fl_loop:    
  826.     ld    a,(hl)
  827.     xor    080H
  828.     jr    z,fl_wait
  829.     ld    (de),a
  830.     inc    de
  831.     inc    hl
  832.     jr    fl_loop
  833. fl_wait:
  834.     call    scn_in
  835.     cp    cr
  836.     jr    nz,fl_wait
  837.     ld    hl,save_p
  838.     ld    de,vdu
  839.     ld    bc,flash_max
  840.     ldir
  841.     map    bios_map
  842.     ret
  843.  
  844.  
  845. BPAR_OUT:    
  846.     push    hl
  847.     ld    hl,par_flag
  848. PAR_O1:    
  849.     bit    0,(hl)
  850.     jr    nz,par_o1
  851.     ld    (hl),-1
  852.     out    (pioa_data),a    ;send byte to printer
  853.     pop    hl
  854.     ret
  855. ;
  856. P_LISTST:    
  857.     ld    a,(par_flag)
  858.     cpl
  859.     ret
  860.  
  861.  
  862. INV_BYTE:    defb    0    ;=080H if CONOUT in "INVERSE" mode
  863. ESCTRP:    defb    0        ;indicates esc sequence
  864. CURS_FLAG:    defb    -1    ;non-zero if cursor is ON
  865.  
  866. SAVE_KEY:    defb    -1    ;=-1 if no keys saved, else=ascii code
  867.  
  868. pause_count:    db    0    ;count of number of con status calls to ignore
  869.  
  870. ;disable_kbd:    db    true    ; initially disabled
  871.  
  872. fn_waiting:    db    0    ; Function key currently waiting for repress
  873.