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

Corrected and sketched out state machine far enough to get to a complaint about unhandled work.

This commit is contained in:
Thomas Harte 2016-09-20 15:56:31 -04:00
parent e358057440
commit 3b97b038b9
3 changed files with 81 additions and 3 deletions

View File

@ -10,6 +10,8 @@
using namespace WD;
WD1770::WD1770() : state_(State::Waiting), status_(0), has_command_(false) {}
void WD1770::set_drive(std::shared_ptr<Storage::Disk::Drive> drive)
{
}
@ -20,13 +22,54 @@ void WD1770::set_is_double_density(bool is_double_density)
void WD1770::set_register(int address, uint8_t value)
{
switch(address&3)
{
case 0:
command_ = value;
has_command_ = true;
// TODO: is this force interrupt?
break;
case 1: track_ = value; break;
case 2: sector_ = value; break;
case 3: data_ = value; break;
}
}
uint8_t WD1770::get_register(int address)
{
return 0;
switch(address&3)
{
default: return status_;
case 1: return track_;
case 2: return sector_;
case 3: return data_;
}
}
void WD1770::run_for_cycles(unsigned int number_of_cycles)
{
// perform one step every eight cycles, arbitrariy as I can find no timing documentation
cycles += number_of_cycles;
while(cycles > 8)
{
cycles -= 8;
switch(state_)
{
case State::Waiting:
if(has_command_)
{
has_command_ = false;
if(command_ & 0x80)
state_ = (command_ & 0x40) ? State::BeginType3 : State::BeginType2;
else
state_ = State::BeginType1;
}
continue;
default:
printf("Unhandled state %d!", state_);
return;
}
}
}

View File

@ -15,12 +15,43 @@ namespace WD {
class WD1770 {
public:
WD1770();
void set_drive(std::shared_ptr<Storage::Disk::Drive> drive);
void set_is_double_density(bool is_double_density);
void set_register(int address, uint8_t value);
uint8_t get_register(int address);
void run_for_cycles(unsigned int number_of_cycles);
enum Flag: uint8_t {
MotorOn = 0x80,
WriteProtect = 0x40,
RecordType = 0x20,
SpinUp = 0x20,
RecordNotFound = 0x10,
CRCError = 0x08,
LostData = 0x04,
TrackZero = 0x04,
DataRequest = 0x02,
Index = 0x02,
Busy = 0x01
};
private:
unsigned int cycles;
enum class State {
Waiting,
BeginType1, BeginType2, BeginType3
} state_;
uint8_t status_;
uint8_t track_;
uint8_t sector_;
uint8_t data_;
uint8_t command_;
bool has_command_;
};
}

View File

@ -120,6 +120,10 @@ unsigned int Machine::perform_bus_operation(CPU6502::BusOperation operation, uin
}
else
{
// if((address >> 8) == 0xfc)
// {
// printf("d");
// }
switch(address & 0xff0f)
{
case 0xfe00:
@ -297,7 +301,7 @@ unsigned int Machine::perform_bus_operation(CPU6502::BusOperation operation, uin
}
break;
case 0xfcc4: case 0xfcc5: case 0xfcc6: case 0xfcc7:
case 0xfc04: case 0xfc05: case 0xfc06: case 0xfc07:
if(_wd1770 && (address&0x00f0) == 0x00c0)
{
if(isReadOperation(operation))
@ -306,7 +310,7 @@ unsigned int Machine::perform_bus_operation(CPU6502::BusOperation operation, uin
_wd1770->set_register(address, *value);
}
break;
case 0xfcc0:
case 0xfc00:
if(_wd1770 && (address&0x00f0) == 0x00c0)
{
if(isReadOperation(operation))