Skip to content

Commit

Permalink
peek_word tweak
Browse files Browse the repository at this point in the history
  • Loading branch information
folkertvanheusden committed Jun 23, 2024
1 parent a77d037 commit b17129b
Show file tree
Hide file tree
Showing 8 changed files with 984 additions and 100 deletions.
2 changes: 1 addition & 1 deletion ESP32/console_esp32.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,7 @@ void console_esp32::panel_update_thread()
if (panel_mode == PM_BITS) {
memory_addresses_t rc = b->getMMU()->calculate_physical_address(run_mode, current_PC);

uint16_t current_instr = b->peek_word(current_PC);
uint16_t current_instr = b->peek_word(run_mode, current_PC);

int pixel_offset = 0;

Expand Down
2 changes: 1 addition & 1 deletion breakpoint_memory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ std::optional<std::string> breakpoint_memory::is_triggered() const
uint16_t v = 0;

if (is_virtual)
v = b->peek_word(addr);
v = b->peek_word(rm_cur, addr); // FIXME rm_cur
else
v = b->read_physical(addr);

Expand Down
128 changes: 61 additions & 67 deletions bus.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -238,7 +238,7 @@ void bus::init()
mmu_->setMMR3(0);
}

uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm_selection_t mode_selection, const bool peek_only, const d_i_space_t space)
uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm_selection_t mode_selection, const d_i_space_t space)
{
int run_mode = mode_selection == rm_cur ? c->getPSW_runmode() : c->getPSW_prev_runmode();

Expand All @@ -253,60 +253,58 @@ uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm
//// REGISTERS ////
if (a >= ADDR_KERNEL_R && a <= ADDR_KERNEL_R + 5) { // kernel R0-R5
uint16_t temp = c->getRegister(a - ADDR_KERNEL_R) & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O kernel R%d: %06o", a - ADDR_KERNEL_R, temp);
TRACE("READ-I/O kernel R%d: %06o", a - ADDR_KERNEL_R, temp);
return temp;
}
if (a >= ADDR_USER_R && a <= ADDR_USER_R + 5) { // user R0-R5
uint16_t temp = c->getRegister(a - ADDR_USER_R) & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O user R%d: %06o", a - ADDR_USER_R, temp);
TRACE("READ-I/O user R%d: %06o", a - ADDR_USER_R, temp);
return temp;
}
if (a == ADDR_KERNEL_SP) { // kernel SP
uint16_t temp = c->getStackPointer(0) & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O kernel SP: %06o", temp);
TRACE("READ-I/O kernel SP: %06o", temp);
return temp;
}
if (a == ADDR_PC) { // PC
uint16_t temp = c->getPC() & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O PC: %06o", temp);
TRACE("READ-I/O PC: %06o", temp);
return temp;
}
if (a == ADDR_SV_SP) { // supervisor SP
uint16_t temp = c->getStackPointer(1) & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O supervisor SP: %06o", temp);
TRACE("READ-I/O supervisor SP: %06o", temp);
return temp;
}
if (a == ADDR_USER_SP) { // user SP
uint16_t temp = c->getStackPointer(3) & (word_mode == wm_byte ? 0xff : 0xffff);
if (!peek_only) TRACE("READ-I/O user SP: %06o", temp);
TRACE("READ-I/O user SP: %06o", temp);
return temp;
}
///^ registers ^///

if ((a & 1) && word_mode == wm_word) [[unlikely]] {
if (!peek_only) {
TRACE("READ-I/O odd address %06o UNHANDLED", a);
mmu_->trap_if_odd(addr_in, run_mode, space, false);
throw 0;
return 0;
}
TRACE("READ-I/O odd address %06o UNHANDLED", a);
mmu_->trap_if_odd(addr_in, run_mode, space, false);
throw 0;
return 0;
}

if (a == ADDR_CPU_ERR) { // cpu error register
uint16_t temp = mmu_->getCPUERR() & 0xff;
if (!peek_only) TRACE("READ-I/O CPU error: %03o", temp);
TRACE("READ-I/O CPU error: %03o", temp);
return temp;
}

if (a == ADDR_MAINT) { // MAINT
uint16_t temp = 1; // POWER OK
if (!peek_only) TRACE("READ-I/O MAINT: %o", temp);
TRACE("READ-I/O MAINT: %o", temp);
return temp;
}

if (a == ADDR_CONSW) { // console switch & display register
uint16_t temp = console_switches;
if (!peek_only) TRACE("READ-I/O console switch: %o", temp);
TRACE("READ-I/O console switch: %o", temp);
return temp;
}

Expand All @@ -320,13 +318,13 @@ uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm
else
temp = a == ADDR_PIR ? PIR & 255 : PIR >> 8;

if (!peek_only) TRACE("READ-I/O PIR: %o", temp);
TRACE("READ-I/O PIR: %o", temp);
return temp;
}

if (a == ADDR_SYSTEM_ID) {
uint16_t temp = 011064;
if (!peek_only) TRACE("READ-I/O system id: %o", temp);
TRACE("READ-I/O system id: %o", temp);
return temp;
}

Expand All @@ -335,7 +333,7 @@ uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm

if (a == ADDR_LP11CSR) { // printer, CSR register, LP11
uint16_t temp = 0x80;
if (!peek_only) TRACE("READ-I/O LP11 CSR: %o", temp);
TRACE("READ-I/O LP11 CSR: %o", temp);
return temp;
}

Expand All @@ -354,176 +352,166 @@ uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm
///////////

if (a >= 0177740 && a <= 0177753) { // cache control register and others
if (!peek_only) TRACE("READ-I/O cache control register/others (%06o): %o", a, 0);
TRACE("READ-I/O cache control register/others (%06o): %o", a, 0);
// TODO
return 0;
}

if (a >= 0170200 && a <= 0170377) { // unibus map
if (!peek_only) TRACE("READ-I/O unibus map (%06o): %o", a, 0);
TRACE("READ-I/O unibus map (%06o): %o", a, 0);
// TODO
return 0;
}

if (a >= 0172100 && a <= 0172137) { // MM11-LP parity
if (!peek_only) TRACE("READ-I/O MM11-LP parity (%06o): %o", a, 1);
TRACE("READ-I/O MM11-LP parity (%06o): %o", a, 1);
return 1;
}

if (word_mode == wm_byte) {
if (a == ADDR_PSW) { // PSW
uint8_t temp = c->getPSW();
if (!peek_only) TRACE("READ-I/O PSW LSB: %03o", temp);
TRACE("READ-I/O PSW LSB: %03o", temp);
return temp;
}

if (a == ADDR_PSW + 1) {
uint8_t temp = c->getPSW() >> 8;
if (!peek_only) TRACE("READ-I/O PSW MSB: %03o", temp);
TRACE("READ-I/O PSW MSB: %03o", temp);
return temp;
}
if (a == ADDR_STACKLIM) { // stack limit register
uint8_t temp = c->getStackLimitRegister();
if (!peek_only) TRACE("READ-I/O stack limit register (low): %03o", temp);
TRACE("READ-I/O stack limit register (low): %03o", temp);
return temp;
}
if (a == ADDR_STACKLIM + 1) { // stack limit register
uint8_t temp = c->getStackLimitRegister() >> 8;
if (!peek_only) TRACE("READ-I/O stack limit register (high): %03o", temp);
TRACE("READ-I/O stack limit register (high): %03o", temp);
return temp;
}

if (a == ADDR_MICROPROG_BREAK_REG) { // microprogram break register
uint8_t temp = microprogram_break_register;
if (!peek_only) TRACE("READ-I/O microprogram break register (low): %03o", temp);
TRACE("READ-I/O microprogram break register (low): %03o", temp);
return temp;
}
if (a == ADDR_MICROPROG_BREAK_REG + 1) { // microprogram break register
uint8_t temp = microprogram_break_register >> 8;
if (!peek_only) TRACE("READ-I/O microprogram break register (high): %03o", temp);
TRACE("READ-I/O microprogram break register (high): %03o", temp);
return temp;
}

if (a == ADDR_MMR0) {
uint8_t temp = mmu_->getMMR0();
if (!peek_only) TRACE("READ-I/O MMR0 LO: %03o", temp);
TRACE("READ-I/O MMR0 LO: %03o", temp);
return temp;
}
if (a == ADDR_MMR0 + 1) {
uint8_t temp = mmu_->getMMR0() >> 8;
if (!peek_only) TRACE("READ-I/O MMR0 HI: %03o", temp);
TRACE("READ-I/O MMR0 HI: %03o", temp);
return temp;
}
}
else {
if (a == ADDR_MMR0) {
uint16_t temp = mmu_->getMMR0();
if (!peek_only) TRACE("READ-I/O MMR0: %06o", temp);
TRACE("READ-I/O MMR0: %06o", temp);
return temp;
}

if (a == ADDR_MMR1) { // MMR1
uint16_t temp = mmu_->getMMR1();
if (!peek_only) TRACE("READ-I/O MMR1: %06o", temp);
TRACE("READ-I/O MMR1: %06o", temp);
return temp;
}

if (a == ADDR_MMR2) { // MMR2
uint16_t temp = mmu_->getMMR2();
if (!peek_only) TRACE("READ-I/O MMR2: %06o", temp);
TRACE("READ-I/O MMR2: %06o", temp);
return temp;
}

if (a == ADDR_MMR3) { // MMR3
uint16_t temp = mmu_->getMMR3();
if (!peek_only) TRACE("READ-I/O MMR3: %06o", temp);
TRACE("READ-I/O MMR3: %06o", temp);
return temp;
}

if (a == ADDR_PSW) { // PSW
uint16_t temp = c->getPSW();
if (!peek_only) TRACE("READ-I/O PSW: %06o", temp);
TRACE("READ-I/O PSW: %06o", temp);
return temp;
}

if (a == ADDR_STACKLIM) { // stack limit register
uint16_t temp = c->getStackLimitRegister();
if (!peek_only) TRACE("READ-I/O stack limit register: %06o", temp);
TRACE("READ-I/O stack limit register: %06o", temp);
return temp;
}

if (a == ADDR_CPU_ERR) { // cpu error register
uint16_t temp = mmu_->getCPUERR();
if (!peek_only) TRACE("READ-I/O CPUERR: %06o", temp);
TRACE("READ-I/O CPUERR: %06o", temp);
return temp;
}

if (a == ADDR_MICROPROG_BREAK_REG) { // microprogram break register
uint16_t temp = microprogram_break_register;
if (!peek_only) TRACE("READ-I/O microprogram break register: %06o", temp);
TRACE("READ-I/O microprogram break register: %06o", temp);
return temp;
}
}

if (tm11 && a >= TM_11_BASE && a < TM_11_END && !peek_only)
if (tm11 && a >= TM_11_BASE && a < TM_11_END)
return word_mode == wm_byte ? tm11->read_byte(a) : tm11->read_word(a);

if (rk05_ && a >= RK05_BASE && a < RK05_END && !peek_only)
if (rk05_ && a >= RK05_BASE && a < RK05_END)
return word_mode == wm_byte ? rk05_->read_byte(a) : rk05_->read_word(a);

if (rl02_ && a >= RL02_BASE && a < RL02_END && !peek_only)
if (rl02_ && a >= RL02_BASE && a < RL02_END)
return word_mode == wm_byte ? rl02_->read_byte(a) : rl02_->read_word(a);

if (tty_ && a >= PDP11TTY_BASE && a < PDP11TTY_END && !peek_only)
if (tty_ && a >= PDP11TTY_BASE && a < PDP11TTY_END)
return word_mode == wm_byte ? tty_->read_byte(a) : tty_->read_word(a);

if (dc11_ && a >= DC11_BASE && a < DC11_END && !peek_only)
if (dc11_ && a >= DC11_BASE && a < DC11_END)
return word_mode == wm_byte ? dc11_->read_byte(a) : dc11_->read_word(a);

if (rp06_ && a >= RP06_BASE && a < RP06_END && !peek_only)
if (rp06_ && a >= RP06_BASE && a < RP06_END)
return word_mode == wm_byte ? rp06_->read_byte(a) : rp06_->read_word(a);

// LO size register field must be all 1s, so subtract 1
uint32_t system_size = m->get_memory_size() / 64 - 1;

if (a == ADDR_SYSSIZE + 2) { // system size HI
uint16_t temp = system_size >> 16;
if (!peek_only) TRACE("READ-I/O accessing system size HI: %06o", temp);
TRACE("READ-I/O accessing system size HI: %06o", temp);
return temp;
}

if (a == ADDR_SYSSIZE) { // system size LO
uint16_t temp = system_size;
if (!peek_only) TRACE("READ-I/O accessing system size LO: %06o", temp);
TRACE("READ-I/O accessing system size LO: %06o", temp);
return temp;
}

if (!peek_only) {
TRACE("READ-I/O UNHANDLED read %08o (%c), (base: %o)", m_offset, word_mode == wm_byte ? 'B' : ' ', mmu_->get_io_base());
TRACE("READ-I/O UNHANDLED read %08o (%c), (base: %o)", m_offset, word_mode == wm_byte ? 'B' : ' ', mmu_->get_io_base());

c->trap(004); // no such i/o
throw 1;
}
c->trap(004); // no such i/o
throw 1;

return -1;
}

if ((addr_in & 1) && word_mode == wm_word) {
if (peek_only == false) {
TRACE("READ from %06o - odd address!", addr_in);
mmu_->trap_if_odd(addr_in, run_mode, space, false);
throw 2;
return 0;
}
TRACE("READ from %06o - odd address!", addr_in);
mmu_->trap_if_odd(addr_in, run_mode, space, false);
throw 2;
return 0;
}

// TODO: this will fail for peek & odd addressing
if (m_offset >= m->get_memory_size()) {
if (peek_only) {
TRACE("READ from %06o - out of range!", addr_in);
return 0;
}

c->trap(004); // no such RAM
throw 1;
}
Expand All @@ -534,7 +522,7 @@ uint16_t bus::read(const uint16_t addr_in, const word_mode_t word_mode, const rm
else
temp = m->read_word(m_offset);

if (!peek_only) TRACE("READ from %06o/%07o %c %c: %06o (%s)", addr_in, m_offset, space == d_space ? 'D' : 'I', word_mode == wm_byte ? 'B' : 'W', temp, mode_selection == rm_prev ? "prev" : "cur");
TRACE("READ from %06o/%07o %c %c: %06o (%s)", addr_in, m_offset, space == d_space ? 'D' : 'I', word_mode == wm_byte ? 'B' : 'W', temp, mode_selection == rm_prev ? "prev" : "cur");

return temp;
}
Expand Down Expand Up @@ -861,12 +849,18 @@ uint16_t bus::read_physical(const uint32_t a)

uint16_t bus::read_word(const uint16_t a, const d_i_space_t s)
{
return read(a, wm_word, rm_cur, false, s);
return read(a, wm_word, rm_cur, s);
}

uint16_t bus::peek_word(const uint16_t a)
uint16_t bus::peek_word(const int run_mode, const uint16_t a)
{
return read(a, wm_word, rm_cur, true);
auto meta = mmu_->calculate_physical_address(run_mode, a);

uint32_t io_base = mmu_->get_io_base();
if (meta.physical_instruction >= io_base) // TODO: I/O always returns 0xffff
return 0xffff;

return m->read_word(meta.physical_instruction);
}

void bus::write_word(const uint16_t a, const uint16_t value, const d_i_space_t s)
Expand Down
Loading

0 comments on commit b17129b

Please sign in to comment.