main.c revision 28328
128328Ssos/*-
228328Ssos * Copyright (c) 1991-1997 S�ren Schmidt
328328Ssos * All rights reserved.
428328Ssos *
528328Ssos * Redistribution and use in source and binary forms, with or without
628328Ssos * modification, are permitted provided that the following conditions
728328Ssos * are met:
828328Ssos * 1. Redistributions of source code must retain the above copyright
928328Ssos *    notice, this list of conditions and the following disclaimer
1028328Ssos *    in this position and unchanged.
1128328Ssos * 2. Redistributions in binary form must reproduce the above copyright
1228328Ssos *    notice, this list of conditions and the following disclaimer in the
1328328Ssos *    documentation and/or other materials provided with the distribution.
1428328Ssos * 3. The name of the author may not be used to endorse or promote products
1528328Ssos *    derived from this software withough specific prior written permission
1628328Ssos *
1728328Ssos * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
1828328Ssos * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
1928328Ssos * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
2028328Ssos * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
2128328Ssos * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
2228328Ssos * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
2328328Ssos * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
2428328Ssos * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
2528328Ssos * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
2628328Ssos * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2728328Ssos *
2828328Ssos *  $Id: main.c,v 1.14 1997/08/15 12:32:59 sos Exp $
2928328Ssos */
3028328Ssos
3128328Ssos#include <stdio.h>
3228328Ssos#include <sys/types.h>
3328328Ssos#include <sys/signal.h>
3428328Ssos#include <sys/file.h>
3528328Ssos#include <sys/ioctl.h>
3628328Ssos#include <sys/mman.h>
3728328Ssos#include <machine/console.h>
3828328Ssos#include "vgl.h"
3928328Ssos
4028328SsosVGLBitmap *VGLDisplay;
4128328Ssos
4228328Ssosstatic int VGLMode;
4328328Ssosstatic int VGLOldMode;
4428328Ssosstatic byte *VGLBuf;
4528328Ssosstatic byte *VGLMem;
4628328Ssosstatic int VGLSwitchPending;
4728328Ssosstatic int VGLOnDisplay;
4828328Ssos
4928328Ssosvoid
5028328SsosVGLEnd()
5128328Ssos{
5228328Ssosstruct vt_mode smode;
5328328Ssos
5428328Ssos/*
5528328Ssos  while (!VGLOnDisplay) pause();
5628328Ssos  VGLCheckSwitch();;
5728328Ssos*/
5828328Ssos  outb(0x3c4, 0x02);
5928328Ssos  outb(0x3c5, 0x0f);
6028328Ssos  bzero(VGLMem, 64*1024);
6128328Ssos  ioctl(0, _IO('S', VGLOldMode), 0);
6228328Ssos  ioctl(0, KDDISABIO, 0);
6328328Ssos  ioctl(0, KDSETMODE, KD_TEXT);
6428328Ssos  smode.mode = VT_AUTO;
6528328Ssos  ioctl(0, VT_SETMODE, &smode);
6628328Ssos  free(VGLBuf);
6728328Ssos  free(VGLDisplay);
6828328Ssos}
6928328Ssos
7028328Ssosstatic void
7128328SsosVGLAbort()
7228328Ssos{
7328328Ssos  VGLEnd();
7428328Ssos  exit(0);
7528328Ssos}
7628328Ssos
7728328Ssosstatic void
7828328SsosVGLSwitch()
7928328Ssos{
8028328Ssos  if (!VGLOnDisplay)
8128328Ssos    VGLOnDisplay = 1;
8228328Ssos  else
8328328Ssos    VGLOnDisplay = 0;
8428328Ssos  VGLSwitchPending = 1;
8528328Ssos  signal(SIGUSR1, VGLSwitch);
8628328Ssos}
8728328Ssos
8828328Ssosint
8928328SsosVGLInit(int mode)
9028328Ssos{
9128328Ssos  struct vt_mode smode;
9228328Ssos  struct winsize winsz;
9328328Ssos  int error;
9428328Ssos
9528328Ssos  signal(SIGUSR1, VGLSwitch);
9628328Ssos  signal(SIGINT, VGLAbort);
9728328Ssos  signal(SIGSEGV, VGLAbort);
9828328Ssos  signal(SIGBUS, VGLAbort);
9928328Ssos
10028328Ssos  VGLOnDisplay = 1;
10128328Ssos  VGLSwitchPending = 0;
10228328Ssos
10328328Ssos  ioctl(0, CONS_GET, &VGLOldMode);
10428328Ssos
10528328Ssos  VGLMem = (byte*)mmap(0, 0x10000, PROT_READ|PROT_WRITE, MAP_FILE,
10628328Ssos                          open("/dev/mem", O_RDWR), 0xA0000);
10728328Ssos  if (VGLMem <= (byte*)0)
10828328Ssos    return 1;
10928328Ssos
11028328Ssos  VGLBuf = (byte*)malloc(256*1024);
11128328Ssos  if (VGLBuf == NULL)
11228328Ssos    return 1;
11328328Ssos
11428328Ssos  VGLDisplay = (VGLBitmap*) malloc(sizeof(VGLBitmap));
11528328Ssos  if (VGLDisplay == NULL) {
11628328Ssos    free(VGLBuf);
11728328Ssos    return 1;
11828328Ssos  }
11928328Ssos
12028328Ssos  switch (mode) {
12128328Ssos  case SW_BG640x480: case SW_CG640x480:
12228328Ssos    VGLDisplay->Type = VIDBUF4;
12328328Ssos    break;
12428328Ssos  case SW_VGA_CG320:
12528328Ssos    VGLDisplay->Type = VIDBUF8;
12628328Ssos    break;
12728328Ssos  case SW_VGA_MODEX:
12828328Ssos    VGLDisplay->Type = VIDBUF8X;
12928328Ssos    break;
13028328Ssos  default:
13128328Ssos    VGLEnd();
13228328Ssos    return 1;
13328328Ssos  }
13428328Ssos
13528328Ssos  if ((error = ioctl(0, KDENABIO, 0)))
13628328Ssos    return error;
13728328Ssos
13828328Ssos  ioctl(0, VT_WAITACTIVE, 0);
13928328Ssos  ioctl(0, KDSETMODE, KD_GRAPHICS);
14028328Ssos  if ((error = ioctl(0, mode, 0))) {
14128328Ssos    ioctl(0, KDSETMODE, KD_TEXT);
14228328Ssos    ioctl(0, KDDISABIO, 0);
14328328Ssos    return error;
14428328Ssos  }
14528328Ssos
14628328Ssos  VGLMode = mode;
14728328Ssos
14828328Ssos  outb(0x3c4, 0x02);
14928328Ssos  outb(0x3c5, 0x0f);
15028328Ssos  bzero(VGLMem, 64*1024);
15128328Ssos
15228328Ssos  if (ioctl(0, TIOCGWINSZ, &winsz)) {
15328328Ssos    VGLEnd();
15428328Ssos    return 1;
15528328Ssos  }
15628328Ssos
15728328Ssos  VGLDisplay->Bitmap = VGLMem;
15828328Ssos  VGLDisplay->Xsize = winsz.ws_xpixel;
15928328Ssos  VGLDisplay->Ysize = winsz.ws_ypixel;
16028328Ssos  VGLSavePalette();
16128328Ssos
16228328Ssos  smode.mode = VT_PROCESS;
16328328Ssos  smode.waitv = 0;
16428328Ssos  smode.relsig = SIGUSR1;
16528328Ssos  smode.acqsig = SIGUSR1;
16628328Ssos  smode.frsig  = SIGINT;
16728328Ssos  if (ioctl(0, VT_SETMODE, &smode) == -1) {
16828328Ssos    VGLEnd();
16928328Ssos    return 1;
17028328Ssos  }
17128328Ssos  VGLTextSetFontFile((byte*)0);
17228328Ssos  return 0;
17328328Ssos}
17428328Ssos
17528328Ssosvoid
17628328SsosVGLCheckSwitch()
17728328Ssos{
17828328Ssos  if (VGLSwitchPending) {
17928328Ssos    int i;
18028328Ssos
18128328Ssos    VGLSwitchPending = 0;
18228328Ssos    if (VGLOnDisplay) {
18328328Ssos      ioctl(0, KDENABIO, 0);
18428328Ssos      ioctl(0, KDSETMODE, KD_GRAPHICS);
18528328Ssos      ioctl(0, VGLMode, 0);
18628328Ssos      outb(0x3c6, 0xff);
18728328Ssos      for (i=0; i<4; i++) {
18828328Ssos        outb(0x3c4, 0x02);
18928328Ssos        outb(0x3c5, 0x01<<i);
19028328Ssos        bcopy(&VGLBuf[i*64*1024], VGLMem, 64*1024);
19128328Ssos      }
19228328Ssos      VGLRestorePalette();
19328328Ssos      ioctl(0, VT_RELDISP, VT_ACKACQ);
19428328Ssos      VGLDisplay->Bitmap = VGLMem;
19528328Ssos      switch (VGLMode) {
19628328Ssos      case SW_BG640x480: case SW_CG640x480:
19728328Ssos        VGLDisplay->Type = VIDBUF4;
19828328Ssos        break;
19928328Ssos      case SW_VGA_CG320:
20028328Ssos        VGLDisplay->Type = VIDBUF8;
20128328Ssos        break;
20228328Ssos      case SW_VGA_MODEX:
20328328Ssos        VGLDisplay->Type = VIDBUF8X;
20428328Ssos        break;
20528328Ssos      default:
20628328Ssos        VGLDisplay->Type = VIDBUF8;			/* XXX */
20728328Ssos        break;
20828328Ssos      }
20928328Ssos    }
21028328Ssos    else {
21128328Ssos      for (i=0; i<4; i++) {
21228328Ssos        outb(0x3ce, 0x04);
21328328Ssos        outb(0x3cf, i);
21428328Ssos        bcopy(VGLMem, &VGLBuf[i*64*1024], 64*1024);
21528328Ssos      }
21628328Ssos      ioctl(0, VGLOldMode, 0);
21728328Ssos      ioctl(0, KDSETMODE, KD_TEXT);
21828328Ssos      ioctl(0, KDDISABIO, 0);
21928328Ssos      ioctl(0, VT_RELDISP, VT_TRUE);
22028328Ssos      VGLDisplay->Bitmap = VGLBuf;
22128328Ssos      VGLDisplay->Type = MEMBUF;
22228328Ssos    }
22328328Ssos  }
22428328Ssos  while (!VGLOnDisplay) pause();
22528328Ssos}
22628328Ssos
227