;       SCCSID = @(#)sswunlok.asm	6.2 91/08/28
         page 60,132
; ****************************************************************************
; *                                                                          *
; *                       IBM/Microsoft Confidential                         *
; *                                                                          *
; *                 Copyright (c) IBM Corporation  1987, 1990                *
; *                 Copyright (c) Microsoft Corp.  1987, 1990                *
; *                           All Rights Reserved                            *
; *                                                                          *
; ****************************************************************************


;*********************** START OF SPECIFICATIONS ***********************/
;                                                                      */
;  SUBROUTINE NAME:  DOSSCRUNLOCK                                      */
;                                                                      */
;  DESCRIPTIVE NAME:  Unlock screen                                    */
;                                                                      */
;  FUNCTION:  Allows process to release a previous lock on the         */
;             screen. If a lock is granted and the process times       */
;             out, then the process is suspended. The unlock is        */
;             intended to prevent this from occurring by having the    */
;             thread release the lock without waiting for a timeout.   */
;             This improves the overall efficiency of the screen       */
;             lock mechanism.                                          */
;                                                                      */
;  NOTES:  Executes on Level 3                                         */
;                                                                      */
;  ENTRY POINT:  DosScrUnLock                                          */
;                                                                      */
;  INPUT:  None                                                        */
;                                                                      */
;  EXIT-NORMAL:  AX = 0                                                */
;                                                                      */
;  EXIT-ERROR:   AX = 1 for screen not previously locked               */
;                                                                      */
;  EFFECTS:  Contents of AX destroyed by return code                   */
;                                                                      */
;  INTERNAL REFERENCES:                                                */
;    ROUTINES:                                                         */
;                                                                      */
;  EXTERNAL REFERENCES:                                                */
;    ROUTINES:  DosSemClear, DosCloseSem, DosGetInfoSeg, DosOpenSem,   */
;               DosSemRequest                                          */
;                                                                      */
;       Change History:                                                */
;                                                                      */
;       @TL6 - 03/01/90 - DCR 704 - Merge SMG/SSW instance data into   */
;                         OS2CHAR                                      */
;       @GDW   08/26/91   PTR B725436 Fix to allow semaphore loop on   */
;                         INTERUPT                                     */
;                                                                      */
;************************ END OF SPECIFICATIONS ************************/

; IF <screen lock is in effect> AND
; IF <the current pid owns the screen lock>
;  Clear variables indicating screen lock
;  Clear locktimersem  (the semaphore used to time a screen lock)
; ELSE
;  AX = error_vio_unlock
; ENDIF

         EXTRN   DOSSEMCLEAR:FAR
         EXTRN   DOSSEMSET:FAR
         EXTRN   DOSSEMWAIT:FAR
         EXTRN   DOSCLOSESEM:FAR
         EXTRN   DOSGETINFOSEG:FAR
         EXTRN   DOSOPENSEM:FAR
         EXTRN   DOSEXITLIST:FAR
         EXTRN   SSOPENSYSEM:NEAR
         EXTRN   SSGETSGCB:NEAR
         EXTRN   DOSSEMREQUEST:FAR
         EXTRN   VIOSETMODE:FAR
         EXTRN   VIOGETMODE:FAR
         EXTRN   VIOSAVE:FAR
         EXTRN   savelocksem:byte
         EXTRN   savelockowner:word
         EXTRN   locktimersem:dword
         EXTRN   screenlocksgid:word
         EXTRN   savelockflag:word
         EXTRN   saveundosem:dword
         EXTRN   struc_length:word
         EXTRN   DOSFSRAMSEMREQUEST:FAR
         EXTRN   DOSFSRAMSEMCLEAR:FAR
         EXTRN   SMG_INSTANCE:DWORD     ; SMG/SSW instance data         ;@TL6

         .xlist
         INCLUDE INFOSEG.INC
         INCLUDE SSWLOCK.INC            ; Screen lock stack frame
         INCLUDE SSWEQUAT.INC
         INCLUDE STRUC.INC
         INCLUDE STDATASG.INC
         INCLUDE SSWSTRUC.INC
         INCLUDE ERROR.INC
         INCLUDE ERROR2.INC
         INCLUDE OS2INST.INC            ; SMG/SSW instance data equates ;@TL6
         .list

.386p

CODE    SEGMENT WORD PUBLIC 'CODE' USE16
        ASSUME  CS:CODE, DS:NOTHING,SS:NOTHING,ES:NOTHING               ;@TL6

         PUBLIC  DOSSCRUNLOCK
         PUBLIC  DOSCLEANUP
DOSSCRUNLOCK    PROC    FAR

         PUSH    BP                    ; ES7/8/87
         MOV     BP,SP                 ; ES7/8/87
         PUSH    SI
         PUSH    DI
         PUSH    CX
         PUSH    DX
         PUSH    BX
         PUSH    DS
         PUSH    ES

        .IF <SS:[BP].unlockviohandle e 0>   ; 6/4/87

;@TL6    MOV     AX,INDATASG            ; Get
                                        ;addressability to
                                        ;instanced data
;@TL6    MOV     ES,AX
         MOV     AX,STDATASG
         MOV     DS,AX
         LES     SI,DS:SMG_INSTANCE                                     ;@TL6
         MOV     BX,ES:[SI].in_procid                                   ;@TL6
         MOV     DI,ES:[SI].in_di_reg                                   ;@TL6
         .IF <[DI].sglockineffect ne 0> AND  ; If there is a lock on
         .IF <BX e [DI].sglockineffect>
            MOV     [DI].sglockineffect,0  ; No more lock
            MOV     [DI].kbdowner,0        ; Clear temp flag ES7/15/87
            PUSH    DS
            PUSH    OFFSET locktimersem
            CALL    DOSSEMCLEAR
         .ELSE
            MOV     AX,error_vio_unlock  ; Return an error
         .ENDIF
        .ELSE                                     ; ES7/8/87
            MOV     AX,error_vio_invalid_handle   ; ES7/8/87
        .ENDIF                                    ; ES7/8/87

         POP     ES
         POP     DS
         POP     BX
         POP     DX
         POP     CX
         POP     DI
         POP     SI
         POP     BP

         RET                            ; Return to caller

DOSSCRUNLOCK    ENDP
;---------------------------------------------------------------------------

; Set up pointers to instanced data
; IF <savelockowner eq 0>
;  DOSSEMSET (savelocksem)
; ELSEIF <current procid is not the savelockowner>
;  DOSSEMWAIT (on savelocksem)
; ENDIF
; Set up current procid as savelockowner
; Set up sgcb pointer
; IF <sglockineffect e current procid>
;  clear sglockineffect and sgprocessfrozen variables
; ENDIF
; IF <kbdowner e current procid>
;  Clear kbdowner variable
; ENDIF
; IF <saverestpid is the current process> OR
; IF <saverestpid eq 0>
;  IF <saverestpid in instanced data ne 1>
;   Clear saverestpid variable in the sgcb
;  ENDIF
;  Reset variables
;  Set a variable to alert the DOSSAVE module that there is a problem
;  DOSSEMCLEAR (saveredrawsem)
; ENDIF
; IF <savemodepid is the current process> OR
; IF <savemodepid eq 0>
;  Clear the appropriate variables
;  DOSSEMCLEAR (savemodesem)
;  DOSSEMCLEAR (saveundosem)
; ENDIF
; DOSSEMCLEAR (savelocksem)
; Clear the ownership variables
; DOSEXITLIST



DOSCLEANUP      PROC    FAR             ; In case the calling process dies

;@TL6    MOV     AX,INDATASG
;@TL6    MOV     ES,AX
         MOV     AX,STDATASG
         MOV     DS,AX
         LES     SI,DS:SMG_INSTANCE     ; Gain access to instance data  ;@TL6


         .repeat                                                        ;@GDW
           PUSH    DS
           PUSH    OFFSET savelocksem
           PUSH    dword ptr timeout                                    ;CJ10
;CJ10      PUSH    timeout
           CALL    DOSFSRAMSEMREQUEST
         .until  <ax ne ERROR_INTERRUPT>                                ;@GDW

         MOV     savelockflag,0CH

         MOV     DI,ES:[SI].in_di_reg                                   ;@TL6
         MOV     AX,ES:[SI].in_procid                                   ;@TL6
         .IF <[di].sglockineffect e AX>
            MOV     [di].sglockineffect,0
            MOV     [di].sgprocessfrozen,0
         .ENDIF
         .IF <[di].kbdowner e AX>
            MOV     [di].kbdowner,0
         .ENDIF
         PUSH    AX
         .IF <[di].saverestpid e AX> OR
         .IF <[di].saverestpid e 0>
          .IF<ES:[SI].in_saverestpid ne 1>   ; 9/26/86                  ;@TL6
            MOV     [di].saverestpid,0
          .ENDIF                        ; 9/26/86
            MOV     [di].saveresthreadid,0
            MOV     [di].scrnkillindicator,-1
            MOV     [di].scrnactionflag,-1
            OR      [di].saverestflags,1  ; Tell save there's a problem

;@TL6       MOV     cx,di
            LEA     cx,[di].saveredrawsem                               ;@TL6
            PUSH    ds
            PUSH    cx
            CALL    DOSSEMCLEAR         ; thread
         .ENDIF
         POP     AX
         .IF <[di].savemodepid e AX> OR
         .IF <[di].savemodepid e 0>
            MOV     [di].savemodepid,0
            MOV     [di].savemodethreadid,0
            MOV     [di].modekillindicator,-1
            MOV     [di].modeactionflag,-1
            MOV     [di].savemodeflags,0

;@TL6       MOV     cx,di
            LEA     cx,[di].savemodesem                                 ;@TL6
            PUSH    ds
            PUSH    cx
            CALL    DOSSEMCLEAR         ; thread

            PUSH    ds                  ; Clear block of undo calls
            PUSH    OFFSET saveundosem
            CALL    DOSSEMCLEAR

         .ENDIF

         PUSH    DS
         PUSH    OFFSET savelocksem
         CALL    DOSFSRAMSEMCLEAR

         MOV     screenlocksgid,0       ; of screen lock

         PUSH    3
         PUSH    DWORD PTR 0                                            ;CJ10
;CJ10    PUSH    0
         CALL    DOSEXITLIST


DOSCLEANUP      ENDP

CODE    ENDS                                                            ;@TL6
         END
