I got sort of stuck the way I was looking at this with the A/B/C1/C2 test. The problem with that test is that it runs through many loops before giving a result, so anything within the whole loop could propagate to the result, making it very difficult to debug. So I started a new type of test that does a 1-shot from power on. The challenge here (or possibly benefit?, see below) is that you start with a random state.
Power on: PA12 = 0, wait 3.6msec
- Write 00 to E000 (IRQ Ack / Disable)
- Write 01 to C000 (Reload value)
- Write 00 to C001 (Set IRQ mode to scanline counter mode)
- Write 00 to E001 (IRQ enable)
- Goto [X]
- PA12 = 0
- Do A1 dummy reads
- Goto [Z]
- PA12 = 0
- Do A2 dummy reads
- Goto [Z]
- PA12 = 1
- Do B dummy reads
- Loop to [Y] 20 times (i.e. trigger 20 scanlines)
- After 20 times, stop test, examine waveform triggered on scope.
Results from these values:
A1, A2, B, result
20 20 10 3
20 20 1 3
16 16 10 3
15 15 10 Never
14 14 10 Never
12 16 10 3
11 16 10 3
1 16 10 3
Result=3 means IRQ went low on the 3rd time I got to [Z]. Since this is a power-on test, the internal state machines may come up in any random state. I find that in some cases I get a 2 on at least some of these tests. However, I found no combination that made it ALWAYS 2. It proves that writing to all 4 registers E000, C000, C001, E001 in itself is not enough to completely initialize all of the scanline state machines into known states.
I modified the test as follows:
Insert 514 dummy reads before the register writes. No change.
I then removed that modification and did a different modification as follows:
Before writing to any of the registers, set PA12 = 1, delay, do a dummy read, set PA12 = 0, delay, then proceed with the normal test. Always the result is 2 scanlines with this modification. To me, this change represents entering sprite region, so it suggests that the 8-bit counter reload can only be unlocked from within sprite region. I made this change on the state diagram.
I then added to this test an additional 20 dummy reads like this:
Before writing to any of the registers, set PA12 = 1, delay, do a dummy read, set PA12 = 0, delay, [20 DUMMY READS], then proceed with the normal test.
I still get result = 2 scanlines when doing this, even though this test will have returned to background region before writing to the registers. So 8-bit reload remains unlocked even when entering background region. We already knew and are again confirming that PA12 must be 1 (i.e. re-enter sprite region) in order to lock out the 8-bit reload.
Since there are now 2 inter-dependencies between the sprite/background state machine and the lock/unlock state machine, I merged them into 1. They are still functionally the same, just providing 2 different ways of looking at it. This is another incremental progress but not finished and not tested enough yet.