code clean-up
This commit is contained in:
parent
92c5c2c573
commit
1aa6c47f8e
2 changed files with 68 additions and 21 deletions
76
rl02.cpp
76
rl02.cpp
|
@ -1,4 +1,4 @@
|
|||
// (C) 2018-2023 by Folkert van Heusden
|
||||
// (C) 2018-2024 by Folkert van Heusden
|
||||
// Released under MIT license
|
||||
|
||||
#include <errno.h>
|
||||
|
@ -13,9 +13,6 @@
|
|||
#include "utils.h"
|
||||
|
||||
|
||||
constexpr int sectors_per_track = 40;
|
||||
constexpr int bytes_per_sector = 256;
|
||||
|
||||
static const char * const regnames[] = {
|
||||
"control status",
|
||||
"bus address ",
|
||||
|
@ -43,6 +40,10 @@ void rl02::reset()
|
|||
{
|
||||
memset(registers, 0x00, sizeof registers);
|
||||
memset(xfer_buffer, 0x00, sizeof xfer_buffer);
|
||||
|
||||
track = 0;
|
||||
head = 0;
|
||||
sector = 0;
|
||||
}
|
||||
|
||||
uint8_t rl02::readByte(const uint16_t addr)
|
||||
|
@ -102,13 +103,9 @@ void rl02::update_bus_address(const uint32_t a)
|
|||
registers[(RL02_CSR - RL02_BASE) / 2] |= ((a >> 16) & 3) << 4;
|
||||
}
|
||||
|
||||
uint32_t rl02::calcOffset(const uint16_t da) const
|
||||
uint32_t rl02::calcOffset() const
|
||||
{
|
||||
int sector = da & 63;
|
||||
int track = (da >> 6) & 1023;
|
||||
uint32_t offset = (sectors_per_track * track + sector) * bytes_per_sector;
|
||||
|
||||
return offset;
|
||||
return (rl02_sectors_per_track * track * 2 + head * rl02_sectors_per_track + sector) * rl02_bytes_per_sector;
|
||||
}
|
||||
|
||||
void rl02::writeWord(const uint16_t addr, uint16_t v)
|
||||
|
@ -126,22 +123,49 @@ void rl02::writeWord(const uint16_t addr, uint16_t v)
|
|||
|
||||
DOLOG(debug, false, "RL02 set command %d, exec: %d", command, do_exec);
|
||||
|
||||
uint32_t disk_offset = calcOffset(registers[(RL02_DAR - RL02_BASE) / 2] & ~1);
|
||||
int device = 0; // TODO
|
||||
int device = 0; // TODO
|
||||
|
||||
bool do_int = false;
|
||||
|
||||
*disk_read_acitivity = true;
|
||||
|
||||
if (command == 2) { // get status
|
||||
registers[(RL02_MPR - RL02_BASE) / 2] = 0;
|
||||
}
|
||||
else if (command == 6 || command == 7) { // read data / read data without header check
|
||||
*disk_read_acitivity = true;
|
||||
else if (command == 3) { // seek
|
||||
uint16_t temp = registers[(RL02_DAR - RL02_BASE) / 2];
|
||||
|
||||
uint32_t temp_disk_offset = disk_offset;
|
||||
int cylinder_count = (((temp >> 7) & 255) + 1) * (temp & 4 ? 1 : -1);
|
||||
|
||||
int32_t new_track = 0; // when bit 4 is set, a reset is performed
|
||||
|
||||
if ((temp & 8) == 0) {
|
||||
new_track = track + cylinder_count;
|
||||
|
||||
if (new_track < 0)
|
||||
new_track = 0;
|
||||
else if (new_track >= rl02_track_count)
|
||||
new_track = rl02_track_count;
|
||||
}
|
||||
|
||||
DOLOG(debug, false, "RL02: seek from cylinder %d to %d (distance: %d, DAR: %06o)", track, new_track, cylinder_count, temp);
|
||||
track = new_track;
|
||||
|
||||
do_int = true;
|
||||
}
|
||||
else if (command == 6 || command == 7) { // read data / read data without header check
|
||||
uint16_t temp = registers[(RL02_DAR - RL02_BASE) / 2];
|
||||
sector = temp & 63;
|
||||
head = !!(temp & 64);
|
||||
track = temp >> 7;
|
||||
|
||||
uint32_t temp_disk_offset = calcOffset();
|
||||
|
||||
uint32_t memory_address = get_bus_address();
|
||||
|
||||
uint32_t count = (65536l - registers[(RL02_MPR - RL02_BASE) / 2]) * 2;
|
||||
|
||||
DOLOG(debug, false, "RL02 read %d bytes (dec) from %d (dec) to %06o (oct)", count, disk_offset, memory_address);
|
||||
DOLOG(debug, false, "RL02 read %d bytes (dec) from %d (dec) to %06o (oct) [cylinder: %d, head: %d, sector: %d]", count, temp_disk_offset, memory_address, track, head, sector);
|
||||
|
||||
while(count > 0) {
|
||||
uint32_t cur = std::min(uint32_t(sizeof xfer_buffer), count);
|
||||
|
@ -160,15 +184,31 @@ void rl02::writeWord(const uint16_t addr, uint16_t v)
|
|||
temp_disk_offset += cur;
|
||||
|
||||
count -= cur;
|
||||
|
||||
sector++;
|
||||
if (sector >= rl02_sectors_per_track) {
|
||||
sector = 0;
|
||||
|
||||
head++;
|
||||
if (head >= 2) {
|
||||
head = 0;
|
||||
|
||||
track++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
do_int = true;
|
||||
}
|
||||
|
||||
if (do_int) {
|
||||
if (registers[(RL02_CSR - RL02_BASE) / 2] & 64) { // interrupt enable?
|
||||
DOLOG(debug, false, "RL02 triggering interrupt");
|
||||
|
||||
b->getCpu()->queue_interrupt(4, 0160);
|
||||
}
|
||||
|
||||
*disk_read_acitivity = false;
|
||||
}
|
||||
|
||||
*disk_read_acitivity = false;
|
||||
}
|
||||
}
|
||||
|
|
13
rl02.h
13
rl02.h
|
@ -1,4 +1,4 @@
|
|||
// (C) 2018-2023 by Folkert van Heusden
|
||||
// (C) 2018-2024 by Folkert van Heusden
|
||||
// Released under MIT license
|
||||
|
||||
#pragma once
|
||||
|
@ -19,6 +19,10 @@
|
|||
#define RL02_BASE RL02_CSR
|
||||
#define RL02_END (RL02_MPR + 2)
|
||||
|
||||
constexpr const int rl02_sectors_per_track = 40;
|
||||
constexpr const int rl02_track_count = 512;
|
||||
constexpr const int rl02_bytes_per_sector = 256;
|
||||
|
||||
class bus;
|
||||
|
||||
class rl02
|
||||
|
@ -26,7 +30,10 @@ class rl02
|
|||
private:
|
||||
bus *const b;
|
||||
uint16_t registers[4];
|
||||
uint8_t xfer_buffer[512];
|
||||
uint8_t xfer_buffer[rl02_bytes_per_sector];
|
||||
int16_t track { 0 };
|
||||
uint8_t head { 0 };
|
||||
uint8_t sector { 0 };
|
||||
std::vector<disk_backend *> fhs;
|
||||
|
||||
std::atomic_bool *const disk_read_acitivity { nullptr };
|
||||
|
@ -34,7 +41,7 @@ private:
|
|||
|
||||
uint32_t get_bus_address() const;
|
||||
void update_bus_address(const uint32_t a);
|
||||
uint32_t calcOffset(uint16_t) const;
|
||||
uint32_t calcOffset() const;
|
||||
|
||||
public:
|
||||
rl02(const std::vector<disk_backend *> & files, bus *const b, std::atomic_bool *const disk_read_acitivity, std::atomic_bool *const disk_write_acitivity);
|
||||
|
|
Loading…
Add table
Reference in a new issue