openMSX
SVIFDC.cc
Go to the documentation of this file.
1#include "SVIFDC.hh"
2#include "serialize.hh"
3
4// Floppy disk controller FD1793
5//
6// 30H Command to FDC
7// 30H Status from FDC
8// 31H Track register
9// 32H Sector register
10// 33H Data register
11//
12// 34H Address of INTRQ and DRQ
13// 10000000B Interrupt request bit
14// 01000000B Data request bit
15//
16// 34H Address of disk select and motor control
17// 00000001B Select disk 0 bit
18// 00000010B Select disk 1 bit
19// 00000100B Disk 0 motor on bit
20// 00001000B Disk 1 motor on bit
21//
22// 38H Address of density select flag
23// 00000000B Density MFM bit
24// 00000001B Density FM bit
25// 00000010B Select second side
26
27namespace openmsx {
28
30 : WD2793BasedFDC(config, "", false) // doesn't require a <rom>
31{
32}
33
34byte SVIFDC::readIO(word port, EmuTime::param time)
35{
36 switch (port & 0x07) {
37 case 0:
38 return controller.getStatusReg(time);
39 case 1:
40 return controller.getTrackReg(time);
41 case 2:
42 return controller.getSectorReg(time);
43 case 3:
44 return controller.getDataReg(time);
45 case 4:
46 return (controller.getIRQ (time) ? 0x80 : 0x00) |
47 (controller.getDTRQ(time) ? 0x40 : 0x00);
48 }
49 return 255;
50}
51
52byte SVIFDC::peekIO(word port, EmuTime::param time) const
53{
54 switch (port & 0x07) {
55 case 0:
56 return controller.peekStatusReg(time);
57 case 1:
58 return controller.peekTrackReg(time);
59 case 2:
60 return controller.peekSectorReg(time);
61 case 3:
62 return controller.peekDataReg(time);
63 case 4:
64 return (controller.peekIRQ (time) ? 0x80 : 0x00) |
65 (controller.peekDTRQ(time) ? 0x40 : 0x00);
66 }
67 return 255;
68}
69
70void SVIFDC::writeIO(word port, byte value, EmuTime::param time)
71{
72 switch (port & 0x0F) {
73 case 0:
74 controller.setCommandReg(value, time);
75 break;
76 case 1:
77 controller.setTrackReg(value, time);
78 break;
79 case 2:
80 controller.setSectorReg(value, time);
81 break;
82 case 3:
83 controller.setDataReg(value, time);
84 break;
85 case 4: {
86 // bit 0: drive select A
87 // bit 1: drive select B
88 // bit 2: motor on drive A
89 // bit 3: motor on drive B
90 auto [drive, motor] = [&]() -> std::pair<DriveMultiplexer::DriveNum, bool> {
91 switch (value & 0x03) {
92 case 1:
93 return {DriveMultiplexer::DRIVE_A, value & 0x04};
94 case 2:
95 return {DriveMultiplexer::DRIVE_B, value & 0x08};
96 default:
97 // No drive selected or two drives at same time
98 // In a real machine you must take care to do not select more
99 // than one drive at the same time (you could get data
100 // collision).
101 return {DriveMultiplexer::NO_DRIVE, false};
102 }
103 }();
104 multiplexer.selectDrive(drive, time);
105 multiplexer.setMotor(motor, time);
106 break;
107 }
108 case 8:
109 // bit 0: density flag (1=single, 0=double)
110 // bit 1: side select
111 // TODO density flag not yet supported
112 multiplexer.setSide((value & 0x02) != 0);
113 break;
114 }
115}
116
117template<typename Archive>
118void SVIFDC::serialize(Archive& ar, unsigned /*version*/)
119{
120 ar.template serializeBase<WD2793BasedFDC>(*this);
121}
124
125} // namespace openmsx
#define REGISTER_MSXDEVICE(CLASS, NAME)
Definition MSXDevice.hh:354
void setMotor(bool status, EmuTime::param time) override
Set motor on/off.
void selectDrive(DriveNum num, EmuTime::param time)
void setSide(bool side) override
Side select.
byte peekIO(word port, EmuTime::param time) const override
Read a byte from a given IO port.
Definition SVIFDC.cc:52
byte readIO(word port, EmuTime::param time) override
Read a byte from an IO port at a certain time from this device.
Definition SVIFDC.cc:34
SVIFDC(const DeviceConfig &config)
Definition SVIFDC.cc:29
void serialize(Archive &ar, unsigned version)
Definition SVIFDC.cc:118
void writeIO(word port, byte value, EmuTime::param time) override
Write a byte to a given IO port at a certain time to this device.
Definition SVIFDC.cc:70
DriveMultiplexer multiplexer
uint8_t peekDataReg(EmuTime::param time) const
Definition WD2793.cc:314
bool peekIRQ(EmuTime::param time) const
Definition WD2793.cc:99
uint8_t getStatusReg(EmuTime::param time)
Definition WD2793.cc:159
void setTrackReg(uint8_t value, EmuTime::param time)
Definition WD2793.cc:205
void setSectorReg(uint8_t value, EmuTime::param time)
Definition WD2793.cc:220
uint8_t getTrackReg(EmuTime::param time) const
Definition WD2793.cc:210
uint8_t peekSectorReg(EmuTime::param time) const
Definition WD2793.cc:230
bool peekDTRQ(EmuTime::param time) const
Definition WD2793.cc:84
void setCommandReg(uint8_t value, EmuTime::param time)
Definition WD2793.cc:111
uint8_t peekTrackReg(EmuTime::param time) const
Definition WD2793.cc:215
bool getDTRQ(EmuTime::param time) const
Definition WD2793.cc:79
uint8_t peekStatusReg(EmuTime::param time) const
Definition WD2793.cc:199
uint8_t getDataReg(EmuTime::param time)
Definition WD2793.cc:249
void setDataReg(uint8_t value, EmuTime::param time)
Definition WD2793.cc:235
bool getIRQ(EmuTime::param time) const
Definition WD2793.cc:94
uint8_t getSectorReg(EmuTime::param time) const
Definition WD2793.cc:225
This file implemented 3 utility functions:
Definition Autofire.cc:9
uint16_t word
16 bit unsigned integer
Definition openmsx.hh:29
#define INSTANTIATE_SERIALIZE_METHODS(CLASS)