e8555c89 Andy McCall 1 month ago
1
#include " VictorFDC.hh"
2
3
#include " DriveMultiplexer.hh"
4
#include " WD2793.hh"
5
6
#include " CacheLine.hh"
7
#include " serialize.hh"
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
namespace openmsx {
27
28
static constexpr int DRIVE_A_MOTOR = 0x01 ;
29
static constexpr int DRIVE_B_MOTOR = 0x02 ;
30
static constexpr int DRIVE_SELECT = 0x04 ;
31
static constexpr int SIDE_SELECT = 0x08 ;
32
static constexpr int DRIVE_DISABLE = 0x10 ;
33
static constexpr int DATA_REQUEST = 0x40 ;
34
static constexpr int INTR_REQUEST = 0x80 ;
35
36
37
VictorFDC:: VictorFDC ( DeviceConfig& config )
38
: WD2793BasedFDC ( config )
39
{
40
41
parseRomVisibility ( config, 0x4000 , 0x4000 ) ;
42
43
reset ( getCurrentTime ( ) ) ;
44
}
45
46
void VictorFDC:: reset ( EmuTime time )
47
{
48
WD2793BasedFDC:: reset ( time ) ;
49
50
51
52
writeMem ( 0x7FFC , DRIVE_DISABLE, time) ;
53
}
54
55
byte VictorFDC:: readMem ( uint16_t address , EmuTime time )
56
{
57
switch ( address) {
58
case 0x7FF8 :
59
return controller. getStatusReg ( time ) ;
60
case 0x7FF9 :
61
return controller. getTrackReg ( time ) ;
62
case 0x7FFA :
63
return controller. getSectorReg ( time ) ;
64
case 0x7FFB :
65
return controller. getDataReg ( time ) ;
66
case 0x7FFC : {
67
byte value = driveControls;
68
if ( controller. getIRQ ( time ) ) value |= INTR_REQUEST;
69
if ( controller. getDTRQ ( time ) ) value |= DATA_REQUEST;
70
value ^= SIDE_SELECT;
71
return value;
72
}
73
default :
74
return VictorFDC:: peekMem ( address, time ) ;
75
}
76
}
77
78
byte VictorFDC:: peekMem ( uint16_t address , EmuTime time ) const
79
{
80
switch ( address) {
81
case 0x7FF8 :
82
return controller. peekStatusReg ( time ) ;
83
case 0x7FF9 :
84
return controller. peekTrackReg ( time ) ;
85
case 0x7FFA :
86
return controller. peekSectorReg ( time ) ;
87
case 0x7FFB :
88
return controller. peekDataReg ( time ) ;
89
case 0x7FFC : {
90
byte value = driveControls;
91
if ( controller. peekIRQ ( time ) ) value |= INTR_REQUEST;
92
if ( controller. peekDTRQ ( time ) ) value |= DATA_REQUEST;
93
value ^= SIDE_SELECT;
94
return value;
95
}
96
default :
97
return MSXFDC:: peekMem ( address, time ) ;
98
}
99
}
100
101
const byte* VictorFDC:: getReadCacheLine ( uint16_t start ) const
102
{
103
if ( ( start & CacheLine:: HIGH) == ( 0x7FF8 & CacheLine:: HIGH) ) {
104
105
return nullptr ;
106
} else {
107
return MSXFDC:: getReadCacheLine ( start ) ;
108
}
109
}
110
111
void VictorFDC:: writeMem ( uint16_t address , byte value , EmuTime time )
112
{
113
switch ( address) {
114
case 0x7FF8 :
115
controller. setCommandReg ( value, time ) ;
116
break ;
117
case 0x7FF9 :
118
controller. setTrackReg ( value, time ) ;
119
break ;
120
case 0x7FFA :
121
controller. setSectorReg ( value, time ) ;
122
break ;
123
case 0x7FFB :
124
controller. setDataReg ( value, time ) ;
125
break ;
126
case 0x7FFC :
127
auto drive
128
= ( ( value & DRIVE_DISABLE) != 0 )
129
? DriveMultiplexer:: Drive:: NONE
130
: ( ( ( value & DRIVE_SELECT) != 0 ) ? DriveMultiplexer:: Drive:: B
131
: DriveMultiplexer:: Drive:: A) ;
132
multiplexer. selectDrive ( drive, time ) ;
133
multiplexer. setSide ( ( value & SIDE_SELECT) != 0 ) ;
134
multiplexer. setMotor ( ( drive == DriveMultiplexer:: Drive:: A) ? ( ( value & DRIVE_A_MOTOR) != 0 ) : ( ( value & DRIVE_B_MOTOR) != 0 ) , time) ;
135
136
driveControls = value & ( DRIVE_A_MOTOR | DRIVE_B_MOTOR | DRIVE_SELECT | SIDE_SELECT | DRIVE_DISABLE) ;
137
break ;
138
}
139
}
140
141
byte* VictorFDC:: getWriteCacheLine ( uint16_t address )
142
{
143
if ( ( address & CacheLine:: HIGH) == ( 0x7FF8 & CacheLine:: HIGH) ) {
144
145
return nullptr ;
146
} else {
147
return unmappedWrite. data ( ) ;
148
}
149
}
150
151
bool VictorFDC:: allowUnaligned ( ) const
152
{
153
154
return true ;
155
}
156
157
158
template < typename Archive>
159
void VictorFDC:: serialize ( Archive& ar , unsigned )
160
{
161
ar. template serializeBase < WD2793BasedFDC> ( * this ) ;
162
ar. serialize ( " driveControls" , driveControls) ;
163
}
164
INSTANTIATE_SERIALIZE_METHODS ( VictorFDC ) ;
165
REGISTER_MSXDEVICE ( VictorFDC, " VictorFDC" ) ;
166
167
}