mirror of
https://github.com/ARMSX2/ARMSX1.git
synced 2026-08-24 16:53:35 -07:00
Input fixes
Fixes Silent Hill, Harvest Moon, Chrono Cross, Capcom vs. SNK, US Racer, Army Men - Air Attack, Alone in the Dark - The New Nightmare, and more
This commit is contained in:
+36
-32
@@ -304,6 +304,7 @@ void cdrom_cmd_setloc(psx_cdrom_t* cdrom) {
|
||||
int m = PFIFO_POP;
|
||||
|
||||
if (!(VALID_BCD(m) && VALID_BCD(s) && VALID_BCD(f) && (f < 0x75))) {
|
||||
printf("setloc: invalid msf\n");
|
||||
cdrom->irq_delay = DELAY_1MS;
|
||||
cdrom->delayed_command = CDL_ERROR;
|
||||
cdrom->state = CD_STATE_ERROR;
|
||||
@@ -323,11 +324,11 @@ void cdrom_cmd_setloc(psx_cdrom_t* cdrom) {
|
||||
|
||||
cdrom->seek_pending = 1;
|
||||
|
||||
log_fatal("setloc: %02x:%02x:%02x",
|
||||
cdrom->seek_msf.m,
|
||||
cdrom->seek_msf.s,
|
||||
cdrom->seek_msf.f
|
||||
);
|
||||
// printf("setloc: %02x:%02x:%02x\n",
|
||||
// cdrom->seek_msf.m,
|
||||
// cdrom->seek_msf.s,
|
||||
// cdrom->seek_msf.f
|
||||
// );
|
||||
|
||||
cdrom->irq_delay = DELAY_1MS;
|
||||
cdrom->delayed_command = CDL_SETLOC;
|
||||
@@ -336,7 +337,7 @@ void cdrom_cmd_setloc(psx_cdrom_t* cdrom) {
|
||||
|
||||
case CD_STATE_SEND_RESP1: {
|
||||
SET_BITS(ifr, IFR_INT, IFR_INT3);
|
||||
RESP_PUSH(GETSTAT_MOTOR);
|
||||
RESP_PUSH(GETSTAT_MOTOR | GETSTAT_SEEK);
|
||||
|
||||
if (cdrom->ongoing_read_command) {
|
||||
// printf("command=%02x\n", cdrom->ongoing_read_command);
|
||||
@@ -881,24 +882,24 @@ void cdrom_cmd_getlocl(psx_cdrom_t* cdrom) {
|
||||
|
||||
case CD_STATE_SEND_RESP1: {
|
||||
SET_BITS(ifr, IFR_INT, IFR_INT3);
|
||||
RESP_PUSH(cdrom->dfifo[0x13]);
|
||||
RESP_PUSH(cdrom->dfifo[0x12]);
|
||||
RESP_PUSH(cdrom->dfifo[0x11]);
|
||||
RESP_PUSH(cdrom->dfifo[0x10]);
|
||||
RESP_PUSH(cdrom->dfifo[0x0f]);
|
||||
RESP_PUSH(cdrom->dfifo[0x0e]);
|
||||
RESP_PUSH(cdrom->dfifo[0x0d]);
|
||||
RESP_PUSH(cdrom->dfifo[0x0c]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x13]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x12]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x11]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x10]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x0f]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x0e]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x0d]);
|
||||
RESP_PUSH(cdrom->xa_sector_buf[0x0c]);
|
||||
|
||||
// if (cdrom->ongoing_read_command) {
|
||||
// // printf("command=%02x\n", cdrom->ongoing_read_command);
|
||||
// cdrom->state = CD_STATE_SEND_RESP2;
|
||||
// cdrom->delayed_command = cdrom->ongoing_read_command;
|
||||
// cdrom->irq_delay = DELAY_1MS;
|
||||
// } else {
|
||||
if (cdrom->ongoing_read_command) {
|
||||
// printf("command=%02x\n", cdrom->ongoing_read_command);
|
||||
cdrom->state = CD_STATE_SEND_RESP2;
|
||||
cdrom->delayed_command = cdrom->ongoing_read_command;
|
||||
cdrom->irq_delay = DELAY_1MS;
|
||||
} else {
|
||||
cdrom->delayed_command = CDL_NONE;
|
||||
cdrom->state = CD_STATE_RECV_CMD;
|
||||
// }
|
||||
}
|
||||
} break;
|
||||
}
|
||||
}
|
||||
@@ -1564,6 +1565,9 @@ uint8_t cdrom_read_status(psx_cdrom_t* cdrom) {
|
||||
}
|
||||
|
||||
uint8_t cdrom_read_rfifo(psx_cdrom_t* cdrom) {
|
||||
if (cdrom->rfifo_index < 0)
|
||||
return 0;
|
||||
|
||||
uint8_t data = cdrom->rfifo[--cdrom->rfifo_index];
|
||||
|
||||
if (cdrom->rfifo_index == 0)
|
||||
@@ -1608,17 +1612,17 @@ void cdrom_write_status(psx_cdrom_t* cdrom, uint8_t value) {
|
||||
}
|
||||
|
||||
void cdrom_write_cmd(psx_cdrom_t* cdrom, uint8_t value) {
|
||||
// printf("%s(%02x) %u params=[%02x, %02x, %02x, %02x, %02x, %02x]\n",
|
||||
// g_psx_cdrom_command_names[value],
|
||||
// value,
|
||||
// cdrom->pfifo_index,
|
||||
// cdrom->pfifo[0],
|
||||
// cdrom->pfifo[1],
|
||||
// cdrom->pfifo[2],
|
||||
// cdrom->pfifo[3],
|
||||
// cdrom->pfifo[4],
|
||||
// cdrom->pfifo[5]
|
||||
// );
|
||||
printf("%s(%02x) %u params=[%02x, %02x, %02x, %02x, %02x, %02x]\n",
|
||||
g_psx_cdrom_command_names[value],
|
||||
value,
|
||||
cdrom->pfifo_index,
|
||||
cdrom->pfifo[0],
|
||||
cdrom->pfifo[1],
|
||||
cdrom->pfifo[2],
|
||||
cdrom->pfifo[3],
|
||||
cdrom->pfifo[4],
|
||||
cdrom->pfifo[5]
|
||||
);
|
||||
|
||||
cdrom->command = value;
|
||||
cdrom->state = CD_STATE_RECV_CMD;
|
||||
|
||||
+3
-1
@@ -239,7 +239,9 @@ void psx_dma_do_gpu_linked(psx_dma_t* dma) {
|
||||
uint32_t size = hdr >> 24;
|
||||
uint32_t addr = dma->gpu.madr;
|
||||
|
||||
while (true) {
|
||||
int timeout = 16384;
|
||||
|
||||
while (timeout--) {
|
||||
while (size--) {
|
||||
addr = (addr + (CHCR_STEP(gpu) ? -4 : 4)) & 0x1ffffc;
|
||||
|
||||
|
||||
+15
-4
@@ -12,6 +12,7 @@ void psx_mcd_init(psx_mcd_t* mcd, const char* path) {
|
||||
mcd->flag = 0x08;
|
||||
mcd->path = path;
|
||||
mcd->buf = malloc(MCD_MEMORY_SIZE);
|
||||
mcd->tx_data_ready = 0;
|
||||
|
||||
memset(mcd->buf, 0, MCD_MEMORY_SIZE);
|
||||
|
||||
@@ -33,8 +34,6 @@ void psx_mcd_init(psx_mcd_t* mcd, const char* path) {
|
||||
}
|
||||
|
||||
uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
return 0xff;
|
||||
|
||||
switch (mcd->state) {
|
||||
case MCD_STATE_TX_HIZ: mcd->tx_data = 0xff; break;
|
||||
case MCD_STATE_TX_FLG: mcd->tx_data = mcd->flag; mcd->flag = 0x00; break;
|
||||
@@ -49,6 +48,8 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
case 'S': mcd->state = MCD_S_STATE_TX_ACK1; break;
|
||||
}
|
||||
|
||||
// printf("mcd read %02x\n", mcd->tx_data);
|
||||
|
||||
// log_set_quiet(0);
|
||||
// log_fatal("mcd read %02x", mcd->tx_data);
|
||||
// log_set_quiet(1);
|
||||
@@ -77,6 +78,8 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
break;
|
||||
}
|
||||
|
||||
// printf("mcd read %02x\n", data);
|
||||
|
||||
// log_set_quiet(0);
|
||||
// log_fatal("mcd read %02x", data);
|
||||
// log_set_quiet(1);
|
||||
@@ -92,6 +95,8 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
// log_fatal("mcd read %02x", 'G');
|
||||
// log_set_quiet(1);
|
||||
|
||||
// printf("mcd read %02x\n", 'G');
|
||||
|
||||
return 'G';
|
||||
} break;
|
||||
|
||||
@@ -110,6 +115,8 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
break;
|
||||
}
|
||||
|
||||
// printf("mcd read %02x\n", mcd->rx_data);
|
||||
|
||||
// log_set_quiet(0);
|
||||
// log_fatal("mcd read %02x", mcd->rx_data);
|
||||
// log_set_quiet(1);
|
||||
@@ -127,6 +134,8 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
// log_fatal("mcd read %02x", 'G');
|
||||
// log_set_quiet(1);
|
||||
|
||||
// printf("mcd read %02x\n", 'G');
|
||||
|
||||
return 'G';
|
||||
} break;
|
||||
}
|
||||
@@ -138,16 +147,18 @@ uint8_t psx_mcd_read(psx_mcd_t* mcd) {
|
||||
// log_fatal("mcd read %02x", mcd->tx_data);
|
||||
// log_set_quiet(1);
|
||||
|
||||
// printf("mcd read %02x\n", mcd->tx_data);
|
||||
|
||||
return mcd->tx_data;
|
||||
}
|
||||
|
||||
void psx_mcd_write(psx_mcd_t* mcd, uint8_t data) {
|
||||
return;
|
||||
|
||||
// log_set_quiet(0);
|
||||
// log_fatal("mcd write %02x", data);
|
||||
// log_set_quiet(1);
|
||||
|
||||
// printf("mcd write %02x\n", data);
|
||||
|
||||
switch (mcd->state) {
|
||||
case MCD_STATE_TX_FLG: mcd->mode = data; break;
|
||||
case MCD_R_STATE_RX_MSB: mcd->msb = data; break;
|
||||
|
||||
+76
-51
@@ -5,6 +5,8 @@
|
||||
#include "pad.h"
|
||||
#include "../log.h"
|
||||
|
||||
#define JOY_IRQ_DELAY 512
|
||||
|
||||
uint32_t pad_read_rx(psx_pad_t* pad) {
|
||||
int slot = (pad->ctrl >> 13) & 1;
|
||||
|
||||
@@ -34,10 +36,6 @@ uint32_t pad_read_rx(psx_pad_t* pad) {
|
||||
} break;
|
||||
|
||||
case DEST_MCD: {
|
||||
pad->dest[slot] = 0;
|
||||
|
||||
return 0xff;
|
||||
|
||||
if (!mcd) {
|
||||
pad->dest[slot] = 0;
|
||||
|
||||
@@ -58,7 +56,6 @@ uint32_t pad_read_rx(psx_pad_t* pad) {
|
||||
|
||||
void pad_write_tx(psx_pad_t* pad, uint16_t data) {
|
||||
int slot = (pad->ctrl >> 13) & 1;
|
||||
// printf("slot=%u dest=%02x write tx data=%02x ", slot, pad->dest[slot], data);
|
||||
|
||||
psx_input_t* joy = pad->joy_slot[slot];
|
||||
psx_mcd_t* mcd = pad->mcd_slot[slot];
|
||||
@@ -66,20 +63,18 @@ void pad_write_tx(psx_pad_t* pad, uint16_t data) {
|
||||
if (!(pad->ctrl & CTRL_TXEN))
|
||||
return;
|
||||
|
||||
// if (slot == 0)
|
||||
// printf("slot %u (%02x) write %08x\n", slot, pad->dest[slot], data);
|
||||
|
||||
if (!pad->dest[slot]) {
|
||||
if ((data == DEST_JOY) || (data == DEST_MCD)) {
|
||||
pad->dest[slot] = data;
|
||||
|
||||
// printf(" slot=%u dest=%02x\n", slot, data);
|
||||
if ((data == DEST_JOY) && !joy)
|
||||
return;
|
||||
|
||||
// if (slot == 0)
|
||||
// printf("dest=%02x\n", data);
|
||||
if ((data == DEST_MCD) && !mcd)
|
||||
return;
|
||||
|
||||
if (pad->ctrl & CTRL_ACIE)
|
||||
pad->cycles_until_irq = 1500;
|
||||
pad->cycles_until_irq = JOY_IRQ_DELAY;
|
||||
}
|
||||
} else {
|
||||
switch (pad->dest[slot]) {
|
||||
@@ -97,10 +92,6 @@ void pad_write_tx(psx_pad_t* pad, uint16_t data) {
|
||||
} break;
|
||||
|
||||
case DEST_MCD: {
|
||||
pad->dest[slot] = 0;
|
||||
|
||||
return;
|
||||
|
||||
if (!mcd) {
|
||||
pad->dest[slot] = 0;
|
||||
|
||||
@@ -114,33 +105,33 @@ void pad_write_tx(psx_pad_t* pad, uint16_t data) {
|
||||
} break;
|
||||
}
|
||||
|
||||
if (pad->ctrl & CTRL_ACIE)
|
||||
pad->cycles_until_irq = 1500;
|
||||
if (pad->ctrl & CTRL_ACIE) {
|
||||
pad->irq_bit = 1;
|
||||
pad->cycles_until_irq = JOY_IRQ_DELAY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t pad_handle_stat_read(psx_pad_t* pad) {
|
||||
// // log_set_quiet(0);
|
||||
// printf("pad stat read\n");
|
||||
// // log_set_quiet(1);
|
||||
// return 0x07;
|
||||
psx_input_t* joy = pad->joy_slot[(pad->ctrl >> 13) & 1];
|
||||
|
||||
if (!joy)
|
||||
return 0xff;
|
||||
|
||||
return 0x7;
|
||||
return pad->stat | 7;
|
||||
}
|
||||
|
||||
void pad_handle_ctrl_write(psx_pad_t* pad, uint32_t value) {
|
||||
int slot = pad->ctrl & CTRL_SLOT;
|
||||
|
||||
pad->ctrl = value;
|
||||
|
||||
if (!(pad->ctrl & CTRL_JOUT)) {
|
||||
// pad->dest[0] = 0;
|
||||
// pad->dest[1] = 0;
|
||||
pad->ctrl &= ~CTRL_SLOT;
|
||||
|
||||
psx_mcd_reset(pad->mcd_slot[(pad->ctrl >> 13) & 1]);
|
||||
if (pad->mcd_slot[slot >> 13])
|
||||
psx_mcd_reset(pad->mcd_slot[slot >> 13]);
|
||||
}
|
||||
|
||||
// Reset STAT bits 3, 4, 5, 9
|
||||
if (pad->ctrl & CTRL_ACKN) {
|
||||
pad->stat &= 0xfdc7;
|
||||
pad->ctrl &= ~CTRL_ACKN;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -155,48 +146,65 @@ void psx_pad_init(psx_pad_t* pad, psx_ic_t* ic) {
|
||||
|
||||
pad->io_base = PSX_PAD_BEGIN;
|
||||
pad->io_size = PSX_PAD_SIZE;
|
||||
|
||||
pad->joy_slot[0] = NULL;
|
||||
pad->joy_slot[1] = NULL;
|
||||
pad->mcd_slot[0] = NULL;
|
||||
pad->mcd_slot[1] = NULL;
|
||||
}
|
||||
|
||||
uint32_t psx_pad_read32(psx_pad_t* pad, uint32_t offset) {
|
||||
uint32_t v = 0;
|
||||
|
||||
switch (offset) {
|
||||
case 0: return pad_read_rx(pad);
|
||||
case 4: return pad_handle_stat_read(pad);
|
||||
case 8: return pad->mode;
|
||||
case 10: return pad->ctrl;
|
||||
case 14: return pad->baud;
|
||||
case 0: v = pad_read_rx(pad); break;
|
||||
case 4: v = pad_handle_stat_read(pad); break;
|
||||
case 8: v = pad->mode; break;
|
||||
case 10: v = pad->ctrl; break;
|
||||
case 14: v = pad->baud; break;
|
||||
}
|
||||
|
||||
printf("Unhandled 32-bit PAD read at offset %08x", offset);
|
||||
|
||||
return 0x0;
|
||||
return v;
|
||||
}
|
||||
|
||||
uint16_t psx_pad_read16(psx_pad_t* pad, uint32_t offset) {
|
||||
uint32_t v = 0;
|
||||
|
||||
switch (offset) {
|
||||
case 0: return pad_read_rx(pad) & 0xffff;
|
||||
case 4: return pad_handle_stat_read(pad) & 0xffff;
|
||||
case 8: return pad->mode;
|
||||
case 10: return pad->ctrl & 0xffff;
|
||||
case 14: return pad->baud;
|
||||
case 0: v = pad_read_rx(pad) & 0xffff; break;
|
||||
case 4: v = pad_handle_stat_read(pad) & 0xffff; break;
|
||||
case 8: v = pad->mode; break;
|
||||
case 10: v = pad->ctrl & 0xffff; break;
|
||||
case 14: v = pad->baud; break;
|
||||
}
|
||||
|
||||
return v;
|
||||
|
||||
printf("Unhandled 16-bit PAD read at offset %08x", offset);
|
||||
|
||||
return 0x0;
|
||||
}
|
||||
|
||||
uint8_t psx_pad_read8(psx_pad_t* pad, uint32_t offset) {
|
||||
uint32_t v = 0;
|
||||
|
||||
switch (offset) {
|
||||
case 0: return pad_read_rx(pad) & 0xff;
|
||||
case 4: return pad_handle_stat_read(pad) & 0xff;
|
||||
case 8: return pad->mode & 0xff;
|
||||
case 10: return pad->ctrl & 0xff;
|
||||
case 14: return pad->baud & 0xff;
|
||||
case 0: v = pad_read_rx(pad) & 0xff; break;
|
||||
case 4: v = pad_handle_stat_read(pad) & 0xff; break;
|
||||
case 8: v = pad->mode; break;
|
||||
case 10: v = pad->ctrl & 0xff; break;
|
||||
case 14: v = pad->baud; break;
|
||||
}
|
||||
|
||||
printf("Unhandled 8-bit PAD read at offset %08x", offset);
|
||||
// if (offset <= 0xa)
|
||||
// printf("slot=%d dest=%02x pad_read8(%02x) -> %02x\n",
|
||||
// (pad->ctrl & CTRL_SLOT) >> 13,
|
||||
// pad->dest[(pad->ctrl & CTRL_SLOT) >> 13],
|
||||
// offset,
|
||||
// v
|
||||
// );
|
||||
|
||||
return 0x0;
|
||||
return v;
|
||||
}
|
||||
|
||||
void psx_pad_write32(psx_pad_t* pad, uint32_t offset, uint32_t value) {
|
||||
@@ -222,6 +230,14 @@ void psx_pad_write16(psx_pad_t* pad, uint32_t offset, uint16_t value) {
|
||||
}
|
||||
|
||||
void psx_pad_write8(psx_pad_t* pad, uint32_t offset, uint8_t value) {
|
||||
// if (offset <= 0xa)
|
||||
// printf("slot=%d dest=%02x pad_write8(%02x) -> %02x\n",
|
||||
// (pad->ctrl & CTRL_SLOT) >> 13,
|
||||
// pad->dest[(pad->ctrl & CTRL_SLOT) >> 13],
|
||||
// offset,
|
||||
// value
|
||||
// );
|
||||
|
||||
switch (offset) {
|
||||
case 0: pad_write_tx(pad, value); return;
|
||||
case 8: pad->mode = value; return;
|
||||
@@ -270,6 +286,10 @@ void psx_pad_detach_joy(psx_pad_t* pad, int slot) {
|
||||
}
|
||||
|
||||
void psx_pad_attach_mcd(psx_pad_t* pad, int slot, const char* path) {
|
||||
printf("Memory Card support is disabled\n");
|
||||
|
||||
return;
|
||||
|
||||
if (pad->mcd_slot[slot])
|
||||
psx_pad_detach_mcd(pad, slot);
|
||||
|
||||
@@ -295,6 +315,11 @@ void psx_pad_update(psx_pad_t* pad, int cyc) {
|
||||
if (pad->cycles_until_irq <= 0) {
|
||||
psx_ic_irq(pad->ic, IC_JOY);
|
||||
|
||||
if (pad->irq_bit) {
|
||||
pad->stat |= STAT_IRQ7;
|
||||
pad->irq_bit = 0;
|
||||
}
|
||||
|
||||
pad->cycles_until_irq = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -115,6 +115,7 @@ typedef struct {
|
||||
int cycles_until_irq;
|
||||
int cycle_counter;
|
||||
int dest[2];
|
||||
int irq_bit;
|
||||
|
||||
uint16_t mode, ctrl, baud, stat;
|
||||
} psx_pad_t;
|
||||
|
||||
+1
-8
@@ -23,7 +23,7 @@ void psxi_sda_init(psxi_sda_t* sda, uint16_t model) {
|
||||
sda->model = model;
|
||||
sda->state = SDA_STATE_TX_HIZ;
|
||||
sda->sw = 0xffff;
|
||||
sda->sa_mode = 0;
|
||||
sda->sa_mode = SA_MODE_DIGITAL;
|
||||
sda->adc0 = 0x80;
|
||||
sda->adc1 = 0x80;
|
||||
sda->adc2 = 0x80;
|
||||
@@ -81,11 +81,6 @@ void psxi_sda_write(void* udata, uint16_t data) {
|
||||
psxi_sda_t* sda = (psxi_sda_t*)udata;
|
||||
|
||||
// To-do: Handle TAP and MOT bytes here
|
||||
if (data == 0x01) {
|
||||
sda->tx_data = 0xff;
|
||||
sda->tx_data_ready = 1;
|
||||
sda->state = SDA_STATE_TX_HIZ;
|
||||
}
|
||||
|
||||
if (data == 0x43) {
|
||||
if (sda->sa_mode == SA_MODE_ANALOG) {
|
||||
@@ -97,8 +92,6 @@ void psxi_sda_write(void* udata, uint16_t data) {
|
||||
sda->state = SDA_STATE_TX_HIZ;
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
void psxi_sda_on_button_press(void* udata, uint32_t data) {
|
||||
|
||||
Reference in New Issue
Block a user