Diff for /np2/io/fdc.c between versions 1.3 and 1.12

version 1.3, 2003/10/21 11:22:05 version 1.12, 2004/05/07 11:42:29
Line 4 Line 4
   
   
 #include        "compiler.h"  #include        "compiler.h"
   #include        "cpucore.h"
 #include        "pccore.h"  #include        "pccore.h"
 #include        "iocore.h"  #include        "iocore.h"
 #include        "fddfile.h"  #include        "fddfile.h"
   
   enum {
           FDC_DMACH2HD    = 2,
           FDC_DMACH2DD    = 3
   };
   
 static const BYTE FDCCMD_TABLE[32] = {  static const UINT8 FDCCMD_TABLE[32] = {
                                                 0, 0, 8, 2, 1, 8, 8, 1, 0, 8, 1, 0, 8, 5, 0, 2,                                                  0, 0, 8, 2, 1, 8, 8, 1, 0, 8, 1, 0, 8, 5, 0, 2,
                                                 0, 8, 0, 0, 0, 0, 0, 0, 0, 8, 0, 0, 0, 8, 0, 0};                                                  0, 8, 0, 0, 0, 0, 0, 0, 0, 8, 0, 0, 0, 8, 0, 0};
   
   
 #define FDC_FORCEREADY (1)  #define FDC_FORCEREADY (1)
 #define FDC_MAXDRIVE    2  
 #define FDC_DELAYERROR7  #define FDC_DELAYERROR7
   
 void fdc_interrupt(void) {  
   
         fdc.intreq = TRUE;  void fdc_intwait(NEVENTITEM item) {
         if (CTRL_FDMEDIA == DISKTYPE_2HD) {  
                 pic_setirq(0x0b);          if (item->flag & NEVENT_SETEVENT) {
         }                  fdc.intreq = TRUE;
         else {                  if (fdc.chgreg & 1) {
                 pic_setirq(0x0a);                          pic_setirq(0x0b);
                   }
                   else {
                           pic_setirq(0x0a);
                   }
         }          }
         nevent_forceexit();  }
   
   void fdc_interrupt(void) {
   
           nevent_set(NEVENT_FDCINT, 512, fdc_intwait, NEVENT_ABSOLUTE);
 }  }
   
 static void fdc_interruptreset(void) {  static void fdc_interruptreset(void) {
Line 40  static BOOL fdc_isfdcinterrupt(void) { Line 51  static BOOL fdc_isfdcinterrupt(void) {
         return(fdc.intreq);          return(fdc.intreq);
 }  }
   
 BYTE DMACCALL fdc_dmafunc(BYTE func) {  REG8 DMACCALL fdc_dmafunc(REG8 func) {
   
   //      TRACEOUT(("fdc_dmafunc = %d", func));
         switch(func) {          switch(func) {
                 case DMAEXT_START:                  case DMAEXT_START:
                         return(1);                          return(1);
Line 53  BYTE DMACCALL fdc_dmafunc(BYTE func) { Line 65  BYTE DMACCALL fdc_dmafunc(BYTE func) {
         return(0);          return(0);
 }  }
   
 static void fdc_dmaready(BYTE enable) {  static void fdc_dmaready(REG8 enable) {
   
         if (CTRL_FDMEDIA == DISKTYPE_2HD) {          if (fdc.chgreg & 1) {
                 dmac.dmach[DMA_2HD].ready = enable;                  dmac.dmach[FDC_DMACH2HD].ready = enable;
         }          }
         else {          else {
                 dmac.dmach[DMA_2DD].ready = enable;                  dmac.dmach[FDC_DMACH2DD].ready = enable;
         }          }
 }  }
   
 void fdcbusy_error7(NEVENTITEM item) {  
   
         if (item->flag & NEVENT_SETEVENT) {  
                 if (fdc.event == FDCEVENT_BUSY) {  
                         fdcsend_error7();  
                 }  
         }  
 }  
   
 #if 0           // ↑イベントは残しとく...  
 static void fdcderay_error7(SINT16 ms) {                                                        // ver0.27  
   
         fdc.busy = 1;  
         fdc.event = FDCEVENT_BUSY;  
         fdc.status &= ~FDCSTAT_RQM;  
         nevent_setbyms(NEVENT_FDCBUSY, ms, fdcbusy_error7, NEVENT_ABSOLUTE);  
 }  
 #endif  
   
   
 // ----------------------------------------------------------------------  // ----------------------------------------------------------------------
   
Line 143  static void fdc_timeoutset(void) { Line 136  static void fdc_timeoutset(void) {
   
   
   
 static BOOL FDC_DriveCheck(BYTE protectcheck) {  static BOOL FDC_DriveCheck(BOOL protectcheck) {
   
         if (!fddfile[fdc.us].fname[0]) {          if (!fddfile[fdc.us].fname[0]) {
                 fdc.stat[fdc.us] = FDCRLT_IC0 | FDCRLT_NR | (fdc.hd << 2) | fdc.us;                  fdc.stat[fdc.us] = FDCRLT_IC0 | FDCRLT_NR | (fdc.hd << 2) | fdc.us;
Line 245  static void FDC_SenseDeviceStatus(void)  Line 238  static void FDC_SenseDeviceStatus(void) 
                         get_hdus();                          get_hdus();
                         fdc.buf[0] = (fdc.hd << 2) | fdc.us;                          fdc.buf[0] = (fdc.hd << 2) | fdc.us;
                         fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;                          fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;
                         if (fdc.us < FDC_MAXDRIVE) {                          if (fdc.equip & (1 << fdc.us)) {
                                 fdc.buf[0] |= 0x20;                                  fdc.buf[0] |= 0x08;
                                 if (!fddfile[fdc.us].fname[0]) {  
                                         fdc.buf[0] |= 0x08;  
                                 }  
                                 else if (fddfile[fdc.us].protect) {  
                                         fdc.buf[0] |= 0x40;  
                                 }  
                                 if (!fdc.treg[fdc.us]) {                                  if (!fdc.treg[fdc.us]) {
                                         fdc.buf[0] |= 0x10;                                          fdc.buf[0] |= 0x10;
                                 }                                  }
                                   if (fddfile[fdc.us].fname[0]) {
                                           fdc.buf[0] |= 0x20;
                                   }
                                   if (fddfile[fdc.us].protect) {
                                           fdc.buf[0] |= 0x40;
                                   }
                         }                          }
                         else {                          else {
                                 fdc.buf[0] |= 0x80;                                  fdc.buf[0] |= 0x80;
                         }                          }
   //                      TRACEOUT(("FDC_SenseDeviceStatus %.2x", fdc.buf[0]));
                         fdc.event = FDCEVENT_BUFSEND;                          fdc.event = FDCEVENT_BUFSEND;
                         fdc.bufcnt = 1;                          fdc.bufcnt = 1;
                         fdc.bufp = 0;                          fdc.bufp = 0;
Line 352  static void readsector(void) { Line 346  static void readsector(void) {
                 fdcsend_error7();                  fdcsend_error7();
                 return;                  return;
         }          }
   
         fdc.event = FDCEVENT_BUFSEND2;          fdc.event = FDCEVENT_BUFSEND2;
         fdc.bufp = 0;          fdc.bufp = 0;
 #if 1                                                                                                                   // ver0.27 ??  #if 1                                                                                                                   // ver0.27 ??
Line 407  static void FDC_Recalibrate(void) {      Line 402  static void FDC_Recalibrate(void) {     
                         fdc.ncn = 0;                          fdc.ncn = 0;
                         fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;                          fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;
                         fdc.stat[fdc.us] |= FDCRLT_SE;                          fdc.stat[fdc.us] |= FDCRLT_SE;
                         if ((fdc.us >= FDC_MAXDRIVE) || (!fddfile[fdc.us].fname[0])) {                          if (!(fdc.equip & (1 << fdc.us))) {
                                 fdc.stat[fdc.us] |= FDCRLT_NR | FDCRLT_IC0;                                  fdc.stat[fdc.us] |= FDCRLT_NR | FDCRLT_IC0;
                         }                          }
                           else if (!fddfile[fdc.us].fname[0]) {
                                   fdc.stat[fdc.us] |= FDCRLT_NR;
                           }
                         else {                          else {
                                 fdd_seek();                                  fdd_seek();
                         }                          }
Line 436  static void FDC_SenceintStatus(void) {   Line 434  static void FDC_SenceintStatus(void) {  
                         fdc.buf[1] = fdc.treg[fdc.us];                          fdc.buf[1] = fdc.treg[fdc.us];
                         fdc.bufcnt = 2;                          fdc.bufcnt = 2;
                         fdc.stat[fdc.us] = 0;                          fdc.stat[fdc.us] = 0;
   //                      TRACEOUT(("fdc stat - %d [%.2x]", fdc.us, fdc.buf[0]));
                 }                  }
                 else {                  else {
                         for (; i<4; i++) {                          for (; i<4; i++) {
Line 444  static void FDC_SenceintStatus(void) {   Line 443  static void FDC_SenceintStatus(void) {  
                                         fdc.buf[1] = fdc.treg[i];                                          fdc.buf[1] = fdc.treg[i];
                                         fdc.bufcnt = 2;                                          fdc.bufcnt = 2;
                                         fdc.stat[i] = 0;                                          fdc.stat[i] = 0;
   //                                      TRACEOUT(("fdc stat - %d [%.2x]", i, fdc.buf[0]));
                                         break;                                          break;
                                 }                                  }
                         }                          }
Line 453  static void FDC_SenceintStatus(void) {   Line 453  static void FDC_SenceintStatus(void) {  
                                 break;                                  break;
                         }                          }
                 }                  }
                 if (i>=4) {                  if (i >= 4) {
                         fdc_interruptreset();                          fdc_interruptreset();
                 }                  }
         }          }
Line 463  static void FDC_SenceintStatus(void) {   Line 463  static void FDC_SenceintStatus(void) {  
         }          }
 }  }
   
 #if 0   // for test..  
 static void FDC_ReadID(void) {                                                  // cmd: 0a  static void FDC_ReadID(void) {                                                  // cmd: 0a
   
         switch(fdc.event) {          switch(fdc.event) {
                 case FDCEVENT_CMDRECV:                  case FDCEVENT_CMDRECV:
                           fdc.mf = fdc.cmd & 0x40;
                         get_hdus();                          get_hdus();
                           if (fdd_readid() == SUCCESS) {
                                   fdcsend_success7();
                           }
                           else {
                                   fdc.stat[fdc.us] = fdc.us | (fdc.hd << 2) |
                                                                                                           FDCRLT_IC0 | FDCRLT_MA;
                                   fdcsend_error7();
                           }
                         break;                          break;
         }          }
 }  }
 #endif  
   
 static void FDC_WriteID(void) {                                                 // cmd: 0d  static void FDC_WriteID(void) {                                                 // cmd: 0d
   
Line 545  static void FDC_Seek(void) {       // cm Line 552  static void FDC_Seek(void) {       // cm
                         fdc.ncn = fdc.cmds[1];                          fdc.ncn = fdc.cmds[1];
                         fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;                          fdc.stat[fdc.us] = (fdc.hd << 2) | fdc.us;
                         fdc.stat[fdc.us] |= FDCRLT_SE;                          fdc.stat[fdc.us] |= FDCRLT_SE;
                         if ((fdc.us >= FDC_MAXDRIVE) || (!fddfile[fdc.us].fname[0])) {                          if ((!(fdc.equip & (1 << fdc.us))) ||
                                   (!fddfile[fdc.us].fname[0])) {
                                 fdc.stat[fdc.us] |= FDCRLT_NR | FDCRLT_IC0;                                  fdc.stat[fdc.us] |= FDCRLT_NR | FDCRLT_IC0;
                         }                          }
                         else {                          else {
Line 588  static const FDCOPE FDC_Ope[0x20] = { Line 596  static const FDCOPE FDC_Ope[0x20] = {
                                 FDC_Recalibrate,                                  FDC_Recalibrate,
                                 FDC_SenceintStatus,                                  FDC_SenceintStatus,
                                 FDC_WriteData,                                  FDC_WriteData,
                                 FDC_Invalid,                    // FDC_ReadID,                                  FDC_ReadID,
                                 FDC_Invalid,                                  FDC_Invalid,
                                 FDC_ReadData,                                  FDC_ReadData,
                                 FDC_WriteID,                                  FDC_WriteID,
Line 620  static void fdcstatusreset(void) { Line 628  static void fdcstatusreset(void) {
         fdc.status = FDCSTAT_RQM;          fdc.status = FDCSTAT_RQM;
 }  }
   
 void DMACCALL fdc_DataRegWrite(BYTE data) {  void DMACCALL fdc_datawrite(REG8 data) {
   
 //      if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO)) == FDCSTAT_RQM) {  //      if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO)) == FDCSTAT_RQM) {
                 switch(fdc.event) {                  switch(fdc.event) {
Line 659  void DMACCALL fdc_DataRegWrite(BYTE data Line 667  void DMACCALL fdc_DataRegWrite(BYTE data
 //      }  //      }
 }  }
   
   REG8 DMACCALL fdc_dataread(void) {
 BYTE DMACCALL fdc_DataRegRead(void) {  
   
 //      if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO))  //      if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO))
 //                                                                      == (FDCSTAT_RQM | FDCSTAT_DIO)) {  //                                                                      == (FDCSTAT_RQM | FDCSTAT_DIO)) {
Line 675  BYTE DMACCALL fdc_DataRegRead(void) { Line 682  BYTE DMACCALL fdc_DataRegRead(void) {
   
                         case FDCEVENT_BUFSEND2:                          case FDCEVENT_BUFSEND2:
                                 if (fdc.bufcnt) {                                  if (fdc.bufcnt) {
 //                                      TRACE_("read data", fdc.bufp);  
                                         fdc.lastdata = fdc.buf[fdc.bufp++];                                          fdc.lastdata = fdc.buf[fdc.bufp++];
                                         fdc.bufcnt--;                                          fdc.bufcnt--;
                                 }                                  }
Line 704  BYTE DMACCALL fdc_DataRegRead(void) { Line 710  BYTE DMACCALL fdc_DataRegRead(void) {
   
 // ---- I/O  // ---- I/O
   
 static void IOOUTCALL fdc_o92(UINT port, BYTE dat) {  static void IOOUTCALL fdc_o92(UINT port, REG8 dat) {
   
         CTRL_FDMEDIA = DISKTYPE_2HD;          TRACEOUT(("fdc out %.2x %.2x [%.4x:%.4x]", port, dat, CPU_CS, CPU_IP));
   
           if (((port >> 4) ^ fdc.chgreg) & 1) {
                   return;
           }
         if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO)) == FDCSTAT_RQM) {          if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO)) == FDCSTAT_RQM) {
                 fdc_DataRegWrite(dat);                  fdc_datawrite(dat);
         }          }
         (void)port;  
 }  }
   
 static void IOOUTCALL fdc_o94(UINT port, BYTE dat) {  static void IOOUTCALL fdc_o94(UINT port, REG8 dat) {
   
         CTRL_FDMEDIA = DISKTYPE_2HD;          TRACEOUT(("fdc out %.2x %.2x [%.4x:%.4x]", port, dat, CPU_CS, CPU_IP));
   
           if (((port >> 4) ^ fdc.chgreg) & 1) {
                   return;
           }
         if ((fdc.ctrlreg ^ dat) & 0x10) {          if ((fdc.ctrlreg ^ dat) & 0x10) {
                 fdcstatusreset();                  fdcstatusreset();
                 fdc_dmaready(0);                  fdc_dmaready(0);
                 dmac_check();                  dmac_check();
         }          }
         fdc.ctrlreg = dat;          fdc.ctrlreg = dat;
         (void)port;  
 }  }
   
 static BYTE IOINPCALL fdc_i90(UINT port) {  static REG8 IOINPCALL fdc_i90(UINT port) {
   
         CTRL_FDMEDIA = DISKTYPE_2HD;          TRACEOUT(("fdc in %.2x %.2x [%.4x:%.4x]", port, fdc.status,
                                                                                                                           CPU_CS, CPU_IP));
   
         (void)port;          if (((port >> 4) ^ fdc.chgreg) & 1) {
                   return(0xff);
           }
         return(fdc.status);          return(fdc.status);
 }  }
   
 static BYTE IOINPCALL fdc_i92(UINT port) {  static REG8 IOINPCALL fdc_i92(UINT port) {
   
         BYTE    ret;          REG8    ret;
   
         CTRL_FDMEDIA = DISKTYPE_2HD;          if (((port >> 4) ^ fdc.chgreg) & 1) {
                   return(0xff);
           }
         if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO))          if ((fdc.status & (FDCSTAT_RQM | FDCSTAT_DIO))
                                                                                 == (FDCSTAT_RQM | FDCSTAT_DIO)) {                                                                                  == (FDCSTAT_RQM | FDCSTAT_DIO)) {
                 ret = fdc_DataRegRead();                  ret = fdc_dataread();
         }          }
         else {          else {
                 ret = fdc.lastdata;                  ret = fdc.lastdata;
         }          }
         (void)port;          TRACEOUT(("fdc in %.2x %.2x [%.4x:%.4x]", port, ret, CPU_CS, CPU_IP));
         return(ret);          return(ret);
 }  }
   
 static BYTE IOINPCALL fdc_i94(UINT port) {  static REG8 IOINPCALL fdc_i94(UINT port) {
   
         CTRL_FDMEDIA = DISKTYPE_2HD;          if (((port >> 4) ^ fdc.chgreg) & 1) {
                   return(0xff);
         (void)port;          }
         return(0x40);          return(0x40);
 }  }
   
   
 static void IOOUTCALL fdc_oca(UINT port, BYTE dat) {  static void IOOUTCALL fdc_obe(UINT port, REG8 dat) {
   
         CTRL_FDMEDIA = DISKTYPE_2DD;  
         fdc_DataRegWrite(dat);  
         (void)port;  
 }  
   
 static void IOOUTCALL fdc_occ(UINT port, BYTE dat) {  
   
         CTRL_FDMEDIA = DISKTYPE_2DD;  
         fdc.ctrlreg = dat;  
         (void)port;  
 }  
   
 static BYTE IOINPCALL fdc_ic8(UINT port) {  
   
         CTRL_FDMEDIA = DISKTYPE_2DD;  
   
         (void)port;  
         return(fdc.status);  
 }  
   
 static BYTE IOINPCALL fdc_ica(UINT port) {  
   
         BYTE    ret;  
   
         CTRL_FDMEDIA = DISKTYPE_2DD;  
         ret = fdc_DataRegRead();  
   
           fdc.chgreg = dat;
           if (fdc.chgreg & 2) {
                   CTRL_FDMEDIA = DISKTYPE_2HD;
           }
           else {
                   CTRL_FDMEDIA = DISKTYPE_2DD;
           }
         (void)port;          (void)port;
         return(ret);  
 }  }
   
 static BYTE IOINPCALL fdc_icc(UINT port) {  static REG8 IOINPCALL fdc_ibe(UINT port) {
   
         CTRL_FDMEDIA = DISKTYPE_2DD;  
   
         (void)port;          (void)port;
         return(0x74);          return((fdc.chgreg & 3) | 8);
 }  }
   
   static void IOOUTCALL fdc_o4be(UINT port, REG8 dat) {
   
 static void IOOUTCALL fdc_obe(UINT port, BYTE dat) {          fdc.reg144 = dat;
           if (dat & 0x10) {
         fdc.chgreg = dat;                  fdc.rpm[(dat >> 5) & 3] = dat & 1;
           }
         (void)port;          (void)port;
 }  }
   
 static BYTE IOINPCALL fdc_ibe(UINT port) {  static REG8 IOINPCALL fdc_i4be(UINT port) {
   
         (void)port;          (void)port;
         return((fdc.chgreg & 3) | 8);          return(fdc.rpm[(fdc.reg144 >> 5) & 3] | 0xf0);
 }  }
   
   
Line 819  static const IOOUT fdco90[4] = { Line 815  static const IOOUT fdco90[4] = {
                                         NULL,           fdc_o92,        fdc_o94,        NULL};                                          NULL,           fdc_o92,        fdc_o94,        NULL};
 static const IOINP fdci90[4] = {  static const IOINP fdci90[4] = {
                                         fdc_i90,        fdc_i92,        fdc_i94,        NULL};                                          fdc_i90,        fdc_i92,        fdc_i94,        NULL};
 static const IOOUT fdcoc8[4] = {  
                                         NULL,           fdc_oca,        fdc_occ,        NULL};  
 static const IOINP fdcic8[4] = {  
                                         fdc_ic8,        fdc_ica,        fdc_icc,        NULL};  
   
 static const IOOUT fdcobe[1] = {fdc_obe};  static const IOOUT fdcobe[1] = {fdc_obe};
 static const IOINP fdcibe[1] = {fdc_ibe};  static const IOINP fdcibe[1] = {fdc_ibe};
   
 void fdc_reset(void) {  void fdc_reset(void) {
   
         ZeroMemory(&fdc, sizeof(fdc));          ZeroMemory(&fdc, sizeof(fdc));
           fdc.equip = np2cfg.fddequip;
   #if defined(SUPPORT_PC9821)
           fdc.support144 = 1;
   #else
           fdc.support144 = np2cfg.usefd144;
   #endif
         fdcstatusreset();          fdcstatusreset();
           dmac_attach(DMADEV_2HD, FDC_DMACH2HD);
           dmac_attach(DMADEV_2DD, FDC_DMACH2DD);
         CTRL_FDMEDIA = DISKTYPE_2HD;          CTRL_FDMEDIA = DISKTYPE_2HD;
           fdc.chgreg = 3;
 }  }
   
 void fdc_bind(void) {  void fdc_bind(void) {
   
         iocore_attachcmnoutex(0x0090, 0x00f9, fdco90, 4);          iocore_attachcmnoutex(0x0090, 0x00f9, fdco90, 4);
         iocore_attachcmninpex(0x0090, 0x00f9, fdci90, 4);          iocore_attachcmninpex(0x0090, 0x00f9, fdci90, 4);
         iocore_attachcmnoutex(0x00c8, 0x00f9, fdcoc8, 4);          iocore_attachcmnoutex(0x00c8, 0x00f9, fdco90, 4);
         iocore_attachcmninpex(0x00c8, 0x00f9, fdcic8, 4);          iocore_attachcmninpex(0x00c8, 0x00f9, fdci90, 4);
   
           if (fdc.support144) {
                   iocore_attachout(0x04be, fdc_o4be);
                   iocore_attachinp(0x04be, fdc_i4be);
           }
         iocore_attachsysoutex(0x00be, 0x0cff, fdcobe, 1);          iocore_attachsysoutex(0x00be, 0x0cff, fdcobe, 1);
         iocore_attachsysinpex(0x00be, 0x0cff, fdcibe, 1);          iocore_attachsysinpex(0x00be, 0x0cff, fdcibe, 1);
 }  }

Removed from v.1.3  
changed lines
  Added in v.1.12


RetroPC.NET-CVS <cvs@retropc.net>