home *** CD-ROM | disk | FTP | other *** search
- List-
-
- ;================================================
- ; The external dispatcher code. This file contains
- ; the code to allow a redirection table to interface
- ; with an external runtime library. Include this
- ; file in the application program along with the
- ; redirection tables (like IO.RED).
-
- ;================================================
- ; Macro to set up the dispatch information and
- ; transfer control to the dispatcher. The
- ; redirection routines should push BX, load their
- ; own dispatch index to BL, and jump to this
- ; code. One of these macros is needed for each
- ; external library. This code assumes that it's
- ; in the same segment as the dispatch code below.
- ;
- ; LIB_NAME - file name of the library file: string.
-
- Dispatch Macro Lib_Name
- Push Si
- Mov Si, Offset Dat ;set control block offset
- Jmp Library_Dispatcher ;branch to dispatch code
-
- ;--- control block for this library
-
- Dat Label Word
- Dw 0 ;initial status
- Dw ? ;code offset (initialized when loaded)
- Dw ? ;code segment (initialized when loaded)
- Dw Offset Nam ;location of library name
-
- Nam Db Lib_Name, 0 ;name of library file
- Endm
-
- ;================================================
- ; Code to transfer request to library interface.
- ; The registers BX, SI, and DS should set the to
- ; the following: BL= dispatch index, SI= offset
- ; control block. The original values should be
- ; pushed on the stack. This code should be
- ; branched to, not called.
- ;
- ; On entry, the stack should look like the
- ; following:
- ;
- ; | SI | - top of stack (TOS)
- ; | BX |
- ; |<return>| - original return address
- ; | :: | put there by first call
- ;
- ; If there is an error, the error code is displayed
- ; and also returned in the ERRORLEVEL variable. The
- ; error codes are:
- ;
- ; 01 could not allocate memory
- ; 02 could not open library file
- ; 03 incompatible library version
- ; 04 error in library file
- ; 05 unknown error
-
- Library_Dispatcher
-
- ;--- test if ready, and if so transfer to library (library does return)
-
- Cs:
- Test Word [Si], 1 ;test if ready bit set
- Jz DispatchNotReady ;jump if not
-
- Push Cs ;segment to return to
- Cs:
- Jmp Dword [Si+2] ;transfer to library
-
- ;--- ready bit not set, try to load
-
- DispatchNotReady
- Push Ax
-
- Mov Al, 5 ;error number, in case file has been read
- Cs:
- Test Word [Si], 10b ;test if file has been read
- Jnz DispatchCritErr ;jump if so, unknown error
- Call Load_Library ;try to load library
- Jc DispatchCritErr ;jump if unsuccessful
-
- Pop Ax
- Jmp Library_Dispatcher ;go back to the start otherwise
-
- ;--- some kind of error, could not load library, error code should be in AL
-
- DispatchCritErr
- Push Ax
- Push Cs
- Pop Ds ;set data segment
-
- Sub Ah, Ah ;error number is in AX
- Mov Bl, 10 ;number base
- Div Al, Bl ;convert binary to decimal
- Mov Bx, Offset DispatchCritMess ;message location
- Add [Bx+14], Al ;set tens
- Add [Bx+15], Ah ;set ones
-
- Mov Ah, 9 ;display function
- Mov Dx, Bx ;message
- Int 21h ;execute
-
- Pop Ax ;restore error number
- Mov Ah, 4ch ;exit function
- Int 21h ;execute
-
- ;--- data
-
- Dispatch_Mark Equ 128 ;library marker
- Dispatch_Ver Db 1, 0 ;library version (1.00)
-
- DispatchCritMess Db 'Runtime error 00$' ;error message
-
- ;================================================
- ; Given the data block in DS:SI, an attempt is made
- ; to load the external library. If successful, the
- ; carry will be cleared, otherwise the carry will
- ; be set and AL will return the error code.
-
- Load_Library Proc Near
- Push Bx
- Push Cx
- Push Dx
- Push Di
- Push Ds
-
- Push Cs
- Pop Ds ;set data segment to control block
-
- ;--- open file
-
- Mov Ax, 3d00h ;open file
- Mov Dx, [Si+6] ;location of file name
- Int 21h ;execute
- Jnc LoadLibraryCont0 ;jump if ok
-
- Mov Al, 2 ;error code
- Jmp LoadLibraryErr0
-
- ;--- find size of file
-
- LoadLibraryCont0
- Mov Bx, Ax
- Mov Ax, 4202h ;move to end of file
- Sub Cx, Cx
- Mov Dx, Cx ;offset 0000.0000 from end
- Int 21h ;execute
- Or Dx, Dx
- Jz LoadLibraryCont1 ;jump if fewer than 10000H bytes, ok
-
- Mov Al, 4 ;error code
- Jmp LoadLibraryErr0
-
- LoadLibraryCont1
- Or Ax, Ax
- Jnz LoadLibraryCont2 ;jump if more than zero bytes, ok
-
- Mov Al, 4 ;error code
- Jmp LoadLibraryErr0
-
- ;--- allocate memory
-
- LoadLibraryCont2
- Mov Cl, 4
- Shr Ax, Cl ;make paragraph form
- Inc Ax ;account for partial paragraph
-
- Push Bx
- Mov Bx, Ax
- Mov Ah, 48h ;allocate function
- Int 21h ;execute
- Pop Bx
- Jnc LoadLibraryCont3 ;jump if ok
-
- Mov Al, 1 ;error code
- Jmp LoadLibraryErr0
-
- ;--- save segment in library module and prepare for read
-
- LoadLibraryCont3
- Mov [Si+4], Ax ;save segment in control block
-
- Push Ax
- Pop Ds ;set data segment for read
-
- ;--- move read pointer back to start of file
-
- Mov Ax, 4200h ;function
- Sub Cx, Cx
- Mov Dx, Cx ;offset 0000.0000
- Int 21h ;execute
-
- ;--- read file into newly allocated memory
-
- Mov Ah, 3fh ;function number
- Mov Cx, 0ffffh ;read all bytes (size was checked earlier)
- Sub Dx, Dx ;start of segment
- Int 21h ;execute
-
- ;--- check checksum (total checksum of library should be zero)
-
- Mov Cx, Ax ;set count (number of bytes read)
- Sub Al, Al ;initial sum
- Sub Di, Di ;start of segment
-
- LoadLibraryLoop
- Add Al, [Di] ;add next byte
- Inc Di ;advance pointer
- Loop LoadLibraryLoop ;loop back if more
-
- Or Al, Al ;check if zero
- Jz LoadLibraryCont4 ;jump if so, ok
-
- Mov Al, 4 ;error code
- Jmp LoadLibraryErr0
-
- ;--- library marker
-
- LoadLibraryCont4
- Cmp Byte [0], Dispatch_Mark ;check library marker
- Je LoadLibraryCont5 ;jump if ok
-
- Mov Al, 4 ;error code
- Jmp LoadLibraryErr0
-
- ;--- version number
-
- LoadLibraryCont5
- Cs:
- Mov Ax, Word Dispatch_Ver ;get highest compatible version
- Mov Dx, [1] ;get library version
- Xchg Al, Ah
- Xchg Dl, Dh ;make most significant byte high
- Cmp Ax, Dx ;compare version numbers
- Jae LoadLibraryCont6 ;jump if loading lower or equal version, ok
-
- Mov Al, 3 ;error code
- Jmp LoadLibraryErr0
-
- ;--- loaded successfully
-
- LoadLibraryCont6
- Mov Ax, [3] ;get starting offset
-
- Cs:
- Mov [Si+2], Ax ;save offset
- Cs:
- Mov Word [Si], 11b ;set loaded and ready bits
-
- Pop Ds
- Pop Di
- Pop Dx
- Pop Cx
- Pop Bx ;restore regs
- Clc
- Ret
-
- ;--- did not load correctly, error code in AL
-
- LoadLibraryErr0
- Pop Ds
- Pop Di
- Pop Dx
- Pop Cx
- Pop Bx ;restore regs
- Stc
- Ret
- Endp
-
-