home *** CD-ROM | disk | FTP | other *** search
/ Microsoft Programmer's Library 1.3 / Microsoft-Programers-Library-v1.3.iso / sampcode / video / 10 / 10_13.asm < prev    next >
Encoding:
Assembly Source File  |  1988-08-11  |  4.3 KB  |  180 lines

  1.         TITLE    'Listing 10-13'
  2.         NAME    AlphaModeSet
  3.         PAGE    55,132
  4.  
  5. ;
  6. ; Name:        AlphaModeSet
  7. ;
  8. ;        Program the CRTC in 80-column VGA alphanumeric modes
  9. ;
  10. ; Caller:    Microsoft C:
  11. ;
  12. ;            void AlphaModeSet(w,h,c);
  13. ;
  14. ;            int    w;    /* width of character matrix */
  15. ;            int    h;    /* height of character matrix */
  16. ;            int    c;    /* character code size */
  17. ;
  18.  
  19. ARGw        EQU    byte ptr [bp+4]        ; must be 8 or 9 pixels wide
  20. ARGh        EQU    byte ptr [bp+6]        ; must be 2-32 pixels high
  21. ARGc        EQU    byte ptr [bp+8]        ; must be 8 or 9 bits
  22.  
  23. CRT_COLS    EQU    4Ah        ; addresses in video BIOS data area
  24. ADDR_6845    EQU    63h
  25.  
  26. DGROUP        GROUP    _DATA
  27.  
  28. _TEXT        SEGMENT    byte public 'CODE'
  29.         ASSUME    cs:_TEXT,ds:DGROUP
  30.  
  31.         PUBLIC    _AlphaModeSet
  32. _AlphaModeSet    PROC    near
  33.  
  34.         push    bp        ; preserve caller registers
  35.         mov    bp,sp
  36.         push    si
  37.  
  38. ; Program the CRTC
  39.  
  40.         mov    bx,40h
  41.         mov    es,bx        ; ES := video BIOS data segment
  42.  
  43.         mov    bl,ARGw        ; BL := character width
  44.         mov    bh,ARGh        ; BH := character height
  45.         call    SetCRTC
  46.  
  47. ; Program the Sequencer and Attribute Controller for 8 or 9 dots per character
  48.  
  49.         mov    dx,3C4h
  50.         mov    ax,0100h    ; AH bit 1 := 0 (synchronous reset)
  51.                     ; AL := 0 (Reset register number)
  52.         cli            ; disable interrupts
  53.         out    dx,ax        ; Sequencer synchronous reset
  54.  
  55.         mov    bx,1        ; BH,BL := values for 8-wide chars:
  56.                     ;  BH := 0 (value for Horiz Pel Pan)
  57.                     ;  BL := 1 (value for Clocking Mode)
  58.         cmp    ARGw,8
  59.         je    L01        ; jump if 8-wide characters
  60.  
  61.         mov    bx,0800h    ; BH,BL := values for 9-wide characters
  62.  
  63. L01:        mov    ah,bl        ; AH := value for Clocking Mode reg
  64.         mov    al,1        ; AL := Clocking Mode reg number
  65.         out    dx,ax        ; program the Sequencer
  66.  
  67.         mov    ax,0300h    ; AH := 3 (disable reset)
  68.                     ; AL := 0 (Sequencer register number)
  69.         out    dx,ax        ; disable Sequencer reset
  70.         sti            ; enable interrupts
  71.  
  72.         mov    bl,13h        ; BL := Horizontal Pel Pan reg number
  73.         mov    ax,1000h    ; AH := 10H (INT 10H function number)
  74.                     ; AL := 0 (set specified register)
  75.         int    10h        ; program Attribute Controller
  76.  
  77. ; Program the Attribute Controller for 8- or 9-bit character codes
  78.  
  79.         mov    ax,1000h    ; AH := 10H (INT 10H function number)
  80.                     ; AL := 0 (set specified register)
  81.         mov    bx,0F12h    ; BH := 0FH (Color Plane Enable value)
  82.                     ; BL := 12H (Color Plane Enable reg #)
  83.         cmp    ARGc,8
  84.         je    L02        ; jump if 8-bit character codes
  85.  
  86.         mov    bh,7        ; BH bit 3 := 0 (ignore bit 3 of all
  87.                     ;  attributes)
  88. L02:        int    10h        ; update Color Plane Enable register
  89.  
  90. ; update video BIOS data area
  91.  
  92.         mov    ax,720        ; AX := displayed pixels per row
  93.         div    ARGw        ; AL := displayed character columns
  94.         mov    es:[CRT_COLS],al
  95.  
  96.         pop    si
  97.         pop    bp
  98.         ret
  99.  
  100. _AlphaModeSet    ENDP
  101.  
  102.  
  103. SetCRTC         PROC    near        ; Caller:    BH = character height
  104.                     ;        BL = character width
  105.  
  106.         push    dx
  107.         mov    dx,es:[ADDR_6845]  ; CRTC I/O port
  108.  
  109. ; establish CRTC vertical timing and cursor position in character matrix
  110.  
  111.         push    bx        ; preserve char height and width 
  112.         mov    ax,1110h    ; AH := 11H (INT 10H function number)
  113.                     ; AL := 0 (user alpha load)
  114.         xor    cx,cx        ; CX := 0 (store no characters)
  115.         int    10h        ; call BIOS to program CRTC
  116.         pop    bx
  117.  
  118. ; enable I/O writes to CRTC registers
  119.  
  120.         mov    al,11h        ; AL := Vertical Retrace End reg number
  121.         out    dx,al
  122.         inc    dx
  123.         in    al,dx        ; AL := current value of this register
  124.         dec    dx
  125.  
  126.         mov    ah,al        ; AH := current value
  127.         mov    al,11h        ; AL := register number
  128.         push    ax        ; save on stack
  129.  
  130.         and    ah,01111111b    ; zero bit 7
  131.         out    dx,ax        ; update this register
  132.  
  133. ; establish CRTC horizontal timing
  134.  
  135.         xor    bh,bh        ; BX := character width
  136.         sub    bl,8        ; BX := 0 or 1
  137.         neg    bx        ; BX := 0 or 0FFFFH
  138.         and    bx,14        ; BX := 0 or 14 (offset into table)
  139.         mov    si,bx        ; SI := offset into table
  140.  
  141.         add    si,offset DGROUP:HorizParms    ; DS:SI -> parameters
  142.         call    UpdateCRTC
  143.  
  144. ; write-protect CRTC registers
  145.  
  146.         pop    ax        ; AX := previous VR End register data
  147.         out    dx,ax        ; restore this register
  148.  
  149.         pop    dx
  150.         ret
  151.  
  152. SetCRTC         ENDP
  153.  
  154.  
  155. UpdateCRTC    PROC    near        ; Caller:    DX = CRTC address port
  156.                     ;        DS:SI -> parameters
  157.                     ; Destroys:    AX,CX
  158.  
  159.         mov    cx,7        ; CX := number of registers to update
  160.         
  161. L10:        lodsw            ; AH := data for CRTC register in AL
  162.         out    dx,ax        ; update the register
  163.         loop    L10
  164.  
  165.         ret
  166.  
  167. UpdateCRTC    ENDP
  168.  
  169. _TEXT        ENDS
  170.  
  171.  
  172. _DATA        SEGMENT    word public 'DATA'
  173.  
  174. HorizParms    DW    6A00h,5901h,5A02h,8D03h,6304h,8805h,2D13h  ; 8-wide
  175.         DW    5F00h,4F01h,5002h,8203h,5504h,8105h,2813h  ; 9-wide
  176.  
  177. _DATA        ENDS
  178.  
  179.         END
  180.