PCem

changeset 20:62da6e2cb833

Mach64 changes : - No longer crashes PCem when remapping (mostly seen when changing resolution in Windows) - Added PCI registers - Added LFB emulation (PCI only) - Source pattern modes now work correctly - Vsync flag now emulated correctly - Scrolling in accelerator modes now works correctly Also disabled some debug.
author TomW
date Sat Oct 12 16:20:27 2013 +0100
parents 925de5938e9a
children b162911b1c10
files src/sis496.c src/vid_ati_eeprom.c src/vid_ati_mach64.c src/vid_ics2595.c src/vid_svga.c src/win-keyboard.cc
diffstat 6 files changed, 293 insertions(+), 83 deletions(-) [+]
line diff
     1.1 --- a/src/sis496.c	Sat Aug 24 15:11:30 2013 +0100
     1.2 +++ b/src/sis496.c	Sat Oct 12 16:20:27 2013 +0100
     1.3 @@ -61,7 +61,7 @@
     1.4  void sis496_write(int func, int addr, uint8_t val, void *p)
     1.5  {
     1.6          sis496_t *sis496 = (sis496_t *)p;
     1.7 -pclog("sis496_write : addr=%02x val=%02x\n", addr, val);
     1.8 +//pclog("sis496_write : addr=%02x val=%02x\n", addr, val);
     1.9          switch (addr)
    1.10          {
    1.11                  case 0x44: /*Shadow configure*/
     2.1 --- a/src/vid_ati_eeprom.c	Sat Aug 24 15:11:30 2013 +0100
     2.2 +++ b/src/vid_ati_eeprom.c	Sat Oct 12 16:20:27 2013 +0100
     2.3 @@ -54,7 +54,7 @@
     2.4  void ati_eeprom_write(ati_eeprom_t *eeprom, int ena, int clk, int dat)
     2.5  {
     2.6          int c;
     2.7 -        pclog("EEPROM write %i %i %i\n", ena, clk, dat);
     2.8 +//        pclog("EEPROM write %i %i %i\n", ena, clk, dat);
     2.9          if (!ena)
    2.10          {
    2.11                  eeprom->out = 1;
    2.12 @@ -70,7 +70,7 @@
    2.13                  }
    2.14                  else if (ena)
    2.15                  {
    2.16 -                        pclog("EEPROM receive %i %i %i\n", ena, clk, dat);
    2.17 +//                        pclog("EEPROM receive %i %i %i\n", ena, clk, dat);
    2.18                          switch (eeprom->state)
    2.19                          {
    2.20                                  case EEPROM_WAIT:
    2.21 @@ -83,7 +83,7 @@
    2.22                                  eeprom->count--;
    2.23                                  if (!eeprom->count)
    2.24                                  {
    2.25 -                                        pclog("EEPROM opcode - %i\n", eeprom->opcode);
    2.26 +//                                        pclog("EEPROM opcode - %i\n", eeprom->opcode);
    2.27                                          switch (eeprom->opcode)
    2.28                                          {
    2.29                                                  case EEPROM_OP_WRITE:
    2.30 @@ -115,11 +115,11 @@
    2.31                                  eeprom->count--;
    2.32                                  if (!eeprom->count)
    2.33                                  {
    2.34 -                                        pclog("EEPROM dat - %02X\n", eeprom->dat);
    2.35 +//                                        pclog("EEPROM dat - %02X\n", eeprom->dat);
    2.36                                          switch (eeprom->opcode)
    2.37                                          {
    2.38                                                  case EEPROM_OP_WRITE:
    2.39 -                                                pclog("EEPROM_OP_WRITE addr %02X eeprom_dat %04X\n", (eeprom->dat >> 16) & (eeprom->type ? 255 : 63), eeprom->dat & 0xffff);
    2.40 +//                                                pclog("EEPROM_OP_WRITE addr %02X eeprom_dat %04X\n", (eeprom->dat >> 16) & (eeprom->type ? 255 : 63), eeprom->dat & 0xffff);
    2.41                                                  if (!eeprom->wp)
    2.42                                                  {
    2.43                                                          eeprom->data[(eeprom->dat >> 16) & (eeprom->type ? 255 : 63)] = eeprom->dat & 0xffff;
    2.44 @@ -133,10 +133,10 @@
    2.45                                                  eeprom->count = 17;
    2.46                                                  eeprom->state = EEPROM_OUTPUT;
    2.47                                                  eeprom->dat = eeprom->data[eeprom->dat];
    2.48 -                                                pclog("Trigger EEPROM_OUTPUT %04X\n", eeprom->dat);
    2.49 +//                                                pclog("Trigger EEPROM_OUTPUT %04X\n", eeprom->dat);
    2.50                                                  break;
    2.51                                                  case EEPROM_OP_EW:
    2.52 -                                                pclog("EEPROM_OP_EW %i\n", eeprom->dat);
    2.53 +//                                                pclog("EEPROM_OP_EW %i\n", eeprom->dat);
    2.54                                                  switch (eeprom->dat)
    2.55                                                  {
    2.56                                                          case EEPROM_OP_EWDS:
    2.57 @@ -162,7 +162,7 @@
    2.58                                                  break;
    2.59  
    2.60                                                  case EEPROM_OP_ERASE:
    2.61 -                                                pclog("EEPROM_OP_ERASE %i\n", eeprom->dat);
    2.62 +//                                                pclog("EEPROM_OP_ERASE %i\n", eeprom->dat);
    2.63                                                  if (!eeprom->wp)
    2.64                                                  {
    2.65                                                          eeprom->data[eeprom->dat] = 0xffff;
    2.66 @@ -173,7 +173,7 @@
    2.67                                                  break;
    2.68  
    2.69                                                  case EEPROM_OP_WRALMAIN:
    2.70 -                                                pclog("EEPROM_OP_WRAL %04X\n", eeprom->dat);
    2.71 +//                                                pclog("EEPROM_OP_WRAL %04X\n", eeprom->dat);
    2.72                                                  if (!eeprom->wp)
    2.73                                                  {
    2.74                                                          for (c = 0; c < 256; c++)
    2.75 @@ -199,11 +199,11 @@
    2.76                                  case EEPROM_OUTPUT:
    2.77                                  eeprom->out = (eeprom->dat & 0x10000) ? 1 : 0;
    2.78                                  eeprom->dat <<= 1;
    2.79 -                                pclog("EEPROM_OUTPUT - data %i\n", eeprom->out);
    2.80 +//                                pclog("EEPROM_OUTPUT - data %i\n", eeprom->out);
    2.81                                  eeprom->count--;
    2.82                                  if (!eeprom->count)
    2.83                                  {
    2.84 -                                        pclog("EEPROM_OUTPUT complete\n");
    2.85 +//                                        pclog("EEPROM_OUTPUT complete\n");
    2.86                                          eeprom->state = EEPROM_IDLE;
    2.87                                  }
    2.88                                  break;
     3.1 --- a/src/vid_ati_mach64.c	Sat Aug 24 15:11:30 2013 +0100
     3.2 +++ b/src/vid_ati_mach64.c	Sat Oct 12 16:20:27 2013 +0100
     3.3 @@ -4,6 +4,7 @@
     3.4  #include "device.h"
     3.5  #include "io.h"
     3.6  #include "mem.h"
     3.7 +#include "pci.h"
     3.8  #include "video.h"
     3.9  #include "vid_svga.h"
    3.10  #include "vid_ati68860_ramdac.h"
    3.11 @@ -12,16 +13,14 @@
    3.12  #include "vid_svga_render.h"
    3.13  
    3.14  //#define MACH64_DEBUG
    3.15 -void mach64_write(uint32_t addr, uint8_t val, void *priv);
    3.16 -uint8_t mach64_read(uint32_t addr, void *priv);
    3.17  
    3.18  typedef struct mach64_t
    3.19  {
    3.20 -        svga_t svga;
    3.21          ati68860_ramdac_t ramdac;
    3.22          ati_eeprom_t eeprom;
    3.23          ics2595_t ics2595;
    3.24 -
    3.25 +        svga_t svga;
    3.26 +        
    3.27          uint8_t regs[256];
    3.28          int index;
    3.29  
    3.30 @@ -81,22 +80,28 @@
    3.31          
    3.32          uint32_t scratch_reg0, scratch_reg1;
    3.33  
    3.34 -        uint32_t src_cntl;        
    3.35 +        uint32_t src_cntl;
    3.36          uint32_t src_off_pitch;
    3.37          uint32_t src_y_x;
    3.38 +        uint32_t src_y_x_start;
    3.39 +        uint32_t src_height1_width1, src_height2_width2;
    3.40  
    3.41 -        uint8_t stat;
    3.42 -        
    3.43 +
    3.44 +        uint32_t linear_base, old_linear_base;
    3.45 +
    3.46          struct
    3.47          {
    3.48                  int op;
    3.49                  
    3.50                  int dst_x, dst_y;
    3.51 -                int dst_x_start;
    3.52 +                int dst_x_start, dst_y_start;
    3.53                  int src_x, src_y;
    3.54 -                int src_x_start;
    3.55 +                int src_x_start, src_y_start;
    3.56                  int xinc, yinc;
    3.57                  int x_count, y_count;
    3.58 +                int src_x_count, src_y_count;
    3.59 +                int src_width1, src_height1;
    3.60 +                int src_width2, src_height2;
    3.61                  uint32_t src_offset, src_pitch;
    3.62                  uint32_t dst_offset, dst_pitch;                
    3.63                  int mix_bg, mix_fg;
    3.64 @@ -149,6 +154,13 @@
    3.65          OP_LINE
    3.66  };
    3.67  
    3.68 +enum
    3.69 +{
    3.70 +        SRC_PATT_EN     = 1,
    3.71 +        SRC_PATT_ROT_EN = 2,
    3.72 +        SRC_LINEAR_EN   = 4
    3.73 +};
    3.74 +
    3.75  static int mach64_width[6] = {0, 0, 0, 1, 1, 2};
    3.76  
    3.77  enum
    3.78 @@ -156,6 +168,10 @@
    3.79          DST_24_ROT_EN = 0x80
    3.80  };
    3.81  
    3.82 +void mach64_write(uint32_t addr, uint8_t val, void *priv);
    3.83 +uint8_t mach64_read(uint32_t addr, void *priv);
    3.84 +void mach64_updatemapping(mach64_t *mach64);
    3.85 +
    3.86  uint8_t  mach64_ext_readb(uint32_t addr, void *priv);
    3.87  uint16_t mach64_ext_readw(uint32_t addr, void *priv);
    3.88  uint32_t mach64_ext_readl(uint32_t addr, void *priv);
    3.89 @@ -190,30 +206,10 @@
    3.90                  case 0x3cf:
    3.91                  if (svga->gdcaddr == 6)
    3.92                  {
    3.93 -                        if ((svga->gdcreg[6] & 0xc) != (val & 0xc))
    3.94 -                        {
    3.95 -                                mem_removehandler(0xa0000, 0x20000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
    3.96 -                                mem_removehandler(0xa0000, 0x20000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
    3.97 -                                mem_removehandler(0xbc000, 0x04000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
    3.98 -//                                pclog("Write mapping %02X\n", val);
    3.99 -                                switch (val & 0xc)
   3.100 -                                {
   3.101 -                                        case 0x0: /*128k at A0000*/
   3.102 -                                        mem_sethandler(0xa0000, 0x10000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
   3.103 -                                        mem_sethandler(0xbc000, 0x04000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
   3.104 -                                        break;
   3.105 -                                        case 0x4: /*64k at A0000*/
   3.106 -                                        mem_sethandler(0xa0000, 0x10000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
   3.107 -                                        break;
   3.108 -                                        case 0x8: /*32k at B0000*/
   3.109 -                                        mem_sethandler(0xb0000, 0x08000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
   3.110 -                                        break;
   3.111 -                                        case 0xC: /*32k at B8000*/
   3.112 -                                        mem_sethandler(0xb8000, 0x08000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
   3.113 -                                        break;
   3.114 -                                }
   3.115 -                        }
   3.116 +                        uint8_t old_val = svga->gdcreg[6];
   3.117                          svga->gdcreg[6] = val;
   3.118 +                        if ((svga->gdcreg[6] & 0xc) != (old_val & 0xc))
   3.119 +                                mach64_updatemapping(mach64);
   3.120                          return;
   3.121                  }
   3.122                  break;
   3.123 @@ -280,8 +276,9 @@
   3.124                  svga->vsyncstart = (mach64->crtc_v_sync_strt_wid & 2047) + 1;
   3.125                  svga->rowoffset = (mach64->crtc_off_pitch >> 22);
   3.126                  svga->clock = cpuclock / mach64->ics2595.output_clock;
   3.127 -                svga->ma = (mach64->crtc_off_pitch & 0x1fffff) * 2;
   3.128 +                svga->ma_latch = (mach64->crtc_off_pitch & 0x1fffff) * 2;
   3.129                  svga->linedbl = svga->rowcount = 0;
   3.130 +                svga->split = 0xffffff;
   3.131  //                svga_htotal <<= 1;
   3.132  //                svga_hdisp <<= 1;
   3.133                  svga->rowoffset <<= 1;                
   3.134 @@ -317,10 +314,47 @@
   3.135                          break;
   3.136                  }
   3.137                  
   3.138 -  //              pclog("mach64_recalctimings : frame %i,%i disp %i,%i vsync at %i rowoffset %i pixel clock %f MA %08X\n", svga->htotal, svga->vtotal, svga->hdisp, svga->dispend, svga->vsyncstart, svga->rowoffset, svga->clock, svga->ma);
   3.139 +//                pclog("mach64_recalctimings : frame %i,%i disp %i,%i vsync at %i rowoffset %i pixel clock %f MA %08X\n", svga->htotal, svga->vtotal, svga->hdisp, svga->dispend, svga->vsyncstart, svga->rowoffset, svga->clock, svga->ma);
   3.140          }
   3.141  }
   3.142  
   3.143 +void mach64_updatemapping(mach64_t *mach64)
   3.144 +{
   3.145 +        svga_t *svga = &mach64->svga;
   3.146 +        mem_removehandler(0xa0000, 0x10000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
   3.147 +        mem_removehandler(0xa0000, 0x20000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
   3.148 +        mem_removehandler(0xbc000, 0x04000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
   3.149 +        if (mach64->old_linear_base >= (mem_size << 20))
   3.150 +        {
   3.151 +                mem_removehandler(mach64->old_linear_base, (8 << 20) - 0x4000, svga_read_linear, svga_readw_linear, svga_readl_linear, svga_write_linear, svga_writew_linear, svga_writel_linear,  svga);
   3.152 +                mem_removehandler(mach64->old_linear_base + ((8 << 20) - 0x4000), 0x4000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
   3.153 +        }
   3.154 +//        pclog("Write mapping %02X\n", val);
   3.155 +        switch (svga->gdcreg[6] & 0xc)
   3.156 +        {
   3.157 +                case 0x0: /*128k at A0000*/
   3.158 +                mem_sethandler(0xa0000, 0x10000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
   3.159 +                mem_sethandler(0xbc000, 0x04000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
   3.160 +                break;
   3.161 +                case 0x4: /*64k at A0000*/
   3.162 +                mem_sethandler(0xa0000, 0x10000, mach64_read, NULL, NULL, mach64_write, NULL, NULL,  mach64);
   3.163 +                break;
   3.164 +                case 0x8: /*32k at B0000*/
   3.165 +                mem_sethandler(0xb0000, 0x08000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
   3.166 +                break;
   3.167 +                case 0xC: /*32k at B8000*/
   3.168 +                mem_sethandler(0xb8000, 0x08000, svga_read, svga_readw, svga_readl, svga_write, svga_writew, svga_writel,  svga);
   3.169 +                break;
   3.170 +        }
   3.171 +        if (mach64->linear_base >= (mem_size << 20))
   3.172 +        {
   3.173 +                mem_sethandler(mach64->linear_base, (8 << 20) - 0x4000, svga_read_linear, svga_readw_linear, svga_readl_linear, svga_write_linear, svga_writew_linear, svga_writel_linear,  svga);
   3.174 +                mem_sethandler(mach64->linear_base + ((8 << 20) - 0x4000), 0x4000, mach64_ext_readb, mach64_ext_readw, mach64_ext_readl, mach64_ext_writeb, mach64_ext_writew, mach64_ext_writel,  mach64);
   3.175 +//                pclog("Mach64 LFB %08X\n", mach64->linear_base);
   3.176 +        }
   3.177 +        mach64->old_linear_base = mach64->linear_base;
   3.178 +}
   3.179 +
   3.180  #define READ8(addr, var)        switch ((addr) & 3)                                     \
   3.181                                  {                                                       \
   3.182                                          case 0: ret = (var) & 0xff;         break;      \
   3.183 @@ -340,24 +374,50 @@
   3.184  void mach64_cursor_dump(mach64_t *mach64)
   3.185  {
   3.186          svga_t *svga = &mach64->svga;
   3.187 -        pclog("Mach64 cursor :\n");
   3.188 -        pclog("Ena = %i X = %i Y = %i Addr = %05X Xoff = %i Yoff = %i\n", svga->hwcursor.ena, svga->hwcursor.x, svga->hwcursor.y, svga->hwcursor.addr, svga->hwcursor.xoff, svga->hwcursor.yoff);
   3.189 +/*        pclog("Mach64 cursor :\n");
   3.190 +        pclog("Ena = %i X = %i Y = %i Addr = %05X Xoff = %i Yoff = %i\n", svga->hwcursor.ena, svga->hwcursor.x, svga->hwcursor.y, svga->hwcursor.addr, svga->hwcursor.xoff, svga->hwcursor.yoff);*/
   3.191  }
   3.192  
   3.193  void mach64_start_fill(mach64_t *mach64)
   3.194  {
   3.195          int x, y;
   3.196          
   3.197 -        mach64->accel.dst_x = (mach64->dst_y_x >> 16) & 0xfff;
   3.198 -        mach64->accel.dst_y =  mach64->dst_y_x        & 0xfff;
   3.199 +        mach64->accel.dst_x = 0;
   3.200 +        mach64->accel.dst_y = 0;
   3.201 +        mach64->accel.dst_x_start = (mach64->dst_y_x >> 16) & 0xfff;
   3.202 +        mach64->accel.dst_y_start =  mach64->dst_y_x        & 0xfff;
   3.203  
   3.204          mach64->accel.dst_width  = (mach64->dst_height_width >> 16) & 0x1fff;
   3.205          mach64->accel.dst_height =  mach64->dst_height_width        & 0x1fff;        
   3.206          mach64->accel.x_count = mach64->accel.dst_width;
   3.207          
   3.208 -        mach64->accel.src_x = (mach64->src_y_x >> 16) & 0xfff;
   3.209 -        mach64->accel.src_y =  mach64->src_y_x        & 0xfff;
   3.210 +        mach64->accel.src_x = 0;
   3.211 +        mach64->accel.src_y = 0;
   3.212 +        mach64->accel.src_x_start = (mach64->src_y_x >> 16) & 0xfff;
   3.213 +        mach64->accel.src_y_start =  mach64->src_y_x        & 0xfff;
   3.214 +        if (mach64->src_cntl & SRC_LINEAR_EN)
   3.215 +                mach64->accel.src_x_count = 0x7ffffff; /*Essentially infinite*/
   3.216 +        else
   3.217 +                mach64->accel.src_x_count = (mach64->src_height1_width1 >> 16) & 0x7fff;
   3.218 +        if (!(mach64->src_cntl & SRC_PATT_EN))
   3.219 +                mach64->accel.src_y_count = 0x7ffffff; /*Essentially infinite*/
   3.220 +        else
   3.221 +                mach64->accel.src_y_count = mach64->src_height1_width1 & 0x1fff;
   3.222  
   3.223 +        mach64->accel.src_width1  = (mach64->src_height1_width1 >> 16) & 0x7fff;
   3.224 +        mach64->accel.src_height1 =  mach64->src_height1_width1        & 0x1fff;        
   3.225 +        mach64->accel.src_width2  = (mach64->src_height2_width2 >> 16) & 0x7fff;
   3.226 +        mach64->accel.src_height2 =  mach64->src_height2_width2        & 0x1fff;        
   3.227 +
   3.228 +#ifdef MACH64_DEBUG
   3.229 +        pclog("src %i %i  %i %i  %08X %08X\n", mach64->accel.src_x_count,
   3.230 +                                               mach64->accel.src_y_count,
   3.231 +                                               mach64->accel.src_width1,
   3.232 +                                               mach64->accel.src_height1,
   3.233 +                                               mach64->src_height1_width1,
   3.234 +                                               mach64->src_height2_width2);
   3.235 +#endif
   3.236 +                                               
   3.237          mach64->accel.src_pitch  = (mach64->src_off_pitch >> 22) * 8;
   3.238          mach64->accel.src_offset = (mach64->src_off_pitch & 0xfffff) * 8;
   3.239  
   3.240 @@ -385,9 +445,6 @@
   3.241          
   3.242          mach64->accel.src_offset >>= mach64->accel.src_size;
   3.243          mach64->accel.dst_offset >>= mach64->accel.dst_size;
   3.244 -
   3.245 -        mach64->accel.src_x_start = mach64->accel.src_x;
   3.246 -        mach64->accel.dst_x_start = mach64->accel.dst_x;
   3.247                  
   3.248  /*        if (mach64->accel.source_fg == SRC_BLITSRC || mach64->accel.source_bg == SRC_BLITSRC)
   3.249          {*/
   3.250 @@ -557,6 +614,8 @@
   3.251                          uint32_t src_dat, dest_dat;
   3.252                          uint32_t host_dat;
   3.253                          int mix;
   3.254 +                        int dst_x = mach64->accel.dst_x + mach64->accel.dst_x_start;
   3.255 +                        int dst_y = mach64->accel.dst_y + mach64->accel.dst_y_start;
   3.256                  
   3.257                          if (mach64->accel.source_host)
   3.258                          {
   3.259 @@ -586,24 +645,27 @@
   3.260                                  cpu_dat <<= 1;
   3.261                                  break;
   3.262                                  case MONO_SRC_PAT:
   3.263 -                                mix = mach64->accel.pattern[mach64->accel.dst_y & 7][mach64->accel.dst_x & 7];
   3.264 +                                mix = mach64->accel.pattern[dst_y & 7][dst_x & 7];
   3.265                                  break;
   3.266                                  case MONO_SRC_1:
   3.267                                  default:
   3.268                                  mix = 1;
   3.269                                  break;
   3.270                          }
   3.271 -                
   3.272 -                        if (mach64->accel.dst_x >= mach64->accel.sc_left && mach64->accel.dst_x <= mach64->accel.sc_right &&
   3.273 -                            mach64->accel.dst_y >= mach64->accel.sc_top  && mach64->accel.dst_y <= mach64->accel.sc_bottom)
   3.274 +
   3.275 +                        if (dst_x >= mach64->accel.sc_left && dst_x <= mach64->accel.sc_right &&
   3.276 +                            dst_y >= mach64->accel.sc_top  && dst_y <= mach64->accel.sc_bottom)
   3.277                          {
   3.278 +                                int src_x = mach64->accel.src_x + mach64->accel.src_x_start;
   3.279 +                                int src_y = mach64->accel.src_y + mach64->accel.src_y_start;
   3.280 +                                
   3.281                                  switch (mix ? mach64->accel.source_fg : mach64->accel.source_bg)
   3.282                                  {
   3.283                                          case SRC_HOST:
   3.284                                          src_dat = host_dat;
   3.285                                          break;
   3.286                                          case SRC_BLITSRC:
   3.287 -                                        READ(mach64->accel.src_offset + (mach64->accel.src_y * mach64->accel.src_pitch) + mach64->accel.src_x, src_dat, mach64->accel.src_size);
   3.288 +                                        READ(mach64->accel.src_offset + (src_y * mach64->accel.src_pitch) + src_x, src_dat, mach64->accel.src_size);
   3.289                                          break;
   3.290                                          case SRC_FG:
   3.291                                          src_dat = mach64->accel.dp_frgd_clr;
   3.292 @@ -616,15 +678,11 @@
   3.293                                          break;
   3.294                                  }
   3.295                  
   3.296 -                                READ(mach64->accel.dst_offset + (mach64->accel.dst_y * mach64->accel.dst_pitch) + mach64->accel.dst_x, dest_dat, mach64->accel.dst_size);
   3.297 +                                READ(mach64->accel.dst_offset + (dst_y * mach64->accel.dst_pitch) + dst_x, dest_dat, mach64->accel.dst_size);
   3.298  
   3.299 -//                                pclog("Blit %i,%i %i,%i  %X %X  %i  %02X %02X %i ", mach64->accel.src_x, mach64->accel.src_y, mach64->accel.dst_x, mach64->accel.dst_y,  (mach64->accel.src_offset + (mach64->accel.src_y * mach64->accel.src_pitch) + mach64->accel.src_x) & 0x7fffff, (mach64->accel.dst_offset + (mach64->accel.dst_y * mach64->accel.dst_pitch) + mach64->accel.dst_x) & 0x7fffff, count, src_dat, dest_dat, mix);
   3.300 -                                
   3.301                                  MIX
   3.302  
   3.303 -//                                pclog("%02X  %i\n", dest_dat, mach64->accel.dst_height);
   3.304 -
   3.305 -                                WRITE(mach64->accel.dst_offset + (mach64->accel.dst_y * mach64->accel.dst_pitch) + mach64->accel.dst_x, mach64->accel.dst_size);
   3.306 +                                WRITE(mach64->accel.dst_offset + (dst_y * mach64->accel.dst_pitch) + dst_x, mach64->accel.dst_size);
   3.307                          }
   3.308                  
   3.309                          if (mach64->dst_cntl & DST_24_ROT_EN)
   3.310 @@ -635,16 +693,43 @@
   3.311                  
   3.312                          mach64->accel.src_x += mach64->accel.xinc;
   3.313                          mach64->accel.dst_x += mach64->accel.xinc;
   3.314 +                        mach64->accel.src_x_count--;
   3.315 +                        if (mach64->accel.src_x_count <= 0)
   3.316 +                        {
   3.317 +                                mach64->accel.src_x = 0;
   3.318 +                                if ((mach64->src_cntl & (SRC_PATT_ROT_EN | SRC_PATT_EN)) == (SRC_PATT_ROT_EN | SRC_PATT_EN))
   3.319 +                                {
   3.320 +                                        mach64->accel.src_x_start = (mach64->src_y_x_start >> 16) & 0xfff;
   3.321 +                                        mach64->accel.src_x_count = mach64->accel.src_width2;
   3.322 +                                }
   3.323 +                                else
   3.324 +                                        mach64->accel.src_x_count = mach64->accel.src_width1;
   3.325 +                        }
   3.326 +                        
   3.327                          mach64->accel.x_count--;
   3.328                          
   3.329                          if (mach64->accel.x_count <= 0)
   3.330                          {
   3.331                                  mach64->accel.x_count = mach64->accel.dst_width;
   3.332 -                                mach64->accel.src_x = mach64->accel.src_x_start;
   3.333 -                                mach64->accel.dst_x = mach64->accel.dst_x_start;
   3.334 +                                mach64->accel.src_x = 0;
   3.335 +                                mach64->accel.dst_x = 0;
   3.336 +                                mach64->accel.src_x_start = (mach64->src_y_x >> 16) & 0xfff;
   3.337  
   3.338                                  mach64->accel.src_y += mach64->accel.yinc;                        
   3.339                                  mach64->accel.dst_y += mach64->accel.yinc;
   3.340 +                                mach64->accel.src_y_count--;
   3.341 +                                if (mach64->accel.src_y_count <= 0)
   3.342 +                                {
   3.343 +                                        mach64->accel.src_y = 0;
   3.344 +                                        if ((mach64->src_cntl & (SRC_PATT_ROT_EN | SRC_PATT_EN)) == (SRC_PATT_ROT_EN | SRC_PATT_EN))
   3.345 +                                        {
   3.346 +                                                mach64->accel.src_y_start = mach64->src_y_x_start & 0xfff;
   3.347 +                                                mach64->accel.src_y_count = mach64->accel.src_height2;
   3.348 +                                        }
   3.349 +                                        else
   3.350 +                                                mach64->accel.src_y_count = mach64->accel.src_height1;
   3.351 +                                }
   3.352 +
   3.353                                  mach64->accel.dst_height--;
   3.354                  
   3.355                                  if (mach64->accel.dst_height <= 0)
   3.356 @@ -888,13 +973,17 @@
   3.357                  READ8(addr, mach64->crtc_v_sync_strt_wid);
   3.358                  break;
   3.359  
   3.360 +                case 0x12: case 0x13:
   3.361 +                READ8(addr - 2, mach64->svga.vc);
   3.362 +                break;
   3.363 +                
   3.364                  case 0x14: case 0x15: case 0x16: case 0x17:
   3.365                  READ8(addr, mach64->crtc_off_pitch);
   3.366                  break;
   3.367                  
   3.368                  case 0x18:
   3.369                  ret = mach64->crtc_int_cntl & ~1;
   3.370 -                if (mach64->stat & 8)
   3.371 +                if (mach64->svga.cgastat & 8)
   3.372                          ret |= 1;
   3.373                  break;
   3.374  
   3.375 @@ -946,7 +1035,7 @@
   3.376                  break;
   3.377                  
   3.378                  case 0xe0: case 0xe1: case 0xe2: case 0xe3:
   3.379 -                READ8(addr, 0xd7); /*88800GX*/
   3.380 +                READ8(addr, 0x020000d7); /*88800GX-2*/
   3.381                  break;
   3.382                  
   3.383                  case 0x100: case 0x101: case 0x102: case 0x103:
   3.384 @@ -998,6 +1087,33 @@
   3.385                  case 0x18c: case 0x18d: case 0x18e: case 0x18f:
   3.386                  READ8(addr, mach64->src_y_x);
   3.387                  break;
   3.388 +                case 0x190: case 0x191:
   3.389 +                READ8(addr + 2, mach64->src_height1_width1);
   3.390 +                break;
   3.391 +                case 0x194: case 0x195:
   3.392 +                READ8(addr, mach64->src_height1_width1);
   3.393 +                break;
   3.394 +                case 0x198: case 0x199: case 0x19a: case 0x19b:
   3.395 +                READ8(addr, mach64->src_height1_width1);
   3.396 +                break;
   3.397 +                case 0x19c: case 0x19d:
   3.398 +                READ8(addr, mach64->src_y_x_start);
   3.399 +                break;
   3.400 +                case 0x1a0: case 0x1a1:
   3.401 +                READ8(addr + 2, mach64->src_y_x_start);
   3.402 +                break;
   3.403 +                case 0x1a4: case 0x1a5: case 0x1a6: case 0x1a7:
   3.404 +                READ8(addr, mach64->src_y_x_start);
   3.405 +                break;
   3.406 +                case 0x1a8: case 0x1a9:
   3.407 +                READ8(addr + 2, mach64->src_height2_width2);
   3.408 +                break;
   3.409 +                case 0x1ac: case 0x1ad:
   3.410 +                READ8(addr, mach64->src_height2_width2);
   3.411 +                break;
   3.412 +                case 0x1b0: case 0x1b1: case 0x1b2: case 0x1b3:
   3.413 +                READ8(addr, mach64->src_height2_width2);
   3.414 +                break;
   3.415  
   3.416                  case 0x1b4: case 0x1b5: case 0x1b6: case 0x1b7:
   3.417                  READ8(addr, mach64->src_cntl);
   3.418 @@ -1098,7 +1214,7 @@
   3.419          {
   3.420                  case 0x18:
   3.421                  ret = mach64->crtc_int_cntl & ~1;
   3.422 -                if (mach64->stat & 8)
   3.423 +                if (mach64->svga.cgastat & 8)
   3.424                          ret |= 1;
   3.425                  break;
   3.426  
   3.427 @@ -1317,6 +1433,33 @@
   3.428                  case 0x18c: case 0x18d: case 0x18e: case 0x18f:
   3.429                  WRITE8(addr, mach64->src_y_x, val);
   3.430                  break;
   3.431 +                case 0x190: case 0x191:
   3.432 +                WRITE8(addr + 2, mach64->src_height1_width1, val);
   3.433 +                break;
   3.434 +                case 0x194: case 0x195:
   3.435 +                WRITE8(addr, mach64->src_height1_width1, val);
   3.436 +                break;
   3.437 +                case 0x198: case 0x199: case 0x19a: case 0x19b:
   3.438 +                WRITE8(addr, mach64->src_height1_width1, val);
   3.439 +                break;
   3.440 +                case 0x19c: case 0x19d:
   3.441 +                WRITE8(addr, mach64->src_y_x_start, val);
   3.442 +                break;
   3.443 +                case 0x1a0: case 0x1a1:
   3.444 +                WRITE8(addr + 2, mach64->src_y_x_start, val);
   3.445 +                break;
   3.446 +                case 0x1a4: case 0x1a5: case 0x1a6: case 0x1a7:
   3.447 +                WRITE8(addr, mach64->src_y_x_start, val);
   3.448 +                break;
   3.449 +                case 0x1a8: case 0x1a9:
   3.450 +                WRITE8(addr + 2, mach64->src_height2_width2, val);
   3.451 +                break;
   3.452 +                case 0x1ac: case 0x1ad:
   3.453 +                WRITE8(addr, mach64->src_height2_width2, val);
   3.454 +                break;
   3.455 +                case 0x1b0: case 0x1b1: case 0x1b2: case 0x1b3:
   3.456 +                WRITE8(addr, mach64->src_height2_width2, val);
   3.457 +                break;
   3.458  
   3.459                  case 0x1b4: case 0x1b5: case 0x1b6: case 0x1b7:
   3.460                  WRITE8(addr, mach64->src_cntl, val);
   3.461 @@ -1485,6 +1628,10 @@
   3.462                  ret = mach64_ext_readb(0x0c | (port & 3), p);
   3.463                  break;
   3.464  
   3.465 +                case 0x12ec: case 0x12ed: case 0x12ee: case 0x12ef:
   3.466 +                ret = mach64_ext_readb(0x10 | (port & 3), p);
   3.467 +                break;
   3.468 +
   3.469                  case 0x16ec: case 0x16ed: case 0x16ee: case 0x16ef:
   3.470                  ret = mach64_ext_readb(0x14 | (port & 3), p);
   3.471                  break;
   3.472 @@ -1557,6 +1704,8 @@
   3.473                  break;
   3.474  
   3.475                  case 0x6aec: case 0x6aed: case 0x6aee: case 0x6aef:
   3.476 +                mach64->config_cntl = (mach64->config_cntl & ~0x3ff0) | ((mach64->linear_base >> 22) << 4);
   3.477 +                mach64->config_cntl = (mach64->config_cntl & ~3) | 2;
   3.478                  READ8(port, mach64->config_cntl);
   3.479                  break;
   3.480                  
   3.481 @@ -1758,19 +1907,21 @@
   3.482  void mach64_write(uint32_t addr, uint8_t val, void *p)
   3.483  {
   3.484          mach64_t *mach64 = (mach64_t *)p;
   3.485 +        svga_t *svga = &mach64->svga;
   3.486  //        pclog("mach64_write : %05X %02X  ", addr, val);
   3.487          addr = (addr & 0x7fff) + mach64->bank_w[(addr >> 15) & 1];
   3.488  //        pclog("%08X\n", addr);
   3.489 -        svga_write_linear(addr, val, p);
   3.490 +        svga_write_linear(addr, val, svga);
   3.491  }
   3.492  
   3.493  uint8_t mach64_read(uint32_t addr, void *p)
   3.494  {
   3.495          mach64_t *mach64 = (mach64_t *)p;
   3.496 +        svga_t *svga = &mach64->svga;
   3.497          uint8_t ret;
   3.498  //        pclog("mach64_read : %05X ", addr);
   3.499          addr = (addr & 0x7fff) + mach64->bank_r[(addr >> 15) & 1];
   3.500 -        ret = svga_read_linear(addr, p);
   3.501 +        ret = svga_read_linear(addr, svga);
   3.502  //        pclog("%08X %02X\n", addr, ret);  
   3.503          return ret;      
   3.504  }
   3.505 @@ -1800,6 +1951,63 @@
   3.506          svga->hwcursor_latch.addr += 16;
   3.507  }
   3.508  
   3.509 +uint8_t mach64_pci_read(int func, int addr, void *p)
   3.510 +{
   3.511 +        mach64_t *mach64 = (mach64_t *)p;
   3.512 +        svga_t *svga = &mach64->svga;
   3.513 +
   3.514 +//        pclog("Mach64 PCI read %08X\n", addr);
   3.515 +
   3.516 +        switch (addr)
   3.517 +        {
   3.518 +                case 0x00: return 0x02; /*ATi*/
   3.519 +                case 0x01: return 0x10;
   3.520 +                
   3.521 +                case 0x02: return 'X'; /*88800GX*/
   3.522 +                case 0x03: return 'G';
   3.523 +                
   3.524 +                case 0x04: return 0x03; /*Respond to IO and memory accesses*/
   3.525 +
   3.526 +                case 0x07: return 1 << 1; /*Medium DEVSEL timing*/
   3.527 +                
   3.528 +                case 0x08: return 0; /*Revision ID*/
   3.529 +                case 0x09: return 0; /*Programming interface*/
   3.530 +                
   3.531 +                case 0x0a: return 0x01; /*Supports VGA interface, XGA compatible*/
   3.532 +                case 0x0b: return 0x03;
   3.533 +                
   3.534 +                case 0x10: return 0x00; /*Linear frame buffer address*/
   3.535 +                case 0x11: return 0x00;
   3.536 +                case 0x12: return mach64->linear_base >> 16;
   3.537 +                case 0x13: return mach64->linear_base >> 24;
   3.538 +
   3.539 +                case 0x30: return 0x01; /*BIOS ROM address*/
   3.540 +                case 0x31: return 0x00;
   3.541 +                case 0x32: return 0x0C;
   3.542 +                case 0x33: return 0x00;
   3.543 +        }
   3.544 +        return 0;
   3.545 +}
   3.546 +
   3.547 +void mach64_pci_write(int func, int addr, uint8_t val, void *p)
   3.548 +{
   3.549 +        mach64_t *mach64 = (mach64_t *)p;
   3.550 +
   3.551 +//        pclog("Mach64 PCI write %08X %02X\n", addr, val);
   3.552 +        
   3.553 +        switch (addr)
   3.554 +        {
   3.555 +                case 0x12:
   3.556 +                mach64->linear_base = (mach64->linear_base & 0xff000000) | ((val & 0x80) << 16);
   3.557 +                mach64_updatemapping(mach64);
   3.558 +                break;
   3.559 +                case 0x13:
   3.560 +                mach64->linear_base = (mach64->linear_base & 0x800000) | (val << 24);
   3.561 +                mach64_updatemapping(mach64);
   3.562 +                break;
   3.563 +        }
   3.564 +}
   3.565 +
   3.566  void *mach64gx_init()
   3.567  {
   3.568          int c;
   3.569 @@ -1818,11 +2026,13 @@
   3.570                  io_sethandler((c * 0x1000) + 0x2ec, 0x0004, mach64_ext_inb, mach64_ext_inw, mach64_ext_inl, mach64_ext_outb, mach64_ext_outw, mach64_ext_outl, mach64);
   3.571                  io_sethandler((c * 0x1000) + 0x6ec, 0x0004, mach64_ext_inb, mach64_ext_inw, mach64_ext_inl, mach64_ext_outb, mach64_ext_outw, mach64_ext_outl, mach64);
   3.572                  io_sethandler((c * 0x1000) + 0xaec, 0x0004, mach64_ext_inb, mach64_ext_inw, mach64_ext_inl, mach64_ext_outb, mach64_ext_outw, mach64_ext_outl, mach64);
   3.573 -                io_sethandler((c * 0x1000) + 0xeec, 0x0004, mach64_ext_inb, mach64_ext_inw, mach64_ext_inl, mach64_ext_outb, mach64_ext_outw, mach64_ext_outl, mach64);                                                
   3.574 +                io_sethandler((c * 0x1000) + 0xeec, 0x0004, mach64_ext_inb, mach64_ext_inw, mach64_ext_inl, mach64_ext_outb, mach64_ext_outw, mach64_ext_outl, mach64);
   3.575          }
   3.576  
   3.577          io_sethandler(0x01ce, 0x0002, mach64_in, NULL, NULL, mach64_out, NULL, NULL, mach64);
   3.578 -        
   3.579 +
   3.580 +        pci_add(mach64_pci_read, mach64_pci_write, mach64);
   3.581 +                
   3.582          ati_eeprom_load(&mach64->eeprom, "mach64.nvr", 1);
   3.583  
   3.584          mach64->dac_cntl = 5 << 16; /*ATI 68860 RAMDAC*/        
     4.1 --- a/src/vid_ics2595.c	Sat Aug 24 15:11:30 2013 +0100
     4.2 +++ b/src/vid_ics2595.c	Sat Oct 12 16:20:27 2013 +0100
     4.3 @@ -15,12 +15,12 @@
     4.4  
     4.5  void ics2595_write(ics2595_t *ics2595, int strobe, int dat)
     4.6  {
     4.7 -        pclog("ics2595_write : %i %i\n", strobe, dat);
     4.8 +//        pclog("ics2595_write : %i %i\n", strobe, dat);
     4.9          if (strobe)
    4.10          {
    4.11                  if ((dat & 8) && !ics2595->oldfs3) /*Data clock*/
    4.12                  {
    4.13 -                        pclog(" - new dat %i\n", dat & 4);
    4.14 +//                        pclog(" - new dat %i\n", dat & 4);
    4.15                          switch (ics2595->state)
    4.16                          {
    4.17                                  case ICS2595_IDLE:
    4.18 @@ -35,13 +35,13 @@
    4.19                                  if (ics2595->pos == 20)
    4.20                                  {
    4.21                                          int d, n, l;
    4.22 -                                        pclog("ICS2595_WRITE : dat %08X\n", ics2595->dat);
    4.23 +//                                        pclog("ICS2595_WRITE : dat %08X\n", ics2595->dat);
    4.24                                          l = (ics2595->dat >> 2) & 0xf;
    4.25                                          n = ((ics2595->dat >> 7) & 255) + 257;
    4.26                                          d = ics2595_div[(ics2595->dat >> 16) & 3];
    4.27  
    4.28                                          ics2595->clocks[l] = (14318181.8 * ((double)n / 46.0)) / (double)d;
    4.29 -                                        pclog("ICS2595 clock set - L %i N %i D %i freq = %f\n", l, n, d, (14318181.8 * ((double)n / 46.0)) / (double)d);
    4.30 +//                                        pclog("ICS2595 clock set - L %i N %i D %i freq = %f\n", l, n, d, (14318181.8 * ((double)n / 46.0)) / (double)d);
    4.31                                          ics2595->state = ICS2595_IDLE;
    4.32                                  }
    4.33                                  break;                                                
     5.1 --- a/src/vid_svga.c	Sat Aug 24 15:11:30 2013 +0100
     5.2 +++ b/src/vid_svga.c	Sat Oct 12 16:20:27 2013 +0100
     5.3 @@ -1116,7 +1116,7 @@
     5.4  
     5.5  void svga_doblit(int y1, int y2, int wx, int wy, svga_t *svga)
     5.6  {
     5.7 -        pclog("svga_doblit start\n");
     5.8 +//        pclog("svga_doblit start\n");
     5.9          svga->frames++;
    5.10  //        pclog("doblit %i %i\n", y1, y2);
    5.11          if (y1 > y2) 
    5.12 @@ -1141,7 +1141,7 @@
    5.13          }
    5.14          video_blit_memtoscreen(32, 0, y1, y2, xsize, ysize);
    5.15          if (readflash) rectfill(screen,winsizex-40,8,winsizex-8,14,0xFFFFFFFF);      
    5.16 -        pclog("svga_doblit end\n");
    5.17 +//        pclog("svga_doblit end\n");
    5.18  }
    5.19  
    5.20  void svga_writew(uint32_t addr, uint16_t val, void *p)
     6.1 --- a/src/win-keyboard.cc	Sat Aug 24 15:11:30 2013 +0100
     6.2 +++ b/src/win-keyboard.cc	Sat Oct 12 16:20:27 2013 +0100
     6.3 @@ -99,11 +99,11 @@
     6.4          }
     6.5          for (c = 0; c < 256; c++)
     6.6          {
     6.7 -                if (dinput_key[c] & 0x80) pclog("Dinput key down %i %02X\n", c, c);
     6.8 +//                if (dinput_key[c] & 0x80) pclog("Dinput key down %i %02X\n", c, c);
     6.9                  if (keyboard_lookup[c] != -1)
    6.10                  {
    6.11                          key[c] = dinput_key[keyboard_lookup[c]] & 0x80;
    6.12 -                        if (key[c]) pclog("Key down %i %02X  %i %02X\n", c, c, keyboard_lookup[c], keyboard_lookup[c]);
    6.13 +//                        if (key[c]) pclog("Key down %i %02X  %i %02X\n", c, c, keyboard_lookup[c], keyboard_lookup[c]);
    6.14                  }
    6.15          }
    6.16  }