Merge pull request #3 from folkertvanheusden/multiple-rk05
Multiple rk05
This commit is contained in:
commit
ff9cbd45c4
3 changed files with 37 additions and 48 deletions
34
main.cpp
34
main.cpp
|
@ -164,7 +164,7 @@ int main(int argc, char *argv[])
|
||||||
|
|
||||||
c -> setEmulateMFPT(true);
|
c -> setEmulateMFPT(true);
|
||||||
|
|
||||||
std::string rk05_file;
|
std::vector<std::string> rk05_files;
|
||||||
bool testCases = false;
|
bool testCases = false;
|
||||||
int opt = -1;
|
int opt = -1;
|
||||||
while((opt = getopt(argc, argv, "hm:T:R:p:ndL:")) != -1)
|
while((opt = getopt(argc, argv, "hm:T:R:p:ndL:")) != -1)
|
||||||
|
@ -196,7 +196,7 @@ int main(int argc, char *argv[])
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'R':
|
case 'R':
|
||||||
rk05_file = optarg;
|
rk05_files.push_back(optarg);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'p':
|
case 'p':
|
||||||
|
@ -220,8 +220,8 @@ int main(int argc, char *argv[])
|
||||||
else
|
else
|
||||||
cnsl = new console_posix(&terminate, b);
|
cnsl = new console_posix(&terminate, b);
|
||||||
|
|
||||||
if (rk05_file.empty() == false) {
|
if (rk05_files.empty() == false) {
|
||||||
b->add_rk05(new rk05(rk05_file, b, cnsl->get_disk_read_activity_flag(), cnsl->get_disk_write_activity_flag()));
|
b->add_rk05(new rk05(rk05_files, b, cnsl->get_disk_read_activity_flag(), cnsl->get_disk_write_activity_flag()));
|
||||||
|
|
||||||
setBootLoader(b);
|
setBootLoader(b);
|
||||||
}
|
}
|
||||||
|
@ -262,26 +262,8 @@ int main(int argc, char *argv[])
|
||||||
for(;;) {
|
for(;;) {
|
||||||
c->step();
|
c->step();
|
||||||
|
|
||||||
if (event) {
|
if (event)
|
||||||
#if !defined(ESP32)
|
|
||||||
FILE *fh = fopen("halt.mac", "wb");
|
|
||||||
if (fh) {
|
|
||||||
uint16_t pc = 024320;
|
|
||||||
fprintf(fh, "\t.LINK %06o\n", pc);
|
|
||||||
|
|
||||||
for(int i=0; i<4096; i += 2)
|
|
||||||
fprintf(fh, "\t.DW %06o\n", b->readWord((pc + i) & 0xffff));
|
|
||||||
|
|
||||||
fprintf(fh, "\tmake_raw\n");
|
|
||||||
|
|
||||||
fclose(fh);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
//c->setRegister(7, 01000);
|
|
||||||
//c->resetHalt();
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
|
|
||||||
icount++;
|
icount++;
|
||||||
|
|
||||||
|
@ -301,12 +283,6 @@ int main(int argc, char *argv[])
|
||||||
|
|
||||||
D(fprintf(stderr, "instructions_executed: %u, took_ms: %lu, new refresh_interval: %u\n", icount, took_ms, refresh_interval);)
|
D(fprintf(stderr, "instructions_executed: %u, took_ms: %lu, new refresh_interval: %u\n", icount, took_ms, refresh_interval);)
|
||||||
|
|
||||||
// if (withUI) {
|
|
||||||
// mvwprintw(w_main_b -> win, 0, 24, "%.1f/s ", icount * 1000.0 / took_ms);
|
|
||||||
// mvwprintw(w_main_b -> win, 0, 42, "%06o", b->get_switch_register());
|
|
||||||
// mydoupdate();
|
|
||||||
// }
|
|
||||||
|
|
||||||
if (terminate)
|
if (terminate)
|
||||||
event = 1;
|
event = 1;
|
||||||
|
|
||||||
|
|
44
rk05.cpp
44
rk05.cpp
|
@ -1,4 +1,4 @@
|
||||||
// (C) 2018 by Folkert van Heusden
|
// (C) 2018-2022 by Folkert van Heusden
|
||||||
// Released under Apache License v2.0
|
// Released under Apache License v2.0
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
@ -24,7 +24,7 @@ const char * const regnames[] = {
|
||||||
"RK05_DATABUF "
|
"RK05_DATABUF "
|
||||||
};
|
};
|
||||||
|
|
||||||
rk05::rk05(const std::string & file, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity) :
|
rk05::rk05(const std::vector<std::string> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity) :
|
||||||
b(b),
|
b(b),
|
||||||
disk_read_acitivity(disk_read_acitivity),
|
disk_read_acitivity(disk_read_acitivity),
|
||||||
disk_write_acitivity(disk_write_acitivity)
|
disk_write_acitivity(disk_write_acitivity)
|
||||||
|
@ -64,9 +64,13 @@ rk05::rk05(const std::string & file, bus *const b, std::atomic_bool *const disk_
|
||||||
Serial.println(F("rk05: open failed"));
|
Serial.println(F("rk05: open failed"));
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
fh = fopen(file.c_str(), "rb");
|
for(auto file : files) {
|
||||||
if (!fh)
|
FILE *fh = fopen(file.c_str(), "rb");
|
||||||
error_exit(true, "rk05: cannot open \"%s\"", file.c_str());
|
if (!fh)
|
||||||
|
error_exit(true, "rk05: cannot open \"%s\"", file.c_str());
|
||||||
|
|
||||||
|
fhs.push_back(fh);
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -75,7 +79,8 @@ rk05::~rk05()
|
||||||
#if defined(ESP32)
|
#if defined(ESP32)
|
||||||
fh.close();
|
fh.close();
|
||||||
#else
|
#else
|
||||||
fclose(fh);
|
for(auto fh : fhs)
|
||||||
|
fclose(fh);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -146,15 +151,16 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
|
|
||||||
if (addr == RK05_CS) {
|
if (addr == RK05_CS) {
|
||||||
if (v & 1) { // GO
|
if (v & 1) { // GO
|
||||||
const int func = (v >> 1) & 7; // FUNCTION
|
const int func = (v >> 1) & 7; // FUNCTION
|
||||||
int16_t wc = registers[(RK05_WC - RK05_BASE) / 2];
|
int16_t wc = registers[(RK05_WC - RK05_BASE) / 2];
|
||||||
const size_t reclen = wc < 0 ? (-wc * 2) : wc * 2;
|
const size_t reclen = wc < 0 ? (-wc * 2) : wc * 2;
|
||||||
|
|
||||||
uint16_t dummy = registers[(RK05_DA - RK05_BASE) / 2];
|
uint16_t temp = registers[(RK05_DA - RK05_BASE) / 2];
|
||||||
uint8_t sector = dummy & 0b1111;
|
uint8_t sector = temp & 0b1111;
|
||||||
uint8_t surface = (dummy >> 4) & 1;
|
uint8_t surface = (temp >> 4) & 1;
|
||||||
int track = (dummy >> 4) & 511;
|
int track = (temp >> 4) & 511;
|
||||||
uint16_t cylinder = (dummy >> 5) & 255;
|
uint16_t cylinder = (temp >> 5) & 255;
|
||||||
|
uint8_t device = temp >> 13;
|
||||||
|
|
||||||
const int diskoff = track * 12 + sector;
|
const int diskoff = track * 12 + sector;
|
||||||
|
|
||||||
|
@ -168,7 +174,7 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
else if (func == 1) { // write
|
else if (func == 1) { // write
|
||||||
*disk_write_acitivity = true;
|
*disk_write_acitivity = true;
|
||||||
|
|
||||||
D(fprintf(stderr, "RK05 position sec %d surf %d cyl %d, reclen %zo, WRITE to %o, mem: %o\n", sector, surface, cylinder, reclen, diskoffb, memoff);)
|
D(fprintf(stderr, "RK05 drive %d position sec %d surf %d cyl %d, reclen %zo, WRITE to %o, mem: %o\n", device, sector, surface, cylinder, reclen, diskoffb, memoff);)
|
||||||
|
|
||||||
uint32_t p = reclen; // FIXME
|
uint32_t p = reclen; // FIXME
|
||||||
for(size_t i=0; i<reclen; i++)
|
for(size_t i=0; i<reclen; i++)
|
||||||
|
@ -180,6 +186,7 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
if (fh.write(xfer_buffer, reclen) != reclen)
|
if (fh.write(xfer_buffer, reclen) != reclen)
|
||||||
fprintf(stderr, "RK05 fwrite error %s\n", strerror(errno));
|
fprintf(stderr, "RK05 fwrite error %s\n", strerror(errno));
|
||||||
#else
|
#else
|
||||||
|
FILE *fh = fhs.at(device);
|
||||||
if (fseek(fh, diskoffb, SEEK_SET) == -1)
|
if (fseek(fh, diskoffb, SEEK_SET) == -1)
|
||||||
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
||||||
if (fwrite(xfer_buffer, 1, reclen, fh) != reclen)
|
if (fwrite(xfer_buffer, 1, reclen, fh) != reclen)
|
||||||
|
@ -206,12 +213,13 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
else if (func == 2) { // read
|
else if (func == 2) { // read
|
||||||
*disk_read_acitivity = true;
|
*disk_read_acitivity = true;
|
||||||
|
|
||||||
D(fprintf(stderr, "RK05 position sec %d surf %d cyl %d, reclen %zo, READ from %o, mem: %o\n", sector, surface, cylinder, reclen, diskoffb, memoff);)
|
D(fprintf(stderr, "RK05 drive %d position sec %d surf %d cyl %d, reclen %zo, READ from %o, mem: %o\n", device, sector, surface, cylinder, reclen, diskoffb, memoff);)
|
||||||
|
|
||||||
#if defined(ESP32)
|
#if defined(ESP32)
|
||||||
if (!fh.seek(diskoffb))
|
if (!fh.seek(diskoffb))
|
||||||
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
||||||
#else
|
#else
|
||||||
|
FILE *fh = fhs.at(device);
|
||||||
if (fseek(fh, diskoffb, SEEK_SET) == -1)
|
if (fseek(fh, diskoffb, SEEK_SET) == -1)
|
||||||
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
fprintf(stderr, "RK05 seek error %s\n", strerror(errno));
|
||||||
#endif
|
#endif
|
||||||
|
@ -273,8 +281,12 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
registers[(RK05_CS - RK05_BASE) / 2] |= 128; // control ready
|
registers[(RK05_CS - RK05_BASE) / 2] |= 128; // control ready
|
||||||
|
|
||||||
// bit 6, invoke interrupt when done vector address 220, see http://www.pdp-11.nl/peripherals/disk/rk05-info.html
|
// bit 6, invoke interrupt when done vector address 220, see http://www.pdp-11.nl/peripherals/disk/rk05-info.html
|
||||||
if (v & 64)
|
if (v & 64) {
|
||||||
|
registers[(RK05_DS - RK05_BASE) / 2] &= ~(7 << 13); // store id of the device that caused the interrupt
|
||||||
|
registers[(RK05_DS - RK05_BASE) / 2] |= device << 13;
|
||||||
|
|
||||||
b->getCpu()->queue_interrupt(5, 0220);
|
b->getCpu()->queue_interrupt(5, 0220);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
7
rk05.h
7
rk05.h
|
@ -1,4 +1,4 @@
|
||||||
// (C) 2018 by Folkert van Heusden
|
// (C) 2018-2022 by Folkert van Heusden
|
||||||
// Released under Apache License v2.0
|
// Released under Apache License v2.0
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
@ -6,6 +6,7 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
#if defined(ESP32)
|
#if defined(ESP32)
|
||||||
#include <SPI.h>
|
#include <SPI.h>
|
||||||
|
@ -37,13 +38,13 @@ private:
|
||||||
SdFat32 sd;
|
SdFat32 sd;
|
||||||
File32 fh;
|
File32 fh;
|
||||||
#else
|
#else
|
||||||
FILE *fh;
|
std::vector<FILE *> fhs;
|
||||||
#endif
|
#endif
|
||||||
std::atomic_bool *const disk_read_acitivity { nullptr };
|
std::atomic_bool *const disk_read_acitivity { nullptr };
|
||||||
std::atomic_bool *const disk_write_acitivity { nullptr };
|
std::atomic_bool *const disk_write_acitivity { nullptr };
|
||||||
|
|
||||||
public:
|
public:
|
||||||
rk05(const std::string & file, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
rk05(const std::vector<std::string> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
||||||
virtual ~rk05();
|
virtual ~rk05();
|
||||||
|
|
||||||
uint8_t readByte(const uint16_t addr);
|
uint8_t readByte(const uint16_t addr);
|
||||||
|
|
Loading…
Add table
Reference in a new issue