Пример #1
0
void
Z47Interface::out(BYTE addr,
                  BYTE val)
{
    BYTE offset = getPortOffset(addr);

    debugss(ssH47, ALL, "(%d) = 0x%02x\n", addr, val);

    switch (offset)
    {
        case StatusPort_Offset_c:
            debugss(ssH47, ALL, "StatusPort\n");
            writeStatus(val);
            break;

        case DataPort_Offset_c:
            debugss(ssH47, ALL, " DataPort\n");
            writeData(val);
            break;

        default:
            debugss(ssH47, ERROR, "Unknown Port offset - %d\n", offset);
            break;
    }
}
Пример #2
0
void
HardSectoredDisk::eject(const char* name)
{
    FILE* file;
    debugss(ssFloppyDisk, ALL, "Save: %s\n", name);

    if ((file = fopen(name, "wb")) != nullptr)
    {
        unsigned long readCount;

        for (int head = 0; head < sides_m; head++)
        {
            for (int track = 0; track < tracks_m; track++)
            {
                if ((readCount =
                         fwrite(&rawImage_m[head][track][0], bytesPerTrack_c, 1, file)) != 1)
                {
                    debugss(ssFloppyDisk, ERROR, "Unable to save file: %s head: %d track: %d\n",
                            name, head, track);
                }
            }
        }

        fclose(file);
    }
    else
    {
        debugss(ssFloppyDisk, WARNING, "unable to save file - %s\n", name);
    }
}
Пример #3
0
void
Z47Controller::processReadReadyStatus(void)
{
    debugss(ssH47, ALL, "\n");
    statePosition_m++;

    if (statePosition_m == 2)
    {
        commandComplete();
        return;
    }

    if (statePosition_m != 1)
    {
        debugss(ssH47, ERROR, "Unexpected position\n");
    }

    dataToTransmit_m = readyState;
    curLinkState     = st_Link_AwaitingToTransmit_c;
    countDown_m      = 10;

    // after reading the status, the changed status bits must be reset.
    readyState      &= ~(stat_Ready_Drive0ReadyChanged_c |
                         stat_Ready_Drive1ReadyChanged_c |
                         stat_Ready_Drive2ReadyChanged_c |
                         stat_Ready_Drive3ReadyChanged_c);
}
Пример #4
0
void
Z47Controller::processReadSectorsBufffered(BYTE val)
{
    statePosition_m++;
    debugss(ssH47, ALL, "statePosition: %d\n", statePosition_m);

    if (bytesToTransfer == 0)
    {
        debugss(ssH47, ALL, "All Sectors Read\n");

        commandComplete();
        return;
    }

    if (statePosition_m > 3)
    {
        dataToTransmit_m = diskData[diskOffset++];
        bytesToTransfer--;
        curLinkState     = st_Link_AwaitingToTransmit_c;
        countDown_m      = 10;
        return;
    }

    if (statePosition_m == 3)
    {
        // val passed in is drive and side.
        decodeSideDriveSector(val);

        diskOffset       = track_m * (sectorSize * 26) + ((sector_m - 1) * sectorSize);
        bytesToTransfer  = sectorCount * sectorSize - 1;
        // reset sector count
        sectorCount      = 1;

        dataToTransmit_m = diskData[diskOffset++];
        curLinkState     = st_Link_AwaitingToTransmit_c;
        countDown_m      = 10;
        return;
    }

    if (statePosition_m == 2)
    {
        decodeTrack(val);

        // based on side_m and drive_m set value to return (by asking drive - which asks disk)
        // but for now just say single sided, single density, and sector length byte of 128
        // (which is hopefully 0);

        curLinkState = st_Link_AwaitingToReqReceive_c;
        countDown_m  = 10;
        return;
    }

    if (statePosition_m == 1)
    {
        // val invalid.

        curLinkState = st_Link_AwaitingToReqReceive_c;
        countDown_m  = 10;
    }
}
Пример #5
0
bool
Z47Controller::connectDrive(BYTE       unitNum,
                            DiskDrive* drive)
{
    debugss(ssH47, ALL, "%d - %p\n", unitNum, drive);

    if (unitNum < numDrives_c)
    {
        if (drives_m[unitNum] == 0)
        {
            drives_m[unitNum] = drive;
        }
        else
        {
            debugss(ssH47, ERROR, "drive conflict - %d.\n", unitNum);
            return false;
        }
    }
    else
    {
        debugss(ssH47, ERROR, "invalid drive - %d\n", unitNum);
        return false;
    }

    return true;
}
Пример #6
0
BYTE
Z47Interface::in(BYTE addr)
{
    debugss(ssH47, ALL, "(%d)\n", addr);
    BYTE offset = getPortOffset(addr);
    BYTE data   = 0;

    switch (offset)
    {
        case StatusPort_Offset_c:
            readStatus(data);
            debugss(ssH47, ALL, "StatusPort - 0x%02x\n", data);
            break;

        case DataPort_Offset_c:
            readData(data);
            debugss(ssH47, ALL, "DataPort - 0x%02x\n", data);
            break;

        default:
            debugss(ssH47, ERROR, "Unknown Port offset - %d\n", offset);
            break;
    }

    return data;
}
Пример #7
0
SoftSectoredDisk::SoftSectoredDisk(const char*     name,
                                   DiskImageFormat format): initialized_m(false)
{
    debugss(ssFloppyDisk, INFO, "Insert Disk: %s\n", name);

    if (format == dif_Unknown)
    {
        determineDiskFormat(name, format);
    }

    switch (format)
    {
        case dif_IMD:
            readIMD(name);
            break;

        case dif_TD0:
            readTD0(name);
            break;

        case dif_RAW:
            readRaw(name);
            break;

        case dif_8RAW:
            readRaw8(name);
            break;

        default:
            // Unknown format
            debugss(ssFloppyDisk, ERROR, "Unknown disk format: %d\n", format);

            break;
    }
}
Пример #8
0
bool
MMS77320::connectDrive(BYTE              unitNum,
                       GenericSASIDrive* drive)
{
    bool retVal = false;

    debugss(ssMMS77320, INFO, "unit (%d), drive (%p)\n", unitNum, drive);

    if (unitNum < numDisks_c)
    {
        if (drives_m[unitNum] == NULL)
        {
            drives_m[unitNum] = drive;
            retVal            = true;
        }
        else
        {
            debugss(ssMMS77320, ERROR, "drive already connect\n");
        }
    }
    else
    {
        debugss(ssMMS77320, ERROR, "Invalid unit number (%d)\n", unitNum);
    }

    return (retVal);
}
Пример #9
0
void
Z47Controller::processLoadSectorCount(BYTE val)
{
    debugss(ssH47, ALL, "\n");
    statePosition_m++;

    if (statePosition_m == 3)
    {
        sectorCount |= val;
        debugss(ssH47, ALL, "sector Count = %d\n", sectorCount);

        commandComplete();
        return;
    }

    if (statePosition_m == 2)
    {
        // val passed in is MSB of sector count.
        sectorCount  = (val << 8);

        curLinkState = st_Link_AwaitingToReqReceive_c;
        countDown_m  = 10;
        return;

    }

    if (statePosition_m == 1)
    {
        // val invalid.

        curLinkState = st_Link_AwaitingToReqReceive_c;
        countDown_m  = 10;
    }

}
Пример #10
0
void
Z47Interface::writeStatus(BYTE cmd)
{
    debugss(ssH47, ALL, "cmd = 0x%02x\n", cmd);

    if ((cmd & cmd_MasterReset_c) == cmd_MasterReset_c)
    {
        debugss(ssH47, INFO, "Master Reset\n");
        reset();
    }

    if ((cmd & cmd_U137BSet_c) == cmd_U137BSet_c)
    {
        debugss(ssH47, INFO, "FlipFlop U137B\n");
    }

    if ((cmd & cmd_InterruptsEnabled_c) == cmd_InterruptsEnabled_c)
    {
        debugss(ssH47, INFO, "Interrupts Enabled\n");
        interruptsEnabled_m = true;
    }
    else
    {
        interruptsEnabled_m = false;
    }

    if ((cmd & cmd_Undefined_c) != 0)
    {
        debugss(ssH47, WARNING, "Unexpected command bits: 0x%02x\n", cmd);
    }
}
Пример #11
0
bool
SoftSectoredDisk::readRaw(const char* name)
{
    // Currently just supporting the RAW HDOS 3.0 disk images... 40 track, single density,
    // single sided, 10 sectors/track, 256 bytes/sector.
    std::ifstream     file;
    unsigned long int fileSize;
    unsigned long int pos = 0;
    BYTE*             buf;

    file.open(name, std::ios::binary);

    if (!file.is_open())
    {
        debugss(ssFloppyDisk, ERROR, "Unable to open file: %s\n", name);
        return false;
    }

    file.seekg(0, std::ios::end);
    fileSize = file.tellg();
    file.seekg(0, std::ios::beg);

    buf      = new BYTE[fileSize];
    file.read((char*) buf, fileSize);

    file.close();

    debugss(ssFloppyDisk, INFO, "RAW File: %s\n", name);

    if (fileSize != (256 * 10 * 40))
    {
        debugss(ssFloppyDisk, ERROR, "Invalid File Size: %s - %ld\n", name,
                fileSize);
        delete [] buf;

        return false;
    }

    for (int trk = 0; trk < 40; trk++)
    {
        Track* track = new Track(0, trk);

        for (int sect = 0; sect < 10; sect++, pos += 256)
        {
            Sector* sector = new Sector(0, trk, sect, 256, &buf[pos]);

            track->addSector(sector);
            track->setDensity(Track::singleDensity);
            track->setDataRate(Track::dr_300kbps);
        }

        tracks_m[0].push_back(track);
    }

    numTracks_m   = 40;
    numHeads_m    = 1;
    initialized_m = false;
    return true;
}
Пример #12
0
HardSectoredDisk::HardSectoredDisk(const char* name)
{
    FILE* file;

    initialized_m = true;
    memset(rawImage_m, 0, maxHeads_c * bytesPerTrack_c * maxTracksPerSide_c);

    if ((file = fopen(name, "r")) != nullptr)
    {
        unsigned long readCount;
        int           trk  = 0;
        int           head = 0;

        do
        {
            if (trk == 80)
            {
                // Check to see if we read both sides.
                if (head == 1)
                {
                    break;
                }

                trk = 0;
                head++;
            }

            if ((readCount =
                     fread(&rawImage_m[head][trk][0], bytesPerTrack_c, 1, file)) == 1)
            {
                trk++;
            }
            else if ((trk == 0) && (head == 1))
            {
                // check to see if we have to adjust side and track.
                head = 0;
                trk  = 80;
            }
        }
        while (readCount == 1);

        tracks_m = trk;
        sides_m  = head + 1;
        debugss(ssFloppyDisk, ALL, "Sides: %d  Tracks: %d\n", sides_m, tracks_m);
        fclose(file);
    }
    else
    {
        debugss(ssFloppyDisk, ERROR, "unable to open file - %s\n", name);
        initialized_m = false;
    }

    if (initialized_m)
    {
        debugss(ssFloppyDisk, INFO, "Success %s\n", name);
    }
}
Пример #13
0
void
MMS77316::out(BYTE addr,
              BYTE val)
{
    BYTE offset = getPortOffset(addr);

    debugss(ssMMS77316, VERBOSE, "(addr: %d, %d (0x%x))\n", addr, val, val);

    if (offset >= Wd1797_Offset_c)
    {
        offset -= Wd1797_Offset_c;

        if (offset == WD1797::DataPort_Offset_c)
        {
            // See notes for MMS77316::in()...
            int timeout = 0;

            while (burstMode() && !drqRaised_m && !intrqRaised_m && ++timeout < 16)
            {
                wd1797_m->waitForData();
            }
        }

        wd1797_m->out(offset, val);
    }
    else if (offset == ControlPort_Offset_c)
    {
        debugss(ssMMS77316, VERBOSE, "(ControlPort) %02x\n", val);
        controlReg_m = val;
        drqCount_m   = 0;

        if ((controlReg_m & ctrl_525DriveSel_c) != 0)
        {
            GenericFloppyDrive* drive = getCurrentDrive();

            if (drive)
            {
                drive->motor(true);
            }
        }

        wd1797_m->setDoubleDensity((controlReg_m & ctrl_SetMFMRecordingN_c) == 0);

        if ((controlReg_m & ctrl_EnableIntReq_c) != 0 && (intrqRaised_m || drqRaised_m))
        {
            // Interrupt still pending, but now un-masked. Raise it.
            ic_m->setIntrq(intrqRaised_m);
            ic_m->setDrq(drqRaised_m);
        }

    }
    else
    {
        debugss(ssMMS77316, ERROR, "(Unknown addr- 0x%02x): %d\n", addr, val);
    }
}
Пример #14
0
GenericFloppyDrive*
GenericFloppyDrive::getInstance(std::string type)
{
    unsigned int heads;
    unsigned int tracks;
    unsigned int mediaSize;

    if (type.find("FDD_5_25") == 0)
    {
        mediaSize = 5;

        if (type.find("ST") != std::string::npos)
        {
            tracks = 40;
        }
        else if (type.find("DT") != std::string::npos)
        {
            tracks = 80;
        }
        else
        {
            debugss(ssGenericFloppyDrive, ERROR, "number of tracks not specified\n");
            return nullptr;
        }
    }
    else if (type.find("FDD_8" == 0))
    {
        mediaSize = 8;
        tracks    = 77;
    }
    else
    {
        debugss(ssGenericFloppyDrive, ERROR, "disk size not specified\n");
        return NULL;
    }

    if (type.find("SS") != std::string::npos)
    {
        heads = 1;
    }
    else if (type.find("DS") != std::string::npos)
    {
        heads = 2;
    }
    else
    {
        debugss(ssGenericFloppyDrive, ERROR, "number of sides not specified\n");
        return nullptr;
    }

    return new GenericFloppyDrive(heads, tracks, mediaSize);
}
Пример #15
0
void
Z47Interface::writeData(BYTE data)
{
    debugss(ssH47, ALL, "data = 0x%02x\n", data);

    if (linkToDrive_m)
    {
        linkToDrive_m->sendDriveData(data);
    }
    else
    {
        debugss(ssH47, ERROR, "link to Drive not configured\n");
    }
}
Пример #16
0
void
Z47Controller::connectHostLink(ParallelLink* link)
{
    debugss(ssH47, ALL, "\n");
    linkToHost_m = link;

    if (linkToHost_m)
    {
        linkToHost_m->registerDevice(this);
    }
    else
    {
        debugss(ssH47, ERROR, "link invalid\n");
    }
}
Пример #17
0
void
IOBus::out(BYTE addr,
           BYTE val)
{
    debugss(ssIO, ALL, "(%03o) = 0x%02x\n", addr, val);

    if (iodevices[addr])
    {
        iodevices[addr]->out(addr, val);
    }
    else
    {
        debugss(ssIO, WARNING, "undefined port (%03o) = 0x%02x\n", addr, val);
    }
}
Пример #18
0
bool
IOBus::removeDevice(IODevice* device)
{
    bool retVal = true;

    if (device)
    {
        BYTE base = device->getBaseAddress();
        BYTE num  = device->getNumPorts();
        BYTE last = base + num;

        debugss(ssIO, INFO, "ports (%03o - %03o)\n", base, last);

        if (num)
        {
            for (BYTE port = base; port < last; ++port)
            {
                if (iodevices[port] == device)
                {
                    // TODO: call destructor? (i.e. "delete iodevices[port];"?)
                    iodevices[port] = 0;
                }
                else
                {
                    // Doesn't match what is attempting to be removed.
                    debugss(ssIO, ERROR, "non-matching device on port (%03o)\n", port);
                    retVal = false;
                }
            }
        }
        else
        {
            // no ports.
            debugss(ssIO, ERROR, "no ports\n");

            retVal = false;
        }
    }
    else
    {
        // NULL device passed in
        debugss(ssIO, ERROR, "Null Device\n");

        retVal = false;
    }

    return (retVal);
}
Пример #19
0
void
Z47Interface::connectDriveLink(ParallelLink* link)
{
    debugss(ssH47, ALL, "\n");

    linkToDrive_m = link;

    if (linkToDrive_m)
    {
        linkToDrive_m->registerHost(this);
    }
    else
    {
        debugss(ssH47, ERROR, "link to Drive not configured\n");
    }
}
Пример #20
0
void
Z47Controller::processFormatDoubleDensity(BYTE val)
{
    debugss(ssH47, ALL, "\n");
    statePosition_m++;

    if (statePosition_m == 3)
    {
        commandComplete();
        return;

    }

    if (statePosition_m == 2)
    {
        //
        decodeSideDriveSector(val);

        countDown_m  = 10000;
        memset(&diskData[0], 0xe5, 256256);

        curLinkState = st_Link_AwaitingControllerComplete_c;
        return;
    }

    if (statePosition_m == 1)
    {
        // val invalid.

        curLinkState = st_Link_AwaitingToReqReceive_c;
        countDown_m  = 10;
    }


}
Пример #21
0
void
MMS77316::lowerIntrq()
{
    debugss(ssMMS77316, INFO, "\n");

    intrqRaised_m = false;
    ic_m->setIntrq(intrqRaised_m);
}
Пример #22
0
void
MMS77316::lowerDrq()
{
    debugss(ssMMS77316, INFO, "\n");

    drqRaised_m = false;
    ic_m->setDrq(drqRaised_m);
}
Пример #23
0
void
SoftSectoredDisk::determineDiskFormat(const char*      name,
                                      DiskImageFormat& format)
{
    debugss(ssFloppyDisk, INFO, "Name: %s\n", name);
    /// \todo implement
    format = dif_Unknown;
}
Пример #24
0
ROM::~ROM()
{
    debugss(ssROM, INFO, "Destroying ROM\n");

    delete[] data_m;
    data_m = 0;
    size_m = 0;
}
Пример #25
0
void
Z47Controller::pulseSignal(SignalType sigType)
{
    debugss(ssH47, ALL, "\n");

    raiseSignal(sigType);
    lowerSignal(sigType);
}
Пример #26
0
bool
IOBus::addDevice(IODevice* device)
{
    debugss(ssIO, INFO, "\n");

    if (device == nullptr)
    {
        // NULL device passed in
        debugss(ssIO, ERROR, "Null Device\n");
        return (false);
    }

    BYTE base = device->getBaseAddress();
    BYTE num  = device->getNumPorts();
    BYTE last = base + num;

    debugss(ssIO, INFO, "ports (%03o - %03o)\n", base, last);

    if (!num)
    {
        // no ports.
        debugss(ssIO, ERROR, "no ports\n");

        return (false);
    }

    // First make sure there is no conflict
    for (BYTE port = base; port < last; ++port)
    {
        if (iodevices[port])
        {
            // Address already in use
            debugss(ssIO, ERROR, "duplicate devices on port (%03o)\n", port);
            return (false);
        }
    }

    // Now set the new value
    for (BYTE port = base; port < last; ++port)
    {
        iodevices[port] = device;
    }

    return (true);
}
Пример #27
0
void
ROM::writeByte(WORD addr,
               BYTE val)
{
    // can't write to ROM.
    /// \todo update to set the RAM.
    debugss(ssROM, INFO, "Attempting to write to ROM [%d] = %d\n", addr, val);
    return;
}
Пример #28
0
ROM::ROM(int size):
    data_m(0),
    base_m(0),
    size_m(size)
{
    debugss(ssROM, INFO, "Creating ROM: %d\n", size_m);

    data_m = new BYTE[size_m];
}
Пример #29
0
void
Z47Controller::commandComplete(void)
{
    debugss(ssH47, ALL, "state: %s\n", getStateStr(curState));

    curState     = st_None_c;
    curLinkState = st_Link_AwaitingReadyState_c;
    countDown_m  = 120;

    if (linkToHost_m)
    {
        linkToHost_m->setBusy(false);
        // linkToHost_m->setDTR(true);
    }

    debugss(ssH47, ALL, "=============END of CMD============\n");

}
Пример #30
0
IOBus::IOBus()
{
    debugss(ssIO, INFO, "%\n");

    for (int port = 0; port < 256; ++port)
    {
        iodevices[port] = 0;
    }
}