windll.asm

来自「开放源码的编译器open watcom 1.6.0版的源代码」· 汇编 代码 · 共 552 行 · 第 1/2 页

ASM
552
字号
;*****************************************************************************
;*
;*                            Open Watcom Project
;*
;*    Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
;*
;*  ========================================================================
;*
;*    This file contains Original Code and/or Modifications of Original
;*    Code as defined in and that are subject to the Sybase Open Watcom
;*    Public License version 1.0 (the 'License'). You may not use this file
;*    except in compliance with the License. BY USING THIS FILE YOU AGREE TO
;*    ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
;*    provided with the Original Code and Modifications, and is also
;*    available at www.sybase.com/developer/opensource.
;*
;*    The Original Code and all software distributed under the License are
;*    distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
;*    EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
;*    ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
;*    MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
;*    NON-INFRINGEMENT. Please see the License for the specific language
;*    governing rights and limitations under the License.
;*
;*  ========================================================================
;*
;* Description:  C/C++ Windows 386 Supervisor DLL startup code (16-bit).
;*
;*****************************************************************************


;****************************************************************************
;***                                                                      ***
;*** WINDLL.ASM - windows 32-bit dll                                      ***
;***                                                                      ***
;****************************************************************************
.386p

 DGROUP group _NULL,_DATA,DATA,_emu_init_start,_emu_init,_emu_init_end,_BSS

public  pLocalHeap
public  pAtomTable
public  pStackTop
public  pStackMin
public  pStackBot

pLocalHeap      equ     0006H
pAtomTable      equ     0008H
pStackTop       equ     000AH
pStackMin       equ     000CH
pStackBot       equ     000EH


        .DOSSEG

_BSS          segment word public 'BSS' use16
_BSS          ends

DATA    segment word public 'DATA' use16
DATA    ends
_emu_init_start segment word public 'EMU' use16
__emu_init_start label word
_emu_init_start ends

_emu_init segment byte public 'EMU' use16
_emu_init ends

_emu_init_end segment word public 'EMU' use16
__emu_init_end label word
_emu_init_end ends

_NULL   segment para public 'BEGDATA' use16
__nullarea label word
           dw   0,0
           dw   5
           dw   0               ; pLocalHeap
           dw   0               ; pAtomTable
__STACKLOW dw   0               ; pStackTop: lowest address in stack
__STACKTOP dw   0               ; pStackMin:
           dw   0               ; pStackBot: highest address in stack
        public  __nullarea
_NULL   ends

_DATA segment word public 'DATA' use16
;*
;*** externals we need
;*
assume es:nothing
assume ss:nothing
assume ds:dgroup
assume cs:_TEXT
extrn   Fini_:proc
extrn   _DataSelector:WORD
extrn   _StackSelector:WORD
extrn   _EntryStackSave:DWORD
extrn   _ReturnCode:DWORD
extrn   _SaveSP:DWORD
extrn   _StackSize:DWORD
extrn   _EDataAddr:DWORD
extrn   _CodeEntry:FWORD
extrn   __DLLEntryAddr:DWORD
extrn   __WEPAddr:DWORD

__aaltstkovr dw -1              ; alternate stack overflow routine address
__curbrk   dw 0                 ; top of usable memory
__psp      dw 0                 ; segment addr of program segment prefix
__osmajor  db 0                 ; major DOS version number
__osminor  db 0                 ; minor DOS version number
__child    dw 0                 ; non-zero => a spawned process is running
__no87     dw 0                 ; always try to use the 8087
__FPE_handler dd 0              ; FPE handler
__HShift   db 0                 ; Huge Shift value
__osmode   db 1                 ; mode
__WEPflag  db 0                 ; non-zero => WEP has been run

PUBLIC  _InDebugger
_InDebugger     dw 0


        public  __osmode
        public  __curbrk
        public  __psp
        public  __osmajor
        public  __osminor
        public  __STACKLOW
        public  __STACKTOP
        public  __child
        public  __no87
        public  "C",__FPE_handler
        public  __HShift

DLLRoutine      LABEL FWORD
DLLEIP          dd 0
DLLCS           dw 0
_DATA ends

extrn LOCALINIT:FAR

;*
;*** the windows extender code lies here
;*
_TEXT segment word public 'CODE' use16

public          _small_code_
_small_code_    equ 0

;****************************************************************************
;***                                                                      ***
;*** LibEntry - 16-bit library entry point                                ***
;***                                                                      ***
;****************************************************************************
extrn LibMain:FAR
PUBLIC LibEntry
LibEntry PROC FAR
__DLLstart_:
        public  __DLLstart_

        mov     ax,ds
        nop
        inc     bp
        push    bp
        mov     bp,sp
        push    ds
        mov     ds,ax
        push    di              ; handle of the module instance
        push    ds              ; library data segment
        push    cx              ; heap size
        push    es              ; command line segment
        push    si              ; command line offset
        jcxz    callc           ; skip heap init
        xor     ax,ax
        push    ds
        push    ax
        push    cx
        call    LOCALINIT
        or      ax,ax           ; did it do it ok ?
        jz      error1           ; quit if it failed

callc:
        call    LibMain         ; invoke the 'C' routine (result in AX)
        jmp     short exit      ; LibMain is responsible for stack clean up

error1:

        pop     si               ; clean up stack on a LocalInit error
        pop     es
        pop     cx
        pop     ds
        pop     di
        jmp     short exit
__exit_with_msg_:
        mov     ah,04cH                 ; DOS call to exit with return code
        int     021h                    ; back to DOS

        public  __exit_with_msg_
exit:

         lea    sp,-2H[bp]
         pop    ds
         pop    bp
         dec    bp
         retf
LibEntry ENDP

        assume ds:nothing
dsvalue dw      DGROUP
;****************************************************************************
;***                                                                      ***
;*** WEP - end procedure, called when dll is unloaded                     ***
;***                                                                      ***
;****************************************************************************
        public  WEP
WEP     proc    far
        inc     bp                      ; indicate far call
        push    bp                      ; save bp
        mov     bp,sp                   ; get access to parm
        push    ds                      ; save ds
        mov     ds,cs:dsvalue           ; get our DS value
        assume  ds:DGROUP
        cmp     byte ptr __WEPflag,0    ; quit if WEP already run
        jne     short WEP_exit          ; ...
        inc     byte ptr __WEPflag      ; set flag
        mov     eax,__WEPAddr           ; get addr of 32-bit __WEP routine
        or      eax,eax                 ; check for NULL routine
        je      short no_WEP            ; skip if no WEP routine defined
        sub     eax,eax                 ; zero 32-bit register
        mov     ax,6[bp]                ; get parm
        mov     word ptr [_EntryStackSave],sp   ; save 16-bit stack pointer
        mov     word ptr [_EntryStackSave+2],ss ; ...
        mov     dx,word ptr _CodeEntry+4; get 32-bit CS
        mov     es,_DataSelector        ; load 32-bit DS
        mov     ss,_StackSelector       ; switch to 32-bit stack
        mov     esp,_SaveSP             ; ...
        push    edx                     ; push 32-bit CS
        push    __WEPAddr               ; push address of __WEP routine
        push    _EntryStackSave         ; save 16-bit stack pointer
        mov     ds,_DataSelector        ; load 32-bit DS
        call    fword ptr 4[esp]        ; call __WEP
        lss     sp,[esp]                ; switch back to 16-bit stack
no_WEP: push    0                       ; indicate no message
        call    Fini_                   ; do final cleanup
        add     sp,2                    ; clean up stack
WEP_exit:mov    ax,1                    ; indicate success
        pop     ds                      ; restore ds
        pop     bp                      ; restore bp
        dec     bp                      ; decrement bp
        ret     2                       ; return
WEP     endp

        DLL_Entry       macro   num
        public  DLL&num
DLL&num proc    near
        call    __DLL_entry
        nop
DLL&num endp
        endm

        DLL_Entry       1
        DLL_Entry       2
        DLL_Entry       3
        DLL_Entry       4
        DLL_Entry       5
        DLL_Entry       6
        DLL_Entry       7
        DLL_Entry       8
        DLL_Entry       9
        DLL_Entry       10
        DLL_Entry       11
        DLL_Entry       12
        DLL_Entry       13
        DLL_Entry       14
        DLL_Entry       15
        DLL_Entry       16
        DLL_Entry       17
        DLL_Entry       18
        DLL_Entry       19

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?