1
0
mirror of https://github.com/TomHarte/CLK.git synced 2024-11-23 03:32:32 +00:00

Continues trying to get to write support.

This commit is contained in:
Thomas Harte 2019-07-12 21:20:05 -04:00
parent 5b05a9bc61
commit d53d1c616f
2 changed files with 87 additions and 9 deletions

View File

@ -86,7 +86,7 @@ uint8_t IWM::read(int address) {
return uint8_t( return uint8_t(
(mode_&0x1f) | (mode_&0x1f) |
((state_ & ENABLE) ? 0x20 : 0x00) | ((state_ & ENABLE) ? 0x20 : 0x00) |
(drives_[active_drive_] ? (drives_[active_drive_]->read() ? 0x80 : 0x00) : 0x80) sense()
); );
} break; } break;
@ -138,6 +138,14 @@ void IWM::write(int address, uint8_t input) {
case Q7|Q6|ENABLE: // Write data register. case Q7|Q6|ENABLE: // Write data register.
LOG("Data register write"); LOG("Data register write");
// if(write_handshake_ & 0x80) {
// shift_register_ = input;
// output_bits_remaining_ = 8;
// } else {
// next_output_ = input;
// write_handshake_ &= ~0x80;
// }
break; break;
} }
} }
@ -158,7 +166,7 @@ void IWM::access(int address) {
state_ &= ~mask; state_ &= ~mask;
} }
// React appropriately to motor requests and to LSTRB register writes. // React appropriately to ENABLE and DRIVESEL changes, and changes into/out of write mode.
if(old_state != state_) { if(old_state != state_) {
push_drive_state(); push_drive_state();
@ -189,6 +197,34 @@ void IWM::access(int address) {
} }
} }
} break; } break;
case Q6:
case Q7: {
const auto old_shift_mode = shift_mode_;
switch(state_ & (Q6|Q7)) {
default: shift_mode_ = ShiftMode::CheckingWriteProtect; break;
case 0: shift_mode_ = ShiftMode::Reading; break;
case Q7:
// "The IWM is put into the write state by a transition from the write protect sense state to the
// write load state".
if(shift_mode_ == ShiftMode::CheckingWriteProtect) shift_mode_ = ShiftMode::Writing;
break;
}
// LOG("Shift mode is now " << int(shift_mode_));
if(drives_[active_drive_]) {
if(old_shift_mode == ShiftMode::Writing && shift_mode_ != ShiftMode::Writing) {
drives_[active_drive_]->end_writing();
write_handshake_ = 0xc0;
}
if(old_shift_mode != ShiftMode::Writing && shift_mode_ == ShiftMode::Writing) {
drives_[active_drive_]->begin_writing(Storage::Time(1, clock_rate_), false);
}
}
} break;
} }
} }
} }
@ -227,9 +263,8 @@ void IWM::run_for(const Cycles cycles) {
// Activity otherwise depends on mode and motor state. // Activity otherwise depends on mode and motor state.
int integer_cycles = cycles.as_int(); int integer_cycles = cycles.as_int();
switch(state_ & (Q6 | Q7 | ENABLE)) { switch(shift_mode_) {
case 0: case ShiftMode::Reading:
case ENABLE: // i.e. read mode.
if(drive_is_rotating_[active_drive_]) { if(drive_is_rotating_[active_drive_]) {
while(integer_cycles--) { while(integer_cycles--) {
drives_[active_drive_]->run_for(Cycles(1)); drives_[active_drive_]->run_for(Cycles(1));
@ -247,10 +282,38 @@ void IWM::run_for(const Cycles cycles) {
} }
break; break;
case Q6|Q7: /* case ShiftMode::Writing:
case Q6|Q7|ENABLE: // write mode? while(cycles_since_shift_ + integer_cycles >= bit_length_) {
printf("IWM write mode?\n"); const auto cycles_until_write = cycles_since_shift_ + integer_cycles - bit_length_;
break; drives_[active_drive_]->run_for(cycles_until_write);
drives_[active_drive_]->write_bit(shift_register_ & 0x80); // Is this correct?
shift_register_ <<= 1;
cycles_since_shift_ = Cycles(0);
integer_cycles -= cycles_until_write.as_int();
--output_bits_remaining_;
if(!output_bits_remaining_) {
if(!(write_handshake_ & 0x80)) {
write_handshake_ |= 0x80;
shift_register_ = next_output_;
output_bits_remaining_ = 8;
} else {
write_handshake_ &= ~0x40;
drives_[active_drive_]->end_writing();
}
}
}
cycles_since_shift_ = integer_cycles;
break;*/
// case ShiftMode::CheckingWriteProtect:
// while(--integer_cycles) {
// shift_register_ = (shift_register_ >> 1) | sense();
// }
// break;
default: default:
if(drive_is_rotating_[active_drive_]) drives_[active_drive_]->run_for(cycles); if(drive_is_rotating_[active_drive_]) drives_[active_drive_]->run_for(cycles);
@ -258,6 +321,10 @@ void IWM::run_for(const Cycles cycles) {
} }
} }
uint8_t IWM::sense() {
return drives_[active_drive_] ? (drives_[active_drive_]->read() ? 0x80 : 0x00) : 0x80;
}
void IWM::process_event(const Storage::Disk::Drive::Event &event) { void IWM::process_event(const Storage::Disk::Drive::Event &event) {
switch(event.type) { switch(event.type) {
case Storage::Disk::Track::Event::IndexHole: return; case Storage::Disk::Track::Event::IndexHole: return;

View File

@ -92,11 +92,22 @@ class IWM:
void access(int address); void access(int address);
uint8_t shift_register_ = 0; uint8_t shift_register_ = 0;
uint8_t next_output_ = 0;
int output_bits_remaining_ = 0;
void propose_shift(uint8_t bit); void propose_shift(uint8_t bit);
Cycles cycles_since_shift_; Cycles cycles_since_shift_;
Cycles bit_length_; Cycles bit_length_;
void push_drive_state(); void push_drive_state();
enum class ShiftMode {
Reading,
Writing,
CheckingWriteProtect
} shift_mode_;
uint8_t sense();
}; };