disk backend
This commit is contained in:
parent
a672841865
commit
6236d96b83
10 changed files with 117 additions and 162 deletions
|
@ -14,6 +14,8 @@ add_executable(
|
||||||
console_posix.cpp
|
console_posix.cpp
|
||||||
cpu.cpp
|
cpu.cpp
|
||||||
debugger.cpp
|
debugger.cpp
|
||||||
|
disk_backend.cpp
|
||||||
|
disk_backend_file.cpp
|
||||||
error.cpp
|
error.cpp
|
||||||
kw11-l.cpp
|
kw11-l.cpp
|
||||||
loaders.cpp
|
loaders.cpp
|
||||||
|
|
9
disk_backend.cpp
Normal file
9
disk_backend.cpp
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
#include "disk_backend.h"
|
||||||
|
|
||||||
|
disk_backend::disk_backend()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
disk_backend::~disk_backend()
|
||||||
|
{
|
||||||
|
}
|
16
disk_backend.h
Normal file
16
disk_backend.h
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
|
||||||
|
class disk_backend
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
disk_backend();
|
||||||
|
virtual ~disk_backend();
|
||||||
|
|
||||||
|
virtual bool read(const off_t offset, const size_t n, uint8_t *const target) = 0;
|
||||||
|
|
||||||
|
virtual bool write(const off_t offset, const size_t n, const uint8_t *const from) = 0;
|
||||||
|
};
|
30
disk_backend_file.cpp
Normal file
30
disk_backend_file.cpp
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
#include "disk_backend_file.h"
|
||||||
|
#include "log.h"
|
||||||
|
|
||||||
|
|
||||||
|
disk_backend_file::disk_backend_file(const std::string & filename) :
|
||||||
|
fd(open(filename.c_str(), O_RDWR))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
disk_backend_file::~disk_backend_file()
|
||||||
|
{
|
||||||
|
close(fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool disk_backend_file::read(const off_t offset, const size_t n, uint8_t *const target)
|
||||||
|
{
|
||||||
|
DOLOG(debug, false, "disk_backend_file::read: read %zu bytes from offset %zu", n, offset);
|
||||||
|
|
||||||
|
return pread(fd, target, n, offset) == ssize_t(n);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool disk_backend_file::write(const off_t offset, const size_t n, const uint8_t *const from)
|
||||||
|
{
|
||||||
|
DOLOG(debug, false, "disk_backend_file::write: write %zu bytes to offset %zu", n, offset);
|
||||||
|
|
||||||
|
return pwrite(fd, from, n, offset) == ssize_t(n);
|
||||||
|
}
|
18
disk_backend_file.h
Normal file
18
disk_backend_file.h
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#include "disk_backend.h"
|
||||||
|
|
||||||
|
|
||||||
|
class disk_backend_file : public disk_backend
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
const int fd { -1 };
|
||||||
|
|
||||||
|
public:
|
||||||
|
disk_backend_file(const std::string & filename);
|
||||||
|
virtual ~disk_backend_file();
|
||||||
|
|
||||||
|
bool read(const off_t offset, const size_t n, uint8_t *const target);
|
||||||
|
|
||||||
|
bool write(const off_t offset, const size_t n, const uint8_t *const from);
|
||||||
|
};
|
10
main.cpp
10
main.cpp
|
@ -12,6 +12,8 @@
|
||||||
#include "console_posix.h"
|
#include "console_posix.h"
|
||||||
#include "cpu.h"
|
#include "cpu.h"
|
||||||
#include "debugger.h"
|
#include "debugger.h"
|
||||||
|
#include "disk_backend.h"
|
||||||
|
#include "disk_backend_file.h"
|
||||||
#include "gen.h"
|
#include "gen.h"
|
||||||
#include "kw11-l.h"
|
#include "kw11-l.h"
|
||||||
#include "loaders.h"
|
#include "loaders.h"
|
||||||
|
@ -59,8 +61,8 @@ int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
//setlocale(LC_ALL, "");
|
//setlocale(LC_ALL, "");
|
||||||
|
|
||||||
std::vector<std::string> rk05_files;
|
std::vector<disk_backend *> rk05_files;
|
||||||
std::vector<std::string> rl02_files;
|
std::vector<disk_backend *> rl02_files;
|
||||||
|
|
||||||
bool run_debugger = false;
|
bool run_debugger = false;
|
||||||
bool tracing = false;
|
bool tracing = false;
|
||||||
|
@ -132,11 +134,11 @@ int main(int argc, char *argv[])
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'R':
|
case 'R':
|
||||||
rk05_files.push_back(optarg);
|
rk05_files.push_back(new disk_backend_file(optarg));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'r':
|
case 'r':
|
||||||
rl02_files.push_back(optarg);
|
rl02_files.push_back(new disk_backend_file(optarg));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'p':
|
case 'p':
|
||||||
|
|
82
rk05.cpp
82
rk05.cpp
|
@ -22,42 +22,21 @@ static const char * const regnames[] = {
|
||||||
"RK05_DATABUF "
|
"RK05_DATABUF "
|
||||||
};
|
};
|
||||||
|
|
||||||
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) :
|
rk05::rk05(const std::vector<disk_backend *> & 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)
|
||||||
{
|
{
|
||||||
memset(registers, 0x00, sizeof registers);
|
memset(registers, 0x00, sizeof registers );
|
||||||
memset(xfer_buffer, 0x00, sizeof xfer_buffer);
|
memset(xfer_buffer, 0x00, sizeof xfer_buffer);
|
||||||
|
|
||||||
for(auto file : files) {
|
fhs = files;
|
||||||
#if defined(ESP32)
|
|
||||||
File32 *fh = new File32();
|
|
||||||
|
|
||||||
if (!fh->open(file.c_str(), O_RDWR)) {
|
|
||||||
delete fh;
|
|
||||||
error_exit(true, "rk05: cannot open \"%s\"", file.c_str());
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
FILE *fh = fopen(file.c_str(), "rb");
|
|
||||||
if (!fh)
|
|
||||||
error_exit(true, "rk05: cannot open \"%s\"", file.c_str());
|
|
||||||
#endif
|
|
||||||
|
|
||||||
fhs.push_back(fh);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
rk05::~rk05()
|
rk05::~rk05()
|
||||||
{
|
{
|
||||||
for(auto fh : fhs) {
|
for(auto fh : fhs)
|
||||||
#if defined(ESP32)
|
|
||||||
fh->close();
|
|
||||||
delete fh;
|
delete fh;
|
||||||
#else
|
|
||||||
fclose(fh);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t rk05::readByte(const uint16_t addr)
|
uint8_t rk05::readByte(const uint16_t addr)
|
||||||
|
@ -158,19 +137,8 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
for(size_t i=0; i<reclen; i++)
|
for(size_t i=0; i<reclen; i++)
|
||||||
xfer_buffer[i] = b->readUnibusByte(memoff + i);
|
xfer_buffer[i] = b->readUnibusByte(memoff + i);
|
||||||
|
|
||||||
#if defined(ESP32)
|
if (!fhs.at(device)->write(diskoffb, reclen, xfer_buffer))
|
||||||
File32 *fh = fhs.at(device);
|
DOLOG(ll_error, true, "RK05 pwrite error %s", strerror(errno));
|
||||||
if (!fh->seek(diskoffb))
|
|
||||||
DOLOG(ll_error, true, "RK05 seek error %s", strerror(errno));
|
|
||||||
if (fh->write(xfer_buffer, reclen) != reclen)
|
|
||||||
DOLOG(ll_error, true, "RK05 fwrite error %s", strerror(errno));
|
|
||||||
#else
|
|
||||||
FILE *fh = fhs.at(device);
|
|
||||||
if (fseek(fh, diskoffb, SEEK_SET) == -1)
|
|
||||||
DOLOG(ll_error, true, "RK05 seek error %s", strerror(errno));
|
|
||||||
if (fwrite(xfer_buffer, 1, reclen, fh) != reclen)
|
|
||||||
DOLOG(ll_error, true, "RK05 fwrite error %s", strerror(errno));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (v & 2048)
|
if (v & 2048)
|
||||||
DOLOG(debug, true, "RK05 inhibit BA increase");
|
DOLOG(debug, true, "RK05 inhibit BA increase");
|
||||||
|
@ -194,43 +162,19 @@ void rk05::writeWord(const uint16_t addr, uint16_t v)
|
||||||
|
|
||||||
DOLOG(debug, true, "RK05 drive %d position sec %d surf %d cyl %d, reclen %zo, READ from %o, mem: %o", device, sector, surface, cylinder, reclen, diskoffb, memoff);
|
DOLOG(debug, true, "RK05 drive %d position sec %d surf %d cyl %d, reclen %zo, READ from %o, mem: %o", device, sector, surface, cylinder, reclen, diskoffb, memoff);
|
||||||
|
|
||||||
bool proceed = true;
|
int temp_diskoffb = diskoffb;
|
||||||
|
|
||||||
#if defined(ESP32)
|
|
||||||
File32 *fh = fhs.at(device);
|
|
||||||
if (!fh->seek(diskoffb)) {
|
|
||||||
DOLOG(ll_error, true, "RK05 seek error %s", strerror(errno));
|
|
||||||
proceed = false;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
FILE *fh = nullptr;
|
|
||||||
|
|
||||||
if (device >= fhs.size())
|
|
||||||
proceed = false;
|
|
||||||
else {
|
|
||||||
fh = fhs.at(device);
|
|
||||||
|
|
||||||
if (fseek(fh, diskoffb, SEEK_SET) == -1) {
|
|
||||||
DOLOG(ll_error, true, "RK05 seek error %s", strerror(errno));
|
|
||||||
proceed = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
uint32_t temp = reclen;
|
uint32_t temp = reclen;
|
||||||
uint32_t p = memoff;
|
uint32_t p = memoff;
|
||||||
while(proceed && temp > 0) {
|
while(temp > 0) {
|
||||||
uint32_t cur = std::min(uint32_t(sizeof xfer_buffer), temp);
|
uint32_t cur = std::min(uint32_t(sizeof xfer_buffer), temp);
|
||||||
|
|
||||||
#if defined(ESP32)
|
if (!fhs.at(device)->read(temp_diskoffb, cur, xfer_buffer)) {
|
||||||
yield();
|
DOLOG(ll_error, true, "RK05 read error %s", strerror(errno));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if (fh->read(xfer_buffer, cur) != size_t(cur))
|
temp_diskoffb += cur;
|
||||||
DOLOG(debug, true, "RK05 fread error: %s", strerror(errno));
|
|
||||||
#else
|
|
||||||
if (fread(xfer_buffer, 1, cur, fh) != size_t(cur))
|
|
||||||
DOLOG(debug, true, "RK05 fread error: %s", strerror(errno));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
for(uint32_t i=0; i<cur; i++) {
|
for(uint32_t i=0; i<cur; i++) {
|
||||||
if (p < 0160000)
|
if (p < 0160000)
|
||||||
|
|
19
rk05.h
19
rk05.h
|
@ -1,4 +1,4 @@
|
||||||
// (C) 2018-2022 by Folkert van Heusden
|
// (C) 2018-2023 by Folkert van Heusden
|
||||||
// Released under Apache License v2.0
|
// Released under Apache License v2.0
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
@ -8,9 +8,7 @@
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#if defined(ESP32)
|
#include "disk_backend.h"
|
||||||
#include "esp32.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
#define RK05_DS 0177400 // drive status
|
#define RK05_DS 0177400 // drive status
|
||||||
|
@ -28,19 +26,16 @@ class bus;
|
||||||
class rk05
|
class rk05
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
bus *const b;
|
bus *const b { nullptr };
|
||||||
uint16_t registers[7];
|
uint16_t registers [ 7];
|
||||||
uint8_t xfer_buffer[512];
|
uint8_t xfer_buffer[512];
|
||||||
#if defined(ESP32)
|
std::vector<disk_backend *> fhs;
|
||||||
std::vector<File32 *> fhs;
|
|
||||||
#else
|
|
||||||
std::vector<FILE *> fhs;
|
|
||||||
#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::vector<std::string> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
rk05(const std::vector<disk_backend *> & 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);
|
||||||
|
|
75
rl02.cpp
75
rl02.cpp
|
@ -22,7 +22,7 @@ static const char * const regnames[] = {
|
||||||
"multipurpose "
|
"multipurpose "
|
||||||
};
|
};
|
||||||
|
|
||||||
rl02::rl02(const std::vector<std::string> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity) :
|
rl02::rl02(const std::vector<disk_backend *> & 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)
|
||||||
|
@ -30,34 +30,13 @@ rl02::rl02(const std::vector<std::string> & files, bus *const b, std::atomic_boo
|
||||||
memset(registers, 0x00, sizeof registers);
|
memset(registers, 0x00, sizeof registers);
|
||||||
memset(xfer_buffer, 0x00, sizeof xfer_buffer);
|
memset(xfer_buffer, 0x00, sizeof xfer_buffer);
|
||||||
|
|
||||||
for(auto file : files) {
|
fhs = files;
|
||||||
#if defined(ESP32)
|
|
||||||
File32 *fh = new File32();
|
|
||||||
|
|
||||||
if (!fh->open(file.c_str(), O_RDWR)) {
|
|
||||||
delete fh;
|
|
||||||
error_exit(true, "rl02: cannot open \"%s\"", file.c_str());
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
FILE *fh = fopen(file.c_str(), "rb");
|
|
||||||
if (!fh)
|
|
||||||
error_exit(true, "rl02: cannot open \"%s\"", file.c_str());
|
|
||||||
#endif
|
|
||||||
|
|
||||||
fhs.push_back(fh);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
rl02::~rl02()
|
rl02::~rl02()
|
||||||
{
|
{
|
||||||
for(auto fh : fhs) {
|
for(auto fh : fhs)
|
||||||
#if defined(ESP32)
|
|
||||||
fh->close();
|
|
||||||
delete fh;
|
delete fh;
|
||||||
#else
|
|
||||||
fclose(fh);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t rl02::readByte(const uint16_t addr)
|
uint8_t rl02::readByte(const uint16_t addr)
|
||||||
|
@ -138,44 +117,13 @@ void rl02::writeWord(const uint16_t addr, uint16_t v)
|
||||||
|
|
||||||
if (command == 2) { // get status
|
if (command == 2) { // get status
|
||||||
registers[(RL02_MPR - RL02_BASE) / 2] = 0;
|
registers[(RL02_MPR - RL02_BASE) / 2] = 0;
|
||||||
#if 0
|
|
||||||
if (registers[(RL02_DAR - RL02_BASE) / 2] & 2) { // get status -> load status word in MPR
|
|
||||||
registers[(RL02_MPR - RL02_BASE) / 2] = 5 | // lock on
|
|
||||||
(1 << 3) | // brushes are home
|
|
||||||
(1 << 7) | // this is an RL02
|
|
||||||
0;
|
|
||||||
|
|
||||||
DOLOG(debug, true, "RL02 set MPR for status to %06o", registers[(RL02_MPR - RL02_BASE) / 2]);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
else if (command == 6 || command == 7) { // read data / read data without header check
|
else if (command == 6 || command == 7) { // read data / read data without header check
|
||||||
*disk_read_acitivity = true;
|
*disk_read_acitivity = true;
|
||||||
|
|
||||||
bool proceed = true;
|
bool proceed = true;
|
||||||
|
|
||||||
#if defined(ESP32)
|
uint32_t temp_disk_offset = disk_offset;
|
||||||
File32 *fh = fhs.at(device);
|
|
||||||
|
|
||||||
if (!fh->seek(disk_offset)) {
|
|
||||||
DOLOG(ll_error, true, "RL02 seek to %d error %s", disk_offset, strerror(errno));
|
|
||||||
|
|
||||||
proceed = false;
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
FILE *fh = nullptr;
|
|
||||||
|
|
||||||
if (size_t(device) >= fhs.size())
|
|
||||||
proceed = false;
|
|
||||||
else {
|
|
||||||
fh = fhs.at(device);
|
|
||||||
|
|
||||||
if (fseek(fh, disk_offset, SEEK_SET) == -1) {
|
|
||||||
DOLOG(ll_error, true, "RL02 seek error %s", strerror(errno));
|
|
||||||
proceed = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
uint32_t memory_address = registers[(RL02_BAR - RL02_BASE) / 2];
|
uint32_t memory_address = registers[(RL02_BAR - RL02_BASE) / 2];
|
||||||
|
|
||||||
|
@ -187,19 +135,16 @@ void rl02::writeWord(const uint16_t addr, uint16_t v)
|
||||||
while(proceed && count > 0) {
|
while(proceed && count > 0) {
|
||||||
uint32_t cur = std::min(uint32_t(sizeof xfer_buffer), count);
|
uint32_t cur = std::min(uint32_t(sizeof xfer_buffer), count);
|
||||||
|
|
||||||
#if defined(ESP32)
|
if (!fhs.at(device)->read(temp_disk_offset, cur, xfer_buffer)) {
|
||||||
yield();
|
DOLOG(ll_error, true, "RL02 read error %s", strerror(errno));
|
||||||
|
break;
|
||||||
if (fh->read(xfer_buffer, cur) != size_t(cur))
|
}
|
||||||
DOLOG(info, true, "RL02 fread error: %s", strerror(errno));
|
|
||||||
#else
|
|
||||||
if (fread(xfer_buffer, 1, cur, fh) != size_t(cur))
|
|
||||||
DOLOG(info, true, "RL02 fread error: %s", strerror(errno));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
for(uint32_t i=0; i<cur; i++, p++)
|
for(uint32_t i=0; i<cur; i++, p++)
|
||||||
b->writeByte(p, xfer_buffer[i]);
|
b->writeByte(p, xfer_buffer[i]);
|
||||||
|
|
||||||
|
temp_disk_offset += cur;
|
||||||
|
|
||||||
count -= cur;
|
count -= cur;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
16
rl02.h
16
rl02.h
|
@ -1,4 +1,4 @@
|
||||||
// (C) 2022 by Folkert van Heusden
|
// (C) 2023 by Folkert van Heusden
|
||||||
// Released under Apache License v2.0
|
// Released under Apache License v2.0
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
@ -8,9 +8,8 @@
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#if defined(ESP32)
|
#include "disk_backend.h"
|
||||||
#include "esp32.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define RL02_CSR 0174400 // control status register
|
#define RL02_CSR 0174400 // control status register
|
||||||
#define RL02_BAR 0174402 // bus address register
|
#define RL02_BAR 0174402 // bus address register
|
||||||
|
@ -27,12 +26,7 @@ private:
|
||||||
bus *const b;
|
bus *const b;
|
||||||
uint16_t registers[4];
|
uint16_t registers[4];
|
||||||
uint8_t xfer_buffer[512];
|
uint8_t xfer_buffer[512];
|
||||||
|
std::vector<disk_backend *> fhs;
|
||||||
#if defined(ESP32)
|
|
||||||
std::vector<File32 *> fhs;
|
|
||||||
#else
|
|
||||||
std::vector<FILE *> fhs;
|
|
||||||
#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 };
|
||||||
|
@ -40,7 +34,7 @@ private:
|
||||||
uint32_t calcOffset(uint16_t);
|
uint32_t calcOffset(uint16_t);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
rl02(const std::vector<std::string> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
rl02(const std::vector<disk_backend *> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
||||||
virtual ~rl02();
|
virtual ~rl02();
|
||||||
|
|
||||||
uint8_t readByte(const uint16_t addr);
|
uint8_t readByte(const uint16_t addr);
|
||||||
|
|
Loading…
Add table
Reference in a new issue