home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 9 / 09.iso / l / l040 / 13.ddi / RTLSYS.ZIP / DAPP.ASM < prev    next >
Encoding:
Assembly Source File  |  1992-10-28  |  8.3 KB  |  393 lines

  1.  
  2. ; *******************************************************
  3. ; *                            *
  4. ; *     Turbo Pascal Run-time Library                   *
  5. ; *    DPMI Application Main module            *
  6. ; *                            *
  7. ; *     Copyright (c) 1988,92 Borland International     *
  8. ; *                            *
  9. ; *******************************************************
  10.  
  11.     TITLE    DAPP
  12.  
  13.     INCLUDE    SE.ASM
  14.  
  15. DATA    SEGMENT WORD PUBLIC
  16.  
  17. ; Externals
  18.  
  19.     EXTRN    Input:BYTE,Output:BYTE,SaveInt00:DWORD
  20.     EXTRN    SelectorInc:WORD,Seg0040:WORD,SegA000:WORD
  21.     EXTRN    SegB000:WORD,SegB800:WORD,RealModeRegs:BYTE
  22.     EXTRN    ExitProc:DWORD,PrefixSeg:WORD,HInstance:WORD
  23.     EXTRN    ExitCode:WORD,ErrorAddr:DWORD,Test8086:BYTE
  24.     EXTRN    SaveInt21:DWORD
  25.  
  26. DATA    ENDS
  27.  
  28. ; Run-time manager externals
  29.  
  30.     EXTRN    __AHIncr:ABS,__0040H:ABS,__A000H:ABS
  31.     EXTRN    __B000H:ABS,__B800H:ABS
  32.  
  33. CODE    SEGMENT    BYTE PUBLIC
  34.  
  35.     ASSUME    CS:CODE,DS:DATA
  36.  
  37. ; Externals
  38.  
  39.     EXTRN    AssignText:NEAR,ResetText:NEAR,RewriteText:NEAR
  40.     EXTRN    CloseText:NEAR,HaltTurbo:NEAR,Terminate:NEAR
  41.  
  42. ; Publics
  43.  
  44.     PUBLIC    InitTurbo
  45.  
  46. ; CS-based variables for Ctrl-Break handling
  47.  
  48. Int21Vector    DD    0        ;Saved INT 21H vector
  49. CtrlBreakFlag    DB    0        ;Ctrl-Break flag
  50.  
  51. ; Initialize runtime library. First instruction in any program
  52. ; is a call to this routine.
  53.  
  54. InitTurbo:
  55.  
  56.     MOV    DX,SEG DATA        ;Initialize DS
  57.     MOV    DS,DX
  58.     XOR    BP,BP            ;End of stack frame chain
  59.     MOV    PrefixSeg,ES        ;Save InitTask return values
  60.     MOV    HInstance,DI
  61.     MOV    AX,SP
  62.     ADD    AX,4
  63.     MOV    SS:pStackTop,10H    ;Set stack top
  64.     MOV    SS:pStackBot,AX        ;Set stack bottom
  65.     MOV    SS:pStackMin,AX        ;Set stack low water mark
  66.     MOV    AX,dpmiGetVersion    ;Determine CPU type
  67.     INT    DPMI
  68.     DEC    CL
  69.     MOV    Test8086,CL
  70.     MOV    SelectorInc,__AHIncr    ;Set selector increment
  71.     MOV    Seg0040,__0040H        ;Set predefined selectors
  72.     MOV    SegA000,__A000H
  73.     MOV    SegB000,__B000H
  74.     MOV    SegB800,__B800H
  75.     MOV    DI,OFFSET SaveInt00    ;Capture interrupt vectors
  76.     MOV    SI,OFFSET SaveIntTab
  77.     MOV    CX,SaveIntCnt
  78.     CLD
  79. @@1:    PUSH    CX
  80.     SEGCS    LODSW
  81.     MOV    BL,AH            ;Interrupt/exception number
  82.     MOV    AH,2            ;AX = 0200H, 0202H, 0204H
  83.     INT    DPMI
  84.     MOV    [DI].ofs,DX
  85.     MOV    [DI].seg,CX
  86.     ADD    DI,4
  87.     POP    CX
  88.     LOOP    @@1
  89.     MOV    AX,CS            ;Get code segment alias
  90.     ADD    AX,__AHIncr
  91.     MOV    ES,AX
  92.     MOV    AX,SaveInt21.ofs    ;Copy saved INT 21H vector to CS
  93.     MOV    ES:Int21Vector.ofs,AX
  94.     MOV    AX,SaveInt21.seg
  95.     MOV    ES:Int21Vector.seg,AX
  96.     MOV    AX,dpmiSetExcept    ;Install DIV 0 handler
  97.     MOV    BL,00H
  98.     MOV    DX,OFFSET Int00Handler
  99.     MOV    CX,CS
  100.     INT    DPMI
  101.     MOV    AX,0FB43H        ;If TDX is present, rely on it to
  102.     MOV    BX,100H            ;handle stack and GP faults
  103.     INT    2FH
  104.     CMP    BX,0FB43H        ;TDX present?
  105.     JE    @@2            ;Yes, @@2
  106.     MOV    AX,dpmiSetExcept    ;Install stack fault handler
  107.     MOV    BL,0CH
  108.     MOV    DX,OFFSET Int0CHandler
  109.     MOV    CX,CS
  110.     INT    DPMI
  111.     MOV    AX,dpmiSetExcept    ;Install GP fault handler
  112.     MOV    BL,0DH
  113.     MOV    DX,OFFSET Int0DHandler
  114.     MOV    CX,CS
  115.     INT    DPMI
  116. @@2:    MOV    AX,dpmiSetInt        ;Install INT 21H handler
  117.     MOV    BL,21H
  118.     MOV    DX,OFFSET Int21Handler
  119.     MOV    CX,CS
  120.     INT    DPMI
  121.     MOV    BL,23H            ;Install Ctrl-Break handler
  122.     MOV    SI,OFFSET Int23Handler
  123.     CALL    SetRealInt
  124.     MOV    BL,24H            ;Install critical error handler
  125.     MOV    SI,OFFSET Int24Handler
  126.     CALL    SetRealInt
  127.     MOV    AX,OFFSET Input        ;Assign/Reset Input file
  128.     PUSH    DS
  129.     PUSH    AX
  130.     PUSH    DS
  131.     PUSH    AX
  132.     MOV    AX,OFFSET ZeroString
  133.     PUSH    CS
  134.     PUSH    AX
  135.     PUSH    CS
  136.     CALL    AssignText
  137.     PUSH    CS
  138.     CALL    ResetText
  139.     MOV    AX,OFFSET Output    ;Assign/Rewrite Output file
  140.     PUSH    DS
  141.     PUSH    AX
  142.     PUSH    DS
  143.     PUSH    AX
  144.     MOV    AX,OFFSET ZeroString
  145.     PUSH    CS
  146.     PUSH    AX
  147.     PUSH    CS
  148.     CALL    AssignText
  149.     PUSH    CS
  150.     CALL    RewriteText
  151.     MOV    ExitProc.ofs,OFFSET ExitTurbo ;Install exit procedure
  152.     MOV    ExitProc.seg,CS
  153.     RETF                ;Back to main program
  154.  
  155. ; Set real mode interrupt
  156. ; In    BL = Interrupt number
  157. ;    SI = Handler offset
  158.  
  159. SetRealInt:
  160.  
  161.     MOV    AX,dpmiGetRMCB        ;Create real mode call-back
  162.     MOV    DI,OFFSET RealModeRegs
  163.     PUSH    DS
  164.     POP    ES
  165.     PUSH    CS
  166.     POP    DS
  167.     INT    DPMI
  168.     PUSH    ES
  169.     POP    DS
  170.     MOV    AX,dpmiSetRealInt    ;Set real mode interrupt
  171.     INT    DPMI
  172.     RET
  173.  
  174. ; Runtime library exit procedure. This is the last exit procedure to
  175. ; get executed when an application terminates.
  176.  
  177. ExitTurbo:
  178.  
  179.     MOV    AX,OFFSET Input        ;Close Input file
  180.     PUSH    DS
  181.     PUSH    AX
  182.     PUSH    CS
  183.     CALL    CloseText
  184.     MOV    AX,OFFSET Output    ;Close Output file
  185.     PUSH    DS
  186.     PUSH    AX
  187.     PUSH    CS
  188.     CALL    CloseText
  189.     MOV    DI,OFFSET SaveInt00    ;Restore interrupt vectors
  190.     MOV    SI,OFFSET SaveIntTab
  191.     MOV    CX,SaveIntCnt
  192.     CLD
  193. @@1:    PUSH    CX
  194.     SEGCS    LODSW
  195.     MOV    BL,AH
  196.     MOV    AH,2
  197.     INC    AX            ;AX = 0201H, 0203H, 0205H
  198.     MOV    DX,[DI].ofs
  199.     MOV    CX,[DI].seg
  200.     INT    DPMI
  201.     ADD    DI,4
  202.     POP    CX
  203.     LOOP    @@1
  204.     RETF
  205.  
  206. ; Divide by zero exception handler
  207.  
  208. Int00Handler:
  209.  
  210.     PUSH    AX
  211.     MOV    AX,200
  212.     JMP    SHORT Exception
  213.  
  214. ; Stack fault exception handler
  215.  
  216. Int0CHandler:
  217.  
  218.     PUSH    AX
  219.     MOV    AX,202
  220.     JMP    SHORT Exception
  221.  
  222. ; General protection fault handler
  223.  
  224. Int0DHandler:
  225.  
  226.     PUSH    AX
  227.     MOV    AX,216
  228.  
  229. ; Common exception handler. Saves off the error code and error address
  230. ; and modifies the exception handler stack frame to return to the
  231. ; ExceptHalt routine. 
  232.  
  233. Exception:
  234.  
  235.     PUSH    DS
  236.     PUSH    BP
  237.     MOV    BP,SEG DATA
  238.     MOV    DS,BP
  239.     MOV    BP,SP
  240.     MOV    ExitCode,AX
  241.     MOV    AX,[BP+12].ofs
  242.     MOV    ErrorAddr.ofs,AX
  243.     MOV    AX,[BP+12].seg
  244.     MOV    ErrorAddr.seg,AX
  245.     MOV    [BP+12].ofs,OFFSET ExceptHalt
  246.     MOV    [BP+12].seg,CS
  247.     CMP    [BP+18].ofs,1024
  248.     JAE    @@1
  249.     MOV    [BP+18].ofs,1024
  250. @@1:    POP    BP
  251.     POP    DS
  252.     POP    AX
  253.     RETF
  254.  
  255. ; Here on return from exception handler. Restores the error code and
  256. ; error address and terminates the application.
  257.  
  258. ExceptHalt:
  259.  
  260.     MOV    AX,SEG DATA
  261.     MOV    DS,AX
  262.     MOV    AX,ExitCode
  263.     MOV    CX,ErrorAddr.ofs
  264.     MOV    BX,ErrorAddr.seg
  265.     JMP    Terminate
  266.  
  267. ; INT 21H handler. DPMI does not allow a Ctrl-Break handler to terminate
  268. ; an application, so the Ctrl-Break handler sets a flag which is then
  269. ; checked in this INT 21H hook.
  270.  
  271. Int21Handler:
  272.  
  273.     STI                ;Re-enable interrupts
  274.     PUSHF                ;Chain to original INT 21H handler
  275.     CALL    Int21Vector
  276.     PUSHF                ;Save flags
  277.     CMP    CtrlBreakFlag,0        ;Ctrl-Break detected?
  278.     JNE    @@1            ;Yes, @@1
  279.     POPF                ;Restore flags
  280.     RETF    2            ;Return
  281. @@1:    MOV    AX,CS            ;Get code segment alias
  282.     ADD    AX,__AHIncr
  283.     MOV    DS,AX
  284.     MOV    DS:CtrlBreakFlag,0    ;Clear Ctrl-Break flag
  285.     MOV    AX,255            ;Terminate application
  286.     JMP    HaltTurbo
  287.  
  288. ; Ctrl-Break interrupt handler. Control arrives here through a real mode
  289. ; call-back when DOS detects a Ctrl-C or Ctrl-Break. Since a Ctrl-Break
  290. ; handler is not allowed to terminate an application under DPMI, the
  291. ; handler sets a flag which is then checked by the INT 21H hook.
  292.  
  293. Int23Handler:
  294.  
  295.     CALL    RealModeIRET        ;Simulate real mode IRET
  296.     MOV    AX,CS            ;Get code segment alias
  297.     ADD    AX,__AHIncr
  298.     MOV    DS,AX
  299.     MOV    DS:CtrlBreakFlag,1    ;Set Ctrl-Break flag
  300.     IRET                ;Return from call-back
  301.     
  302. ; Critical error interrupt handler. Control arrives here when DOS
  303. ; encounters a critical error. The handler converts the critical error
  304. ; code to a Turbo Pascal I/O error code.
  305.  
  306. Int24Handler:
  307.  
  308.     MOV    AH,54H            ;Dummy function call to get DOS
  309.     INT    21H            ;into a stable state
  310.     ADD    SI,6            ;Discard IRET from real mode stack
  311.     CLD
  312.     LODSW                ;Pop AX from real mode stack
  313.     MOV    DX,ES:[DI].realDI.w0    ;Get critical error code
  314.     AND    DX,1FH            ;Return AX=150..181
  315.     ADD    DX,150
  316.     CMP    AH,39H            ;DOS 2.0 style function?
  317.     JAE    @@1            ;Yes, @@1
  318.     MOV    DX,0FFFFH        ;Return AX=0FFFFH
  319. @@1:    MOV    ES:[DI].realAX.w0,DX    ;Save return AX
  320.     LODSW                ;Restore other registers
  321.     MOV    ES:[DI].realBX.w0,AX
  322.     LODSW
  323.     MOV    ES:[DI].realCX.w0,AX
  324.     LODSW
  325.     MOV    ES:[DI].realDX.w0,AX
  326.     LODSW
  327.     MOV    ES:[DI].realSI.w0,AX
  328.     LODSW
  329.     MOV    ES:[DI].realDI.w0,AX
  330.     LODSW
  331.     MOV    ES:[DI].realBP.w0,AX
  332.     LODSW
  333.     MOV    ES:[DI].realDS,AX
  334.     LODSW
  335.     MOV    ES:[DI].realES,AX
  336.     ADD    ES:[DI].realSP,24    ;Adjust real mode SP
  337.     CALL    RealModeIRET        ;Simulate real mode IRET
  338.     OR    ES:[DI].realFlags,1    ;Set CF in return flags
  339.     IRET                ;Return from call-back
  340.  
  341. ; Simulate an IRET in a real mode call-back
  342.  
  343. RealModeIRET:
  344.  
  345.     CLD
  346.     LODSW
  347.     MOV    ES:[DI].realIP,AX
  348.     LODSW
  349.     MOV    ES:[DI].realCS,AX
  350.     LODSW
  351.     MOV    ES:[DI].realFlags,AX
  352.     ADD    ES:[DI].realSP,6
  353.     RET
  354.  
  355. ; Saved interrupt and exception numbers. The first byte of each entry
  356. ; is the low byte of the 02xxH DPMI function code to use when modifying
  357. ; the vector. 0 means real mode interrupt, 2 means protected mode
  358. ; exception, and 4 means protected mode interrupt.
  359.  
  360. SaveIntTab    LABEL    BYTE
  361.  
  362.     DB    2,00H
  363.     DB    4,02H
  364.     DB    2,0CH
  365.     DB    2,0DH
  366.     DB    4,1BH
  367.     DB    4,21H
  368.     DB    0,23H
  369.     DB    0,24H
  370.     DB    4,34H
  371.     DB    4,35H
  372.     DB    4,36H
  373.     DB    4,37H
  374.     DB    4,38H
  375.     DB    4,39H
  376.     DB    4,3AH
  377.     DB    4,3BH
  378.     DB    4,3CH
  379.     DB    4,3DH
  380.     DB    4,3EH
  381.     DB    4,3FH
  382.     DB    4,75H
  383.  
  384. SaveIntCnt    EQU    ($-SaveIntTab)/2
  385.  
  386. ; Empty string
  387.  
  388. ZeroString    DB    0
  389.  
  390. CODE    ENDS
  391.  
  392.     END
  393.