GUS gameport work
Classic: gameport toggleable by jumper/config option (pre-rev 3.4), disabled by default MAX: gameport toggleable by software register (post-rev 3.4), enabled by default Disable access to rev 3.4+ registers on Classic
This commit is contained in:
@@ -13,6 +13,7 @@
|
|||||||
#include <86box/io.h>
|
#include <86box/io.h>
|
||||||
#include <86box/midi.h>
|
#include <86box/midi.h>
|
||||||
#include <86box/nmi.h>
|
#include <86box/nmi.h>
|
||||||
|
#include <86box/gameport.h>
|
||||||
#include <86box/pic.h>
|
#include <86box/pic.h>
|
||||||
#include <86box/sound.h>
|
#include <86box/sound.h>
|
||||||
#include "cpu.h"
|
#include "cpu.h"
|
||||||
@@ -120,7 +121,9 @@ typedef struct gus_t {
|
|||||||
uint8_t sb_ctrl;
|
uint8_t sb_ctrl;
|
||||||
int sb_nmi;
|
int sb_nmi;
|
||||||
|
|
||||||
|
uint8_t joy_trim;
|
||||||
uint8_t reg_ctrl;
|
uint8_t reg_ctrl;
|
||||||
|
uint8_t jumper;
|
||||||
|
|
||||||
uint8_t ad_status;
|
uint8_t ad_status;
|
||||||
uint8_t ad_data;
|
uint8_t ad_data;
|
||||||
@@ -143,6 +146,8 @@ typedef struct gus_t {
|
|||||||
|
|
||||||
uint8_t usrr;
|
uint8_t usrr;
|
||||||
|
|
||||||
|
void *gameport;
|
||||||
|
|
||||||
uint8_t max_ctrl;
|
uint8_t max_ctrl;
|
||||||
|
|
||||||
ad1848_t ad1848;
|
ad1848_t ad1848;
|
||||||
@@ -159,6 +164,9 @@ int gusfreqs[] = {
|
|||||||
|
|
||||||
double vol16bit[4096];
|
double vol16bit[4096];
|
||||||
|
|
||||||
|
void gus_write(uint16_t addr, uint8_t val, void *priv);
|
||||||
|
uint8_t gus_read(uint16_t addr, void *priv);
|
||||||
|
|
||||||
void
|
void
|
||||||
gus_update_int_status(gus_t *gus)
|
gus_update_int_status(gus_t *gus)
|
||||||
{
|
{
|
||||||
@@ -537,6 +545,10 @@ gus_write(uint16_t addr, uint8_t val, void *priv)
|
|||||||
gus->t2on = 1;
|
gus->t2on = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 0x4B: /*Joystick trim DAC*/
|
||||||
|
gus->joy_trim = val;
|
||||||
|
break;
|
||||||
|
|
||||||
case 0x4c: /*Reset*/
|
case 0x4c: /*Reset*/
|
||||||
gus->reset = val;
|
gus->reset = val;
|
||||||
break;
|
break;
|
||||||
@@ -634,9 +646,23 @@ gus_write(uint16_t addr, uint8_t val, void *priv)
|
|||||||
gus->gp2_addr = val;
|
gus->gp2_addr = val;
|
||||||
break;
|
break;
|
||||||
case 5:
|
case 5:
|
||||||
gus->usrr = 0;
|
if (gus->type > GUS_CLASSIC)
|
||||||
|
gus->usrr = 0;
|
||||||
break;
|
break;
|
||||||
case 6:
|
case 6:
|
||||||
|
if (gus->type > GUS_CLASSIC) {
|
||||||
|
if (!(val & 0x2) && (gus->jumper & 0x2))
|
||||||
|
io_removehandler(0x0100 + gus->base, 0x0002, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
|
else if ((val & 0x2) && !(gus->jumper & 0x2))
|
||||||
|
io_sethandler(0x0100 + gus->base, 0x0002, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
|
|
||||||
|
if (!(val & 0x4) && (gus->jumper & 0x4))
|
||||||
|
gameport_remap(gus->gameport, 0x0);
|
||||||
|
else if ((val & 0x4) && !(gus->jumper & 0x4))
|
||||||
|
gameport_remap(gus->gameport, 0x201);
|
||||||
|
|
||||||
|
gus->jumper = val;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@@ -672,7 +698,8 @@ gus_write(uint16_t addr, uint8_t val, void *priv)
|
|||||||
gus->sb_2xe = val;
|
gus->sb_2xe = val;
|
||||||
break;
|
break;
|
||||||
case 0x20f:
|
case 0x20f:
|
||||||
gus->reg_ctrl = val;
|
if (gus->type > GUS_CLASSIC)
|
||||||
|
gus->reg_ctrl = val;
|
||||||
break;
|
break;
|
||||||
case 0x306:
|
case 0x306:
|
||||||
case 0x706:
|
case 0x706:
|
||||||
@@ -746,10 +773,10 @@ gus_read(uint16_t addr, void *priv)
|
|||||||
return val;
|
return val;
|
||||||
|
|
||||||
case 0x20F:
|
case 0x20F:
|
||||||
if (gus->type == GUS_MAX)
|
if (gus->type > GUS_CLASSIC)
|
||||||
val = 0x02;
|
val = gus->jumper;
|
||||||
else
|
else
|
||||||
val = 0x00;
|
val = 0xff;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x302:
|
case 0x302:
|
||||||
@@ -842,6 +869,9 @@ gus_read(uint16_t addr, void *priv)
|
|||||||
case 0x49: /*Sampling control*/
|
case 0x49: /*Sampling control*/
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
case 0x4B: /*Joystick trim DAC*/
|
||||||
|
return gus->joy_trim;
|
||||||
|
|
||||||
case 0x00:
|
case 0x00:
|
||||||
case 0x01:
|
case 0x01:
|
||||||
case 0x02:
|
case 0x02:
|
||||||
@@ -884,22 +914,24 @@ gus_read(uint16_t addr, void *priv)
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0x20b:
|
case 0x20b:
|
||||||
switch (gus->reg_ctrl & 0x07) {
|
if (gus->type > GUS_CLASSIC) {
|
||||||
case 1:
|
switch (gus->reg_ctrl & 0x07) {
|
||||||
val = gus->gp1;
|
case 1:
|
||||||
break;
|
val = gus->gp1;
|
||||||
case 2:
|
break;
|
||||||
val = gus->gp2;
|
case 2:
|
||||||
break;
|
val = gus->gp2;
|
||||||
case 3:
|
break;
|
||||||
val = gus->gp1_addr;
|
case 3:
|
||||||
break;
|
val = gus->gp1_addr;
|
||||||
case 4:
|
break;
|
||||||
val = gus->gp2_addr;
|
case 4:
|
||||||
break;
|
val = gus->gp2_addr;
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1292,6 +1324,7 @@ gus_reset(void *priv)
|
|||||||
gus->sb_ctrl = 0;
|
gus->sb_ctrl = 0;
|
||||||
gus->sb_nmi = 0;
|
gus->sb_nmi = 0;
|
||||||
|
|
||||||
|
gus->joy_trim = 29;
|
||||||
gus->reg_ctrl = 0;
|
gus->reg_ctrl = 0;
|
||||||
|
|
||||||
gus->ad_status = 0;
|
gus->ad_status = 0;
|
||||||
@@ -1355,12 +1388,21 @@ gus_init(UNUSED(const device_t *info))
|
|||||||
|
|
||||||
gus->type = info->local;
|
gus->type = info->local;
|
||||||
|
|
||||||
|
gus->jumper = 0x06;
|
||||||
|
|
||||||
gus->base = device_get_config_hex16("base");
|
gus->base = device_get_config_hex16("base");
|
||||||
|
|
||||||
io_sethandler(gus->base, 0x0010, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
io_sethandler(gus->base, 0x0010, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
io_sethandler(0x0100 + gus->base, 0x0010, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
io_sethandler(0x0100 + gus->base, 0x0002, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
|
io_sethandler(0x0102 + gus->base, 0x000e, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
io_sethandler(0x0506 + gus->base, 0x0001, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
io_sethandler(0x0506 + gus->base, 0x0001, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
io_sethandler(0x0388, 0x0002, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
io_sethandler(0x0388, 0x0002, gus_read, NULL, NULL, gus_write, NULL, NULL, gus);
|
||||||
|
if (gus->type == GUS_CLASSIC && device_get_config_int("gameport"))
|
||||||
|
gus->gameport = gameport_add(&gameport_201_device);
|
||||||
|
else {
|
||||||
|
gus->gameport = gameport_add(&gameport_pnp_1io_device);
|
||||||
|
gameport_remap(gus->gameport, 0x201);
|
||||||
|
}
|
||||||
|
|
||||||
if (gus->type == GUS_MAX) {
|
if (gus->type == GUS_MAX) {
|
||||||
ad1848_init(&gus->ad1848, AD1848_TYPE_CS4231);
|
ad1848_init(&gus->ad1848, AD1848_TYPE_CS4231);
|
||||||
@@ -1442,6 +1484,17 @@ static const device_config_t gus_config[] = {
|
|||||||
},
|
},
|
||||||
.bios = { { 0 } }
|
.bios = { { 0 } }
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
.name = "gameport",
|
||||||
|
.description = "Enable Game port",
|
||||||
|
.type = CONFIG_BINARY,
|
||||||
|
.default_string = NULL,
|
||||||
|
.default_int = 0,
|
||||||
|
.file_filter = NULL,
|
||||||
|
.spinner = { 0 },
|
||||||
|
.selection = { { 0 } },
|
||||||
|
.bios = { { 0 } }
|
||||||
|
},
|
||||||
{
|
{
|
||||||
.name = "receive_input",
|
.name = "receive_input",
|
||||||
.description = "Receive MIDI input",
|
.description = "Receive MIDI input",
|
||||||
|
|||||||
Reference in New Issue
Block a user