예제 #1
0
int drive_check_type(unsigned int drive_type, unsigned int dnr)
{
    if (!drive_check_bus(drive_type, iec_available_busses()))
        return 0;

    if (drive_check_dual(drive_type)) {
        if (is_drive1(dnr)) {
            /* Dual drives only supported on even device numbers.  */
            return 0;
        } else {
            if (drive_context[mk_drive1(dnr)]->drive->type != DRIVE_TYPE_NONE)
                /* Disable dual drive if second device is enabled.  */
                return 0;
        }
    } else {
        if (is_drive1(dnr)) {
            if (drive_check_dual(drive_context[mk_drive0(dnr)]->drive->type))
                /* Disable second device if dual drive is enabled.  */
                return drive_type == DRIVE_TYPE_NONE;
        }
    }

    if (machine_drive_rom_check_loaded(drive_type) < 0)
        return 0;

    return 1;
}
예제 #2
0
파일: drive.c 프로젝트: twinaphex/vice-next
/* Update the status bar in the UI.  */
void drive_update_ui_status(void)
{
	int i;

	if (console_mode || vsid_mode)
		return;

	/* Update the LEDs and the track indicators.  */
	for (i = 0; i < DRIVE_NUM; i++)
	{
		drive_t *drive;

		drive = drive_context[i]->drive;
		if (drive->enable || ((i == 1) && drive_context[0]->drive->enable && drive_check_dual(drive_context[0]->drive->type)))
		{
			drive_led_update(drive);

			if (drive->current_half_track != drive->old_half_track)
			{
				drive->old_half_track = drive->current_half_track;
				ui_display_drive_track(i, (i < 2 && drive_context[0]->drive->enable && drive_check_dual(drive_context[0]->drive->type))
						? 0 : 8, drive->current_half_track);
			}
		}
	}
}
예제 #3
0
int drive_check_type(unsigned int drive_type, unsigned int dnr)
{
    if (!drive_check_bus(drive_type, dnr, iec_available_busses()))
        return 0;

    if (drive_check_dual(drive_type)) {
        if (dnr > 0) {
            /* A second dual drive is not supported.  */
            return 0;
        } else {
            if (drive_context[1]->drive->type != DRIVE_TYPE_NONE)
                /* Disable dual drive if second drive is enabled.  */
                return 0;
        }
    }

    /* If the first drive is dual no second drive is supported at all.  */
    if (drive_check_dual(drive_context[0]->drive->type) && dnr > 0)
        return 0;

    if (machine_drive_rom_check_loaded(drive_type) < 0)
        return 0;

    return 1;
}
예제 #4
0
파일: drive.c 프로젝트: twinaphex/vice-next
/* Activate full drive emulation. */
int drive_enable(drive_context_t *drv)
{
    int i, drive_true_emulation = 0;
    unsigned int dnr;
    drive_t *drive;
    unsigned int enabled_drives = 0;

    dnr = drv->mynumber;
    drive = drv->drive;

    /* This must come first, because this might be called before the drive
       initialization.  */
    if (!rom_loaded)
        return -1;

    resources_get_int("DriveTrueEmulation", &drive_true_emulation);

    /* Always disable kernal traps. */
    if (!drive_true_emulation)
        return 0;

    if (drive->type == DRIVE_TYPE_NONE)
        return 0;

    /* Recalculate drive geometry.  */
    if (drive->image != NULL)
        drive_image_attach(drive->image, dnr + 8);

    drivecpu_wake_up(drv);

    /* Make sure the UI is updated.  */
    for (i = 0; i < DRIVE_NUM; i++) {
        unsigned int the_drive;
 
        the_drive = 1 << i;
        if (drive_context[i]->drive->enable) {
            enabled_drives |= the_drive;
            drive_context[i]->drive->old_led_status = -1;
            drive_context[i]->drive->old_half_track = -1;
        }
    }

    /* FIXME: this doesn't care about dual drives anymore */
    drive_set_active_led_color(drive->type, dnr);
    ui_enable_drive_status(enabled_drives,
                           drive_led_color);

#if 0
    /* this is the old code not respecting more than 2 drives */
    ui_enable_drive_status((drive_context[0]->drive->enable
                           ? UI_DRIVE_ENABLE_0 : 0)
                           | ((drive_context[1]->drive->enable
                           || (drive_context[0]->drive->enable
                           && drive_check_dual(drive_context[0]->drive->type))
                           ) ? UI_DRIVE_ENABLE_1 : 0),
                           drive_led_color);
#endif
    return 0;
}
예제 #5
0
파일: drive.c 프로젝트: twinaphex/vice-next
int drive_num_leds(unsigned int dnr)
{
	if (drive_check_old(drive_context[dnr]->drive->type))
		return 2;

	if ((dnr == 1) && drive_check_dual(drive_context[0]->drive->type))
		return 2;

	return 1;
}
예제 #6
0
파일: fdc.c 프로젝트: bobsummerwill/VICE
void fdc_reset(unsigned int fnum, unsigned int drive_type)
{
    fdc_t *thefdc = &fdc[fnum];
    int drive1 = mk_drive1(fnum);
    disk_image_t *saved_image0,
                 *saved_image1;

#ifdef FDC_DEBUG
    log_message(fdc_log, "fdc_reset: drive %d type=%d\n",fnum, drive_type);
#endif

    saved_image0 = fdc[fnum].realimage;
    saved_image1 = NULL;

    /* detach disk images */
    if (thefdc->image) {
        thefdc->wps_change = 0;
        fdc_detach_image(thefdc->image, fnum + 8);
    }
    if (thefdc->num_drives == 2) {
        saved_image1 = fdc[drive1].realimage;
        if (fdc[drive1].image) {
            fdc[drive1].wps_change = 0;
            fdc_detach_image(fdc[drive1].image, drive1 + 8);
        }
    }

    if (drive_check_old(drive_type)) {
        thefdc->drive_type = drive_type;
        thefdc->num_drives = is_drive1(fnum) ? 1 :
                             drive_check_dual(drive_type) ? 2 : 1;
        thefdc->fdc_state = FDC_RESET0;
        alarm_set(thefdc->fdc_alarm, drive_clk[fnum] + 20);
    } else {
        thefdc->drive_type = DRIVE_TYPE_NONE;
        alarm_unset(thefdc->fdc_alarm);
        thefdc->fdc_state = FDC_UNUSED;
        thefdc->num_drives = 0;
    }

    /* re-attach disk images */
    if (saved_image0) {
#ifdef FDC_DEBUG
        printf("ieee/fdc.c:fdc_reset dev %d type %d drive 0 re-attach image %p (drive: %p)\n", fnum+8, drive_type, saved_image0, drive_context[fnum]->drive->image);
#endif
        fdc_attach_image(saved_image0, fnum + 8);
    }
    if (saved_image1) {
#ifdef FDC_DEBUG
        printf("ieee/fdc.c:fdc_reset dev %d type %d drive 1 re-attach image %p (drive: %p)\n", fnum+8, drive_type, saved_image0, drive_context[drive1]->drive->image);
#endif
        fdc_attach_image(saved_image1, drive1 + 8);
    }
}
예제 #7
0
파일: drive.c 프로젝트: twinaphex/vice-next
/* Disable full drive emulation.  */
void drive_disable(drive_context_t *drv)
{
    int i, drive_true_emulation = 0;
    unsigned int dnr;
    drive_t *drive;
    unsigned int enabled_drives = 0;

    dnr = drv->mynumber;
    drive = drv->drive;

    /* This must come first, because this might be called before the true
       drive initialization.  */
    drive->enable = 0;

    resources_get_int("DriveTrueEmulation", &drive_true_emulation);

    if (rom_loaded) {
        drivecpu_sleep(drv);
        machine_drive_port_default(drv);

        drive_gcr_data_writeback(drive);
    }

    /* Make sure the UI is updated.  */
    for (i = 0; i < DRIVE_NUM; i++) {
        unsigned int the_drive;

        the_drive = 1 << i;
        if (drive_context[i]->drive->enable) {
            enabled_drives |= the_drive;
            drive_context[i]->drive->old_led_status = -1;
            drive_context[i]->drive->old_half_track = -1;
        }
    }

    ui_enable_drive_status(enabled_drives,
                           drive_led_color);
#if 0
    ui_enable_drive_status((drive_context[0]->drive->enable
                           ? UI_DRIVE_ENABLE_0 : 0)
                           | ((drive_context[1]->drive->enable
                           || (drive_context[0]->drive->enable
                           && drive_check_dual(drive_context[0]->drive->type))
                           ) ? UI_DRIVE_ENABLE_1 : 0),
                           drive_led_color);
/*
    ui_enable_drive_status((drive_context[0]->drive->enable
                           ? UI_DRIVE_ENABLE_0 : 0)
                           | (drive_context[1]->drive->enable
                           ? UI_DRIVE_ENABLE_1 : 0),
                           drive_led_color);
*/
#endif
}
예제 #8
0
int drive_set_disk_drive_type(unsigned int type, struct drive_context_s *drv)
{
    unsigned int dnr;
    drive_t *drive;
    drive_t *drive1;

    dnr = drv->mynumber;

    if (machine_drive_rom_check_loaded(type) < 0) {
        return -1;
    }

    drive = drv->drive;
    rotation_rotate_disk(drive);

    drivesync_clock_frequency(type, drive);

    rotation_init(0, dnr);
    drive->type = type;
    if (type == DRIVE_TYPE_2000 || type == DRIVE_TYPE_4000) {
        drivecpu65c02_setup_context(drv, 0);
    } else {
        drivecpu_setup_context(drv, 0);
    }
    drive->side = 0;
    machine_drive_rom_setup_image(dnr);
    drivesync_factor(drv);
    drive_set_active_led_color(type, dnr);

    /* set up (relatively) easy detection of dual drives */
    drive1 = drive_context[mk_drive1(dnr)]->drive;
    drive->drive0 = NULL;
    drive1->drive1 = NULL;
    if (is_drive0(dnr) && drive_check_dual(type)) {
        drive->drive1 = drive1;
        drive1->drive0 = drive;
    } else {
        drive->drive1 = NULL;
        drive1->drive0 = NULL;
    }

    if (type == DRIVE_TYPE_2000 || type == DRIVE_TYPE_4000) {
        drivecpu65c02_init(drv, type);
    } else {
        drivecpu_init(drv, type);
    }

    return 0;
}
예제 #9
0
static void store_prb(riot_context_t *riot_context, BYTE byte)
{
    driveriot2_context_t *riot2p;

    riot2p = (driveriot2_context_t *)(riot_context->prv);

    /* bit 3 Act LED 1 */
    /* bit 4 Act LED 0 */
    /* bit 5 Error LED */

    /* 1001 only needs LED 0 and Error LED */
    riot2p->drive->led_status = (byte >> 4) & 0x03;

    if ((is_drive0(riot2p->number)) && (drive_check_dual(riot2p->drive->type))) {
        drive_context[mk_drive1(riot2p->number)]->drive->led_status
            = ((byte & 8) ? 1 : 0) | ((byte & 32) ? 2 : 0);
    }
}
예제 #10
0
static void undump_prb(riot_context_t *riot_context, BYTE byte)
{
    driveriot2_context_t *riot2p;

    riot2p = (driveriot2_context_t *)(riot_context->prv);

    /* bit 3 Act LED 1 */
    /* bit 4 Act LED 0 */
    /* bit 5 Error LED */

    /* 1001 only needs LED 0 and Error LED */
    riot2p->drive->led_status = (byte >> 4) & 0x03;

    if ((is_drive0(riot2p->number)) && (drive_check_dual(riot2p->drive->type))) {
        drive_context[mk_drive1(riot2p->number)]->drive->led_status
            = ((byte & 8) ? 1 : 0) | ((byte & 32) ? 2 : 0);
    }

    if (riot2p->drive->led_status & 1) {
        riot2p->drive->led_active_ticks += *(riot_context->clk_ptr)
                                           - riot2p->drive->led_last_change_clk;
    }
    riot2p->drive->led_last_change_clk = *(riot_context->clk_ptr);
}
예제 #11
0
static int drive_resources_type(int val, void *param)
{
    unsigned int type, dnr;
    int busses;
    drive_t *drive, *drive0;

    dnr = vice_ptr_to_uint(param);
    drive = drive_context[dnr]->drive;

    type = (unsigned int)val;
    busses = iec_available_busses();

    /* if bus for drive type is not allowed, set to default value for bus */
    if (!drive_check_bus(type, busses)) {
        if (busses & IEC_BUS_IEC) {
            type = DRIVE_TYPE_1541;
        } else
        if (busses & IEC_BUS_IEEE) {
            type = DRIVE_TYPE_2031;
        } else {
            type = DRIVE_TYPE_NONE;
        }
    }

    if (is_drive0(dnr)) {
        if (drive_check_dual(type)) {
            int drive1 = mk_drive1(dnr);

            /* dual disk drives disable second emulated unit */
            log_warning(drive->log,
                        "Dual disk drive %d disables emulated drive %d", dnr, drive1);

            drive_resources_type(DRIVE_TYPE_NONE, int_to_void_ptr(drive1));
        }
    } else {
        drive0 = drive_context[mk_drive0(dnr)]->drive;
        if (drive0->enable && drive_check_dual(drive0->type)) {
            /* dual disk drives disable second emulated unit */
            log_warning(drive->log,
                        "Dual disk drive %d disables emulated drive %d", mk_drive0(dnr), dnr);

            type = DRIVE_TYPE_NONE;
        }
    }

    switch (type) {
        case DRIVE_TYPE_1541:
        case DRIVE_TYPE_1541II:
        case DRIVE_TYPE_1551:
        case DRIVE_TYPE_1570:
        case DRIVE_TYPE_1571:
        case DRIVE_TYPE_1571CR:
        case DRIVE_TYPE_1581:
        case DRIVE_TYPE_2000:
        case DRIVE_TYPE_4000:
        case DRIVE_TYPE_2031:
        case DRIVE_TYPE_1001:
        case DRIVE_TYPE_2040:
        case DRIVE_TYPE_3040:
        case DRIVE_TYPE_4040:
        case DRIVE_TYPE_8050:
        case DRIVE_TYPE_8250:
            if (drive->type != type) {
                drive->current_half_track = 2 * 18;
                if ((type == DRIVE_TYPE_1001)
                    || (type == DRIVE_TYPE_8050)
                    || (type == DRIVE_TYPE_8250)) {
                    drive->current_half_track = 2 * 38;
                }
            }
            drive->type = type;
            if (drive_true_emulation) {
                drive->enable = 1;
                drive_enable(drive_context[dnr]);
                /* 1551 drive does not use the IEC bus */
                machine_bus_status_drivetype_set(dnr + 8, drive_check_bus(type,
                                                                          IEC_BUS_IEC));
            } else {
                drive_enable_update_ui(drive_context[dnr]);
            }
            drive_set_disk_drive_type(type, drive_context[dnr]);
            driverom_initialize_traps(drive);
            machine_drive_idling_method(dnr);
            return 0;
        case DRIVE_TYPE_NONE:
            drive->type = type;
            drive_disable(drive_context[dnr]);
            machine_bus_status_drivetype_set(dnr + 8, 0);
            return 0;
        default:
            return -1;
    }
}
예제 #12
0
static int drive0_resources_type(int val, void *param)
{
    unsigned int type;
    int busses;
    drive_t *drive;

    drive = drive_context[0]->drive;
    type = (unsigned int)val;
    busses = iec_available_busses();

    /* if bus for drive type is not allowed, set to default value for bus */
    if (!drive_check_bus(type, 0, busses)) {
        if (busses & IEC_BUS_IEC) {
            type = DRIVE_TYPE_1541;
        } else
        if (busses & IEC_BUS_IEEE) {
            type = DRIVE_TYPE_2031;
        } else
            type = DRIVE_TYPE_NONE;
    }

    if (drive_check_dual(type))
    {
        /* dual disk drives disable second emulated unit */
	#ifdef CELL_DEBUG
	printf("WARNING: Dual disk drive disables second emulated drive\n");
	#endif

        drive1_resources_type(DRIVE_TYPE_NONE, NULL);
    }

    switch (type) {
      case DRIVE_TYPE_1541:
      case DRIVE_TYPE_1541II:
      case DRIVE_TYPE_1551:
      case DRIVE_TYPE_1570:
      case DRIVE_TYPE_1571:
      case DRIVE_TYPE_1571CR:
      case DRIVE_TYPE_1581:
      case DRIVE_TYPE_2031:
      case DRIVE_TYPE_1001:
      case DRIVE_TYPE_2040:
      case DRIVE_TYPE_3040:
      case DRIVE_TYPE_4040:
      case DRIVE_TYPE_8050:
      case DRIVE_TYPE_8250:
        if (drive->type != type) {
            drive->current_half_track = 2 * 18;
            if ((type == DRIVE_TYPE_1001)
                || (type == DRIVE_TYPE_8050)
                || (type == DRIVE_TYPE_8250)) {
                drive->current_half_track = 2 * 38;
            }
        }
        drive->type = type;
        if (drive_true_emulation) {
            drive->enable = 1;
            drive_enable(drive_context[0]);
            /* 1551 drive does not use the IEC bus */
            machine_bus_status_drivetype_set(8, drive_check_bus(type, 0,
                                             IEC_BUS_IEC));
        }
        drive_set_disk_drive_type(type, drive_context[0]);
        driverom_initialize_traps(drive);
        machine_drive_idling_method(0);
        return 0;
      case DRIVE_TYPE_NONE:
        drive->type = type;
        drive_disable(drive_context[0]);
        machine_bus_status_drivetype_set(8, 0);
        return 0;
      default:
        return -1;
    }
}