COMMENT $
Copyright (C) Magna Carta Software, Inc. 1987-1990. All Rights Reserved.
MCARTA.MAC -- A set of macros for assembly language modules.
$
;.XLIST
;.SALL
PAGE 50,110
;IF ((.TYPE PASS) AND 20H) EQ 0
; PASS = 0
;ENDIF
PASS EQU 1
IFNDEF ??version
IF2
PASS = PASS + 1
ENDIF
ELSE
%OUT Using Turbo Assembler
ENDIF
MSG MACRO str, passnum
IFNB <passnum>
IFDEF PASS
IF PASS EQ passnum
%OUT str
ENDIF
ENDIF
ELSE
%OUT str
ENDIF
ENDM
MSG <Starting pass %PASS>
MSG <Including CMACROS.MAC>, 1
IFDEF POSTFIXP
@prefixd = 1 ; put underscore in front of EXTERN data
@prefixp = 0
msg <EXTERN prefixing ON>, 1
ELSE
IFDEF MSC
@prefixp = 1 ; put underscore in front of PROCs
@prefixd = 1 ; put underscore in front of EXTERN data
msg <Assembling for MSC/QUICK C>, 1
msg <PROC prefixing ON>, 1
msg <EXTERN prefixing ON>, 1
ELSE
IFDEF __WATCOMC__
@prefixp = 0 ; put underscore in front of PROCs
@prefixd = 1 ; put underscore in front of EXTERN data
msg <Assembling for WATCOM C>, 1
msg <PROC prefixing ON>, 1
msg <EXTERN prefixing ON>, 1
ELSE
IFDEF __TURBOC__
@prefixp = 1 ; put underscore in front of PROCs
@prefixd = 1 ; put underscore in front of EXTERN data
msg <Assembling for TURBO C>, 1
msg <PROC prefixing ON>, 1
msg <EXTERN prefixing ON>, 1
ELSE
@prefixp = 0
@prefixd = 0
msg <Assembling for POWER C>, 1
msg <PROC prefixing OFF>, 1
msg <EXTERN prefixing OFF>, 1
ENDIF
ENDIF
ENDIF
ENDIF
IFDEF M_I86SM
msg <Small model defined>, 1
?codesize = 0
?datasize = 0
ELSE
IFDEF M_I86CM
msg <Compact model defined>, 1
?codesize = 0
?datasize = 1
ELSE
IFDEF M_I86MM
msg <Medium model defined>, 1
?codesize = 1
?datasize = 0
ELSE
IFDEF M_I86LM
msg <Large model defined>, 1
?codesize = 1
?datasize = 1
ELSE
.ERR
%OUT A memory model must be defined=1
%OUT Syntax: MASM @FILENAME <x> /D<compiler> /la /mx /p /v /w2 /z %1;
%OUT Where x= S | M | C | L and <compiler> = MSC | __TURBOC__ | __WATCOMC__ | __POWERC
ENDIF
ENDIF
ENDIF
ENDIF
FALSE EQU 0
TRUE EQU 1
;;Data types
_SHORT EQU 2
IF ?datasize
DPTR EQU 4
ELSE
DPTR EQU 2
ENDIF
FAR_DPTR EQU 4
IF ?codesize
CSIZE EQU 4
ELSE
CSIZE EQU 2
ENDIF
SOFF = CSIZE ;Stack OFFset of first function argument
PRESERVE MACRO r1, r2, r3, r4, r5, r6, r7, r8, r9, r10, r11
IFNB <r1>
push r1
PRESERVE r2, r3, r4, r5, r6, r7, r8, r9, r10
ENDIF
ENDM
RESTORE MACRO r1, r2, r3, r4, r5, r6, r7, r8, r9, r10, r11
IFNB <r1>
pop r1
RESTORE r2, r3, r4, r5, r6, r7, r8, r9, r10
ENDIF
ENDM
DEFSEG MACRO arg1, arg2
;; Name the code segment
IF @prefixp
IFE ?codesize
CSEG EQU <_TEXT>
ELSE
CSEG EQU <_&arg1&_TEXT>
ENDIF
ELSE
IFE ?codesize
CSEG EQU <TEXT>
ELSE
CSEG EQU <&arg1&_TEXT>
ENDIF
ENDIF
;; Name the data segment
IF @prefixp
IFB <arg2>
IFE ?datasize
DSEG EQU <_DATA>
ELSE
DSEG EQU <_&arg1&_DATA>
ENDIF
ELSE
DSEG EQU <arg2>
ENDIF
ELSE
IFB <arg2>
IFE ?datasize
DSEG EQU <_DATA>
ELSE
DSEG EQU <&arg1&_DATA>
ENDIF
ELSE
DSEG EQU <arg2>
ENDIF
ENDIF
;; Declare the segment order
CSEG SEGMENT WORD PUBLIC 'CODE'
CSEG ENDS
DSEG SEGMENT WORD PUBLIC 'DATA'
DSEG ENDS
_BSS SEGMENT WORD PUBLIC 'BSS'
_BSS ENDS
DGROUP GROUP DSEG, _BSS
IFE ?datasize
ASSUME CS:CSEG, SS:DGROUP, DS:DGROUP
ELSE
IFDEF __WATCOMC__
ASSUME CS:CSEG, SS:DGROUP
ELSE
IFDEF __TURBOC__
ASSUME CS:CSEG, DS:DGROUP
ELSE ;MSC and POWER C
ASSUME CS:CSEG, SS:DGROUP, DS:DGROUP
ENDIF
ENDIF
ENDIF
ENDM
CALC_OFF MACRO off, var
LOCAL @1
@1 = SOFF
IF off EQ _SHORT
var EQU <[bp + @1]>
ELSE
IF off EQ FAR_DPTR
var EQU <[bp + @1]>
ELSE
IF off EQ DPTR
IF ?datasize
var EQU <[bp + @1]>
ELSE
var EQU <[bp + @1]>
ENDIF
ENDIF
ENDIF
ENDIF
SOFF = SOFF + &off
ENDM
DO_CALC MACRO arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8
IFNB <arg1>
CALC_OFF arg1
DO_CALC <arg2>, <arg3>, <arg4>, <arg5>, <arg6>, <arg7>
ENDIF
ENDM
NAME_PROC MACRO arg1, arg2
LOCAL lname
IFB <arg2>
IF @prefixp
lname EQU <_&arg1>
ELSE
lname EQU <arg1>
ENDIF
IF ?codesize
lname PROC FAR
ELSE
lname PROC NEAR
ENDIF
IF @prefixp
PUBLIC _&arg1
ELSE
PUBLIC arg1
ENDIF
; arg1 EQU <lname>
ELSE
IF @prefixp
lname EQU <_&arg2>
arg2 EQU <lname>
ELSE
lname EQU <arg2>
ENDIF
IFIDN <arg1>, <_FAR>
lname PROC FAR
IFE ?codesize
SOFF = 4
ENDIF
ELSE
lname PROC NEAR
ENDIF
IF @prefixp
PUBLIC _&arg2
ELSE
PUBLIC arg2
ENDIF
ENDIF
ENDM
START_PROC MACRO name, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9
SOFF = CSIZE ;Reset stack offset
NAME_PROC name
SSAVE = FALSE
IFNB <arg1>
push bp
mov bp, sp
SOFF = SOFF + 2 ; allow for BP
SSAVE = TRUE
CALC_OFF arg1
DO_CALC <arg2>, <arg3>, <arg4>, <arg5>, <arg6>, <arg7>, <arg8>, <arg9>
ENDIF
ENDM
END_PROC MACRO name
IF SSAVE EQ TRUE
mov sp,bp
pop bp
ENDIF
ret
IF @prefixp
_&name ENDP
ELSE
&name ENDP
ENDIF
SOFF = CSIZE ;Reset stack offset
ENDM
?lds MACRO arg1, arg2
IF ?datasize
lds arg1, arg2
ELSE
mov arg1, arg2
ENDIF
ENDM
?les MACRO arg1, arg2
IF ?datasize
les arg1, arg2
ELSE
mov arg1, ds
mov es, arg1
mov arg1, arg2
ENDIF
ENDM
?ifFP MACRO arg1, arg2
IF ?datasize
arg1 arg2
ENDIF
ENDM
;Does not handle PROCs yet
EXTERN MACRO arg1, arg2
IF @prefixd
IFIDN <arg1>, <_SHORT>
EXTRN _&arg2&:WORD
ENDIF
IFIDN <arg1>, <FAR_DPTR>
EXTRN _&arg2&:DWORD
ENDIF
IF arg1 EQ DPTR
IF ?datasize
EXTRN _&arg2&:DWORD
ELSE
EXTRN _&arg2&:WORD
ENDIF
ENDIF
&arg2 EQU _&arg2
ELSE
IF arg1 EQ _SHORT
EXTRN &arg2&:WORD
ENDIF
IF arg1 EQ FAR_DPTR
EXTRN &arg2&:DWORD
ENDIF
IF arg1 EQ DPTR
IF ?datasize
EXTRN &arg2&:DWORD
ELSE
EXTRN &arg2&:WORD
ENDIF
ENDIF
ENDIF
ENDM
msg <Ending pass %PASS>