home *** CD-ROM | disk | FTP | other *** search
/ Simtel MSDOS - Coast to Coast / simteldosarchivecoasttocoast.iso / screen / scrollk.asm < prev    next >
Assembly Source File  |  1994-03-05  |  8KB  |  233 lines

  1. TITLE SCROLLK.COM -- DOS RESIDENT SCROLL LOCK CONTROL
  2. PAGE 60,132
  3.  
  4. COMMENT* This program provides scrolling control of the video display with
  5.     the Scroll Lock key.  Assemble, Link, and convert the EXE file to a
  6.     COM program. Run the program once on system boot-up then the Scroll
  7.     Lock key can be used to toggle scrolling on and off. If scroll lock
  8.     is ON, the screen will pause after 23 continuous lines are displayed.
  9.     Press the Left shift key to scroll another 23 lines or the Right
  10.     shift key to scroll one line; or press Scroll Lock again to turn OFF
  11.     the lock and the screen will scroll uninterrupted.*
  12.  
  13. ;----------------------------------------------------------------------------;
  14. ;This program intercepts calls to the VIDEO_IO routines.  Commands to scroll
  15. ;the screen will be intercepted; all others passed through. This routine is
  16. ;attached to DOS.
  17. ;
  18. ;Program by John Socha, 'Softalk', May 1983, pp. 38-49
  19. ;
  20. ;keyed in by Lee M Buck, Arlington VA
  21. ;
  22. ;----------------------------------------------------------------------------;
  23.  
  24.  
  25. ;----------------------------------------------------------------------------;
  26. ;Interrupt vectors for video and keyboard routines
  27. ;----------------------------------------------------------------------------;
  28.  
  29. VECTORS SEGMENT AT 0
  30.     ORG    10H*4
  31. VIDEO_INT    LABEL DWORD
  32.     ORG    16H*4
  33. KEYBOARD_INT    LABEL DWORD
  34. VECTORS ENDS
  35.  
  36.  
  37. ;----------------------------------------------------------------------------;
  38. ;ROM BIOS data area for keyboard
  39. ;
  40. ;Contents of KB_FLAG - bits 7 to 0
  41. ;<---      ---      ---      ---      ---      ---      ---      --->
  42. ;  ^INS_STATE       ^NUM_STATE       ^ALT_SHIFT       ^LEFT_SHIFT
  43. ;       ^CAPS_STATE       ^SCROLL_STATE   ^CTL_STATE       ^RIGHT_SHIFT
  44. ;----------------------------------------------------------------------------;
  45.  
  46. ROM_BIOS_DATA    SEGMENT AT 40H
  47.     ORG    17H
  48. KB_FLAG        DB    ?        ;Bit 4 set for scroll lock
  49. ROM_BIOS_DATA    ENDS
  50.  
  51.  
  52. ;----------------------------------------------------------------------------;
  53. ;Initialize vectors and attach to DOS
  54. ;----------------------------------------------------------------------------;
  55.  
  56. CSEG    SEGMENT        PARA
  57.     ASSUME        CS:CSEG
  58.     ORG        100H        ;Set starting point for COM file
  59. BEGIN:  JMP        INIT_VECTORS    ;Initialize INT 10H and attach to DOS
  60.  
  61.  
  62. ;----------------------------------------------------------------------------;
  63. ;These memory locations store the addresses of the ROM routines for video and
  64. ;keyboard I/O routines
  65. ;----------------------------------------------------------------------------;
  66.  
  67. ROM_VIDEO_IO        DD        ;Address of the ROM routines
  68. ROM_KEYBOARD_IO        DD
  69. SCROLL_COUNT        DB    0    ;Lines scrolled since last pause
  70. LAST_LOCK_STATE        DB    0    ;0 if scrl lock off last time checked
  71. MAX_LINES        DB    23    ;Scroll by 23 lines, leaving one old
  72.                     ;line at top before pausing
  73. LAST_LINE        DB        ;Last line cursor was on
  74.  
  75. ;----------------------------------------------------------------------------;
  76. ;This routine intercepts all calls to the VIDEO_IO routine in ROM.
  77. ;Scroll Lock:
  78. ;    OFF        This routine passes control directly to the ROM BIOS
  79. ;            routine.
  80. ;    ON        Functions other than SCROLL UP or SCROLL DOWN are
  81. ;            passed directly to the ROM routines. Otherwise, this
  82. ;            routine increments the scroll count and checks to see
  83. ;            if it exceeds the page size of 23 lines (MAX_LINES).
  84. ;            If so, loop until either shift key pressed.
  85. ;                Left shift allows scroll of whole window
  86. ;                Right shift scrolls one line.
  87. ;--------------------------------------------------------------------------;
  88.  
  89. INTERCEPT_VIDEO        PROC    FAR
  90.     ASSUME  CS:CSEG
  91.     STI                ;Turn on interrupts again
  92.     PUSH    DS            ;Save registers used
  93.     PUSH    BX
  94.     PUSH    AX
  95.  
  96.     ASSUME  DS:ROM_BIOS_DATA
  97.     MOV    BX,ROM_BIOS_DATA
  98.     MOV    DS,BX
  99.     MOV    AL,KB_FLAG        ;Check state of scroll lock key
  100.     AND    AL,10H            ;Isolate scroll lock bit
  101.     ASSUME  DS:CSEG
  102.     MOV    BX,CS            ;Data segment for variables (above)
  103.     MOV    DS,BX
  104.     CMP    AL,LAST_LOCK_STATE
  105.     JE    UN_CHANGED        ;Scroll lock key hasn't changed
  106.     MOV    BL,MAX_LINES        ;Scroll lock key has changed, set to
  107.     MOV    SCROLL_COUNT,BL        ;MAX_LINES to stop scrolling
  108.     MOV    LAST_LOCK_STATE,AL    ;Save the new scroll lock state
  109.     PUSH    CX            ;Now read current cursor position and
  110.     PUSH    DX            ;save in LAST_LINE so SCROLLK won't
  111.     PUSH    AX            ;freeze in the middle of a line
  112.     MOV    AH,3
  113.     MOV    BH,0
  114.     PUSHF
  115.     CALL    ROM_VIDEO_IO        ;This is a pseudo INT 10H call to BIOS
  116.     MOV    LAST_LINE,DH        ;to find old cursor position and save
  117.     POP    AX            ;in LAST_LINE. (see Tech. Ref. A-43)
  118.     POP    DX
  119.     POP    CX
  120. UN_CHANGED:
  121.     XCHG    AX,BX        ;Recover function (AH) and retain scroll lock
  122.     POP    AX
  123.     OR    BL,BL        ;Is scroll lock on?
  124.     JZ    TO_VIDEO_IO    ;No, jump to the ROM VIDEO_IO routine
  125.     ;-----------------------;
  126.     ;Scroll Lock ON        ;
  127.     ;-----------------------;
  128.     CMP    AH,2        ;Check for SET CURSOR POSITION function
  129.     JNE    NOPE
  130.     CMP    DH,LAST_LINE    ;Is the cursor being moved to the next line?
  131.     MOV    LAST_LINE,DH        ;Save new cursor line
  132.     JLE    TO_VIDEO_IO        ;No, jump to ROM routine
  133.     JMP    SHORT CHECK_LOCK    ;Yes, see if need to lock
  134. NOPE:    CMP    AH,6            ;Scroll up?
  135.     JNE    TO_VIDEO_IO        ;No, go to ROM routines
  136. CHECK_LOCK:
  137.     INC    SCROLL_COUNT        ;Take care of scroll lock
  138.     MOV    BH,MAX_LINES
  139.     CMP    SCROLL_COUNT,BH        ;Have we scrolled more than MAX_LINES?
  140.     JL    TO_VIDEO_IO        ;Nope, it's ok to scroll
  141.                     ;Yes, wait until a shift key is hit
  142.     MOV    BL,BH            ;Set SCROLL_COUNT to MAX_LINES-1
  143.     DEC    BL            ;so we can print one more line
  144.     MOV    SCROLL_COUNT,BL
  145.     ASSUME  DS:ROM_BIOS_DATA
  146.     MOV    BX,ROM_BIOS_DATA
  147.     MOV    DS,BX
  148. LOOP:    MOV    BL,KB_FLAG        ;Wait for left or right shift key push
  149.     TEST    BL,10H            ;Is scroll lock still on?
  150.     JZ    TO_VIDEO_IO
  151.     AND    BL,3            ;Pick off shift key info
  152.     JZ    LOOP            ;Stay in loop until shift key pressed
  153.     CMP    BL,1            ;Right shift key pressed?
  154.     JE    SCROLL_LINE        ;Yes, allow scroll of one line
  155.                 ;No, must be left shift key, so reset scroll count
  156.     XOR    BX,BX
  157.     MOV    SCROLL_COUNT,BL
  158. SCROLL_LINE:
  159.  
  160. TO_VIDEO_IO:
  161.     POP    BX            ;Restore BX register
  162.     PUSHF
  163.     CALL    ROM_VIDEO_IO        ;Perform a pseudo INT 10H call to BIOS
  164.     POP DS
  165.     IRET                ;interrupt Return
  166. INTERCEPT_VIDEO        ENDP
  167.  
  168.  
  169. ;----------------------------------------------------------------------------;
  170. ;This routine intercepts all calls to KEYBOARD_IO
  171. ;If the keyboard function calls for a read (AH=0) then reset the scroll count
  172. ;----------------------------------------------------------------------------;
  173.  
  174. INTERCEPT_KEYBOARD    PROC    FAR
  175.     ASSUME  CS:CSEG,DS:CSEG
  176.     STI                ;Turn interrupts on
  177.     PUSH    DS            ;Save registers used by this routine
  178.     PUSH    BX
  179.     MOV    BX,CS            ;Set up data segment for variables
  180.     MOV    DS,BX
  181.     OR    AH,AH            ;Check to see if AH=0
  182.     JNZ    KB1            ;Nope, branch to keyboard I/O
  183.     XOR    BX,BX            ;Yes, set scroll count to 0
  184.     MOV    SCROLL_COUNT,BL
  185. KB1:    POP BX                ;Restore BX register
  186.     ASSUME  DS:NOTHING
  187.     POP    DS
  188.     JMP    ROM_KEYBOARD_IO        ;Jump to keyboard routine and return
  189.                     ;directly to the routine that called
  190.                     ;this one
  191. INTERCEPT_KEYBOARD    ENDP
  192.  
  193. ;----------------------------------------------------------------------------;
  194. ;This section of code saves the old interrupt vectors for the keyboard and
  195. ;video I/O routines. These vectors are replaced by the addresses of
  196. ;INTERCEPT_VIDEO and INTERCEPT_KEYBOARD PROCS above.
  197. ;----------------------------------------------------------------------------;
  198.  
  199. INIT_VECTORS    PROC    NEAR
  200.     ASSUME  CS:CSEG,DS:CSEG
  201.     MOV    AH,3            ;Set LAST_LINE to cursor line number
  202.     XOR    BH,BH
  203.     INT    10H
  204.     MOV    LAST_LINE,DH
  205.  
  206.     ASSUME  CS:CSEG,DS:VECTORS
  207.     MOV    AX,VECTORS
  208.     MOV    DS,AX
  209.  
  210.     MOV    AX,VIDEO_INT        ;Save the ROM routine address
  211.     MOV    ROM_VIDEO_IO,AX
  212.     MOV    AX,VIDEO_INT[2]
  213.     MOV    ROM_VIDEO_IO[2],AX
  214.     MOV    AX,OFFSET INTERCEPT_VIDEO    ;Set video INT 10H to point to
  215.     MOV    VIDEO_INT,AX            ;INTERCEPT_VIDEO PROC above.
  216.     MOV    VIDEO_INT[2],CS
  217.  
  218.     MOV    AX,KEYBOARD_INT        ;Save the ROM routine address
  219.     MOV    ROM_KEYBOARD_IO,AX
  220.     MOV    AX,KEYBOARD_INT[2]
  221.     MOV    ROM_KEYBOARD_IO[2],AX
  222.     MOV    AX,OFFSET INTERCEPT_KEYBOARD    ;Set keyboard INT 16H to point
  223.     MOV    KEYBOARD_INT,AX            ;to INTERCEPT_KEYBOARD PROC
  224.     MOV    KEYBOARD_INT[2],CS
  225.  
  226.     MOV    DX,OFFSET INIT_VECTORS  ;End of resident portion
  227.     INT    27H            ;Terminate but stay resident
  228. INIT_VECTORS    ENDP
  229.  
  230. CSEG    ENDS
  231.     END    BEGIN
  232.  
  233.