From a0c70ecb0c74920aa92065e7a218ca2b2738aa12 Mon Sep 17 00:00:00 2001 From: Olivier Galibert Date: Tue, 20 Nov 2012 20:33:37 +0000 Subject: [PATCH] pc floppies: Merge the common parts of d88/imd [O. Galibert] --- src/lib/formats/d88_dsk.c | 91 +++++----------------- src/lib/formats/flopimg.c | 159 ++++++++++++++++++++++++++++++++++++++ src/lib/formats/flopimg.h | 15 ++++ src/lib/formats/imd_dsk.c | 157 ++++++++----------------------------- 4 files changed, 228 insertions(+), 194 deletions(-) diff --git a/src/lib/formats/d88_dsk.c b/src/lib/formats/d88_dsk.c index 5da599891c4..6fa5d6a93e7 100644 --- a/src/lib/formats/d88_dsk.c +++ b/src/lib/formats/d88_dsk.c @@ -504,7 +504,6 @@ bool d88_format::load(io_generic *io, UINT32 form_factor, floppy_image *image) if(!head_count) return false; - UINT32 *track_data = global_alloc_array(UINT32, cell_count+10000); UINT32 track_pos[164]; io_generic_read(io, track_pos, 32, 164*4); @@ -514,97 +513,49 @@ bool d88_format::load(io_generic *io, UINT32 form_factor, floppy_image *image) if(!pos) continue; + desc_pc_sector sects[256]; UINT8 sect_data[65536]; - int tpos = 0; - - // gap 4a , IAM and gap 1 - for(int i=0; i<80; i++) mfm_w(track_data, tpos, 8, 0x4e); - for(int i=0; i<12; i++) mfm_w(track_data, tpos, 8, 0x00); - for(int i=0; i< 3; i++) raw_w(track_data, tpos, 16, 0x5224); - mfm_w(track_data, tpos, 8, 0xfc); - for(int i=0; i<50; i++) mfm_w(track_data, tpos, 8, 0x4e); - - // Read all sector headers to compute the available and expected size for gap3 + int sdatapos = 0; int sector_count = 1; - int gap3 = 84; - int etpos = tpos; - int rpos = pos; - for(int i=0; i cell_count) - throw emu_fatalerror("d88_format: Incorrect layout on track %d head %d, expected_size=%d, current_size=%d", track, head, cell_count, etpos); - - if(etpos + gap3*16*(sector_count-1) > cell_count) - gap3 = (cell_count - etpos) / 16 / (sector_count-1); - - // Build the track for(int i=0; i> (16+tpos-cell_count)); - - generate_track_from_levels(track, head, track_data, cell_count, 0, image); + build_pc_track_mfm(track, head, image, cell_count, sector_count, sects, calc_default_pc_gap3_size(form_factor, sects[0].actual_size)); } - global_free(track_data); return true; } bool d88_format::save(io_generic *io, floppy_image *image) { - return true; + return false; } bool d88_format::supports_save() const { - return true; + return false; } const floppy_format_type FLOPPY_D88_FORMAT = &floppy_image_format_creator; diff --git a/src/lib/formats/flopimg.c b/src/lib/formats/flopimg.c index b445b286469..2ad7f45e0b8 100644 --- a/src/lib/formats/flopimg.c +++ b/src/lib/formats/flopimg.c @@ -2463,3 +2463,162 @@ void floppy_image_format_t::get_track_data_fm_pc(int track, int head, floppy_ima memset(sd, 0, sector_size); } } + +int floppy_image_format_t::calc_default_pc_gap3_size(UINT32 form_factor, int sector_size) +{ + return + form_factor == floppy_image::FF_8 ? 25 : + sector_size < 512 ? + (form_factor == floppy_image::FF_35 ? 54 : 50) : + (form_factor == floppy_image::FF_35 ? 84 : 80); +} + +void floppy_image_format_t::build_wd_track_fm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_1, int gap_2) +{ + build_pc_track_fm(track, head, image, cell_count, sector_count, sects, gap_3, -1, gap_1, gap_2); +} + +void floppy_image_format_t::build_wd_track_mfm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_1, int gap_2) +{ + build_pc_track_mfm(track, head, image, cell_count, sector_count, sects, gap_3, -1, gap_1, gap_2); +} + +void floppy_image_format_t::build_pc_track_fm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_4a, int gap_1, int gap_2) +{ + UINT32 *track_data = global_alloc_array(UINT32, cell_count+10000); + int tpos = 0; + + // gap 4a , IAM and gap 1 + if(gap_4a != -1) { + for(int i=0; i cell_count) + throw emu_fatalerror("Incorrect layout on track %d head %d, expected_size=%d, current_size=%d", track, head, cell_count, etpos); + + if(etpos + gap_3*16*(sector_count-1) > cell_count) + gap_3 = (cell_count - etpos) / 16 / (sector_count-1); + + // Build the track + for(int i=0; i> (16+tpos-cell_count)); + + generate_track_from_levels(track, head, track_data, cell_count, 0, image); + global_free(track_data); +} + +void floppy_image_format_t::build_pc_track_mfm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_4a, int gap_1, int gap_2) +{ + UINT32 *track_data = global_alloc_array(UINT32, cell_count+10000); + int tpos = 0; + + // gap 4a , IAM and gap 1 + if(gap_4a != -1) { + for(int i=0; i cell_count) + throw emu_fatalerror("Incorrect layout on track %d head %d, expected_size=%d, current_size=%d", track, head, cell_count, etpos); + + if(etpos + gap_3*16*(sector_count-1) > cell_count) + gap_3 = (cell_count - etpos) / 16 / (sector_count-1); + + // Build the track + for(int i=0; i> (16+tpos-cell_count)); + + generate_track_from_levels(track, head, track_data, cell_count, 0, image); + global_free(track_data); +} + diff --git a/src/lib/formats/flopimg.h b/src/lib/formats/flopimg.h index a51cb8570aa..2b93f5a84e3 100644 --- a/src/lib/formats/flopimg.h +++ b/src/lib/formats/flopimg.h @@ -469,6 +469,21 @@ protected: const UINT8 *data; //!< Data within this sector }; + struct desc_pc_sector { + UINT8 track, head, sector, size; + int actual_size; + UINT8 *data; + bool deleted; + bool bad_crc; + }; + + int calc_default_pc_gap3_size(UINT32 form_factor, int sector_size); + void build_wd_track_fm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_1, int gap_2); + void build_wd_track_mfm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_1, int gap_2=22); + void build_pc_track_fm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_4a=40, int gap_1=26, int gap_2=11); + void build_pc_track_mfm(int track, int head, floppy_image *image, int cell_count, int sector_count, const desc_pc_sector *sects, int gap_3, int gap_4a=80, int gap_1=50, int gap_2=22); + + //! @brief Extract standard sectors from a regenerated bitstream. //! Sectors must point to an array of 256 desc_xs. diff --git a/src/lib/formats/imd_dsk.c b/src/lib/formats/imd_dsk.c index d1cdc8704e2..b18f5f41659 100644 --- a/src/lib/formats/imd_dsk.c +++ b/src/lib/formats/imd_dsk.c @@ -414,7 +414,7 @@ bool imd_format::load(io_generic *io, UINT32 form_factor, floppy_image *image) if(ssize == 0xff) throw emu_fatalerror("imd_format: Unsupported variable sector size on track %d head %d", track, head); - UINT32 size = ssize < 7 ? 128 << ssize : 8192; + UINT32 actual_size = ssize < 7 ? 128 << ssize : 8192; static const int rates[3] = { 500000, 300000, 250000 }; bool fm = mode < 3; @@ -433,135 +433,44 @@ bool imd_format::load(io_generic *io, UINT32 form_factor, floppy_image *image) head &= 0x3f; - UINT32 *track_data = global_alloc_array(UINT32, cell_count+10000); - int tpos = 0; + int gap_3 = calc_default_pc_gap3_size(form_factor, actual_size); - // gap 4a , IAM and gap 1 - if(fm) { - for(int i=0; i<40; i++) fm_w(track_data, tpos, 8, 0xff); - for(int i=0; i< 6; i++) fm_w(track_data, tpos, 8, 0x00); - raw_w(track_data, tpos, 16, 0xf77a); - for(int i=0; i<26; i++) fm_w(track_data, tpos, 8, 0xff); - } else { - for(int i=0; i<80; i++) mfm_w(track_data, tpos, 8, 0x4e); - for(int i=0; i<12; i++) mfm_w(track_data, tpos, 8, 0x00); - for(int i=0; i< 3; i++) raw_w(track_data, tpos, 16, 0x5224); - mfm_w(track_data, tpos, 8, 0xfc); - for(int i=0; i<50; i++) mfm_w(track_data, tpos, 8, 0x4e); + desc_pc_sector sects[256]; + + for(int i=0; i 8) { + sects[i].data = NULL; + + } else { + sects[i].deleted = stype == 3 || stype == 4 || stype == 7 || stype == 8; + sects[i].bad_crc = stype == 5 || stype == 6 || stype == 7 || stype == 8; + + if(stype == 2 || stype == 4 || stype == 6 || stype == 8) { + sects[i].data = global_alloc_array(UINT8, actual_size); + memset(sects[i].data, img[pos++], actual_size); + + } else { + sects[i].data = img + pos; + pos += actual_size; + } + } } - // Compute the available and expected size for gap3 - int gap3 = form_factor == floppy_image::FF_8 ? 25 : - size < 512 ? - (form_factor == floppy_image::FF_35 ? 54 : 50) : - (form_factor == floppy_image::FF_35 ? 84 : 80); - - int etpos = tpos; if(fm) - etpos += sector_count*(6+5+2+11+6+1+size+2)*16; + build_pc_track_fm(track, head, image, cell_count, sector_count, sects, gap_3); else - etpos += sector_count*(12+3+5+2+22+12+3+1+size+2)*16; + build_pc_track_mfm(track, head, image, cell_count, sector_count, sects, gap_3); - if(etpos > cell_count) - throw emu_fatalerror("imd_format: Incorrect layout on track %d head %d, expected_size=%d, current_size=%d", track, head, cell_count, etpos); - - if(etpos + gap3*16*(sector_count-1) > cell_count) - gap3 = (cell_count - etpos) / 16 / (sector_count-1); - - // Build the track - if(fm) { - for(int i=0; i 8) - for(int j=0; j<6+1+size+2+gap3; j++) fm_w(track_data, tpos, 8, 0xff); - - else { - // sync, DAM, data and gap 3 - for(int j=0; j< 6; j++) fm_w(track_data, tpos, 8, 0x00); - cpos = tpos; - 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> (16+tpos-cell_count)); - - } else { - for(int i=0; i 8) - for(int j=0; j<12+4+size+2+gap3; j++) mfm_w(track_data, tpos, 8, 0x4e); - - else { - // sync, DAM, data and gap 3 - for(int j=0; j<12; j++) mfm_w(track_data, tpos, 8, 0x00); - cpos = tpos; - for(int j=0; j< 3; j++) raw_w(track_data, tpos, 16, 0x4489); - mfm_w(track_data, tpos, 8, stype == 3 || stype == 4 || stype == 7 || stype == 8 ? 0xf8 : 0xfb); - if(stype == 2 || stype == 4 || stype == 6 || stype == 8) { - for(int j=0; j> (16+tpos-cell_count)); - } - - generate_track_from_levels(track, head, track_data, cell_count, 0, image); - global_free(track_data); + for(int i=0; i= img+size)) + global_free(sects[i].data); } global_free(img);