⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ibmmsdos.c

📁 知名gba模拟器vgba代码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* IbmMsdos.c
   This file is part of the VGB-DOS project
   Copyright (C) Marcel de Kogel (m.dekogel@student.utwente.nl), 1996
   You may not use this file for commercial purposes
   Please notify me if you make any changes to this file */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <crt0.h>
#include <go32.h>
#include <dpmi.h>
#include <dos.h>
#include <pc.h>
#include <conio.h>
#include "GB.h"
#include "IbmMsDos.h"

/* Define if you've installed ANSI.SYS on your terminal */
/* #define USE_ANSI */

extern char szGifFile[];

int _crt0_startup_flags = _CRT0_FLAG_NONMOVE_SBRK |
                          _CRT0_FLAG_LOCK_MEMORY  |
                          _CRT0_FLAG_DROP_EXE_SUFFIX;

struct _SB_Info SB_Info;
int swapbuttons=0;
int videomode=0;
int soundmode=1;
int IntSync=1;
static int OldTimer,NewTimer,ReadTimerMin;
int brightness=0;
int spritebrightness=1000,windowbrightness=1000,backgroundbrightness=1000;
unsigned short cs_alias;

static int KEY_LEFT,KEY_RIGHT,KEY_UP,KEY_DOWN,
           KEY_BUTTONA,KEY_BUTTONB,KEY_START,KEY_SELECT;
char *szKeys="CBCDC8D0381D2A2C";

#ifdef DEBUG
int nDebugKey=0;
static int showwindow=1;
#else
#define showwindow 1
#endif

#define NUM_STACKS      16
#define STACK_SIZE      8192

#ifdef DEBUG
/* Called when one of the keys 1-9 is pressed */
static void ParseDebugKey (void)
{
 const char *szRegNames[16] = {
 "LCDCONT", "LCDSTAT", "SCROLLY", "SCROLLX",
 "CURLINE", "CMPLINE", "       ", "BGRDPAL",
 "SPR0PAL", "SPR1PAL", "WNDPOSX", "WNDPOSY",
 "       ", "       ", "       ", "       " };
 int i;
 switch (nDebugKey)
 {
      case 1:
       Trace=!Trace;
       break;
      case 2:
 #ifdef USE_ANSI
       fprintf(stdout,"\033[H\033[2J");
 #endif
       fprintf(stdout,"*** REGISTERS: ***\n");
       for(i=0xFF40;i<0xFF50;i++)
        fprintf(stdout,"%s (%04Xh) = %02Xh\n",szRegNames[i-0xFF40],i,RAM[i]);
       fprintf(stdout,"ISWITCH = %02Xh\n",ISWITCH);
       fflush(stdout);
       break;
      case 3:
 #ifdef USE_ANSI
       fprintf(stdout,"\033[H\033[2J");
 #endif
       fprintf(stdout,"*** SPRITES: ***\n");
       for(i=0xFE9C;i<0xFE9C+4*40;i+=4)
        fprintf (stdout,"SPRITE %d: %d,%d   Pat %d   Attr %d\n",
                 (i-0xFE9C)/4,RAM[i+1],RAM[i],RAM[i+2],RAM[i+3]);
       fflush(stdout);
       break;
      case 4:
       showwindow=!showwindow;
       break;
 }
 nDebugKey=0;
}
#endif

/* Parse the BLASTER environment variable */
static void GetSBInfo (void)
{
 char *blaster=getenv ("BLASTER");
 memset (&SB_Info,0,sizeof(SB_Info));
 if (blaster)
 {
  strupr (blaster);
  while (*blaster)
  {
   while (*blaster==' ' || *blaster=='\t')
    ++blaster;
   switch (*blaster++)
   {
    case 'A': SB_Info.baseport=(word)strtol(blaster,NULL,16);
              break;
    case 'I': SB_Info.irq=(byte)strtol(blaster,NULL,10);
              break;
    case 'D': SB_Info.dma_low=(byte)strtol(blaster,NULL,10);
              break;
    case 'H': SB_Info.dma_high=(byte)strtol(blaster,NULL,10);
              break;
    case 'T': SB_Info.type=(byte)strtol(blaster,NULL,10);
              break;
    case 'E': SB_Info.emu_baseport=(word)strtol(blaster,NULL,16);
              break;
    case 'P': SB_Info.mpu_baseport=(word)strtol(blaster,NULL,16);
              break;
   }
   while (*blaster && *blaster!=' ' && *blaster!='\t')
    ++blaster;
  }
 }
}

/** Various variables and short functions ********************/
#define WIDTH  176
#define HEIGHT 160

int DosSelector;                /* Used by the assembly routines */
byte *XBuf,XPal[16];            /* Screen buffer and palette */

static void VGA_SetPalette (byte *pal,int start,int numcolors)
{
 int i;
 disable ();
 while ((inportb(0x3DA)&0x08)!=0); /* Wait until vertical retrace is off */
 while ((inportb(0x3DA)&0x08)==0); /* Now wait until it is on */
 outportb (0x3C8,start);
 for (i=0;i<numcolors*3;++i)
  outportb(0x3C9,pal[i]/4);
 enable ();
}

static int nOldVideoMode;
void VGA_Reset (void)            /* Reset old video mode */
{
 __dpmi_regs r;
 r.x.ax=(short)nOldVideoMode;
 __dpmi_int (0x10, &r);
}

/* For a 360x144 mode */
static unsigned char crtc_regs[24]=
{
  0x6B,0x59,0x5A,0x8E,
  0x5E,0x8A,0x5F,0x1F,
  0x00,0x41,0x00,0x00,
  0x00,0x00,0x00,0x00,
  0x3C,0x2E,0x2F,0x2D,
  0x40,0x36,0x59,0xA3
};

/* 256x200 */
static unsigned char crtc_regs_256[24]=
{
  0x4F,0x3F,0x40,0x92,
  0x44,0x10,0xBF,0x1F,
  0x00,0x41,0x00,0x00,
  0x00,0x08,0x00,0x00,
  0x9C,0x8E,0x8F,0x28,
  0x40,0x96,0xB9,0xA3
};

static void VGA_SetFullScreenMode (void)
{
 int i;
 disable ();
 while (inportb(0x3DA)&8);
 while ((inportb(0x3DA)&8)==0);
 outportw (0x3C4,0x100);                        /* sequencer reset */
 outportb (0x3C2,0x27);                         /* misc. output reg */
 outportw (0x3C4,0x300);                        /* clear sequencer reset */
 outportw (0x3D4,((crtc_regs[0x11]&0x7F)<<8)+0x11); /* deprotect regs 0-7 */
 for (i=0;i<24;++i)
  outportw (0x3D4,(crtc_regs[i]<<8)+i);
 enable ();
}

static void VGA_Set256x200 (void)
{
 int i;
 disable ();
 while (inportb(0x3DA)&8);
 while ((inportb(0x3DA)&8)==0);
 outportw (0x3C4,0x100);
 outportb (0x3C2,0x63);
 outportw (0x3C4,0x300);
 outportw (0x3D4,((crtc_regs_256[0x11]&0x7F)<<8)+0x11);
 for (i=0;i<24;++i)
  outportw (0x3D4,(crtc_regs_256[i]<<8)+i);
 enable ();
}

char *ColorNames[16];
struct ColorName_struct
{
 char *name;
 int color;
};
typedef struct ColorName_struct ColorName_t;

static ColorName_t ColorName[]=
{
 { "black"   ,0x000000 },
 { "blue"    ,0x0000FF },
 { "green"   ,0x00FF00 },
 { "cyan"    ,0x55FFFF },
 { "red"     ,0xFF0000 },
 { "magenta" ,0xFF55FF },
 { "brown"   ,0xAA5500 },
 { "orange"  ,0xFF7711 },
 { "pink"    ,0xFFAAAA },
 { "gray"    ,0xAAAAAA },
 { "yellow"  ,0xFFFF00 },
 { "white"   ,0xFFFFFF },
 { "dkgray"    ,0x555555 },
 { "dkblue"    ,0x0000AA },
 { "dkgreen"   ,0x00AA00 },
 { "dkcyan"    ,0x00AAAA },
 { "dkred"     ,0xAA0000 },
 { "dkmagenta" ,0xAA00AA },
 { NULL,-1 }
};

int ColorNameToColor (char *colorname)
{
 int tmp;
 char *pTmp;
 int j;
 tmp=-1;
 if (colorname)
 {
  if (colorname[0]=='#')
   tmp=strtoul (colorname+1,&pTmp,16);
  else
   for (j=0;ColorName[j].name;++j)
    if (!strcmp(colorname,ColorName[j].name))
     tmp=ColorName[j].color;
 }
 return tmp;
}

static void ParseColorNames (char *pal)
{
 int i,tmp;
 for (i=0;i<16;++i)
 {
  tmp=ColorNameToColor (ColorNames[i]);
  if (tmp>=0)
  {
   *pal++=(tmp>>16)&0xFF;
   *pal++=(tmp>>8)&0xFF;
   *pal++=tmp&0xFF;
  }
  else
   pal+=3;
 }
}

static void _brightness (byte *pal,int brightness)
{
 int tmp;
 tmp=(int)(unsigned)*pal;
 tmp=tmp*(brightness+200)/200;
 if (tmp>255)
  tmp=255;
 *pal=(byte)tmp;
}

/* Set mode and palette, put decoded GIF on screen */
static int VGA_Init (char *pGifPalette,char *pGifBytes)
{
 static byte fspal[256*3];
 static byte pal[64*3]={ 0,0,0,                 /* Overscan colour */
                         0xFF,0xFF,0xFF,        /* Background colours */
                         0xB0,0xB0,0xB0,
                         0x60,0x60,0x60,
                         0x00,0x00,0x00,
                         0xFF,0xFF,0xFF,        /* Sprite colours */
                         0xB0,0xB0,0xB0,
                         0x60,0x60,0x60,
                         0x00,0x00,0x00,
                         0xFF,0xFF,0xFF,        /* Window colours */
                         0xB0,0xB0,0xB0,
                         0x60,0x60,0x60,
                         0x00,0x00,0x00 };

 int a,b;
 __dpmi_regs r;
 r.x.ax=0x0F00;
 __dpmi_int (0x10,&r);
 nOldVideoMode=(int)(r.h.al & 0x7F);
 r.x.ax=0x0013;
 __dpmi_int (0x10,&r);
 if (videomode==2 || videomode==3)
 {
  VGA_SetFullScreenMode ();
 }
 else
 {
  if (videomode==4 || videomode==5)
  {
   VGA_Set256x200 ();
   videomode-=4;
  }
  if (videomode!=1)
  {
   if (pGifBytes)
   {
    VGA_SetPalette (pGifPalette,0,256);
    dosmemput (pGifBytes,64000,0xA0000);
   }
  }
  videomode=0;
 }
 ParseColorNames (pal+3);
 if (brightness<-100 || brightness>100)
  brightness=0;
 if (backgroundbrightness>100)
  backgroundbrightness=brightness;
 if (backgroundbrightness<-100 || backgroundbrightness>100)
  backgroundbrightness=0;
 for (a=1;a<5;++a)
 {
  _brightness (&pal[a*3+0],backgroundbrightness);
  _brightness (&pal[a*3+1],backgroundbrightness);
  _brightness (&pal[a*3+2],backgroundbrightness);
 }
 if (spritebrightness>100)
  spritebrightness=brightness;
 if (spritebrightness<-100 || spritebrightness>100)
  spritebrightness=0;
 for (a=5;a<9;++a)
 {
  _brightness (&pal[a*3+0],spritebrightness);
  _brightness (&pal[a*3+1],spritebrightness);
  _brightness (&pal[a*3+2],spritebrightness);
 }
 if (windowbrightness>100)
  windowbrightness=brightness;
 if (windowbrightness<-100 || windowbrightness>100)
  windowbrightness=0;
 for (a=9;a<13;++a)
 {
  _brightness (&pal[a*3+0],windowbrightness);
  _brightness (&pal[a*3+1],windowbrightness);
  _brightness (&pal[a*3+2],windowbrightness);
 }
 if (videomode==2 || videomode==3)
 {
  for (a=0;a<15;++a)
   for (b=0;b<15;++b)
    if (b==0 || videomode==3)
    {
     fspal[a*3+b*16*3+0]=pal[a*3+0];
     fspal[a*3+b*16*3+1]=pal[a*3+1];
     fspal[a*3+b*16*3+2]=pal[a*3+2];
    }
    else
    {
     fspal[a*3+b*16*3+0]=pal[a*3+0]/2+pal[b*3+0]/2;
     fspal[a*3+b*16*3+1]=pal[a*3+1]/2+pal[b*3+1]/2;
     fspal[a*3+b*16*3+2]=pal[a*3+2]/2+pal[b*3+2]/2;
    }
  VGA_SetPalette (fspal,0,256);
 }
 else
 {
  /* Handy for debugging */
  for (a=0,b=16;a<16;++a,++b)
  {
   pal[b*3+0]=pal[a*3+0];
   pal[b*3+1]=255;
   pal[b*3+2]=pal[a*3+2];
  }
  for (a=0,b=32;a<32;++a,++b)
  {
   pal[b*3+0]=255;
   pal[b*3+1]=pal[a*3+1];
   pal[b*3+2]=pal[a*3+2];
  }
  VGA_SetPalette (pal,0,64);
 }
 return 1;
}

static __volatile__ int PausePressed=0;
static __volatile__ byte keybstatus[256];            /* 1 if key is pressed */
static _go32_dpmi_seginfo newirqkeyb,oldirqkeyb;

void keyb_interrupt (void)
{
 unsigned code;
 static int extkey;
 code=inportb (0x60);           /* get scancode */
 if (code<0xE0)                 /* ignore codes >0xE0 */
 {
  if (code & 0x80)              /* key is released */
  {
   code&=0x7F;
   if (extkey)
    keybstatus[code+128]=0;
   else
    keybstatus[code]=0;
  }
  else                          /* key is pressed */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -