(mess) upd765: Add read fm sector support [O. Galibert]

This commit is contained in:
Olivier Galibert 2012-11-16 09:16:15 +00:00
parent 2aa1e82537
commit efe49873d4
6 changed files with 135 additions and 13 deletions

View File

@ -23,6 +23,7 @@ const device_type FLOPPY_525_DD = &device_creator<floppy_525_dd>;
const device_type FLOPPY_525_QD = &device_creator<floppy_525_qd>;
const device_type FLOPPY_525_HD = &device_creator<floppy_525_hd>;
const device_type FLOPPY_8_SSSD = &device_creator<floppy_8_sssd>;
const device_type FLOPPY_8_DSDD = &device_creator<floppy_8_dsdd>;
floppy_connector::floppy_connector(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) :
device_t(mconfig, FLOPPY_CONNECTOR, "Floppy drive connector abstraction", tag, owner, clock),
@ -174,6 +175,7 @@ void floppy_image_device::commit_image()
void floppy_image_device::device_start()
{
rpm = 0;
motor_always_on = false;
setup_characteristics();
idx = 0;
@ -194,6 +196,8 @@ void floppy_image_device::device_reset()
revolution_start_time = attotime::never;
revolution_count = 0;
mon = 1;
if(motor_always_on)
mon_w(0);
}
void floppy_image_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr)
@ -1032,7 +1036,8 @@ void floppy_8_sssd::setup_characteristics()
form_factor = floppy_image::FF_8;
tracks = 77;
sides = 1;
set_rpm(300);
motor_always_on = true;
set_rpm(360);
}
void floppy_8_sssd::handled_variants(UINT32 *variants, int &var_count) const
@ -1040,3 +1045,29 @@ void floppy_8_sssd::handled_variants(UINT32 *variants, int &var_count) const
var_count = 0;
variants[var_count++] = floppy_image::SSSD;
}
floppy_8_dsdd::floppy_8_dsdd(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) :
floppy_image_device(mconfig, FLOPPY_8_DSDD, "8\" double density double sided floppy drive", tag, owner, clock)
{
}
floppy_8_dsdd::~floppy_8_dsdd()
{
}
void floppy_8_dsdd::setup_characteristics()
{
form_factor = floppy_image::FF_8;
tracks = 77;
sides = 2;
motor_always_on = true;
set_rpm(360);
}
void floppy_8_dsdd::handled_variants(UINT32 *variants, int &var_count) const
{
var_count = 0;
variants[var_count++] = floppy_image::SSSD;
variants[var_count++] = floppy_image::SSDD;
variants[var_count++] = floppy_image::DSDD;
}

View File

@ -110,6 +110,7 @@ protected:
int tracks; /* addressable tracks */
int sides; /* number of heads */
UINT32 form_factor; /* 3"5, 5"25, etc */
bool motor_always_on;
/* state of input lines */
int dir; /* direction */
@ -282,6 +283,17 @@ protected:
virtual void setup_characteristics();
};
class floppy_8_dsdd : public floppy_image_device {
public:
floppy_8_dsdd(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
virtual ~floppy_8_dsdd();
virtual void handled_variants(UINT32 *variants, int &var_count) const;
virtual void device_config_complete() { m_shortname = "floppy_8_dsdd"; }
virtual const char *image_interface() const { return "floppy_8"; }
protected:
virtual void setup_characteristics();
};
class floppy_connector: public device_t,
public device_slot_interface
{
@ -314,5 +326,6 @@ extern const device_type FLOPPY_525_DD;
extern const device_type FLOPPY_525_QD;
extern const device_type FLOPPY_525_HD;
extern const device_type FLOPPY_8_SSSD;
extern const device_type FLOPPY_8_DSDD;
#endif /* FLOPPY_H */

View File

@ -475,9 +475,9 @@ bool imd_format::load(io_generic *io, UINT32 form_factor, floppy_image *image)
int cpos;
UINT16 crc;
// sync and IDAM and gap 2
for(int j=0; j< 6; j++) fm_w(track_data, tpos, 8, 0xff);
for(int j=0; j< 6; j++) fm_w(track_data, tpos, 8, 0x00);
cpos = tpos;
raw_w(track_data, tpos, 8, 0xf57e);
raw_w(track_data, tpos, 16, 0xf57e);
fm_w (track_data, tpos, 8, tnum ? tnum[i] : track);
fm_w (track_data, tpos, 8, hnum ? hnum[i] : head);
fm_w (track_data, tpos, 8, snum[i]);
@ -491,9 +491,9 @@ bool imd_format::load(io_generic *io, UINT32 form_factor, floppy_image *image)
else {
// sync, DAM, data and gap 3
for(int j=0; j< 6; j++) fm_w(track_data, tpos, 8, 0xff);
for(int j=0; j< 6; j++) fm_w(track_data, tpos, 8, 0x00);
cpos = tpos;
raw_w(track_data, tpos, 8, stype == 3 || stype == 4 || stype == 7 || stype == 8 ? 0xf56a : 0xf56f);
raw_w(track_data, tpos, 16, stype == 3 || stype == 4 || stype == 7 || stype == 8 ? 0xf56a : 0xf56f);
if(stype == 2 || stype == 4 || stype == 6 || stype == 8) {
for(int j=0; j<size; j++) fm_w(track_data, tpos, 8, img[pos]);
pos++;

View File

@ -613,7 +613,7 @@ static const floppy_format_type apc_floppy_formats[] = {
};
static SLOT_INTERFACE_START( apc_floppies )
SLOT_INTERFACE( "8sd", FLOPPY_8_SSSD ) // TODO: Ok?
SLOT_INTERFACE( "8", FLOPPY_8_DSDD )
SLOT_INTERFACE_END
PALETTE_INIT_MEMBER(apc_state,apc)
@ -641,8 +641,8 @@ static MACHINE_CONFIG_START( apc, apc_state )
MCFG_I8237_ADD("8237dma", MAIN_CLOCK, dma8237_config)
MCFG_UPD765A_ADD("upd765", true, true)
MCFG_FLOPPY_DRIVE_ADD("upd765:0", apc_floppies, "8sd", 0, apc_floppy_formats)
MCFG_FLOPPY_DRIVE_ADD("upd765:1", apc_floppies, "8sd", 0, apc_floppy_formats)
MCFG_FLOPPY_DRIVE_ADD("upd765:0", apc_floppies, "8", 0, apc_floppy_formats)
MCFG_FLOPPY_DRIVE_ADD("upd765:1", apc_floppies, "8", 0, apc_floppy_formats)
/* video hardware */
MCFG_SCREEN_ADD("screen", RASTER)

View File

@ -195,7 +195,7 @@ void upd765_family_device::ready_w(bool _ready)
bool upd765_family_device::get_ready(int fid)
{
if(ready_connected)
return flopi[fid].dev ? flopi[fid].dev->ready_r() : false;
return flopi[fid].dev ? !flopi[fid].dev->ready_r() : false;
return external_ready;
}
@ -438,8 +438,11 @@ void upd765_family_device::disable_transfer()
void upd765_family_device::fifo_push(UINT8 data, bool internal)
{
if(fifo_pos == 16) {
if(internal)
if(internal) {
if(!(st1 & ST1_OR))
logerror("%s: Fifo overrun\n", tag());
st1 |= ST1_OR;
}
return;
}
fifo[fifo_pos++] = data;
@ -456,8 +459,11 @@ void upd765_family_device::fifo_push(UINT8 data, bool internal)
UINT8 upd765_family_device::fifo_pop(bool internal)
{
if(!fifo_pos) {
if(internal)
if(internal) {
if(!(st1 & ST1_OR))
logerror("%s: Fifo underrun\n", tag());
st1 |= ST1_OR;
}
return 0;
}
UINT8 r = fifo[0];
@ -668,6 +674,30 @@ void upd765_family_device::live_run(attotime limit)
break;
}
case SEARCH_ADDRESS_MARK_HEADER_FM:
if(read_one_bit(limit))
return;
#if 0
fprintf(stderr, "%s: shift = %04x data=%02x c=%d\n", tts(cur_live.tm).cstr(), cur_live.shift_reg,
(cur_live.shift_reg & 0x4000 ? 0x80 : 0x00) |
(cur_live.shift_reg & 0x1000 ? 0x40 : 0x00) |
(cur_live.shift_reg & 0x0400 ? 0x20 : 0x00) |
(cur_live.shift_reg & 0x0100 ? 0x10 : 0x00) |
(cur_live.shift_reg & 0x0040 ? 0x08 : 0x00) |
(cur_live.shift_reg & 0x0010 ? 0x04 : 0x00) |
(cur_live.shift_reg & 0x0004 ? 0x02 : 0x00) |
(cur_live.shift_reg & 0x0001 ? 0x01 : 0x00),
cur_live.bit_counter);
#endif
if(cur_live.shift_reg == 0xf57e) {
cur_live.crc = 0xef21;
cur_live.data_separator_phase = false;
cur_live.bit_counter = 0;
cur_live.state = READ_ID_BLOCK;
}
break;
case READ_ID_BLOCK: {
if(read_one_bit(limit))
return;
@ -757,6 +787,34 @@ void upd765_family_device::live_run(attotime limit)
cur_live.state = IDLE;
return;
case SEARCH_ADDRESS_MARK_DATA_FM:
if(read_one_bit(limit))
return;
#if 0
fprintf(stderr, "%s: shift = %04x data=%02x c=%d.%x\n", tts(cur_live.tm).cstr(), cur_live.shift_reg,
(cur_live.shift_reg & 0x4000 ? 0x80 : 0x00) |
(cur_live.shift_reg & 0x1000 ? 0x40 : 0x00) |
(cur_live.shift_reg & 0x0400 ? 0x20 : 0x00) |
(cur_live.shift_reg & 0x0100 ? 0x10 : 0x00) |
(cur_live.shift_reg & 0x0040 ? 0x08 : 0x00) |
(cur_live.shift_reg & 0x0010 ? 0x04 : 0x00) |
(cur_live.shift_reg & 0x0004 ? 0x02 : 0x00) |
(cur_live.shift_reg & 0x0001 ? 0x01 : 0x00),
cur_live.bit_counter >> 4, cur_live.bit_counter & 15);
#endif
if(cur_live.bit_counter > 23*16) {
live_delay(SEARCH_ADDRESS_MARK_DATA_FAILED);
return;
}
if(cur_live.bit_counter >= 11*16 && (cur_live.shift_reg == 0xf56a || cur_live.shift_reg == 0xf56f)) {
cur_live.crc = cur_live.shift_reg == 0xf56a ? 0x8fe7 : 0xbf84;
cur_live.data_separator_phase = false;
cur_live.bit_counter = 0;
cur_live.state = READ_SECTOR_DATA;
}
break;
case READ_SECTOR_DATA: {
if(read_one_bit(limit))
return;
@ -1331,7 +1389,7 @@ void upd765_family_device::read_data_continue(floppy_info &fi)
case SEEK_DONE:
fi.counter = 0;
fi.sub_state = SCAN_ID;
live_start(fi, SEARCH_ADDRESS_MARK_HEADER);
live_start(fi, command[0] & 0x40 ? SEARCH_ADDRESS_MARK_HEADER : SEARCH_ADDRESS_MARK_HEADER_FM);
return;
case SCAN_ID:
@ -1364,7 +1422,7 @@ void upd765_family_device::read_data_continue(floppy_info &fi)
sector_size = calc_sector_size(cur_live.idbuf[3]);
fifo_expect(sector_size, false);
fi.sub_state = SECTOR_READ;
live_start(fi, SEARCH_ADDRESS_MARK_DATA);
live_start(fi, command[0] & 0x40 ? SEARCH_ADDRESS_MARK_DATA : SEARCH_ADDRESS_MARK_DATA_FM);
return;
case SCAN_ID_FAILED:
@ -2019,6 +2077,23 @@ void upd765_family_device::live_write_mfm(UINT8 mfm)
// logerror("write %02x %04x %04x\n", mfm, cur_live.crc, raw);
}
void upd765_family_device::live_write_fm(UINT8 fm)
{
bool context = cur_live.data_bit_context;
UINT16 raw = 0;
for(int i=0; i<8; i++) {
bool bit = fm & (0x80 >> i);
raw |= 0x8000 >> (2*i);
if(bit)
raw |= 0x4000 >> (2*i);
context = bit;
}
cur_live.data_reg = fm;
cur_live.shift_reg = raw;
cur_live.data_bit_context = context;
// logerror("write %02x %04x %04x\n", fm, cur_live.crc, raw);
}
bool upd765_family_device::sector_matches() const
{
return

View File

@ -208,10 +208,12 @@ protected:
// Live states
SEARCH_ADDRESS_MARK_HEADER,
SEARCH_ADDRESS_MARK_HEADER_FM,
READ_HEADER_BLOCK_HEADER,
READ_DATA_BLOCK_HEADER,
READ_ID_BLOCK,
SEARCH_ADDRESS_MARK_DATA,
SEARCH_ADDRESS_MARK_DATA_FM,
SEARCH_ADDRESS_MARK_DATA_FAILED,
READ_SECTOR_DATA,
READ_SECTOR_DATA_BYTE,
@ -374,6 +376,7 @@ protected:
void live_sync();
void live_run(attotime limit = attotime::never);
void live_write_raw(UINT16 raw);
void live_write_fm(UINT8 fm);
void live_write_mfm(UINT8 mfm);
bool read_one_bit(attotime limit);