You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: FloppyDriveController.sketch/FloppyDriveController.sketch.ino
+207-8Lines changed: 207 additions & 8 deletions
Original file line number
Diff line number
Diff line change
@@ -78,10 +78,19 @@
78
78
79
79
80
80
81
-
// Paula on the Amiga used to find the SYNC WORDS and then read 0x1900 further WORDS. A dos track is 11968 bytes in size, theritical revolution is 12800 bytes.
82
-
#defineRAW_TRACKDATA_LENGTH (0x1900*2+0x440) // Paula assumed it was 12868 bytes, so we read that, plus thre size of a sectors
81
+
// Paula on the Amiga used to find the SYNC WORDS and then read 0x1900 further WORDS.
82
+
// A dos track is 11968 bytes in size, theritical revolution is 12800 bytes.
83
+
/* The ATARI ST could format a track with up to 11 Sectors, so the AMIGA settings are OK. */
84
+
#defineRAW_TRACKDATA_LENGTH (0x1900*2+0x440) // Paula assumed it was 12868 bytes, so we read that, plus the size of a sector, to find overlap
83
85
84
-
// The current track that the head is over
86
+
/* For the HD (1.4 MBytes) Disks the amount of data should be about 26688: */
87
+
#defineRAW_HD_TRACKDATA_LENGTH (0x1900*2*2+0x440)
88
+
89
+
90
+
/* The current track that the head is over
91
+
(at the beginning this would be unknown and so a
92
+
seek to Track0 should be done first.
93
+
*/
85
94
int currentTrack = 0;
86
95
87
96
// If the drive has been switched on or not
@@ -91,6 +100,9 @@ bool driveEnabled = 0;
91
100
bool inWriteMode = 0;
92
101
93
102
103
+
/* Where there should be a HD Disk been read (1) or a DD and SD Disk (0).*/
104
+
105
+
bool disktypeHD = 0;
94
106
95
107
96
108
@@ -112,6 +124,13 @@ void stepDirectionHead() {
112
124
smalldelay(5);
113
125
digitalWrite(PIN_MOTOR_STEP,HIGH);
114
126
}
127
+
// Step the head once. Do it a bit faster...
128
+
voidstepDirectionHead_fast() {
129
+
smalldelay(4);
130
+
digitalWrite(PIN_MOTOR_STEP,LOW);
131
+
smalldelay(3);
132
+
digitalWrite(PIN_MOTOR_STEP,HIGH);
133
+
}
115
134
116
135
// Prepare serial port - We dont want to use the arduino serial library as we want to use faster speeds and no serial interrupts
117
136
voidprepSerialInterface() {
@@ -276,7 +295,7 @@ bool goToTrack0() {
276
295
digitalWrite(PIN_MOTOR_DIR,MOTOR_TRACK_DECREASE); // Set the direction to go backwards
277
296
int counter=0;
278
297
while (digitalRead(PIN_DETECT_TRACK_0) != LOW) {
279
-
stepDirectionHead(); // Keep moving the head until we see the TRACK 0 detection pin
298
+
stepDirectionHead_fast(); // Keep moving the head until we see the TRACK 0 detection pin
280
299
counter++;
281
300
// If this happens we;ve steps twice as many as needed and still havent found track 0
282
301
if (counter>170) {
@@ -288,7 +307,7 @@ bool goToTrack0() {
288
307
returntrue;
289
308
}
290
309
291
-
// Goto a specific track. During testing it was easier for the track number to be supplied as two ASCII characters, so I left it like this
310
+
// Goto to a specific track. During testing it was easier for the track number to be supplied as two ASCII characters, so I left it like this
292
311
boolgotoTrackX() {
293
312
// Read the bytes
294
313
byte track1 = readByteFromUART();
@@ -562,7 +581,167 @@ void readTrackDataFast() {
562
581
TCCR2B = 0; // No Clock (turn off)
563
582
}
564
583
584
+
// Read the track for a HD disk
585
+
voidreadTrackDataFast_HD() {
586
+
// Configure timer 2 just as a counter in NORMAL mode
587
+
TCCR2A = 0 ; // No physical output port pins and normal operation
588
+
TCCR2B = bit(CS20); // Precale = 1
589
+
590
+
// First wait for the serial port to be available
591
+
while(!(UCSR0A & (1<<UDRE0)));
592
+
593
+
// Signal we're active
594
+
digitalWrite(PIN_ACTIVITY_LED,HIGH);
595
+
596
+
// Force data to be stored in a register
597
+
registerunsignedchar DataOutputByte = 0;
598
+
599
+
// While the INDEX pin is high wait if the other end requires us to
600
+
if (readByteFromUART())
601
+
while (PIN_INDEX_PORT & PIN_INDEX_MASK) {};
602
+
603
+
// Prepare the two counter values as follows:
604
+
TCNT2=0; // Reset the counter
605
+
606
+
registerunsignedchar counter;
607
+
long totalBits=0;
608
+
long target = ((long)RAW_HD_TRACKDATA_LENGTH)*(long)8;
609
+
610
+
while (totalBits<target) {
611
+
for (registerunsignedchar bits=0; bits<4; bits++) {
612
+
// Wait while pin is high
613
+
614
+
while (PIN_READ_DATA_PORT & PIN_READ_DATA_MASK) {};
615
+
counter = TCNT2, TCNT2 = 0; // reset - must be done with a COMMA
616
+
617
+
DataOutputByte<<=2;
618
+
619
+
// DO NOT USE BRACES HERE, use the "," or the optomiser messes it up
620
+
if (counter<40) DataOutputByte|=B00000001,totalBits+=2; else// this accounts for just a '1' or a '01' as two '1' arent allowed in a row
621
+
if (counter>55) DataOutputByte|=B00000011,totalBits+=4; else DataOutputByte|=B00000010,totalBits+=3;
622
+
623
+
// Wait until pin is high again
624
+
while (!(PIN_READ_DATA_PORT & PIN_READ_DATA_MASK)) {};
625
+
}
626
+
UDR0 = DataOutputByte;
627
+
}
628
+
// Because of the above rules the actual valid two-bit sequences output are 01, 10 and 11, so we use 00 to say "END OF DATA"
629
+
writeByteToUART(0);
565
630
631
+
// turn off the status LED
632
+
digitalWrite(PIN_ACTIVITY_LED,LOW);
633
+
634
+
// Disable the counter
635
+
TCCR2B = 0; // No Clock (turn off)
636
+
}
637
+
638
+
staticchar *i2a(unsignedint i, char *a, unsigned r) {
0 commit comments