2020-10-17 18:10:48 +00:00
|
|
|
package storage
|
2020-08-29 19:48:09 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
See:
|
|
|
|
"Beneath Apple DOS" https://fabiensanglard.net/fd_proxy/prince_of_persia/Beneath%20Apple%20DOS.pdf
|
|
|
|
https://github.com/TomHarte/CLK/wiki/Apple-GCR-disk-encoding
|
|
|
|
*/
|
|
|
|
|
|
|
|
type diskette16sectorWritable struct {
|
|
|
|
nib *fileNib
|
|
|
|
position int
|
|
|
|
|
|
|
|
// Needed to write back
|
|
|
|
hasDirtyTrack bool
|
|
|
|
dirtyTrack int
|
|
|
|
}
|
|
|
|
|
2020-10-17 18:10:48 +00:00
|
|
|
func (d *diskette16sectorWritable) PowerOn(cycle uint64) {
|
2020-08-29 19:48:09 +00:00
|
|
|
// Not used
|
|
|
|
}
|
2020-10-17 18:10:48 +00:00
|
|
|
func (d *diskette16sectorWritable) PowerOff(_ uint64) {
|
2020-08-29 19:48:09 +00:00
|
|
|
d.commit()
|
|
|
|
}
|
|
|
|
|
2020-10-17 18:10:48 +00:00
|
|
|
func (d *diskette16sectorWritable) Read(quarterTrack int, cycle uint64) uint8 {
|
|
|
|
track := d.nib.track[quarterTrack/4]
|
2020-08-29 19:48:09 +00:00
|
|
|
value := track[d.position]
|
|
|
|
d.position = (d.position + 1) % nibBytesPerTrack
|
|
|
|
return value
|
|
|
|
}
|
|
|
|
|
2020-10-17 18:10:48 +00:00
|
|
|
func (d *diskette16sectorWritable) Write(quarterTrack int, value uint8, _ uint64) {
|
|
|
|
track := quarterTrack / 4
|
2020-08-29 19:48:09 +00:00
|
|
|
|
|
|
|
if d.hasDirtyTrack && track != d.dirtyTrack {
|
|
|
|
d.commit()
|
|
|
|
}
|
|
|
|
|
|
|
|
d.nib.track[track][d.position] = value
|
|
|
|
d.position = (d.position + 1) % nibBytesPerTrack
|
|
|
|
|
|
|
|
d.hasDirtyTrack = true
|
|
|
|
d.dirtyTrack = track
|
|
|
|
}
|
|
|
|
|
|
|
|
func (d *diskette16sectorWritable) commit() {
|
|
|
|
if d.hasDirtyTrack {
|
|
|
|
d.nib.saveTrack(d.dirtyTrack)
|
|
|
|
d.hasDirtyTrack = false
|
|
|
|
}
|
|
|
|
}
|