home *** CD-ROM | disk | FTP | other *** search
/ ftp.barnyard.co.uk / 2015.02.ftp.barnyard.co.uk.tar / ftp.barnyard.co.uk / cpm / walnut-creek-CDROM / CPM / MODEMS / ZMODEM / ZMO-H89.ZZ0 / ZMO-H89.Z80
Text File  |  2000-06-30  |  13KB  |  632 lines

  1. ;-----------------------------------------------------------------------------
  2. ;
  3. ;    Heath-89 Overlay for ZMP (Z-Modem Program)
  4. ;       modifications by Howard Dutton
  5. ;
  6. ;    Name    ZMO-H89.Z80 
  7. ;
  8. ;    Dated Sep 14, 1988
  9. ;
  10. ;    Written by -
  11. ;      Ron Murray, c/o Z-Node 62, 061-9-450-0200, Perth, Western Australia.
  12. ;
  13. ;    Modified to ZMP v1.2 standard rjm 15/9/88
  14. ;    Modified to ZMP v1.3 standard rjm 11/10/88
  15. ;    Modified to ZMP v1.4 standard rjm 20/11/88
  16. ;
  17. ;
  18. ;-----------------------------------------------------------------------------
  19. ;
  20. ;
  21. ;    System-dependent code overlay for ZMODEM
  22. ;
  23. ;
  24. ;
  25. ;    Insert your own code as necessary in this file. Code contained herein
  26. ; has been written in Z80 code for use with M80 or SLR. Assemble as follows:
  27. ;
  28. ;    SLR ZMO-xx01/h
  29. ;    MLOAD ZMP.COM=ZMODEM.COM,ZMO-xx01.HEX
  30. ; or
  31. ;    M80 =ZMO-xx01.Z80
  32. ;    RELHEX ZMO-xx01
  33. ;    MLOAD ZMP.COM=ZMODEM.COM,ZMO-xx01.HEX
  34. ;
  35. ;
  36. ;       (Don't use L80 without changing the source for assembly as a
  37. ;         cseg file.)
  38. ;
  39. ;-----------------------------------------------------------------------------
  40. ;
  41. ;
  42. ;    Don't forget to set your clock speed at the clkspd variable.
  43. ;
  44. ;
  45. ;    If you find your overlay exceeds the maximum size (currently 0400h),
  46. ; you will have to contact me for another version. If too many people need 
  47. ; to do it, we haven't allowed enough room.
  48. ;
  49. ; Ron Murray 15/8/88
  50. ;
  51. ;
  52. ;
  53. ;---------------------------------------------------------------------------
  54.  
  55. false    equ    0
  56. true    equ    not false
  57.  
  58. ;------------------------------------------------------------------------------
  59.  
  60. ; User-set variables: 
  61.  
  62. clkspd    equ    6        ; Processor clock speed in MHz
  63. debug    equ    false        ; to allow debugging of overlay with Z8E etc.
  64.  
  65. ;Set the following two equates to the drive and user area which will contain
  66. ;   ZMP's .OVR files, .CFG file, .FON file and .HLP file. Set both to zero
  67. ;   (null) to locate them on the drive from which ZMP was invoked.
  68.  
  69. overdrive    equ    'A'    ; Drive to find overlay files on ('A'-'P')
  70. overuser    equ    0    ; User area to find files
  71.  
  72. ;------------------------------------------------------------------------------
  73.  
  74.  
  75. ; NOT user-set variables
  76.  
  77. userdef    equ    0145h        ; origin of this overlay
  78.                 ; This address should not change with
  79.                 ; subsequent revisions.
  80. mspeed    equ    03ch        ; location of current baud rate. 
  81. ovsize    equ    0400h        ; max size of this overlay
  82.  
  83.     .z80            ; use z80 code
  84.     aseg            ; absolute
  85.  
  86.      if    debug
  87.     org    100h        ; so you can debug it with cebug, zsid, etc
  88.      else
  89.     org    userdef
  90.      endif
  91.  
  92.  
  93. mport    equ    0d8h        ; the modem port on a h88-3 serial card
  94. conport    equ    0e0h        ; the console serial port on a H89
  95.  
  96. esc    equ    1bh
  97. ctrlq    equ    11h
  98. cr    equ    0dh
  99. lf    equ    0ah
  100. bdos    equ    5
  101.  
  102.  
  103. codebgn    equ    $
  104.  
  105. ;Jump table for the overlay: do NOT change this
  106. jump_tab:
  107.     jp    scrnpr        ; screen print
  108.     jp    mrd        ; modem read with timeout
  109.     jp    mchin        ; get a character from modem
  110.     jp    mchout        ; send a character to the modem
  111.     jp    mordy        ; test for tx buffer empty
  112.     jp    mirdy        ; test for character received
  113.     jp    sndbrk        ; send break
  114.     jp    cursadd        ; cursor addressing
  115.     jp    cls        ; clear screen
  116.     jp    invon        ; inverse video on
  117.     jp    invoff        ; inverse video off
  118.     jp    hide        ; hide cursor
  119.     jp    show        ; show cursor
  120.     jp    savecu        ; save cursor position
  121.     jp    rescu        ; restore cursor position
  122.     jp    mint        ; service modem interrupt
  123.     jp    invec        ; initialise interrupt vectors
  124.     jp    dinvec        ; de-initialise interrupt vectors
  125.     jp    mdmerr        ; test uart flags for error
  126.     jp    dtron        ; turn DTR on
  127.     jp    dtroff        ; turn DTR OFF
  128.     jp    init        ; initialise uart
  129.     jp    wait        ; wait seconds
  130.     jp    mswait        ; wait milliseconds
  131.     jp    userin        ; user-defined entry routine
  132.     jp    userout        ; user-defined exit routine
  133.     jp    getvars        ; get system variables
  134.  
  135. ; Spare jumps for compatibility with future versions
  136.     jp    spare        ; spare for later use
  137.     jp    spare        ; spare for later use
  138.     jp    spare        ; spare for later use
  139.     jp    spare        ; spare for later use
  140.     jp    spare        ; spare for later use
  141.     jp    spare        ; spare for later use
  142.  
  143. ;
  144. ; Main code starts here
  145. ;
  146. ;Screen print function
  147. scrnpr:
  148.                 ; <== Insert your own code here
  149.     call    print
  150.     db    'This function not supported.',cr,lf,0
  151.                 ; <== End of your own code
  152. spare:
  153.     ret
  154.  
  155. ; User-defined entry routine: leave empty if not needed
  156. userin:
  157.     ret
  158.  
  159. ; User-defined exit routine: leave empty if not needed
  160. userout:
  161.     ret
  162.  
  163.  
  164. ;Get a character from the modem: return in HL
  165. mchin:
  166.     push    bc
  167.     in    a,(mport)
  168.     ld    l,a        ; put in HL
  169.     ld    h,0
  170.     or    a        ; set/clear Z
  171.     pop    bc
  172.     ret
  173.  
  174. ;Send a character to the modem
  175. mchout:
  176.     ld    hl,2        ; get the character
  177.     add    hl,sp
  178.     ld    a,(hl)
  179.     out    (mport),a
  180.     ret            ; done
  181.  
  182. ;Test for output ready: return TRUE (1) in HL if ok
  183. mordy:
  184.     ld    hl,0        ;
  185.     in    a,(mport+5)    ;
  186.     bit    5,a        ; bit 5 is set if uart is ready for a char
  187.     jp    z,mordy1    ;
  188.     ld    hl,1
  189.  
  190. mordy1:    ld    a,l        ; set/clear Z
  191.     or    a
  192.     ret
  193.  
  194. ;Test for character at modem: return TRUE (1) in HL if so
  195. mirdy:
  196.     ld    hl,0        ;
  197.     in    a,(mport+5)    ;
  198.     bit    0,a        ; bit 0 is set if data is ready
  199.     jp    z,mirdy1    ;
  200.     ld    hl,1
  201.  
  202. mirdy1:    ld    a,l        ; set/clear Z
  203.     or    a
  204.     ret
  205.  
  206. ;Send a break to the modem: leave empty if your system can't do it
  207. sndbrk:
  208.  
  209.     in    a,(mport+3)    ;
  210.     set    6,a        ; set break bit
  211.     out    (mport+3),a    ;
  212.  
  213.     push    af
  214.     ld    hl,300        ; wait 300 mS
  215.     call    waithlms
  216.     pop    af
  217.  
  218.     res    6,a        ; reset break bit
  219.     out    (mport+3),a    ;
  220.  
  221.     ret
  222. ;
  223. ;Test UART flags for error: return TRUE (1) in HL if error.
  224. mdmerr:
  225.     ld    hl,0
  226.     in    a,(mport+5)    ; get line status
  227.     and    00001110B    ; mask
  228.     jp    z,mdmer1    ; a should = 0 if everything is ok
  229.     ld    hl,1        ;
  230.  
  231. mdmer1:    ld    a,l        ; set/clear Z
  232.     or    a
  233.     ret
  234.  
  235.  
  236. ;Turn DTR ON
  237. dtron:
  238.     in    a,(mport+4)    ;
  239.     set    0,a        ; set the DTR bit
  240.     out    (mport+4),a    ;
  241.  
  242.     ret
  243.  
  244.  
  245.  
  246. ;Turn DTR OFF
  247. dtroff:
  248.     in    a,(mport+4)    ;
  249.     res    0,a        ; reset the DTR bit
  250.     out    (mport+4),a    ;
  251.  
  252.     ret
  253.  
  254.  
  255. ;Initialise the uart
  256.  
  257. init:    ld    hl,2        ; get parameters
  258.     add    hl,sp
  259.     ex    de,hl
  260.     call    getparm        ; in HL
  261.     ld    (brate),hl    ; baud rate
  262.     call    getparm
  263.     ld    (parity),hl    ; parity
  264.     call    getparm
  265.     ld    (data),hl    ; data bits (BINARY 7 or 8)
  266.     call    getparm
  267.     ld    (stop),hl    ; stop bits (BINARY 1 or 2)
  268.  
  269. ; get the 8250 ready for programming
  270.     ld    a,0        ; clear interrupts
  271.     out    (mport+1),a    ;
  272.  
  273.     ld    a,00010000B    ; set to loop-back mode
  274.     out    (mport+4),a    ;
  275.  
  276. ; program the baud-rate (if it's valid)
  277.     ld    hl,(brate)    ; check to see if baud-rate is valid
  278.     ld    de,12        ;
  279.     or    a        ; clear carry
  280.     sbc    hl,de        ; hl=brate-12
  281.     jp    p,prb1        ; negitive if brate is 0..11
  282.  
  283.     ld    a,l        ;
  284.     ld    (mspeed),a    ; let zmp know it's valid
  285.  
  286.     ld    a,10000000B    ; set divisor latch access bit
  287.     out    (mport+3),a    ;
  288.  
  289.     ld    hl,(brate)    ; compute offset to baud-rate divisor
  290.     add    hl,hl        ;
  291.     ex    de,hl        ;
  292.     ld    hl,brtbl    ;
  293.     add    hl,de        ; HL now has address of divisor
  294.     ld    a,(hl)        ; get the low-order byte
  295.     out    (mport),a    ;
  296.     inc    hl        ;
  297.     ld    a,(hl)        ;
  298.     out    (mport+1),a    ;
  299.  
  300. ; program the: type of parity / # data bits / # stop bits
  301. prb1:    ld    b,0        ; set the LCR value (in B for now) to 0
  302.     ld    a,(parity)    ; set bits in B to type of parity
  303.     cp    'N'        ;
  304.     jp    z,parN        ;
  305.     cp    'E'        ;
  306.     jp    z,ParE         ;
  307.     cp    'O'        ;
  308.     jp    z,ParO        ;
  309. Skip3:    ld    a,(Data)    ; set bits in B to # of data bits
  310.     cp    7        ;
  311.     jp    z,data7        ;
  312.     cp    8        ;
  313.     jp    z,data8        ;
  314. Skip4:    ld    a,(Stop)    ;
  315.     cp    1        ;
  316.     jp    z,Stop1        ;
  317.     cp    2        ;
  318.     jp    z,Stop2        ;
  319. Skip5:    ld    a,b        ; get 'LCR' value
  320.     out    (mport+3),a    ; (also de-selects divisor access)
  321.  
  322. ; take 8250 out of loop-back mode
  323.     in    a,(mport)    ; read a char
  324.     add    hl,hl        ; waste some time
  325.     add    hl,hl        ;
  326.     in    a,(mport)    ; read another char
  327.     ld    a,0        ;
  328.     out    (mport+4),a    ; take 8250 out of loop-back mode
  329.  
  330.     ret
  331.  
  332. ; Types of parity
  333. ParN:
  334.     jp    Skip3
  335. ParE:
  336.     set    3,b
  337.     set    4,b
  338.     jp    Skip3
  339. ParO:
  340.     set    3,b
  341.     jp    Skip3
  342. ; Number of data bits
  343. Data7:
  344.     set    1,b
  345.     jp    Skip4
  346. Data8:
  347.     set    0,b
  348.     set    1,b
  349.     jp    Skip4
  350. ; Number of stop bits
  351. Stop1:
  352.     jp    Skip5
  353. Stop2:    
  354.     set    2,b
  355.     jp    Skip5
  356.  
  357. ; baud rate divisor table for 8250
  358. brtbl:    dw    1047        ; 110     0
  359.     dw    384        ; 300     1
  360.     dw    256        ; 450     2
  361.     dw    192        ; 600     3
  362.     dw    162        ; 710     4
  363.     dw    96        ; 1200    5
  364.     dw    48        ; 2400    6
  365.     dw    24        ; 4800    7
  366.     dw    12        ; 9600    8
  367.     dw    6        ; 19200   9
  368.     dw    3        ; 38400  10
  369.     dw    2        ; 57600  11
  370.  
  371. ;--------------------------------------------------------------------------
  372.  
  373. stop:    dw    1        ; stop bits
  374. parity:    dw    'N'        ; parity
  375. data:    dw    8        ; data bits
  376. brate:    dw    5        ; baud rate: 1200
  377.  
  378. ;--------------------------------------------------------------------------
  379. ;Values of brate for each baud rate
  380. ;
  381. ; baud rate    brate
  382. ;
  383. ;   110         0
  384. ;   300         1
  385. ;   450         2
  386. ;   600         3
  387. ;   710         4
  388. ;  1200         5
  389. ;  2400         6
  390. ;  4800         7
  391. ;  9600         8
  392. ; 19200         9
  393. ; 38400        10
  394. ; 57600         11
  395. ;
  396.  
  397. ;****************************************************************************
  398. ;Video terminal sequences: these are for the H19
  399. ;Cursor addressing:
  400. cursadd:
  401.     ld    hl,2        ; get parameters
  402.     add    hl,sp
  403.     ex    de,hl
  404.     call    getparm        ; in HL
  405.     ld    (row),hl    ; row
  406.     call    getparm
  407.     ld    (col),hl    ; column
  408.  
  409.                 ; using values in row and col
  410.     call    print
  411.     db    esc,'Y',0    ; H19 leadin
  412.     ld    a,(row)        ; row first
  413.     add    a,' '        ; add offset
  414.     call    cout
  415.     ld    a,(col)        ; sane for column
  416.     add    a,' '
  417.     call    cout
  418.  
  419.     ret
  420.  
  421. row:    ds    2        ; row
  422. col:    ds    2        ; column
  423.  
  424.  
  425. ;Clear screen:
  426. cls:
  427.     call    print
  428.     db    esc,'E',0
  429.     ret
  430.  
  431. ;Inverse video on:
  432. invon:
  433.     call    print
  434.     db    esc,'p',0
  435.     ret
  436.  
  437. ;Inverse video off:
  438. invoff:
  439.     call    print
  440.     db    esc,'q',0
  441.     ret
  442.  
  443. ;Turn off cursor:
  444. hide:
  445.     call    print
  446.     db    esc,'x5',0
  447.     ret
  448.  
  449. ;Turn on cursor:
  450. show:
  451.     call    print
  452.     db    esc,'y5',0
  453.     ret
  454.  
  455. ;Save cursor position:
  456. savecu:
  457.     call    print
  458.     db    esc,'j',0
  459.     ret
  460.  
  461. ;Restore cursor position:
  462. rescu:
  463.     call    print
  464.     db    esc,'k',0
  465.     ret
  466.  
  467. ;****************************************************************************
  468.  
  469. ;Service modem interrupt:
  470. mint:
  471.     ret            ; my system doesn't need this
  472.  
  473. ;Initialise interrupt vectors:
  474. invec:
  475.     ret            ; ditto
  476.  
  477. ;De-initialise interrupt vectors:
  478. dinvec:
  479.     ret            ; ditto
  480.  
  481. ;****************** End of user-defined code ********************************
  482. ;        Do not change anything below here.
  483.  
  484. ;Modem character test for 100 ms
  485. mrd:
  486.     push    bc        ; save bc
  487.     ld    bc,100        ; set limit
  488. mrd1:
  489.     call    mirdy        ; char at modem?
  490.     jr    nz,mrd2        ; yes, exit
  491.     ld    hl,1        ; else wait 1ms
  492.     call    waithlms
  493.     dec    bc        ; loop till done
  494.     ld    a,b
  495.     or    c
  496.     jr    nz,mrd1
  497.     ld    hl,0        ; none there, result=0
  498.     xor    a
  499. mrd2:
  500.     pop    bc
  501.     ret
  502.  
  503. ; Inline print routine: destroys A and HL
  504.  
  505. print:
  506.     ex    (sp),hl        ; get address of string
  507. ploop:
  508.     ld    a,(hl)        ; get next
  509.     inc    hl        ; bump pointer
  510.     or    a        ; done if zero
  511.     jr    z,pdone
  512.     call    cout        ; else print
  513.     jr    ploop        ; and loop
  514. pdone:
  515.     ex    (sp),hl        ; restore return address
  516.     ret            ; and quit
  517.  
  518. ;
  519. ;Output a character in A to the console
  520. ;
  521. cout:
  522.     push    bc        ; save regs
  523.     push    de
  524.     push    hl
  525.     ld    e,a        ; character to E
  526.     ld    c,2
  527.     call    bdos        ; print it
  528.     pop    hl
  529.     pop    de
  530.     pop    bc
  531.     ret
  532.  
  533. ;Wait(seconds)
  534. wait:
  535.     ld    hl,2
  536.     add    hl,sp
  537.     ex    de,hl        ; get delay size
  538.     call    getparm
  539.                 ; fall thru to..
  540. ;Wait seconds in HL
  541. waiths:
  542.     push    bc        ; save bc
  543.     push    de        ; de
  544.     push    ix        ; and ix
  545.     ld    ix,0        ; then point ix to 0
  546.                 ; so we don't upset memory-mapped i/o
  547.  
  548. ;Calculate values for loop constants. Need to have two loops to avoid
  549. ;   16-bit overflow with clock speeds above 9 MHz.
  550.  
  551. outerval    equ    (clkspd / 10) + 1
  552. innerval    equ    (6667 / outerval) * clkspd
  553.  
  554. wait10:
  555.     ld    b,outerval
  556.  
  557. wait11:
  558.     ld    de,innerval
  559.  
  560. wait12:
  561.     bit    0,(ix)        ; time-wasters
  562.     bit    0,(ix)
  563.     bit    0,(ix)        ; 20 T-states each
  564.     bit    0,(ix)
  565.     bit    0,(ix)
  566.     bit    0,(ix)
  567.     dec    de
  568.     ld    a,e
  569.     ld    a,d
  570.     or    e
  571.     jr    nz,wait12    ; 150 T-states per inner loop
  572.     djnz    wait11        ; decrement outer loop
  573.     dec    hl        ; ok, decrement count in hl
  574.     ld    a,h
  575.     or    l
  576.     jr    nz,wait10
  577.     pop    ix        ; done -- restore ix
  578.     pop    de        ; de
  579.     pop    bc        ; and bc
  580.     ret
  581.  
  582. ;Wait milliseconds
  583. mswait:
  584.     ld    hl,2
  585.     add    hl,sp
  586.     ex    de,hl        ; get delay size
  587.     call    getparm
  588.                 ; fall thru to..
  589. ;Wait milliseconds in HL
  590. waithlms:
  591.     push    de
  592. w1ms0:
  593.     ld    de,39 * clkspd
  594. w1ms1:
  595.     dec    de
  596.     ld    a,d
  597.     or    e
  598.     jr    nz,w1ms1
  599.     dec    hl
  600.     ld    a,h
  601.     or    l
  602.     jr    nz,w1ms0
  603.     pop    de
  604.     ret
  605.  
  606. ;Get next parameter from (de) into hl
  607. getparm:
  608.     ex    de,hl        ; get address into hl
  609.     ld    e,(hl)        ; get lo
  610.     inc    hl
  611.     ld    d,(hl)        ; then hi
  612.     inc    hl        ; bump for next
  613.     ex    de,hl        ; result in hl, address still in de
  614.     ret
  615.  
  616. ;Get address of user-defined variables
  617.  
  618. getvars:
  619.     ld    hl,uservars
  620.     ret
  621.  
  622. uservars:
  623.     dw    overdrive    ; .OVR etc. drive/user
  624.     dw    overuser
  625.  
  626.  
  627.      if    ($ - codebgn) gt ovsize
  628. toobig:    jp    errval        ; Overlay too large!
  629.      endif
  630.  
  631.     end
  632.