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
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
bool peekIRQ(EmuTime::param time) const
Definition: WD2793.cc:108
byte peekStatusReg(EmuTime::param time) const
Definition: WD2793.cc:208
byte getTrackReg(EmuTime::param time) const
Definition: WD2793.cc:219
byte getDataReg(EmuTime::param time)
Definition: WD2793.cc:258
byte getSectorReg(EmuTime::param time) const
Definition: WD2793.cc:234
bool peekDTRQ(EmuTime::param time) const
Definition: WD2793.cc:93
bool getDTRQ(EmuTime::param time) const
Definition: WD2793.cc:88
byte getStatusReg(EmuTime::param time)
Definition: WD2793.cc:168
byte peekTrackReg(EmuTime::param time) const
Definition: WD2793.cc:224
void setTrackReg(byte value, EmuTime::param time)
Definition: WD2793.cc:214
void setDataReg(byte value, EmuTime::param time)
Definition: WD2793.cc:244
byte peekDataReg(EmuTime::param time) const
Definition: WD2793.cc:323
void setCommandReg(byte value, EmuTime::param time)
Definition: WD2793.cc:120
bool getIRQ(EmuTime::param time) const
Definition: WD2793.cc:103
void setSectorReg(byte value, EmuTime::param time)
Definition: WD2793.cc:229
byte peekSectorReg(EmuTime::param time) const
Definition: WD2793.cc:239
This file implemented 3 utility functions:
Definition: Autofire.cc:9
REGISTER_MSXDEVICE(ChakkariCopy, "ChakkariCopy")
uint16_t word
16 bit unsigned integer
Definition: openmsx.hh:29
#define INSTANTIATE_SERIALIZE_METHODS(CLASS)
Definition: serialize.hh:1009