The FD179X (X=1,2,3,4,5,7) can be considered the end result of both the FD177X and 178X designs. In order to maintain compatibility, the FD177X, FD178X and FD179X were made as close as possible with the instruction set and I/O registers being identical. The 1793 is identical to the 1791 except the Data Access Lines are TRUE (for systems that utilize true data buses). The 1792 and 1794 are "single density only" versions of the 1791 and 1793 respectively. The 1795/7 has a side select output for controlling double sided drives.
The following I/O ports are used to communicate with the FDC
SVI | MSX | Read/Write | Description |
30H | D0H | R | Status register |
30H | D1H | W | Command Register |
31H | D2H | R/W | Track register |
32H | D3H | R/W | Sector register |
33H | D4H | R/W | Data register |
34H | D5H | R | Read INTRQ and DRQ |
34H | D5H | W | Disk select register (bit 0 and 1) |
38H | D7H | W | Density/Side select register (bit 0=density, bit 1=side) |
This 8-bit register assembles serial data from the Read Data input (/RAW READ) during Read operations and transfers serial data to the Write Data output during Write operations.
This 8-bit register is used as a holding register during Disk Read and Write operations. In Disk Read operations the assembled data byte is transferred in parallel to the Data Register from the Data Shift Register. In Disk Write operations information is transferred in parallel from the Data Register to the Data Shift Register.
When executing the Seek command the Data Register holds the address of the desired Track position. This register is loaded from the DAL and gated onto the DAL under processor control.
This 8-bit register holds the track number of the current Read/Write head position. It is incremented by one every time the head is stepped in (towards track 76) and decremeted by one when the head is stepped out (towards track 00). The contents of the register are compared with the recorded track number in the ID field during disk Read, Write and Verify operations. The Track Register can be loaded from or transferred to the DAL. This Register should not be loaded when the device is busy.
This 8-bit register holds the address of the desired sector position. The contents of the register are compared with the recorded sector number in the ID field during disk Read or Write operations. The Sector Register contents can be loaded from or transferred to the DAL. This register should not be loaded when the device is busy.
This 8-bit register holds the command presently being executed. This register should not be loaded when the device is busy unless the new command is a force interrupt. The command register can be loaded from the DAL, but not read onto the DAL.
This 8-bit register holds device Status information. The meaning of the Status bits is a function of the type of command previously executed. This register can be read onto the DAL, but not loaded from the DAL.
The address bits A1 and A0, combined with the signals R/W, are interpreted as selecting the following registers:
A1 A0 Read Write 0 0 Status Register Command Register 0 1 Track Register Track Register 1 0 Sector Register Sector Register 1 1 Data Register Data Register
On Disk Read operations, the Data Request is activated when an assembled serial input byte is transferred in paralled to the Data Register. This bit is cleared when the Data Register is read by the processor. If the Data Register is read after one or more character are lost, by having not transferred into the register prior to processor readout, the Lost Data bit is set in the Status Register. The Read operation continues until the end of sector is reached.
On Disk Write operations the Data Request is activated when the Data Register transfers its contents to the Data Shift Register, and requires a new data byte. It is reset when the Data Register is loaded with new data by the processor. If new data is not loaded at the time the next serial byte is required by the floppy disk, a byte of zeroes is written on the diskette and the Lost Data bit is set in the Status Register.
At the completion of every command an INTRQ is generated. INTRQ is reset by either reading the status register or by loading the command register with a new command. In addition, INTRQ is generated if a Force Interrupt command condition is met.
Command words should only be loaded in the Command Register when the Busy status bit is off (Status bit 0). The one exception is the Force Interrupt command. Whenever a command is being executed, the Busy status bit is set. When a command is completed, an interrupt is generated and the busy status bit is reset. The Status Register indicates whethter the completed command encountered an error or was fault free. For ease of discussion, commands are divided into four types (I, II, III, IV).
Type Command b7 b6 b5 b4 b3 b2 b1 b0 I Restore 0 0 0 0 h V r1 r0 I Seek 0 0 0 1 h V r1 r0 I Step 0 0 1 T h V r1 r0 I Step-In 0 1 0 T h V r1 r0 I Step-Out 0 1 1 T h V r1 r0 II Read Sector 1 0 0 m S E C 0 II Write Sector 1 0 1 m S E C a0 III Read Address 1 1 0 0 0 E 0 0 III Read Track 1 1 1 0 0 E 0 0 III Write Track 1 1 1 1 0 E 0 0 IV Force Interrupt 1 1 0 1 i3 i2 i1 i0
r1 r0 Stepping Motor Rate V Track Number Verify Flag (0: no verify, 1: verify on dest track) h Head Load Flag (1: load head at beginning, 0: unload head) T Track Update Flag (0: no update, 1: update Track Register) a0 Data Address Mark (0: FB, 1: F8 (deleted DAM)) C Side Compare Flag (0: disable side compare, 1: enable side comp) E 15 ms delay (0: no 15ms delay, 1: 15 ms delay) S Side Compare Flag (0: compare for side 0, 1: compare for side 1) m Multiple Record Flag (0: single record, 1: multiple records) i3 i2 i1 i0 Interrupt Condition Flags i3-i0 = 0 Terminate with no interrupt (INTRQ) i3 = 1 Immediate interrupt, requires a reset i2 = 1 Index pulse i1 = 1 Ready to not ready transition i0 = 1 Not ready to ready transition
The type I commands include the Restore, Seek, Step, Step-In and Step-Out commands. Each of the Type I commands contains a rate field r1 r0 which determines the stepping motor rate.
r1 r0 Stepping rate 0 0 6 ms 0 1 12 ms 1 0 20 ms 1 1 30 ms
An optional verification of head position can be performed by settling bit 2 (V=1) in the command word. The track number from the first encountered ID Field is compared against the contents of the Track Register. If the track numbers compare (and the ID Field CRC is correct) the verify operation is complete and an INTRQ is generated with no errors.
Upon receipt of this command, the TR00 input is sampled. If TR00 is active (low) indicating the head is positioned over track 0, the Track Register is loaded with zeroes and an interrupt is generated. If TR00 is not active, stepping pulses at a rate specified by the r1 r0 field are issued until the TR00 input is activated. At this time, the Track Register is loaded with zeroes and an interrupt is generated.
This command assumes that the Track Register contains the track number of the current position of the head and the Data Register contains the desired track number. The FD179X will update the Track Register and issue stepping pulses in the appropriate direction until the contents of the Track Register are equal to the contents of the Data Register. An interrupt is generated at the completion of the command. Note: when using multiple drives, the track register must be updated for the drive selected before seeks are issued.
Upon receipt of this command, the FD179X issues one stepping pulse to the disk drive. The stepping direction motor direction is the same as in the previous step command. An interrupt is generated at the end of the command.
Upon receipt of this command, the FD179X issues one stepping pulse in the direction towards track 76. An interrupt is generated at the end of the command.
Upon receipt of this command, the FD179X issues one stepping pulse in the direction towards track 0. An interrupt is generated at the end of the command.
Type II commands are the Read Sector and Write Sector commands. Prior to loading the Type II command into the Command Register, the computer must load the Sector Register with the desired sector number. Upon receipt of the Type II command, the busy status bit is set. The FD179X must find an ID field with a matching Track number and Sector number, otherwise the Record not found status bit is set and the command is terminated with an interrupt. Each of the Type II commands contains an m flag which determines if multiple records (sectors) are to be read or written. If m=0, a single sector is read or written and an interrupt is generated at the completion of the command. If m=1, multiple records are read or written with the sector register internally updated so that an address verification can occur on the next record. The FD179X will continue to read or write multiple records and update the sector register in numerical ascending sequence until the sector register exceeds the number of sectors on the track or until the Force Interrupt command is loaded into the Command Register. The Type II commands for 1791-94 also contain side select compare flags. When C=0 (bit 1), no comparison is made. When C=1, the LSB of the side number is read off the ID Field of the disk and compared with the contents of the S flag.
Upon receipt of the command, the head is loaded, the busy status bit set and when an ID field is encountered that has the correct track number, correct sector number, correct side number, and correct CRC, the data field is presented to the computer. An DRQ is generated each time a byte is transferred to the DR. At the end of the Read operation, the type of Data Address Mark encountered in the data field is recorded in the Status Register (bit 5).
Upon receipt of the command, the head is loaded, the busy status bit set and when an ID field is encountered that has the correct track number, correct sector number, correct side number, and correct CRC, a DRQ is generated. The FD179X counts off 22 bytes (in double density) from the CRC field and the Write Gate output is made active if the DRQ is serviced (ie. the DR has been loaded by the computer). If DRQ has not been serviced, the command is terminated and the Lost Data status bit is set. If the DRQ has been serviced, 12 bytes of zeroes (in double density) are written to the disk, then the Data Address Mark as determined by the a0 field of the command. The FD179X then writes the data field and generates DRQ's to the computer. If the DRQ is not serviced in time for continuous writing the Lost Data Status bit is set and a byte of zeroes is written on the disk (the command is not terminated). After the last data byte has been written on the disk, the two-byte CRC is computed internally and written on the disk followed by one byte of logic ones.
Upon receipt of the Read Address command, the head is loaded and the Busy Status bit is set. The next encountered ID field is then read in from the disk, and the six data bytes of the ID field are assembled and transferred to the DR, and a DRQ is generated for each byte. The six bytes of the ID field are : Track address, Side number, Sector address, Sector Length, CRC1, CRC2. Although the CRC bytes are transferred to the computer, the FD179X checks for validity and the CRC error status bit is set if there is a CRC error. The track address of the ID field is written into the sector register so that a comparison can be made by the user. At the end of the operation, an interrupt is generated and the Busy status bit is reset.
Upon receipt of the Read Track command, the head is loaded, and the busy status bit is set. Reading starts with the leading edge of the first encountered index pulse and continues until the next index pulse. All gap, header, and data bytes are assembled and transferred to the data register and DRQ's are generated for each byte. The accumulation of bytes is synchronized to each address mark encountered. An interrupt is generated at the completion of the command. The ID Address Mark, ID field, ID CRC bytes, DAM, Data and Data CRC bytes for each sector will be correct. The gap bytes may be read incorrectly during write-splice time because of synchronization.
Upon receipt of the Write Track command, the head is loaded and the Busy Status bit is set. Writing starts with the leading edge of the first encountered index pulse and continues until the next index pulse, at which time the interrupt is activated. The Data Request is activated immediately upon receiving the command, but writing will not start until after the first byte has been loaded into the DR. If the DR has not been loaded by the time the index pulse is encountered, the operation is terminated making the device Not Busy, the Lost Data status bit is set, and the interrupt is activated. If a byte is not present in the DR when needed, a byte of zeroes is substituted. This sequence continues from one index mark to the next index mark. Normally, whatever data pattern appears in the data register is written on the disk with a normal clock pattern. However, if the FD179X detects a data pattern of F5 thru FE in the data register, this is interpreted as data address marks with missing clocks or CRC generation. The CRC generator is initialized when an F5 data byte is about to be transferred (in MFM). An F7 pattern will generate two CRC bytes. As a consequence, the patterns F5 thru FE must not appear in the gaps, data fiels, or ID fiels. Tracks may be formatted with sector lengths of 128, 256, 512 or 1024 bytes.
00 thru F4 Write 00 thru F4 F5 Write A1, preset CRC F6 Write C2 F7 Generate 2 CRC bytes F8 thru FF Write F8 thru FF
Number of Bytes (decimal) Value of byte written 80 4E 12 00 3 F6 (writes C2) 1 FC (index mark) 50 4E +----------- | 12 00 | 3 F5 (writes A1) | 1 FE (ID address mark) | 1 Track number | 1 Side number | 1 Sector Number | 1 01 (sector length) | 1 F7 (2 CRCs written) | 22 4E | 12 00 | 3 F5 (writes A1) | 1 FB (data address mark) | 256 DATA | 1 F7 (2 CRCs written) | 54 4E +----------- to the end 4E
The Forced Interrupt command is generally used to terminate a multiple sector read or write command or insure Type I status register. This command can be loaded into the command register at any time. If there is a current command under execution (busy status bit set), the command will be terminated and the busy status bit reset.
Upon receipt of any command, except the Force Interrupt command, the Busy Status bit is set and the rest of the status bits are updated or cleared for the new command. If the Force Interrupt command is received when there is a current command under execution, the Busy status bit is reset and the rest of the status bits are unchanged. If the ForceInterrupt command is received when there is not a current command under execution, the Busy Status bit is reset and the rest of the status bits are updated or cleared. In this case, Status reflects the Type I commands. The user has the option of reading the status register through program control or using the DRQ line with DMA or interrupt methods. When the DR is read the DRQ bit in the Status register and the DRQ line are automatically reset. A write to the DR also causes both DRQ's to reset. The busy bit in the status may be monitored with a user program to determine when a command is complete, in lieu of using the INTRQ line. When using the INTRQ, a busy status check is not recommended because a read of the status register to determine the condition of busy will reset the INTRQ line.
This table is a summary of the Status Register usage with different commands:
Bit | All type I commands | Read Address | Read Sector | Read Track | Write Sector | Write Track |
7 | Not Ready | Not Ready | Not Ready | Not Ready | Not Ready | Not Ready |
6 | Write Protect | 0 | 0 | 0 | Write Protect | Write Protect |
5 | Head Loaded | 0 | Record Type | 0 | Write Fault | Write Fault |
4 | Seek Error | RNF | RNF | 0 | RNF | 0 |
3 | CRC Error | CRC Error | CRC Error | 0 | CRC Error | 0 |
2 | Track 0 | Lost Data | Lost Data | Lost Data | Lost Data | Lost Data |
1 | Index | DRQ | DRQ | DRQ | DRQ | DRQ |
0 | Busy | Busy | Busy | Busy | Busy | Busy |
Bit | Name | Description |
7 | Not Ready | This bit when set indicates the drive is not ready. When reset it indicates that the drive is ready. This bit is an inverted copy of the Ready input and logically 'ored' with MR. |
6 | Protected | When set, indicates Write Protect is activated. This bit is an inverted copy of /WRPT input. |
5 | Head Loaded | When set, it indicates the head is loaded an engaged. This bit is a logical "and" of HLD and HLT signals. |
4 | Seek Error | When set, the desired track was not verified. This bit is reset 0 when updated. |
3 | CRC Error | CRC encountered in ID field. |
2 | Track 0 | When set, indicates Read/Write head i positioned to Track 0. This bit is an inverted copy of the /TR00 input. |
1 | Index | When set, indicates index mark detected from drive. This bit is an inverted copy of the /IP input. |
0 | Busy | When set command is in progress. When reset no command is in progress. |
Bit | Name | Description |
7 | Not Ready | This bit when set indicates the drive is not ready. When reset it indicates that the drive is ready. This bit is an inverted copy of the Ready input and logically 'ored' with MR. |
6 | Protected | On Read Record or Read Track, not used. On any write: it indicates a Write Protect. This bit is reset when updated. |
5 | Record Type / Write Fault | On Read Record: it indicates the record-type code from data field address mark (1: Deleted Data Mark, 0: Data Mark). On any write: it indicates a Write Fault. This bit is reset when updated. |
4 | Record Not Found (RNF) | When set, it indicates the desired track, sector, or side were not found. This bit is reset when updated. |
3 | CRC Error | if b4 is set, an error is found in one or more ID fields otherwise it indicates error in data field. This bit is reset when updated. |
2 | Lost Data | When set, it indicates the computer did not respond to DRQ in one byte time. This bit is reset to zero when updated. |
1 | Data Request | This bit is a copy of the DRQ output. When set, it indicates the DR is full on a Read operation or the DR is empty on a Write operation. This bit is reset to zero when updated. |
0 | Busy | When set, command is under execution. When reset, no command is under execution. |
Since the floppy disk controller can not set the drive number or density, this must be done by an external circuit. This is an example of how its done on a SVI-3x8 system:
; Sample - Disk and Density select equates DSKSEL EQU 34H ;Addr of disk select & motor control SD0 EQU 00000001B ;Select disk 0 bit SD1 EQU 00000010B ;Select disk 1 bit MOTOR0 EQU 00000100B ;Disk 0 motor on bit MOTOR1 EQU 00001000B ;Disk 1 motor on bit DENSEL EQU 38H ;Addr of density select flag DESMFM EQU 00000000B ;Density MFM bit DESFM EQU 00000001B ;Density FM bit SIDE2 EQU 00000010B ;Side 2 of MFM bit (double & 2)
Flag settings are:
r1 and r2 = 0
h=0
V=1
The step motor rate (r1, r2) is 6 ms for a 3.5-inch floppy disk drive.
If the V flag is set to 1, when the seek is completed, the drive automatically goes into read out mode and the track position is verified. In other words, the track number in the first ID field encountered is compared with the target track number that has been set in the data register. If these track numbers do not match, the Seek Error bit of the status register is set.
When V=0, the head position is not verified. This is convenient for using a disk that as not been initialized. It does not come up in the seek command, but the u flag for the step, step in, and step out commands is usually set to 1.
If this u flag is set to 0, the track register is not updated when the step pulse is output from the FDC. When the FDC receives one of these commands, it sets the Busy bit in the status register to 1, resets the interrupt request signal, and starts the seek or other command. After the seek, if the track position is not being verified, the command ends once the last step pulse is output. Since the result is that there is not enough time for step stability, the host system must use its software to make the floppy disk wait a certain period before reading or writing the track just arrived at. When the seek command is complete, the interrupt request is set and at the same time, the Busy bit in the status register is set to 0. When the CPU reads the status register, it resets the interrupt request signal.