;****************************************************************************
;*
;*                        The Universal VESA VBE
;*
;*                  Copyright (C) 1993 Kendall Bennett.
;*                          All rights reserved.
;*
;* Filename:    $RCSfile: _chips.asm $
;* Version:     $Revision: 1.2 $
;*
;* Language:    8086 Assembler
;* Environment: IBM PC (MS DOS)
;*
;* Description: Assembly language support routines for Chips & Technologies
;*              SuperVGA's.
;*
;*              Contains code to perform initialisation, bank switching
;*              and extended page flipping if possible.
;*
;* $Id: _chips.asm 1.2 1993/09/24 05:22:51 kjb release $
;*
;* Revision History:
;* -----------------
;*
;* $Log: _chips.asm $
;* Revision 1.2  1993/09/24  05:22:51  kjb
;* Fixed a number of bugs.
;*
;* Revision 1.1  1993/09/19  01:26:40  kjb
;* Initial revision
;*
;****************************************************************************

grCHIPS_82c451      =   0   ; C&T 82c451 chip
grCHIPS_82c452      =   1   ; C&T 82c452 chip
grCHIPS_82c453      =   2   ; C&T 82c453 chip

;----------------------------------------------------------------------------
; CHIPS451_bank Change to a new 64k bank (reading and writing)
;----------------------------------------------------------------------------
;
; Entry:        AX  - Number of 64k bank
;
; Registers:    All preserved!
;
;----------------------------------------------------------------------------
PROC    CHIPS451_bank   far

		push    ax
		push    dx
		mov     ah,al
		mov     al,0Bh              ; Index of Single/Low Map register
		mov     dx,3D6h
		out     dx,ax               ; Set the register value
		pop     dx
		pop     ax
		ret

ENDP    CHIPS451_bank

CHIPS451_bank_len   =   ($-CHIPS451_bank)

;----------------------------------------------------------------------------
; CHIPS452_bank16   Change to a new 64k bank (reading and writing)
;----------------------------------------------------------------------------
;
; Entry:        AX  - Number of 64k bank
;
; Registers:    All preserved!
;
;----------------------------------------------------------------------------
PROC    CHIPS452_bank16 far

		push    ax
		push    dx
		mov     ah,al
		shl     ah,4                ; Change 64k bank into 4k bank number
		mov     al,10h              ; Index of Single/Low Map register
		mov     dx,3D6h
		out     dx,ax               ; Set the register value
		pop     dx
		pop     ax
		ret

ENDP    CHIPS452_bank16

CHIPS452_bank16_len =   ($-CHIPS452_bank16)

;----------------------------------------------------------------------------
; CHIPS452_bank256  Change to a new 64k bank (reading and writing)
;----------------------------------------------------------------------------
;
; Entry:        AX  - Number of 64k bank
;
; Registers:    All preserved!
;
;----------------------------------------------------------------------------
PROC    CHIPS452_bank256    far

		push    ax
		push    dx
		mov     ah,al
		shl     ah,2                ; Change 64k bank into 16k bank number
		mov     al,10h              ; Index of Single/Low Map register
		mov     dx,3D6h
		out     dx,ax               ; Set the register value
		pop     dx
		pop     ax
		ret

ENDP    CHIPS452_bank256

CHIPS452_bank256_len    =   ($-CHIPS452_bank256)

;----------------------------------------------------------------------------
; CHIPS453_bank16   Change to a new 64k bank (reading and writing)
;----------------------------------------------------------------------------
;
; Entry:        AX  - Number of 64k bank
;
; Registers:    All preserved!
;
;----------------------------------------------------------------------------
PROC    CHIPS453_bank16 far

		push    ax
		push    dx
		mov     ah,al
		shl     ah,6                ; Change 64k bank into 4k bank number
		mov     al,10h              ; Index of Single/Low Map register
		mov     dx,3D6h
		out     dx,ax               ; Set the register value
		pop     dx
		pop     ax
		ret

ENDP    CHIPS453_bank16

CHIPS453_bank16_len =   ($-CHIPS453_bank16)

;----------------------------------------------------------------------------
; CHIPS453_bank256  Change to a new 64k bank (reading and writing)
;----------------------------------------------------------------------------
;
; Entry:        AX  - Number of 64k bank
;
; Registers:    All preserved!
;
;----------------------------------------------------------------------------
PROC    CHIPS453_bank256    far

		push    ax
		push    dx
		mov     ah,al
		shl     ah,4                ; Change 64k bank into 4k bank number
		mov     al,10h              ; Index of Single/Low Map register
		mov     dx,3D6h
		out     dx,ax               ; Set the register value
		pop     dx
		pop     ax
		ret

ENDP    CHIPS453_bank256

CHIPS453_bank256_len    =   ($-CHIPS453_bank256)

;----------------------------------------------------------------------------
; CHIPS_page	Set the extended CRT starting address.
;----------------------------------------------------------------------------
;
; Entry:        BL  - Index of start address low register
;               BH  - Bits 7-0 of new start address
;               CL  - Index of start address high register
;               CH  - Bits 15-8 of new start address
;               SI  - Bits 16+ for new start address
;
; Registers:    AX,BX,CX,DX,SI
;
;----------------------------------------------------------------------------
PROC    CHIPS_page  far

        SetLowStartAddress
        mov     dx,03D6h
        mov     al,0Ch
        mov     ah,bl
        out     dx,ax               ; Set the extended start address
        mov     al,04h
        out     dx,al               ; Index memory map register
        inc     dx
        in      al,dx               ; Read register value
        or      al,4                ; Set bit 2 for extended paging
        out     dx,al               ; Set the value
        ret

ENDP    CHIPS_page

CHIPS_page_len  =   ($-CHIPS_page)

;----------------------------------------------------------------------------
; CHIPS_setup   Setup the SuperVGA for correct operation
;----------------------------------------------------------------------------
PROC    CHIPS_setup near

        outp    46E8h, 1Eh          ; Place chip in setup mode
        outp    103h, 80h           ; Enable extended registers
        outp    46E8h, 0Eh          ; Bring chip out of setup mode
        modinx  3D6h, 4, 4, 4       ; Enable bank access and extended CRTC
        modinx  3D6h, 0Bh, 3, 1     ; Enable extended paging
        ret

ENDP    CHIPS_setup

CHIPS_setup_len =   ($-CHIPS_setup)

;----------------------------------------------------------------------------
; CHIPS_exit    Return the SuperVGA to default operation
;----------------------------------------------------------------------------
PROC    CHIPS_exit  near

        outp    46E8h, 1Eh          ; Place chip in setup mode
        outp    103h, 0             ; Disable extended registers
        outp    46E8h, 0Eh          ; Bring chip out of setup mode
        ret

ENDP    CHIPS_exit

CHIPS_exit_len  =   ($-CHIPS_exit)

;----------------------------------------------------------------------------
; CHIPS_init
;----------------------------------------------------------------------------
; We have a Chips & Technologies 82c451/452/453, so set up a few things
; specific to this card.
;----------------------------------------------------------------------------
PROC    CHIPS_init  near

; Setup the correct vectors to use the C&T bank switching and paging routines

        mov     [TwoBanks],false
        mov     [WriteBank16],offset CHIPS453_bank16
        mov     [WriteBank16Len],CHIPS453_bank16_len
        mov     [WriteBank256],offset CHIPS453_bank256
        mov     [WriteBank256Len],CHIPS453_bank256_len
		mov     [NewPage16],offset CHIPS_page
		mov     [NewPage16Len],CHIPS_page_len
		mov     [NewPage256],offset CHIPS_page
		mov     [NewPage256Len],CHIPS_page_len
		mov     [SetupSVGA],offset CHIPS_setup
        mov     [SetupSVGALen],CHIPS_setup_len
        mov     [ExitSVGA],offset CHIPS_exit
        mov     [ExitSVGALen],CHIPS_exit_len

        mov     bx,[CntChipID]      ; BX := chip id
        cmp     bx,grCHIPS_82c453
        je      @@Exit              ; Done for 82c453

        mov     [WriteBank16],offset CHIPS452_bank16
        mov     [WriteBank16Len],CHIPS452_bank16_len
        mov     [WriteBank256],offset CHIPS452_bank256
        mov     [WriteBank256Len],CHIPS452_bank256_len
        cmp     bx,grCHIPS_82c452
        je      @@Exit              ; Done for 82c452

        mov     [WriteBank16],offset CHIPS451_bank
        mov     [WriteBank16Len],CHIPS451_bank_len
        mov     [WriteBank256],offset CHIPS451_bank
        mov     [WriteBank256Len],CHIPS451_bank_len
		mov     [NewPage16],NOT_VALID	; No page flipping :-(
		mov     [NewPage256],NOT_VALID

@@Exit:
        ret

ENDP    CHIPS_init
