home *** CD-ROM | disk | FTP | other *** search
/ ftp.barnyard.co.uk / 2015.02.ftp.barnyard.co.uk.tar / ftp.barnyard.co.uk / cpm / commercial-software / programming / AZTEC302.ZIP / MCH86.ARC < prev    next >
Text File  |  1998-09-16  |  26KB  |  1,717 lines

  1. csav.asm
  2. ; Copyright (C) 1983 by Manx Software Systems
  3. ; :ts=8
  4.     include lmacros.h
  5.     extrn    $begin:far
  6.     dw    near ptr $begin
  7.     public    $csav, $cret
  8. $csav    proc
  9.     pop    bx
  10. ifdef FARPROC
  11.     pop    dx
  12. endif
  13.     push    bp
  14.     mov    bp,sp
  15.     add    sp,ax
  16.     push    di
  17.     push    si
  18. ifndef FARPROC
  19.     call    bx
  20. else
  21.     push    cs
  22.     mov    ax, offset $cret
  23.     push    ax
  24.     push    dx
  25.     push    bx
  26.     ret
  27. endif
  28.  
  29. $cret:
  30.     pop    si
  31.     pop    di
  32.     mov    sp,bp
  33.     pop    bp
  34.     ret
  35. $csav    endp
  36.     finish
  37.     end
  38. cswt.asm
  39. ; Copyright (C) 1983, 85 by Manx Software Systems
  40. ; :ts=8
  41.     include lmacros.h
  42.     ifdef    FARPROC
  43. data    equ    word ptr es:[bx]
  44. addr    equ    word ptr es:2[bx]
  45. dflt    equ    word ptr es:[bx]
  46.     else
  47. data    equ    word ptr cs:[bx]
  48. addr    equ    word ptr cs:2[bx]
  49. dflt    equ    word ptr cs:[bx]
  50.     endif
  51. slot    equ    4
  52.     public $swt
  53.  
  54. $swt    proc
  55.     pop    bx
  56. ifdef FARPROC
  57. ifndef LONGPTR
  58.     mov    dx,es
  59. endif
  60.     pop    es
  61.     push    es
  62. endif
  63.     mov    cx,data
  64.     add    bx,2
  65.     jcxz    eswt
  66. swtloop:
  67.     cmp    ax,data
  68.     je    found
  69.     add    bx,slot
  70.     loop    swtloop
  71. eswt:
  72.     push    dflt
  73. ifdef FARPROC
  74. ifndef LONGPTR
  75.     mov    es,dx
  76. endif
  77. endif
  78.     ret
  79. found:
  80.     push    addr
  81. ifdef FARPROC
  82. ifndef LONGPTR
  83.     mov    es,dx
  84. endif
  85. endif
  86.     ret
  87. $swt    endp
  88.     finish
  89.     end
  90. farcall.asm
  91. ; :ts=8
  92. ;Copyright (C) 1983, 85 by Manx Software Systems
  93.     include    lmacros.h
  94.     procdef farcall, <<where,dword>, <srcregs,ptr>, <dstregs,ptr>>
  95.     push    si
  96.     push    di
  97.     push    ds
  98.     push    es
  99. ;
  100.     ldptr    bx,srcregs,ds
  101.     mov    ax,[bx]
  102.     push    2[bx]        ;save BX value for later
  103.     mov    cx,4[bx]
  104.     mov    dx,6[bx]
  105.     mov    si,8[bx]
  106.     mov    di,10[bx]
  107.     mov    es,14[bx]
  108.     mov    ds,12[bx]    ;trash DS last
  109.     pop    bx        ;now get value for BX
  110.     push    bp
  111.     call    where
  112.     pop    bp
  113.     push    ds        ;save returned DS
  114.     push    bx        ;save returned BX
  115.     mov    ds,-6[bp]    ;fetch C's data seg, for small model
  116.     ldptr    bx,dstregs,ds
  117.     mov    [bx],ax
  118.     pop    2[bx]        ;value returned in BX
  119.     mov    4[bx],cx
  120.     mov    6[bx],dx
  121.     mov    8[bx],si
  122.     mov    10[bx],di
  123.     pop    12[bx]        ;value returned in DS
  124.     mov    14[bx],es
  125.     pop    es
  126.     pop    ds
  127.     pop    di
  128.     pop    si
  129.     pop    bp
  130.     pushf
  131.     pop    ax
  132.     ret
  133.     pend    farcall
  134.     finish
  135.     end
  136. index.asm
  137. ; :ts=8
  138. ;Copyright (C) 1983 by Manx Software Systems
  139.     include lmacros.h
  140.     procdef index, <<arg,ptr>,<val,byte>>
  141.     cld
  142.     push    si
  143.     pushds
  144.     ldptr    si,arg,ds
  145.     mov    bl,val
  146. lookloop:
  147.     lodsb
  148.     test    al,al
  149.     jz    notfound
  150.     cmp    al,bl
  151.     jne    lookloop
  152.     retptrr si,ds
  153.     dec    ax
  154.     popds
  155.     pop    si
  156.     pret
  157. notfound:
  158.     retnull
  159.     popds
  160.     pop    si
  161.     pret
  162.     pend    index
  163.     finish
  164.     end
  165. lsubs.asm
  166. ;    Copyright (C) 1983 1984 by Manx Software Systems
  167. ; :ts=8
  168.     include    lmacros.h
  169.     internal $longs
  170. ;
  171.     intrdef    $ldv
  172. ;long divide    (primary = primary/secondary)
  173.     push    di
  174.     sub    di,di            ;mark result as positive
  175.     test    dx,dx
  176.     jns    prim_ok
  177.     neg    dx
  178.     neg    ax
  179.     sbb    dx,0
  180.     inc    di            ;mark as negative
  181. prim_ok:
  182.     test    bx,bx
  183.     jns    sec_ok
  184.     neg    bx
  185.     neg    cx
  186.     sbb    bx,0
  187.     xor    di,1            ;flip sign of result
  188. sec_ok:
  189.     call comdivide
  190. chksign:
  191.     test    di,di
  192.     jz    posres
  193.     neg    dx
  194.     neg    ax
  195.     sbb    dx,0
  196. posres:
  197.     pop    di
  198.     ret
  199. ;
  200.     intrdef    $lrm
  201. ;long remainder    (primary = primary%secondary)
  202.     push    di
  203.     mov    di,0            ;mark result as positive
  204.     test    dx,dx
  205.     jns    rprim_ok
  206.     neg    dx
  207.     neg    ax
  208.     sbb    dx,0
  209.     inc    di            ;mark as negative
  210. rprim_ok:
  211.     test    bx,bx
  212.     jns    rsec_ok
  213.     neg    bx
  214.     neg    cx
  215.     sbb    bx,0
  216. rsec_ok:
  217.     call comdivide
  218.     mov    ax,cx
  219.     mov    dx,bx
  220.     jmp    chksign
  221. ;
  222.     intrdef    $lum
  223. ;unsigned long remainder    (primary = primary%secondary)
  224.     call comdivide
  225.     mov    ax,cx
  226.     mov    dx,bx
  227.     ret
  228. ;
  229.     intrdef    $lud
  230. ;unsigned long divide    (primary = primary/secondary)
  231.     ifdef    FARPROC
  232.     call    comdivide
  233.     ret
  234.     endif
  235.  
  236. ;    fall thru into common divide routine if not large code model
  237. ;
  238. comdivide proc near        ; divide (dx,ax) by (bx,cx):
  239. ;                returns quotient in (dx,ax)
  240. ;                    remainder in (bx,cx)
  241. ;
  242.     test    bx,bx        ;check for easy case
  243.     jnz    hardldv
  244.     cmp    cx,dx
  245.     ja    veryeasy
  246.     push    ax
  247.     mov    ax,dx
  248.     sub    dx,dx
  249.     div    cx
  250.     mov    bx,ax        ;save high word of quotient
  251.     pop    ax
  252.     div    cx
  253.     mov    cx,dx        ;save remainder
  254.     mov    dx,bx
  255.     sub    bx,bx
  256.     ret
  257. veryeasy:
  258.     div    cx
  259.     mov    cx,dx        ;save remainder
  260.     mov    dx,bx        ;bx is already zero if we are here
  261.     ret
  262. hardldv:
  263.     push    bp
  264.     push    di
  265.     push    si
  266.     mov    si,cx        ;copy divisor (bx,cx) into (di,si)
  267.     mov    di,bx
  268.     sub    bx,bx        ;clear out top half of dividend
  269.     sub    bp,bp
  270.     mov    cx,32        ;set up loop count
  271. hardloop:
  272.     shl    ax,1        ;shift dividend left one bit
  273.     rcl    dx,1
  274.     rcl    bp,1
  275.     rcl    bx,1
  276.     sub    bp,si        ;subtract divisor till negative
  277.     sbb    bx,di
  278.     js    zerobit
  279. onebit:
  280.     inc    ax        ;set bit in quotient
  281.     loop    hardloop
  282.     jmp    hard_done
  283. zeroloop:
  284.     shl    ax,1        ;shift dividend left one bit
  285.     rcl    dx,1
  286.     rcl    bp,1
  287.     rcl    bx,1
  288.     add    bp,si        ;add divisor till positive
  289.     adc    bx,di
  290.     jns    onebit
  291. zerobit:
  292.     loop    zeroloop
  293.     add    bp,si        ;add divisor in one more time
  294.     adc    bx,di        ;to fix remainder
  295. hard_done:
  296.     mov    cx,bp        ;copy low part of rem.
  297.     pop    si
  298.     pop    di
  299.     pop    bp
  300.     ret
  301. comdivide endp
  302. $longs    endp
  303.     finish
  304.     end
  305. movblock.asm
  306. ;Copyright (C) 1983, 1985 by Manx Software Systems
  307. ; :ts=8
  308.     include    lmacros.h
  309.     procdef movblock,<<src,dword>,<dest,dword>,<len,word>>
  310.     push    di
  311.     push    si
  312.     push    ds
  313.     push    es
  314.     pushf
  315.     cld
  316.     mov    cx,len
  317.     les    di,dest
  318.     lds    si,src
  319.     cmp    cx,4
  320.     jne    not_int
  321.     cli
  322. not_int:
  323.     test    cx,cx
  324.     jnz    not_mov_all
  325.     mov    cx,8000H
  326.     jmp    short movwords
  327. not_mov_all:
  328.     mov    dx,cx
  329.     shr    cx,1
  330.     jz    mv_skip
  331. movwords:
  332. rep    movsw
  333. mv_skip:
  334.     test    dl,1
  335.     jz    done
  336.     movsb
  337. done:
  338.     popf
  339.     pop    es
  340.     pop    ds
  341.     pop    si
  342.     pop    di
  343.     pret
  344.     pend    movblock
  345.     finish
  346.     end
  347. movmem.asm
  348. ;Copyright (C) 1984, 1985 by Manx Software Systems
  349. ; :ts=8
  350.     include    lmacros.h
  351.     procdef movmem,<<arg1,ptr>,<arg2,ptr>,<len,word>>
  352.     pushf
  353.     cld
  354.     push    si
  355.     push    di
  356.     pushds
  357. ifndef LONGPTR
  358.     mov    di,ds
  359.     mov    es,di
  360. endif
  361.     ldptr    si,arg1
  362.     ldptr    di,arg2
  363.     mov    cx,len
  364.     mov    ax,es
  365.     mov    dx,ds
  366.     cmp    ax,dx
  367.     jne    move_forward
  368.     cmp    di,si
  369.     je    done
  370.     jb    move_forward
  371.     std
  372.     add    di,cx
  373.     add    si,cx
  374.     dec    di
  375.     dec    si
  376.     test    cl,1
  377.     jz    nobyte
  378.     movsb
  379. nobyte:
  380.     dec    di
  381.     dec    si
  382.     jmp    short domove
  383. ;
  384. move_forward:
  385.     test    cl,1
  386.     jz    domove
  387.     movsb
  388. domove:
  389.     shr    cx,1
  390.     jz    done
  391. rep    movsw
  392. done:
  393.     popds
  394.     pop    di
  395.     pop    si
  396.     popf
  397.     pret
  398.     pend    movmem
  399.     finish
  400.     end
  401. peek.asm
  402. ;Copyright (C) 1983, 1985 by Manx Software Systems
  403. ; :ts=8
  404.     include    lmacros.h
  405.     procdef peekw,<<addr,dword>>
  406.     push    ds
  407.     lds    bx,addr
  408.     mov    ax,ds:[bx]
  409.     pop    ds
  410.     pret
  411.     pend    peekw
  412. ;
  413.     entrdef peekb
  414.     procdef peek,<<addr1,dword>>
  415.     push    ds
  416.     lds    bx,addr1
  417.     mov    al,ds:[bx]
  418.     and    ax,0ffH
  419.     pop    ds
  420.     pret
  421.     pend    peek
  422. ;
  423.     procdef pokew,<<addr2,dword>,<val,word>>
  424.     push    ds
  425.     mov    ax,val
  426.     lds    bx,addr2
  427.     mov    ds:[bx],ax
  428.     pop    ds
  429.     pret
  430.     pend    pokew
  431. ;
  432.     entrdef poke
  433.     procdef pokeb,<<addr3,dword>,<val1,byte>>
  434.     push    ds
  435.     mov    al,val1
  436.     lds    bx,addr3
  437.     mov    ds:[bx],al
  438.     pop    ds
  439.     pret
  440.     pend    pokeb
  441.     finish
  442.     end
  443. port.asm
  444. ;Copyright (C) 1983, 1985 by Manx Software Systems
  445. ; :ts=8
  446.     include lmacros.h
  447.     entrdef    inport
  448.     procdef inportb,<<port,word>>
  449.     mov    dx,port
  450.     in    al,dx
  451.     and    ax,0ffH
  452.     pret
  453.     pend    inportb
  454. ;
  455.     procdef inportw,<<port1,word>>
  456.     mov    dx,port1
  457.     in    ax,dx
  458.     pret
  459.     pend    inportw
  460. ;
  461.     entrdef    outport
  462.     procdef outportb,<<port2,word>,<val,byte>>
  463.     mov    dx,port2
  464.     mov    al,val
  465.     out    dx,al
  466.     pret
  467.     pend    outportb
  468. ;
  469.     procdef outportw,<<port3,word>,<val1,word>>
  470.     mov    dx,port3
  471.     mov    ax,val1
  472.     out    dx,ax
  473.     pret
  474.     pend    outportw
  475.     finish
  476.     end
  477. rindex.asm
  478. ; :ts=8
  479. ;Copyright (C) 1983 by Manx Software Systems
  480.     include lmacros.h
  481.     procdef rindex, <<string,ptr>,<chr,byte>>
  482.     pushf
  483.     cld
  484.     push    di
  485. ifndef LONGPTR
  486.     mov    di,ds
  487.     mov    es,di
  488. endif
  489.     ldptr    di,string,es
  490.     mov    dx,di        ;save for later
  491.     sub    ax,ax
  492.     mov    cx,7fffH
  493. repne    scasb
  494.     mov    cx,di
  495.     sub    cx,dx        ;compute length of string
  496.     dec    di        ;backup to null byte
  497.     mov    al,chr        ;get byte to look for
  498.     std            ;now go backwards
  499. repne    scasb
  500.     je    found
  501.     retnull
  502.     pop    di
  503.     popf
  504.     pret
  505. found:
  506.     retptrr    di,es
  507.     inc    ax
  508.     pop    di
  509.     popf
  510.     pret
  511.     pend    rindex
  512.     finish
  513.     end
  514. sav.asm
  515. ; Copyright (C) 1983 by Manx Software Systems
  516. ; :ts=8
  517. codeseg    segment    byte public 'code'
  518.     extrn    $begin:far
  519.     dw    near ptr $begin
  520.     public    $sav,$ret
  521. $sav    proc    near
  522.     pop    bx
  523.     push    di
  524.     push    si
  525.     push    bp
  526.     mov    bp,sp
  527.     add    sp,ax
  528.     call    bx
  529. $ret:
  530.     mov    sp,bp
  531.     pop    bp
  532.     pop    si
  533.     pop    di
  534.     ret
  535. $sav    endp
  536. codeseg    ends
  537.     end
  538. cswit.asm
  539. ; Copyright (C) 1983, 85 by Manx Software Systems
  540. ; :ts=8
  541.     include lmacros.h
  542.     public $cswt
  543.  
  544. $cswt    proc
  545.     pop    bx            ; get address of table
  546.     push    di
  547. ifndef LONGPTR
  548.     push    es
  549. endif
  550.     mov    di,cs
  551.     mov    es,di
  552.     mov    di,bx            ; make di to point to table of values
  553.     mov    bx,cx            ; save number of entries in bx
  554.     shl    bx,1            ; adjusted for size of an entry
  555.     cld
  556. repne    scasw                ; find the right entry
  557.     mov    cx,es:word ptr -4[di][bx] ; pick up target address
  558. ifndef LONGPTR
  559.     pop    es
  560. endif
  561.     pop    di
  562.     jmp    cx            ; jump there
  563. $cswt    endp
  564.     finish
  565.     end
  566. segread.asm
  567. ; :ts=8
  568. ;Copyright (C) 1983, 1985 by Manx Software Systems
  569.     include lmacros.h
  570.     procdef segread,<<segs,ptr>>
  571. ifndef LONGPTR
  572.     mov    bx,ds
  573.     mov    es,bx
  574. endif
  575.     ldptr    bx,segs,es
  576. ifdef FARPROC
  577.     mov    ax,4[bp]
  578.     mov    es:[bx],ax
  579. else
  580.     mov    es:[bx],cs
  581. endif
  582.     mov    es:2[bx],ss
  583.     mov    es:4[bx],ds
  584.     mov    es:6[bx],es
  585.     pret
  586.     pend    segread
  587.     finish
  588.     end
  589. setjmp.asm
  590. ; :ts=8
  591. ;Copyright (C) 1983 by Manx Software Systems
  592.     include    lmacros.h
  593.     procdef setjmp,<<jmpbuf,ptr>>
  594.     pushds
  595.     ldptr    bx,jmpbuf,ds
  596.     lea    ax,jmpbuf
  597.     mov    [bx],ax
  598.     mov    ax,0[bp]    ;get caller's BP
  599.     mov    2[bx],ax
  600.     mov    4[bx],si
  601.     mov    6[bx],di
  602.     mov    ax,2[bp]    ;caller's IP
  603.     mov    8[bx],ax
  604. ifdef FARPROC
  605.     mov    ax,4[bp]    ;caller's CS
  606.     mov    10[bx],ax
  607. endif
  608.     sub    ax,ax
  609.     popds
  610.     pret
  611.     pend    setjmp
  612. ;
  613.     procdef longjmp,<<jbuf,ptr>,<retval,word>>
  614.     mov    ax,retval
  615. ifndef LONGPTR
  616.     mov    bx,ds
  617.     mov    es,bx
  618. endif
  619.     ldptr    bx,jbuf,es
  620.     mov    sp,es:[bx]
  621.     mov    bp,es:2[bx]
  622.     mov    si,es:4[bx]
  623.     mov    di,es:6[bx]
  624.     test    ax,ax
  625.     jnz    ax_ok
  626.     inc    ax
  627. ax_ok:
  628. ifdef FARPROC
  629.     jmp    es:dword ptr 8[bx]
  630. else
  631.     jmp    es:word ptr 8[bx]
  632. endif
  633.     pend    longjmp
  634.     finish
  635.     end
  636. setmem.asm
  637. ; :ts=8
  638. ;Copyright (C) 1983 by Manx Software Systems
  639.     include    lmacros.h
  640.     procdef setmem,<<src,ptr>,<len,word>,<val,byte>>
  641.     pushf
  642.     cld
  643.     push    di
  644. ifndef LONGPTR
  645.     mov    di,ds
  646.     mov    es,di
  647. endif
  648.     ldptr    di,src,es
  649.     mov    cx,len
  650.     mov    al,val
  651.     mov    ah,al
  652.     mov    dx,cx
  653.     shr    cx,1
  654.     jz    skip
  655. rep    stosw
  656. skip:
  657.     test    dl,1
  658.     jz    done
  659.     stosb
  660. done:
  661.     pop    di
  662.     popf
  663.     pret
  664.     pend    setmem
  665.     finish
  666.     end
  667. strcat.asm
  668. ; :ts=8
  669. ;Copyright (C) 1983, 1985 by Manx Software Systems
  670.     include    lmacros.h
  671.     procdef strcat,<<a,ptr>,<b,ptr>>
  672.     mov    dx,7fffH
  673.     jmp    short catcommon
  674.     pend    strcat
  675.  
  676.     procdef    strncat,<<str1,ptr>,<str2,ptr>,<len,word>>
  677.     mov    dx,len
  678. catcommon:
  679.     cld
  680.     push    si
  681.     push    di
  682.     pushds
  683. ifndef LONGPTR
  684.     mov    di,ds
  685.     mov    es,di
  686. endif
  687.     ldptr    di,str1
  688.     sub    ax,ax
  689.     mov    cx,7fffH
  690. repne    scasb            ;find end of destination string
  691.     dec    di        ;backup to null byte
  692.     ldptr    si,str2
  693.     mov    cx,dx
  694. cpyloop:
  695.     lodsb
  696.     stosb
  697.     test    al,al
  698.     loopnz    cpyloop
  699.     jz    nul_ok
  700.     sub    al,al        ;guarantee that string is nul terminated
  701.     stosb
  702. nul_ok:
  703.     popds
  704.     pop    di
  705.     pop    si
  706.     retptrm    str1
  707.     pret
  708.     pend    strncat
  709.     finish
  710.     end
  711. strcmp.asm
  712. ; :ts=8
  713. ;Copyright (C) 1983 by Manx Software Systems
  714.     include    lmacros.h
  715.     procdef strcmp,<<a,ptr>,<b,ptr>>
  716.     mov    cx,7fffh
  717.     jmp    short cmpcommon
  718.     pend    strcmp
  719.  
  720.     procdef    strncmp,<<str1,ptr>,<str2,ptr>,<len,word>>
  721.     mov    cx,len
  722. cmpcommon:
  723.     cld
  724.     push    si
  725.     push    di
  726.     pushds
  727.     ldptr    si,str1
  728. ifndef LONGPTR
  729.     mov    di,ds
  730.     mov    es,di
  731. endif
  732.     ldptr    di,str2
  733. cmploop:
  734.     lodsb
  735.     scasb
  736.     jne    notequal
  737.     test    al,al
  738.     loopnz    cmploop
  739.     sub    ax,ax
  740. done:
  741.     popds
  742.     pop    di
  743.     pop    si
  744.     pret
  745. notequal:
  746.     mov    ax,0
  747.     jb    less
  748.     inc    ax
  749.     jmp    done
  750. less:
  751.     dec    ax
  752.     jmp    done
  753.  
  754.     pend    strncmp
  755.     finish
  756.     end
  757. strcpy.asm
  758. ; :ts=8
  759. ;Copyright (C) 1983, 1985 by Manx Software Systems
  760.     include lmacros.h
  761.     procdef strcpy,<<str1,ptr>,<str2,ptr>>
  762.     cld
  763.     push    si
  764.     push    di
  765.     pushds
  766. ifndef LONGPTR
  767.     mov    di,ds
  768.     mov    es,di
  769. endif
  770.     ldptr    di,str1
  771.     ldptr    si,str2
  772. cpyloop:
  773.     lodsb
  774.     stosb
  775.     test    al,al
  776.     jnz    cpyloop
  777.     popds
  778.     pop    di
  779.     pop    si
  780.     retptrm    str1
  781.     pret
  782.     pend    strcpy
  783.     finish
  784.     end
  785. strlen.asm
  786. ; :ts=8
  787. ;Copyright (C) 1983 by Manx Software Systems
  788.     include    lmacros.h
  789.     procdef strlen,<<str1,ptr>>
  790.     cld
  791.     push    di
  792. ifndef LONGPTR
  793.     mov    di,ds
  794.     mov    es,di
  795. endif
  796.     ldptr    di,str1
  797.     mov    bx,di        ;save for later
  798.     sub    ax,ax
  799.     mov    cx,7fffH
  800. repne    scasb
  801.     mov    ax,di
  802.     sub    ax,bx        ;compute length of string
  803.     dec    ax
  804.     pop    di
  805.     pret
  806.     pend    strlen
  807.     finish
  808.     end
  809. strncpy.asm
  810. ; :ts=8
  811. ;Copyright (C) 1983, 1985 by Manx Software Systems
  812.     include    lmacros.h
  813.     procdef strncpy,<<str1,ptr>,<str2,ptr>,<len,word>>
  814.     cld
  815.     push    si
  816.     push    di
  817.     pushds
  818.     mov    cx,len
  819. ifndef LONGPTR
  820.     mov    di,ds
  821.     mov    es,di
  822. endif
  823.     ldptr    di,str1
  824.     ldptr    si,str2
  825.     jcxz    cpydone
  826. cpyloop:
  827.     lodsb
  828.     test    al,al
  829.     jz    zerofill
  830.     stosb
  831.     loop    cpyloop
  832.     jmp    short cpydone
  833. zerofill:
  834. rep    stosb
  835. cpydone:
  836.     popds
  837.     pop    di
  838.     pop    si
  839.     retptrm    str1
  840.     pret
  841.     pend    strncpy
  842.     finish
  843.     end
  844. swapmem.asm
  845. ; :ts=8
  846. ;Copyright (C) 1984 by Manx Software Systems
  847.     include    lmacros.h
  848.     procdef swapmem,<<str1,ptr>,<str2,ptr>,<len,word>>
  849.     push    si
  850.     push    di
  851.     pushds
  852. ifndef LONGPTR
  853.     mov    di,ds
  854.     mov    es,di
  855. endif
  856.     ldptr    si,str1
  857.     ldptr    di,str2
  858.     mov    cx,len
  859.     jcxz    done
  860. ifdef LONGPTR
  861.     mov    ax,ds
  862.     mov    dx,es
  863.     cmp    ax,dx
  864.     jne    swaploop
  865. endif
  866.     cmp    di,si
  867.     je    done
  868. swaploop:
  869.     mov    al,es:[di]
  870.     xchg    al,ds:[si]
  871.     stosb
  872.     inc    si
  873.     loop    swaploop
  874. done:
  875.     popds
  876.     pop    di
  877.     pop    si
  878.     pret
  879.     pend    swapmem
  880.     finish
  881.     end
  882. sysint.asm
  883. ; :ts=8
  884. ;Copyright (C) 1983 by Manx Software Systems
  885.     include lmacros.h
  886.     procdef sysint,<<num,byte>,<sregs,ptr>,<dregs,ptr>>
  887.     sub    sp,14
  888.     push    si
  889.     push    di
  890.     push    es
  891.     push    ds
  892. ;
  893. ;    build instruction sequence on the stack to issue int
  894. ;        and restore ss:sp to value before int.
  895. ;    Note: All this is because some handlers don't restore ss and sp.
  896. ;
  897.     mov    byte ptr -10[bp],0cdH        ;int xx
  898.     mov    al,num
  899.     mov    byte ptr -9[bp],al
  900.     mov    word ptr -8[bp],0cd8cH        ;mov bp,cs
  901.     mov    word ptr -6[bp],0d58eH        ;mov ss,bp
  902.     mov    byte ptr -4[bp],0bcH        ;mov sp,xx
  903.     mov    ax,sp
  904.     sub    ax,6
  905.     mov    word ptr -3[bp],ax
  906.     mov    byte ptr -1[bp],0cbH        ;retf
  907.     mov    word ptr -12[bp],ss        ;set up pointer to above code
  908.     lea    ax,-10[bp]
  909.     mov    word ptr -14[bp],ax
  910. ;
  911.     ldptr    bx,sregs,ds
  912.     mov    ax,[bx]
  913.     push    2[bx]        ;value to go into BX
  914.     mov    cx,4[bx]
  915.     mov    dx,6[bx]
  916.     mov    si,8[bx]
  917.     mov    di,10[bx]
  918.     mov    es,14[bx]
  919.     mov    ds,12[bx]
  920.     pop    bx
  921.     push    bp
  922.     call    ss:dword ptr -14[bp]
  923.     pop    bp
  924.     push    ds        ;save values so we have working registers
  925.     push    bx
  926.     ldptr    bx,dregs,ds
  927. ifdef LONGPTR
  928.     mov    [bx],ax
  929.     pop    2[bx]        ;value returned in BX
  930.     mov    4[bx],cx
  931.     mov    6[bx],dx
  932.     mov    8[bx],si
  933.     mov    10[bx],di
  934.     pop    12[bx]        ;value returned in DS
  935.     mov    14[bx],es
  936.     pop    ds
  937. else
  938.     mov    ss:14[bx],es
  939.     pop    ss:2[bx]        ;value returned in BX
  940.     pop    ss:12[bx]        ;value returned in DS
  941.     pop    ds
  942.     mov    [bx],ax
  943.     mov    4[bx],cx
  944.     mov    6[bx],dx
  945.     mov    8[bx],si
  946.     mov    10[bx],di
  947. endif
  948.     pop    es
  949.     pop    di
  950.     pop    si
  951.     pushf
  952.     pop    ax
  953.     add    sp,14
  954.     pret
  955.     pend    sysint
  956.     finish
  957.     end
  958. toupper.asm
  959. ; Copyright (C) 1983  by Manx Software Systems
  960.     include lmacros.h
  961.     procdef toupper,<<val1,byte>>
  962. ;
  963.     mov    al,val1
  964.     sub    ah,ah
  965.     cmp    al,'a'
  966.     jl    tu_done
  967.     cmp    al,'z'
  968.     jg    tu_done
  969.     sub    al,'a'-'A'
  970. tu_done:
  971.     pret
  972.     pend    toupper
  973. ;
  974. ;
  975.     procdef tolower,<<val2,byte>>
  976. ;
  977.     mov    al,val2
  978.     sub    ah,ah
  979.     cmp    al,'A'
  980.     jl    skip
  981.     cmp    al,'Z'
  982.     jg    skip
  983.     add    al,'a'-'A'
  984. skip:
  985.     pret
  986.     pend    tolower
  987.     finish
  988.     end
  989. memccpy.asm
  990. ; Copyright (C) 1984, 1985 by Manx Software Systems, Inc.
  991. ; :ts=8
  992.     include lmacros.h
  993.     procdef    memccpy,<<s1,ptr>,<s2,ptr>,<char,byte>,<lim,word>>
  994.     push    si
  995.     push    di
  996.     pushds
  997.     cld
  998. ifndef LONGPTR
  999.     mov    di,ds
  1000.     mov    es,di
  1001. endif
  1002.     ldptr    di,s1
  1003.     ldptr    si,s2
  1004.     mov    bl,char
  1005.     mov    cx,lim
  1006.     jcxz    cpydone
  1007. cpyloop:
  1008.     lodsb
  1009.     stosb
  1010.     cmp    al,bl
  1011.     jz    cpyfnd
  1012.     loop    cpyloop
  1013.     jmp    short cpydone
  1014. cpyfnd:
  1015.     retptrr    di,es
  1016.     popds
  1017.     pop    di
  1018.     pop    si
  1019.     pret
  1020. cpydone:
  1021.     retnull
  1022.     popds
  1023.     pop    di
  1024.     pop    si
  1025.     pret
  1026.     pend    memccpy
  1027.     finish
  1028.     end
  1029. memchr.asm
  1030. ; Copyright (C) 1984 by Manx Software Systems
  1031. ; :ts=8
  1032.     include lmacros.h
  1033.     procdef    memchr,<<area,ptr>,<char,byte>,<lim,word>>
  1034.     push si
  1035.     pushds
  1036.     cld
  1037.     ldptr    si,area
  1038.     mov    al,char
  1039.     mov    cx,lim
  1040.     jcxz    notfound
  1041. repne    lodsb
  1042.     jne    notfound
  1043.     dec    si
  1044.     retptrr    si,ds
  1045.     popds
  1046.     pop    si
  1047.     pret
  1048. notfound:
  1049.     retnull
  1050.     popds
  1051.     pop    si
  1052.     pret
  1053.     pend    memchr
  1054.     finish
  1055.     end
  1056. memcmp.asm
  1057. ; Copyright (C) 1984, 1985 by Manx Software Systems, Inc.
  1058. ; :ts=8
  1059.     include lmacros.h
  1060.     procdef    memcmp,<<dest,ptr>,<src,ptr>,<lim,word>>
  1061.     push    si
  1062.     push    di
  1063.     pushds
  1064.     cld
  1065. ifndef LONGPTR
  1066.     mov    di,ds
  1067.     mov    es,di
  1068. endif
  1069.     ldptr    si,dest
  1070.     ldptr    di,src
  1071.     mov    cx,lim
  1072.     jcxz    done
  1073. repe    cmpsb
  1074.     mov    ax,0
  1075.     ja    greater
  1076.     je    done
  1077.     dec    ax
  1078. done:
  1079.     popds
  1080.     pop    di
  1081.     pop    si
  1082.     pret
  1083. greater:
  1084.     inc    ax
  1085.     jmp    done
  1086.     pend    memcmp
  1087.     finish
  1088.     end
  1089. memcpy.asm
  1090. ; Copyright (C) 1984, 1985 by Manx Software Systems, Inc.
  1091. ; :ts=8
  1092.     include lmacros.h
  1093.     procdef    memcpy,<<s1,ptr>,<s2,ptr>,<lim,word>>
  1094.     push    si
  1095.     push    di
  1096.     pushds
  1097.     cld
  1098. ifndef LONGPTR
  1099.     mov    di,ds
  1100.     mov    es,di
  1101. endif
  1102.     ldptr    di,s1
  1103.     ldptr    si,s2
  1104.     mov    cx,lim
  1105.     mov    dx,cx
  1106.     shr    cx,1
  1107.     jcxz    chk_odd
  1108. rep    movsw
  1109. chk_odd:
  1110.     test    dl,1
  1111.     jz    done
  1112.     movsb
  1113. done:
  1114.     retptrm    s1
  1115.     popds
  1116.     pop    di
  1117.     pop    si
  1118.     pret
  1119.     pend    memcpy
  1120.     finish
  1121.     end
  1122. memset.asm
  1123. ; Copyright (C) 1984, 1985 by Manx Software Systems, Inc.
  1124. ; :ts=8
  1125.     include lmacros.h
  1126.     procdef    memset,<<area,ptr>,<char,byte>,<lim,word>>
  1127.     push    di
  1128.     cld
  1129. ifndef LONGPTR
  1130.     mov    di,ds
  1131.     mov    es,di
  1132. endif
  1133.     ldptr    di,area
  1134.     mov    al,char
  1135.     mov    ah,al
  1136.     mov    cx,lim
  1137.     mov    dx,cx
  1138.     shr    cx,1
  1139.     jcxz    nowords
  1140. rep    stosw
  1141. nowords:
  1142.     test    dl,1
  1143.     jz    done
  1144.     stosb
  1145. done:
  1146.     retptrm    area
  1147.     pop    di
  1148.     pret
  1149.     pend    memset
  1150.     finish
  1151.     end
  1152. strchr.asm
  1153. ; :ts=8
  1154. ;Copyright (C) 1985 by Manx Software Systems
  1155.     include lmacros.h
  1156.     procdef strchr, <<arg,ptr>,<val,byte>>
  1157.     cld
  1158.     push    si
  1159.     pushds
  1160.     ldptr    si,arg,ds
  1161.     mov    bl,val
  1162. lookloop:
  1163.     lodsb
  1164.     cmp    al,bl
  1165.     je    found
  1166.     test    al,al
  1167.     jnz    lookloop
  1168.     retnull
  1169.     popds
  1170.     pop    si
  1171.     pret
  1172. found:
  1173.     retptrr si,ds
  1174.     dec    ax
  1175.     popds
  1176.     pop    si
  1177.     pret
  1178.     pend    strchr
  1179.     finish
  1180.     end
  1181. strrchr.asm
  1182. ; :ts=8
  1183. ;Copyright (C) 1983 by Manx Software Systems
  1184.     include lmacros.h
  1185.     procdef strrchr, <<string,ptr>,<chr,byte>>
  1186.     pushf
  1187.     cld
  1188.     push    di
  1189. ifndef LONGPTR
  1190.     mov    di,ds
  1191.     mov    es,di
  1192. endif
  1193.     ldptr    di,string,es
  1194.     mov    dx,di        ;save for later
  1195.     sub    ax,ax
  1196.     mov    cx,7fffH
  1197. repne    scasb
  1198.     mov    cx,di
  1199.     sub    cx,dx        ;compute length of string
  1200.     dec    di        ;backup to null byte
  1201.     mov    al,chr        ;get byte to look for
  1202.     std            ;now go backwards
  1203. repne    scasb
  1204.     je    found
  1205.     retnull
  1206.     pop    di
  1207.     popf
  1208.     pret
  1209. found:
  1210.     retptrr    di,es
  1211.     inc    ax
  1212.     pop    di
  1213.     popf
  1214.     pret
  1215.     pend    strrchr
  1216.     finish
  1217.     end
  1218. pointers.asm
  1219. ; :ts=8
  1220. ;Copyright (C) 1985 by Manx Software Systems
  1221.     include lmacros.h
  1222.     assume    ds:dataseg
  1223. ;
  1224. ; ptrtoabs(lptr): convert pointer to 20-bit physical address
  1225. ;
  1226.     procdef    ptrtoabs,<<lptr,word>,<llptr,word>>
  1227.     mov    ax,lptr
  1228.     mov    dx,llptr
  1229.     mov    cx,4
  1230.     rol    dx,cl
  1231.     mov    bx,dx
  1232.     and    bx,0fff0h
  1233.     and    dx,0fh
  1234.     add    ax,bx
  1235.     adc    dx,0
  1236.     pret
  1237.     pend    ptrtoabs
  1238. ;
  1239. ; abstoptr(laddr): convert 20-bit physical address to pointer
  1240. ;
  1241.     procdef    abstoptr,<<laddr,word>,<lladdr,word>>
  1242.     mov    ax,laddr
  1243.     mov    dx,lladdr
  1244.     and    dx,0fh
  1245.     mov    bx,ax
  1246.     mov    cx,4
  1247.     ror    dx,cl
  1248.     shr    bx,cl
  1249.     and    bx,0fffh
  1250.     or    dx,bx
  1251.     and    ax,0fh
  1252.     pret
  1253.     pend    abstoptr
  1254.     finish
  1255.     end
  1256. ptrdiff.asm
  1257. ; :ts=8
  1258. ;Copyright (C) 1985 by Manx Software Systems
  1259.     include lmacros.h
  1260. ;
  1261. ; long _ptrdiff(lptr1, lptr2): return long pointer difference
  1262. ;
  1263.     procdef    _ptrdiff,<<off1,word>,<seg1,word>,<off2,word>,<seg2,word>>
  1264.     mov    ax,seg1
  1265.     sub    ax,seg2
  1266.     sbb    dx,dx
  1267.     mov    cx,4
  1268. sloop:    shl    ax,1
  1269.     rcl    dx,1
  1270.     loop    sloop
  1271.     add    ax,off1
  1272.     adc    dx,0
  1273.     sub    ax,off2
  1274.     sbb    dx,0
  1275.     mov    bx,dx
  1276.     pret
  1277.     pend    _ptrdiff
  1278.     finish
  1279.     end
  1280. ptradd.asm
  1281. ; :ts=8
  1282. ;Copyright (C) 1985 by Manx Software Systems
  1283.     include lmacros.h
  1284. ;
  1285. ;char *_ptradd(lptr, long): return lptr+long
  1286. ;
  1287.     procdef    _ptradd,<<offs,word>,<segm,word>,<incrl,word>,<incrh,word>>
  1288.     mov    ax,segm
  1289.     sub    dx,dx
  1290.     mov    cx,4
  1291. sloop:    shl    ax,1
  1292.     rcl    dx,1
  1293.     loop    sloop
  1294.     add    ax,offs
  1295.     adc    dx,0
  1296.     add    ax,incrl
  1297.     adc    dx,incrh
  1298.     mov    bx,ax
  1299.     mov    cx,4
  1300. sloop2:    shr    dx,1
  1301.     rcr    ax,1
  1302.     loop    sloop2
  1303.     mov    dx,ax
  1304.     mov    ax,bx
  1305.     and    ax,15
  1306.     mov    bx,dx
  1307.     pret
  1308.     pend    _ptradd
  1309.     finish
  1310.     end
  1311. inthand.asm
  1312. ;Copyright (C) 1985 by Manx Software Systems
  1313. ; :ts=8
  1314.     include lmacros.h
  1315.  
  1316. dataseg    segment    word public 'data'
  1317. ;
  1318. ;    this is the code for the initial handlers
  1319. ;
  1320. template label    byte
  1321.     push    si
  1322.     push    es
  1323.     call    common_handler
  1324. tIP    dw    0    ;original vector IP
  1325. tCS    dw    0    ;original vector CS
  1326. tDS    dw    0    ;current data segment
  1327. tSP    dw    0    ;offset of handler's stack
  1328. ifdef FARPROC
  1329. tCfunc    dd    0    ;C function address
  1330. else
  1331. tCfunc    dw    0    ;C function address
  1332. endif
  1333. tmpl_end label    byte
  1334. tmpl_len equ    offset tmpl_end - offset template
  1335.  
  1336. origIP    equ    es:0[si]    ;original vector IP
  1337. origCS    equ    es:2[si]    ;original vector CS
  1338. saveSS    equ    es:4[si]    ;save area for interupted SS
  1339. saveSP    equ    es:6[si]    ;ditto for SP
  1340. ourDS    equ    es:8[si]    ;current data segment
  1341. newSP    equ    es:10[si]    ;offset of handler's stack
  1342. ifdef FARPROC
  1343. Cfunc    equ    es:dword ptr 12[si]    ;C function address
  1344. else
  1345. Cfunc    equ    es:dword ptr 12[si]    ;C function address
  1346. endif
  1347.  
  1348. dataseg    ends
  1349.  
  1350.     assume    ds:dataseg
  1351.  
  1352. common_handler label far
  1353.     pop    si        ;get address of table stuff
  1354.     pop    es        ;following code block
  1355.     push    ax
  1356.     push    bx
  1357.     push    cx
  1358.     mov    bx,ss        ;save stack info
  1359.     mov    cx,sp
  1360.     mov    ax,es
  1361.     mov    ss,ax        ;switch to private stack
  1362.     mov    sp,newSP
  1363.     push    bx        ;save old stack stuff on new stack
  1364.     push    cx
  1365.     push    dx
  1366.     push    ds
  1367.     mov    ds,ourDS
  1368.     push    es        ;save across call
  1369.     cld
  1370.     call    Cfunc
  1371.     pop    es
  1372.     pop    ds
  1373.     pop    dx
  1374.     pop    cx
  1375.     pop    bx
  1376.     cli            ;just in case
  1377.     mov    ss,bx
  1378.     mov    sp,cx
  1379.     pop    cx
  1380.     pop    bx
  1381.     pop    ax
  1382.     pop    es
  1383.     pop    si
  1384.     iret
  1385.  
  1386.     finish
  1387.     end
  1388. fcall.asm
  1389. ; Copyright (C) 1985 by Manx Software Systems
  1390. ; :ts=8
  1391.     largecode
  1392. codeseg    segment byte public 'code'
  1393.     assume cs:codeseg
  1394.     public    $fcall
  1395. $fcall    proc    far
  1396.     push    dx
  1397.     push    ax
  1398.     ret
  1399. $fcall    endp
  1400. codeseg    ends
  1401.     end
  1402. ovbgn.asm
  1403. ; :ts=8
  1404. ;Copyright (C) 1984 by Manx Software Systems
  1405. codeseg    segment    para public 'code'
  1406. dataseg    segment    para public 'data'
  1407. save_si    dw    0
  1408. save_di    dw    0
  1409. save_sp    dw    0
  1410. save_bp    dw    0
  1411. save_ret dw    0
  1412.     extrn    _Uorg_:word, _Uend_:word
  1413. dataseg    ends
  1414.     assume    cs:codeseg,ds:dataseg
  1415.     extrn    ovmain_:near
  1416.     public $ovbgn
  1417. $ovbgn proc near
  1418.     pop    save_ret
  1419.     pop    cx        ;throw away overlay name
  1420.     mov    save_sp,sp
  1421.     mov    save_bp,bp
  1422.     mov    save_si,si
  1423.     mov    save_di,di
  1424.     cld
  1425.     mov    di,offset _Uorg_    ;clear uninitialized data
  1426.     mov    cx,offset _Uend_
  1427.     sub    cx,di
  1428.     shr    cx,1
  1429.     jz    nobss
  1430.     sub    ax,ax
  1431. rep    stosw
  1432. nobss:
  1433.     call    ovmain_
  1434. ;
  1435. ;    fall through into ovexit code
  1436. ;
  1437.     public    ovexit_
  1438. ovexit_:
  1439.     mov    bp,save_bp
  1440.     mov    sp,save_sp
  1441.     mov    si,save_si
  1442.     mov    di,save_di
  1443.     push    cx        ;fake argument to replace overlay name
  1444.     jmp    save_ret
  1445. $ovbgn endp
  1446. codeseg    ends
  1447.     end    $ovbgn
  1448. ovloader.c
  1449. /* Copyright (C) 1984 by Manx Software Systems */
  1450.  
  1451. #define OV_MAGIC 0xf2
  1452.  
  1453. struct ovrheader {            /* overlay header header */
  1454.     short o_magic;
  1455.     unsigned short o_corg;
  1456.     unsigned short o_csize;
  1457.     unsigned short o_dorg;
  1458.     unsigned short o_dsize;
  1459.     unsigned short o_bss;
  1460.     unsigned short o_entry;
  1461. };
  1462.  
  1463. static char *ovname;
  1464.  
  1465. #asm
  1466.     public    ovloader_
  1467. ovloader_ proc near
  1468.     mov    bx,sp
  1469.     mov    ax,word ptr 2[bx]
  1470.     mov    ovname_,ax
  1471.     call    _ovld_
  1472.     jmp    ax
  1473. ovloader_ endp
  1474. #endasm
  1475.  
  1476. static
  1477. _ovld()
  1478. {
  1479.     int fd, flag;
  1480.     register char *cp, *xp;
  1481.     auto struct ovrheader hdr;
  1482.     char *getenv(), path[64];
  1483.     extern char *_mbot, _Cend[], _Uend[];
  1484.  
  1485. #ifdef DOS20
  1486.     if ((cp = getenv("PATH")) == 0)
  1487.         cp = "";
  1488.     xp = path;
  1489.     for (;;) {
  1490.         strcpy(xp, ovname);
  1491.         strcat(path, ".ovr");
  1492.         if ((fd = open(path, 0)) != -1)
  1493.             break;
  1494.         do {
  1495.             if (*cp == 0)
  1496.                 loadabort(10);
  1497.             xp = path;
  1498.             while (*cp) {
  1499.                 if (*cp == ';') {
  1500.                     ++cp;
  1501.                     break;
  1502.                 }
  1503.                 *xp++ = *cp++;
  1504.             }
  1505.             *xp = 0;
  1506.         } while (path[0] == 0);
  1507.     }
  1508.  
  1509. #else
  1510.     strcpy(path, ovname);
  1511.     strcat(path, ".ovr");
  1512.     if ((fd = open(path, 0)) == -1)
  1513.         loadabort(10);
  1514. #endif
  1515.  
  1516.     if (read(fd, &hdr, sizeof hdr) != sizeof hdr)
  1517.         loadabort(20);
  1518.  
  1519.     /* safety check overlay header */
  1520.     if (hdr.o_magic != OV_MAGIC)
  1521.         loadabort(30);
  1522.     if (_mbot < hdr.o_dorg+hdr.o_dsize+hdr.o_bss)
  1523.         loadabort(40);
  1524.     if (_Cend > hdr.o_corg || _Uend > hdr.o_dorg)
  1525.         loadabort(60);
  1526.  
  1527.     if (_csread(fd, hdr.o_corg, hdr.o_csize) < hdr.o_csize
  1528.             || read(fd, hdr.o_dorg, hdr.o_dsize) < hdr.o_dsize)
  1529.         loadabort(50);
  1530.     close(fd);
  1531.     return hdr.o_entry;
  1532. }
  1533.  
  1534. static
  1535. loadabort(code)
  1536. {
  1537.     char buffer[80];
  1538.  
  1539.     sprintf(buffer, "Error %d loading overlay: %s$", code, ovname);
  1540.     bdos(9, buffer);
  1541.     exit(100);
  1542. }
  1543. srom.asm
  1544. ; Copyright (C) 1984 by Manx Software Systems
  1545. ; :ts=8
  1546. ;
  1547. ;    stacksize should be set according to your program's requirements
  1548. ;
  1549. stacksize equ    2048
  1550. ;
  1551. ;    Dseg is the data segment address (as a paragraph #)
  1552. ;
  1553. Dseg    equ    040H    ;physical addr 0x400, just above the int vectors
  1554.  
  1555. codeseg    segment    para public 'code'
  1556.     public    $MEMRY
  1557.     public    _mbot_, sbot
  1558. dataseg    segment    para public 'data'
  1559. $MEMRY    dw    -1
  1560.     public    errno_
  1561. errno_    dw    0
  1562.     public    _dsval_,_csval_
  1563. _dsval_    dw    0
  1564. _csval_    dw    0
  1565. _mbot_    dw    0
  1566. sbot    dw    0
  1567.     extrn    _Corg_:byte,_Cend_:byte
  1568.     extrn    _Dorg_:byte,_Dend_:byte
  1569.     extrn    _Uorg_:byte,_Uend_:byte
  1570.     bss    cstack:byte,stacksize
  1571. dataseg    ends
  1572.  
  1573.     assume    cs:codeseg
  1574.     extrn main_:near
  1575.     public    $begin
  1576. $begin    proc    far
  1577.     cli
  1578.     cld
  1579.     mov    ax,cs
  1580.     mov    ds,ax        ; temporary until data is copied
  1581.     mov    bx,Dseg
  1582.     mov    es,bx
  1583.     mov    ss,bx
  1584.     mov    sp,offset cstack + stacksize
  1585. ;
  1586. ;        copy Init data from rom to ram
  1587.     mov    di,offset _Dorg_
  1588.     mov    cx,offset _Dend_
  1589.     inc    cx
  1590.     shr    cx,1
  1591.     jcxz    nocopy
  1592.     mov    si,offset _Cend_
  1593.     add    si,15        
  1594.     and    si,0fff0H    ;Initialzed Data starts @ next para after code
  1595.     add    si,di
  1596. rep    movsw
  1597. nocopy:
  1598. ;
  1599. ;        clear uninitialized data
  1600.     mov    di,offset _Uorg_
  1601.     mov    cx,offset _Uend_
  1602.     sub    cx,di
  1603.     inc    cx
  1604.     shr    cx,1
  1605.     jcxz    noclear
  1606.     sub    ax,ax
  1607. rep    stosw
  1608. noclear:
  1609. ;
  1610.     assume    ds:dataseg,es:dataseg,ss:dataseg
  1611.  
  1612.     mov    ds,bx            ;set DS, now DS, SS, ES are equal
  1613.     mov    di,$MEMRY
  1614.     inc    di
  1615.     and    di,0fffeH    ;adjust to word boundary
  1616.     mov    $MEMRY,di    ;save memory allocation info for sbrk()
  1617.     mov    _mbot_,di
  1618.     mov    sbot,0ffffH    ;this is the heap limit for sbrk()
  1619.     mov    _dsval_,ds
  1620.     mov    _csval_,cs
  1621.     sti
  1622.     jmp    main_        ;main shouldn't return in ROM based system
  1623. $begin    endp
  1624. codeseg    ends
  1625.     end    $begin
  1626. lrom.asm
  1627. ; Copyright (C) 1984, 1985 by Manx Software Systems
  1628. ; :ts=8
  1629.     include lmacros.h
  1630. ;
  1631. ;    stacksize should be set according to your program's requirements
  1632. ;
  1633. stacksize equ    2048
  1634. ;
  1635. ;    Dseg is the data segment address (as a paragraph #)
  1636. ;
  1637. ;    in large model this is picked from the -D option of the linker
  1638. ;Dseg    equ    040H    ;physical addr 0x400, just above the int vectors
  1639.  
  1640. dataseg    segment    word public 'data'
  1641.     bss    cstack:byte,stacksize
  1642.     public    $MEMRY
  1643. $MEMRY    dw    -1
  1644.     public    errno_
  1645. errno_    dw    0
  1646.     public    _dsval_,_csval_
  1647. _dsval_    dw    0
  1648. _csval_    dw    0
  1649.     public    _mbot_, sbot
  1650. _mbot_    dw    0
  1651. sbot    dw    0
  1652.     extrn    _Dorg_:byte,_Dend_:byte
  1653.     extrn    _Uorg_:byte,_Uend_:byte
  1654. dataseg    ends
  1655.     extrn    _Corg_:byte,_Cend_:byte
  1656.  
  1657. ifdef    FARPROC
  1658.     extrn main_:far
  1659. else
  1660.     extrn main_:near
  1661. endif
  1662.  
  1663.     public    $begin
  1664. $begin    proc    far
  1665.     cli
  1666.     cld
  1667.     mov    ax,seg _Cend_    ;Initialzed Data starts @ next para after code
  1668.     mov    cx,offset _Cend_
  1669.     jcxz    nobump
  1670.     inc    ax
  1671. nobump:
  1672.     mov    ds,ax        ;place where data is in rom
  1673.     mov    bx,dataseg    ;place where data is to go in ram
  1674.     mov    es,bx
  1675.     mov    ss,bx
  1676.     mov    sp,offset cstack
  1677. ;
  1678. ;        copy Init data from rom to ram
  1679.     mov    di,0
  1680.     mov    cx,offset _Dend_
  1681.     inc    cx
  1682.     shr    cx,1
  1683.     jcxz    nocopy
  1684.     mov    si,0
  1685. rep    movsw
  1686. nocopy:
  1687. ;
  1688. ;        clear uninitialized data
  1689.     mov    di,offset _Uorg_
  1690.     mov    cx,offset _Uend_
  1691.     sub    cx,di
  1692.     inc    cx
  1693.     shr    cx,1
  1694.     jcxz    noclear
  1695.     sub    ax,ax
  1696. rep    stosw
  1697. noclear:
  1698. ;
  1699.     assume    ds:dataseg,es:dataseg
  1700.  
  1701.     mov    ds,bx            ;set DS, now DS, SS, ES are equal
  1702.     mov    di,$MEMRY
  1703.     inc    di
  1704.     and    di,0fffeH    ;adjust to word boundary
  1705.     mov    $MEMRY,di    ;save memory allocation info for sbrk()
  1706.     mov    _mbot_,di
  1707.     mov    sbot,0ffffH    ;this is the heap limit for sbrk()
  1708.     mov    _dsval_,ds
  1709.     mov    _csval_,cs    ;this is of dubious value in large code
  1710.     sti
  1711.     jmp    main_        ;main shouldn't return in ROM based system
  1712. $begin    endp
  1713. codeseg    ends
  1714.     end    $begin
  1715. get sign
  1716.     and    cl,80H
  1717.     or    ah,cl        ;merge si