Routes in the ADB keyboard ROM. This should get as far as parsing.

This commit is contained in:
Thomas Harte 2021-01-18 16:59:49 -05:00
parent 8b19c523cf
commit ec0018df79
7 changed files with 40 additions and 2 deletions

View File

@ -8,6 +8,7 @@
#include "Executor.hpp"
#include <algorithm>
#include <cassert>
using namespace InstructionSet::M50740;
@ -18,13 +19,31 @@ Executor::Executor() {
Decoder decoder;
for(size_t c = 0; c < 256; c++) {
const auto instruction = decoder.instrucion_for_opcode(uint8_t(c));
performers_[c] = performer_lookup_.performer(instruction.operation, instruction.addressing_mode);
// Treat invalid as NOP, because I've got to do _something_.
if(instruction.operation == Operation::Invalid) {
performers_[c] = performer_lookup_.performer(Operation::NOP, instruction.addressing_mode);
} else {
performers_[c] = performer_lookup_.performer(instruction.operation, instruction.addressing_mode);
}
}
// TODO: read reset vector, etc. This is just the start of ROM.
set_program_counter(0x1400);
}
void Executor::set_rom(const std::vector<uint8_t> &rom) {
// Copy into place, and reset.
const auto length = std::min(size_t(0x1000), rom.size());
memcpy(&memory_[0x2000 - length], rom.data(), length);
reset();
}
void Executor::reset() {
// Just jump to the reset vector.
set_program_counter(uint16_t(memory_[0x1ffe] | (memory_[0x1fff] << 8)));
}
template <Operation operation, AddressingMode addressing_mode> void Executor::perform() {
// Deal with all modes that don't access memory up here;
// those that access memory will go through a slightly longer

View File

@ -13,6 +13,9 @@
#include "Parser.hpp"
#include "../CachingExecutor.hpp"
#include <cstdint>
#include <vector>
namespace InstructionSet {
namespace M50740 {
@ -22,6 +25,8 @@ using CachingExecutor = CachingExecutor<Executor, 0x1fff, 256, Instruction, fals
class Executor: public CachingExecutor {
public:
Executor();
void set_rom(const std::vector<uint8_t> &rom);
void reset();
private:
// MARK: - CachingExecutor-facing interface.

View File

@ -211,3 +211,7 @@ uint8_t GLU::read_microcontroller_address(uint16_t address) {
return 0x40;
return 0;
}
void GLU::set_microcontroller_rom(const std::vector<uint8_t> &rom) {
executor_.set_rom(rom);
}

View File

@ -11,6 +11,7 @@
#include <cstdint>
#include <vector>
#include "../../../InstructionSets/M50740/Executor.hpp"
namespace Apple {
namespace IIgs {
@ -34,6 +35,8 @@ class GLU {
void set_status(uint8_t);
void clear_key_strobe();
void set_microcontroller_rom(const std::vector<uint8_t> &rom);
private:
bool is_rom03_ = false;
std::vector<uint8_t> next_command_;
@ -52,6 +55,8 @@ class GLU {
void set_configuration_bytes(uint8_t *);
uint8_t read_microcontroller_address(uint16_t);
InstructionSet::M50740::Executor executor_;
};
}

View File

@ -88,13 +88,15 @@ class ConcreteMachine:
break;
}
rom_descriptions.push_back(video_->rom_description(Video::Video::CharacterROM::EnhancedIIe));
rom_descriptions.emplace_back(machine_name, "the Apple IIgs ADB microcontroller ROM", "341s0632-2", 4*1024, 0xe1c11fb0);
const auto roms = rom_fetcher(rom_descriptions);
if(!roms[0] || !roms[1]) {
if(!roms[0] || !roms[1] || !roms[2]) {
throw ROMMachine::Error::MissingROMs;
}
rom_ = *roms[0];
video_->set_character_rom(*roms[1]);
adb_glu_.set_microcontroller_rom(*roms[2]);
// Run only the currently-interesting self test.
rom_[0x36402] = 2;

View File

@ -27,6 +27,8 @@
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
shouldUseLaunchSchemeArgsEnv = "YES"
enableAddressSanitizer = "YES"
enableUBSanitizer = "YES"
disableMainThreadChecker = "YES"
codeCoverageEnabled = "YES">
<MacroExpansion>

View File

@ -2,5 +2,6 @@ ROM files would ordinarily go here; they are copyright Apple so are not included
Expected files (as usual, using the most conventional pre-existing names):
341s0632-2.bin — the ADB microcontroller ROM;
APPLE2GS.ROM - ROM version 1; and
APPLE2GS.ROM2 - ROM version 3.