I ran into an interesting difference between Z64k and real HW.
"the Bank2 story"
While progressing nicely on my cpm-bios-tinkering (advert: 60k TPA with ZPM using Ticmanis Fast text + removed brakes on VDC access)
The following happened:
The CPM-BIOS must poke a jump instruction and address at locations 0 (to warm-boot) and 5 (to bdos).
The bios does that by switching to bank1 (from shared memory) writing to page0.
I was looking for bytes to reach 60K TPA so I thought these 15 bytes of code were up for grabs.
I am supposed to be able to write to page0 in bank1 while bank0 is selected using the MMU page0 remapping.
Page0 and 1 are mapped to bank1 by the BIOS boot-code.
Interestingly, that doesn't work.
While Bank0 is in context, the Z80 rom is remapped from Dxxx to 0xxx.
I read that selecting 'bank2" returns bank0 without-Z80-Rom, and indeed this works.
On Z64K, writing to ROM (0,1,2 and 5,6,7) will nicely update Bank1 0,1,2 and 5,6,7 but on real HW this is NOT the case.
What is the simulation supposed to do then?
Allow me to divert you with my totally free rambling on what could be the case:
I imagine that C= used the MMU in a particular way: it has circuitry with the ability to switch a page (implemented for page 0 and page 1). I can well imagine the MOS chip-designers used that circuitry also to cause "if Z80 and Bank0 then swap IO-block with 0000"
Why IO?
Well, they needed to swap 4k of rom around and the page remapping would only do 256bytes.
The MMU design "knows" about IO because it controls its visibility and therefore has circuitry to Hide/Show the Dxxx range.
By adding to that, and combining with the swapping-circuitry of page0/1 they could have achieved the remapping of Z80 rom to 0000 with minimal extra gates.
That would be clever...
Downside: attempting to write to IO at 0000 (with rom swap, Z80 Out) causes a RAM write at Dxxx because you're swapping apparent RAM with apparent IO (not ram with ram because you wanted to use the IO circuitry to map 4K), and MMU knows about Z80 active.
This, I believe, would explains perfectly why bank2 still works (without Z80 rom). Because the MMU connects its remapping to the selected bank.
I surmise:
- Z80 Reading from 0xxx in with bank0 in context (io probably not relevant?) returns Z80 ROM (which was swapped with Dxxx RAM)
- Writing to 00xx in bank0 (I tested with IO off) does not end up in bank1-00xx even though remapping is enabled at the time (page0 and 1 and mapped to bank1 by the cpm boot code in the z80 rom, and also the shared mem for low mem is zero)
- What happens when I write (ram, not IO) to 00xx (bank0)? Data is not going to bank1 and not to VIC (tried $0020) not easy to test the bank0-0page
Z64K would need to map an attempt to OUT into Bank0 0xxx to Dxxx
Z64K would need to write in mem under ROM without MMU page remapping (at least not write to remapped page)
Z64K would need to hide Z80 rom and apply MMU page remapping if bank2 is selected
Of course, for C256 the code will not work anymore (I expect very few C128 were ever changed with the double MMU)
PS: the BIOS source code from C= has the following in it, in cxio.asm (
Csoren_cxio.asm )
;
; The following code does not work with the NEW MMU
;
;?ldccp:
...
; call do$move$0$to$1
In the code that follows we see the programmer (this must be Von, given his code predated the final MMU version) is updating the page0 and page1 pointers with LDIR to copy from bank0 to bank1 (see the discussion on this forum on accessing ram under ff00,
accessing-ff00)
Now consider the statement we see about "NEW MMU". It would stand to reason to assume that he was regularly making the rom-code as part of CPM, the rom-code was the loader. The code layout in the CPM folder (with shared CXequ defines) supports that assumption.
Then the Z80 ROM was (finally) achieved and with the 'new mmu' that ROM was in effect instead of the (presumably loaded code) of the original thing that was the proto-c128.
The reason Von's code didn't work anymore was he relied on the ROM being UnMapped during Bank0-RAM-Only. That changed with the new mmu. I say he would have been able to use this code if someone told him about the bank2 setting.
This shows us that using page-0 and page-1 pointers for inter-bank-move existed even before the C128 was released.