mirror of
https://github.com/TomHarte/CLK.git
synced 2025-01-02 08:34:14 +00:00
Merge pull request #716 from TomHarte/PartialDecoding
Clarifies IO decoding, adds YM mirrors.
This commit is contained in:
commit
4578b65487
@ -264,11 +264,11 @@ class ConcreteMachine:
|
||||
return delay;
|
||||
|
||||
case BusDevice::IO:
|
||||
switch(address >> 1) {
|
||||
switch(address & 0xfffe) { // TODO: surely it's going to be even less precise than this?
|
||||
default:
|
||||
// assert(false);
|
||||
|
||||
case 0x7fc000:
|
||||
case 0x8000:
|
||||
/* Memory controller configuration:
|
||||
b0, b1: bank 1
|
||||
b2, b3: bank 0
|
||||
@ -280,8 +280,64 @@ class ConcreteMachine:
|
||||
*/
|
||||
break;
|
||||
|
||||
case 0x7fc400: /* PSG: write to select register, read to read register. */
|
||||
case 0x7fc401: /* PSG: write to write register. */
|
||||
// Video controls.
|
||||
case 0x8200: case 0x8202: case 0x8204: case 0x8206:
|
||||
case 0x8208: case 0x820a: case 0x820c: case 0x820e:
|
||||
case 0x8210: case 0x8212: case 0x8214: case 0x8216:
|
||||
case 0x8218: case 0x821a: case 0x821c: case 0x821e:
|
||||
case 0x8220: case 0x8222: case 0x8224: case 0x8226:
|
||||
case 0x8228: case 0x822a: case 0x822c: case 0x822e:
|
||||
case 0x8230: case 0x8232: case 0x8234: case 0x8236:
|
||||
case 0x8238: case 0x823a: case 0x823c: case 0x823e:
|
||||
case 0x8240: case 0x8242: case 0x8244: case 0x8246:
|
||||
case 0x8248: case 0x824a: case 0x824c: case 0x824e:
|
||||
case 0x8250: case 0x8252: case 0x8254: case 0x8256:
|
||||
case 0x8258: case 0x825a: case 0x825c: case 0x825e:
|
||||
case 0x8260: case 0x8262:
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
cycle.set_value16(video_->read(int(address >> 1)));
|
||||
} else {
|
||||
video_->write(int(address >> 1), cycle.value16());
|
||||
}
|
||||
break;
|
||||
|
||||
// DMA.
|
||||
case 0x8604: case 0x8606: case 0x8608: case 0x860a: case 0x860c:
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
cycle.set_value16(dma_->read(int(address >> 1)));
|
||||
} else {
|
||||
dma_->write(int(address >> 1), cycle.value16());
|
||||
}
|
||||
break;
|
||||
|
||||
// Audio.
|
||||
//
|
||||
// Re: mirrors, Dan Hollis' hardware register list asserts:
|
||||
//
|
||||
// "Note: PSG Registers are now fixed at these addresses. All other addresses are masked out on the Falcon. Any
|
||||
// writes to the shadow registers $8804-$88FF will cause bus errors.", which I am taking to imply that those shadow
|
||||
// registers exist on the Atari ST.
|
||||
case 0x8800: case 0x8802: case 0x8804: case 0x8806: case 0x8808: case 0x880a: case 0x880c: case 0x880e:
|
||||
case 0x8810: case 0x8812: case 0x8814: case 0x8816: case 0x8818: case 0x881a: case 0x881c: case 0x881e:
|
||||
case 0x8820: case 0x8822: case 0x8824: case 0x8826: case 0x8828: case 0x882a: case 0x882c: case 0x882e:
|
||||
case 0x8830: case 0x8832: case 0x8834: case 0x8836: case 0x8838: case 0x883a: case 0x883c: case 0x883e:
|
||||
case 0x8840: case 0x8842: case 0x8844: case 0x8846: case 0x8848: case 0x884a: case 0x884c: case 0x884e:
|
||||
case 0x8850: case 0x8852: case 0x8854: case 0x8856: case 0x8858: case 0x885a: case 0x885c: case 0x885e:
|
||||
case 0x8860: case 0x8862: case 0x8864: case 0x8866: case 0x8868: case 0x886a: case 0x886c: case 0x886e:
|
||||
case 0x8870: case 0x8872: case 0x8874: case 0x8876: case 0x8878: case 0x887a: case 0x887c: case 0x887e:
|
||||
case 0x8880: case 0x8882: case 0x8884: case 0x8886: case 0x8888: case 0x888a: case 0x888c: case 0x888e:
|
||||
case 0x8890: case 0x8892: case 0x8894: case 0x8896: case 0x8898: case 0x889a: case 0x889c: case 0x889e:
|
||||
case 0x88a0: case 0x88a2: case 0x88a4: case 0x88a6: case 0x88a8: case 0x88aa: case 0x88ac: case 0x88ae:
|
||||
case 0x88b0: case 0x88b2: case 0x88b4: case 0x88b6: case 0x88b8: case 0x88ba: case 0x88bc: case 0x88be:
|
||||
case 0x88c0: case 0x88c2: case 0x88c4: case 0x88c6: case 0x88c8: case 0x88ca: case 0x88cc: case 0x88ce:
|
||||
case 0x88d0: case 0x88d2: case 0x88d4: case 0x88d6: case 0x88d8: case 0x88da: case 0x88dc: case 0x88de:
|
||||
case 0x88e0: case 0x88e2: case 0x88e4: case 0x88e6: case 0x88e8: case 0x88ea: case 0x88ec: case 0x88ee:
|
||||
case 0x88f0: case 0x88f2: case 0x88f4: case 0x88f6: case 0x88f8: case 0x88fa: case 0x88fc: case 0x88fe:
|
||||
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
advance_time(HalfCycles(2));
|
||||
@ -292,25 +348,26 @@ class ConcreteMachine:
|
||||
cycle.set_value8_high(ay_.get_data_output());
|
||||
ay_.set_control_lines(GI::AY38910::ControlLines(0));
|
||||
} else {
|
||||
if((address >> 1) == 0x7fc400) {
|
||||
ay_.set_control_lines(GI::AY38910::BC1);
|
||||
} else {
|
||||
ay_.set_control_lines(GI::AY38910::ControlLines(GI::AY38910::BC2 | GI::AY38910::BDIR));
|
||||
}
|
||||
// Net effect here: addresses with bit 1 set write to a register,
|
||||
// addresses with bit 1 clear select a register.
|
||||
ay_.set_control_lines(GI::AY38910::ControlLines(
|
||||
GI::AY38910::BC2 | GI::AY38910::BDIR
|
||||
| ((address&2) ? 0 : GI::AY38910::BC1)
|
||||
));
|
||||
ay_.set_data_input(cycle.value8_high());
|
||||
ay_.set_control_lines(GI::AY38910::ControlLines(0));
|
||||
}
|
||||
return delay + HalfCycles(2);
|
||||
|
||||
// The MFP block:
|
||||
case 0x7ffd00: case 0x7ffd01: case 0x7ffd02: case 0x7ffd03:
|
||||
case 0x7ffd04: case 0x7ffd05: case 0x7ffd06: case 0x7ffd07:
|
||||
case 0x7ffd08: case 0x7ffd09: case 0x7ffd0a: case 0x7ffd0b:
|
||||
case 0x7ffd0c: case 0x7ffd0d: case 0x7ffd0e: case 0x7ffd0f:
|
||||
case 0x7ffd10: case 0x7ffd11: case 0x7ffd12: case 0x7ffd13:
|
||||
case 0x7ffd14: case 0x7ffd15: case 0x7ffd16: case 0x7ffd17:
|
||||
case 0x7ffd18: case 0x7ffd19: case 0x7ffd1a: case 0x7ffd1b:
|
||||
case 0x7ffd1c: case 0x7ffd1d: case 0x7ffd1e: case 0x7ffd1f:
|
||||
case 0xfa00: case 0xfa02: case 0xfa04: case 0xfa06:
|
||||
case 0xfa08: case 0xfa0a: case 0xfa0c: case 0xfa0e:
|
||||
case 0xfa10: case 0xfa12: case 0xfa14: case 0xfa16:
|
||||
case 0xfa18: case 0xfa1a: case 0xfa1c: case 0xfa1e:
|
||||
case 0xfa20: case 0xfa22: case 0xfa24: case 0xfa26:
|
||||
case 0xfa28: case 0xfa2a: case 0xfa2c: case 0xfa2e:
|
||||
case 0xfa30: case 0xfa32: case 0xfa34: case 0xfa36:
|
||||
case 0xfa38: case 0xfa3a: case 0xfa3c: case 0xfa3e:
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
@ -320,53 +377,19 @@ class ConcreteMachine:
|
||||
}
|
||||
break;
|
||||
|
||||
// Video controls.
|
||||
case 0x7fc100: case 0x7fc101: case 0x7fc102: case 0x7fc103:
|
||||
case 0x7fc104: case 0x7fc105: case 0x7fc106: case 0x7fc107:
|
||||
case 0x7fc108: case 0x7fc109: case 0x7fc10a: case 0x7fc10b:
|
||||
case 0x7fc10c: case 0x7fc10d: case 0x7fc10e: case 0x7fc10f:
|
||||
case 0x7fc110: case 0x7fc111: case 0x7fc112: case 0x7fc113:
|
||||
case 0x7fc114: case 0x7fc115: case 0x7fc116: case 0x7fc117:
|
||||
case 0x7fc118: case 0x7fc119: case 0x7fc11a: case 0x7fc11b:
|
||||
case 0x7fc11c: case 0x7fc11d: case 0x7fc11e: case 0x7fc11f:
|
||||
case 0x7fc120: case 0x7fc121: case 0x7fc122: case 0x7fc123:
|
||||
case 0x7fc124: case 0x7fc125: case 0x7fc126: case 0x7fc127:
|
||||
case 0x7fc128: case 0x7fc129: case 0x7fc12a: case 0x7fc12b:
|
||||
case 0x7fc12c: case 0x7fc12d: case 0x7fc12e: case 0x7fc12f:
|
||||
case 0x7fc130: case 0x7fc131:
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
cycle.set_value16(video_->read(int(address >> 1)));
|
||||
} else {
|
||||
video_->write(int(address >> 1), cycle.value16());
|
||||
}
|
||||
break;
|
||||
|
||||
// ACIAs.
|
||||
case 0x7ffe00: case 0x7ffe01: case 0x7ffe02: case 0x7ffe03: {
|
||||
case 0xfc00: case 0xfc02: case 0xfc04: case 0xfc06: {
|
||||
// Set VPA.
|
||||
mc68000_.set_is_peripheral_address(!cycle.data_select_active());
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
const auto acia_ = ((address >> 1) < 0x7ffe02) ? &keyboard_acia_ : &midi_acia_;
|
||||
const auto acia_ = (address & 4) ? &midi_acia_ : &keyboard_acia_;
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
cycle.set_value8_high((*acia_)->read(int(address >> 1)));
|
||||
} else {
|
||||
(*acia_)->write(int(address >> 1), cycle.value8_high());
|
||||
}
|
||||
} break;
|
||||
|
||||
// DMA.
|
||||
case 0x7fc302: case 0x7fc303: case 0x7fc304: case 0x7fc305: case 0x7fc306:
|
||||
if(!cycle.data_select_active()) return delay;
|
||||
|
||||
if(cycle.operation & Microcycle::Read) {
|
||||
cycle.set_value16(dma_->read(int(address >> 1)));
|
||||
} else {
|
||||
dma_->write(int(address >> 1), cycle.value16());
|
||||
}
|
||||
break;
|
||||
}
|
||||
return HalfCycles(0);
|
||||
}
|
||||
|
@ -23,9 +23,9 @@
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Release"
|
||||
selectedDebuggerIdentifier = ""
|
||||
selectedLauncherIdentifier = "Xcode.IDEFoundation.Launcher.PosixSpawn"
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
disableMainThreadChecker = "YES"
|
||||
codeCoverageEnabled = "YES">
|
||||
@ -68,8 +68,8 @@
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Release"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
selectedDebuggerIdentifier = ""
|
||||
selectedLauncherIdentifier = "Xcode.IDEFoundation.Launcher.PosixSpawn"
|
||||
enableASanStackUseAfterReturn = "YES"
|
||||
disableMainThreadChecker = "YES"
|
||||
launchStyle = "0"
|
||||
|
Loading…
Reference in New Issue
Block a user