void drive_image_init_track_size_d64(drive_t *drive) { unsigned int track; for (track = 0; track < MAX_TRACKS_1541; track++) { drive->gcr->track_size[track] = raw_track_size[disk_image_speed_map_1541(track)]; memset(drive->gcr->speed_zone, disk_image_speed_map_1541(track), NUM_MAX_BYTES_TRACK); } }
static int fsimage_create_gcr(disk_image_t *image) { BYTE gcr_header[12], gcr_track[7930], *gcrptr; DWORD gcr_track_p[MAX_TRACKS_1541 * 2]; DWORD gcr_speed_p[MAX_TRACKS_1541 * 2]; unsigned int track, sector; fsimage_t *fsimage; fsimage = image->media.fsimage; strcpy((char *)gcr_header, "GCR-1541"); gcr_header[8] = 0; gcr_header[9] = MAX_TRACKS_1541 * 2; gcr_header[10] = 7928 % 256; gcr_header[11] = 7928 / 256; if (fwrite((char *)gcr_header, sizeof(gcr_header), 1, fsimage->fd) < 1) { log_error(createdisk_log, "Cannot write GCR header."); return -1; } for (track = 0; track < MAX_TRACKS_1541; track++) { gcr_track_p[track * 2] = 12 + MAX_TRACKS_1541 * 16 + track * 7930; gcr_track_p[track * 2 + 1] = 0; gcr_speed_p[track * 2] = disk_image_speed_map_1541(track); gcr_speed_p[track * 2 + 1] = 0; } if (util_dword_write(fsimage->fd, gcr_track_p, util_arraysize(gcr_track_p)) < 0) { log_error(createdisk_log, "Cannot write track header."); return -1; } if (util_dword_write(fsimage->fd, gcr_speed_p, util_arraysize(gcr_speed_p)) < 0) { log_error(createdisk_log, "Cannot write speed header."); return -1; } for (track = 0; track < MAX_TRACKS_1541; track++) { const int raw_track_size[4] = { 6250, 6666, 7142, 7692 }; memset(&gcr_track[2], 0x55, 7928); gcr_track[0] = raw_track_size[disk_image_speed_map_1541(track)] % 256; gcr_track[1] = raw_track_size[disk_image_speed_map_1541(track)] / 256; gcrptr = &gcr_track[2]; for (sector = 0; sector < disk_image_sector_per_track(DISK_IMAGE_TYPE_D64, track + 1); sector++) { BYTE chksum, id[2], rawdata[260]; int i; id[0] = id[1] = 0xa0; memset(rawdata, 0, 260); rawdata[0] = 7; chksum = rawdata[1]; for (i = 1; i < 256; i++) chksum ^= rawdata[i + 1]; rawdata[257] = chksum; gcr_convert_sector_to_GCR(rawdata, gcrptr, track + 1, sector, id[0], id[1], 0); gcrptr += 360; } if (fwrite((char *)gcr_track, sizeof(gcr_track), 1, fsimage->fd) < 1 ) { log_error(createdisk_log, "Cannot write track data."); return -1; } } return 0; }
static int fsimage_create_p64(disk_image_t *image) { TP64MemoryStream P64MemoryStreamInstance; TP64Image P64Image; BYTE gcr_track[7928], *gcrptr; unsigned int track, sector; fsimage_t *fsimage; int rc = -1; fsimage = image->media.fsimage; P64ImageCreate(&P64Image); for (track = 0; track < MAX_TRACKS_1541; track++) { const int raw_track_size[4] = { 6250, 6666, 7142, 7692 }; memset(&gcr_track[0], 0x55, 7928); gcrptr = &gcr_track[0]; for (sector = 0; sector < disk_image_sector_per_track(DISK_IMAGE_TYPE_D64, track + 1); sector++) { BYTE chksum, id[2], rawdata[260]; int i; id[0] = id[1] = 0xa0; memset(rawdata, 0, 260); rawdata[0] = 7; chksum = rawdata[1]; for (i = 1; i < 256; i++) { chksum ^= rawdata[i + 1]; } rawdata[257] = chksum; gcr_convert_sector_to_GCR(rawdata, gcrptr, track + 1, sector, id[0], id[1], 0); gcrptr += 360; } P64PulseStreamConvertFromGCR(&P64Image.PulseStreams[(track + 1) << 1], (void*)&gcr_track[0], raw_track_size[disk_image_speed_map_1541(track)] << 3); } P64MemoryStreamCreate(&P64MemoryStreamInstance); P64MemoryStreamClear(&P64MemoryStreamInstance); if (P64ImageWriteToStream(&P64Image,&P64MemoryStreamInstance)) { if (fwrite(P64MemoryStreamInstance.Data, P64MemoryStreamInstance.Size, 1, fsimage->fd) < 1) { log_error(createdisk_log, "Cannot write image data."); rc = -1; } else { rc = 0; } } P64MemoryStreamDestroy(&P64MemoryStreamInstance); P64ImageDestroy(&P64Image); return rc; }
int fsimage_p64_read_track(disk_image_t *image, unsigned int track, BYTE *gcr_data, int *gcr_track_size) { PP64Image P64Image = (void*)image->p64; if (P64Image == NULL) { log_error(fsimage_p64_log, "P64 image not loaded."); return -1; } if (track > 42) { log_error(fsimage_p64_log, "Track %i out of bounds. Cannot read P64 track.", track); return -1; } memset(gcr_data, 0xff, 6250); *gcr_track_size = (P64PulseStreamConvertToGCRWithLogic(&P64Image->PulseStreams[track << 1], (void*)gcr_data, NUM_MAX_MEM_BYTES_TRACK, disk_image_speed_map_1541((track > 0) ? (track - 1) : 0)) + 7) >> 3; if (*gcr_track_size < 1) { *gcr_track_size = 6520; } return 0; }
inline static unsigned int sector_offset(unsigned int track, unsigned int sector, unsigned int max_sector, drive_t *drive) { return GCR_OFFSET(track) + (SECTOR_GCR_SIZE_WITH_HEADER + gaps_between_sectors[disk_image_speed_map_1541(track-1)]) * sector; }