Update Apu class

This commit is contained in:
scawful
2024-04-24 10:04:24 -04:00
parent 5741596a89
commit 6842c08b3a
2 changed files with 55 additions and 56 deletions

View File

@@ -31,10 +31,21 @@ void Apu::Init() {
}
void Apu::Reset() {
clock_.ResetAccumulatedTime();
spc700_.Reset(true);
dsp_.Reset();
romReadable = true;
ram.clear();
rom_readable_ = true;
dsp_adr_ = 0;
cycles_ = 0;
memset(in_ports_, 0, sizeof(in_ports_));
memset(out_ports_, 0, sizeof(out_ports_));
for (int i = 0; i < 3; i++) {
timer_[i].cycles = 0;
timer_[i].divider = 0;
timer_[i].target = 0;
timer_[i].counter = 0;
timer_[i].enabled = false;
}
}
void Apu::Update() {
@@ -69,18 +80,18 @@ void Apu::Cycle() {
// handle timers
for (int i = 0; i < 3; i++) {
if (timer[i].cycles == 0) {
timer[i].cycles = i == 2 ? 16 : 128;
if (timer[i].enabled) {
timer[i].divider++;
if (timer[i].divider == timer[i].target) {
timer[i].divider = 0;
timer[i].counter++;
timer[i].counter &= 0xf;
if (timer_[i].cycles == 0) {
timer_[i].cycles = i == 2 ? 16 : 128;
if (timer_[i].enabled) {
timer_[i].divider++;
if (timer_[i].divider == timer_[i].target) {
timer_[i].divider = 0;
timer_[i].counter++;
timer_[i].counter &= 0xf;
}
}
}
timer[i].cycles--;
timer_[i].cycles--;
}
cycles_++;
@@ -96,10 +107,10 @@ uint8_t Apu::Read(uint16_t adr) {
return 0;
}
case 0xf2: {
return dspAdr;
return dsp_adr_;
}
case 0xf3: {
return dsp_.Read(dspAdr & 0x7f);
return dsp_.Read(dsp_adr_ & 0x7f);
}
case 0xf4:
case 0xf5:
@@ -107,20 +118,20 @@ uint8_t Apu::Read(uint16_t adr) {
case 0xf7:
case 0xf8:
case 0xf9: {
return inPorts[adr - 0xf4];
return in_ports_[adr - 0xf4];
}
case 0xfd:
case 0xfe:
case 0xff: {
uint8_t ret = timer[adr - 0xfd].counter;
timer[adr - 0xfd].counter = 0;
uint8_t ret = timer_[adr - 0xfd].counter;
timer_[adr - 0xfd].counter = 0;
return ret;
}
}
if (romReadable && adr >= 0xffc0) {
if (rom_readable_ && adr >= 0xffc0) {
return bootRom[adr - 0xffc0];
}
return aram_.read(adr);
return ram[adr];
}
void Apu::Write(uint16_t adr, uint8_t val) {
@@ -130,51 +141,51 @@ void Apu::Write(uint16_t adr, uint8_t val) {
}
case 0xf1: {
for (int i = 0; i < 3; i++) {
if (!timer[i].enabled && (val & (1 << i))) {
timer[i].divider = 0;
timer[i].counter = 0;
if (!timer_[i].enabled && (val & (1 << i))) {
timer_[i].divider = 0;
timer_[i].counter = 0;
}
timer[i].enabled = val & (1 << i);
timer_[i].enabled = val & (1 << i);
}
if (val & 0x10) {
inPorts[0] = 0;
inPorts[1] = 0;
in_ports_[0] = 0;
in_ports_[1] = 0;
}
if (val & 0x20) {
inPorts[2] = 0;
inPorts[3] = 0;
in_ports_[2] = 0;
in_ports_[3] = 0;
}
romReadable = val & 0x80;
rom_readable_ = val & 0x80;
break;
}
case 0xf2: {
dspAdr = val;
dsp_adr_ = val;
break;
}
case 0xf3: {
if (dspAdr < 0x80) dsp_.Write(dspAdr, val);
if (dsp_adr_ < 0x80) dsp_.Write(dsp_adr_, val);
break;
}
case 0xf4:
case 0xf5:
case 0xf6:
case 0xf7: {
outPorts[adr - 0xf4] = val;
out_ports_[adr - 0xf4] = val;
break;
}
case 0xf8:
case 0xf9: {
inPorts[adr - 0xf4] = val;
in_ports_[adr - 0xf4] = val;
break;
}
case 0xfa:
case 0xfb:
case 0xfc: {
timer[adr - 0xfa].target = val;
timer_[adr - 0xfa].target = val;
break;
}
}
aram_.write(adr, val);
ram[adr] = val;
}
uint8_t Apu::SpcRead(uint16_t adr) {

View File

@@ -56,8 +56,8 @@ typedef struct Timer {
*/
class Apu {
public:
Apu(MemoryImpl &memory, AudioRam &aram, Clock &clock)
: aram_(aram), clock_(clock), memory_(memory) {}
Apu(MemoryImpl &memory, Clock &clock)
: clock_(clock), memory_(memory) {}
void Init();
void Reset();
@@ -73,34 +73,22 @@ class Apu {
uint8_t Read(uint16_t address);
void Write(uint16_t address, uint8_t data);
// Called upon a reset
void Initialize() {
spc700_.Reset();
dsp_.Reset();
}
void UpdateClock(int delta_time) { clock_.UpdateClock(delta_time); }
auto dsp() -> Dsp & { return dsp_; }
uint8_t inPorts[6]; // includes 2 bytes of ram
uint8_t outPorts[4];
// Port buffers (equivalent to $2140 to $2143 for the main CPU)
uint8_t in_ports_[6]; // includes 2 bytes of ram
uint8_t out_ports_[4];
private:
// Constants for communication
static const uint8_t READY_SIGNAL_0 = 0xAA;
static const uint8_t READY_SIGNAL_1 = 0xBB;
static const uint8_t BEGIN_SIGNAL = 0xCC;
// Port buffers (equivalent to $2140 to $2143 for the main CPU)
uint8_t ports_[4] = {0};
Timer timer[3];
Timer timer_[3];
uint32_t cycles_;
uint8_t dspAdr;
bool romReadable = false;
uint8_t dsp_adr_;
bool rom_readable_ = false;
std::vector<uint8_t> ram = std::vector<uint8_t>(0x10000, 0);
// Member variables to store internal APU state and resources
AudioRam &aram_;
Clock &clock_;
MemoryImpl &memory_;
@@ -109,8 +97,8 @@ class Apu {
[&](uint16_t adr) { return SpcRead(adr); },
[&](bool waiting) { SpcIdle(waiting); },
};
Dsp dsp_{aram_};
Spc700 spc700_{aram_, callbacks_};
Dsp dsp_{ram};
Spc700 spc700_{callbacks_};
};
} // namespace audio