.xlist
;  prologue.h - Macro Header for Microsoft C v3.0,4.0 & 5.x, ASM files.
;
;  Copyright (C) 1984-1989 Greenleaf Software Inc. All rights reserved.
;
;  Include this with all assembler modules, preceded by the proper
;  version of MODEL.H to select the compiler and memory model.
;
;  Modified 7/22/85 DK to add leading underscore char to names
;  Modified 7/24/85 DN to add leading underscore char to alias label
;
;;  David Nienhiser   11-JUN-1986  16:17:46.80
;       Modified for Microsoft C 4.0, compact and huge memory models.
;;  David Nienhiser   14-JUL-1986  16:58:23.77
;       Added DefineVar and ReferVar macros & added LABEL option to
;       ?cproc macro.
;;  David Nienhiser   28-MAY-1987  10:06:18.71
;       Added GetDsAx macro.

        .xcref  mesg,?cproc,?moderr
        .cref

mesg    macro   txt
        if1
        %out    txt
        endif
        endm

?moderr = 0

        ifndef  _MSC3
        ifdef   _MSC
_MSC3   equ     0
        endif
        endif

        ifndef  _MSC
          ifdef _MSC3
_MSC    equ     3
          else
            ?moderr = 1
          endif
        else
        if      (_MSC ne 3) and (_MSC ne 4) and (_MSC ne 5)
        ?moderr = 1
        endif
        endif

        ifndef  _HUGE
_HUGE   equ     0
        endif


        if      _HUGE eq 1
        if      (_LCODE ne 1) or (_LDATA ne 1)
        mesg    <Options Conflict in Model.h>
        ?moderr = 1
        endif

        endif

        if      ?moderr eq 0
        mesg    <Greenleaf Software Prologue.h Version 4.04 23-JUN-1988>
        if      _MSC eq 3
        mesg    <Microsoft C Version 3.0>
        endif

        if      (_MSC eq 4) or (_MSC eq 5)
        mesg    <Microsoft C Version 5 / Quick-C>
        endif
        mesg    <Copyright (C) 1985-1989 Greenleaf Software Inc. All rights reserved>

        if      (_LCODE eq 0) and (_LDATA eq 0) and (_HUGE eq 0);;Small Model
        mesg    <Small Memory Model>
        endif

        if      (_LCODE eq 0) and (_LDATA ne 0) and (_HUGE eq 0);;
        mesg    <Compact Memory Model>
        endif

        if      (_LCODE ne 0) and (_LDATA eq 0) and (_HUGE eq 0);;Medium Model
        mesg    <Medium Memory Model>
        endif

        if      (_LCODE ne 0) and (_LDATA ne 0) and (_HUGE eq 0);;Large Model
        mesg    <Large Memory Model>
        endif

        if      (_LCODE ne 0) and (_LDATA ne 0) and (_HUGE ne 0);;Huge Model
        mesg    <Huge Memory Model>
        endif


;  Argument Base address on stack:
;
if      _LCODE
@ab     equ     6               ; arg offset if far call
parm1_  equ     [bp+6]
parm2_  equ     [bp+8]
parm3_  equ     [bp+10]
parm4_  equ     [bp+12]
parm5_  equ     [bp+14]
parm6_  equ     [bp+16]
parm7_  equ     [bp+18]
parm8_  equ     [bp+20]
parm9_  equ     [bp+22]
parm10_ equ     [bp+24]
parm11_ equ     [bp+26]
parm12_ equ     [bp+28]
parm14_ equ     [bp+30]
        else
@ab     equ     4               ; ..if near call
parm1_  equ     [bp+4]
parm2_  equ     [bp+6]
parm3_  equ     [bp+8]
parm4_  equ     [bp+10]
parm5_  equ     [bp+12]
parm6_  equ     [bp+14]
parm7_  equ     [bp+16]
parm8_  equ     [bp+18]
parm9_  equ     [bp+20]
parm10_ equ     [bp+22]
parm11_ equ     [bp+24]
parm12_ equ     [bp+26]
parm13_ equ     [bp+28]
parm14_ equ     [bp+30]
        endif

        if      _LDATA
ptrsize equ     2               ; Number of words in pointer
        else
ptrsize equ     1
        endif


;  The DSEG and PSEG macros are defined to generate the appropriate GROUP
;  and SEGMENT statements for the compiler and memory model in use.
;  In addition, ENDDS and ENDPS are used to end these segments.
;
pseg    macro   segname

        ifb     <segname>
        mesg    <Missing Segment Name on pseg macro>
        error
        endif

        if      (_LCODE eq 0)           ;; Small Model Program Segment
_TEXT segment byte public 'CODE'
        assume cs:_TEXT

endps   &macro
_TEXT   ends
        purge   endps
        &endm
        endif

        if      (_LCODE ne 0)           ;; Medium or Large model
segname&_TEXT segment byte public 'CODE'
        assume cs:&segname&_TEXT

endps   &macro
segname&_TEXT   ends
        purge   endps
        &endm
        endif

        endm                                    ;;pseg


dseg    macro

DGROUP  group   _DATA
_DATA   segment word public 'DATA'
        assume ds:DGROUP

endds   &macro
_DATA   ends
        purge   endds
        &endm
        endm

GetDsAx macro
        mov     ax,DGROUP
        endm

cproc   macro   name1,name2,name1s,name2s,storage,options
        ?N1L = 0
        ?N2L = 0
        ifb     <name1>
          error   label not specified
        endif
        irpc    ?x,name1
          ?N1L = ?N1L + 1
        endm

        if      ?N1L gt 8
          ifb   <name1s>
            error       short name for name1 not specified
          else
            ??NS = 0
            irpc  ?x,name1s
              ??NS = ??NS + 1
            endm
            if ??NS gt 8
              error     name1s too long
            endif
          endif
        endif

        ifnb    <name2>
          irpc  ?x,name2
            ?N2L = ?N2L + 1
          endm
          if    ?N2L gt 8
            ifb <name2s>
              error     short name for name2 not specified
            else
              ??NS = 0
              irpc  ?x,name2s
                ??NS = ??NS + 1
              endm
              if ??NS gt 8
                error name2s too long
              endif
            endif
          endif
        endif
        ?cproc <name1>,<name2>,storage,<options>
        endm                                    ;; cproc

        ?cproc  macro   name1,name2,storage,options
                public  _&name1
                ifnb    <name2>
                  public        _&name2
                endif
                if      _LCODE
_&name1         proc    far
                  ifnb  <name2>
_&name2         label   far
                  endif
                else
_&name1         proc    near
                ifnb    <name2>
_&name2         label   near
                endif
                endif                           ;;_LCODE

??LRA           =       0
??SDS           =       0                       ;; Save ds?
??SES           =       0                       ;; Save es?
??SSI           =       1                       ;; Default for push si
??SDI           =       1                       ;; Default for push di
??EXIT          =       0                       ;; exit point wanted?
??EREXIT        =       0                       ;; error exit point
??OKEXIT        =       0                       ;; OK Exit point

                ifnb    <options>
                irp     x,<options>

                ifidn   <x>,<LABEL>
                if      _LCODE
name1           label   far
                else
name1           label   near
                endif
                endif

                ifidn   <x>,<LRA>               ;; Leave registers alone
                ??LRA = 1
                endif
                ifidn   <x>,<DS>                ;; Save ds
                ??SDS = 1
                endif
                ifidn   <x>,<ES>                ;; Save es
                ??SES = 1
                endif
                ifidn   <x>,<NOSI>
                ??SSI = 0
                endif
                ifidn   <x>,<NODI>
                ??SDI = 0
                endif
                ifidn   <x>,<EXIT>
                ??EXIT = 1
                endif
                ifidn   <x>,<ERROREXIT>
                ??EREXIT = 1
                ??EXIT = 1
                endif
                ifidn   <x>,<OKEXIT>
                ??OKEXIT = 1
                ??EXIT = 1
                endif

                endm
                endif

                if      ??LRA eq 0
                push    bp
                endif

                ifnb    <storage>
                sub     sp,storage
                endif

                if      ??LRA eq 0
                mov     bp,sp
                if      ??SSI eq 1
                push    si
                endif
                if      ??SDI eq 1
                push    di
                endif
                endif
                if      ??SDS eq 1
                push    ds
                endif
                if      ??SES eq 1
                push    es
                endif

cproce          &macro

                if      ??EXIT eq 1
name1&exit:
                endif
                if      ??SES eq 1
                pop     es
                endif
                if      ??SDS eq 1
                pop     ds
                endif
                if      ??LRA eq 0
                if      ??SDI eq 1
                pop     di
                endif
                if      ??SSI eq 1
                pop     si
                endif
                endif
                ifnb    <storage>
                add     sp,storage
                endif
                if      ??LRA eq 0
                pop     bp
                endif
                ret
                if      ??OKEXIT eq 1
name1&success:  xor     ax,ax
                jmp     name1&exit
                endif
                if      ??EREXIT eq 1
name1&error:    mov     ax,-1
                jmp     name1&exit
                endif

_&name1         endp
                purge   cproce
                &endm

funcerror       &macro
                jmp     name1&error
                &endm
funcok          &macro
                jmp     name1&success
                &endm
funcexit        &macro
                jmp     name1&exit
                &endm

                endm                            ;; ?cproc


ReferFunc       macro   name
  if    _LCODE
         extrn  _&name:far
  else
         extrn  _&name:near
  endif
        name    equ     _&name
                endm

DefineVar       macro   name,type,value
                ifb     <type>
                        error   Type missing on DefineVAr
                endif
                ifb     <value>
                        error   Value missing on DefineVar
                endif

                ifnb    <name>
                  public        _&name
                endif

                ifidn   <type>,<cByte>
                  ifnb  <name>
                    _&name      db      value
                  else
                                db      value
                  endif
                endif

                ifidn   <type>,<cWord>
                  ifnb  <name>
                    _&name      dw      value
                  else
                                dw      value
                  endif
                endif


                ifidn   <type>,<cLong>
                  ifnb  <name>
                    _&name      dd      value
                  else
                                dd      value
                  endif
                endif


                ifidn   <type>,<cDataPointer>
                  if    _LDATA
                    ifnb  <name>
                      _&name    dd      value
                    else
                                dd      value
                    endif
                  else
                    ifnb <name>
                      _&name    dw      value
                    else
                                dw      value
                    endif
                  endif
                endif

                ifidn   <type>,<cFuncPointer>
                  if    _LCODE
                    ifnb  <name>
                      _&name    dd      value
                    else
                                dd      value
                    endif
                  else
                    ifnb  <name>
                      _&name    dw      value
                    else
                                dw      value
                    endif
                  endif
                endif

                ifnb    <name>
                  name  equ     _&name
                endif
                endm

ReferVar        macro   name,type
                ifb     <name>
                  error Name missing on ReferVar
                endif
                ifb     <type>
                  error Type missing on ReferVar
                endif
                ifidn   <type>,<cByte>
                extrn   _&name:byte
                endif
                ifidn   <type>,<cWord>
                extrn   _&name:word
                endif
                ifidn   <type>,<cLong>
                extrn   _&name:dword
                endif
                ifidn   <type>,<cDataPointer>
                if      _LDATA
                extrn   _&name:dword
                else
                extrn   _&name:word
                endif
                endif
                ifidn   <type>,<cFuncPointer>
                if      _LCODE
                extrn   _&name:dword
                else
                extrn   _&name:word
                endif
                endif
                name    equ     _&name
                endm



                else
                mesg    <Incorrect Model.h file>
                endif

                .list