Ported twilen's S3 ViRGE and Trio/Vision fixes to 86box.
This commit is contained in:
@@ -3331,10 +3331,31 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
uint32_t rd_mask = s3->accel.rd_mask;
|
uint32_t rd_mask = s3->accel.rd_mask;
|
||||||
int cmd = s3->accel.cmd >> 13;
|
int cmd = s3->accel.cmd >> 13;
|
||||||
int read = 0, byte_cnt = 0, i;
|
int read = 0, byte_cnt = 0, i;
|
||||||
|
uint32_t srcbase, dstbase;
|
||||||
|
|
||||||
if ((s3->chip >= S3_TRIO64) && (s3->accel.cmd & (1 << 11)))
|
if ((s3->chip >= S3_TRIO64) && (s3->accel.cmd & (1 << 11)))
|
||||||
cmd |= 8;
|
cmd |= 8;
|
||||||
|
|
||||||
|
// SRC-BASE/DST-BASE
|
||||||
|
if ((s3->accel.multifunc[0xd] >> 4) & 7) {
|
||||||
|
srcbase = 0x100000 * ((s3->accel.multifunc[0xd] >> 4) & 3);
|
||||||
|
} else {
|
||||||
|
srcbase = 0x100000 * ((s3->accel.multifunc[0xe] >> 2) & 3);
|
||||||
|
}
|
||||||
|
if ((s3->accel.multifunc[0xd] >> 0) & 7) {
|
||||||
|
dstbase = 0x100000 * ((s3->accel.multifunc[0xd] >> 0) & 3);
|
||||||
|
} else {
|
||||||
|
dstbase = 0x100000 * ((s3->accel.multifunc[0xe] >> 0) & 3);
|
||||||
|
}
|
||||||
|
if (s3->bpp == 1) {
|
||||||
|
srcbase >>= 1;
|
||||||
|
dstbase >>= 1;
|
||||||
|
} else if (s3->bpp == 3) {
|
||||||
|
srcbase >>= 2;
|
||||||
|
dstbase >>= 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
if ((s3_cpu_src(s3) || s3_cpu_dest(s3))) {
|
if ((s3_cpu_src(s3) || s3_cpu_dest(s3))) {
|
||||||
if (s3->accel.pixtrans_failed) { /*Some hack for some 911/924 driver*/
|
if (s3->accel.pixtrans_failed) { /*Some hack for some 911/924 driver*/
|
||||||
if (s3->busy)
|
if (s3->busy)
|
||||||
@@ -3410,8 +3431,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
{
|
{
|
||||||
while (count-- && s3->accel.sy >= 0)
|
while (count-- && s3->accel.sy >= 0)
|
||||||
{
|
{
|
||||||
if (s3->accel.cx >= clip_l && s3->accel.cx <= clip_r &&
|
if ((s3->accel.cx & 0xfff) >= clip_l && (s3->accel.cx & 0xfff) <= clip_r &&
|
||||||
s3->accel.cy >= clip_t && s3->accel.cy <= clip_b)
|
(s3->accel.cy & 0xfff) >= clip_t && (s3->accel.cy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
switch ((mix_dat & mix_mask) ? frgd_mix : bkgd_mix)
|
switch ((mix_dat & mix_mask) ? frgd_mix : bkgd_mix)
|
||||||
{
|
{
|
||||||
@@ -3469,8 +3490,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
|
|
||||||
while (count-- && s3->accel.sy >= 0)
|
while (count-- && s3->accel.sy >= 0)
|
||||||
{
|
{
|
||||||
if (s3->accel.cx >= clip_l && s3->accel.cx <= clip_r &&
|
if ((s3->accel.cx & 0xfff) >= clip_l && (s3->accel.cx & 0xfff) <= clip_r &&
|
||||||
s3->accel.cy >= clip_t && s3->accel.cy <= clip_b)
|
(s3->accel.cy & 0xfff) >= clip_t && (s3->accel.cy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
switch ((mix_dat & mix_mask) ? frgd_mix : bkgd_mix)
|
switch ((mix_dat & mix_mask) ? frgd_mix : bkgd_mix)
|
||||||
{
|
{
|
||||||
@@ -3552,7 +3573,7 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
s3->accel.cy = s3->accel.cur_y;
|
s3->accel.cy = s3->accel.cur_y;
|
||||||
if (s3->accel.cur_y & 0x1000) s3->accel.cy |= ~0xfff;
|
if (s3->accel.cur_y & 0x1000) s3->accel.cy |= ~0xfff;
|
||||||
|
|
||||||
s3->accel.dest = s3->accel.cy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.cy * s3->width;
|
||||||
|
|
||||||
if (s3_cpu_src(s3)) {
|
if (s3_cpu_src(s3)) {
|
||||||
return; /*Wait for data from CPU*/
|
return; /*Wait for data from CPU*/
|
||||||
@@ -3580,8 +3601,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
|
|
||||||
while (count-- && s3->accel.sy >= 0)
|
while (count-- && s3->accel.sy >= 0)
|
||||||
{
|
{
|
||||||
if (s3->accel.cx >= clip_l && s3->accel.cx <= clip_r &&
|
if ((s3->accel.cx & 0xfff) >= clip_l && (s3->accel.cx & 0xfff) <= clip_r &&
|
||||||
s3->accel.cy >= clip_t && s3->accel.cy <= clip_b)
|
(s3->accel.cy & 0xfff) >= clip_t && (s3->accel.cy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
if (s3_cpu_dest(s3) && ((s3->accel.multifunc[0xa] & 0xc0) == 0x00))
|
if (s3_cpu_dest(s3) && ((s3->accel.multifunc[0xa] & 0xc0) == 0x00))
|
||||||
mix_dat = mix_mask; /* Mix data = forced to foreground register. */
|
mix_dat = mix_mask; /* Mix data = forced to foreground register. */
|
||||||
@@ -3656,7 +3677,7 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
if (s3->accel.cmd & 0x80) s3->accel.cy++;
|
if (s3->accel.cmd & 0x80) s3->accel.cy++;
|
||||||
else s3->accel.cy--;
|
else s3->accel.cy--;
|
||||||
|
|
||||||
s3->accel.dest = s3->accel.cy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.cy * s3->width;
|
||||||
s3->accel.sy--;
|
s3->accel.sy--;
|
||||||
|
|
||||||
if (s3->accel.sy < 0) {
|
if (s3->accel.sy < 0) {
|
||||||
@@ -3699,8 +3720,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
s3->accel.cy = s3->accel.cur_y & 0xfff;
|
s3->accel.cy = s3->accel.cur_y & 0xfff;
|
||||||
if (s3->accel.cur_y & 0x1000) s3->accel.cy |= ~0xfff;
|
if (s3->accel.cur_y & 0x1000) s3->accel.cy |= ~0xfff;
|
||||||
|
|
||||||
s3->accel.src = s3->accel.cy * s3->width;
|
s3->accel.src = srcbase + s3->accel.cy * s3->width;
|
||||||
s3->accel.dest = s3->accel.dy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.dy * s3->width;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((s3->accel.cmd & 0x100) && !cpu_input) {
|
if ((s3->accel.cmd & 0x100) && !cpu_input) {
|
||||||
@@ -3715,8 +3736,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
{
|
{
|
||||||
while (1)
|
while (1)
|
||||||
{
|
{
|
||||||
if (s3->accel.dx >= clip_l && s3->accel.dx <= clip_r &&
|
if ((s3->accel.dx & 0xfff) >= clip_l && (s3->accel.dx & 0xfff) <= clip_r &&
|
||||||
s3->accel.dy >= clip_t && s3->accel.dy <= clip_b)
|
(s3->accel.dy & 0xfff) >= clip_t && (s3->accel.dy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
READ(s3->accel.src + s3->accel.cx, src_dat);
|
READ(s3->accel.src + s3->accel.cx, src_dat);
|
||||||
READ(s3->accel.dest + s3->accel.dx, dest_dat);
|
READ(s3->accel.dest + s3->accel.dx, dest_dat);
|
||||||
@@ -3738,8 +3759,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
s3->accel.cy++;
|
s3->accel.cy++;
|
||||||
s3->accel.dy++;
|
s3->accel.dy++;
|
||||||
|
|
||||||
s3->accel.src = s3->accel.cy * s3->width;
|
s3->accel.src = srcbase + s3->accel.cy * s3->width;
|
||||||
s3->accel.dest = s3->accel.dy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.dy * s3->width;
|
||||||
|
|
||||||
s3->accel.sy--;
|
s3->accel.sy--;
|
||||||
|
|
||||||
@@ -3754,8 +3775,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
{
|
{
|
||||||
while (count-- && s3->accel.sy >= 0)
|
while (count-- && s3->accel.sy >= 0)
|
||||||
{
|
{
|
||||||
if (s3->accel.dx >= clip_l && s3->accel.dx <= clip_r &&
|
if ((s3->accel.dx & 0xfff) >= clip_l && (s3->accel.dx & 0xfff) <= clip_r &&
|
||||||
s3->accel.dy >= clip_t && s3->accel.dy <= clip_b)
|
(s3->accel.dy & 0xfff) >= clip_t && (s3->accel.dy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
if (vram_mask)
|
if (vram_mask)
|
||||||
{
|
{
|
||||||
@@ -3827,8 +3848,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
s3->accel.dy--;
|
s3->accel.dy--;
|
||||||
}
|
}
|
||||||
|
|
||||||
s3->accel.src = s3->accel.cy * s3->width;
|
s3->accel.src = srcbase + s3->accel.cy * s3->width;
|
||||||
s3->accel.dest = s3->accel.dy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.dy * s3->width;
|
||||||
|
|
||||||
s3->accel.sy--;
|
s3->accel.sy--;
|
||||||
|
|
||||||
@@ -3864,12 +3885,12 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
|
|
||||||
/*Align source with destination*/
|
/*Align source with destination*/
|
||||||
s3->accel.pattern = (s3->accel.cy * s3->width) + s3->accel.cx;
|
s3->accel.pattern = (s3->accel.cy * s3->width) + s3->accel.cx;
|
||||||
s3->accel.dest = s3->accel.dy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.dy * s3->width;
|
||||||
|
|
||||||
s3->accel.cx = s3->accel.dx & 7;
|
s3->accel.cx = s3->accel.dx & 7;
|
||||||
s3->accel.cy = s3->accel.dy & 7;
|
s3->accel.cy = s3->accel.dy & 7;
|
||||||
|
|
||||||
s3->accel.src = s3->accel.pattern + (s3->accel.cy * s3->width);
|
s3->accel.src = srcbase + s3->accel.pattern + (s3->accel.cy * s3->width);
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((s3->accel.cmd & 0x100) && !cpu_input) return; /*Wait for data from CPU*/
|
if ((s3->accel.cmd & 0x100) && !cpu_input) return; /*Wait for data from CPU*/
|
||||||
@@ -3879,8 +3900,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
|
|
||||||
while (count-- && s3->accel.sy >= 0)
|
while (count-- && s3->accel.sy >= 0)
|
||||||
{
|
{
|
||||||
if (s3->accel.dx >= clip_l && s3->accel.dx <= clip_r &&
|
if ((s3->accel.dx & 0xfff) >= clip_l && (s3->accel.dx & 0xfff) <= clip_r &&
|
||||||
s3->accel.dy >= clip_t && s3->accel.dy <= clip_b)
|
(s3->accel.dy & 0xfff) >= clip_t && (s3->accel.dy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
if (vram_mask)
|
if (vram_mask)
|
||||||
{
|
{
|
||||||
@@ -3952,8 +3973,8 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
s3->accel.dy--;
|
s3->accel.dy--;
|
||||||
}
|
}
|
||||||
|
|
||||||
s3->accel.src = s3->accel.pattern + (s3->accel.cy * s3->width);
|
s3->accel.src = srcbase + s3->accel.pattern + (s3->accel.cy * s3->width);
|
||||||
s3->accel.dest = s3->accel.dy * s3->width;
|
s3->accel.dest = dstbase + s3->accel.dy * s3->width;
|
||||||
|
|
||||||
s3->accel.sy--;
|
s3->accel.sy--;
|
||||||
|
|
||||||
@@ -3988,12 +4009,12 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
int y = s3->accel.poly_cy;
|
int y = s3->accel.poly_cy;
|
||||||
int x_count = ABS((s3->accel.poly_cx2 >> 20) - s3->accel.poly_x) + 1;
|
int x_count = ABS((s3->accel.poly_cx2 >> 20) - s3->accel.poly_x) + 1;
|
||||||
|
|
||||||
s3->accel.dest = y * s3->width;
|
s3->accel.dest = dstbase + y * s3->width;
|
||||||
|
|
||||||
while (x_count-- && count--)
|
while (x_count-- && count--)
|
||||||
{
|
{
|
||||||
if (s3->accel.poly_x >= clip_l && s3->accel.poly_x <= clip_r &&
|
if ((s3->accel.poly_x & 0xfff) >= clip_l && (s3->accel.poly_x & 0xfff) <= clip_r &&
|
||||||
s3->accel.poly_cy >= clip_t && s3->accel.poly_cy <= clip_b)
|
(s3->accel.poly_cy & 0xfff) >= clip_t && (s3->accel.poly_cy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
switch (frgd_mix)
|
switch (frgd_mix)
|
||||||
{
|
{
|
||||||
@@ -4064,15 +4085,15 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
|||||||
int y = s3->accel.poly_cy;
|
int y = s3->accel.poly_cy;
|
||||||
int x_count = ABS((s3->accel.poly_cx2 >> 20) - s3->accel.poly_x) + 1;
|
int x_count = ABS((s3->accel.poly_cx2 >> 20) - s3->accel.poly_x) + 1;
|
||||||
|
|
||||||
s3->accel.src = s3->accel.pattern + ((y & 7) * s3->width);
|
s3->accel.src = srcbase + s3->accel.pattern + ((y & 7) * s3->width);
|
||||||
s3->accel.dest = y * s3->width;
|
s3->accel.dest = dstbase + y * s3->width;
|
||||||
|
|
||||||
while (x_count-- && count--)
|
while (x_count-- && count--)
|
||||||
{
|
{
|
||||||
int pat_x = s3->accel.poly_x & 7;
|
int pat_x = s3->accel.poly_x & 7;
|
||||||
|
|
||||||
if (s3->accel.poly_x >= clip_l && s3->accel.poly_x <= clip_r &&
|
if ((s3->accel.poly_x & 0xfff) >= clip_l && (s3->accel.poly_x & 0xfff) <= clip_r &&
|
||||||
s3->accel.poly_cy >= clip_t && s3->accel.poly_cy <= clip_b)
|
(s3->accel.poly_cy & 0xfff) >= clip_t && (s3->accel.poly_cy & 0xfff) <= clip_b)
|
||||||
{
|
{
|
||||||
if (vram_mask) {
|
if (vram_mask) {
|
||||||
READ(s3->accel.src + pat_x, mix_dat);
|
READ(s3->accel.src + pat_x, mix_dat);
|
||||||
|
@@ -1787,13 +1787,13 @@ static void s3_virge_bitblt(virge_t *virge, int count, uint32_t cpu_dat)
|
|||||||
for (x = 0; x < 8; x++)
|
for (x = 0; x < 8; x++)
|
||||||
{
|
{
|
||||||
if (virge->s3d.mono_pat_0 & (1 << (x + y*8)))
|
if (virge->s3d.mono_pat_0 & (1 << (x + y*8)))
|
||||||
mono_pattern[y*8 + x] = virge->s3d.pat_fg_clr;
|
mono_pattern[y*8 + (7 - x)] = virge->s3d.pat_fg_clr;
|
||||||
else
|
else
|
||||||
mono_pattern[y*8 + x] = virge->s3d.pat_bg_clr;
|
mono_pattern[y*8 + (7 - x)] = virge->s3d.pat_bg_clr;
|
||||||
if (virge->s3d.mono_pat_1 & (1 << (x + y*8)))
|
if (virge->s3d.mono_pat_1 & (1 << (x + y*8)))
|
||||||
mono_pattern[(y+4)*8 + x] = virge->s3d.pat_fg_clr;
|
mono_pattern[(y+4)*8 + (7 - x)] = virge->s3d.pat_fg_clr;
|
||||||
else
|
else
|
||||||
mono_pattern[(y+4)*8 + x] = virge->s3d.pat_bg_clr;
|
mono_pattern[(y+4)*8 + (7 - x)] = virge->s3d.pat_bg_clr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1951,7 +1951,8 @@ static void s3_virge_bitblt(virge_t *virge, int count, uint32_t cpu_dat)
|
|||||||
|
|
||||||
while (count && virge->s3d.h)
|
while (count && virge->s3d.h)
|
||||||
{
|
{
|
||||||
dest_addr = virge->s3d.dest_base + (virge->s3d.dest_x * x_mul) + (virge->s3d.dest_y * virge->s3d.dest_str);
|
source = virge->s3d.pat_fg_clr;
|
||||||
|
dest_addr = virge->s3d.dest_base + (virge->s3d.dest_x * x_mul) + (virge->s3d.dest_y * virge->s3d.dest_str);
|
||||||
pattern = virge->s3d.pat_fg_clr;
|
pattern = virge->s3d.pat_fg_clr;
|
||||||
out = 0;
|
out = 0;
|
||||||
update = 1;
|
update = 1;
|
||||||
@@ -3900,36 +3901,6 @@ static const device_config_t s3_virge_config[] =
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
static const device_config_t s3_virge_vx_config[] =
|
|
||||||
{
|
|
||||||
{
|
|
||||||
"memory", "Memory size", CONFIG_SELECTION, "", 4,
|
|
||||||
{
|
|
||||||
{
|
|
||||||
"2 MB", 2
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"4 MB", 4
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"8 MB", 8
|
|
||||||
},
|
|
||||||
{
|
|
||||||
""
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"bilinear", "Bilinear filtering", CONFIG_BINARY, "", 1
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"dithering", "Dithering", CONFIG_BINARY, "", 1
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"", "", -1
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#if defined(DEV_BRANCH) && defined(USE_S3TRIO3D2X)
|
#if defined(DEV_BRANCH) && defined(USE_S3TRIO3D2X)
|
||||||
static const device_config_t s3_trio3d_2x_config[] =
|
static const device_config_t s3_trio3d_2x_config[] =
|
||||||
{
|
{
|
||||||
@@ -3998,7 +3969,7 @@ const device_t s3_virge_988_vlb_device =
|
|||||||
s3_virge_988_available,
|
s3_virge_988_available,
|
||||||
s3_virge_speed_changed,
|
s3_virge_speed_changed,
|
||||||
s3_virge_force_redraw,
|
s3_virge_force_redraw,
|
||||||
s3_virge_vx_config
|
s3_virge_config
|
||||||
};
|
};
|
||||||
|
|
||||||
const device_t s3_virge_988_pci_device =
|
const device_t s3_virge_988_pci_device =
|
||||||
@@ -4012,7 +3983,7 @@ const device_t s3_virge_988_pci_device =
|
|||||||
s3_virge_988_available,
|
s3_virge_988_available,
|
||||||
s3_virge_speed_changed,
|
s3_virge_speed_changed,
|
||||||
s3_virge_force_redraw,
|
s3_virge_force_redraw,
|
||||||
s3_virge_vx_config
|
s3_virge_config
|
||||||
};
|
};
|
||||||
|
|
||||||
const device_t s3_virge_375_vlb_device =
|
const device_t s3_virge_375_vlb_device =
|
||||||
|
Reference in New Issue
Block a user