📄 rtmload.asm
字号:
TITLE RTMLOAD - Runtime module loader
;***
; RTMLOAD - DOS 2/3 Runtime Module Loader
;
; Copyright <C> 1986, Microsoft Corporation
;
; Purpose:
; This module is linked to a BASCOM-generated object
; file created with the RTM option (no /O). This code
; will load the RTM EXE directly and place the code in
; high memory and the data to the compiled program DGROUP.
; The RTM code will then finish the initialization and
; start execution of the compiled program.
;
; This module is also used to load a user libraries EXE file
; into high memory, along with it's symbol table, for the
; QB4 interpreter. QB4 user libraries are very similar to the
; compiler DOS 3 RTM except that user libraries also contain
; a symbol table concatenated to the end of the file.
;
;******************************************************************************
INCLUDE switch.inc
INCLUDE rmacros.inc
USESEG <_DATA>
INCLUDE seg.inc
INCLUDE addr.inc
INCLUDE baslibma.inc
INCLUDE files.inc
INCLUDE array.inc
INCLUDE rtps.inc
INCLUDE ulib.inc
INCLUDE const.inc
INCLUDE string.inc
CondEnd MACRO entrypoint ; generate END
END
ENDM
CreateSeg LOADRTM,LOADRTM,BYTE, PUBLIC, CODE
CreateSeg LOADRTMEND, LOADRTMEND, PARA, PUBLIC, CODE
CreateSeg CODE, UL_TEXT,BYTE, PUBLIC, CODE
INCLUDE idmac.inc
; QBI message numbers used to call QBI message mapper
EXTRN ER_DMA:ABS ;Dos Arena error
EXTRN ER_ULM:ABS ;Memory allocation error
EXTRN ER_ULO:ABS ;Out of memory error
EXTRN ER_ULI:ABS ;Invalid user library format error
EXTRN ER_ULD:ABS ;Disk IO error
EXTRN ER_ULF:ABS ;Cannot find file error (if redirected IO)
EXTRN ER_ULE:ABS ;Error message preamble
EXTRN ER_ULG:ABS ;Error message postamble
EXTRN ER_ULP:ABS ;Path prompt preamble
EXTRN ER_ULT:ABS ;Path prompt postamble
externFP B$END ;Quick exit routine
externFP B$Pause ;Displays - Hit any key to continue
externFP B$Shell ;QBC Exec helper
externFP B$ShellSetup ;Prepares runtime for QBC Exec
externFP B$ShellRecover ;Recovers state after QBC exec
externFP B$ULDataRelease ;releases data images
externFP B$ULTerm ;calls UL terminators
externFP B$ULGetCommon ;search for compiled common
externFP B$ITCR ; print CR-LF
externFP OpenCheckDrive
externFP FindAndOpenFile
externFP B$FHAllocFAR
externFP B$FHDeallocFAR
externFP __ctermsub ; terminates math and restores
; divide-by-zero interrupts
INCLUDE exehdr.inc ;structure for EXE file header area
sBegin _DATA
externW __psp ;program prefix
externB bufStdMsg ;QBI message buffer
externW b$pBC_SAB ;ptr to BC start address table
externW __asizds ;max DGROUP space
externW STKHQQ ;C low water mark for stack
externW __atopsp ;top of allocated stack space
externW b$pend ;bottom of allocated stack space
externW b$pendchk ;low water mark for stack
externW b$ULSymSeg ;User Library symbol table segment
externW b$ULDataLength ;length of UL static data
externW b$ULDataStart ;offset of UL static data in DGROUP
externW b$FHDStart ;terminating Far heap descriptor
globalW b$pULVars,0 ;address of shared data defined in UL
externB fDebugScr ; address of shared data defined in UL
externB b$Buf1 ; general purpose filename buffer
externB qbIniFName ; Literal "qb.ini"
externW bdExePath ; bd for user-specified exe path
externW bdLibPath ; bd for user-specified lib path
externW bdInclPath ;bd for user-specified include path
QBINC db '_QB_INC=' ;our own environment variable name
cbQBINC = $ - QBINC ;length of the string
public CB_bufPath
public CB_bufLib
globalB bufPath,<"PATH">
CB_bufPath = $ - bufPath
globalB bufLib,<"LIB">
CB_bufLib = $ - bufLib
globalB bufCurDir,<".\",0>
sEnd DATA
assumes CS,LOADRTM
assumes DS,LOADRTM
assumes ES,NOTHING
sBegin LOADRTM
; Data for runtime module loader.
EHBuffer DB SIZE ExeHeader DUP(?) ;buffer for RTM EXE header
externNP ListStdMsgRtmNear ;QBI message mapper
ULBuffer DB SIZE UserLib_Hdr DUP(?) ;buffer for UL header
ProgramPSP DW 1 DUP(?) ;PSP of program
RtmCodeSeg DW 1 DUP(?) ;local copy of code Seg
RtmCodeSize DW 1 DUP(?) ;size of RTM code
ULSymSeg DW 1 DUP(?) ;segment of user lib symbol table
ULSymSize DW 1 DUP(?) ;size of user lib symbol table
DbPub ULSquishSize
DbPub ULCodeSquishSize
ULSquishSize DW 1 DUP(?) ;byte count of compressed leading
; zeros in QLB, both DATA and CODE
ULCodeSquishSize DW 1 DUP(?) ;byte count of compressed leading
; zeros at start of QLB code
ULCheckSum DW 1 DUP(?) ;check sum for user library
fQBCExec DB 0 ;non-zero if QBC compile in progress
fULQBCReload DB 0 ;non-zero if we need to reload
;UL because of QBC exec.
fNoIntHooked DB 0 ; non-zero if no interrupts are
; hooked (during make-exe) and
; __ctermsub shouldn't be done upon
; error.
PathEnvPtr LABEL DWORD
RelocBufPtr LABEL DWORD
SavedSSinCS LABEL WORD
PathEnvOffset LABEL WORD
RelocBufOffset LABEL WORD
DW 1 DUP(?) ;offset to ENV PATH or reloc item
SavedSPinCS LABEL WORD
PathEnvSegment LABEL WORD
RelocBufSegment LABEL WORD
DW 1 DUP(?) ;segment to ENV PATH or reloc item
QBCDataBlock STRUC
CommandList DW ? ;Set by UI - psd of commands to exec.
fErrorCode DW ? ;Set by Loader - non zero if an error
;occurred in one of the execs (contains
;error code returned by the exec.
QBCDataBlock ENDS
PUBLIC b$QBCData
b$QBCData QBCDataBlock<> ;QBCData block - defined in LOADRTM seg
QBExe DB 'QB.EXE',0 ;name of QB interpreter
EXEExt EQU OFFSET QBExe + 2 ;pts to .EXE extension
QBExeLength = $ - QBExe ;length of the file name
LibString DB "LIB=" ;environment variable for LIB
LibStringLength = $ - LibString
Filename DB "QB.QLB",0 ;default userlib filename
FilenameLength = $ - Filename ;length of just the filename
QLBExt EQU OFFSET Filename + 2 ;pts to .QLB extension
; The following three items are order-dependent.
PUBLIC b$ULfsd
PUBLIC b$ULNameLen
PUBLIC b_ULfsd ;Interpreter Reachable Label
PUBLIC b_ULNameLen ;Interpreter Reachable Label
b_ULfsd LABEL WORD ;Interpreter Reachable Label
b$ULfsd DW OFFSET Filename ;Offset of user lib name
DW SEG LOADRTM ;Segment of user lib name
b_ULNameLen LABEL WORD ;Interpreter Reachable Label
b$ULNameLen DW FilenameLength ;Length of user lib name
;
;Definition of Bits for fUserPrompt
;
F_SAVED = 1 ; We have saved the QLIB name (TRUE) vs not been saved (FALSE)
F_PRPATH = 2 ; We should print path with msgs (TRUE) vs. base name only (FALSE)
fUserPrompt DB 0 ; Flags for loading a file.
; The following string descriptors are order dependent.
sdNull DW szNullLength,OFFSET szNull ;string desc for NULL
sdStack DW szStackLength,OFFSET szStack ;string desc for STACK
sdSym DW szSymLength, OFFSET szSym ;string desc for SYMBOLS
sdBSA DW szBSALength, OFFSET szBSA ;string desc for BC_SAB
szNull DB 'NULL',0
szNullLength = $ - szNull
szStack DB 'STACK',0
szStackLength = $ - szStack
szSym DB 'SYMBOL',0
szSymLength = $ - szSym
szBSA DB 'BC_SAB',0
szBSALength = $ - szBSA
; String descriptor for b_ULVars (shared data defined in UL).
sdULVars DW szVarLength,OFFSET szVars ;string desc for b_ULVars
szVars DB 'B_ULVARS',0
szVarLength = $ - szVars
; Note: The Name Buffer Length only needs to be a byte. However by
; wasting one byte here, we save several bytes later in the file by
; not having to clear CH when we do a MOV CX,FNameBuffLen
MaxFNameBuff = 13 ; Maximum length of a filename
DbPub FNameBuff
DbPub FNameBuffLen
FNameBuff DB MaxFNameBuff DUP(?) ;Buffer for filename as it is created
FNameBuffLen DW 1 DUP(0) ;Length of FNameBuff (must be inited)
; The following three items are order-dependent.
DbPub SpecBuffer
InputMaxLen DB SpecBufLength ;max length for DOS 0AH input
InputStrLen DB 1 DUP(?) ;length returned by DOS 0AH input
SpecBuffer DB FILNAML DUP(?) ;buffer for RTM file specification
SpecBufLength = FILNAML -1 -FilenameLength ;max path that will fit
; Error messages are defined in the include file for localization.
INCLUDE messages.inc
;***
;StartupStub - runtime module startup code (RTM Only). Added with [41].
;
;Purpose:
; This code is executed BEFORE the C startup. The RTM is loaded
; (if the program has not been chanined to), and the C startup (in
; the RTM is jumped to).
;Entry:
; DS = ES = PSP of new program.
;Exit:
; RTM loaded if not chaining.
;Uses:
; All.
;Exceptions:
; None
;******************************************************************************
;***
; B$RtmLoad - runtime module loader (RTM Only)
;
;Purpose:
; This code is executed BEFORE the C startup if the program has
; not been chained. The RTM is loaded and DGROUP is built.
;Entry:
; SS = DGROUP of new program.
; ES = LOADRTM
;Exit:
; DS, ES destroyed.
;Uses:
; All
;Exceptions:
; Various errors given if error occurs in loading RTM.
;******************************************************************************
;***
; B$ULLoad - User library loader and initialization (UL Only)
;
;Purpose:
; Added as part of revision [10].
; This code is executed after the C startup. QB4 has parsed the
; command line and called B$IINIT to init the runtime. B$IINIT
; calls B$ULLOAD to load a user library. B$ULLoad will determine
; if a library is to be loaded, load it, and build DGROUP.
;Entry:
; DS = DGROUP of new program.
; SS:SI = ptr to command parameters
; [SI] - UlibNameOffset
; [SI+2] - UlibNameSegment
; [SI+4] - cbLibName
; If [SI] = 0, then no /L was found
; If [SI] = FFFF, then /L without filename found
; else [SI+2]:[SI] = far pointer to filename, [SI+4] = length of filename
;
;Exit:
; DS = ES = DGROUP of new program.
; BP = 0
; b$pULSyms = far pointer to symbol table for user library.
;
;Uses:
; All.
;Exceptions:
; Initialization errors:
; "memory allocation" error
; "disk I/O" error
; "invalid format" error
; "out of memory" error
; "DOS memory arena corrupted" error
;******************************************************************************
; Assume C startup has been done - program memory has been
; cut back to top of STACK.
; Code for user library loader. Set up segment registers.
;***
; ULLoad - Core user library loader (UL Only)
;
;Purpose:
; Added as part of revision [18].
; Does the core user library loading.
;Entry:
; DX:SI = Filename to load
; CX = Length of that file
;Exit:
; AX - end of static data after load.
;Uses:
; All.
;Exceptions:
; Initialization errors:
; "memory allocation" error
; "disk I/O" error
; "invalid format" error
; "out of memory" error
; "DOS memory arena corrupted" error
;******************************************************************************
;***
; Standalone error messages - output and exit to DOS. (RTM and UL)
;
;******************************************************************************
NoFileError:
MOV AX,ER_ULF ;get error number
JMP SHORT PrintError ;jump to give "cannot find file" error
MemAllocError:
MOV AX,ER_ULM ;get error number
JMP SHORT PrintError ;jump to give "memory allocation" error
OutOfMemError:
MOV AX,ER_ULO ;get error number
JMP SHORT PrintError ;jump to give "out of memory" error
ArenaBadError:
MOV AX,ER_DMA ;get error number
JMP SHORT PrintError ;jump to give "Arena trashed" error
InvalidError:
MOV AX,ER_ULI ;get error number
JMP SHORT PrintError ;jump to give "invalid userlib" error
DiskIOError:
MOV AX,ER_ULD ;get error number give "UL disk I/O" error
assumes DS,LOADRTM
PrintError:
PUSH SS
POP DS ;set DS to current DGROUP
assumes DS,DGROUP
PUSH AX ;save error number
MOV AX,ER_ULE ;get number of UL error message preamble
CALL PrintMessage ;print message preamble
CALL PrintFileName ;print file name
MOV AX,ER_ULG ;get number of postamble
CALL PrintMessage ;print message postamble
POP AX ;recover error number
CALL PrintMessage ;Print error message
CMP b$ULSymSeg,0 ;non zero if we have finished initialization
JZ Scram ;brif we haven't finished initialization
JMP B$END ;print error message and terminate
labelFP <PUBLIC,B$IScram> ;Kill QBI entry point
Scram:
cmp cs:fNoIntHooked,0 ; do we have any interrupts hooked?
jnz NoIntHooked ; brif not
push ss ; DS = DGROUP
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -