From e8b11f49b9d081a08962d3cc70eec8870195018d Mon Sep 17 00:00:00 2001 From: Sergiy Dvodnenko Date: Fri, 4 Apr 2025 20:53:08 +0300 Subject: [PATCH 1/4] PCECD: abort SAPEP interrupt by the other command. --- support/pcecd/pcecd.h | 1 + support/pcecd/pcecdd.cpp | 14 +++++++++++--- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/support/pcecd/pcecd.h b/support/pcecd/pcecd.h index fdf785d..7f0fe61 100644 --- a/support/pcecd/pcecd.h +++ b/support/pcecd/pcecd.h @@ -98,6 +98,7 @@ private: int CDDAStart; int CDDAEnd; int CDDAFirst; + int int_pend; uint8_t CDDAMode; sense_t sense; uint8_t region; diff --git a/support/pcecd/pcecdd.cpp b/support/pcecd/pcecdd.cpp index ff0f50d..02cdf3a 100644 --- a/support/pcecd/pcecdd.cpp +++ b/support/pcecd/pcecdd.cpp @@ -330,6 +330,7 @@ void pcecdd_t::Reset() { CDDAStart = 0; CDDAEnd = 0; CDDAMode = PCECD_CDDAMODE_SILENT; + int_pend = false; stat = 0x0000; @@ -451,11 +452,13 @@ void pcecdd_t::Update() { this->state = PCECD_STATE_IDLE; } - if (this->CDDAMode == PCECD_CDDAMODE_INTERRUPT) { + if (this->int_pend) { SendStatus(MAKE_STATUS(PCECD_STATUS_GOOD, 0)); } - printf("\x1b[32mPCECD: playback reached the end %d\n\x1b[0m", this->lba); + printf("\x1b[32mPCECD: playback reached the end %d, int mode = %i\n\x1b[0m", this->lba, this->int_pend); + + this->int_pend = false; } } else if (this->state == PCECD_STATE_PAUSE) @@ -476,6 +479,8 @@ void pcecdd_t::CommandExec() { memset(buf, 0, 32); + this->int_pend = false; + switch (comm[0]) { case PCECD_COMM_TESTUNIT: if (state == PCECD_STATE_NODISC) { @@ -727,7 +732,10 @@ void pcecdd_t::CommandExec() { this->state = PCECD_STATE_PLAY; } - if (this->CDDAMode != PCECD_CDDAMODE_INTERRUPT) { + if (this->CDDAMode == PCECD_CDDAMODE_INTERRUPT) { + this->int_pend = true; + } + else { SendStatus(MAKE_STATUS(PCECD_STATUS_GOOD, 0)); } From 8b5187ef2cd50b33ef4fa57b13725bed33ded01b Mon Sep 17 00:00:00 2001 From: Sergiy Dvodnenko Date: Fri, 18 Apr 2025 15:48:21 +0300 Subject: [PATCH 2/4] PCECD: returns READSUBQ data and status at the end of the frame. end. --- support/pcecd/pcecd.h | 3 +- support/pcecd/pcecdd.cpp | 81 ++++++++++++++++++++++++++-------------- 2 files changed, 54 insertions(+), 30 deletions(-) diff --git a/support/pcecd/pcecd.h b/support/pcecd/pcecd.h index 7f0fe61..fa2c3b4 100644 --- a/support/pcecd/pcecd.h +++ b/support/pcecd/pcecd.h @@ -98,7 +98,8 @@ private: int CDDAStart; int CDDAEnd; int CDDAFirst; - int int_pend; + bool subq_pend; + bool int_pend; uint8_t CDDAMode; sense_t sense; uint8_t region; diff --git a/support/pcecd/pcecdd.cpp b/support/pcecd/pcecdd.cpp index 02cdf3a..cc07192 100644 --- a/support/pcecd/pcecdd.cpp +++ b/support/pcecd/pcecdd.cpp @@ -11,6 +11,7 @@ #include "pcecd.h" #define PCECD_DATA_IO_INDEX 2 +#define PCECD_CDDA_IO_INDEX 3 float get_cd_seek_ms(int start_sector, int target_sector); @@ -331,12 +332,34 @@ void pcecdd_t::Reset() { CDDAEnd = 0; CDDAMode = PCECD_CDDAMODE_SILENT; int_pend = false; + subq_pend = false; stat = 0x0000; - } void pcecdd_t::Update() { + msf_t msf; + uint8_t buf[12]; + buf[0] = 0x0A; + buf[1] = 0 | 0x80; + buf[2] = this->state == PCECD_STATE_PAUSE ? 2 : (this->state == PCECD_STATE_PLAY ? 0 : 3); + buf[3] = 0; + buf[4] = BCD(this->index + 1); + buf[5] = BCD(this->index); + + int lba_rel = this->lba - this->toc.tracks[this->index].start; + LBAToMSF(lba_rel, &msf); + buf[6] = BCD(msf.m); + buf[7] = BCD(msf.s); + buf[8] = BCD(msf.f); + + LBAToMSF(this->lba + 150, &msf); + buf[9] = BCD(msf.m); + buf[10] = BCD(msf.s); + buf[11] = BCD(msf.f); + + bool subq_send = false; + if (this->state == PCECD_STATE_READ) { if (this->latency > 0) @@ -408,13 +431,13 @@ void pcecdd_t::Update() { if (this->latency > 0) { this->latency--; - return; + goto skip; } if (this->audiodelay > 0) { this->audiodelay--; - return; + goto skip; } this->index = GetTrackByLBA(this->lba, &this->toc); @@ -434,7 +457,7 @@ void pcecdd_t::Update() { ReadCDDA(sec_buf + 2); if (SendData) - SendData(sec_buf, 2352 + 2, PCECD_DATA_IO_INDEX); + SendData(sec_buf, 2352 + 2, PCECD_CDDA_IO_INDEX); //printf("\x1b[32mPCECD: Audio sector send = %i, track = %i, offset = %i\n\x1b[0m", this->lba, this->index, (this->lba * 2352) - this->toc.tracks[index].offset); } @@ -460,15 +483,37 @@ void pcecdd_t::Update() { this->int_pend = false; } + + skip: + if (this->subq_pend) { + this->subq_pend = false; + subq_send = true; + } } else if (this->state == PCECD_STATE_PAUSE) { + subq_send = this->subq_pend; + this->subq_pend = false; + if (this->latency > 0) { this->latency--; - return; } } + else + { + subq_send = this->subq_pend; + this->subq_pend = false; + } + + if (subq_send) { + subq_send = false; + + if (SendData) + SendData(buf, 10 + 2, PCECD_DATA_IO_INDEX); + + SendStatus(MAKE_STATUS(PCECD_STATUS_GOOD, 0)); + } } void pcecdd_t::CommandExec() { @@ -752,31 +797,9 @@ void pcecdd_t::CommandExec() { break; case PCECD_COMM_READSUBQ: { - int lba_rel = this->lba - this->toc.tracks[this->index].start; + this->subq_pend = true; - buf[0] = 0x0A; - buf[1] = 0 | 0x80; - buf[2] = this->state == PCECD_STATE_PAUSE ? 2 : (this->state == PCECD_STATE_PLAY ? 0 : 3); - buf[3] = 0; - buf[4] = BCD(this->index + 1); - buf[5] = BCD(this->index); - - LBAToMSF(lba_rel, &msf); - buf[6] = BCD(msf.m); - buf[7] = BCD(msf.s); - buf[8] = BCD(msf.f); - - LBAToMSF(this->lba+150, &msf); - buf[9] = BCD(msf.m); - buf[10] = BCD(msf.s); - buf[11] = BCD(msf.f); - - if (SendData) - SendData(buf, 10 + 2, PCECD_DATA_IO_INDEX); - - //printf("\x1b[32mPCECD: Command READSUBQ, [1] = %02X, track = %i, index = %i, lba_rel = %i, lba_abs = %i\n\x1b[0m", comm[1], this->index + 1, this->index, lba_rel, this->lba); - - SendStatus(MAKE_STATUS(PCECD_STATUS_GOOD, 0)); + printf("\x1b[32mPCECD: Command READSUBQ, [1] = %02X, track = %i, index = %i, lba_abs = %i\n\x1b[0m", comm[1], this->index + 1, this->index, this->lba); } break; From 5ab85ddac3344addbd486e55db34c5ebc142f082 Mon Sep 17 00:00:00 2001 From: Sergiy Dvodnenko Date: Sat, 19 Apr 2025 14:43:16 +0300 Subject: [PATCH 3/4] Saturn: fix the track offset for 2048 byte mode. --- support/saturn/saturncdd.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/support/saturn/saturncdd.cpp b/support/saturn/saturncdd.cpp index a68bbff..f5c1869 100644 --- a/support/saturn/saturncdd.cpp +++ b/support/saturn/saturncdd.cpp @@ -249,7 +249,7 @@ int satcdd_t::LoadCUE(const char* filename) { } } else if (idx == 1) { - this->toc.tracks[this->toc.last].offset += pregap * 2352; + this->toc.tracks[this->toc.last].offset += pregap * this->sectorSize; if (!new_file) { @@ -265,7 +265,7 @@ int satcdd_t::LoadCUE(const char* filename) { else { this->toc.tracks[this->toc.last].start = this->toc.end + pregap; - this->toc.tracks[this->toc.last].offset += this->toc.end * 2352; + this->toc.tracks[this->toc.last].offset += this->toc.end * this->sectorSize; int sectorSize = 2352; if (this->toc.tracks[this->toc.last].type) sectorSize = this->sectorSize; From 5529461cfed80bd8d99a8fe2a17fef6384833b70 Mon Sep 17 00:00:00 2001 From: Sergiy Dvodnenko Date: Sun, 20 Apr 2025 11:30:26 +0300 Subject: [PATCH 4/4] Saturn: increase delay for the Seek command (Radiant Silvergun stage 4D) --- support/saturn/saturncdd.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/support/saturn/saturncdd.cpp b/support/saturn/saturncdd.cpp index f5c1869..1f2e0bd 100644 --- a/support/saturn/saturncdd.cpp +++ b/support/saturn/saturncdd.cpp @@ -620,7 +620,7 @@ void satcdd_t::CommandExec() { this->index = this->toc.GetIndexByLBA(this->track, this->seek_lba); this->seek_pend = true; - this->seek_delay = 5; + this->seek_delay = 7; this->final_read = this->read_pend; this->read_pend = false; this->pause_pend = false;