Modifications qui seront validées :

modifié :         devices/video/vid_cl54xx.c
	modifié :         devices/video/vid_svga_render.c
	modifié :         devices/video/vid_svga_render.h
	modifié :         devices/video/video.h
	modifié :         devices/video/video_dev.c
This commit is contained in:
Altheos
2018-10-22 14:16:17 +02:00
parent 7a2ea3560a
commit 283120c692
5 changed files with 238 additions and 16 deletions

View File

@@ -58,6 +58,7 @@
#include "vid_svga_render.h"
#define BIOS_GD5422_PATH L"video/cirruslogic/1-cl5422.bin"
#define BIOS_GD5426_PATH L"video/cirruslogic/diamond speedstar pro vlb v3.04.bin"
#define BIOS_GD5428_ISA_PATH L"video/cirruslogic/gd5428.bin"
#define BIOS_GD5428_VLB_PATH L"video/cirruslogic/vlbusjapan.bin"
@@ -72,6 +73,9 @@
#define BIOS_GD5480_PATH L"video/cirruslogic/gd5480.rom"
#define CIRRUS_ID_CLGD5420 0x88
#define CIRRUS_ID_CLGD5422 0x8c
#define CIRRUS_ID_CLGD5424 0x94
#define CIRRUS_ID_CLGD5426 0x90
#define CIRRUS_ID_CLGD5428 0x98
#define CIRRUS_ID_CLGD5429 0x9c
@@ -192,6 +196,9 @@ typedef struct gd54xx_t
uint8_t pci_regs[256];
uint8_t int_line;
uint8_t fc; /*Feature Connector */
uint8_t clgd_latch[8];
int card;
uint32_t lfb_base;
@@ -245,16 +252,17 @@ gd54xx_out(uint16_t addr, uint8_t val, void *p)
case 0x3c0:
case 0x3c1:
if (!svga->attrff) {
svga->attraddr = val & 31;
svga->attraddr = val & 0x3f;
if ((val & 0x20) != svga->attr_palette_enable) {
svga->fullchange = 3;
svga->attr_palette_enable = val & 0x20;
svga_recalctimings(svga);
}
} else {
o = svga->attrregs[svga->attraddr & 31];
svga->attrregs[svga->attraddr & 31] = val;
if (svga->attraddr < 16)
o = svga->attrregs[svga->attraddr & 0x3f];
if ((svga->attraddr < 0x20) || (svga->attraddr >= 0x30))
svga->attrregs[svga->attraddr & 0x3f] = val;
if (svga->attraddr < 0x10)
svga->fullchange = changeframecount;
if (svga->attraddr == 0x10 || svga->attraddr == 0x14 || svga->attraddr < 0x10) {
for (c = 0; c < 16; c++) {
@@ -287,12 +295,39 @@ gd54xx_out(uint16_t addr, uint8_t val, void *p)
o = svga->seqregs[svga->seqaddr & 0x1f];
svga->seqregs[svga->seqaddr & 0x1f] = val;
switch (svga->seqaddr & 0x1f) {
case 6:
case 0x06:
val &= 0x17;
if (val == 0x12)
svga->seqregs[6] = 0x12;
else
svga->seqregs[6] = 0x0f;
case 0x08: // Todo EEPROM
break;
case 0x0a:
if (gd54xx_is_5434(svga))
{
svga->seqregs[0x0a] = val;
}
else { /* Hack to force memory size on some GD-542x BIOSes*/
val &= 0xe7;
switch (gd54xx->vram_size)
{
case 0x80000:
svga->seqregs[0x0a] = val | 0x08;
break;
case 0x100000:
svga->seqregs[0x0a] = val | 0x10;
break;
case 0x200000:
svga->seqregs[0x0a] = val | 0x18;
break;
}
}
break;
case 0x0b: case 0x0c: case 0x0d: case 0x0e: /* VCLK stuff */
gd54xx->vclk_n[svga->seqaddr-0x0b] = val;
@@ -319,16 +354,39 @@ gd54xx_out(uint16_t addr, uint8_t val, void *p)
svga->hwcursor.xsize = svga->hwcursor.ysize = (val & CIRRUS_CURSOR_LARGE) ? 64 : 32;
svga->hwcursor.yoff = (svga->hwcursor.ysize == 32) ? 32 : 0;
if (val & CIRRUS_CURSOR_LARGE)
svga->hwcursor.addr = (((gd54xx->vram_size<<20)-0x4000) + ((svga->seqregs[0x13] & 0x3c) * 256));
svga->hwcursor.addr = (((svga->vram_display_mask + 1)-0x4000) + ((svga->seqregs[0x13] & 0x3c) * 256));
else
svga->hwcursor.addr = (((gd54xx->vram_size<<20)-0x4000) + ((svga->seqregs[0x13] & 0x3f) * 256));
svga->hwcursor.addr = (((svga->vram_display_mask + 1)-0x4000) + ((svga->seqregs[0x13] & 0x3f) * 256));
break;
case 0x13:
if (svga->seqregs[0x12] & CIRRUS_CURSOR_LARGE)
svga->hwcursor.addr = (((gd54xx->vram_size<<20)-0x4000) + ((val & 0x3c) * 256));
svga->hwcursor.addr = (((svga->vram_display_mask + 1)-0x4000) + ((val & 0x3c) * 256));
else
svga->hwcursor.addr = (((gd54xx->vram_size<<20)-0x4000) + ((val & 0x3f) * 256));
svga->hwcursor.addr = (((svga->vram_display_mask + 1)-0x4000) + ((val & 0x3f) * 256));
break;
case 0x15:
if (gd54xx_is_5434(svga))
{
/* Hack to force memory size on some GD-543x BIOSes*/
val &= 0xf8;
switch (gd54xx->vram_size)
{
case 0x100000:
svga->seqregs[0x15] = val | 0x2;
break;
case 0x200000:
svga->seqregs[0x15] = val | 0x3;
break;
case 0x400000:
svga->seqregs[0x15] = val | 0x4;
break;
}
}
else
return;
break;
case 0x07:
svga->set_reset_disabled = svga->seqregs[7] & 1;
case 0x17:
@@ -384,6 +442,9 @@ gd54xx_out(uint16_t addr, uint8_t val, void *p)
break;
}
return;
case 0x3ba: case 0x3da:
gd54xx->fc = val ;
break;
case 0x3cf:
if (svga->gdcaddr == 0)
gd543x_mmio_write(0xb8000, val, gd54xx);
@@ -532,6 +593,8 @@ gd54xx_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 ((svga->crtcreg == 0x25) || (svga->crtcreg == 0x27))
return;
old = svga->crtc[svga->crtcreg];
svga->crtc[svga->crtcreg] = val;
@@ -636,6 +699,10 @@ gd54xx_in(uint16_t addr, void *p)
}
gd54xx->ramdac.state++;
break;
case 0x3ca:
return gd54xx->fc;
case 0x3cf:
if (svga->gdcaddr > 8) {
return svga->gdcreg[svga->gdcaddr & 0x3f];
@@ -701,7 +768,7 @@ gd543x_recalc_mapping(gd54xx_t *gd54xx)
switch (svga->gdcreg[6] & 0x0c) {
case 0x0: /*128k at A0000*/
mem_map_set_addr(&svga->mapping, 0xa0000, 0x20000);
svga->banked_mask = 0xffff;
svga->banked_mask = 0x1ffff;
break;
case 0x4: /*64k at A0000*/
mem_map_set_addr(&svga->mapping, 0xa0000, 0x10000);
@@ -783,12 +850,18 @@ gd54xx_recalctimings(svga_t *svga)
svga->bpp = 8;
if (gd54xx->ramdac.ctrl & 0x80) {
if (gd54xx->ramdac.ctrl & 0x40) {
if (gd54xx->ramdac.ctrl & 0x80) { /* Extended Color Mode enabled */
if (gd54xx->ramdac.ctrl & 0x40) { /* Enable all Extended modes */
switch (gd54xx->ramdac.ctrl & 0xf) {
case 0:
if (gd54xx->ramdac.ctrl & 0x10) { /* Mixed Mode */
svga->render = svga_render_mixed_highres;
}
else
{
svga->bpp = 15;
svga->render = svga_render_15bpp_highres;
}
break;
case 1:
@@ -808,6 +881,11 @@ gd54xx_recalctimings(svga_t *svga)
}
break;
//case 8: Todo : Grayscale VGA rendering*/
//break;
//case 9: Todo : 3-3-2 8bit RGB*/
//break;
case 0xf:
switch (svga->seqregs[7] & CIRRUS_SR7_BPP_MASK) {
case CIRRUS_SR7_BPP_32:
@@ -835,6 +913,7 @@ gd54xx_recalctimings(svga_t *svga)
break;
}
} else {
/* Default to 5-5-5 Sierra Mode */
svga->bpp = 15;
svga->render = svga_render_15bpp_highres;
}
@@ -1036,6 +1115,7 @@ gd54xx_write(uint32_t addr, uint8_t val, void *p)
}
addr &= svga->banked_mask;
if (svga->banked_mask != 0x1ffff)
addr = (addr & 0x7fff) + gd54xx->bank[(addr >> 15) & 1];
svga_write_linear(addr, val, svga);
@@ -1060,6 +1140,7 @@ gd54xx_writew(uint32_t addr, uint16_t val, void *p)
}
addr &= svga->banked_mask;
if (svga->banked_mask != 0x1ffff)
addr = (addr & 0x7fff) + gd54xx->bank[(addr >> 15) & 1];
if (svga->writemode < 4)
@@ -1091,6 +1172,7 @@ gd54xx_writel(uint32_t addr, uint32_t val, void *p)
}
addr &= svga->banked_mask;
if (svga->banked_mask != 0x1ffff)
addr = (addr & 0x7fff) + gd54xx->bank[(addr >> 15) & 1];
if (svga->writemode < 4)
@@ -1552,6 +1634,7 @@ gd54xx_read(uint32_t addr, void *p)
addr &= svga->banked_mask;
addr = (addr & 0x7fff) + gd54xx->bank[(addr >> 15) & 1];
addr &= svga->vram_mask;
return svga_read_linear(addr, svga);
}
@@ -1566,6 +1649,7 @@ gd54xx_readw(uint32_t addr, void *p)
return svga_readw(addr, svga);
addr &= svga->banked_mask;
if (svga->banked_mask != 0x1ffff)
addr = (addr & 0x7fff) + gd54xx->bank[(addr >> 15) & 1];
return svga_readw_linear(addr, svga);
@@ -2228,6 +2312,7 @@ gd54xx_init(const device_t *info)
gd54xx_t *gd54xx = (gd54xx_t *)mem_alloc(sizeof(gd54xx_t));
svga_t *svga = &gd54xx->svga;
int id = info->local & 0xff;
int vram;
wchar_t *romfn = NULL;
memset(gd54xx, 0, sizeof(gd54xx_t));
@@ -2237,6 +2322,11 @@ gd54xx_init(const device_t *info)
gd54xx->rev = 0;
gd54xx->has_bios = 1;
switch (id) {
case CIRRUS_ID_CLGD5422:
case CIRRUS_ID_CLGD5424:
romfn = BIOS_GD5422_PATH;
break;
case CIRRUS_ID_CLGD5426:
romfn = BIOS_GD5426_PATH;
break;
@@ -2290,13 +2380,17 @@ gd54xx_init(const device_t *info)
break;
}
gd54xx->vram_size = device_get_config_int("memory");
gd54xx->vram_mask = (gd54xx->vram_size << 20) - 1;
vram = device_get_config_int("memory");
if (vram)
gd54xx->vram_size = vram << 20;
else
gd54xx->vram_size = 512 << 10;
gd54xx->vram_mask = gd54xx->vram_size - 1;
if (romfn)
rom_init(&gd54xx->bios_rom, romfn, 0xc0000, 0x8000, 0x7fff, 0, MEM_MAPPING_EXTERNAL);
svga_init(&gd54xx->svga, gd54xx, gd54xx->vram_size << 20,
svga_init(&gd54xx->svga, gd54xx, gd54xx->vram_size,
gd54xx_recalctimings, gd54xx_in, gd54xx_out,
gd54xx_hwcursor_draw, NULL);
svga->ven_write = gd54xx_write_modes45;
@@ -2336,6 +2430,12 @@ gd54xx_init(const device_t *info)
return gd54xx;
}
static int
gd5422_available(void)
{
return rom_present(BIOS_GD5422_PATH);
}
static int
gd5426_available(void)
{
@@ -2436,6 +2536,26 @@ gd54xx_force_redraw(void *p)
gd54xx->svga.fullchange = changeframecount;
}
static const device_config_t gd5422_config[] =
{
{
"memory","Memory size",CONFIG_SELECTION,"",1,
{
{
"512 KB",0
},
{
"1 MB",1
},
{
""
}
},
},
{
"","",-1
}
};
static const device_config_t gd5428_config[] =
{
@@ -2504,6 +2624,34 @@ static const video_timings_t cl_gd_isa_timing = {VID_ISA,3,3,6,8,8,12};
static const video_timings_t cl_gd_vlb_timing = {VID_BUS,4,4,8,10,10,20};
static const video_timings_t cl_gd_pci_timing = {VID_BUS,4,4,8,10,10,20};
const device_t gd5422_isa_device =
{
"Cirrus Logic GD-5422",
DEVICE_AT | DEVICE_ISA,
CIRRUS_ID_CLGD5422,
gd54xx_init,
gd54xx_close,
NULL,
gd5422_available,
gd54xx_speed_changed,
gd54xx_force_redraw,
&cl_gd_isa_timing,
gd5422_config,
};
const device_t gd5424_vlb_device =
{
"Cirrus Logic GD-5424",
DEVICE_VLB,
CIRRUS_ID_CLGD5424,
gd54xx_init,
gd54xx_close,
NULL,
gd5422_available,
gd54xx_speed_changed,
gd54xx_force_redraw,
&cl_gd_vlb_timing,
gd5422_config,
};
const device_t gd5426_vlb_device = {
"Cirrus Logic GD-5426",

View File

@@ -652,6 +652,69 @@ void svga_render_15bpp_highres(svga_t *svga)
}
}
void svga_render_mixed_highres(svga_t *svga)
{
int y_add = enable_overscan ? (overscan_y >> 1) : 0;
int x_add = enable_overscan ? 8 : 0;
if (svga->changedvram[svga->ma >> 12] || svga->changedvram[(svga->ma >> 12) + 1] || svga->fullchange)
{
int x;
int offset = (8 - ((svga->scrollcache & 6) >> 1)) + 24;
uint32_t *p = &((uint32_t *)buffer32->line[svga->displine + y_add])[offset + x_add];
if (svga->firstline_draw == 2000)
svga->firstline_draw = svga->displine;
svga->lastline_draw = svga->displine;
for (x = 0; x <= svga->hdisp; x += 8)
{
uint32_t dat = *(uint32_t *)(&svga->vram[(svga->ma + (x << 1)) & svga->vram_display_mask]);
if (dat & 0x8000)
p[x] = svga->pallook[dat & 0xff];
else
p[x] = video_15to32[dat & 0x7fff];
if ((dat >> 16) & 0x8000)
p[x + 1] = svga->pallook[(dat >> 16) & 0xff];
else
p[x + 1] = video_15to32[(dat >> 16) & 0x7fff];
dat = *(uint32_t *)(&svga->vram[(svga->ma + (x << 1) + 4) & svga->vram_display_mask]);
if (dat & 0x8000)
p[x + 2] = svga->pallook[dat & 0xff];
else
p[x + 2] = video_15to32[dat & 0x7fff];
if ((dat >> 16) & 0x8000)
p[x + 3] = svga->pallook[(dat >> 16) & 0xff];
else
p[x + 3] = video_15to32[(dat >> 16) & 0x7fff];
dat = *(uint32_t *)(&svga->vram[(svga->ma + (x << 1) + 8) & svga->vram_display_mask]);
if (dat & 0x8000)
p[x + 4] = svga->pallook[dat & 0xff];
else
p[x + 4] = video_15to32[dat & 0x7fff];
if ((dat >> 16) & 0x8000)
p[x + 5] = svga->pallook[(dat >> 16) & 0xff];
else
p[x + 5] = video_15to32[(dat >> 16) & 0x7fff];
dat = *(uint32_t *)(&svga->vram[(svga->ma + (x << 1) + 12) & svga->vram_display_mask]);
if (dat & 0x8000)
p[x + 6] = svga->pallook[dat & 0xff];
else
p[x + 6] = video_15to32[dat & 0x7fff];
if ((dat >> 16) & 0x8000)
p[x + 7] = svga->pallook[(dat >> 16) & 0xff];
else
p[x + 7] = video_15to32[(dat >> 16) & 0x7fff];
}
svga->ma += x << 1;
svga->ma &= svga->vram_display_mask;
}
}
void svga_render_16bpp_lowres(svga_t *svga)
{
int y_add = enable_overscan ? (overscan_y >> 1) : 0;

View File

@@ -64,6 +64,7 @@ void svga_render_8bpp_lowres(svga_t *svga);
void svga_render_8bpp_highres(svga_t *svga);
void svga_render_15bpp_lowres(svga_t *svga);
void svga_render_15bpp_highres(svga_t *svga);
void svga_render_mixed_highres(svga_t *svga);
void svga_render_16bpp_lowres(svga_t *svga);
void svga_render_16bpp_highres(svga_t *svga);
void svga_render_24bpp_lowres(svga_t *svga);

View File

@@ -170,6 +170,10 @@ extern const device_t mach64vt2_device;
extern const device_t cga_device;
/* Cirrus Logic GD-series cards. */
#if defined(DEV_BRANCH)
extern const device_t gd5422_isa_device;
extern const device_t gd5424_vlb_device;
#endif
extern const device_t gd5426_vlb_device;
extern const device_t gd5428_isa_device;
extern const device_t gd5428_vlb_device;

View File

@@ -84,6 +84,9 @@ static const struct {
{ "ati28800w", &ati28800_wonderxl24_device },
#endif
{ "superega", &sega_device },
#if defined(DEV_BRANCH)
{ "cl_gd5422_isa", &gd5422_isa_device },
#endif
{ "cl_gd5428_isa", &gd5428_isa_device },
{ "cl_gd5429_isa", &gd5429_isa_device },
{ "cl_gd5434_isa", &gd5434_isa_device },
@@ -137,6 +140,9 @@ static const struct {
{ "mach64gx_vlb", &mach64gx_vlb_device },
{ "et4000w32p_vlb", &et4000w32p_cardex_vlb_device },
#if defined(DEV_BRANCH)
{ "cl_gd5424_vlb", &gd5424_vlb_device },
#endif
{ "cl_gd5429_vlb", &gd5429_vlb_device },
{ "cl_gd5434_vlb", &gd5434_vlb_device },
{ "stealth32_vlb", &et4000w32p_vlb_device },