|
@@ -29,8 +29,10 @@
|
|
|
|
|
|
static int bus_type = -1;
|
|
|
static int unit_nr = -1;
|
|
|
-static struct {
|
|
|
+static struct unit {
|
|
|
int cyl;
|
|
|
+ bool_t initialised;
|
|
|
+ bool_t is_flippy;
|
|
|
bool_t motor;
|
|
|
} unit[3];
|
|
|
|
|
@@ -140,13 +142,9 @@ static void step_one_in(void)
|
|
|
|
|
|
static void _set_bus_type(uint8_t type)
|
|
|
{
|
|
|
- int i;
|
|
|
bus_type = type;
|
|
|
unit_nr = -1;
|
|
|
- for (i = 0; i < ARRAY_SIZE(unit); i++) {
|
|
|
- unit[i].cyl = -1;
|
|
|
- unit[i].motor = FALSE;
|
|
|
- }
|
|
|
+ memset(unit, 0, sizeof(unit));
|
|
|
reset_bus();
|
|
|
}
|
|
|
|
|
@@ -163,48 +161,51 @@ static bool_t set_bus_type(uint8_t type)
|
|
|
return TRUE;
|
|
|
}
|
|
|
|
|
|
-static uint8_t floppy_seek(unsigned int cyl)
|
|
|
+static uint8_t floppy_seek(int cyl)
|
|
|
{
|
|
|
- int cur_cyl;
|
|
|
+ struct unit *u;
|
|
|
|
|
|
if (unit_nr < 0)
|
|
|
return ACK_NO_UNIT;
|
|
|
- cur_cyl = unit[unit_nr].cyl;
|
|
|
-
|
|
|
- if ((cyl == 0) || (cur_cyl < 0)) {
|
|
|
+ u = &unit[unit_nr];
|
|
|
|
|
|
+ if (!u->initialised) {
|
|
|
unsigned int i;
|
|
|
for (i = 0; i < 256; i++) {
|
|
|
if (get_trk0() == LOW)
|
|
|
- break;
|
|
|
+ goto found_trk0;
|
|
|
step_one_out();
|
|
|
}
|
|
|
- cur_cyl = 0;
|
|
|
- if (get_trk0() == HIGH) {
|
|
|
- unit[unit_nr].cyl = -1;
|
|
|
- return ACK_NO_TRK0;
|
|
|
- }
|
|
|
-
|
|
|
+ return ACK_NO_TRK0;
|
|
|
+ found_trk0:
|
|
|
+ u->is_flippy = flippy_detect();
|
|
|
+ u->initialised = TRUE;
|
|
|
+ u->cyl = 0;
|
|
|
}
|
|
|
|
|
|
- if (cur_cyl < 0) {
|
|
|
+ if ((cyl < (u->is_flippy ? -8 : 0)) || (cyl > 100))
|
|
|
+ return ACK_BAD_CYLINDER;
|
|
|
|
|
|
- } else if (cur_cyl <= cyl) {
|
|
|
+ flippy_trk0_sensor_disable();
|
|
|
|
|
|
- unsigned int nr = cyl - cur_cyl;
|
|
|
+ if (u->cyl <= cyl) {
|
|
|
+
|
|
|
+ int nr = cyl - u->cyl;
|
|
|
while (nr--)
|
|
|
step_one_in();
|
|
|
|
|
|
} else {
|
|
|
|
|
|
- unsigned int nr = cur_cyl - cyl;
|
|
|
+ int nr = u->cyl - cyl;
|
|
|
while (nr--)
|
|
|
step_one_out();
|
|
|
|
|
|
}
|
|
|
|
|
|
+ flippy_trk0_sensor_enable();
|
|
|
+
|
|
|
delay_ms(delay_params.seek_settle);
|
|
|
- unit[unit_nr].cyl = cyl;
|
|
|
+ u->cyl = cyl;
|
|
|
|
|
|
return ACK_OKAY;
|
|
|
}
|
|
@@ -230,15 +231,37 @@ static void floppy_flux_end(void)
|
|
|
continue;
|
|
|
}
|
|
|
|
|
|
-static void floppy_reset(void)
|
|
|
+static void do_auto_off(void)
|
|
|
{
|
|
|
- floppy_state = ST_inactive;
|
|
|
- auto_off.armed = FALSE;
|
|
|
+ int i;
|
|
|
|
|
|
floppy_flux_end();
|
|
|
|
|
|
+ for (i = 0; i < ARRAY_SIZE(unit); i++) {
|
|
|
+
|
|
|
+ struct unit *u = &unit[i];
|
|
|
+ if (!u->initialised)
|
|
|
+ continue;
|
|
|
+
|
|
|
+ if (u->cyl < 0) {
|
|
|
+ drive_select(i);
|
|
|
+ floppy_seek(0);
|
|
|
+ }
|
|
|
+
|
|
|
+ if (u->motor)
|
|
|
+ drive_motor(i, FALSE);
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
drive_deselect();
|
|
|
|
|
|
+ auto_off.armed = FALSE;
|
|
|
+}
|
|
|
+
|
|
|
+static void floppy_reset(void)
|
|
|
+{
|
|
|
+ floppy_state = ST_inactive;
|
|
|
+ do_auto_off();
|
|
|
act_led(FALSE);
|
|
|
}
|
|
|
|
|
@@ -1089,8 +1112,8 @@ static void process_command(void)
|
|
|
break;
|
|
|
}
|
|
|
case CMD_SEEK: {
|
|
|
- uint8_t cyl = u_buf[2];
|
|
|
- if ((len != 3) || (cyl > 85))
|
|
|
+ int8_t cyl = u_buf[2];
|
|
|
+ if (len != 3)
|
|
|
goto bad_command;
|
|
|
u_buf[1] = floppy_seek(cyl);
|
|
|
goto out;
|
|
@@ -1244,17 +1267,10 @@ static void floppy_configure(void)
|
|
|
|
|
|
void floppy_process(void)
|
|
|
{
|
|
|
- int i, len;
|
|
|
+ int len;
|
|
|
|
|
|
- if (auto_off.armed && (time_since(auto_off.deadline) >= 0)) {
|
|
|
- floppy_flux_end();
|
|
|
- for (i = 0; i < ARRAY_SIZE(unit); i++) {
|
|
|
- if (unit[i].motor)
|
|
|
- drive_motor(i, FALSE);
|
|
|
- }
|
|
|
- drive_deselect();
|
|
|
- auto_off.armed = FALSE;
|
|
|
- }
|
|
|
+ if (auto_off.armed && (time_since(auto_off.deadline) >= 0))
|
|
|
+ do_auto_off();
|
|
|
|
|
|
switch (floppy_state) {
|
|
|
|