Fixed ISO loading;

Fixed ESDI and XT MFM hard disk initialization;
The IDE SET_FEATURES command is now actually recognized by the command register write handler.
This commit is contained in:
OBattler
2017-05-15 00:35:26 +02:00
parent 84ac082bc4
commit 6a3f3727a7
8 changed files with 389 additions and 359 deletions

View File

@@ -205,6 +205,9 @@ bool CDROM_Interface_Image::IsMode2(unsigned long sector)
bool CDROM_Interface_Image::LoadIsoFile(char* filename)
{
int shift = 0;
int totalPregap = 0;
tracks.clear();
// data track
@@ -216,6 +219,7 @@ bool CDROM_Interface_Image::LoadIsoFile(char* filename)
return false;
}
track.number = 1;
track.track_number = 1;//IMPORTANT: This is needed.
track.attr = DATA_TRACK;//data
// try to detect iso type
@@ -239,7 +243,7 @@ bool CDROM_Interface_Image::LoadIsoFile(char* filename)
// leadout track
track.number = 2;
track.track_number = 0xAA;
track.attr = 0;
track.attr = 0x16; /* Was 0x00 but I believe 0x16 is appropriate. */
track.start = track.length;
track.length = 0;
track.file = NULL;
@@ -389,7 +393,8 @@ bool CDROM_Interface_Image::LoadCueSheet(char *cuefile)
// add leadout track
track.number++;
track.track_number = 0xAA;
track.attr = 0;//sync with load iso
// track.attr = 0;//sync with load iso
track.attr = 0x16; /* Was 0x00 but I believe 0x16 is appropriate. */
track.start = 0;
track.length = 0;
track.file = NULL;

View File

@@ -228,7 +228,7 @@ static int image_get_last_block(uint8_t id, uint8_t starttrack, int msf, int max
{
uint32_t address;
cdimg[id]->GetAudioTrackInfo(c+1, number, tmsf, attr);
address = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr);
address = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr) - 150; /* Do the - 150 here as well. */
if (address > lb)
lb = address;
}
@@ -733,7 +733,7 @@ static void lba_to_msf(uint8_t *buf, int lba)
lba += 150;
buf[0] = (lba / 75) / 60;
buf[1] = (lba / 75) % 60;
buf[2] = lba % 75;
buf[2] = lba % 75;
}
static uint32_t image_size(uint8_t id)
@@ -743,6 +743,7 @@ static uint32_t image_size(uint8_t id)
static int image_readtoc(uint8_t id, unsigned char *b, unsigned char starttrack, int msf, int maxlen, int single)
{
if (!cdimg[id]) return 0;
int len=4;
int c,d;
uint32_t temp;
@@ -752,9 +753,6 @@ static int image_readtoc(uint8_t id, unsigned char *b, unsigned char starttrack,
int number;
unsigned char attr;
TMSF tmsf;
if (!cdimg[id]) return 0;
cdimg[id]->GetAudioTracks(first_track, last_track, tmsf);
b[2] = first_track;
@@ -779,6 +777,7 @@ static int image_readtoc(uint8_t id, unsigned char *b, unsigned char starttrack,
break;
cdimg[id]->GetAudioTrackInfo(c+1, number, tmsf, attr);
// pclog("Len %i max %i Track %02X - %02X %02X %02i:%02i:%02i %08X\n",len,maxlen,toc[c].cdte_track,toc[c].cdte_adr,toc[c].cdte_ctrl,toc[c].cdte_addr.msf.minute, toc[c].cdte_addr.msf.second, toc[c].cdte_addr.msf.frame,MSFtoLBA(toc[c].cdte_addr.msf.minute, toc[c].cdte_addr.msf.second, toc[c].cdte_addr.msf.frame));
b[len++] = 0; /* reserved */
b[len++] = attr;
b[len++] = number; /* track number */
@@ -793,7 +792,7 @@ static int image_readtoc(uint8_t id, unsigned char *b, unsigned char starttrack,
}
else
{
temp = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr);
temp = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr) - 150;
b[len++] = temp >> 24;
b[len++] = temp >> 16;
b[len++] = temp >> 8;
@@ -802,14 +801,22 @@ static int image_readtoc(uint8_t id, unsigned char *b, unsigned char starttrack,
if (single)
break;
}
if (len > maxlen)
{
len = maxlen;
}
b[0] = (uint8_t)(((len-2) >> 8) & 0xff);
b[1] = (uint8_t)((len-2) & 0xff);
/*
pclog("Table of Contents:\n");
pclog("First track - %02X\n", first_track);
pclog("Last track - %02X\n", last_track);
for (c = 0; c <= last_track; c++)
{
cdimg[id]->GetAudioTrackInfo(c+1, number, tmsf, attr);
pclog("Track %02X - number %02X control %02X adr %02X address %02X %02X %02X %02X\n", c, number, attr, 0, 0, tmsf.min, tmsf.sec, tmsf.fr);
}
for (c = 0;c <= last_track; c++) {
cdimg[id]->GetAudioTrackInfo(c+1, number, tmsf, attr);
pclog("Track %02X - number %02X control %02X adr %02X address %06X\n", c, number, attr, 0, MSF_TO_FRAMES(tmsf.min, tmsf.sec, tmsf.fr));
}
*/
return len;
}
@@ -825,6 +832,11 @@ static int image_readtoc_session(uint8_t id, unsigned char *b, int msf, int maxl
cdimg[id]->GetAudioTrackInfo(1, number, tmsf, attr);
if (number == 0)
{
number = 1;
}
b[2] = 1;
b[3] = 1;
b[len++] = 0; /* reserved */
@@ -840,7 +852,7 @@ static int image_readtoc_session(uint8_t id, unsigned char *b, int msf, int maxl
}
else
{
uint32_t temp = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr);
uint32_t temp = MSFtoLBA(tmsf.min, tmsf.sec, tmsf.fr) - 150; /* Do the - 150. */
b[len++] = temp >> 24;
b[len++] = temp >> 16;
b[len++] = temp >> 8;

View File

@@ -19,6 +19,8 @@ extern void image_close(uint8_t id);
void update_status_bar_icon_state(int tag, int state);
extern void cdrom_set_null_handler(uint8_t id);
void pclog(const char *format, ...);
#ifdef __cplusplus
}
#endif

View File

@@ -796,7 +796,7 @@ static void esdi_mca_write(int port, uint8_t val, void *p)
}
}
static void loadhd(esdi_t *esdi, int d, const wchar_t *fn)
static void loadhd(esdi_t *esdi, int hdc_num, int d, const wchar_t *fn)
{
esdi_drive_t *drive = &esdi->drives[d];
@@ -829,15 +829,16 @@ static void loadhd(esdi_t *esdi, int d, const wchar_t *fn)
}
}
drive->spt = hdc[d].spt;
drive->hpc = hdc[d].hpc;
drive->tracks = hdc[d].tracks;
drive->sectors = hdc[d].spt * hdc[d].hpc * hdc[d].tracks;
drive->spt = hdc[hdc_num].spt;
drive->hpc = hdc[hdc_num].hpc;
drive->tracks = hdc[hdc_num].tracks;
drive->sectors = hdc[hdc_num].spt * hdc[hdc_num].hpc * hdc[hdc_num].tracks;
}
static void *esdi_init()
{
int i = 0;
int c = 0;
esdi_t *esdi = malloc(sizeof(esdi_t));
memset(esdi, 0, sizeof(esdi_t));
@@ -847,7 +848,12 @@ static void *esdi_init()
for (i = 0; i < HDC_NUM; i++)
{
loadhd(esdi, hdc[i].mfm_channel, hdd_fn[i]);
if ((hdc[i].bus == 1) && (hdc[i].mfm_channel < MFM_NUM))
{
loadhd(esdi, i, hdc[i].mfm_channel, hdd_fn[i]);
c++;
if (c >= MFM_NUM) break;
}
}
timer_add(esdi_callback, &esdi->callback, &esdi->callback, esdi);

657
src/ide.c
View File

@@ -905,7 +905,7 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
switch (addr)
{
case 0x1F0: /* Data */
case 0x1F0: /* Data */
writeidew(ide_board, val | (val << 8));
return;
@@ -924,7 +924,7 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
ide_other->cylprecomp = val;
return;
case 0x1F2: /* Sector count */
case 0x1F2: /* Sector count */
if (ide_drive_is_cdrom(ide))
{
ide_log("Sector count write: %i\n", val);
@@ -940,14 +940,14 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
ide_other->secount = val;
return;
case 0x1F3: /* Sector */
case 0x1F3: /* Sector */
ide->sector = val;
ide->lba_addr = (ide->lba_addr & 0xFFFFF00) | val;
ide_other->sector = val;
ide_other->lba_addr = (ide_other->lba_addr & 0xFFFFF00) | val;
return;
case 0x1F4: /* Cylinder low */
case 0x1F4: /* Cylinder low */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[cur_ide[ide_board]]].request_length &= 0xFF00;
@@ -965,7 +965,7 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
ide_other->lba_addr = (ide_other->lba_addr&0xFFF00FF) | (val << 8);
return;
case 0x1F5: /* Cylinder high */
case 0x1F5: /* Cylinder high */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[cur_ide[ide_board]]].request_length &= 0xFF;
@@ -983,7 +983,7 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
ide_other->lba_addr = (ide_other->lba_addr & 0xF00FFFF) | (val << 16);
return;
case 0x1F6: /* Drive/Head */
case 0x1F6: /* Drive/Head */
if (cur_ide[ide_board] != ((val>>4)&1)+(ide_board<<1))
{
cur_ide[ide_board]=((val>>4)&1)+(ide_board<<1);
@@ -1036,254 +1036,255 @@ void writeide(int ide_board, uint16_t addr, uint8_t val)
ide_irq_update(ide);
return;
case 0x1F7: /* Command register */
case 0x1F7: /* Command register */
if (ide->type == IDE_NONE)
{
return;
}
ide_irq_lower(ide);
ide->command=val;
ide_irq_lower(ide);
ide->command=val;
ide->error=0;
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].error = 0;
}
switch (val)
{
case WIN_SRST: /* ATAPI Device Reset */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = READY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 100*IDE_TIME;
}
idecallback[ide_board]=100*IDE_TIME;
timer_update_outstanding();
return;
ide->error=0;
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].error = 0;
}
switch (val)
{
case WIN_SRST: /* ATAPI Device Reset */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = READY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 100*IDE_TIME;
}
idecallback[ide_board]=100*IDE_TIME;
timer_update_outstanding();
return;
case WIN_RESTORE:
case WIN_SEEK:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT;
}
else
{
ide->atastat = READY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 100*IDE_TIME;
}
idecallback[ide_board]=100*IDE_TIME;
timer_update_outstanding();
return;
case WIN_RESTORE:
case WIN_SEEK:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT;
}
else
{
ide->atastat = READY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 100*IDE_TIME;
}
idecallback[ide_board]=100*IDE_TIME;
timer_update_outstanding();
return;
case WIN_READ_MULTIPLE:
/* Fatal removed in accordance with the official ATAPI reference:
If the Read Multiple command is attempted before the Set Multiple Mode
command has been executed or when Read Multiple commands are
disabled, the Read Multiple operation is rejected with an Aborted Com-
mand error. */
ide->blockcount = 0;
case WIN_READ:
case WIN_READ_NORETRY:
case WIN_READ_DMA:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
case WIN_READ_MULTIPLE:
/* Fatal removed in accordance with the official ATAPI reference:
If the Read Multiple command is attempted before the Set Multiple Mode
command has been executed or when Read Multiple commands are
disabled, the Read Multiple operation is rejected with an Aborted Com-
mand error. */
ide->blockcount = 0;
case WIN_READ:
case WIN_READ_NORETRY:
case WIN_READ_DMA:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_WRITE_MULTIPLE:
if (!ide->blocksize && !ide_drive_is_cdrom(ide))
{
fatal("Write_MULTIPLE - blocksize = 0\n");
}
ide->blockcount = 0;
case WIN_WRITE:
case WIN_WRITE_NORETRY:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = DRQ_STAT | DSC_STAT | READY_STAT;
cdrom[atapi_cdrom_drives[ide->channel]].pos = 0;
}
else
{
ide->atastat = DRQ_STAT | DSC_STAT | READY_STAT;
ide->pos=0;
}
return;
case WIN_WRITE_DMA:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_VERIFY:
case WIN_VERIFY_ONCE:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_FORMAT:
if (ide_drive_is_cdrom(ide))
{
goto ide_bad_command;
}
else
{
ide->atastat = DRQ_STAT;
ide->pos=0;
}
return;
case WIN_SPECIFY: /* Initialize Drive Parameters */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 30*IDE_TIME;
}
idecallback[ide_board]=30*IDE_TIME;
timer_update_outstanding();
return;
case WIN_DRIVE_DIAGNOSTICS: /* Execute Drive Diagnostics */
case WIN_PIDENTIFY: /* Identify Packet Device */
case WIN_SET_MULTIPLE_MODE: /* Set Multiple Mode */
case WIN_SET_FEATURES: /* Set Features */
case WIN_NOP:
case WIN_STANDBYNOW1:
case WIN_IDLENOW1:
case WIN_SETIDLE1: /* Idle */
case WIN_CHECKPOWERMODE1:
case WIN_SLEEP1:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 30*IDE_TIME;
}
idecallback[ide_board]=30*IDE_TIME;
timer_update_outstanding();
return;
case WIN_IDENTIFY: /* Identify Device */
case WIN_READ_NATIVE_MAX:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_PACKETCMD: /* ATAPI Packet */
/* Skip the command callback wait, and process immediately. */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].packet_status = CDROM_PHASE_IDLE;
cdrom[atapi_cdrom_drives[ide->channel]].pos=0;
cdrom[atapi_cdrom_drives[ide->channel]].phase = 1;
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT | DRQ_STAT | (cdrom[cur_ide[ide_board]].status & ERR_STAT);
}
else
{
ide->atastat = BUSY_STAT;
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
idecallback[ide_board]=1;
timer_update_outstanding();
return;
case WIN_WRITE_MULTIPLE:
if (!ide->blocksize && !ide_drive_is_cdrom(ide))
{
fatal("Write_MULTIPLE - blocksize = 0\n");
}
ide->blockcount = 0;
case WIN_WRITE:
case WIN_WRITE_NORETRY:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = DRQ_STAT | DSC_STAT | READY_STAT;
cdrom[atapi_cdrom_drives[ide->channel]].pos = 0;
}
else
{
ide->atastat = DRQ_STAT | DSC_STAT | READY_STAT;
ide->pos=0;
}
return;
ide->pos=0;
}
return;
case WIN_WRITE_DMA:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_VERIFY:
case WIN_VERIFY_ONCE:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_FORMAT:
if (ide_drive_is_cdrom(ide))
{
goto ide_bad_command;
}
else
{
ide->atastat = DRQ_STAT;
ide->pos=0;
}
return;
case WIN_SPECIFY: /* Initialize Drive Parameters */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 30*IDE_TIME;
}
idecallback[ide_board]=30*IDE_TIME;
timer_update_outstanding();
return;
case WIN_DRIVE_DIAGNOSTICS: /* Execute Drive Diagnostics */
case WIN_PIDENTIFY: /* Identify Packet Device */
case WIN_SET_MULTIPLE_MODE: /*Set Multiple Mode*/
case WIN_NOP:
case WIN_STANDBYNOW1:
case WIN_IDLENOW1:
case WIN_SETIDLE1: /* Idle */
case WIN_CHECKPOWERMODE1:
case WIN_SLEEP1:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 30*IDE_TIME;
}
idecallback[ide_board]=30*IDE_TIME;
timer_update_outstanding();
return;
case WIN_IDENTIFY: /* Identify Device */
case WIN_READ_NATIVE_MAX:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = BUSY_STAT;
}
else
{
ide->atastat = BUSY_STAT;
}
timer_process();
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].callback = 200*IDE_TIME;
}
idecallback[ide_board]=200*IDE_TIME;
timer_update_outstanding();
return;
case WIN_PACKETCMD: /* ATAPI Packet */
/* Skip the command callback wait, and process immediately. */
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].packet_status = CDROM_PHASE_IDLE;
cdrom[atapi_cdrom_drives[ide->channel]].pos=0;
cdrom[atapi_cdrom_drives[ide->channel]].phase = 1;
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT | DRQ_STAT | (cdrom[cur_ide[ide_board]].status & ERR_STAT);
}
else
{
ide->atastat = BUSY_STAT;
timer_process();
idecallback[ide_board]=1;
timer_update_outstanding();
ide->pos=0;
}
return;
case 0xF0:
default:
case 0xF0:
default:
ide_bad_command:
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT | ERR_STAT | DSC_STAT;
cdrom[atapi_cdrom_drives[ide->channel]].error = ABRT_ERR;
}
else
{
ide->atastat = READY_STAT | ERR_STAT | DSC_STAT;
ide->error = ABRT_ERR;
}
ide_irq_raise(ide);
return;
if (ide_drive_is_cdrom(ide))
{
cdrom[atapi_cdrom_drives[ide->channel]].status = READY_STAT | ERR_STAT | DSC_STAT;
cdrom[atapi_cdrom_drives[ide->channel]].error = ABRT_ERR;
}
else
{
ide->atastat = READY_STAT | ERR_STAT | DSC_STAT;
ide->error = ABRT_ERR;
}
ide_irq_raise(ide);
return;
}
return;
@@ -1424,7 +1425,7 @@ uint8_t readide(int ide_board, uint16_t addr)
/* For ATAPI: Bits 7-4 = sense key, bit 3 = MCR (media change requested),
Bit 2 = ABRT (aborted command), Bit 1 = EOM (end of media),
and Bit 0 = ILI (illegal length indication). */
and Bit 0 = ILI (illegal length indication). */
case 0x1F1: /* Error */
if (ide->type == IDE_NONE)
{
@@ -2125,161 +2126,159 @@ void ide_callback_qua()
void ide_write_pri(uint16_t addr, uint8_t val, void *priv)
{
writeide(0, addr, val);
writeide(0, addr, val);
}
void ide_write_pri_w(uint16_t addr, uint16_t val, void *priv)
{
writeidew(0, val);
writeidew(0, val);
}
void ide_write_pri_l(uint16_t addr, uint32_t val, void *priv)
{
writeidel(0, val);
writeidel(0, val);
}
uint8_t ide_read_pri(uint16_t addr, void *priv)
{
return readide(0, addr);
return readide(0, addr);
}
uint16_t ide_read_pri_w(uint16_t addr, void *priv)
{
return readidew(0);
return readidew(0);
}
uint32_t ide_read_pri_l(uint16_t addr, void *priv)
{
return readidel(0);
return readidel(0);
}
void ide_write_sec(uint16_t addr, uint8_t val, void *priv)
{
writeide(1, addr, val);
writeide(1, addr, val);
}
void ide_write_sec_w(uint16_t addr, uint16_t val, void *priv)
{
writeidew(1, val);
writeidew(1, val);
}
void ide_write_sec_l(uint16_t addr, uint32_t val, void *priv)
{
writeidel(1, val);
writeidel(1, val);
}
uint8_t ide_read_sec(uint16_t addr, void *priv)
{
return readide(1, addr);
return readide(1, addr);
}
uint16_t ide_read_sec_w(uint16_t addr, void *priv)
{
return readidew(1);
return readidew(1);
}
uint32_t ide_read_sec_l(uint16_t addr, void *priv)
{
return readidel(1);
return readidel(1);
}
/* *** REMOVE FROM CODE SUBMITTED TO MAINLINE - START *** */
void ide_write_ter(uint16_t addr, uint8_t val, void *priv)
{
writeide(2, addr, val);
writeide(2, addr, val);
}
void ide_write_ter_w(uint16_t addr, uint16_t val, void *priv)
{
writeidew(2, val);
writeidew(2, val);
}
void ide_write_ter_l(uint16_t addr, uint32_t val, void *priv)
{
writeidel(2, val);
writeidel(2, val);
}
uint8_t ide_read_ter(uint16_t addr, void *priv)
{
return readide(2, addr);
return readide(2, addr);
}
uint16_t ide_read_ter_w(uint16_t addr, void *priv)
{
return readidew(2);
return readidew(2);
}
uint32_t ide_read_ter_l(uint16_t addr, void *priv)
{
return readidel(2);
return readidel(2);
}
void ide_write_qua(uint16_t addr, uint8_t val, void *priv)
{
writeide(3, addr, val);
writeide(3, addr, val);
}
void ide_write_qua_w(uint16_t addr, uint16_t val, void *priv)
{
writeidew(3, val);
writeidew(3, val);
}
void ide_write_qua_l(uint16_t addr, uint32_t val, void *priv)
{
writeidel(3, val);
writeidel(3, val);
}
uint8_t ide_read_qua(uint16_t addr, void *priv)
{
return readide(3, addr);
return readide(3, addr);
}
uint16_t ide_read_qua_w(uint16_t addr, void *priv)
{
return readidew(3);
return readidew(3);
}
uint32_t ide_read_qua_l(uint16_t addr, void *priv)
{
return readidel(3);
return readidel(3);
}
/* *** REMOVE FROM CODE SUBMITTED TO MAINLINE - END *** */
static uint16_t ide_base_main[2] = { 0x1f0, 0x170 };
static uint16_t ide_side_main[2] = { 0x3f6, 0x376 };
void ide_pri_enable()
{
io_sethandler(0x01f0, 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
io_sethandler(0x03f6, 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
ide_base_main[0] = 0x1f0;
ide_side_main[0] = 0x3f6;
io_sethandler(0x01f0, 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
io_sethandler(0x03f6, 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
ide_base_main[0] = 0x1f0;
ide_side_main[0] = 0x3f6;
}
void ide_pri_enable_ex()
{
if (ide_base_main[0] & 0x300)
{
pclog("Enabling primary base (%04X)...\n", ide_base_main[0]);
io_sethandler(ide_base_main[0], 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
}
if (ide_side_main[0] & 0x300)
{
pclog("Enabling primary side (%04X)...\n", ide_side_main[0]);
io_sethandler(ide_side_main[0], 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
}
if (ide_base_main[0] & 0x300)
{
pclog("Enabling primary base (%04X)...\n", ide_base_main[0]);
io_sethandler(ide_base_main[0], 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
}
if (ide_side_main[0] & 0x300)
{
pclog("Enabling primary side (%04X)...\n", ide_side_main[0]);
io_sethandler(ide_side_main[0], 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
}
}
void ide_pri_disable()
{
io_removehandler(ide_base_main[0], 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
io_removehandler(ide_side_main[0], 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
io_removehandler(ide_base_main[0], 0x0008, ide_read_pri, ide_read_pri_w, ide_read_pri_l, ide_write_pri, ide_write_pri_w, ide_write_pri_l, NULL);
io_removehandler(ide_side_main[0], 0x0001, ide_read_pri, NULL, NULL, ide_write_pri, NULL, NULL , NULL);
}
void ide_sec_enable()
{
io_sethandler(0x0170, 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
io_sethandler(0x0376, 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
ide_base_main[1] = 0x170;
ide_side_main[1] = 0x376;
io_sethandler(0x0170, 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
io_sethandler(0x0376, 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
ide_base_main[1] = 0x170;
ide_side_main[1] = 0x376;
}
void ide_sec_enable_ex()
{
if (ide_base_main[1] & 0x300)
{
io_sethandler(ide_base_main[1], 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
}
if (ide_side_main[1] & 0x300)
{
io_sethandler(ide_side_main[1], 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
}
if (ide_base_main[1] & 0x300)
{
io_sethandler(ide_base_main[1], 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
}
if (ide_side_main[1] & 0x300)
{
io_sethandler(ide_side_main[1], 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
}
}
void ide_sec_disable()
{
io_removehandler(ide_base_main[1], 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
io_removehandler(ide_side_main[1], 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
io_removehandler(ide_base_main[1], 0x0008, ide_read_sec, ide_read_sec_w, ide_read_sec_l, ide_write_sec, ide_write_sec_w, ide_write_sec_l, NULL);
io_removehandler(ide_side_main[1], 0x0001, ide_read_sec, NULL, NULL, ide_write_sec, NULL, NULL , NULL);
}
void ide_set_base(int controller, uint16_t port)
@@ -2292,75 +2291,73 @@ void ide_set_side(int controller, uint16_t port)
ide_side_main[controller] = port;
}
/* *** REMOVE FROM CODE SUBMITTED TO MAINLINE - START *** */
void ide_ter_enable()
{
io_sethandler(0x0168, 0x0008, ide_read_ter, ide_read_ter_w, ide_read_ter_l, ide_write_ter, ide_write_ter_w, ide_write_ter_l, NULL);
io_sethandler(0x036e, 0x0001, ide_read_ter, NULL, NULL, ide_write_ter, NULL, NULL , NULL);
io_sethandler(0x0168, 0x0008, ide_read_ter, ide_read_ter_w, ide_read_ter_l, ide_write_ter, ide_write_ter_w, ide_write_ter_l, NULL);
io_sethandler(0x036e, 0x0001, ide_read_ter, NULL, NULL, ide_write_ter, NULL, NULL , NULL);
}
void ide_ter_disable()
{
io_removehandler(0x0168, 0x0008, ide_read_ter, ide_read_ter_w, ide_read_ter_l, ide_write_ter, ide_write_ter_w, ide_write_ter_l, NULL);
io_removehandler(0x036e, 0x0001, ide_read_ter, NULL, NULL, ide_write_ter, NULL, NULL , NULL);
io_removehandler(0x0168, 0x0008, ide_read_ter, ide_read_ter_w, ide_read_ter_l, ide_write_ter, ide_write_ter_w, ide_write_ter_l, NULL);
io_removehandler(0x036e, 0x0001, ide_read_ter, NULL, NULL, ide_write_ter, NULL, NULL , NULL);
}
void ide_ter_disable_cond()
{
if ((ide_drives[4].type == IDE_NONE) && (ide_drives[5].type == IDE_NONE))
{
ide_ter_disable();
}
if ((ide_drives[4].type == IDE_NONE) && (ide_drives[5].type == IDE_NONE))
{
ide_ter_disable();
}
}
void ide_ter_init()
{
ide_ter_enable();
ide_ter_enable();
timer_add(ide_callback_ter, &idecallback[2], &idecallback[2], NULL);
timer_add(ide_callback_ter, &idecallback[2], &idecallback[2], NULL);
}
void ide_qua_enable()
{
io_sethandler(0x01e8, 0x0008, ide_read_qua, ide_read_qua_w, ide_read_qua_l, ide_write_qua, ide_write_qua_w, ide_write_qua_l, NULL);
io_sethandler(0x03ee, 0x0001, ide_read_qua, NULL, NULL, ide_write_qua, NULL, NULL , NULL);
io_sethandler(0x01e8, 0x0008, ide_read_qua, ide_read_qua_w, ide_read_qua_l, ide_write_qua, ide_write_qua_w, ide_write_qua_l, NULL);
io_sethandler(0x03ee, 0x0001, ide_read_qua, NULL, NULL, ide_write_qua, NULL, NULL , NULL);
}
void ide_qua_disable_cond()
{
if ((ide_drives[6].type == IDE_NONE) && (ide_drives[7].type == IDE_NONE))
{
ide_qua_disable();
}
if ((ide_drives[6].type == IDE_NONE) && (ide_drives[7].type == IDE_NONE))
{
ide_qua_disable();
}
}
void ide_qua_disable()
{
io_removehandler(0x01e8, 0x0008, ide_read_qua, ide_read_qua_w, ide_read_qua_l, ide_write_qua, ide_write_qua_w, ide_write_qua_l, NULL);
io_removehandler(0x03ee, 0x0001, ide_read_qua, NULL, NULL, ide_write_qua, NULL, NULL , NULL);
io_removehandler(0x01e8, 0x0008, ide_read_qua, ide_read_qua_w, ide_read_qua_l, ide_write_qua, ide_write_qua_w, ide_write_qua_l, NULL);
io_removehandler(0x03ee, 0x0001, ide_read_qua, NULL, NULL, ide_write_qua, NULL, NULL , NULL);
}
void ide_qua_init()
{
ide_qua_enable();
ide_qua_enable();
timer_add(ide_callback_qua, &idecallback[3], &idecallback[3], NULL);
timer_add(ide_callback_qua, &idecallback[3], &idecallback[3], NULL);
}
/* *** REMOVE FROM CODE SUBMITTED TO MAINLINE - END *** */
void ide_init()
{
ide_pri_enable();
ide_sec_enable();
ide_bus_master_read = ide_bus_master_write = NULL;
timer_add(ide_callback_pri, &idecallback[0], &idecallback[0], NULL);
timer_add(ide_callback_sec, &idecallback[1], &idecallback[1], NULL);
ide_pri_enable();
ide_sec_enable();
ide_bus_master_read = ide_bus_master_write = NULL;
timer_add(ide_callback_pri, &idecallback[0], &idecallback[0], NULL);
timer_add(ide_callback_sec, &idecallback[1], &idecallback[1], NULL);
}
void ide_set_bus_master(int (*read)(int channel, uint8_t *data, int transfer_length), int (*write)(int channel, uint8_t *data, int transfer_length), void (*set_irq)(int channel))
{
ide_bus_master_read = read;
ide_bus_master_write = write;
ide_bus_master_set_irq = set_irq;
ide_bus_master_read = read;
ide_bus_master_write = write;
ide_bus_master_set_irq = set_irq;
}

View File

@@ -763,7 +763,7 @@ static void xebec_callback(void *p)
}
}
static void loadhd(xebec_t *xebec, int d, const wchar_t *fn)
static void loadhd(xebec_t *xebec, int c, int d, const wchar_t *fn)
{
mfm_drive_t *drive = &xebec->drives[d];
@@ -796,9 +796,9 @@ static void loadhd(xebec_t *xebec, int d, const wchar_t *fn)
}
}
drive->spt = hdc[d].spt;
drive->hpc = hdc[d].hpc;
drive->tracks = hdc[d].tracks;
drive->spt = hdc[c].spt;
drive->hpc = hdc[c].hpc;
drive->tracks = hdc[c].tracks;
}
static struct
@@ -844,15 +844,18 @@ static void xebec_set_switches(xebec_t *xebec)
static void *xebec_init()
{
int i = 0;
int c = 0;
xebec_t *xebec = malloc(sizeof(xebec_t));
memset(xebec, 0, sizeof(xebec_t));
for (i = 0; i < HDC_NUM; i++)
{
if (hdc[i].bus == 1)
if ((hdc[i].bus == 1) && (hdc[i].mfm_channel < MFM_NUM))
{
loadhd(xebec, hdc[i].mfm_channel, hdd_fn[i]);
loadhd(xebec, i, hdc[i].mfm_channel, hdd_fn[i]);
c++;
if (c > MFM_NUM) break;
}
}
@@ -904,15 +907,18 @@ device_t mfm_xebec_device =
static void *dtc_5150x_init()
{
int i = 0;
int c = 0;
xebec_t *xebec = malloc(sizeof(xebec_t));
memset(xebec, 0, sizeof(xebec_t));
for (i = 0; i < HDC_NUM; i++)
{
if (hdc[i].bus == 1)
if ((hdc[i].bus == 1) && (hdc[i].mfm_channel < MFM_NUM))
{
loadhd(xebec, hdc[i].mfm_channel, hdd_fn[i]);
loadhd(xebec, i, hdc[i].mfm_channel, hdd_fn[i]);
c++;
if (c > MFM_NUM) break;
}
}

View File

@@ -26,6 +26,7 @@
#include "ibm.h"
#include "io.h"
#include "mem.h"
#include "mca.h"
#include "rom.h"
#include "dma.h"
#include "pic.h"

View File

@@ -2400,6 +2400,7 @@ LRESULT CALLBACK StatusBarProcedure(HWND hwnd, UINT message, WPARAM wParam, LPAR
return 0;
case WM_LBUTTONDOWN:
case WM_RBUTTONDOWN:
GetClientRect(hwnd, (LPRECT)& rc);
pt.x = GET_X_LPARAM(lParam);
pt.y = GET_Y_LPARAM(lParam);