📄 woainit.asm
字号:
;/*
; * Microsoft Confidential
; * Copyright (C) Microsoft Corporation 1985-1991
; * All Rights Reserved.
; */
;----------------------------------------------------------------------------;
; This file has most of the initialization code. All the procedures in this ;
; file are needed only during the initialization phase and are defined in a ;
; main code segment. WOA will ignore this segment when it does swapping etc ;
; as all of the code in this segment id discardable in any case. ;
; ;
; History: ;
; ;
; Fri June-15-1990. -by- Amit Chatterjee [amitc] ;
; Adapted for the Dos Task Switcher. ;
; ;
; Thu May-03-1990. -by- Amit Chatterjee [amitc] ;
; Created for Windows. (Added the History legend) ;
;----------------------------------------------------------------------------;
?win = 0
?DF = 1
.xlist
include cmacros.inc
include woasegs.inc
include macros.mac
include njmp.mac
include woaerr.inc
include woakeys.inc
include dosx.inc
include grabber.inc
include woaswch.inc
.list
.8086 ;must have to run on 8086s too.
;----------------------------------------------------------------------------;
; define the external function calls. ;
;----------------------------------------------------------------------------;
;-------------------------------------------------------;
; external FAR OLDAPP procedures. ;
;-------------------------------------------------------;
;----------------------------------------------------------------------------;
sBegin Data
;-------------------------------------------------;
; declare all external data seg variables. ;
;-------------------------------------------------;
externB DataSegEnd ;end of _DATA segment
externB EmsFlag ;EMS present or not.
externB XmsFlag ;XMS present or not
externB SwitcherColors ;colors for switcher screen
externB WoaSwap1Path ;first swap path.
externB WoaSwap2Path ;second swap path.
externW Swap1MinK ;min size to be left on 1st path
externW Swap2MinK ;min size to be left on 2nd path
externB ErrorType ;WOA error type
externW hApp ;window handle for this instance
externB CurrentPathId ;swap path id for current AP.
externB StartRestartId ;start or restart
externW HighMemXmsHandle ;handle of the high mem XMS block
externW StubSegSize ;size of real mode stub segment
externW WoaCsSize ;size of protected mode code seg
externW WoaDsSize ;size of winoldap data segment
externD XmsBankSize ;size of XMS to be allocated
externW XmsHeapWalkSel ;scratch selector for walking xms heap
externW WoaStubSel ;sel for current loaction of stub code
externW ArenaWalkSel ;temp selector for walkimg arena chain
externW ArenaRWSel ;temp sel for reading/writing arenas
externW AppXmsBaseSel ;selector to base of apps XMS block
externB DosAppSwapFileName ;app swap file name
externW DosAppNumber ;app number to be run in this instance
externB FileTemplate ;for deleting files
externB WoaSwapFilePrefix ;'~WOA'
externB DiskSwap1Drive ;swap drive index for drive 1
externB DiskSwap2Drive ;swap drive index for drive 1
externD lpXmsControl ;XMS control function address
externW AppMinMem ;minimum memory required
externW AppMinXmsK ;minimum XMS memory required
externW AppMaxXmsK ;maximum xms required
externW LowMemSel ;pointer to start of block
externB LowMemBlockType ;type of the low mem block
externW LowMemArenaSel ;pointer to its arena
externW LowMemParaSize ;size of available low memory in para
externD HighMemSize ;size of available high heap
externW WoaPDBSeg ;WOA's PSP
externW SegResizeBlock ;block to resize in real mode
externW SizeReservedArea ;size of area reserved area at heap st.
externW UsableLowHeapSel ;sel/seg for reusable part of low heap
externW SegAfterReservedArea ;segment after the reserved area
externW StartScreenLines ;startup no of screen lines
externB SwitcherID ;ID of this switcher (bits 14 & 15)
;-------------------------------------------------------;
; define any locally used constants. ;
;-------------------------------------------------------;
;-------------------------------------------------------;
; define any external constants. ;
;-------------------------------------------------------;
externA IS_WINOLDAP_ACTIVE ;(WOAMGR.ASM)
;------------------------------------------------------;
; define public names. ;
;------------------------------------------------------;
public GetSegmentLimits
sEnd Data
;----------------------------------------------------------------------------;
; declare external FAR Winoldap procedures. ;
;----------------------------------------------------------------------------;
externFP ErrorHandler ;(WOAMGR.ASM)
externFP FarCopyBasicSwap1FileName ;(WOAMGR.ASM)
externFP FarCopyBasicSwap2FileName ;(WOAMGR.ASM)
externFP FarAppendUniqueNumber ;(WOAMGR.ASM)
;----------------------------------------------------------------------------;
; Declare the the code segment and any labels that we want to refernce in it;
;----------------------------------------------------------------------------;
;-------------------------------------------------;
; define external data references. ;
;-------------------------------------------------;
sBegin Code
externB CodeSegEnd ;end of _TEXT segment
sEnd Code
sBegin StubSeg
;----------------------------------------------------------------------------;
; declare external data refernces. ;
;----------------------------------------------------------------------------;
externB WoaGrabberName ;(WOARLM.ASM)
externB WoaGrabberSwapPath ;(WOARLM.ASM)
externB WoaPath ;(WOARLM.ASM)
externB WoaParams ;(WOARLM.ASM)
externB WoaFcb1 ;(WOARLM.ASM)
externB WoaFcb2 ;(WOARLM.ASM)
externB Woa6fValue ;(WOARLM.ASM)
externB WoaIrq9Global ;(WOARLM.ASM)
externB WoaNetAsyncSwitching ;(WOARLM.ASM)
externW WoaCpuType ;(WOARLM.ASM)
externW WoaFileEntrySize ;(WOARLM.ASM)
externB WoaBehavior ;(WOARLM.ASM)
externB WoaHotKeys ;(WOARLM.ASM)
externW WoaStartScreenLines ;(WOARLM.ASM)
externB WoaAltTabDisabled ;(WOARLM.ASM)
externB WoaShftAltTabDisabled ;(WOARLM.ASM)
externB WoaAltEscDisabled ;(WOARLM.ASM)
externB WoaShftAltEscDisabled ;(WOARLM.ASM)
externB WoaCtrlEscDisabled ;(WOARLM.ASM)
externB WoaSwitcherID ;(WOARLM.ASM)
sEnd StubSeg
;----------------------------------------------------------------------------;
sBegin StubSeg
; InitStartLine MUST be at the very start of the one time initialization code,
; it is the address which will be used to discard the one time initialization
; code after itis done.
public InitStartLine
InitStartLine equ $ ;MAKE ME FIRST! Everything after this will
; be discarded after initialization
externB XmsStartLine ;start of XMS handler in real mode stub
externB StubSegEnd ;end of _WOARLMSEG segment
;-------------------------------------------------;
; define local entry points ;
;-------------------------------------------------;
assumes cs,StubSeg
assumes ds,Data
assumes es,nothing
;----------------------------------------------------------------------------;
; define temporary strings. ;
;----------------------------------------------------------------------------;
szEmsName db 'EMMXXXX0' ;EMM device name
;----------------------------------------------------------------------------;
; define local constants. ;
;----------------------------------------------------------------------------;
CMD_LINE_PARAM_LEN equ 2 ;length of command line param
VALID_CMD_LINE_PARAM equ 0FE20H ;valid parameter
;----------------------------------------------------------------------------;
; include the HELP text message. This is a separate file for international ;
; conversions. ;
;----------------------------------------------------------------------------;
include woahelp.inc
;----------------------------------------------------------------------------;
; ParseCommandLine: ;
; ;
; DOSSWAP expects a special parameter from the DOSSHELL which tells it that ;
; it is being run from the SHELL and not from a DOS prompt. This is actually ;
; a space followed by a special character which is kinda difficult to type ;
; in from the keyboard (At this point it is 0FEH, 08H would probably have ;
; been the best!). If we do not find this special parameter, we will print ;
; out a help text and exit. ;
;----------------------------------------------------------------------------;
cProc ParseCommandLine,<FAR,PASCAL,PUBLIC>
cBegin
; command line shoule be at DS:80H.
mov si,80h ;default DTA address
lodsb ;get length of command line
cmp al,CMD_LINE_PARAM_LEN ;is it the length that we expect ?
jnz PCL_PrintHelpText ;no, print help text and exit
; check the validity of the parameter.
lodsw ;get the next two words
.errnz CMD_LINE_PARAM_LEN - 2
cmp ax,VALID_CMD_LINE_PARAM ;is it the one that we expect ?
jz PCL_Ret ;yes, carry is clear too.
PCL_PrintHelpText:
; we don't expect any parameters. Simply print an error message an exit
push ds ;save
push cs
pop ds ;ds points has stub seg
mov dx, StubSegOFFSET HelpText
mov ah,9
int 21h ;print help message
pop ds ;restore
stc ;error exit, but no error code
PCL_Ret:
cEnd
;----------------------------------------------------------------------------;
; InitializeWoa: ;
; ;
; This routine setus up some WOA variables by reafing SYSTEM.INI etc. This ;
; code is executed only once and the advantage of having it in a separate ;
; code segment is that we will ignore all the code in this segment after ;
; the initializations are done. ;
;----------------------------------------------------------------------------;
cProc InitializeWoa,<FAR,PASCAL,PUBLIC>
parmW StartRestart ;start or restart
cBegin
;----------------------------------------------------------------------------;
; find out if EMS is present or not, setting flag appropriately. ;
;----------------------------------------------------------------------------;
mov ax,3567h ;want to get INT 67 vector
int 21h ;ES:BX has the vector
mov di,10 ;want to inspect offset 10
mov si,StubSegOFFSET szEmsName ;DS:SI points to exepected name
mov cx,8 ;need to compare 8 bytes
cld ;set proper direction flag
push ds ;save
smov ds,cs ;load code
repz cmpsb ;compare names
pop ds ;restore
jnz @f ;names do not match, driver absent
mov EmsFlag,0ffh ;EMS driver prsent
@@:
;----------------------------------------------------------------------------;
; Parse the FCBS in the command line for the EXEC call. ;
;----------------------------------------------------------------------------;
cmp StartRestart,1 ;if restart
jz @f ;skip this
mov si,StubSegOFFSET WoaParams+1 ;point to the parameters
mov di,StubSegOFFSET Woafcb1 ;fill in the first FCB
smov es,cs ;all in same segment
mov ax,2901h
int 21h ;PARSE DOS call
call find_next_arg ;looks for further args
jnz @f ;no second parameter
mov di,StubSegOFFSET Woafcb2
mov ax,2901h
int 21h ;parse and fill in fcb2
@@:
; deal with memory requirements.
cCall AllocateXms ;allocate all of XMS if HIMEM is loaded
; check for extended memory requirements, if the requirements are not
; satisfied, invoke the error handler and never return.
cCall CheckXmsRequirements ;XMS memory requirement tests
; now get the sizes of various segments etc.
; get the limit fields and save them
call GetSegmentLimits ;set segment limits -- sets StubSegSize
cmp StartRestart,0 ;is it start ?
jnz @f ;yes
; now test to see if the applications conventional and extended mode memory
; requirements can be satisfied or not. If memory requrements cannot be met,
; the following routine will never return
call IsThereEnoughMemory ;check conventional/XMS mem requirements
@@:
clc ;no error
cEnd
;----------------------------------------------------------------------------;
; IsThereEnoughMemory: ;
; ;
; This routine checks to see if enough memory can be released to meet the ;
; apllications conventional. ;
;----------------------------------------------------------------------------;
IsThereEnoughMemory proc near
xor ax,ax ;initialize size of resident area
; now in the resident area of conventional memory the main code and data
; segments will allways be resident in real mode winoldap (this is not true for
; protected mode winoldap). So initialize the size of the real mode resident
; area with the size of the main code and data segments.
mov ax,WoaCsSize ;size of the main code segment
add ax,WoaDsSize ;add in the size of the data segment
;----------------------------------------------------------------------------;
; code independent of real or protected mode. ;
;----------------------------------------------------------------------------;
; now check convetional memory requirements.
mov bx,AppMinMem ;get minimum req. in KB
cmp bx,0 ;was minimum limit specified ?
jz ThereIsEnoughMemory ;memory requirements will be met
; get the size of the stub segment
add ax,StubSegSize ;size of the stub seg
; bx has the minimum memory required in Kbytes, we need to mutiply that by 64
; to get the number of paragraphs.
shiftr ax,4 ;get number of paragraphs
inc ax ;round up
shiftl bx,6 ;ax has min requirement in paragraphs
; if there is not enough memory to run the application, get out and complain
neg ax ;need to subtract from total memory
add ax,LowMemParaSize ;size of low heap area
cmp bx,ax ;is there enough memory
jbe ThereIsEnoughMemory ;yes there is
; we cannot run the appilaction
mov ErrorType,ER_LOW_MEMORY ;error type
jmp ErrorHandler ;get out
ThereIsEnoughMemory:
ret
IsThereEnoughMemory endp
;----------------------------------------------------------------------------;
; GetSegmentLimits: ;
; ;
; This routine gets the limits of the various winoldap segments. It also ;
; obtains the sel values for the block allocated to the switcher by Dos and ;
; also it's size and a sel for it's arena. ;
;----------------------------------------------------------------------------;
GetSegmentLimits proc near
push es ;save
mov ax,CodeOFFSET CodeSegEnd;end label in _TEXT segment
add ax,15 ;take into next para
and ax,0fff0h ;paragraph allign
mov WoaCsSize,ax ;save it
mov ax,DataOFFSET DataSegEnd;end label in _DATA segment
add ax,15 ;take into next para
and ax,0fff0h ;paragraph allign
mov WoaDsSize,ax
; if the XMS handler is not needed we will discard it.
mov bx,StubSegOFFSET InitStartLine ;discardable code line
mov ax,wptr XmsBankSize ;if there is an XMS requirement
or ax,wptr [XmsBankSize+2] ; the XMS handler can't be
jnz @f
mov bx,StubSegOFFSET XmsStartLine ;discard XMS code
@@:
add bx,15 ;take into next para
and bx,0fff0h ;paragraph allign
mov StubSegSize,bx ;usable stub area
pop es ;restore es
mov ah,62h ;get PSP
int 21h ;BX has the PSP segment
mov WoaPDBSeg,bx ;save it
mov LowMemSel,bx ;save it
dec bx ;point to the arena
mov LowMemArenaSel,bx ;save it
push es ;save
mov es,bx ;point to the arena
mov ax,es:[3] ;get the size of block in paragraphs
mov LowMemParaSize,ax ;save it
mov al,es:[0] ;get the block type
mov LowMemBlockType,al ;save it too
pop es ;restore
; save the sel for the block that will be resized.
mov ax,LowMemSel ;selector for the block
mov SegResizeBlock,ax ;save it.
; get the maximum of the 3 segments.
mov ax,_TEXT ;get code segment
mov bx,WoaCsSize ;and its size
cmp ax,DGROUP ;compare with DS seg
ja @f ;no need to swap
mov ax,DGROUP ;load ds
mov bx,WoaDsSize ;load ds's size
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -