Merge pull request #6386 from win2kgamer/cs423x-fixes

Crystal CS423x bugfixes
This commit is contained in:
Miran Grča
2025-10-22 04:27:41 +02:00
committed by GitHub
2 changed files with 22 additions and 2 deletions

View File

@@ -344,7 +344,7 @@ ad1848_write(uint16_t addr, uint8_t val, void *priv)
case 12:
if (ad1848->type >= AD1848_TYPE_CS4248) {
ad1848->regs[12] = 0x80 | (val & 0x70) | (ad1848->regs[12] & 0x0f);
ad1848->regs[12] = 0x80 | (val & 0x60) | (ad1848->regs[12] & 0x0f);
if ((ad1848->type >= AD1848_TYPE_CS4231) && (ad1848->type < AD1848_TYPE_CS4235)) {
if (val & 0x40)
ad1848->fmt_mask |= 0x80;
@@ -425,6 +425,19 @@ ad1848_write(uint16_t addr, uint8_t val, void *priv)
ad1848->fm_vol_r = (int) ad1848_vols_5bits_aux_gain[val & 0x1f];
}
}
if ((ad1848->type >= AD1848_TYPE_CS4232) && (ad1848->type <= AD1848_TYPE_CS4236)) {
if (ad1848->index == 18) {
if (val & 0x80)
ad1848->fm_vol_l = 0;
else
ad1848->fm_vol_l = (int) ad1848_vols_5bits_aux_gain[val & 0x1f];
} else {
if (val & 0x80)
ad1848->fm_vol_r = 0;
else
ad1848->fm_vol_r = (int) ad1848_vols_5bits_aux_gain[val & 0x1f];
}
}
break;
case 20 ... 21:
@@ -508,6 +521,8 @@ readonly_x:
}
if (ad1848->type == AD1848_TYPE_CS4231) /* I23 is reserved and read-only on CS4231 non-A */
goto readonly_i;
if ((ad1848->type >= AD1848_TYPE_CS4232) || (ad1848->type <= AD1848_TYPE_CS4236)) /* I23 bits 7-1 are read-only on CS4231A/4232/4236 non-B, Win2k relies on this for detection */
val = (val & 0x01);
break;
case 24:

View File

@@ -568,7 +568,11 @@ cs423x_ctxswitch_write(uint16_t addr, UNUSED(uint8_t val), void *priv)
{
cs423x_t *dev = (cs423x_t *) priv;
uint8_t ctx = (dev->regs[7] & 0x80);
uint8_t enable_opl = (dev->ad1848.xregs[4] & 0x10) && !(dev->indirect_regs[2] & 0x85);
uint8_t enable_opl = (dev->ad1848.xregs[4] & 0x10) && !(dev->indirect_regs[2] & 0x85); /* CS4236B+ */
/* CS4232/4236 (non-B) doesn't have an IFM bit, always enable the OPL on these chips */
if (dev->type <= CRYSTAL_CS4236)
enable_opl = 1;
/* Check if a context switch (WSS=1 <-> SBPro=0) occurred through the address being written. */
if ((dev->regs[7] & 0x80) ? ((addr & 0xfff0) == dev->sb_base) : ((addr & 0xfffc) == dev->wss_base)) {
@@ -1005,6 +1009,7 @@ cs423x_init(const device_t *info)
/* Initialize SBPro codec. The WSS codec is initialized later by cs423x_reset */
dev->sb = device_add_inst(&sb_pro_compat_device, 1);
sound_set_cd_audio_filter(sbpro_filter_cd_audio, dev->sb); /* CD audio filter for the default context */
music_add_handler(sb_get_music_buffer_sbpro, dev->sb); /* Init the SBPro OPL3 since sb_pro_compat_init does not */
/* Initialize RAM, registers and WSS codec. */
cs423x_reset(dev);