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 / BDSC / BDSC-1 / DEFF2A.CSM < prev    next >
Text File  |  2000-06-30  |  11KB  |  672 lines

  1. ;
  2. ; BD Software C Standard Library Machine Language Functions
  3. ; Written by Leor Zolman
  4. ; v1.46,    3/15/82
  5. ;
  6. ; This file is in "CSM" format; to convert to CRL format,
  7. ; use CASM.SUB in conjunction with CASM.COM, ASM.COM and DDT.COM.
  8. ; Functions appearing in this file:
  9. ;
  10. ;     rread    rwrite    rtell    rseek    rsrec    rcfsiz
  11. ;    setjmp    longjmp
  12. ;    setplot    clrplot    line    plot    txtplot
  13. ;    index    getline
  14. ;
  15. ;    
  16. ;
  17. ; The random-record file I/O function contained here are NOT documented
  18. ; in the User's Guide, because they are non-portable to pre-2.0 CP/M
  19. ; Systems.
  20. ;
  21.  
  22.     maclib    bds
  23.  
  24. ;
  25. ; Here are the new random-access file I/O routines
  26. ; for use with CP/M version 2.x ONLY...these functions
  27. ; will NOT work under pre-2.x CP/M's.
  28. ;
  29. ; The new functions are: rread, rwrite, rtell, rseek,
  30. ;             rsrec, rcfsiz
  31. ;
  32.  
  33.  
  34. ;
  35. ; Rread:
  36. ;
  37. ; Read a number of sectors randomly.
  38. ; Usage:
  39. ;
  40. ;    i = rread(fd, buf, n);
  41. ;
  42. ; The return value is either the number of sectors successfully
  43. ; read, 0 for EOF, or 1000 + (BDOS ERROR CODE)
  44. ; The Random Record Field is incremented following each successful
  45. ; sector is read, just as if the normal (sequentail) read function
  46. ; were being used. Rseek must be used to go back to a previous 
  47. ; sector.
  48. ;
  49.  
  50.     FUNCTION rread
  51.  
  52.     call    arghak
  53.     lda    arg1
  54.     call    fgfd
  55.     jc    error
  56.     mov    a,m
  57.     ani    2
  58.     jz    error
  59.     push    b
  60.     lda    arg1
  61.     call    fgfcb
  62.     shld    tmp2
  63.     lxi    h,0
  64.     shld    tmp2a
  65. r2:    lhld    arg3
  66.     mov    a,h
  67.     ora    l
  68.     lhld    tmp2a
  69.     jnz    r2a
  70.     pop    b
  71.     ret
  72.  
  73. r2a:    lhld    arg2
  74.     xchg
  75.     mvi    c,sdma
  76.     call    bdos
  77.     lhld    tmp2
  78.     xchg
  79.     mvi    c,readr    ;code for BDOS random read
  80.     push    d    ;save de so we can fudge nr field if
  81.     call    bdos    ;we stop reading on extent boundary...
  82.     pop    d    ; CP/M is a pain.
  83.     ora    a
  84.     jz    r4    ;go to r4 if no problem
  85.     cpi    1
  86.     jz    r2b    ;EOF?
  87.     mov    c,a    ;put return error code in BC
  88.     mvi    b,0
  89.     lxi    h,1000    ;add to 1000
  90.     dad    b
  91.     pop    b
  92.     ret
  93.  
  94. r2b:    lxi    h,32    ;yes. are we on extent boundary?
  95.     dad    d
  96.     mov    a,m
  97.     cpi    80h
  98.     jnz    r3
  99.     mvi    m,0    ;yes. reset nr to 0...CP/M leaves it at 80!
  100. r3:    lhld    tmp2a    ;(note: the above "bug" in CP/M was supposedly fixed
  101.     pop    b    ; for 2.x, but one can never be sure...)
  102.     ret
  103.  
  104. r4:    lhld    arg3
  105.     dcx    h
  106.     shld    arg3
  107.     lhld    arg2
  108.     lxi    d,128
  109.     dad    d
  110.     shld    arg2
  111.     lhld    tmp2a
  112.     inx    h
  113.     shld    tmp2a
  114.     lhld    tmp2    ;get address of fcb
  115.     lxi    b,33    ;get addr of random record field
  116.     dad    b
  117.     mov    c,m    ;bump
  118.     inx    h    ;    value
  119.     mov    b,m    ;      of 
  120.     inx    b    ;        random
  121.     mov    m,b    ;          field
  122.     dcx    h    ;            by one
  123.     mov    m,c
  124.     jmp    r2
  125.     ENDFUNC
  126.  
  127. ;
  128. ; Rwrite:
  129. ;
  130. ; The random "write" routine, which always copies the sector
  131. ; to be written down to tbuff before writing. Returns
  132. ; the # of sectors successfully written, or -1 on hard error.
  133. ; (the "1000 + error code" business is not used for rwrite)
  134. ;
  135.  
  136.     FUNCTION rwrite
  137.  
  138.     call    arghak
  139.     lda    arg1
  140.     call    fgfd
  141.     jc    error
  142.     mov    a,m
  143.     ani    4
  144.     jz    error
  145.     push    b
  146.     lda    arg1
  147.     call    fgfcb
  148.     shld    tmp2
  149.     lxi    h,0
  150.     shld    tmp2a
  151.     lxi    d,tbuff ;80 for normal CP/M, else 4280
  152.     mvi    c,sdma
  153.     call    bdos
  154.  
  155. nwr2:    lhld    arg3    ;done yet?
  156.     mov    a,h
  157.     ora    l
  158.     lhld    tmp2a    ;if so, return count
  159.     jnz    nwr2a
  160.     pop    b
  161.     ret
  162.  
  163. nwr2a:    lhld    arg2    ;else copy next 128 bytes down to tbuff
  164.     lxi    d,tbuff    ;80 for normal CP/M, else 4280
  165.     mvi    b,128
  166. nwr3:    mov    a,m
  167.     stax    d
  168.     inx    h
  169.     inx    d
  170.     dcr    b
  171.     jnz    nwr3
  172.     shld    arg2    ;save -> to next 128 bytes
  173.     lhld    tmp2    ;get addr of fcb
  174.     xchg
  175.     mvi    c,writr    ;go write randomly
  176.     call    bdos
  177.     ora    a    ;error?
  178.     lhld    tmp2a    ;if so, return # of successfully written
  179.     pop    b    ;  sectors.
  180.     rnz
  181.     push    b
  182.         
  183.     inx    h    ; else bump successful sector count,
  184.     shld    tmp2a
  185.     lhld    arg3    ; debump countdown,
  186.     dcx    h
  187.     shld    arg3
  188.     lhld    tmp2    ; get address of fcb
  189.     lxi    b,33    ; get address of random field
  190.     dad    b
  191.     mov    c,m    ; bump 16-bit value at random
  192.     inx    h    ; record
  193.     mov    b,m    ;    field
  194.     inx    b    ;         of
  195.     mov    m,b    ;           fcb
  196.     dcx    h    ;          by one
  197.     mov    m,c
  198.     jmp    nwr2    ; and go try next sector
  199.     ENDFUNC
  200.  
  201. ;
  202. ; rseek:
  203. ;
  204. ; rseek(fd, offset, origin)
  205. ;       seeks to offset records if origin == 0,
  206. ;     to present position + offset if origin == 1,
  207. ;    or to end of file + offset if origin == 2.
  208. ; (note that in the last case, the offset must be non-positive)
  209. ;
  210.  
  211.     FUNCTION rseek
  212.  
  213.     call    arghak
  214.     lda    arg1
  215.     call    fgfcb
  216.     jc    error
  217.     push    h
  218.     call    rtell2
  219.     lhld    arg2
  220.     lda    arg3    ;is origin == 0?
  221.     ora    a
  222.     jz    rseek2    ;if so, HL holds new position
  223.     dcr    a    ;no. is origin == 1?
  224.     jnz    rseek1
  225.     dad    d    ;yes. add offset to current position
  226.     jmp    rseek2    ;and result is in HL
  227.  
  228. rseek1:    pop    d    ;else origin must be 2...
  229.     push    d
  230.     push    b
  231.     mvi    c,cfsizc ;compute end of file position
  232.     call    bdos
  233.     pop    b
  234.     pop    h    ;get back fcb
  235.     push    h
  236.     call    rtell2    ;get DE = position
  237.     lhld    arg2    ;add offset
  238.     dad d        ;and HL holds new position
  239. rseek2:    xthl        ;get fcb, push    new position
  240.     lxi    d,33
  241.     dad    d    ;HL points to random field of fcb
  242.     pop    d    ;get new position in DE
  243.     mov    m,e    ;and put into fcb
  244.     inx    h
  245.     mov    m,d
  246.     xchg        ;and return the position value
  247.     ret
  248.  
  249. rtell2:    lxi    d,33
  250.     dad    d
  251.     mov    e,m    
  252.     inx    h
  253.     mov    d,m
  254.     ret
  255.     ENDFUNC
  256.  
  257. ;
  258. ; Rtell:
  259. ;
  260. ; Return random record position of file:
  261. ;
  262.  
  263.     FUNCTION rtell
  264.     call    arghak
  265.     lda    arg1
  266.     call    fgfcb
  267.     jc    error
  268.     lxi    d,33    ;go to random record field
  269.     dad    d
  270.     mov    e,m    ;get value into DE
  271.     inx    h
  272.     mov    d,m
  273.     xchg        ;put into HL
  274.     ret
  275.     ENDFUNC
  276.  
  277. ;
  278. ; Rsrec:
  279. ;
  280. ; Set random field from serial access mode:
  281. ;
  282.  
  283.     FUNCTION rsrec
  284.     call    arghak
  285.     lda    arg1
  286.     call    fgfcb
  287.     jc    error
  288.     push    h
  289.     xchg
  290.     push    b
  291.     mvi    c,srrecc
  292.     call    bdos
  293.     pop    b
  294.     pop    h
  295.     lxi    d,33
  296.     dad    d
  297.     mov    a,m
  298.     inx    h
  299.     mov    h,m
  300.     mov    l,a
  301.     ret
  302.     ENDFUNC
  303.  
  304. ;
  305. ; Rcfsiz:
  306. ;
  307. ; set random record field to end-of-file:
  308. ;
  309.  
  310.     FUNCTION    rcfsiz
  311.     call    arghak
  312.     lda    arg1
  313.     call    fgfcb
  314.     jc    error
  315.     push    h
  316.     xchg
  317.     push    b
  318.     mvi    c,cfsizc
  319.     call    bdos
  320.     pop    b
  321.     pop    h
  322.     lxi    d,33
  323.     dad    d
  324.     mov    a,m
  325.     inx    h
  326.     mov    h,m
  327.     mov    l,a
  328.     ret
  329.     ENDFUNC
  330.  
  331.     FUNCTION    setjmp
  332.     call    ma1toh
  333.     mov    m,c    ;save BC
  334.     inx    h
  335.     mov    m,b
  336.     inx    h
  337.     xchg
  338.     lxi    h,0
  339.     dad    sp
  340.     xchg
  341.     mov    m,e    ;save SP
  342.     inx    h
  343.     mov    m,d
  344.     inx    h
  345.     pop    d    ;save return address
  346.     push    d
  347.     mov    m,e
  348.     inx    h
  349.     mov    m,d
  350.     lxi    h,0    ;and return 0
  351.     ret
  352.     ENDFUNC
  353.  
  354.     FUNCTION    longjmp
  355.     call    ma1toh    ;get buffer address
  356.     mov    c,m    ;restore BC
  357.     inx    h
  358.     mov    b,m
  359.     inx    h
  360.     mov    e,m    ;restore SP...first put it in DE
  361.     inx    h
  362.     mov    d,m
  363.     inx    h
  364.     shld    temp    ;save pointer to return address
  365.     call    ma2toh    ;get return value
  366.     xchg        ;put return val in DE, old SP in HL
  367.     sphl        ;restore SP with old value
  368.     pop    h    ;pop retur address off stack
  369.     lhld    temp    ;get back ptr to return address
  370.     mov    a,m
  371.     inx    h
  372.     mov    h,m
  373.     mov    l,a    ;HL holds return address
  374.     xchg        ;put ret addr in DE, get return value in HL
  375.     push    d    ;push return address on stack
  376.     ret        ;and return...
  377. temp:    ds 2
  378.     ENDFUNC
  379.  
  380.  
  381.     FUNCTION    setplot
  382.     call    arghak
  383.     push    b
  384.      lhld    arg1    ;get base address
  385.     shld    pbase    ;    initialize
  386.     lhld    arg3    ;get y size
  387.     shld    ysize    ;    initialize
  388.     xchg        ;leave it in DE
  389.     lhld    arg2    ;get x size
  390.     shld    xsize    ;    initialize
  391.     call    usmul    ;figure out screen size
  392.     shld    psize    ;    initialize
  393.     pop    b
  394.     ret
  395.     ENDFUNC
  396.  
  397.     FUNCTION    clrplot
  398.     lhld    psize    ;put screen size
  399.     xchg        ;    in DE
  400.     lhld    pbase    ;get screen base in HL
  401. clr2:    mvi    m,' '    ;and
  402.     inx    h    ;   clear
  403.     dcx    d    ;     each
  404.     mov    a,d    ;      location
  405.     ora    e    ;        (all DE of 'em)
  406.     jnz    clr2
  407.     ret
  408.     ENDFUNC
  409.  
  410.     FUNCTION    line
  411.     call    arghak    ;get args
  412.     push    b
  413.     lda    arg2    ;put one set of endpoint data in DE in
  414.     mov    c,a    ;format:  D = x = arg2, E = y = arg3
  415.     lda    arg3
  416.     mov    b,a
  417.     mov    d,b
  418.     mov    e,c
  419.     call    put    ; put up one endpoint at BC
  420.     lda    arg4    ;put other endpoint data in HL
  421.     mov    c,a
  422.     lda    arg5
  423.     mov    b,a
  424.     call    put    ;(but first put up the point from BC)
  425.     mov    h,b
  426.     mov    l,c
  427.     call    liner    ;now connect them...
  428.     pop    b
  429.     ret        ;all done.
  430.  
  431. liner:    mov    a,d
  432.     sub    h
  433.     call    abs
  434.     cpi    2
  435.     jnc    line2    ;are points far enough apart
  436.             ;in both dimensions to warrant
  437.     mov    a,e    ;drawing a line?
  438.     sub    l
  439.     call    abs
  440.     cpi    2
  441.     jnc    line2
  442.     ret        ;if not, return.
  443.  
  444. line2:    call    midp    ;find midpoint
  445.     call    put    ;put it up
  446.     push    d    ;set up recursive calls
  447.     mov    d,b
  448.     mov    e,c
  449.     call    liner
  450.     xthl
  451.     call    liner
  452.     xchg
  453.     pop    h
  454.     ret        ;and we are done!
  455.  
  456. midp:    push    h
  457.     push    d
  458.  
  459.     mov    a,h
  460.     sub    d
  461.     ani    1
  462.     jz    mid3
  463.  
  464.     mov    a,h
  465.     cmp    d
  466.     jc    mid2a
  467.     inr    d
  468.     jmp    mid3
  469.  
  470. mid2a:    dcr    h
  471.  
  472. mid3:    mov    a,l
  473.     sub    e
  474.     ani    1
  475.     jz    mid4
  476.  
  477.     mov    a,l
  478.     cmp    e
  479.     jc    mid3a
  480.     inr    e
  481.     jmp    mid4
  482.  
  483. mid3a:    dcr    l
  484.  
  485. mid4:    mov    a,h
  486.     add    d
  487.     ora    a
  488.     rrc
  489.     mov    b,a
  490.     mov    a,l
  491.     add    e
  492.     ora    a
  493.     rrc
  494.     mov    c,a
  495.     pop    d
  496.     pop    h
  497.     ret
  498.  
  499. put:    push    h
  500.     push    d
  501.     mov    a,b
  502.     lhld    ysize
  503.     xchg
  504.     lhld    pbase
  505.     inr    a
  506. put1:    dcr    a
  507.     jz     put2
  508.     dad    d
  509.     jmp    put1
  510.  
  511. put2:    mov    e,c
  512.     mvi    d,0
  513.     dad    d
  514.     lda    arg1
  515.     mov    m,a
  516.     pop    d
  517.     pop    h
  518.     ret
  519.  
  520. abs:    ora    a
  521.     rp
  522.     cma
  523.     inr    a
  524.     ret
  525.     ENDFUNC
  526.  
  527.     FUNCTION    plot
  528.     call    arghak
  529.     lda    arg1
  530.     lhld    ysize
  531.     xchg
  532.     lhld    pbase
  533.     inr    a
  534. plot1:    dcr    a
  535.     jz    plotc
  536.     dad    d
  537.     jmp    plot1
  538.  
  539. plotc:    lda    arg2
  540.     mov    e,a
  541.     mvi    d,0
  542.     dad    d
  543.     lda    arg3
  544.     mov    m,a
  545.     ret
  546.     ENDFUNC
  547.  
  548.     FUNCTION    txtplot
  549.     call    arghak
  550.     push    b
  551.     lhld    arg2
  552.     xchg
  553.     lhld    ysize
  554.     call    usmul
  555.     xchg
  556.     lhld    arg3
  557.     dad    d
  558.     xchg
  559.     lhld    pbase
  560.     dad    d
  561.     xchg
  562.     lhld    arg1
  563.     mvi    b,0
  564.     lda    arg4
  565.     ora    a
  566.     jz    txt2
  567.     mvi    b,80h
  568. txt2:    mov    a,m
  569.     ora    a
  570.     jnz    txt3
  571.     pop    b
  572.     ret
  573.  
  574. txt3:    ora    b
  575.     stax    d
  576.     inx    h
  577.     inx    d
  578.     jmp    txt2
  579.     ENDFUNC
  580.  
  581. ;
  582. ; Index(str,substr)
  583. ; char *str, *substr;
  584. ;
  585. ; Returns index of substr in str, or -1 if not found.
  586. ;
  587.  
  588.     FUNCTION    index
  589.     call    arghak
  590.     lhld    arg1
  591.     xchg        ;main str ptr in DE
  592.     lhld    arg2    ;substr ptr in HL
  593.     dcx    d
  594. index1:    inx    d
  595.     ldax    d    ;end of str?
  596.     ora    a
  597.     jnz    index2
  598.     lxi    h,-1    ;yes. not found.
  599.     ret
  600. index2:    cmp    m    ;quick check for dissimilarity
  601.     jnz    index1    ;loop if not same right here
  602.     push    d    ;else do long compare
  603.     push    h
  604. index3:    inx    h
  605.     inx    d
  606.     mov    a,m    ;end of substr?
  607.     ora    a
  608.     jnz    index4    ;if not, go on testing
  609.     pop    d    ;else matches
  610.     pop    d    ;get starting address of substr in DE
  611.     lhld    arg1    ;subtract beginning of str
  612.     call    cmh
  613.     dad    d    ;and return the result
  614.     ret
  615.  
  616. index4:    ldax    d    ;current char match?
  617.     cmp    m
  618.     jz    index3    ;if so, keep testing
  619.     pop    h    ;else go on to next char in str
  620.     pop    d
  621.     jmp    index1
  622.     ENDFUNC
  623.  
  624. ;
  625. ; Getline(str,lim)
  626. ; char *str;
  627. ;
  628. ; Gets a line of text from the console, up to 'lim' characters.
  629. ;
  630.  
  631.     FUNCTION    getline
  632.     push    b
  633.     call    ma3toh    ;get max no. of chars
  634.     mov    c,a    ;save in C
  635.     call    ma2toh    ;get destination address
  636.     push    h
  637.     push    h
  638.     lxi    h,-150    ;use space below stack for reading line
  639.     dad    sp
  640.     push    h    ;save buffer address
  641.     mov    m,c    ;Set max # of characters
  642.     mvi    c,getlin
  643.     xchg        ;put buffer addr in DE
  644.     call    bdos    ;get the input line
  645.     mvi    c,conout
  646.     mvi    e,lf    ;put out a LF
  647.     call    bdos
  648.     pop    h    ;get back buffer address
  649.     inx    h    ;point to returned char count
  650.     mov    b,m    ;set B equal to char count
  651.     inx    h    ;HL points to first char of line
  652.     pop    d    ;DE points to start destination area
  653. copyl:    mov    a,b    ;copy line to start of buffer
  654.     ora    a
  655.     jz    gets2
  656.     mov    a,m
  657.     stax    d
  658.     inx    h
  659.     inx    d
  660.     dcr    b
  661.     jmp    copyl
  662.     
  663. gets2:    xra    a    ;store terminating null
  664.     stax    d
  665.     pop    h    ;return buffer address in HL
  666.     pop    b
  667.     ret
  668.     ENDFUNC
  669.  
  670.