;*DDK*************************************************************************/
;
; COPYRIGHT (C) Microsoft Corporation, 1989
; COPYRIGHT    Copyright (C) 1995 IBM Corporation
;
;    The following IBM OS/2 WARP source code is provided to you solely for
;    the purpose of assisting you in your development of OS/2 WARP device
;    drivers. You may use this code in accordance with the IBM License
;    Agreement provided in the IBM Device Driver Source Kit for OS/2. This
;    Copyright statement may not be removed.;
;*****************************************************************************/

;/*****************************************************************************
;*
;* SOURCE FILE NAME = STHUNK.ASM
;*
;* DESCRIPTIVE NAME = Seamless Thunks
;*
;*
;* VERSION      V2.0
;*
;* DATE         02/22/92
;*
;* DESCRIPTION  Seamless Thunks for the cursor exclude functions.
;*
;*
;* FUNCTIONS   far_unexclude16
;*             FAR_EXCLUDE16
;*
;*
;*
;* NOTES        NONE
;*
;* STRUCTURES   NONE
;*
;* EXTERNAL REFERENCES
;*
;*              NONE
;*
;* EXTERNAL FUNCTIONS
;*
;*              NONE
;*
;* CHANGE ACTIVITY =
;*   DATE      FLAG        APAR   CHANGE DESCRIPTION
;*   --------  ----------  -----  --------------------------------------
;*   mm/dd/yy  @Vr.mpppxx  xxxxx  xxxxxxx
;*   02/22/92                     File Compiled Sat Feb 22 11:10:27 1992
;*                                Command Line: x:\tools\thunk prk.thk
;*
;*****************************************************************************/


;/*
;**       Static Name Aliases
;*/

        TITLE   $prk.asm

        .386
        DINCL_BITMAP            equ     1
        DINCL_EGAMEM            equ     1
        DINCL_ENABLE            equ     1
        include pmgre.inc
        include driver.inc
        include extern.inc
        include cursors.inc
        include egafam.inc
        INCLUDE pointer.inc
        include curstrc.inc

EXTERNDEF CurData:CURSORSTRUCT

;/*
;**       Special Equate required until selector values are defined
;*/

THK32R2SS       EQU     04ah

PUBLIC  FAR_EXCLUDE16
PUBLIC  INIT_HW_REGS16

_PtrData32 SEGMENT DWORD PUBLIC USE32 'DATA'
_PtrData32 ENDS

_TEXT   SEGMENT USE32 PUBLIC 'CODE'
        EXTRN   FAR_EXCLUDE:NEAR
        EXTRN   INIT_HW_REGS:NEAR
_TEXT   ENDS

;/*
;** *********** FAR_EXCLUDE16 -> FAR_EXCLUDE ***********
;*/

;/*
;**Create a dummy label to trick MASM into correct fixups
;*/

_TEXT   SEGMENT USE32
        ALIGN   4
T_FAR_EXCLUDE   LABEL FAR
_TEXT   ENDS

EXTERNDEF SeamlessStackEnd:BYTE

_DATA   SEGMENT USE32 PUBLIC 'DATA'
_DATA   ENDS

_SEAMCODE16     SEGMENT PARA USE16 PUBLIC 'CODE'
far_unexclude16 PROC FAR16 SYSCALL USES EAX DS

        mov     ax,SEG FLAT:_DATA
        mov     ds,ax

        ASSUME  DS:FLAT

        LEA     EAX,FLAT:CurData
        MOV     [EAX].CURSORSTRUCT.ExcludeCt,RECT_NOT_PRES

        ASSUME  DS:NOTHING
        ret
far_unexclude16 ENDP


ASSUME CS:_SEAMCODE16
        ALIGN   4

FAR_EXCLUDE16   PROC    FAR

        push    ds
        push    es
        mov     bx,ss
        rol     ebx,16
        mov     bx,sp   ;ebx is now = ss:sp
        mov     ax,SEG FLAT:_DATA
        cli
        mov     ds,ax           ; FLAT selector in DS,
        mov     es,ax           ;   ES, &
        mov     ss,ax           ;   SS
        mov     esp,offset FLAT:SeamlessStackEnd

;/*
;** Now on 32-bit stack
;*/

        push    ebx
        mov     ebx,55555555h
        movzx   ecx,cx
        movzx   edx,dx
        movzx   edi,di
        movzx   esi,si
        jmp     FAR PTR FLAT:C_FAR_EXCLUDE

        ALIGN   4

RET_FAR_EXCLUDE16::
        pop     eax
        mov     dx,ax
        rol     eax,16
        mov     ss,ax
        movzx   esp,dx
        ;;Now on 16-bit stack
        sti
        pop     es
        pop     ds
        ret

        xor     ax,ax
C_FAR_EXCLUDE16:
        push    ebp
        mov     bp,sp
        push    ax
        push    ds
        push    es
        movzx   eax,sp
        push    ss
        push    DWORD PTR 0                       ;storage for esp value

;/*
;** ****> BEGIN Ptr/Structure Section
;*/


;/*
;** ****> END Ptr/Structure Section
;*/

;/*
;** Create new call frame, using 32-bit semantics.
;*/
        and     sp,0FFFCh                        ;dword align stack
;/*
;** Generic Routine: get function number into cx
;*/
        mov     cx,[bp-2]
        movzx   ecx,cx
        mov     ax,ss
        shr     ax,3
        shl     eax,16
        mov     ax,bp   ;eax now holds ebp
        mov     ebp,eax
;/*
;** now convert stack pointer
;*/
        mov     ax,sp   ;eax now holds esp
;/*
;** based on current SS CPL bits we need to load new segregs
;*/
        mov     dx,ss
        and     dx,03h
        cmp     dx,03h
        jne     L2
        push    SEG FLAT:_DATA                   ;push Ring 3 selector
        mov     dx,SEG FLAT:_DATA
        jmp     L3
L2:                                          ;if not ring3, then must be ring2
        push    THK32R2SS                        ;push Ring 2 selector
        mov     dx,SEG FLAT:_DATA
;/*
;** Switch the segments.
;*/

L3:
        push    eax     ;push new esp onto stack
        movzx   esp,sp
        mov     [bp-12],esp                       ;store return esp value
        lss     esp,[esp]                        ; ss:esp = 32-bit ptr
        mov     ds,dx
        mov     es,dx
;/*
;** Jump to 32-bit segment to issue call.
;*/
        jmp     FAR PTR FLAT:T_FAR_EXCLUDE

;/*
;** The following are entry points for routines that
;** have the same semantics and parameters.
;*/

        ALIGN   4
INIT_HW_REGS16::
        ret
        mov     ax,1
        jmp     C_FAR_EXCLUDE16
        ALIGN   4
R_FAR_EXCLUDE16::       ; label defining return jmp location
;/*
;** Restore 16-bit SS:SP.
;*/

        lss     esp,[ebp-12]


;/*
;** Convert Return Code
;** Return type maps directly.
;*/


L4:

;/*
;** ****> BEGIN Pointer/Structure Unpack Section
;*/


;/*
;** ****> END Ptr/Structure Unpack Section
;*/

;/*
;** 16-bit return code.
;*/

        lea     sp,[bp-6]
        pop     es
        pop     ds
        mov     sp,bp
        pop     ebp
        ret
FAR_EXCLUDE16 endp

_SEAMCODE16     ENDS


;/*
;** 32-bit code to make API call.
;*/

_TEXT   SEGMENT
        ASSUME DS:FLAT,ES:FLAT
        .errnz ($ - T_FAR_EXCLUDE)
        mov     eax,offset FLAT:T_FAR_EXCLUDE16
        call    DWORD PTR cs:[eax+ecx*4]
        jmp     FAR PTR R_FAR_EXCLUDE16
T_FAR_EXCLUDE16:
        dd      offset FLAT:FAR_EXCLUDE
        dd      offset FLAT:INIT_HW_REGS

C_FAR_EXCLUDE:
        mov     eax,offset FLAT:T_FAR_EXCLUDE16
        call    DWORD PTR cs:[eax]
        jmp     FAR PTR _SEAMCODE16:RET_FAR_EXCLUDE16

_TEXT   ENDS
        END
