EightBit/MC6850/src/MC6850.cpp

82 lines
3.3 KiB
C++
Raw Normal View History

<EFBFBD><EFBFBD>#include "pch.h"
#include "MC6850.h"
#include <cassert>
bool EightBit::mc6850::selected() {
return
(CS0() == PinLevel::High)
&& (CS1() == PinLevel::High)
&& (CS2() == PinLevel::Low);
}
void EightBit::mc6850::reset() {
if (m_firstMasterReset)
IRQ() = RTS() = PinLevel::High;
status() = 0;
m_firstMasterReset = false;
}
void EightBit::mc6850::step(int cycles) {
for (int i = 0; i < cycles; ++i)
step();
}
void EightBit::mc6850::step() {
if (!(powered() && selected()))
return;
const bool writing = RW() == PinLevel::Low;
const bool reading = !writing;
const bool registers = RS() == PinLevel::Low;
const bool transferring = !registers;
if (registers) {
if (writing) {
// Control register
m_counterDivide = DATA() && (CR0 | CR1);
const bool masterReset = m_counterDivide == 0b11;
if (masterReset) {
reset();
} else {
m_wordConfiguration = (DATA() && (CR2 | CR3 | CR4)) >> 2;
m_transmitterControl = (DATA() && (CR5 | CR6)) >> 5;
m_receiveControl = (DATA() && CR7) >> 7;
}
} else {
// Status register
assert(reading);
DATA() = status();
}
} else {
assert(transferring);
IRQ() = PinLevel::High;
if (writing) {
fillTDR(DATA());
} else {
assert(reading);
DATA() = drainRDR();
}
}
}
void EightBit::mc6850::fillRDR(uint8_t data) {
RDR() = data;
Processor::setFlag(status(), RDRF, true);
}
uint8_t EightBit::mc6850::drainRDR() {
Processor::setFlag(status(), RDRF, false);
return RDR();
}
void EightBit::mc6850::fillTDR(uint8_t data) {
TDR() = data;
}
uint8_t EightBit::mc6850::drainTDR() {
return TDR();
}