171d7fec4Smrg/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/nsc/nsc_gx2_vga.c,v 1.2tsi Exp $ */
271d7fec4Smrg/*
371d7fec4Smrg * $Workfile: nsc_gx2_vga.c $
471d7fec4Smrg * $Revision: 1.1.1.1 $
571d7fec4Smrg * $Author: mrg $
671d7fec4Smrg *
771d7fec4Smrg * This file contains routines to set modes using the VGA registers.
871d7fec4Smrg * Since this file is for the first generation graphics unit, it interfaces
971d7fec4Smrg * to SoftVGA registers.  It works for both VSA1 and VSA2.
1071d7fec4Smrg *
1171d7fec4Smrg * NSC_LIC_ALTERNATIVE_PREAMBLE
1271d7fec4Smrg *
1371d7fec4Smrg * Revision 1.0
1471d7fec4Smrg *
1571d7fec4Smrg * National Semiconductor Alternative GPL-BSD License
1671d7fec4Smrg *
1771d7fec4Smrg * National Semiconductor Corporation licenses this software
1871d7fec4Smrg * ("Software"):
1971d7fec4Smrg *
2071d7fec4Smrg *      nsc XFree86
2171d7fec4Smrg *
2271d7fec4Smrg * under one of the two following licenses, depending on how the
2371d7fec4Smrg * Software is received by the Licensee.
2471d7fec4Smrg *
2571d7fec4Smrg * If this Software is received as part of the Linux Framebuffer or
2671d7fec4Smrg * other GPL licensed software, then the GPL license designated
2771d7fec4Smrg * NSC_LIC_GPL applies to this Software; in all other circumstances
2871d7fec4Smrg * then the BSD-style license designated NSC_LIC_BSD shall apply.
2971d7fec4Smrg *
3071d7fec4Smrg * END_NSC_LIC_ALTERNATIVE_PREAMBLE */
3171d7fec4Smrg
3271d7fec4Smrg/* NSC_LIC_BSD
3371d7fec4Smrg *
3471d7fec4Smrg * National Semiconductor Corporation Open Source License for Durango
3571d7fec4Smrg *
3671d7fec4Smrg * (BSD License with Export Notice)
3771d7fec4Smrg *
3871d7fec4Smrg * Copyright (c) 1999-2001
3971d7fec4Smrg * National Semiconductor Corporation.
4071d7fec4Smrg * All rights reserved.
4171d7fec4Smrg *
4271d7fec4Smrg * Redistribution and use in source and binary forms, with or without
4371d7fec4Smrg * modification, are permitted provided that the following conditions
4471d7fec4Smrg * are met:
4571d7fec4Smrg *
4671d7fec4Smrg *   * Redistributions of source code must retain the above copyright
4771d7fec4Smrg *     notice, this list of conditions and the following disclaimer.
4871d7fec4Smrg *
4971d7fec4Smrg *   * Redistributions in binary form must reproduce the above
5071d7fec4Smrg *     copyright notice, this list of conditions and the following
5171d7fec4Smrg *     disclaimer in the documentation and/or other materials provided
5271d7fec4Smrg *     with the distribution.
5371d7fec4Smrg *
5471d7fec4Smrg *   * Neither the name of the National Semiconductor Corporation nor
5571d7fec4Smrg *     the names of its contributors may be used to endorse or promote
5671d7fec4Smrg *     products derived from this software without specific prior
5771d7fec4Smrg *     written permission.
5871d7fec4Smrg *
5971d7fec4Smrg * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
6071d7fec4Smrg * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
6171d7fec4Smrg * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
6271d7fec4Smrg * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
6371d7fec4Smrg * NATIONAL SEMICONDUCTOR CORPORATION OR CONTRIBUTORS BE LIABLE FOR ANY
6471d7fec4Smrg * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
6571d7fec4Smrg * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
6671d7fec4Smrg * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
6771d7fec4Smrg * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
6871d7fec4Smrg * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE,
6971d7fec4Smrg * INTELLECTUAL PROPERTY INFRINGEMENT, OR OTHERWISE) ARISING IN ANY WAY
7071d7fec4Smrg * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
7171d7fec4Smrg * OF SUCH DAMAGE.
7271d7fec4Smrg *
7371d7fec4Smrg * EXPORT LAWS: THIS LICENSE ADDS NO RESTRICTIONS TO THE EXPORT LAWS OF
7471d7fec4Smrg * YOUR JURISDICTION. It is licensee's responsibility to comply with
7571d7fec4Smrg * any export regulations applicable in licensee's jurisdiction. Under
7671d7fec4Smrg * CURRENT (2001) U.S. export regulations this software
7771d7fec4Smrg * is eligible for export from the U.S. and can be downloaded by or
7871d7fec4Smrg * otherwise exported or reexported worldwide EXCEPT to U.S. embargoed
7971d7fec4Smrg * destinations which include Cuba, Iraq, Libya, North Korea, Iran,
8071d7fec4Smrg * Syria, Sudan, Afghanistan and any other country to which the U.S.
8171d7fec4Smrg * has embargoed goods and services.
8271d7fec4Smrg *
8371d7fec4Smrg * END_NSC_LIC_BSD */
8471d7fec4Smrg
8571d7fec4Smrg/* NSC_LIC_GPL
8671d7fec4Smrg *
8771d7fec4Smrg * National Semiconductor Corporation Gnu General Public License for Durango
8871d7fec4Smrg *
8971d7fec4Smrg * (GPL License with Export Notice)
9071d7fec4Smrg *
9171d7fec4Smrg * Copyright (c) 1999-2001
9271d7fec4Smrg * National Semiconductor Corporation.
9371d7fec4Smrg * All rights reserved.
9471d7fec4Smrg *
9571d7fec4Smrg * Redistribution and use in source and binary forms, with or without
9671d7fec4Smrg * modification, are permitted under the terms of the GNU General
9771d7fec4Smrg * Public License as published by the Free Software Foundation; either
9871d7fec4Smrg * version 2 of the License, or (at your option) any later version
9971d7fec4Smrg *
10071d7fec4Smrg * In addition to the terms of the GNU General Public License, neither
10171d7fec4Smrg * the name of the National Semiconductor Corporation nor the names of
10271d7fec4Smrg * its contributors may be used to endorse or promote products derived
10371d7fec4Smrg * from this software without specific prior written permission.
10471d7fec4Smrg *
10571d7fec4Smrg * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
10671d7fec4Smrg * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
10771d7fec4Smrg * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
10871d7fec4Smrg * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
10971d7fec4Smrg * NATIONAL SEMICONDUCTOR CORPORATION OR CONTRIBUTORS BE LIABLE FOR ANY
11071d7fec4Smrg * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
11171d7fec4Smrg * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
11271d7fec4Smrg * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
11371d7fec4Smrg * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
11471d7fec4Smrg * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE,
11571d7fec4Smrg * INTELLECTUAL PROPERTY INFRINGEMENT, OR OTHERWISE) ARISING IN ANY WAY
11671d7fec4Smrg * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
11771d7fec4Smrg * OF SUCH DAMAGE. See the GNU General Public License for more details.
11871d7fec4Smrg *
11971d7fec4Smrg * EXPORT LAWS: THIS LICENSE ADDS NO RESTRICTIONS TO THE EXPORT LAWS OF
12071d7fec4Smrg * YOUR JURISDICTION. It is licensee's responsibility to comply with
12171d7fec4Smrg * any export regulations applicable in licensee's jurisdiction. Under
12271d7fec4Smrg * CURRENT (2001) U.S. export regulations this software
12371d7fec4Smrg * is eligible for export from the U.S. and can be downloaded by or
12471d7fec4Smrg * otherwise exported or reexported worldwide EXCEPT to U.S. embargoed
12571d7fec4Smrg * destinations which include Cuba, Iraq, Libya, North Korea, Iran,
12671d7fec4Smrg * Syria, Sudan, Afghanistan and any other country to which the U.S.
12771d7fec4Smrg * has embargoed goods and services.
12871d7fec4Smrg *
12971d7fec4Smrg * You should have received a copy of the GNU General Public License
13071d7fec4Smrg * along with this file; if not, write to the Free Software Foundation,
13171d7fec4Smrg * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
13271d7fec4Smrg *
13371d7fec4Smrg * END_NSC_LIC_GPL */
13471d7fec4Smrg
13571d7fec4Smrg#ifdef HAVE_CONFIG_H
13671d7fec4Smrg#include "config.h"
13771d7fec4Smrg#endif
13871d7fec4Smrg
13971d7fec4Smrg/* VGA STRUCTURE */
14071d7fec4Smrg
14171d7fec4Smrg#define GU2_STD_CRTC_REGS 25
14271d7fec4Smrg#define GU2_EXT_CRTC_REGS 15
14371d7fec4Smrg#define GU2_GDC_REGS 9
14471d7fec4Smrg#define GU2_SEQ_REGS 5
14571d7fec4Smrg
14671d7fec4Smrg#define GU2_VGA_FLAG_MISC_OUTPUT	0x1
14771d7fec4Smrg#define GU2_VGA_FLAG_STD_CRTC		0x2
14871d7fec4Smrg#define GU2_VGA_FLAG_EXT_CRTC		0x4
14971d7fec4Smrg#define GU2_VGA_FLAG_GDC		0x10
15071d7fec4Smrg#define GU2_VGA_FLAG_SEQ		0x20
15171d7fec4Smrg#define GU2_VGA_FLAG_PALETTE 	0x40
15271d7fec4Smrg#define GU2_VGA_FLAG_ATTR 	0x80
15371d7fec4Smrg
15471d7fec4Smrgstatic unsigned int GDCregs[10];
15571d7fec4Smrgstatic unsigned int SEQregs[10];
15671d7fec4Smrgstatic unsigned int palette[256];
15771d7fec4Smrgstatic unsigned int ATTRregs[32];
15871d7fec4Smrgstatic unsigned char *font_data = NULL;
15971d7fec4Smrg
16071d7fec4Smrg#define VGA_BLOCK 0x40000		/* 256 k */
16171d7fec4Smrg
16271d7fec4Smrgvoid gu2_vga_extcrtc(char offset, int reset);
16371d7fec4Smrgint gu2_get_vga_active(void);
16471d7fec4Smrgvoid gu2_vga_font_data(int flag);
16571d7fec4Smrgvoid gu2_set_vga(int reset);
16671d7fec4Smrgint gu2_vga_seq_blanking(void);
16771d7fec4Smrgint gu2_vga_attr_ctrl(int reset);
16871d7fec4Smrgvoid gu2_vga_to_gfx(void);
16971d7fec4Smrgvoid gu2_gfx_to_vga(int vga_mode);
17071d7fec4Smrgint gu2_vga_seq_reset(int reset);
17171d7fec4Smrgint gu2_vga_save(gfx_vga_struct * vga, int flags);
17271d7fec4Smrgvoid gu2_vga_clear_extended(void);
17371d7fec4Smrgint gu2_vga_restore(gfx_vga_struct * vga, int flags);
17471d7fec4Smrg
17571d7fec4Smrgint
17671d7fec4Smrggu2_get_vga_active(void)
17771d7fec4Smrg{
17871d7fec4Smrg   int data = gfx_read_reg32(MDC_GENERAL_CFG);
17971d7fec4Smrg
18071d7fec4Smrg   if (data & MDC_GCFG_VGAE)
18171d7fec4Smrg      return 1;
18271d7fec4Smrg   return 0;
18371d7fec4Smrg}
18471d7fec4Smrg
18571d7fec4Smrgvoid
18671d7fec4Smrggu2_vga_font_data(int flag)
18771d7fec4Smrg{
18871d7fec4Smrg   if (flag == 0) {
18971d7fec4Smrg      if (font_data == NULL) {
19071d7fec4Smrg	 font_data = malloc(VGA_BLOCK);
19171d7fec4Smrg      }
19271d7fec4Smrg      DEBUGMSG(1, (0, X_NONE, "Saving VGA Data\n"));
19371d7fec4Smrg      memcpy(font_data, gfx_virt_fbptr, VGA_BLOCK);
19471d7fec4Smrg   } else {
19571d7fec4Smrg      if (font_data) {
19671d7fec4Smrg	 DEBUGMSG(1, (0, X_NONE, "Restore VGA Data\n"));
19771d7fec4Smrg	 memcpy(gfx_virt_fbptr, font_data, VGA_BLOCK);
19871d7fec4Smrg	 free(font_data);
19971d7fec4Smrg	 font_data = NULL;
20071d7fec4Smrg      }
20171d7fec4Smrg   }
20271d7fec4Smrg}
20371d7fec4Smrg
20471d7fec4Smrgvoid
20571d7fec4Smrggu2_set_vga(int reset)
20671d7fec4Smrg{
20771d7fec4Smrg   int data = gfx_read_reg32(MDC_GENERAL_CFG);
20871d7fec4Smrg
20971d7fec4Smrg   if (reset)
21071d7fec4Smrg      data |= MDC_GCFG_VGAE;
21171d7fec4Smrg   else
21271d7fec4Smrg      data &= ~MDC_GCFG_VGAE;
21371d7fec4Smrg   gfx_write_reg32(MDC_GENERAL_CFG, data);
21471d7fec4Smrg}
21571d7fec4Smrg
21671d7fec4Smrgint
21771d7fec4Smrggu2_vga_seq_blanking(void)
21871d7fec4Smrg{
21971d7fec4Smrg   int tmp;
22071d7fec4Smrg
22171d7fec4Smrg   gfx_outb(0x3C4, 1);
22271d7fec4Smrg   tmp = gfx_inb(0x3C5);
22371d7fec4Smrg   tmp |= 0x20;
22471d7fec4Smrg   tmp |= tmp << 8;
22571d7fec4Smrg   gfx_outw(0x3C4, tmp);
22671d7fec4Smrg
22771d7fec4Smrg   gfx_delay_milliseconds(1);
22871d7fec4Smrg   return (GFX_STATUS_OK);
22971d7fec4Smrg}
23071d7fec4Smrg
23171d7fec4Smrgint
23271d7fec4Smrggu2_vga_attr_ctrl(int reset)
23371d7fec4Smrg{
23471d7fec4Smrg   (void) gfx_inb(0x3DA);
23571d7fec4Smrg   gfx_outb(0x3C0, (unsigned char)(reset ? 0x00 : 0x20));
23671d7fec4Smrg   if (reset)
23771d7fec4Smrg      (void) gfx_inb(0x3DA);
23871d7fec4Smrg   return (GFX_STATUS_OK);
23971d7fec4Smrg}
24071d7fec4Smrg
24171d7fec4Smrgvoid
24271d7fec4Smrggu2_vga_to_gfx(void)
24371d7fec4Smrg{
24471d7fec4Smrg   gu2_vga_attr_ctrl(0);
24571d7fec4Smrg
24671d7fec4Smrg   gu2_vga_seq_blanking();
24771d7fec4Smrg   gfx_delay_milliseconds(2);
24871d7fec4Smrg
24971d7fec4Smrg   gu2_vga_extcrtc(0x3F, 1);
25071d7fec4Smrg}
25171d7fec4Smrg
25271d7fec4Smrgvoid
25371d7fec4Smrggu2_gfx_to_vga(int vga_mode)
25471d7fec4Smrg{
25571d7fec4Smrg   char sequencer;
25671d7fec4Smrg
25771d7fec4Smrg   gu2_vga_extcrtc(0x40, vga_mode);
25871d7fec4Smrg
25971d7fec4Smrg   /* clear the display blanking bit */
26071d7fec4Smrg   gfx_outb(MDC_SEQUENCER_INDEX, MDC_SEQUENCER_CLK_MODE);
26171d7fec4Smrg   sequencer = gfx_inb(MDC_SEQUENCER_DATA);
26271d7fec4Smrg   sequencer &= ~MDC_CLK_MODE_SCREEN_OFF;
26371d7fec4Smrg   sequencer |= 1;
26471d7fec4Smrg   gfx_outb(MDC_SEQUENCER_DATA, sequencer);
26571d7fec4Smrg
26671d7fec4Smrg   gfx_delay_milliseconds(1);
26771d7fec4Smrg
26871d7fec4Smrg   /*restart the sequencer */
26971d7fec4Smrg   gfx_outw(0x3C4, 0x300);
27071d7fec4Smrg
27171d7fec4Smrg   /* turn on the attribute controler */
27271d7fec4Smrg   (void) gfx_inb(0x3DA);
27371d7fec4Smrg   gfx_outb(0x3C0, 0x20);
27471d7fec4Smrg   (void) gfx_inb(0x3DA);
27571d7fec4Smrg
27671d7fec4Smrg   gu2_vga_extcrtc(0x3F, 0);
27771d7fec4Smrg}
27871d7fec4Smrg
27971d7fec4Smrg/*-----------------------------------------------------------------------------
28071d7fec4Smrg * gfx_vga_seq_reset
28171d7fec4Smrg *
28271d7fec4Smrg * This routine enables or disables SoftVGA.  It is used to make SoftVGA
28371d7fec4Smrg * "be quiet" and not interfere with any of the direct hardware access from
28471d7fec4Smrg * Durango.  For VSA1, the sequencer is reset to stop text redraws.  VSA2 may
28571d7fec4Smrg * provide a better way to have SoftVGA sit in the background.
28671d7fec4Smrg *-----------------------------------------------------------------------------
28771d7fec4Smrg */
28871d7fec4Smrgint
28971d7fec4Smrggu2_vga_seq_reset(int reset)
29071d7fec4Smrg{
29171d7fec4Smrg   gfx_outb(0x3C4, 0);
29271d7fec4Smrg   gfx_outb(0x3C5, (unsigned char)(reset ? 0x00 : 0x03));
29371d7fec4Smrg   return (GFX_STATUS_OK);
29471d7fec4Smrg}
29571d7fec4Smrg
29671d7fec4Smrg/*-----------------------------------------------------------------------------
29771d7fec4Smrg * gfx_vga_save
29871d7fec4Smrg *
29971d7fec4Smrg * This routine saves the state of the VGA registers into the specified
30071d7fec4Smrg * structure.  Flags indicate what portions of the register state need to
30171d7fec4Smrg * be saved.
30271d7fec4Smrg *-----------------------------------------------------------------------------
30371d7fec4Smrg */
30471d7fec4Smrgint
30571d7fec4Smrggu2_vga_save(gfx_vga_struct * vga, int flags)
30671d7fec4Smrg{
30771d7fec4Smrg   int i;
30871d7fec4Smrg   unsigned short crtcindex, crtcdata;
30971d7fec4Smrg
31071d7fec4Smrg   crtcindex = (gfx_inb(0x3CC) & 0x01) ? 0x3D4 : 0x3B4;
31171d7fec4Smrg   crtcdata = crtcindex + 1;
31271d7fec4Smrg
31371d7fec4Smrg   /* CHECK MISCELLANEOUS OUTPUT FLAG */
31471d7fec4Smrg
31571d7fec4Smrg   if (flags & GU2_VGA_FLAG_MISC_OUTPUT) {
31671d7fec4Smrg      /* SAVE MISCCELLANEOUS OUTPUT REGISTER */
31771d7fec4Smrg
31871d7fec4Smrg      vga->miscOutput = gfx_inb(0x3CC);
31971d7fec4Smrg   }
32071d7fec4Smrg
32171d7fec4Smrg   /* CHECK SEQ */
32271d7fec4Smrg
32371d7fec4Smrg   if (flags & GU2_VGA_FLAG_SEQ) {
32471d7fec4Smrg      /* SAVE STANDARD CRTC REGISTERS */
32571d7fec4Smrg
32671d7fec4Smrg      for (i = 1; i < GU2_SEQ_REGS; i++) {
32771d7fec4Smrg	 gfx_outb(0x3C4, (unsigned char)i);
32871d7fec4Smrg	 SEQregs[i] = gfx_inb(0x3C5);
32971d7fec4Smrg      }
33071d7fec4Smrg   }
33171d7fec4Smrg
33271d7fec4Smrg   /* CHECK STANDARD CRTC FLAG */
33371d7fec4Smrg
33471d7fec4Smrg   if (flags & GU2_VGA_FLAG_STD_CRTC) {
33571d7fec4Smrg      /* SAVE STANDARD CRTC REGISTERS */
33671d7fec4Smrg
33771d7fec4Smrg      for (i = 0; i < GU2_STD_CRTC_REGS; i++) {
33871d7fec4Smrg	 gfx_outb(crtcindex, (unsigned char)i);
33971d7fec4Smrg	 vga->stdCRTCregs[i] = gfx_inb(crtcdata);
34071d7fec4Smrg      }
34171d7fec4Smrg   }
34271d7fec4Smrg
34371d7fec4Smrg   /* CHECK GDC */
34471d7fec4Smrg
34571d7fec4Smrg   if (flags & GU2_VGA_FLAG_GDC) {
34671d7fec4Smrg      /* SAVE STANDARD CRTC REGISTERS */
34771d7fec4Smrg
34871d7fec4Smrg      for (i = 0; i < GU2_GDC_REGS; i++) {
34971d7fec4Smrg	 gfx_outb(0x3CE, (unsigned char)i);
35071d7fec4Smrg	 GDCregs[i] = gfx_inb(0x3CF);
35171d7fec4Smrg      }
35271d7fec4Smrg   }
35371d7fec4Smrg
35471d7fec4Smrg   /* CHECK EXTENDED CRTC FLAG */
35571d7fec4Smrg
35671d7fec4Smrg   if (flags & GU2_VGA_FLAG_EXT_CRTC) {
35771d7fec4Smrg      /* SAVE EXTENDED CRTC REGISTERS */
35871d7fec4Smrg
35971d7fec4Smrg      for (i = 0; i < GU2_EXT_CRTC_REGS; i++) {
36071d7fec4Smrg	 gfx_outb(crtcindex, (unsigned char)(0x40 + i));
36171d7fec4Smrg	 vga->extCRTCregs[i] = gfx_inb(crtcdata);
36271d7fec4Smrg      }
36371d7fec4Smrg   }
36471d7fec4Smrg
36571d7fec4Smrg   if (flags & GU2_VGA_FLAG_PALETTE) {
36671d7fec4Smrg      /* SAVE PALETTE DATA */
36771d7fec4Smrg
36871d7fec4Smrg      for (i = 0; i < 0x100; i++) {
36971d7fec4Smrg	 gfx_outb(0x3C7, i);
37071d7fec4Smrg	 palette[i] = gfx_inb(0x3C9);
37171d7fec4Smrg      }
37271d7fec4Smrg   }
37371d7fec4Smrg
37471d7fec4Smrg   if (flags & GU2_VGA_FLAG_ATTR) {
37571d7fec4Smrg      /* SAVE Attribute  DATA */
37671d7fec4Smrg
37771d7fec4Smrg      for (i = 0; i < 21; i++) {
37871d7fec4Smrg	 gfx_inb(0x3DA);
37971d7fec4Smrg	 gfx_outb(0x3C0, i);
38071d7fec4Smrg	 ATTRregs[i] = gfx_inb(0x3C1);
38171d7fec4Smrg      }
38271d7fec4Smrg   }
38371d7fec4Smrg   /* save the VGA data */
38471d7fec4Smrg   gu2_vga_font_data(0);
38571d7fec4Smrg   return (0);
38671d7fec4Smrg}
38771d7fec4Smrg
38871d7fec4Smrg/*-----------------------------------------------------------------------------
38971d7fec4Smrg * gfx_vga_clear_extended
39071d7fec4Smrg *
39171d7fec4Smrg * This routine clears the extended SoftVGA register values to have SoftVGA
39271d7fec4Smrg * behave like standard VGA.
39371d7fec4Smrg *-----------------------------------------------------------------------------
39471d7fec4Smrg */
39571d7fec4Smrgvoid
39671d7fec4Smrggu2_vga_clear_extended(void)
39771d7fec4Smrg{
39871d7fec4Smrg   int i;
39971d7fec4Smrg   unsigned short crtcindex, crtcdata;
40071d7fec4Smrg
40171d7fec4Smrg   crtcindex = (gfx_inb(0x3CC) & 0x01) ? 0x3D4 : 0x3B4;
40271d7fec4Smrg   crtcdata = crtcindex + 1;
40371d7fec4Smrg
40471d7fec4Smrg   gfx_outb(crtcindex, 0x30);
40571d7fec4Smrg   gfx_outb(crtcdata, 0x57);
40671d7fec4Smrg   gfx_outb(crtcdata, 0x4C);
40771d7fec4Smrg   for (i = 0x41; i <= 0x4F; i++) {
40871d7fec4Smrg      gfx_outb(crtcindex, (unsigned char)i);
40971d7fec4Smrg      gfx_outb(crtcdata, 0);
41071d7fec4Smrg   }
41171d7fec4Smrg   gfx_outb(crtcindex, 0x30);
41271d7fec4Smrg   gfx_outb(crtcdata, 0x00);
41371d7fec4Smrg}
41471d7fec4Smrg
41571d7fec4Smrgvoid
41671d7fec4Smrggu2_vga_extcrtc(char offset, int reset)
41771d7fec4Smrg{
41871d7fec4Smrg   unsigned short crtcindex, crtcdata;
41971d7fec4Smrg
42071d7fec4Smrg   crtcindex = (gfx_inb(0x3CC) & 0x01) ? 0x3D4 : 0x3B4;
42171d7fec4Smrg   crtcdata = crtcindex + 1;
42271d7fec4Smrg
42371d7fec4Smrg   /* UNLOCK EXTENDED CRTC REGISTERS */
42471d7fec4Smrg
42571d7fec4Smrg   gfx_outb(crtcindex, 0x30);
42671d7fec4Smrg   gfx_outb(crtcdata, 0x57);
42771d7fec4Smrg   gfx_outb(crtcdata, 0x4C);
42871d7fec4Smrg
42971d7fec4Smrg   /* RESTORE EXTENDED CRTC REGISTERS */
43071d7fec4Smrg
43171d7fec4Smrg   gfx_outb(crtcindex, offset);
43271d7fec4Smrg   gfx_outb(crtcdata, reset);
43371d7fec4Smrg
43471d7fec4Smrg#if 0
43571d7fec4Smrg   /* LOCK EXTENDED CRTC REGISTERS */
43671d7fec4Smrg
43771d7fec4Smrg   gfx_outb(crtcindex, 0x30);
43871d7fec4Smrg   gfx_outb(crtcdata, 0x00);
43971d7fec4Smrg#endif
44071d7fec4Smrg}
44171d7fec4Smrg
44271d7fec4Smrg/*-----------------------------------------------------------------------------
44371d7fec4Smrg * gfx_vga_restore
44471d7fec4Smrg *
44571d7fec4Smrg * This routine restores the state of the VGA registers from the specified
44671d7fec4Smrg * structure.  Flags indicate what portions of the register state need to
44771d7fec4Smrg * be saved.
44871d7fec4Smrg *-----------------------------------------------------------------------------
44971d7fec4Smrg */
45071d7fec4Smrgint
45171d7fec4Smrggu2_vga_restore(gfx_vga_struct * vga, int flags)
45271d7fec4Smrg{
45371d7fec4Smrg   int i;
45471d7fec4Smrg   unsigned short crtcindex, crtcdata;
45571d7fec4Smrg
45671d7fec4Smrg   crtcindex = (gfx_inb(0x3CC) & 0x01) ? 0x3D4 : 0x3B4;
45771d7fec4Smrg   crtcdata = crtcindex + 1;
45871d7fec4Smrg
45971d7fec4Smrg   /* CHECK MISCELLANEOUS OUTPUT FLAG */
46071d7fec4Smrg
46171d7fec4Smrg   if (flags & GU2_VGA_FLAG_MISC_OUTPUT) {
46271d7fec4Smrg      /* RESTORE MISCELLANEOUS OUTPUT REGISTER VALUE */
46371d7fec4Smrg
46471d7fec4Smrg      gfx_outb(0x3C2, vga->miscOutput);
46571d7fec4Smrg   }
46671d7fec4Smrg
46771d7fec4Smrg   /* CHECK SEQ */
46871d7fec4Smrg
46971d7fec4Smrg   if (flags & GU2_VGA_FLAG_SEQ) {
47071d7fec4Smrg      /* RESTORE STANDARD CRTC REGISTERS */
47171d7fec4Smrg
47271d7fec4Smrg      for (i = 1; i < GU2_SEQ_REGS; i++) {
47371d7fec4Smrg	 gfx_outb(0x3C4, (unsigned char)i);
47471d7fec4Smrg	 gfx_outb(0x3C5, SEQregs[i]);
47571d7fec4Smrg      }
47671d7fec4Smrg   }
47771d7fec4Smrg
47871d7fec4Smrg   /* CHECK STANDARD CRTC FLAG */
47971d7fec4Smrg
48071d7fec4Smrg   if (flags & GU2_VGA_FLAG_STD_CRTC) {
48171d7fec4Smrg      /* UNLOCK STANDARD CRTC REGISTERS */
48271d7fec4Smrg
48371d7fec4Smrg      gfx_outb(crtcindex, 0x11);
48471d7fec4Smrg      gfx_outb(crtcdata, 0);
48571d7fec4Smrg
48671d7fec4Smrg      /* RESTORE STANDARD CRTC REGISTERS */
48771d7fec4Smrg
48871d7fec4Smrg      for (i = 0; i < GU2_STD_CRTC_REGS; i++) {
48971d7fec4Smrg	 gfx_outb(crtcindex, (unsigned char)i);
49071d7fec4Smrg	 gfx_outb(crtcdata, vga->stdCRTCregs[i]);
49171d7fec4Smrg      }
49271d7fec4Smrg   }
49371d7fec4Smrg
49471d7fec4Smrg   /* CHECK GDC */
49571d7fec4Smrg
49671d7fec4Smrg   if (flags & GU2_VGA_FLAG_GDC) {
49771d7fec4Smrg      /* SAVE STANDARD CRTC REGISTERS */
49871d7fec4Smrg
49971d7fec4Smrg      for (i = 0; i < GU2_GDC_REGS; i++) {
50071d7fec4Smrg	 gfx_outb(0x3CE, (unsigned char)i);
50171d7fec4Smrg	 gfx_outb(0x3CF, GDCregs[i]);
50271d7fec4Smrg      }
50371d7fec4Smrg   }
50471d7fec4Smrg
50571d7fec4Smrg   /* CHECK EXTENDED CRTC FLAG */
50671d7fec4Smrg
50771d7fec4Smrg   if (flags & GU2_VGA_FLAG_EXT_CRTC) {
50871d7fec4Smrg      /* UNLOCK EXTENDED CRTC REGISTERS */
50971d7fec4Smrg
51071d7fec4Smrg      gfx_outb(crtcindex, 0x30);
51171d7fec4Smrg      gfx_outb(crtcdata, 0x57);
51271d7fec4Smrg      gfx_outb(crtcdata, 0x4C);
51371d7fec4Smrg
51471d7fec4Smrg      /* RESTORE EXTENDED CRTC REGISTERS */
51571d7fec4Smrg
51671d7fec4Smrg      for (i = 1; i < GU2_EXT_CRTC_REGS; i++) {
51771d7fec4Smrg	 gfx_outb(crtcindex, (unsigned char)(0x40 + i));
51871d7fec4Smrg	 gfx_outb(crtcdata, vga->extCRTCregs[i]);
51971d7fec4Smrg      }
52071d7fec4Smrg
52171d7fec4Smrg      /* LOCK EXTENDED CRTC REGISTERS */
52271d7fec4Smrg
52371d7fec4Smrg      gfx_outb(crtcindex, 0x30);
52471d7fec4Smrg      gfx_outb(crtcdata, 0x00);
52571d7fec4Smrg
52671d7fec4Smrg      /* CHECK IF DIRECT FRAME BUFFER MODE (VESA MODE) */
52771d7fec4Smrg
52871d7fec4Smrg      if (vga->extCRTCregs[0x03] & 1) {
52971d7fec4Smrg	 /* SET BORDER COLOR TO BLACK */
53071d7fec4Smrg	 /* This really should be another thing saved/restored, but */
53171d7fec4Smrg	 /* Durango currently doesn't do the attr controller registers. */
53271d7fec4Smrg
53371d7fec4Smrg	 gfx_inb(0x3BA);		/* Reset flip-flop */
53471d7fec4Smrg	 gfx_inb(0x3DA);
53571d7fec4Smrg	 gfx_outb(0x3C0, 0x11);
53671d7fec4Smrg	 gfx_outb(0x3C0, 0x00);
53771d7fec4Smrg      }
53871d7fec4Smrg   }
53971d7fec4Smrg
54071d7fec4Smrg   if (flags & GU2_VGA_FLAG_PALETTE) {
54171d7fec4Smrg      /* RESTORE PALETTE DATA */
54271d7fec4Smrg
54371d7fec4Smrg      for (i = 0; i < 0x100; i++) {
54471d7fec4Smrg	 gfx_outb(0x3C8, i);
54571d7fec4Smrg	 gfx_outb(0x3C9, palette[i]);
54671d7fec4Smrg      }
54771d7fec4Smrg   }
54871d7fec4Smrg
54971d7fec4Smrg   if (flags & GU2_VGA_FLAG_ATTR) {
55071d7fec4Smrg      /* RESTORE Attribute  DATA */
55171d7fec4Smrg
55271d7fec4Smrg      for (i = 0; i < 21; i++) {
55371d7fec4Smrg	 gfx_inb(0x3DA);
55471d7fec4Smrg	 gfx_outb(0x3C0, i);
55571d7fec4Smrg	 gfx_outb(0x3C0, ATTRregs[i]);
55671d7fec4Smrg      }
55771d7fec4Smrg      /* SAVE Attribute  DATA */
55871d7fec4Smrg
55971d7fec4Smrg      for (i = 0; i < 21; i++) {
56071d7fec4Smrg	 gfx_inb(0x3DA);
56171d7fec4Smrg	 gfx_outb(0x3C0, i);
56271d7fec4Smrg      }
56371d7fec4Smrg   }
56471d7fec4Smrg
56571d7fec4Smrg   /* restore the VGA data */
56671d7fec4Smrg   gu2_vga_font_data(1);
56771d7fec4Smrg
56871d7fec4Smrg   return (0);
56971d7fec4Smrg}
57071d7fec4Smrg
57171d7fec4Smrg/* END OF FILE */
572