Merge remote-tracking branch 'origin/master' into feature/machine_and_kb
This commit is contained in:
@@ -292,7 +292,7 @@ extern const device_t icd2061_device;
|
||||
extern const device_t ics9161_device;
|
||||
extern const device_t sc11483_ramdac_device;
|
||||
extern const device_t sc11487_ramdac_device;
|
||||
extern const device_t sc11484_ramdac_device;
|
||||
extern const device_t sc11486_ramdac_device;
|
||||
extern const device_t sc11484_nors2_ramdac_device;
|
||||
extern const device_t sc1502x_ramdac_device;
|
||||
extern const device_t sdac_ramdac_device;
|
||||
|
||||
@@ -207,7 +207,7 @@ static const device_config_t cms_config[] =
|
||||
const device_t cms_device =
|
||||
{
|
||||
"Creative Music System / Game Blaster",
|
||||
0, 0,
|
||||
DEVICE_ISA, 0,
|
||||
cms_init, cms_close, NULL,
|
||||
{ NULL }, NULL, NULL,
|
||||
cms_config
|
||||
|
||||
@@ -1315,7 +1315,7 @@ static const device_config_t gus_config[] = {
|
||||
const device_t gus_device =
|
||||
{
|
||||
"Gravis UltraSound",
|
||||
DEVICE_ISA,
|
||||
DEVICE_ISA | DEVICE_AT,
|
||||
0,
|
||||
gus_init, gus_close, NULL,
|
||||
{ NULL },
|
||||
|
||||
@@ -118,7 +118,7 @@ static const device_config_t ssi2001_config[] =
|
||||
const device_t ssi2001_device =
|
||||
{
|
||||
"Innovation SSI-2001",
|
||||
0, 0,
|
||||
DEVICE_ISA, 0,
|
||||
ssi2001_init, ssi2001_close, NULL,
|
||||
{ NULL }, NULL, NULL,
|
||||
ssi2001_config
|
||||
|
||||
@@ -59,6 +59,7 @@
|
||||
#endif
|
||||
|
||||
#define BIOS_ROM_PATH "roms/video/ati28800/bios.bin"
|
||||
#define BIOS_VGAXL_ROM_PATH "roms/video/ati28800/ATI_VGAWonder_XL.bin"
|
||||
|
||||
|
||||
typedef struct ati28800_t
|
||||
@@ -82,6 +83,8 @@ typedef struct ati28800_t
|
||||
int get_korean_font_index;
|
||||
uint16_t get_korean_font_base;
|
||||
int ksc5601_mode_enabled;
|
||||
|
||||
int type, type_korean;
|
||||
} ati28800_t;
|
||||
|
||||
|
||||
@@ -111,7 +114,6 @@ ati28800_log(const char *fmt, ...)
|
||||
|
||||
static void ati28800_recalctimings(svga_t *svga);
|
||||
|
||||
|
||||
static void
|
||||
ati28800_out(uint16_t addr, uint8_t val, void *p)
|
||||
{
|
||||
@@ -134,37 +136,36 @@ ati28800_out(uint16_t addr, uint8_t val, void *p)
|
||||
ati28800_log("ATI 28800 write reg=0x%02X, val=0x%02X\n", ati28800->index, val);
|
||||
switch (ati28800->index) {
|
||||
case 0xa3:
|
||||
ati28800->regs[0xa3] = val & 0x1f;
|
||||
svga_recalctimings(svga);
|
||||
if ((old ^ val) & 0x10)
|
||||
svga_recalctimings(svga);
|
||||
break;
|
||||
case 0xa6:
|
||||
ati28800->regs[0xa6] = val & 0xc9;
|
||||
break;
|
||||
case 0xab:
|
||||
ati28800->regs[0xab] = val & 0xdf;
|
||||
case 0xa7:
|
||||
if ((old ^ val) & 0x80)
|
||||
svga_recalctimings(svga);
|
||||
break;
|
||||
case 0xb0:
|
||||
ati28800->regs[0xb0] = val & 0x7d;
|
||||
svga_recalctimings(svga);
|
||||
break;
|
||||
case 0xb1:
|
||||
ati28800->regs[0xb0] = val & 0x7f;
|
||||
if ((old ^ val) & 0x60)
|
||||
svga_recalctimings(svga);
|
||||
break;
|
||||
case 0xb2:
|
||||
case 0xbe:
|
||||
if (ati28800->regs[0xbe] & 0x08) { /* Read/write bank mode */
|
||||
svga->read_bank = (((val & 0x01) << 3) | ((val & 0xe0) >> 5)) * 0x10000;
|
||||
svga->write_bank = ((val & 0x1e) >> 1) * 0x10000;
|
||||
svga->read_bank = (((ati28800->regs[0xb2] & 0x01) << 3) | ((ati28800->regs[0xb2] & 0xe0) >> 5)) * 0x10000;
|
||||
svga->write_bank = ((ati28800->regs[0xb2] & 0x1e) >> 1) * 0x10000;
|
||||
} else { /* Single bank mode */
|
||||
svga->read_bank = ((val & 0x1e) >> 1) * 0x10000;
|
||||
svga->write_bank = ((val & 0x1e) >> 1) * 0x10000;
|
||||
svga->read_bank = ((ati28800->regs[0xb2] & 0x1e) >> 1) * 0x10000;
|
||||
svga->write_bank = ((ati28800->regs[0xb2] & 0x1e) >> 1) * 0x10000;
|
||||
}
|
||||
if (ati28800->index == 0xbe) {
|
||||
if ((old ^ val) & 0x10)
|
||||
svga_recalctimings(svga);
|
||||
}
|
||||
break;
|
||||
case 0xb3:
|
||||
ati28800->regs[0xb3] = val & 0xef;
|
||||
ati_eeprom_write(&ati28800->eeprom, val & 8, val & 2, val & 1);
|
||||
break;
|
||||
case 0xb6:
|
||||
if ((old ^ val) & 0x10)
|
||||
if ((old ^ val) & 0x11)
|
||||
svga_recalctimings(svga);
|
||||
break;
|
||||
case 0xb8:
|
||||
@@ -179,7 +180,10 @@ ati28800_out(uint16_t addr, uint8_t val, void *p)
|
||||
break;
|
||||
|
||||
case 0x3C6: case 0x3C7: case 0x3C8: case 0x3C9:
|
||||
sc1502x_ramdac_out(addr, val, svga->ramdac, svga);
|
||||
if (ati28800->type == 1)
|
||||
sc1148x_ramdac_out(addr, 0, val, svga->ramdac, svga);
|
||||
else
|
||||
svga_out(addr, val, svga);
|
||||
return;
|
||||
|
||||
case 0x3D4:
|
||||
@@ -190,12 +194,6 @@ ati28800_out(uint16_t addr, uint8_t val, void *p)
|
||||
return;
|
||||
if ((svga->crtcreg == 7) && (svga->crtc[0x11] & 0x80))
|
||||
val = (svga->crtc[7] & ~0x10) | (val & 0x10);
|
||||
if ((ati28800->regs[0xb4] & 0x10) && ((svga->crtcreg == 0x0a) || (svga->crtcreg == 0x0b)))
|
||||
return;
|
||||
if ((ati28800->regs[0xb4] & 0x20) && ((svga->crtc[0x08] & 0x7f) && (svga->crtc[0x14] & 0x1f)))
|
||||
return;
|
||||
if ((ati28800->regs[0xb4] & 0x40) && ((svga->crtcreg <= 0x06) && (svga->crtc[0x07] & 0x10) != 0x10))
|
||||
return;
|
||||
|
||||
old = svga->crtc[svga->crtcreg];
|
||||
svga->crtc[svga->crtcreg] = val;
|
||||
@@ -299,22 +297,23 @@ ati28800_in(uint16_t addr, void *p)
|
||||
break;
|
||||
case 0x1cf:
|
||||
switch (ati28800->index) {
|
||||
case 0xa0:
|
||||
temp = 0x10;
|
||||
break;
|
||||
case 0xaa:
|
||||
temp = ati28800->id;
|
||||
break;
|
||||
case 0xb0:
|
||||
if (ati28800->memory == 1024)
|
||||
temp = 0x08;
|
||||
else if (ati28800->memory == 512)
|
||||
temp = 0x10;
|
||||
else
|
||||
temp = 0x00;
|
||||
temp = ati28800->regs[0xb0] | 0x80;
|
||||
if (ati28800->memory == 1024) {
|
||||
temp &= ~0x10;
|
||||
temp |= 0x08;
|
||||
} else if (ati28800->memory == 512) {
|
||||
temp |= 0x10;
|
||||
temp &= ~0x08;
|
||||
} else {
|
||||
temp &= ~0x18;
|
||||
}
|
||||
break;
|
||||
case 0xb7:
|
||||
temp = ati28800->regs[ati28800->index] & ~8;
|
||||
temp = ati28800->regs[0xb7] & ~8;
|
||||
if (ati_eeprom_read(&ati28800->eeprom))
|
||||
temp |= 8;
|
||||
break;
|
||||
@@ -333,7 +332,9 @@ ati28800_in(uint16_t addr, void *p)
|
||||
break;
|
||||
|
||||
case 0x3C6: case 0x3C7: case 0x3C8: case 0x3C9:
|
||||
return sc1502x_ramdac_in(addr, svga->ramdac, svga);
|
||||
if (ati28800->type == 1)
|
||||
return sc1148x_ramdac_in(addr, 0, svga->ramdac, svga);
|
||||
return svga_in(addr, svga);
|
||||
|
||||
case 0x3D4:
|
||||
temp = svga->crtcreg;
|
||||
@@ -401,8 +402,14 @@ ati28800_recalctimings(svga_t *svga)
|
||||
{
|
||||
ati28800_t *ati28800 = (ati28800_t *)svga->p;
|
||||
|
||||
switch (((ati28800->regs[0xbe] & 0x10) >> 1) | ((ati28800->regs[0xb9] & 2) << 1) |
|
||||
((svga->miscout & 0x0C) >> 2)) {
|
||||
if (ati28800->regs[0xa3] & 0x10)
|
||||
svga->ma_latch |= 0x10000;
|
||||
|
||||
if (ati28800->regs[0xb0] & 0x40)
|
||||
svga->ma_latch |= 0x20000;
|
||||
|
||||
switch (((ati28800->regs[0xbe] & 0x10) >> 1) | ((ati28800->regs[0xb9] & 2) << 1) |
|
||||
((svga->miscout & 0x0C) >> 2)) {
|
||||
case 0x00: svga->clock = (cpuclock * (double)(1ull << 32)) / 42954000.0; break;
|
||||
case 0x01: svga->clock = (cpuclock * (double)(1ull << 32)) / 48771000.0; break;
|
||||
case 0x02: ati28800_log ("clock 2\n"); break;
|
||||
@@ -420,38 +427,69 @@ ati28800_recalctimings(svga_t *svga)
|
||||
case 0x0E: svga->clock = (cpuclock * (double)(1ull << 32)) / 75000000.0; break;
|
||||
case 0x0F: svga->clock = (cpuclock * (double)(1ull << 32)) / 65000000.0; break;
|
||||
default: break;
|
||||
}
|
||||
}
|
||||
|
||||
if (ati28800->regs[0xb8] & 0x40)
|
||||
if (ati28800->regs[0xb8] & 0x40)
|
||||
svga->clock *= 2;
|
||||
|
||||
if (ati28800->regs[0xa3] & 0x10)
|
||||
svga->ma |= 0x10000;
|
||||
if (ati28800->regs[0xa7] & 0x80)
|
||||
svga->clock *= 3;
|
||||
|
||||
if (ati28800->regs[0xb0] & 0x40)
|
||||
svga->ma |= 0x20000;
|
||||
|
||||
if (ati28800->regs[0xb6] & 0x10) {
|
||||
if (ati28800->regs[0xb6] & 0x10) {
|
||||
svga->hdisp <<= 1;
|
||||
svga->htotal <<= 1;
|
||||
svga->rowoffset <<= 1;
|
||||
}
|
||||
|
||||
if (!svga->scrblank && (ati28800->regs[0xb0] & 0x20)) { /* Extended 256 colour modes */
|
||||
switch (svga->bpp) {
|
||||
case 8:
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
svga->rowoffset <<= 1;
|
||||
svga->ma <<= 1;
|
||||
break;
|
||||
case 15:
|
||||
svga->render = svga_render_15bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
svga->rowoffset <<= 1;
|
||||
svga->ma <<= 1;
|
||||
break;
|
||||
svga->gdcreg[5] &= ~0x40;
|
||||
}
|
||||
}
|
||||
|
||||
if (ati28800->regs[0xb0] & 0x20) {
|
||||
svga->gdcreg[5] |= 0x40;
|
||||
}
|
||||
|
||||
if (!svga->scrblank && svga->attr_palette_enable) {
|
||||
if ((svga->gdcreg[6] & 1) || (svga->attrregs[0x10] & 1)) {
|
||||
switch (svga->gdcreg[5] & 0x60) {
|
||||
case 0x00:
|
||||
if (svga->seqregs[1] & 8) /*Low res (320)*/
|
||||
svga->render = svga_render_4bpp_lowres;
|
||||
else
|
||||
svga->render = svga_render_4bpp_highres;
|
||||
break;
|
||||
case 0x20: /*4 colours*/
|
||||
if (svga->seqregs[1] & 8) /*Low res (320)*/
|
||||
svga->render = svga_render_2bpp_lowres;
|
||||
else
|
||||
svga->render = svga_render_2bpp_highres;
|
||||
break;
|
||||
case 0x40: case 0x60: /*256+ colours*/
|
||||
switch (svga->bpp) {
|
||||
case 8:
|
||||
svga->map8 = svga->pallook;
|
||||
if (svga->lowres)
|
||||
svga->render = svga_render_8bpp_lowres;
|
||||
else {
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
svga->rowoffset <<= 1;
|
||||
svga->ma_latch <<= 1;
|
||||
}
|
||||
break;
|
||||
case 15:
|
||||
if (svga->lowres)
|
||||
svga->render = svga_render_15bpp_lowres;
|
||||
else {
|
||||
svga->render = svga_render_15bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
svga->rowoffset <<= 1;
|
||||
svga->ma_latch <<= 1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
svga->vram_display_mask = (ati28800->regs[0xb6] & 1) ? ((ati28800->memory << 10) - 1) : 0x3ffff;
|
||||
}
|
||||
|
||||
|
||||
@@ -466,14 +504,15 @@ ati28800k_recalctimings(svga_t *svga)
|
||||
svga->render = svga_render_text_80_ksc5601;
|
||||
}
|
||||
|
||||
|
||||
void *
|
||||
ati28800k_init(const device_t *info)
|
||||
{
|
||||
ati28800_t *ati28800 = (ati28800_t *) malloc(sizeof(ati28800_t));
|
||||
memset(ati28800, 0, sizeof(ati28800_t));
|
||||
|
||||
if (info->local == 0) {
|
||||
ati28800->type_korean = info->local;
|
||||
|
||||
if (ati28800->type_korean == 0) {
|
||||
ati28800->memory = device_get_config_int("memory");
|
||||
video_inform(VIDEO_FLAG_TYPE_SPECIAL, &timing_ati28800);
|
||||
} else {
|
||||
@@ -489,7 +528,7 @@ ati28800k_init(const device_t *info)
|
||||
ati28800->in_get_korean_font_kind_set = 0;
|
||||
ati28800->ksc5601_mode_enabled = 0;
|
||||
|
||||
switch(info->local) {
|
||||
switch(ati28800->type_korean) {
|
||||
case 0:
|
||||
default:
|
||||
rom_init(&ati28800->bios_rom, BIOS_ATIKOR_PATH, 0xc0000, 0x8000, 0x7fff, 0, MEM_MAPPING_EXTERNAL);
|
||||
@@ -512,12 +551,12 @@ ati28800k_init(const device_t *info)
|
||||
NULL,
|
||||
NULL);
|
||||
|
||||
ati28800->svga.ramdac = device_add(&sc1502x_ramdac_device);
|
||||
|
||||
io_sethandler(0x01ce, 0x0002, ati28800k_in, NULL, NULL, ati28800k_out, NULL, NULL, ati28800);
|
||||
io_sethandler(0x03c0, 0x0020, ati28800k_in, NULL, NULL, ati28800k_out, NULL, NULL, ati28800);
|
||||
|
||||
ati28800->svga.miscout = 1;
|
||||
ati28800->svga.bpp = 8;
|
||||
ati28800->svga.packed_chain4 = 1;
|
||||
ati28800->svga.ksc5601_sbyte_mask = 0;
|
||||
ati28800->svga.ksc5601_udc_area_msb[0] = 0xC9;
|
||||
ati28800->svga.ksc5601_udc_area_msb[1] = 0xFE;
|
||||
@@ -541,14 +580,16 @@ ati28800_init(const device_t *info)
|
||||
|
||||
ati28800->memory = device_get_config_int("memory");
|
||||
|
||||
switch(info->local) {
|
||||
ati28800->type = info->local;
|
||||
|
||||
switch(ati28800->type) {
|
||||
case VGAWONDERXL:
|
||||
ati28800->id = 6;
|
||||
rom_init_interleaved(&ati28800->bios_rom,
|
||||
BIOS_VGAXL_EVEN_PATH,
|
||||
BIOS_VGAXL_ODD_PATH,
|
||||
0xc0000, 0x10000, 0xffff,
|
||||
0, MEM_MAPPING_EXTERNAL);
|
||||
ati28800->id = 5;
|
||||
rom_init(&ati28800->bios_rom,
|
||||
BIOS_VGAXL_ROM_PATH,
|
||||
0xc0000, 0x8000, 0x7fff,
|
||||
0, MEM_MAPPING_EXTERNAL);
|
||||
ati28800->svga.ramdac = device_add(&sc11486_ramdac_device);
|
||||
break;
|
||||
|
||||
#if defined(DEV_BRANCH) && defined(USE_XL24)
|
||||
@@ -576,8 +617,6 @@ ati28800_init(const device_t *info)
|
||||
ati28800_in, ati28800_out,
|
||||
NULL,
|
||||
NULL);
|
||||
|
||||
ati28800->svga.ramdac = device_add(&sc1502x_ramdac_device);
|
||||
|
||||
io_sethandler(0x01ce, 2,
|
||||
ati28800_in, NULL, NULL,
|
||||
@@ -587,8 +626,10 @@ ati28800_init(const device_t *info)
|
||||
ati28800_out, NULL, NULL, ati28800);
|
||||
|
||||
ati28800->svga.miscout = 1;
|
||||
ati28800->svga.bpp = 8;
|
||||
ati28800->svga.packed_chain4 = 1;
|
||||
|
||||
switch (info->local) {
|
||||
switch (ati28800->type) {
|
||||
case VGAWONDERXL:
|
||||
ati_eeprom_load(&ati28800->eeprom, "ati28800xl.nvr", 0);
|
||||
break;
|
||||
@@ -616,7 +657,7 @@ ati28800_available(void)
|
||||
|
||||
|
||||
static int
|
||||
ati28800k_available()
|
||||
ati28800k_available(void)
|
||||
{
|
||||
return ((rom_present(BIOS_ATIKOR_PATH) && rom_present(FONT_ATIKOR_PATH)));
|
||||
}
|
||||
@@ -625,7 +666,7 @@ ati28800k_available()
|
||||
static int
|
||||
compaq_ati28800_available(void)
|
||||
{
|
||||
return((rom_present(BIOS_VGAXL_EVEN_PATH) && rom_present(BIOS_VGAXL_ODD_PATH)));
|
||||
return((rom_present(BIOS_VGAXL_ROM_PATH)));
|
||||
}
|
||||
|
||||
|
||||
@@ -719,7 +760,7 @@ static const device_config_t ati28800_wonderxl_config[] =
|
||||
|
||||
const device_t ati28800_device =
|
||||
{
|
||||
"ATI-28800",
|
||||
"ATI 28800-5 (ATI VGA Charger)",
|
||||
DEVICE_ISA,
|
||||
0,
|
||||
ati28800_init, ati28800_close, NULL,
|
||||
@@ -765,7 +806,7 @@ const device_t ati28800k_spc6033p_device =
|
||||
|
||||
const device_t compaq_ati28800_device =
|
||||
{
|
||||
"Compaq ATI-28800",
|
||||
"ATI 28800-5 (ATI VGA Wonder XL)",
|
||||
DEVICE_ISA,
|
||||
VGAWONDERXL,
|
||||
ati28800_init, ati28800_close, NULL,
|
||||
|
||||
@@ -97,11 +97,12 @@ typedef struct et4000w32p_t
|
||||
uint32_t pattern_addr, source_addr, dest_addr, mix_addr;
|
||||
} queued, internal;
|
||||
|
||||
uint8_t osr;
|
||||
uint8_t status;
|
||||
|
||||
int pattern_x, source_x, pattern_x_back, source_x_back,
|
||||
pattern_y, source_y, cpu_dat_pos, pix_pos,
|
||||
cpu_input_num;
|
||||
cpu_input_num, queue;
|
||||
|
||||
uint32_t pattern_addr, source_addr, dest_addr, mix_addr,
|
||||
pattern_back, source_back, dest_back, mix_back,
|
||||
@@ -119,9 +120,9 @@ typedef struct et4000w32p_t
|
||||
|
||||
static int et4000w32_vbus[4] = {1, 2, 4, 4};
|
||||
|
||||
static int et4000w32_max_x[8] = {0, 0, 4, 8, 16, 32, 64, 0x70000000};
|
||||
static int et4000w32_wrap_x[8] = {0, 0, 3, 7, 15, 31, 63, 0xffffffff};
|
||||
static int et4000w32_wrap_y[8] = {1, 2, 4, 8, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff};
|
||||
static int et4000w32_max_x[8] = {0,0,4,8,0x10,0x20,0x40,0x70000000};
|
||||
static int et4000w32_wrap_x[8] = {0,0,3,7,0x0F,0x1F,0x3F,~0};
|
||||
static int et4000w32_wrap_y[8] = {1,2,4,8,~0,~0,~0,~0};
|
||||
|
||||
static video_timings_t timing_et4000w32_vlb = {VIDEO_BUS, 4, 4, 4, 10, 10, 10};
|
||||
static video_timings_t timing_et4000w32_pci = {VIDEO_PCI, 4, 4, 4, 10, 10, 10};
|
||||
@@ -271,14 +272,24 @@ et4000w32p_out(uint16_t addr, uint8_t val, void *p)
|
||||
switch (svga->bpp) {
|
||||
case 8:
|
||||
svga->hwcursor.xoff += 32;
|
||||
break;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (svga->hwcursor.xsize == 128) {
|
||||
svga->hwcursor.xoff &= 0x7f;
|
||||
svga->hwcursor.yoff &= 0x7f;
|
||||
if (et4000->type > ET4000W32P_REVC) {
|
||||
if (svga->bpp == 24) {
|
||||
et4000->adjust_cursor = 2;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (et4000->type > ET4000W32P_REVC) {
|
||||
if (svga->bpp == 24 && et4000->adjust_cursor) {
|
||||
et4000->adjust_cursor = 0;
|
||||
}
|
||||
}
|
||||
svga->hwcursor.xoff &= 0x3f;
|
||||
svga->hwcursor.yoff &= 0x3f;
|
||||
}
|
||||
@@ -331,10 +342,15 @@ et4000w32p_in(uint16_t addr, void *p)
|
||||
case 0x214B: case 0x215B: case 0x216B: case 0x217B:
|
||||
if (et4000->index == 0xec)
|
||||
return (et4000->regs[0xec] & 0xf) | (et4000->rev << 4);
|
||||
if (et4000->index == 0xee) { /* Preliminary implementation */
|
||||
if (svga->bpp == 8)
|
||||
return 3;
|
||||
else if (svga->bpp == 16)
|
||||
if (et4000->index == 0xee) {
|
||||
if (svga->bpp == 8) {
|
||||
if ((svga->gdcreg[5] & 0x60) >= 0x40)
|
||||
return 3;
|
||||
else if ((svga->gdcreg[5] & 0x60) == 0x20)
|
||||
return 1;
|
||||
else
|
||||
return 2;
|
||||
} else if (svga->bpp == 15 || svga->bpp == 16)
|
||||
return 4;
|
||||
else
|
||||
break;
|
||||
@@ -410,13 +426,21 @@ et4000w32p_recalctimings(svga_t *svga)
|
||||
switch (svga->bpp) {
|
||||
case 15: case 16:
|
||||
svga->hdisp >>= 1;
|
||||
if (et4000->type <= ET4000W32P_REVC)
|
||||
et4000->adjust_cursor = 1;
|
||||
if (et4000->type <= ET4000W32P_REVC) {
|
||||
if (et4000->type == ET4000W32P_REVC) {
|
||||
if (svga->hdisp != 1024)
|
||||
et4000->adjust_cursor = 1;
|
||||
} else
|
||||
et4000->adjust_cursor = 1;
|
||||
}
|
||||
break;
|
||||
case 24:
|
||||
svga->hdisp /= 3;
|
||||
if (et4000->type <= ET4000W32P_REVC)
|
||||
et4000->adjust_cursor = 2;
|
||||
if (et4000->type == ET4000W32P_DIAMOND && (svga->hdisp == 640/2 || svga->hdisp == 1232)) {
|
||||
svga->hdisp = 640;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -572,45 +596,51 @@ et4000w32p_accel_write_fifo(et4000w32p_t *et4000, uint32_t addr, uint8_t val)
|
||||
case 0x7f80: et4000->acl.queued.pattern_addr = (et4000->acl.queued.pattern_addr & 0xFFFFFF00) | val; break;
|
||||
case 0x7f81: et4000->acl.queued.pattern_addr = (et4000->acl.queued.pattern_addr & 0xFFFF00FF) | (val << 8); break;
|
||||
case 0x7f82: et4000->acl.queued.pattern_addr = (et4000->acl.queued.pattern_addr & 0xFF00FFFF) | (val << 16); break;
|
||||
case 0x7f83: et4000->acl.queued.pattern_addr = (et4000->acl.queued.pattern_addr & 0x00FFFFFF) | (val << 24); break;
|
||||
case 0x7f83: et4000->acl.queued.pattern_addr = (et4000->acl.queued.pattern_addr & 0x00FFFFFF) | (val << 24); et4000->acl.queue++; break;
|
||||
case 0x7f84: et4000->acl.queued.source_addr = (et4000->acl.queued.source_addr & 0xFFFFFF00) | val; break;
|
||||
case 0x7f85: et4000->acl.queued.source_addr = (et4000->acl.queued.source_addr & 0xFFFF00FF) | (val << 8); break;
|
||||
case 0x7f86: et4000->acl.queued.source_addr = (et4000->acl.queued.source_addr & 0xFF00FFFF) | (val << 16); break;
|
||||
case 0x7f87: et4000->acl.queued.source_addr = (et4000->acl.queued.source_addr & 0x00FFFFFF) | (val << 24); break;
|
||||
case 0x7f87: et4000->acl.queued.source_addr = (et4000->acl.queued.source_addr & 0x00FFFFFF) | (val << 24); et4000->acl.queue++; break;
|
||||
case 0x7f88: et4000->acl.queued.pattern_off = (et4000->acl.queued.pattern_off & 0xFF00) | val; break;
|
||||
case 0x7f89: et4000->acl.queued.pattern_off = (et4000->acl.queued.pattern_off & 0x00FF) | (val << 8); break;
|
||||
case 0x7f89: et4000->acl.queued.pattern_off = (et4000->acl.queued.pattern_off & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7f8a: et4000->acl.queued.source_off = (et4000->acl.queued.source_off & 0xFF00) | val; break;
|
||||
case 0x7f8b: et4000->acl.queued.source_off = (et4000->acl.queued.source_off & 0x00FF) | (val << 8); break;
|
||||
case 0x7f8b: et4000->acl.queued.source_off = (et4000->acl.queued.source_off & 0x00FF) | (val << 8); et4000->acl.queue++;break;
|
||||
case 0x7f8c: et4000->acl.queued.dest_off = (et4000->acl.queued.dest_off & 0xFF00) | val; break;
|
||||
case 0x7f8d: et4000->acl.queued.dest_off = (et4000->acl.queued.dest_off & 0x00FF) | (val << 8); break;
|
||||
case 0x7f8d: et4000->acl.queued.dest_off = (et4000->acl.queued.dest_off & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7f8e:
|
||||
et4000->acl.queue++;
|
||||
if (et4000->type >= ET4000W32P_REVC)
|
||||
et4000->acl.queued.pixel_depth = val;
|
||||
else
|
||||
et4000->acl.queued.vbus = val;
|
||||
break;
|
||||
case 0x7f8f: et4000->acl.queued.xy_dir = val; break;
|
||||
case 0x7f90: et4000->acl.queued.pattern_wrap = val; break;
|
||||
case 0x7f92: et4000->acl.queued.source_wrap = val; break;
|
||||
case 0x7f8f: et4000->acl.queued.xy_dir = val; et4000->acl.queue++; break;
|
||||
case 0x7f90: et4000->acl.queued.pattern_wrap = val; et4000->acl.queue++; break;
|
||||
case 0x7f92: et4000->acl.queued.source_wrap = val; et4000->acl.queue++; break;
|
||||
case 0x7f98: et4000->acl.queued.count_x = (et4000->acl.queued.count_x & 0xFF00) | val; break;
|
||||
case 0x7f99: et4000->acl.queued.count_x = (et4000->acl.queued.count_x & 0x00FF) | (val << 8); break;
|
||||
case 0x7f99: et4000->acl.queued.count_x = (et4000->acl.queued.count_x & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7f9a: et4000->acl.queued.count_y = (et4000->acl.queued.count_y & 0xFF00) | val; break;
|
||||
case 0x7f9b: et4000->acl.queued.count_y = (et4000->acl.queued.count_y & 0x00FF) | (val << 8); break;
|
||||
case 0x7f9c: et4000->acl.queued.ctrl_routing = val; break;
|
||||
case 0x7f9d: et4000->acl.queued.ctrl_reload = val; break;
|
||||
case 0x7f9e: et4000->acl.queued.rop_bg = val; break;
|
||||
case 0x7f9f: et4000->acl.queued.rop_fg = val; break;
|
||||
case 0x7f9b: et4000->acl.queued.count_y = (et4000->acl.queued.count_y & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7f9c: et4000->acl.queued.ctrl_routing = val; et4000->acl.queue++; break;
|
||||
case 0x7f9d: et4000->acl.queued.ctrl_reload = val; et4000->acl.queue++; break;
|
||||
case 0x7f9e: et4000->acl.queued.rop_bg = val; et4000->acl.queue++; break;
|
||||
case 0x7f9f: et4000->acl.queued.rop_fg = val; et4000->acl.queue++; break;
|
||||
case 0x7fa0: et4000->acl.queued.dest_addr = (et4000->acl.queued.dest_addr & 0xFFFFFF00) | val; break;
|
||||
case 0x7fa1: et4000->acl.queued.dest_addr = (et4000->acl.queued.dest_addr & 0xFFFF00FF) | (val << 8); break;
|
||||
case 0x7fa2: et4000->acl.queued.dest_addr = (et4000->acl.queued.dest_addr & 0xFF00FFFF) | (val << 16); break;
|
||||
case 0x7fa3: et4000->acl.queued.dest_addr = (et4000->acl.queued.dest_addr & 0x00FFFFFF) | (val << 24);
|
||||
et4000->acl.queue++;
|
||||
et4000->acl.internal = et4000->acl.queued;
|
||||
if (et4000->type >= ET4000W32P_REVC) {
|
||||
et4000w32p_blit_start(et4000);
|
||||
if (!(et4000->acl.queued.ctrl_routing & 0x43))
|
||||
et4000w32p_blit(0xffffff, ~0, 0, 0, et4000);
|
||||
if ((et4000->acl.queued.ctrl_routing & 0x40) && !(et4000->acl.internal.ctrl_routing & 3))
|
||||
et4000w32p_blit(4, ~0, 0, 0, et4000);
|
||||
if (et4000->acl.osr & 0x10) {
|
||||
et4000w32p_blit_start(et4000);
|
||||
if (!(et4000->acl.queued.ctrl_routing & 0x43)) {
|
||||
et4000w32p_blit(0xffffff, ~0, 0, 0, et4000);
|
||||
}
|
||||
if ((et4000->acl.queued.ctrl_routing & 0x40) && !(et4000->acl.internal.ctrl_routing & 3)) {
|
||||
et4000w32p_blit(4, ~0, 0, 0, et4000);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
et4000w32_blit_start(et4000);
|
||||
et4000->acl.cpu_input_num = 0;
|
||||
@@ -621,15 +651,15 @@ et4000w32p_accel_write_fifo(et4000w32p_t *et4000, uint32_t addr, uint8_t val)
|
||||
case 0x7fa4: et4000->acl.queued.mix_addr = (et4000->acl.queued.mix_addr & 0xFFFFFF00) | val; break;
|
||||
case 0x7fa5: et4000->acl.queued.mix_addr = (et4000->acl.queued.mix_addr & 0xFFFF00FF) | (val << 8); break;
|
||||
case 0x7fa6: et4000->acl.queued.mix_addr = (et4000->acl.queued.mix_addr & 0xFF00FFFF) | (val << 16); break;
|
||||
case 0x7fa7: et4000->acl.queued.mix_addr = (et4000->acl.queued.mix_addr & 0x00FFFFFF) | (val << 24); break;
|
||||
case 0x7fa7: et4000->acl.queued.mix_addr = (et4000->acl.queued.mix_addr & 0x00FFFFFF) | (val << 24); et4000->acl.queue++; break;
|
||||
case 0x7fa8: et4000->acl.queued.mix_off = (et4000->acl.queued.mix_off & 0xFF00) | val; break;
|
||||
case 0x7fa9: et4000->acl.queued.mix_off = (et4000->acl.queued.mix_off & 0x00FF) | (val << 8); break;
|
||||
case 0x7fa9: et4000->acl.queued.mix_off = (et4000->acl.queued.mix_off & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7faa: et4000->acl.queued.error = (et4000->acl.queued.error & 0xFF00) | val; break;
|
||||
case 0x7fab: et4000->acl.queued.error = (et4000->acl.queued.error & 0x00FF) | (val << 8); break;
|
||||
case 0x7fab: et4000->acl.queued.error = (et4000->acl.queued.error & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7fac: et4000->acl.queued.dmin = (et4000->acl.queued.dmin & 0xFF00) | val; break;
|
||||
case 0x7fad: et4000->acl.queued.dmin = (et4000->acl.queued.dmin & 0x00FF) | (val << 8); break;
|
||||
case 0x7fad: et4000->acl.queued.dmin = (et4000->acl.queued.dmin & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
case 0x7fae: et4000->acl.queued.dmaj = (et4000->acl.queued.dmaj & 0xFF00) | val; break;
|
||||
case 0x7faf: et4000->acl.queued.dmaj = (et4000->acl.queued.dmaj & 0x00FF) | (val << 8); break;
|
||||
case 0x7faf: et4000->acl.queued.dmaj = (et4000->acl.queued.dmaj & 0x00FF) | (val << 8); et4000->acl.queue++; break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -641,17 +671,17 @@ et4000w32p_accel_write_mmu(et4000w32p_t *et4000, uint32_t addr, uint8_t val)
|
||||
if (!(et4000->acl.status & ACL_XYST))
|
||||
return;
|
||||
if (et4000->acl.internal.ctrl_routing & 3) {
|
||||
et4000->acl.queue++;
|
||||
if ((et4000->acl.internal.ctrl_routing & 3) == 2) {
|
||||
if (et4000->acl.mix_addr & 7)
|
||||
et4000w32p_blit(8 - (et4000->acl.mix_addr & 7), val >> (et4000->acl.mix_addr & 7), 0, 1, et4000);
|
||||
else
|
||||
et4000w32p_blit(8, val, 0, 1, et4000);
|
||||
et4000w32p_blit(8 - (et4000->acl.mix_addr & 7), val >> (et4000->acl.mix_addr & 7), 0, 1, et4000);
|
||||
}
|
||||
else if ((et4000->acl.internal.ctrl_routing & 3) == 1)
|
||||
else if ((et4000->acl.internal.ctrl_routing & 3) == 1) {
|
||||
et4000w32p_blit(1, ~0, val, 2, et4000);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (!(et4000->acl.status & ACL_XYST)) {
|
||||
et4000->acl.queue++;
|
||||
et4000->acl.queued.dest_addr = (addr & 0x1FFF) + et4000->mmu.base[et4000->bank];
|
||||
et4000->acl.internal = et4000->acl.queued;
|
||||
et4000w32_blit_start(et4000);
|
||||
@@ -661,6 +691,7 @@ et4000w32p_accel_write_mmu(et4000w32p_t *et4000, uint32_t addr, uint8_t val)
|
||||
}
|
||||
|
||||
if (et4000->acl.internal.ctrl_routing & 7) {
|
||||
et4000->acl.queue++;
|
||||
et4000->acl.cpu_input = (et4000->acl.cpu_input &~ (0xFF << (et4000->acl.cpu_input_num << 3))) |
|
||||
(val << (et4000->acl.cpu_input_num << 3));
|
||||
et4000->acl.cpu_input_num++;
|
||||
@@ -719,6 +750,7 @@ et4000w32p_mmu_write(uint32_t addr, uint8_t val, void *p)
|
||||
case 0x7f0a: et4000->mmu.base[2] = (et4000->mmu.base[2] & 0xFF00FFFF) | (val << 16); break;
|
||||
case 0x7f0b: et4000->mmu.base[2] = (et4000->mmu.base[2] & 0x00FFFFFF) | (val << 24); break;
|
||||
case 0x7f13: et4000->mmu.ctrl = val; break;
|
||||
case 0x7f31: et4000->acl.osr = val; break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -774,13 +806,23 @@ et4000w32p_mmu_read(uint32_t addr, void *p)
|
||||
case 0x7f13: return et4000->mmu.ctrl;
|
||||
|
||||
case 0x7f36:
|
||||
if (et4000->type >= ET4000W32P_REVC) {
|
||||
if (et4000->type >= ET4000W32P_REVC) {
|
||||
if (et4000->acl.queue) {
|
||||
et4000->acl.status |= ACL_RDST;
|
||||
et4000->acl.queue = 0;
|
||||
} else
|
||||
et4000->acl.status &= ~ACL_RDST;
|
||||
|
||||
temp = et4000->acl.status;
|
||||
temp &= ~(ACL_RDST | ACL_WRST);
|
||||
if (temp == ACL_XYST && (et4000->acl.internal.ctrl_routing == 1 || et4000->acl.internal.ctrl_routing == 2))
|
||||
temp |= ACL_RDST;
|
||||
} else {
|
||||
et4000->acl.status &= ~(ACL_XYST | ACL_SSO);
|
||||
|
||||
if (et4000->acl.queue) {
|
||||
et4000->acl.status |= ACL_RDST;
|
||||
et4000->acl.queue = 0;
|
||||
} else
|
||||
et4000->acl.status &= ~ACL_RDST;
|
||||
|
||||
temp = et4000->acl.status;
|
||||
}
|
||||
return temp;
|
||||
@@ -886,7 +928,7 @@ et4000w32p_blit_start(et4000w32p_t *et4000)
|
||||
et4000->acl.status |= ACL_XYST;
|
||||
et4000w32_log("ACL status XYST set\n");
|
||||
if ((!(et4000->acl.internal.ctrl_routing & 7) || (et4000->acl.internal.ctrl_routing & 4)) && !(et4000->acl.internal.ctrl_routing & 0x40))
|
||||
et4000->acl.status |= ACL_SSO;
|
||||
et4000->acl.status |= ACL_SSO;
|
||||
|
||||
if (et4000w32_wrap_x[et4000->acl.internal.pattern_wrap & 7]) {
|
||||
et4000->acl.pattern_x = et4000->acl.pattern_addr & et4000w32_wrap_x[et4000->acl.internal.pattern_wrap & 7];
|
||||
@@ -1000,7 +1042,7 @@ et4000w32p_blit(int count, uint32_t mix, uint32_t sdat, int cpu_input, et4000w32
|
||||
if (!(et4000->acl.status & ACL_XYST) && (et4000->type >= ET4000W32P_REVC))
|
||||
return;
|
||||
|
||||
if (et4000->acl.internal.xy_dir & 0x80){ /* Line draw */
|
||||
if (et4000->acl.internal.xy_dir & 0x80) { /* Line draw */
|
||||
while (count--) {
|
||||
et4000w32_log("%i,%i : ", et4000->acl.internal.pos_x, et4000->acl.internal.pos_y);
|
||||
pattern = svga->vram[(et4000->acl.pattern_addr + et4000->acl.pattern_x) & et4000->vram_mask];
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <86box/device.h>
|
||||
#include <86box/video.h>
|
||||
#include <86box/vid_svga.h>
|
||||
#include <86box/vid_svga_render.h>
|
||||
|
||||
#define BIOS_037C_PATH "roms/video/oti/bios.bin"
|
||||
#define BIOS_067_AMA932J_PATH "roms/machines/ama932j/oti067.bin"
|
||||
@@ -82,6 +83,14 @@ oti_out(uint16_t addr, uint8_t val, void *p)
|
||||
return;
|
||||
} else
|
||||
break;
|
||||
break;
|
||||
|
||||
case 0x3c6: case 0x3c7: case 0x3c8: case 0x3c9:
|
||||
if (oti->chip_id == OTI_077)
|
||||
sc1148x_ramdac_out(addr, 0, val, svga->ramdac, svga);
|
||||
else
|
||||
svga_out(addr, val, svga);
|
||||
return;
|
||||
|
||||
case 0x3D4:
|
||||
if (oti->chip_id)
|
||||
@@ -213,6 +222,11 @@ oti_in(uint16_t addr, void *p)
|
||||
temp = oti->enable_register;
|
||||
break;
|
||||
|
||||
case 0x3c6: case 0x3c7: case 0x3c8: case 0x3c9:
|
||||
if (oti->chip_id == OTI_077)
|
||||
return sc1148x_ramdac_in(addr, 0, svga->ramdac, svga);
|
||||
return svga_in(addr, svga);
|
||||
|
||||
case 0x3CF:
|
||||
return svga->gdcreg[svga->gdcaddr & 0xf];
|
||||
|
||||
@@ -340,6 +354,14 @@ oti_recalctimings(svga_t *svga)
|
||||
if ((oti->regs[0x0d] & 0x0c) && !(oti->regs[0x0d] & 0x10)) svga->rowoffset <<= 1;
|
||||
|
||||
svga->interlace = oti->regs[0x14] & 0x80;
|
||||
|
||||
if (svga->bpp == 16) {
|
||||
svga->render = svga_render_16bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
} else if (svga->bpp == 15) {
|
||||
svga->render = svga_render_15bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -393,6 +415,9 @@ oti_init(const device_t *info)
|
||||
svga_init(info, &oti->svga, oti, oti->vram_size << 10,
|
||||
oti_recalctimings, oti_in, oti_out, NULL, NULL);
|
||||
|
||||
if (oti->chip_id == OTI_077)
|
||||
oti->svga.ramdac = device_add(&sc11487_ramdac_device); /*Actually a 82c487, probably a clone.*/
|
||||
|
||||
io_sethandler(0x03c0, 32,
|
||||
oti_in, NULL, NULL, oti_out, NULL, NULL, oti);
|
||||
|
||||
|
||||
@@ -54,6 +54,7 @@ typedef struct paradise_t
|
||||
uint32_t read_bank[4], write_bank[4];
|
||||
|
||||
int interlace;
|
||||
int check;
|
||||
|
||||
struct {
|
||||
uint8_t reg_block_ptr;
|
||||
@@ -105,6 +106,13 @@ void paradise_out(uint16_t addr, uint8_t val, void *p)
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x3c6: case 0x3c7: case 0x3c8: case 0x3c9:
|
||||
if (paradise->type == WD90C30)
|
||||
sc1148x_ramdac_out(addr, 0, val, svga->ramdac, svga);
|
||||
else
|
||||
svga_out(addr, val, svga);
|
||||
return;
|
||||
|
||||
case 0x3cf:
|
||||
if (svga->gdcaddr >= 9 && svga->gdcaddr <= 0x0e) {
|
||||
if ((paradise->pr5 & 7) != 5)
|
||||
@@ -215,7 +223,12 @@ uint8_t paradise_in(uint16_t addr, void *p)
|
||||
return svga->seqregs[svga->seqaddr & 0x1f];
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
case 0x3c6: case 0x3c7: case 0x3c8: case 0x3c9:
|
||||
if (paradise->type == WD90C30)
|
||||
return sc1148x_ramdac_in(addr, 0, svga->ramdac, svga);
|
||||
return svga_in(addr, svga);
|
||||
|
||||
case 0x3cf:
|
||||
if (svga->gdcaddr >= 9 && svga->gdcaddr <= 0x0e) {
|
||||
if ((paradise->pr5 & 7) != 5)
|
||||
@@ -232,8 +245,11 @@ uint8_t paradise_in(uint16_t addr, void *p)
|
||||
paradise->pr1 &= ~0x40;
|
||||
} else if (paradise->vram_mask == (1024 << 10) - 1) {
|
||||
paradise->pr1 |= 0xc0;
|
||||
if (svga->bpp >= 8 && !svga->lowres) /*Horrible tweak, but needed to get around black corruption in 1M mode*/
|
||||
/*The following is a horrible tweak, but needed to get around black corruption in 1M mode*/
|
||||
if (svga->bpp >= 8 && (svga->gdcreg[0x0e] & 0x01) && paradise->check)
|
||||
paradise->pr1 &= ~0x40;
|
||||
else if (!(svga->gdcreg[0x0e] & 0x01) && !(svga->crtc[0x14] & 0x40) && paradise->check)
|
||||
paradise->check = 0;
|
||||
}
|
||||
return paradise->pr1;
|
||||
case 6:
|
||||
@@ -336,9 +352,25 @@ void paradise_recalctimings(svga_t *svga)
|
||||
svga->interlace = 1;
|
||||
}
|
||||
}
|
||||
|
||||
if (svga->bpp >= 8 && !svga->lowres)
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
|
||||
if (paradise->type < WD90C30) {
|
||||
if (svga->bpp >= 8 && !svga->lowres)
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
} else {
|
||||
if (svga->bpp >= 8 && !svga->lowres) {
|
||||
if (svga->bpp == 16) {
|
||||
svga->render = svga_render_16bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
} else if (svga->bpp == 15) {
|
||||
svga->render = svga_render_15bpp_highres;
|
||||
svga->hdisp >>= 1;
|
||||
} else {
|
||||
if ((svga->crtc[0x17] == 0xc2) && (svga->crtc[0x14] & 0x40))
|
||||
paradise->check = 1;
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void paradise_write(uint32_t addr, uint8_t val, void *p)
|
||||
@@ -348,7 +380,7 @@ static void paradise_write(uint32_t addr, uint8_t val, void *p)
|
||||
|
||||
addr &= svga->banked_mask;
|
||||
addr = (addr & 0x7fff) + paradise->write_bank[(addr >> 15) & 3];
|
||||
|
||||
|
||||
svga_write_linear(addr, val, svga);
|
||||
}
|
||||
static void paradise_writew(uint32_t addr, uint16_t val, void *p)
|
||||
@@ -421,6 +453,7 @@ void *paradise_init(const device_t *info, uint32_t memsize)
|
||||
NULL);
|
||||
paradise->vram_mask = memsize - 1;
|
||||
svga->decode_mask = memsize - 1;
|
||||
svga->ramdac = device_add(&sc11487_ramdac_device); /*Actually a Winbond W82c487-80, probably a clone.*/
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
@@ -239,7 +239,7 @@ typedef struct s3_t
|
||||
uint16_t multifunc[16];
|
||||
uint8_t pix_trans[4];
|
||||
int ssv_state;
|
||||
|
||||
|
||||
int cx, cy;
|
||||
int px, py;
|
||||
int sx, sy;
|
||||
@@ -348,6 +348,7 @@ typedef struct s3_t
|
||||
|
||||
int translate;
|
||||
int enable_8514;
|
||||
int color_16bit;
|
||||
volatile int busy, force_busy;
|
||||
|
||||
uint8_t thread_run, serialport;
|
||||
@@ -454,7 +455,7 @@ static void s3_visionx68_video_engine_op(uint32_t cpu_dat, s3_t *s3);
|
||||
temp = svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx)) & s3->vram_mask]; \
|
||||
|
||||
#define READ_PIXTRANS_WORD \
|
||||
if (s3->bpp == 0) { \
|
||||
if (s3->bpp == 0 && !s3->color_16bit) { \
|
||||
temp = svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx)) & s3->vram_mask]; \
|
||||
temp |= (svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx + 1)) & s3->vram_mask] << 8); \
|
||||
} else { \
|
||||
@@ -462,7 +463,7 @@ static void s3_visionx68_video_engine_op(uint32_t cpu_dat, s3_t *s3);
|
||||
}
|
||||
|
||||
#define READ_PIXTRANS_LONG \
|
||||
if (s3->bpp == 0) { \
|
||||
if (s3->bpp == 0 && !s3->color_16bit) { \
|
||||
temp = svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx)) & s3->vram_mask]; \
|
||||
temp |= (svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx + 1)) & s3->vram_mask] << 8); \
|
||||
temp |= (svga->vram[dword_remap(svga, (s3->accel.dest + s3->accel.cx + 2)) & s3->vram_mask] << 16); \
|
||||
@@ -521,7 +522,7 @@ s3_accel_out_pixtrans_w(s3_t *s3, uint16_t val)
|
||||
{
|
||||
svga_t *svga = &s3->svga;
|
||||
|
||||
if (s3_cpu_src(s3)) {
|
||||
if (s3->accel.cmd & 0x100) {
|
||||
switch (s3->accel.cmd & 0x600) {
|
||||
case 0x000:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
@@ -531,8 +532,12 @@ s3_accel_out_pixtrans_w(s3_t *s3, uint16_t val)
|
||||
s3_accel_start(8, 1, val | (val << 16), 0, s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, val | (val << 16), s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, val | (val << 16), s3);
|
||||
} else {
|
||||
if (s3->color_16bit)
|
||||
s3_accel_start(2, 1, 0xffffffff, val | (val << 16), s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, val | (val << 16), s3);
|
||||
}
|
||||
break;
|
||||
case 0x200:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
@@ -587,7 +592,7 @@ s3_accel_out_pixtrans_w(s3_t *s3, uint16_t val)
|
||||
static void
|
||||
s3_accel_out_pixtrans_l(s3_t *s3, uint32_t val)
|
||||
{
|
||||
if (s3_cpu_src(s3)) {
|
||||
if (s3->accel.cmd & 0x100) {
|
||||
switch (s3->accel.cmd & 0x600) {
|
||||
case 0x000:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
@@ -701,12 +706,14 @@ s3_accel_out_fifo(s3_t *s3, uint16_t port, uint8_t val)
|
||||
s3->accel.cur_x2 = (s3->accel.cur_x2 & 0xff) | ((val & 0x0f) << 8);
|
||||
s3->accel.poly_cx2 = s3->accel.cur_x2 << 20;
|
||||
break;
|
||||
|
||||
|
||||
case 0xcae8:
|
||||
case 0x8948: case 0x8ae8:
|
||||
s3->accel.draw_fifo_slot++;
|
||||
s3->accel.desty_axstp = (s3->accel.desty_axstp & 0x3f00) | val;
|
||||
s3->accel.point_1_updated = 1;
|
||||
break;
|
||||
case 0xcae9:
|
||||
case 0x8949: case 0x8ae9:
|
||||
s3->accel.desty_axstp = (s3->accel.desty_axstp & 0xff) | ((val & 0x3f) << 8);
|
||||
if (val & 0x20)
|
||||
@@ -806,7 +813,7 @@ s3_accel_out_fifo(s3_t *s3, uint16_t port, uint8_t val)
|
||||
s3->accel.short_stroke = (s3->accel.short_stroke & 0xff00) | val;
|
||||
break;
|
||||
case 0x9d49: case 0x9ee9:
|
||||
s3->accel.short_stroke = (s3->accel.short_stroke & 0xff) | (val << 8);
|
||||
s3->accel.short_stroke = (s3->accel.short_stroke & 0xff) | (val << 8);
|
||||
s3->accel.ssv_state = 1;
|
||||
|
||||
s3->accel.cx = s3->accel.cur_x;
|
||||
@@ -1016,7 +1023,7 @@ s3_accel_out_fifo(s3_t *s3, uint16_t port, uint8_t val)
|
||||
s3->accel.setup_fifo_slot++;
|
||||
s3->accel.frgd_mix = val;
|
||||
break;
|
||||
|
||||
|
||||
case 0xbd48: case 0xbee8:
|
||||
s3->accel.multifunc_cntl = (s3->accel.multifunc_cntl & 0xff00) | val;
|
||||
break;
|
||||
@@ -1139,8 +1146,12 @@ s3_accel_out_fifo(s3_t *s3, uint16_t port, uint8_t val)
|
||||
s3_accel_start(8, 1, s3->accel.pix_trans[0], 0, s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, s3->accel.pix_trans[0], s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, s3->accel.pix_trans[0], s3);
|
||||
} else {
|
||||
if (s3->color_16bit)
|
||||
s3_accel_start(2, 1, 0xffffffff, s3->accel.pix_trans[0], s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, s3->accel.pix_trans[0], s3);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -1157,8 +1168,9 @@ s3_accel_out_fifo(s3_t *s3, uint16_t port, uint8_t val)
|
||||
s3_accel_start(8, 1, s3->accel.pix_trans[0] | (s3->accel.pix_trans[1] << 8), 0, s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, s3->accel.pix_trans[0] | (s3->accel.pix_trans[1] << 8), s3);
|
||||
} else
|
||||
} else {
|
||||
s3_accel_start(1, 1, 0xffffffff, s3->accel.pix_trans[0] | (s3->accel.pix_trans[1] << 8), s3);
|
||||
}
|
||||
break;
|
||||
case 0x200:
|
||||
/*Windows 95's built-in driver expects this to be loaded regardless of the byte swap bit (0xE2E9) in the 86c928*/
|
||||
@@ -1314,6 +1326,7 @@ s3_accel_out_fifo_l(s3_t *s3, uint16_t port, uint32_t val)
|
||||
} else {
|
||||
s3->accel.b2e8_pix = 0;
|
||||
}
|
||||
|
||||
s3_accel_out_pixtrans_l(s3, val);
|
||||
}
|
||||
|
||||
@@ -1468,8 +1481,26 @@ s3_accel_write_fifo(s3_t *s3, uint32_t addr, uint8_t val)
|
||||
if (addr & 0x8000) {
|
||||
s3_accel_out_fifo(s3, addr & 0xffff, val);
|
||||
} else {
|
||||
s3_accel_out_fifo(s3, 0xe2e8 + (addr & 3), val);
|
||||
}
|
||||
if (s3->accel.cmd & 0x100) {
|
||||
if ((s3->accel.cmd & 0x600) == 0x200) {
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
if (((s3->accel.frgd_mix & 0x60) != 0x40) || ((s3->accel.bkgd_mix & 0x60) != 0x40))
|
||||
s3_accel_start(16, 1, val | (val << 8) | (val << 16) | (val << 24), 0, s3);
|
||||
else
|
||||
s3_accel_start(2, 1, 0xffffffff, val | (val << 8) | (val << 16) | (val << 24), s3);
|
||||
} else
|
||||
s3_accel_start(2, 1, 0xffffffff, val | (val << 8) | (val << 16) | (val << 24), s3);
|
||||
} else {
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
if (((s3->accel.frgd_mix & 0x60) != 0x40) || ((s3->accel.bkgd_mix & 0x60) != 0x40))
|
||||
s3_accel_start(8, 1, val | (val << 8) | (val << 16) | (val << 24), 0, s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, val | (val << 8) | (val << 16) | (val << 24), s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, val | (val << 8) | (val << 16) | (val << 24), s3);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2200,11 +2231,13 @@ s3_io_remove(s3_t *s3)
|
||||
io_removehandler(0xb6e8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xbae8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xbee8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xcae8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xd2e8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xe2e8, 0x0004, s3_accel_in, s3_accel_in_w, s3_accel_in_l, s3_accel_out, s3_accel_out_w, s3_accel_out_l, s3);
|
||||
io_removehandler(0xe6e8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xeae8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xeee8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_removehandler(0xfee8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
|
||||
s3_io_remove_alt(s3);
|
||||
}
|
||||
@@ -2317,13 +2350,15 @@ s3_io_set(s3_t *s3)
|
||||
io_sethandler(0xb6e8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xbae8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xbee8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xcae8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xe2e8, 0x0004, s3_accel_in, s3_accel_in_w, s3_accel_in_l, s3_accel_out, s3_accel_out_w, s3_accel_out_l, s3);
|
||||
if (s3->chip == S3_VISION968 || s3->chip == S3_VISION868) {
|
||||
io_sethandler(0xd2e8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xe6e8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xeae8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
io_sethandler(0xeee8, 0x0004, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
}
|
||||
}
|
||||
io_sethandler(0xfee8, 0x0002, s3_accel_in, NULL, NULL, s3_accel_out, NULL, NULL, s3);
|
||||
|
||||
s3_io_set_alt(s3);
|
||||
}
|
||||
@@ -2361,13 +2396,10 @@ s3_out(uint16_t addr, uint8_t val, void *p)
|
||||
}
|
||||
if (svga->seqaddr == 4) /*Chain-4 - update banking*/
|
||||
{
|
||||
svga->chain4 = !!(val & 8);
|
||||
if (svga->crtc[0x31] & 1) {
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
}
|
||||
if (val & 0x08)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
} else if (svga->seqaddr == 9) {
|
||||
svga->seqregs[svga->seqaddr] = val & 0x80;
|
||||
s3_io_set(s3);
|
||||
@@ -2431,7 +2463,9 @@ s3_out(uint16_t addr, uint8_t val, void *p)
|
||||
return;
|
||||
if ((svga->crtcreg == 0x36) && (svga->crtc[0x39] != 0xa5))
|
||||
return;
|
||||
if ((s3->chip == S3_TRIO64V2) && svga->crtcreg >= 0x80)
|
||||
if ((s3->chip == S3_TRIO64V2) && (svga->crtcreg >= 0x80))
|
||||
return;
|
||||
if ((s3->chip <= S3_86C924) && (svga->crtcreg >= 0x50))
|
||||
return;
|
||||
old = svga->crtc[svga->crtcreg];
|
||||
svga->crtc[svga->crtcreg] = val;
|
||||
@@ -2487,12 +2521,10 @@ s3_out(uint16_t addr, uint8_t val, void *p)
|
||||
|
||||
case 0x35:
|
||||
s3->bank = (s3->bank & 0x70) | (val & 0xf);
|
||||
if (svga->crtc[0x31] & 1) {
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
}
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
break;
|
||||
|
||||
case 0x51:
|
||||
@@ -2503,23 +2535,19 @@ s3_out(uint16_t addr, uint8_t val, void *p)
|
||||
s3->bank = (s3->bank & 0x4f) | ((val & 0xc) << 2);
|
||||
s3->ma_ext = (s3->ma_ext & ~0xc) | ((val & 3) << 2);
|
||||
}
|
||||
if (svga->crtc[0x31] & 1) {
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
}
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
break;
|
||||
|
||||
case 0x6a:
|
||||
if (s3->chip >= S3_VISION964) {
|
||||
s3->bank = val;
|
||||
if (svga->crtc[0x31] & 1) {
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
}
|
||||
if (svga->chain4)
|
||||
svga->write_bank = svga->read_bank = s3->bank << 16;
|
||||
else
|
||||
svga->write_bank = svga->read_bank = s3->bank << 14;
|
||||
}
|
||||
break;
|
||||
|
||||
@@ -2774,6 +2802,7 @@ static void s3_recalctimings(svga_t *svga)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
svga->ma_latch |= (s3->ma_ext << 16);
|
||||
|
||||
if (s3->chip >= S3_86C928) {
|
||||
@@ -2832,8 +2861,18 @@ static void s3_recalctimings(svga_t *svga)
|
||||
}
|
||||
}
|
||||
|
||||
if ((svga->crtc[0x43] & 0x08) && (s3->bpp == 0))
|
||||
if ((svga->crtc[0x43] & 0x08) && (s3->color_16bit == 0) && (s3->chip <= S3_86C805)) {
|
||||
s3->color_16bit = 1;
|
||||
s3->width = 1024;
|
||||
} else if (!(svga->crtc[0x43] & 0x08) && (s3->color_16bit == 1) && (s3->chip <= S3_86C805)) {
|
||||
s3->color_16bit = 0;
|
||||
if (s3->chip <= S3_86C924) {
|
||||
if (s3->accel.advfunc_cntl & 4)
|
||||
s3->width = 1024;
|
||||
else
|
||||
s3->width = 640;
|
||||
}
|
||||
}
|
||||
|
||||
if ((svga->gdcreg[5] & 0x40) && (svga->crtc[0x3a] & 0x10)) {
|
||||
svga->fb_only = 1;
|
||||
@@ -3004,35 +3043,17 @@ static void s3_recalctimings(svga_t *svga)
|
||||
}
|
||||
} else {
|
||||
svga->fb_only = 0;
|
||||
if (!svga->scrblank && svga->attr_palette_enable) {
|
||||
if (!(svga->gdcreg[6] & 1) && !(svga->attrregs[0x10] & 1)) { /*Text mode*/
|
||||
if (svga->seqregs[1] & 8) /*40 column*/ {
|
||||
svga->render = svga_render_text_40;
|
||||
} else {
|
||||
svga->render = svga_render_text_80;
|
||||
}
|
||||
} else {
|
||||
if ((svga->crtc[0x31] & 0x08) && ((svga->gdcreg[5] & 0x60) == 0x00)) {
|
||||
if ((svga->gdcreg[6] & 1) || (svga->attrregs[0x10] & 1)) {
|
||||
if ((svga->crtc[0x31] & 0x08) && ((svga->gdcreg[5] & 0x60) == 0x00)) {
|
||||
if (svga->bpp == 8) {
|
||||
svga->render = svga_render_8bpp_highres; /*Enhanced 4bpp mode, just like the 8bpp mode per spec.*/
|
||||
if (svga->hdisp <= 1024)
|
||||
s3->width = 1024;
|
||||
} else {
|
||||
switch (svga->gdcreg[5] & 0x60) {
|
||||
case 0x00:
|
||||
if (svga->seqregs[1] & 8) /*Low res (320)*/
|
||||
svga->render = svga_render_4bpp_lowres;
|
||||
else
|
||||
svga->render = svga_render_4bpp_highres;
|
||||
break;
|
||||
case 0x20: /*4 colours*/
|
||||
if (svga->seqregs[1] & 8) /*Low res (320)*/
|
||||
svga->render = svga_render_2bpp_lowres;
|
||||
else
|
||||
svga->render = svga_render_2bpp_highres;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (s3->chip <= S3_86C924)
|
||||
s3->width = 1024;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3093,7 +3114,9 @@ static void s3_trio64v_recalctimings(svga_t *svga)
|
||||
if (!svga->rowoffset) svga->rowoffset = 256;
|
||||
|
||||
svga->lowres = !((svga->gdcreg[5] & 0x40) && (svga->crtc[0x3a] & 0x10));
|
||||
|
||||
if ((svga->gdcreg[5] & 0x40) && (svga->crtc[0x3a] & 0x10)) {
|
||||
svga->fb_only = 1;
|
||||
switch (svga->bpp) {
|
||||
case 8:
|
||||
svga->render = svga_render_8bpp_highres;
|
||||
@@ -3114,10 +3137,13 @@ static void s3_trio64v_recalctimings(svga_t *svga)
|
||||
svga->render = svga_render_32bpp_highres;
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else
|
||||
svga->fb_only = 0;
|
||||
}
|
||||
else /*Streams mode*/
|
||||
{
|
||||
svga->fb_only = 1;
|
||||
|
||||
if (s3->streams.buffer_ctrl & 1)
|
||||
svga->ma_latch = s3->streams.pri_fb1 >> 2;
|
||||
else
|
||||
@@ -3203,7 +3229,7 @@ s3_updatemapping(s3_t *s3)
|
||||
svga->banked_mask = 0x7fff;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
if (s3->chip >= S3_86C928) {
|
||||
s3->linear_base = (svga->crtc[0x5a] << 16) | (svga->crtc[0x59] << 24);
|
||||
|
||||
@@ -3260,12 +3286,8 @@ s3_updatemapping(s3_t *s3)
|
||||
|
||||
mem_mapping_set_addr(&s3->linear_mapping, s3->linear_base, s3->linear_size);
|
||||
}
|
||||
if (s3->chip >= S3_TRIO64V)
|
||||
svga->fb_only = 1;
|
||||
} else {
|
||||
mem_mapping_disable(&s3->linear_mapping);
|
||||
if (s3->chip >= S3_TRIO64V)
|
||||
svga->fb_only = 0;
|
||||
}
|
||||
|
||||
/* Memory mapped I/O. */
|
||||
@@ -3279,9 +3301,10 @@ s3_updatemapping(s3_t *s3)
|
||||
} else {
|
||||
mem_mapping_enable(&s3->mmio_mapping);
|
||||
}
|
||||
} else
|
||||
} else {
|
||||
mem_mapping_disable(&s3->mmio_mapping);
|
||||
|
||||
}
|
||||
|
||||
/* New MMIO. */
|
||||
if (svga->crtc[0x53] & 0x08)
|
||||
mem_mapping_set_addr(&s3->new_mmio_mapping, s3->linear_base + 0x1000000, 0x20000);
|
||||
@@ -3312,12 +3335,12 @@ s3_accel_out(uint16_t port, uint8_t val, void *p)
|
||||
s3_t *s3 = (s3_t *)p;
|
||||
svga_t *svga = &s3->svga;
|
||||
|
||||
if (!s3->enable_8514)
|
||||
return;
|
||||
if (port >= 0x8000) {
|
||||
if (!s3->enable_8514)
|
||||
return;
|
||||
|
||||
if (port >= 0x8000)
|
||||
s3_accel_out_fifo(s3, port, val);
|
||||
else {
|
||||
} else {
|
||||
switch (port)
|
||||
{
|
||||
case 0x4148: case 0x42e8:
|
||||
@@ -3337,8 +3360,12 @@ s3_accel_out(uint16_t port, uint8_t val, void *p)
|
||||
s3->width = (val & 4) ? 1600 : 800;
|
||||
svga->fullchange = changeframecount;
|
||||
svga_recalctimings(svga);
|
||||
} else if (s3->chip <= S3_86C805) {
|
||||
svga->fullchange = changeframecount;
|
||||
svga_recalctimings(svga);
|
||||
}
|
||||
s3_updatemapping(s3);
|
||||
if (s3->chip > S3_86C924)
|
||||
s3_updatemapping(s3);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -3802,21 +3829,28 @@ s3_accel_in_w(uint16_t port, void *p)
|
||||
if (s3->accel.cmd & 0x1000)
|
||||
temp = (temp >> 8) | (temp << 8);
|
||||
s3_accel_start(8, 1, temp | (temp << 16), 0, s3);
|
||||
} else
|
||||
} else {
|
||||
s3_accel_start(1, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
}
|
||||
} else {
|
||||
if (s3->color_16bit) {
|
||||
s3_accel_start(2, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
} else {
|
||||
s3_accel_start(1, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0x200:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
if (((s3->accel.frgd_mix & 0x60) != 0x40) || ((s3->accel.bkgd_mix & 0x60) != 0x40)) {
|
||||
if (s3->accel.cmd & 0x1000)
|
||||
temp = (temp >> 8) | (temp << 8);
|
||||
temp = (temp >> 8) | (temp << 8);
|
||||
s3_accel_start(16, 1, temp | (temp << 16), 0, s3);
|
||||
} else
|
||||
s3_accel_start(2, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
} else
|
||||
} else {
|
||||
s3_accel_start(2, 1, 0xffffffff, temp | (temp << 16), s3);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -3965,7 +3999,28 @@ s3_accel_read(uint32_t addr, void *p)
|
||||
if (addr & 0x8000) {
|
||||
temp = s3_accel_in(addr & 0xffff, p);
|
||||
} else if (s3_cpu_dest(s3)) {
|
||||
temp = s3_accel_in(0xe2e8 + (addr & 3), p);
|
||||
READ_PIXTRANS_BYTE_MM
|
||||
|
||||
switch (s3->accel.cmd & 0x600) {
|
||||
case 0x000:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
if (((s3->accel.frgd_mix & 0x60) != 0x40) || ((s3->accel.bkgd_mix & 0x60) != 0x40))
|
||||
s3_accel_start(8, 1, temp | (temp << 8) | (temp << 16) | (temp << 24), 0, s3);
|
||||
else
|
||||
s3_accel_start(1, 1, 0xffffffff, temp | (temp << 8) | (temp << 16) | (temp << 24), s3);
|
||||
} else
|
||||
s3_accel_start(1, 1, 0xffffffff, temp | (temp << 8) | (temp << 16) | (temp << 24), s3);
|
||||
break;
|
||||
case 0x200:
|
||||
if (((s3->accel.multifunc[0xa] & 0xc0) == 0x80) || (s3->accel.cmd & 2)) {
|
||||
if (((s3->accel.frgd_mix & 0x60) != 0x40) || ((s3->accel.bkgd_mix & 0x60) != 0x40))
|
||||
s3_accel_start(16, 1, temp | (temp << 8) | (temp << 16) | (temp << 24), 0, s3);
|
||||
else
|
||||
s3_accel_start(2, 1, 0xffffffff, temp | (temp << 8) | (temp << 16) | (temp << 24), s3);
|
||||
} else
|
||||
s3_accel_start(2, 1, 0xffffffff, temp | (temp << 8) | (temp << 16) | (temp << 24), s3);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4240,8 +4295,8 @@ polygon_setup(s3_t *s3)
|
||||
}
|
||||
}
|
||||
|
||||
#define READ(addr, dat) if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) dat = svga->vram[dword_remap(svga, addr) & s3->vram_mask]; \
|
||||
else if (s3->bpp == 1 || (svga->crtc[0x43] & 0x08)) dat = vram_w[dword_remap_w(svga, addr) & (s3->vram_mask >> 1)]; \
|
||||
#define READ(addr, dat) if (s3->bpp == 0 && !s3->color_16bit) dat = svga->vram[dword_remap(svga, addr) & s3->vram_mask]; \
|
||||
else if (s3->bpp == 1 || s3->color_16bit) dat = vram_w[dword_remap_w(svga, addr) & (s3->vram_mask >> 1)]; \
|
||||
else if (s3->bpp == 2) dat = svga->vram[dword_remap(svga, addr) & s3->vram_mask]; \
|
||||
else dat = vram_l[dword_remap_l(svga, addr) & (s3->vram_mask >> 2)];
|
||||
|
||||
@@ -4546,12 +4601,12 @@ polygon_setup(s3_t *s3)
|
||||
}
|
||||
|
||||
|
||||
#define WRITE(addr, dat) if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) \
|
||||
#define WRITE(addr, dat) if (s3->bpp == 0 && !s3->color_16bit) \
|
||||
{ \
|
||||
svga->vram[dword_remap(svga, addr) & s3->vram_mask] = dat; \
|
||||
svga->vram[dword_remap(svga, addr) & s3->vram_mask] = dat; \
|
||||
svga->changedvram[(dword_remap(svga, addr) & s3->vram_mask) >> 12] = changeframecount; \
|
||||
} \
|
||||
else if (s3->bpp == 1 || (svga->crtc[0x43] & 0x08)) \
|
||||
else if (s3->bpp == 1 || s3->color_16bit) \
|
||||
{ \
|
||||
vram_w[dword_remap_w(svga, addr) & (s3->vram_mask >> 1)] = dat; \
|
||||
svga->changedvram[(dword_remap_w(svga, addr) & (s3->vram_mask >> 1)) >> 11] = changeframecount; \
|
||||
@@ -5062,33 +5117,33 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
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 || (svga->crtc[0x43] & 0x08)) {
|
||||
srcbase >>= 1;
|
||||
dstbase >>= 1;
|
||||
} else if (s3->bpp == 3) {
|
||||
srcbase >>= 2;
|
||||
dstbase >>= 2;
|
||||
}
|
||||
// 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->accel.cmd & 0x100) && ((s3_cpu_src(s3) || (s3_cpu_dest(s3))) && !cpu_input)) {
|
||||
if ((s3->accel.cmd & 0x100) && ((s3_cpu_src(s3) || (s3_cpu_dest(s3)))) && (!cpu_input || (s3_enable_fifo(s3) == 0))) {
|
||||
s3->force_busy = 1;
|
||||
}
|
||||
|
||||
if (!cpu_input)
|
||||
s3->accel.dat_count = 0;
|
||||
|
||||
if (cpu_input && (count <= 4)) {
|
||||
if (cpu_input && (((s3->accel.multifunc[0xa] & 0xc0) != 0x80) || (!(s3->accel.cmd & 2)))) {
|
||||
if ((s3->bpp == 3) && count == 2) {
|
||||
if (s3->accel.dat_count) {
|
||||
cpu_dat = ((cpu_dat & 0xffff) << 16) | s3->accel.dat_buf;
|
||||
@@ -5099,19 +5154,19 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
s3->accel.dat_count = 1;
|
||||
}
|
||||
}
|
||||
if (s3->bpp == 1 || (svga->crtc[0x43] & 0x08))
|
||||
if (s3->bpp == 1 || s3->color_16bit)
|
||||
count >>= 1;
|
||||
if (s3->bpp == 3)
|
||||
count >>= 2;
|
||||
}
|
||||
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08))
|
||||
if (s3->bpp == 0 && !s3->color_16bit)
|
||||
rd_mask &= 0xff;
|
||||
else if (s3->bpp == 1 || (svga->crtc[0x43] & 0x08))
|
||||
else if (s3->bpp == 1 || s3->color_16bit)
|
||||
rd_mask &= 0xffff;
|
||||
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) compare &= 0xff;
|
||||
if (s3->bpp == 1 || (svga->crtc[0x43] & 0x08)) compare &= 0xffff;
|
||||
if (s3->bpp == 0 && !s3->color_16bit) compare &= 0xff;
|
||||
if (s3->bpp == 1 || s3->color_16bit) compare &= 0xffff;
|
||||
|
||||
switch (s3->accel.cmd & 0x600)
|
||||
{
|
||||
@@ -5124,6 +5179,7 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
/*Bit 4 of the Command register is the draw yes bit, which enables writing to memory/reading from memory when enabled.
|
||||
When this bit is disabled, no writing to memory/reading from memory is allowed. (This bit is almost meaningless on
|
||||
the NOP command)*/
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
case 0: /*NOP (Short Stroke Vectors)*/
|
||||
@@ -5164,7 +5220,7 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
|
||||
mix_dat <<= 1;
|
||||
mix_dat |= 1;
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) cpu_dat >>= 8;
|
||||
if (s3->bpp == 0) cpu_dat >>= 8;
|
||||
else cpu_dat >>= 16;
|
||||
if (!s3->accel.ssv_len)
|
||||
break;
|
||||
@@ -5197,14 +5253,13 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
if (s3->accel.cur_y_bit12) s3->accel.cy |= ~0xfff;
|
||||
|
||||
s3->accel.sy = s3->accel.maj_axis_pcnt;
|
||||
|
||||
|
||||
s3_fifo_slots(s3);
|
||||
|
||||
|
||||
if (s3_cpu_src(s3)) {
|
||||
return; /*Wait for data from CPU*/
|
||||
}
|
||||
}
|
||||
|
||||
frgd_mix = (s3->accel.frgd_mix >> 5) & 3;
|
||||
bkgd_mix = (s3->accel.bkgd_mix >> 5) & 3;
|
||||
|
||||
@@ -5223,24 +5278,26 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
case 3: src_dat = 0; break;
|
||||
}
|
||||
|
||||
if (((compare_mode == 2 && src_dat != compare) ||
|
||||
if ((compare_mode == 2 && src_dat != compare) ||
|
||||
(compare_mode == 3 && src_dat == compare) ||
|
||||
compare_mode < 2))
|
||||
compare_mode < 2)
|
||||
{
|
||||
READ((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
|
||||
|
||||
MIX
|
||||
|
||||
if (s3->accel.cmd & 0x10) {
|
||||
WRITE((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
}
|
||||
WRITE((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
}
|
||||
}
|
||||
|
||||
mix_dat <<= 1;
|
||||
mix_dat |= 1;
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) cpu_dat >>= 8;
|
||||
else cpu_dat >>= 16;
|
||||
if (s3->bpp == 0 && !s3->color_16bit)
|
||||
cpu_dat >>= 8;
|
||||
else {
|
||||
cpu_dat >>= 16;
|
||||
}
|
||||
|
||||
if (!s3->accel.sy) {
|
||||
break;
|
||||
}
|
||||
@@ -5256,7 +5313,6 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
case 0xc0: s3->accel.cy++; break;
|
||||
case 0xe0: s3->accel.cx++; s3->accel.cy++; break;
|
||||
}
|
||||
|
||||
s3->accel.sy--;
|
||||
}
|
||||
s3->accel.cur_x = s3->accel.cx;
|
||||
@@ -5287,17 +5343,15 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
case 3: src_dat = 0; break;
|
||||
}
|
||||
|
||||
if (((compare_mode == 2 && src_dat != compare) ||
|
||||
if ((compare_mode == 2 && src_dat != compare) ||
|
||||
(compare_mode == 3 && src_dat == compare) ||
|
||||
compare_mode < 2))
|
||||
compare_mode < 2)
|
||||
{
|
||||
READ((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
|
||||
MIX
|
||||
|
||||
if (s3->accel.cmd & 0x10) {
|
||||
WRITE((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
}
|
||||
WRITE((s3->accel.cy * s3->width) + s3->accel.cx, dest_dat);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5311,13 +5365,16 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
mix_dat <<= 1;
|
||||
mix_dat |= 1;
|
||||
}
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) cpu_dat >>= 8;
|
||||
else cpu_dat >>= 16;
|
||||
if (s3->bpp == 0 && !s3->color_16bit)
|
||||
cpu_dat >>= 8;
|
||||
else {
|
||||
cpu_dat >>= 16;
|
||||
}
|
||||
|
||||
if (!s3->accel.sy) {
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
if (s3->accel.err_term >= s3->accel.maj_axis_pcnt) {
|
||||
s3->accel.err_term += s3->accel.destx_distp;
|
||||
/*Step minor axis*/
|
||||
@@ -5348,7 +5405,6 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
case 0xc0: s3->accel.cy++; break;
|
||||
case 0xe0: s3->accel.cy++; break;
|
||||
}
|
||||
|
||||
s3->accel.sy--;
|
||||
}
|
||||
s3->accel.cur_x = s3->accel.cx;
|
||||
@@ -5456,10 +5512,11 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
mix_dat |= 1;
|
||||
}
|
||||
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08))
|
||||
if (s3->bpp == 0 && !s3->color_16bit)
|
||||
cpu_dat >>= 8;
|
||||
else
|
||||
else {
|
||||
cpu_dat >>= 16;
|
||||
}
|
||||
|
||||
if (s3->accel.cmd & 0x20)
|
||||
s3->accel.cx++;
|
||||
@@ -5486,7 +5543,7 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
if (cpu_input) {
|
||||
if (s3->accel.b2e8_pix) {
|
||||
s3->accel.cur_x = s3->accel.cx;
|
||||
s3->accel.cur_y = s3->accel.cy;
|
||||
s3->accel.cur_y = s3->accel.cy;
|
||||
}
|
||||
return;
|
||||
}
|
||||
@@ -5718,8 +5775,11 @@ s3_accel_start(int count, int cpu_input, uint32_t mix_dat, uint32_t cpu_dat, s3_
|
||||
mix_dat <<= 1;
|
||||
mix_dat |= 1;
|
||||
|
||||
if (s3->bpp == 0 && !(svga->crtc[0x43] & 0x08)) cpu_dat >>= 8;
|
||||
else cpu_dat >>= 16;
|
||||
if (s3->bpp == 0 && !s3->color_16bit)
|
||||
cpu_dat >>= 8;
|
||||
else {
|
||||
cpu_dat >>= 16;
|
||||
}
|
||||
|
||||
if (s3->accel.cmd & 0x20)
|
||||
{
|
||||
@@ -6408,7 +6468,6 @@ static int vram_sizes[] =
|
||||
3 /*8 MB*/
|
||||
};
|
||||
|
||||
|
||||
static void s3_reset(void *priv)
|
||||
{
|
||||
s3_t *s3 = (s3_t *) priv;
|
||||
@@ -6427,14 +6486,14 @@ static void s3_reset(void *priv)
|
||||
svga->crtc[0x36] = 1 | (3 << 2) | (1 << 4);
|
||||
else
|
||||
svga->crtc[0x36] = 3 | (1 << 4);
|
||||
|
||||
|
||||
if (s3->chip >= S3_86C928)
|
||||
svga->crtc[0x36] |= (vram_sizes[s3->vram] << 5);
|
||||
else
|
||||
svga->crtc[0x36] |= ((s3->vram == 1) ? 0x00 : 0x20) | 0x80;
|
||||
|
||||
|
||||
svga->crtc[0x37] = 1 | (7 << 5);
|
||||
|
||||
|
||||
if (s3->chip >= S3_86C928)
|
||||
svga->crtc[0x37] |= 0x04;
|
||||
|
||||
@@ -6464,11 +6523,11 @@ static void s3_reset(void *priv)
|
||||
case S3_PHOENIX_86C805:
|
||||
svga->crtc[0x5a] = 0x0a;
|
||||
break;
|
||||
|
||||
|
||||
case S3_METHEUS_86C928:
|
||||
svga->crtc[0x5a] = 0x0a;
|
||||
break;
|
||||
|
||||
|
||||
case S3_PARADISE_BAHAMAS64:
|
||||
case S3_PHOENIX_VISION864:
|
||||
case S3_MIROCRYSTAL20SD_864:
|
||||
@@ -6886,8 +6945,10 @@ static void *s3_init(const device_t *info)
|
||||
|
||||
if (chip >= S3_86C928)
|
||||
svga->crtc[0x36] |= (vram_sizes[vram] << 5);
|
||||
else
|
||||
svga->crtc[0x36] |= ((vram == 1) ? 0x00 : 0x20) | 0x80;
|
||||
else {
|
||||
svga->crtc[0x36] |= ((vram == 1) ? 0x00 : 0x20) | 0x98;
|
||||
svga->crtc[0x41] = (vram == 1) ? 0x10 : 0x00;
|
||||
}
|
||||
|
||||
svga->crtc[0x37] = 1 | (7 << 5);
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
*
|
||||
* This file is part of the 86Box distribution.
|
||||
*
|
||||
* Emulation of Sierra SC11483 and SC11487 RAMDACs.
|
||||
* Emulation of Sierra SC1148x RAMDACs and clones (e.g.: Winbond).
|
||||
*
|
||||
* Used by the S3 911 and 924 chips.
|
||||
*
|
||||
@@ -43,24 +43,45 @@ sc1148x_ramdac_out(uint16_t addr, int rs2, uint8_t val, void *p, svga_t *svga)
|
||||
{
|
||||
sc1148x_ramdac_t *ramdac = (sc1148x_ramdac_t *) p;
|
||||
uint8_t rs = (addr & 0x03);
|
||||
rs |= ((!!rs2) << 2);
|
||||
rs |= ((!!rs2) << 2);
|
||||
int oldbpp = 0;
|
||||
|
||||
switch (addr) {
|
||||
case 0x3c6:
|
||||
if (ramdac->state == 4) {
|
||||
ramdac->state = 0;
|
||||
ramdac->ctrl = val;
|
||||
if (ramdac->ctrl & 0xa0) {
|
||||
if ((ramdac->ctrl & 0x40) && (ramdac->type == 1))
|
||||
svga->bpp = 16;
|
||||
else
|
||||
svga->bpp = 15;
|
||||
} else
|
||||
svga->bpp = 8;
|
||||
svga_recalctimings(svga);
|
||||
return;
|
||||
switch (ramdac->state) {
|
||||
case 4:
|
||||
ramdac->state = 0;
|
||||
if (val == 0xff)
|
||||
break;
|
||||
ramdac->ctrl = val;
|
||||
ramdac->ctrl = (ramdac->ctrl & ~1) | ((((val >> 2) ^ val) & (val & 0x20)) >> 5);
|
||||
oldbpp = svga->bpp;
|
||||
switch (ramdac->type) {
|
||||
case 0: /* Sierra Mark 2 (11483)*/
|
||||
case 2: /* Sierra Mark 2 (11484)*/
|
||||
case 3: /* Sierra Mark 1 (11486)*/
|
||||
if (val & 0xa0) {
|
||||
svga->bpp = 15;
|
||||
} else if (val == 0x00)
|
||||
svga->bpp = 8;
|
||||
break;
|
||||
case 1: /* Sierra Mark 3 (11487)*/
|
||||
if (val & 0xa0) {
|
||||
if (val & 0x40)
|
||||
svga->bpp = 16;
|
||||
else
|
||||
svga->bpp = 15;
|
||||
} else if (val == 0x00)
|
||||
svga->bpp = 8;
|
||||
break;
|
||||
}
|
||||
if (oldbpp != svga->bpp)
|
||||
svga_recalctimings(svga);
|
||||
return;
|
||||
default:
|
||||
svga_out(addr, val, svga);
|
||||
break;
|
||||
}
|
||||
ramdac->state = 0;
|
||||
break;
|
||||
|
||||
case 0x3c7: case 0x3c8:
|
||||
@@ -82,18 +103,21 @@ sc1148x_ramdac_in(uint16_t addr, int rs2, void *p, svga_t *svga)
|
||||
|
||||
switch (addr) {
|
||||
case 0x3c6:
|
||||
if (ramdac->state == 4) {
|
||||
ramdac->state = 0;
|
||||
ret = ramdac->ctrl;
|
||||
if (ramdac->type == 1) {
|
||||
if (((ramdac->ctrl >> 5) == 1) || ((ramdac->ctrl >> 5) == 3))
|
||||
ret |= 1;
|
||||
else
|
||||
ret &= ~1;
|
||||
}
|
||||
return ret;
|
||||
switch (ramdac->state) {
|
||||
case 1:
|
||||
case 2: case 3:
|
||||
ret = 0x00;
|
||||
ramdac->state++;
|
||||
break;
|
||||
case 4:
|
||||
ret = ramdac->ctrl;
|
||||
ret = (ret & ~0x18) | (svga->dac_mask & 0x18);
|
||||
break;
|
||||
default:
|
||||
ret = svga_in(addr, svga);
|
||||
ramdac->state++;
|
||||
break;
|
||||
}
|
||||
ramdac->state++;
|
||||
break;
|
||||
|
||||
case 0x3c7: case 0x3c8:
|
||||
@@ -150,4 +174,12 @@ const device_t sc11484_nors2_ramdac_device =
|
||||
0, 2,
|
||||
sc1148x_ramdac_init, sc1148x_ramdac_close,
|
||||
NULL, { NULL }, NULL, NULL
|
||||
};
|
||||
|
||||
const device_t sc11486_ramdac_device =
|
||||
{
|
||||
"Sierra SC11486 RAMDAC",
|
||||
0, 3,
|
||||
sc1148x_ramdac_init, sc1148x_ramdac_close,
|
||||
NULL, { NULL }, NULL, NULL
|
||||
};
|
||||
@@ -1060,7 +1060,7 @@ svga_init(const device_t *info, svga_t *svga, void *p, int memsize,
|
||||
svga->translate_address = NULL;
|
||||
svga->ksc5601_english_font_type = 0;
|
||||
|
||||
if ((info->flags & DEVICE_PCI) || (info->flags & DEVICE_VLB)) {
|
||||
if ((info->flags & DEVICE_PCI) || (info->flags & DEVICE_VLB) || (info->flags & DEVICE_MCA)) {
|
||||
mem_mapping_add(&svga->mapping, 0xa0000, 0x20000,
|
||||
svga_read, svga_readw, svga_readl,
|
||||
svga_write, svga_writew, svga_writel,
|
||||
|
||||
@@ -58,12 +58,13 @@ video_cards[] = {
|
||||
{ "ati28800k", &ati28800k_device },
|
||||
{ "ati18800v", &ati18800_vga88_device },
|
||||
{ "ati28800", &ati28800_device },
|
||||
{ "compaq_ati28800", &compaq_ati28800_device },
|
||||
#if defined(DEV_BRANCH) && defined(USE_XL24)
|
||||
{ "ati28800w", &ati28800_wonderxl24_device },
|
||||
#endif
|
||||
{ "ati18800", &ati18800_device },
|
||||
#if defined(DEV_BRANCH) && defined(USE_VGAWONDER)
|
||||
{ "ati18800w", &ati18800_wonder_device },
|
||||
#endif
|
||||
#if defined(DEV_BRANCH) && defined(USE_XL24)
|
||||
{ "ati28800w", &ati28800_wonderxl24_device },
|
||||
#endif
|
||||
{ "cga", &cga_device },
|
||||
{ "superega", &sega_device },
|
||||
@@ -74,7 +75,6 @@ video_cards[] = {
|
||||
{ "cl_gd5428_isa", &gd5428_isa_device },
|
||||
{ "cl_gd5429_isa", &gd5429_isa_device },
|
||||
{ "cl_gd5434_isa", &gd5434_isa_device },
|
||||
{ "compaq_ati28800", &compaq_ati28800_device },
|
||||
{ "compaq_cga", &compaq_cga_device },
|
||||
{ "compaq_cga_2", &compaq_cga_2_device },
|
||||
{ "compaq_ega", &cpqega_device },
|
||||
|
||||
@@ -1382,12 +1382,15 @@ win_settings_sound_proc(HWND hdlg, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
settings_set_check(hdlg, IDC_CHECK_MPU401, temp_mpu401);
|
||||
settings_enable_window(hdlg, IDC_CHECK_MPU401, mpu401_standalone_allow());
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_MPU401, mpu401_standalone_allow() && temp_mpu401);
|
||||
settings_enable_window(hdlg, IDC_CHECK_CMS, (machines[temp_machine].flags & MACHINE_BUS_ISA));
|
||||
settings_set_check(hdlg, IDC_CHECK_CMS, temp_GAMEBLASTER);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_CMS, temp_GAMEBLASTER);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_CMS, (machines[temp_machine].flags & MACHINE_BUS_ISA) && temp_GAMEBLASTER);
|
||||
settings_enable_window(hdlg, IDC_CHECK_GUS, (machines[temp_machine].flags & MACHINE_BUS_ISA16));
|
||||
settings_set_check(hdlg, IDC_CHECK_GUS, temp_GUS);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_GUS, temp_GUS);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_GUS, (machines[temp_machine].flags & MACHINE_BUS_ISA16) && temp_GUS);
|
||||
settings_enable_window(hdlg, IDC_CHECK_SSI, (machines[temp_machine].flags & MACHINE_BUS_ISA));
|
||||
settings_set_check(hdlg, IDC_CHECK_SSI, temp_SSI2001);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_SSI, temp_SSI2001);
|
||||
settings_enable_window(hdlg, IDC_CONFIGURE_SSI, (machines[temp_machine].flags & MACHINE_BUS_ISA) && temp_SSI2001);
|
||||
settings_set_check(hdlg, IDC_CHECK_FLOAT, temp_float);
|
||||
|
||||
free(lptsTemp);
|
||||
|
||||
Reference in New Issue
Block a user