mirror of
https://github.com/cmosher01/v6502cpp.git
synced 2025-04-09 07:39:15 +00:00
refactor: add Cpu6502Helper; extract Common
This commit is contained in:
parent
40ba79a34d
commit
ca692a6fc8
8
Common.cpp
Normal file
8
Common.cpp
Normal file
@ -0,0 +1,8 @@
|
||||
/*
|
||||
* File: Common.cpp
|
||||
* Author: Christopher
|
||||
*
|
||||
* Created on December 14, 2013, 8:47 PM
|
||||
*/
|
||||
|
||||
#include "Common.h"
|
81
Common.h
Normal file
81
Common.h
Normal file
@ -0,0 +1,81 @@
|
||||
/*
|
||||
* File: Common.h
|
||||
* Author: Christopher
|
||||
*
|
||||
* Created on December 14, 2013, 8:47 PM
|
||||
*/
|
||||
|
||||
#ifndef COMMON_H
|
||||
#define COMMON_H
|
||||
|
||||
class Segment;
|
||||
class SegmentCache;
|
||||
|
||||
class Common {
|
||||
public:
|
||||
Segment *VSS, *VCC;
|
||||
Segment *CLK0;
|
||||
Segment *IRQ, *RES, *NMI;
|
||||
Segment *RDY, *SO;
|
||||
Segment *DB0, *DB1, *DB2, *DB3, *DB4, *DB5, *DB6, *DB7;
|
||||
Segment *AB0, *AB1, *AB2, *AB3, *AB4, *AB5, *AB6, *AB7, *AB8, *AB9, *AB10, *AB11, *AB12, *AB13, *AB14, *AB15;
|
||||
Segment *RW, *SYNC;
|
||||
Segment *CLK1OUT, *CLK2OUT;
|
||||
Segment *A0, *A1, *A2, *A3, *A4, *A5, *A6, *A7;
|
||||
Segment *X0, *X1, *X2, *X3, *X4, *X5, *X6, *X7;
|
||||
Segment *Y0, *Y1, *Y2, *Y3, *Y4, *Y5, *Y6, *Y7;
|
||||
Segment *PCL0, *PCL1, *PCL2, *PCL3, *PCL4, *PCL5, *PCL6, *PCL7;
|
||||
Segment *PCH0, *PCH1, *PCH2, *PCH3, *PCH4, *PCH5, *PCH6, *PCH7;
|
||||
Segment *P0, *P1, *P2, *P3, *P4, /* no P5 */ *P6, *P7;
|
||||
Segment *S0, *S1, *S2, *S3, *S4, *S5, *S6, *S7;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
private:
|
||||
Common(
|
||||
Segment* VSS, Segment* VCC,
|
||||
Segment* CLK0,
|
||||
Segment* IRQ, Segment* RES, Segment* NMI,
|
||||
Segment* RDY, Segment* SO,
|
||||
Segment* DB0, Segment* DB1, Segment* DB2, Segment* DB3, Segment* DB4, Segment* DB5, Segment* DB6, Segment* DB7,
|
||||
Segment* AB0, Segment* AB1, Segment* AB2, Segment* AB3, Segment* AB4, Segment* AB5, Segment* AB6, Segment* AB7,
|
||||
Segment* AB8, Segment* AB9, Segment* AB10, Segment* AB11, Segment* AB12, Segment* AB13, Segment* AB14, Segment* AB15,
|
||||
Segment* RW, Segment* SYNC,
|
||||
Segment* CLK1OUT, Segment* CLK2OUT,
|
||||
Segment* A0, Segment* A1, Segment* A2, Segment* A3, Segment* A4, Segment* A5, Segment* A6, Segment* A7,
|
||||
Segment* X0, Segment* X1, Segment* X2, Segment* X3, Segment* X4, Segment* X5, Segment* X6, Segment* X7,
|
||||
Segment* Y0, Segment* Y1, Segment* Y2, Segment* Y3, Segment* Y4, Segment* Y5, Segment* Y6, Segment* Y7,
|
||||
Segment* PCL0, Segment* PCL1, Segment* PCL2, Segment* PCL3, Segment* PCL4, Segment* PCL5, Segment* PCL6, Segment* PCL7,
|
||||
Segment* PCH0, Segment* PCH1, Segment* PCH2, Segment* PCH3, Segment* PCH4, Segment* PCH5, Segment* PCH6, Segment* PCH7,
|
||||
Segment* P0, Segment* P1, Segment* P2, Segment* P3, Segment* P4, /* no P5 */ Segment* P6, Segment* P7,
|
||||
Segment* S0, Segment* S1, Segment* S2, Segment* S3, Segment* S4, Segment* S5, Segment* S6, Segment* S7) :
|
||||
VSS(VSS), VCC(VCC),
|
||||
CLK0(CLK0),
|
||||
IRQ(IRQ), RES(RES), NMI(NMI),
|
||||
RDY(RDY), SO(SO),
|
||||
DB0(DB0), DB1(DB1), DB2(DB2), DB3(DB3), DB4(DB4), DB5(DB5), DB6(DB6), DB7(DB7),
|
||||
AB0(AB0), AB1(AB1), AB2(AB2), AB3(AB3), AB4(AB4), AB5(AB5), AB6(AB6), AB7(AB7),
|
||||
AB8(AB8), AB9(AB9), AB10(AB10), AB11(AB11), AB12(AB12), AB13(AB13), AB14(AB14), AB15(AB15),
|
||||
RW(RW), SYNC(SYNC),
|
||||
CLK1OUT(CLK1OUT), CLK2OUT(CLK2OUT),
|
||||
A0(A0), A1(A1), A2(A2), A3(A3), A4(A4), A5(A5), A6(A6), A7(A7),
|
||||
X0(X0), X1(X1), X2(X2), X3(X3), X4(X4), X5(X5), X6(X6), X7(X7),
|
||||
Y0(Y0), Y1(Y1), Y2(Y2), Y3(Y3), Y4(Y4), Y5(Y5), Y6(Y6), Y7(Y7),
|
||||
PCL0(PCL0), PCL1(PCL1), PCL2(PCL2), PCL3(PCL3), PCL4(PCL4), PCL5(PCL5), PCL6(PCL6), PCL7(PCL7),
|
||||
PCH0(PCH0), PCH1(PCH1), PCH2(PCH2), PCH3(PCH3), PCH4(PCH4), PCH5(PCH5), PCH6(PCH6), PCH7(PCH7),
|
||||
P0(P0), P1(P1), P2(P2), P3(P3), P4(P4), /* no P5 */ P6(P6), P7(P7),
|
||||
S0(S0), S1(S1), S2(S2), S3(S3), S4(S4), S5(S5), S6(S6), S7(S7) {
|
||||
}
|
||||
|
||||
~Common() {
|
||||
}
|
||||
|
||||
Common(const Common&) = delete;
|
||||
Common& operator=(const Common&) = delete;
|
||||
|
||||
friend SegmentCache;
|
||||
};
|
||||
|
||||
#endif /* COMMON_H */
|
183
Cpu6502.cpp
183
Cpu6502.cpp
@ -11,184 +11,63 @@
|
||||
#include "addressbus.h"
|
||||
#include "Trace.h"
|
||||
#include <iostream>
|
||||
|
||||
|
||||
#include <utility>
|
||||
#include "StateCalculator.h"
|
||||
|
||||
#include "Common.h"
|
||||
|
||||
|
||||
|
||||
#define TRACEREG 1
|
||||
//#define TRACESEG 1
|
||||
//#define TRACEMEM 1
|
||||
|
||||
#ifdef TRACEREG
|
||||
#define dumpRegs() this->trace.dumpRegisters()
|
||||
#else
|
||||
#define dumpRegs()
|
||||
#endif
|
||||
|
||||
#ifdef TRACESEG
|
||||
#define dumpSegs() this->trace.dumpSegments()
|
||||
#else
|
||||
#define dumpSegs()
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void Cpu6502::powerOn() {
|
||||
std::cout << "initial state" << std::endl;
|
||||
dumpRegs();
|
||||
dumpSegs();
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* Since we use segs[CLK0].on as our own
|
||||
* temporary variable (see "step" method), we
|
||||
* need to initialize it here, to "phase one".
|
||||
*/
|
||||
n->CLK0->on = true;
|
||||
|
||||
|
||||
|
||||
std::cout << "setting input pins..." << std::endl;
|
||||
initPins();
|
||||
|
||||
std::cout << "initial full calculation..." << std::endl;
|
||||
StateCalculator::recalc(segs.all());
|
||||
dumpRegs();
|
||||
dumpSegs();
|
||||
Cpu6502::Cpu6502(TransNetwork& transNetwork, AddressBus& addressBus, Trace& trace) : transNetwork(transNetwork), addressBus(addressBus), trace(trace), segs(transNetwork.segs), n(segs.c) {
|
||||
}
|
||||
|
||||
void Cpu6502::setSeg(Segment* s, bool on) {
|
||||
s->set(on);
|
||||
}
|
||||
|
||||
void Cpu6502::initPins() {
|
||||
// set voltage supply and ground.
|
||||
setSeg(n->VCC, true);
|
||||
setSeg(n->VSS, false);
|
||||
|
||||
// don't do the set-overflow overriding functionality
|
||||
setSeg(n->SO, false);
|
||||
|
||||
// ready to run (i.e., do not do single-stepping of instructions)
|
||||
setSeg(n->RDY, true);
|
||||
|
||||
// pull up to indicate that we are not interrupting now
|
||||
setSeg(n->IRQ, true);
|
||||
setSeg(n->NMI, true);
|
||||
|
||||
|
||||
/*
|
||||
* RES_BAR pin means "not resetting". Since it is a negated pin, pulling it low means "resetting"
|
||||
* and pulling it high means "not resetting" or equivalently "running".
|
||||
*/
|
||||
|
||||
/*
|
||||
* RES_BAR false: resetting now (i.e., in power-up now; pull high to begin normal operation)
|
||||
* We want to hold RES_BAR low for a while, indicating power-up phase during which the
|
||||
* CPU does not start up normal operations yet. The caller can set RES_BAR high (by calling
|
||||
* reset) whenever he is ready to start the CPU running.
|
||||
*/
|
||||
setSeg(n->RES, false);
|
||||
}
|
||||
|
||||
void Cpu6502::reset() {
|
||||
setSeg(n->RES, true);
|
||||
StateCalculator::recalc(n->RES);
|
||||
}
|
||||
|
||||
void Cpu6502::tick() {
|
||||
step();
|
||||
step();
|
||||
}
|
||||
|
||||
void Cpu6502::step() {
|
||||
/*
|
||||
* We cheat a little bit here: instead of requiring the
|
||||
* caller to toggle clock-zero pin, we let him just call
|
||||
* "step" and *we* keep track of which phase we are in.
|
||||
* To do this, we just use the CLK0 segment value (as
|
||||
* a kind of temporary variable), and just toggle it in
|
||||
* order to know which phase we are going into.
|
||||
*
|
||||
* The real 6502, of course, does not do this.
|
||||
*/
|
||||
const bool nextPhase = !n->CLK0->on;
|
||||
|
||||
clock(nextPhase);
|
||||
rw();
|
||||
|
||||
dumpRegs();
|
||||
dumpSegs();
|
||||
void Cpu6502::setPins(const PinSettings& ps) {
|
||||
setpSeg rec;
|
||||
for (auto p : ps) {
|
||||
p.first->set(p.second);
|
||||
rec.insert(p.first);
|
||||
}
|
||||
StateCalculator::recalc(rec);
|
||||
}
|
||||
|
||||
void Cpu6502::clock(bool phase) {
|
||||
setSeg(n->CLK0, phase);
|
||||
StateCalculator::recalc(n->CLK0);
|
||||
setPins(PinSettings{std::make_pair(n->CLK0,phase)});
|
||||
rw();
|
||||
|
||||
#ifdef TRACEREG
|
||||
this->trace.dumpRegisters();
|
||||
#endif
|
||||
|
||||
#ifdef TRACESEG
|
||||
this->trace.dumpSegments();
|
||||
#endif
|
||||
}
|
||||
|
||||
void Cpu6502::rw() {
|
||||
// database read/write happens during Clock Phase 2 (only)
|
||||
if (n->CLK2OUT->on) {
|
||||
readBus();
|
||||
readData();
|
||||
writeData();
|
||||
}
|
||||
}
|
||||
|
||||
void Cpu6502::readData() {
|
||||
if (this->transNetwork.segs.c->RW->on) {
|
||||
this->transNetwork.segs.setDataSegs(this->addressBus.read(this->transNetwork.segs.rAddr()));
|
||||
|
||||
//???? TODO ???? can this be inside the if block ????
|
||||
setpSeg s;
|
||||
segs.addDataToRecalc(s);
|
||||
StateCalculator::recalc(s);
|
||||
|
||||
writeBus();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void Cpu6502::readBus() {
|
||||
if (this->transNetwork.segs.c->RW->on) {
|
||||
this->transNetwork.segs.setDataSegs(read(this->transNetwork.segs.rAddr()));
|
||||
}
|
||||
}
|
||||
|
||||
void Cpu6502::writeBus() {
|
||||
void Cpu6502::writeData() {
|
||||
if (!this->transNetwork.segs.c->RW->on) {
|
||||
write(this->transNetwork.segs.rAddr(), this->transNetwork.segs.rData());
|
||||
this->addressBus.write(this->transNetwork.segs.rAddr(), this->transNetwork.segs.rData());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
unsigned char Cpu6502::read(unsigned short addr) {
|
||||
const unsigned char x = this->addressBus.read(addr);
|
||||
#ifdef TRACEMEM
|
||||
std::cout << "-------------------------------------------------- ";
|
||||
pHex(x);
|
||||
std::cout << "<";
|
||||
pHexw(addr);
|
||||
std::cout << std::endl;
|
||||
#endif
|
||||
return x;
|
||||
}
|
||||
|
||||
void Cpu6502::write(unsigned short addr, unsigned char data) {
|
||||
this->addressBus.write(addr, data);
|
||||
#ifdef TRACEMEM
|
||||
std::cout << "-------------------------------------------------- ";
|
||||
pHex(data);
|
||||
std::cout << ">";
|
||||
pHexw(addr);
|
||||
std::cout << std::endl;
|
||||
#endif
|
||||
}
|
||||
|
37
Cpu6502.h
37
Cpu6502.h
@ -8,9 +8,12 @@
|
||||
#ifndef CPU6502_H
|
||||
#define CPU6502_H
|
||||
|
||||
#include "TransNetwork.h"
|
||||
|
||||
#include <set>
|
||||
#include <utility>
|
||||
|
||||
class Segment;
|
||||
class SegmentCache;
|
||||
class Common;
|
||||
class TransNetwork;
|
||||
class AddressBus;
|
||||
class Trace;
|
||||
@ -18,38 +21,32 @@ class Trace;
|
||||
class Cpu6502 {
|
||||
public:
|
||||
|
||||
Cpu6502(TransNetwork& transNetwork, AddressBus& addressBus, Trace& trace) : transNetwork(transNetwork), addressBus(addressBus), trace(trace), segs(transNetwork.segs), n(segs.c) {
|
||||
}
|
||||
Cpu6502(TransNetwork& transNetwork, AddressBus& addressBus, Trace& trace);
|
||||
|
||||
virtual ~Cpu6502() {
|
||||
}
|
||||
|
||||
void powerOn();
|
||||
void tick();
|
||||
void reset();
|
||||
typedef std::set<std::pair<Segment*, bool >> PinSettings;
|
||||
void setPins(const PinSettings& ps);
|
||||
|
||||
void clock(bool phase);
|
||||
|
||||
private:
|
||||
Cpu6502(const Cpu6502&);
|
||||
Cpu6502& operator=(const Cpu6502&);
|
||||
|
||||
void initPins();
|
||||
void step();
|
||||
void clock(bool phase);
|
||||
Cpu6502(const Cpu6502&) = delete;
|
||||
Cpu6502& operator=(const Cpu6502&) = delete;
|
||||
|
||||
void rw();
|
||||
void readBus();
|
||||
void writeBus();
|
||||
unsigned char read(unsigned short addr);
|
||||
void write(unsigned short addr, unsigned char data);
|
||||
|
||||
static void setSeg(Segment* s, bool on);
|
||||
void readData();
|
||||
void writeData();
|
||||
|
||||
TransNetwork& transNetwork;
|
||||
AddressBus& addressBus;
|
||||
|
||||
Trace& trace;
|
||||
|
||||
public:
|
||||
SegmentCache& segs;
|
||||
SegmentCache::Common* n;
|
||||
Common* n;
|
||||
};
|
||||
|
||||
#endif /* CPU6502_H */
|
||||
|
@ -6,13 +6,81 @@
|
||||
*/
|
||||
|
||||
#include "Cpu6502Helper.h"
|
||||
#include "Cpu6502.h"
|
||||
#include "SegmentCache.h"
|
||||
#include "TransNetwork.h"
|
||||
#include "trans.h"
|
||||
#include "addressbus.h"
|
||||
#include "Trace.h"
|
||||
#include <iostream>
|
||||
#include "StateCalculator.h"
|
||||
#include <utility>
|
||||
#include <set>
|
||||
#include "Common.h"
|
||||
|
||||
Cpu6502Helper::Cpu6502Helper() {
|
||||
}
|
||||
|
||||
Cpu6502Helper::Cpu6502Helper(const Cpu6502Helper& orig) {
|
||||
Cpu6502Helper::Cpu6502Helper(Cpu6502& cpu) : cpu(cpu), nextPhase(true), n(cpu.segs.c) {
|
||||
}
|
||||
|
||||
Cpu6502Helper::~Cpu6502Helper() {
|
||||
}
|
||||
|
||||
void Cpu6502Helper::powerOn() {
|
||||
Cpu6502::PinSettings ps;
|
||||
|
||||
// set voltage supply and ground.
|
||||
ps.insert(std::make_pair(n->VCC, true));
|
||||
ps.insert(std::make_pair(n->VSS, false));
|
||||
|
||||
// don't do the set-overflow overriding functionality
|
||||
ps.insert(std::make_pair(n->SO, false));
|
||||
|
||||
// ready to run (i.e., do not do single-stepping of instructions)
|
||||
ps.insert(std::make_pair(n->RDY, true));
|
||||
|
||||
// pull up to indicate that we are not interrupting now
|
||||
ps.insert(std::make_pair(n->IRQ, true));
|
||||
ps.insert(std::make_pair(n->NMI, true));
|
||||
|
||||
|
||||
/*
|
||||
* RES_BAR pin means "not resetting". Since it is a negated pin, pulling it low means "resetting"
|
||||
* and pulling it high means "not resetting" or equivalently "running".
|
||||
*/
|
||||
|
||||
/*
|
||||
* RES_BAR false: resetting now (i.e., in power-up now; pull high to begin normal operation)
|
||||
* We want to hold RES_BAR low for a while, indicating power-up phase during which the
|
||||
* CPU does not start up normal operations yet. The caller can set RES_BAR high (by calling
|
||||
* reset) whenever he is ready to start the CPU running.
|
||||
*/
|
||||
ps.insert(std::make_pair(n->RES, false));
|
||||
|
||||
cpu.setPins(ps);
|
||||
|
||||
nextPhase = true;
|
||||
}
|
||||
|
||||
void Cpu6502Helper::tick() {
|
||||
step();
|
||||
step();
|
||||
}
|
||||
|
||||
void Cpu6502Helper::step() {
|
||||
/*
|
||||
* We cheat a little bit here: instead of requiring the
|
||||
* caller to toggle clock-zero pin, we let him just call
|
||||
* "step" and *we* keep track of which phase we are in.
|
||||
* To do this, we just use the CLK0 segment value (as
|
||||
* a kind of temporary variable), and just toggle it in
|
||||
* order to know which phase we are going into.
|
||||
*
|
||||
* The real 6502, of course, does not do this.
|
||||
*/
|
||||
nextPhase = !nextPhase;
|
||||
|
||||
cpu.clock(nextPhase);
|
||||
}
|
||||
|
||||
void Cpu6502Helper::reset() {
|
||||
cpu.setPins(Cpu6502::PinSettings{std::make_pair(n->RES, true)});
|
||||
}
|
||||
|
@ -8,14 +8,31 @@
|
||||
#ifndef CPU6502HELPER_H
|
||||
#define CPU6502HELPER_H
|
||||
|
||||
class Cpu6502;
|
||||
|
||||
class Common;
|
||||
|
||||
class Cpu6502Helper {
|
||||
public:
|
||||
Cpu6502Helper();
|
||||
Cpu6502Helper(const Cpu6502Helper& orig);
|
||||
|
||||
explicit Cpu6502Helper(Cpu6502& cpu);
|
||||
virtual ~Cpu6502Helper();
|
||||
|
||||
void powerOn();
|
||||
void tick();
|
||||
void reset();
|
||||
|
||||
private:
|
||||
|
||||
Cpu6502Helper(const Cpu6502Helper&) = delete;
|
||||
Cpu6502Helper& operator=(const Cpu6502Helper&) = delete;
|
||||
|
||||
void step();
|
||||
|
||||
Cpu6502& cpu;
|
||||
bool nextPhase;
|
||||
|
||||
Common* n;
|
||||
};
|
||||
|
||||
#endif /* CPU6502HELPER_H */
|
||||
|
||||
|
2
Makefile
2
Makefile
@ -1,6 +1,6 @@
|
||||
CXXFLAGS=-g -std=c++11 -Wall -O0
|
||||
|
||||
SRCS = v6502.cpp SegmentCache.cpp TransNetwork.cpp Trace.cpp Circuit.cpp StateCalculator.cpp Cpu6502.cpp
|
||||
SRCS = v6502.cpp SegmentCache.cpp Common.cpp TransNetwork.cpp Trace.cpp Circuit.cpp StateCalculator.cpp Cpu6502.cpp Cpu6502Helper.cpp
|
||||
OBJS = $(SRCS:.cpp=.o)
|
||||
DEPS = $(SRCS:.cpp=.d)
|
||||
|
||||
|
@ -6,10 +6,15 @@
|
||||
*/
|
||||
|
||||
#include "SegmentCache.h"
|
||||
#include "Common.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <map>
|
||||
|
||||
SegmentCache::~SegmentCache() {
|
||||
delete this->c;
|
||||
}
|
||||
|
||||
Segment* SegmentCache::getOrAdd(const std::string& id) {
|
||||
if (this->cache.find(id) == this->cache.end()) {
|
||||
this->cache[id] = std::make_shared<Segment>(id);
|
||||
@ -95,7 +100,7 @@ void SegmentCache::setDataSegs(const unsigned char data) {
|
||||
this->c->DB7->set(x & 1);
|
||||
}
|
||||
|
||||
void SegmentCache::addDataToRecalc(setpSeg& s) {
|
||||
void SegmentCache::addDataToRecalc(setpSeg& s) const {
|
||||
s.insert(this->c->DB0);
|
||||
s.insert(this->c->DB1);
|
||||
s.insert(this->c->DB2);
|
||||
|
161
SegmentCache.h
161
SegmentCache.h
@ -14,18 +14,17 @@
|
||||
#include <map>
|
||||
#include <set>
|
||||
|
||||
class Common;
|
||||
|
||||
class SegmentCache {
|
||||
public:
|
||||
|
||||
SegmentCache() : c(nullptr) {
|
||||
}
|
||||
|
||||
virtual ~SegmentCache() {
|
||||
delete this->c;
|
||||
}
|
||||
virtual ~SegmentCache();
|
||||
|
||||
Segment* getOrAdd(const std::string& id);
|
||||
Segment* get(const std::string& id) const;
|
||||
|
||||
setpSeg all() const {
|
||||
setpSeg s;
|
||||
@ -35,143 +34,6 @@ public:
|
||||
return s;
|
||||
}
|
||||
|
||||
class Common {
|
||||
public:
|
||||
Segment* VSS;
|
||||
Segment* VCC;
|
||||
Segment* CLK0;
|
||||
Segment* IRQ;
|
||||
Segment* RES;
|
||||
Segment* NMI;
|
||||
Segment* RDY;
|
||||
Segment* SO;
|
||||
Segment* DB0;
|
||||
Segment* DB1;
|
||||
Segment* DB2;
|
||||
Segment* DB3;
|
||||
Segment* DB4;
|
||||
Segment* DB5;
|
||||
Segment* DB6;
|
||||
Segment* DB7;
|
||||
Segment* AB0;
|
||||
Segment* AB1;
|
||||
Segment* AB2;
|
||||
Segment* AB3;
|
||||
Segment* AB4;
|
||||
Segment* AB5;
|
||||
Segment* AB6;
|
||||
Segment* AB7;
|
||||
Segment* AB8;
|
||||
Segment* AB9;
|
||||
Segment* AB10;
|
||||
Segment* AB11;
|
||||
Segment* AB12;
|
||||
Segment* AB13;
|
||||
Segment* AB14;
|
||||
Segment* AB15;
|
||||
Segment* RW;
|
||||
Segment* SYNC;
|
||||
Segment* CLK1OUT;
|
||||
Segment* CLK2OUT;
|
||||
Segment* A0;
|
||||
Segment* A1;
|
||||
Segment* A2;
|
||||
Segment* A3;
|
||||
Segment* A4;
|
||||
Segment* A5;
|
||||
Segment* A6;
|
||||
Segment* A7;
|
||||
Segment* X0;
|
||||
Segment* X1;
|
||||
Segment* X2;
|
||||
Segment* X3;
|
||||
Segment* X4;
|
||||
Segment* X5;
|
||||
Segment* X6;
|
||||
Segment* X7;
|
||||
Segment* Y0;
|
||||
Segment* Y1;
|
||||
Segment* Y2;
|
||||
Segment* Y3;
|
||||
Segment* Y4;
|
||||
Segment* Y5;
|
||||
Segment* Y6;
|
||||
Segment* Y7;
|
||||
Segment* PCL0;
|
||||
Segment* PCL1;
|
||||
Segment* PCL2;
|
||||
Segment* PCL3;
|
||||
Segment* PCL4;
|
||||
Segment* PCL5;
|
||||
Segment* PCL6;
|
||||
Segment* PCL7;
|
||||
Segment* PCH0;
|
||||
Segment* PCH1;
|
||||
Segment* PCH2;
|
||||
Segment* PCH3;
|
||||
Segment* PCH4;
|
||||
Segment* PCH5;
|
||||
Segment* PCH6;
|
||||
Segment* PCH7;
|
||||
Segment* P0;
|
||||
Segment* P1;
|
||||
Segment* P2;
|
||||
Segment* P3;
|
||||
Segment* P4;
|
||||
Segment* P6;
|
||||
Segment* P7;
|
||||
Segment* S0;
|
||||
Segment* S1;
|
||||
Segment* S2;
|
||||
Segment* S3;
|
||||
Segment* S4;
|
||||
Segment* S5;
|
||||
Segment* S6;
|
||||
Segment* S7;
|
||||
|
||||
Common(
|
||||
Segment* VSS, Segment* VCC,
|
||||
Segment* CLK0,
|
||||
Segment* IRQ, Segment* RES, Segment* NMI,
|
||||
Segment* RDY, Segment* SO,
|
||||
Segment* DB0, Segment* DB1, Segment* DB2, Segment* DB3, Segment* DB4, Segment* DB5, Segment* DB6, Segment* DB7,
|
||||
Segment* AB0, Segment* AB1, Segment* AB2, Segment* AB3, Segment* AB4, Segment* AB5, Segment* AB6, Segment* AB7,
|
||||
Segment* AB8, Segment* AB9, Segment* AB10, Segment* AB11, Segment* AB12, Segment* AB13, Segment* AB14, Segment* AB15,
|
||||
Segment* RW, Segment* SYNC,
|
||||
Segment* CLK1OUT, Segment* CLK2OUT,
|
||||
Segment* A0, Segment* A1, Segment* A2, Segment* A3, Segment* A4, Segment* A5, Segment* A6, Segment* A7,
|
||||
Segment* X0, Segment* X1, Segment* X2, Segment* X3, Segment* X4, Segment* X5, Segment* X6, Segment* X7,
|
||||
Segment* Y0, Segment* Y1, Segment* Y2, Segment* Y3, Segment* Y4, Segment* Y5, Segment* Y6, Segment* Y7,
|
||||
Segment* PCL0, Segment* PCL1, Segment* PCL2, Segment* PCL3, Segment* PCL4, Segment* PCL5, Segment* PCL6, Segment* PCL7,
|
||||
Segment* PCH0, Segment* PCH1, Segment* PCH2, Segment* PCH3, Segment* PCH4, Segment* PCH5, Segment* PCH6, Segment* PCH7,
|
||||
Segment* P0, Segment* P1, Segment* P2, Segment* P3, Segment* P4, /* no P5 */ Segment* P6, Segment* P7,
|
||||
Segment* S0, Segment* S1, Segment* S2, Segment* S3, Segment* S4, Segment* S5, Segment* S6, Segment* S7) :
|
||||
VSS(VSS), VCC(VCC),
|
||||
CLK0(CLK0),
|
||||
IRQ(IRQ), RES(RES), NMI(NMI),
|
||||
RDY(RDY), SO(SO),
|
||||
DB0(DB0), DB1(DB1), DB2(DB2), DB3(DB3), DB4(DB4), DB5(DB5), DB6(DB6), DB7(DB7),
|
||||
AB0(AB0), AB1(AB1), AB2(AB2), AB3(AB3), AB4(AB4), AB5(AB5), AB6(AB6), AB7(AB7),
|
||||
AB8(AB8), AB9(AB9), AB10(AB10), AB11(AB11), AB12(AB12), AB13(AB13), AB14(AB14), AB15(AB15),
|
||||
RW(RW), SYNC(SYNC),
|
||||
CLK1OUT(CLK1OUT), CLK2OUT(CLK2OUT),
|
||||
A0(A0), A1(A1), A2(A2), A3(A3), A4(A4), A5(A5), A6(A6), A7(A7),
|
||||
X0(X0), X1(X1), X2(X2), X3(X3), X4(X4), X5(X5), X6(X6), X7(X7),
|
||||
Y0(Y0), Y1(Y1), Y2(Y2), Y3(Y3), Y4(Y4), Y5(Y5), Y6(Y6), Y7(Y7),
|
||||
PCL0(PCL0), PCL1(PCL1), PCL2(PCL2), PCL3(PCL3), PCL4(PCL4), PCL5(PCL5), PCL6(PCL6), PCL7(PCL7),
|
||||
PCH0(PCH0), PCH1(PCH1), PCH2(PCH2), PCH3(PCH3), PCH4(PCH4), PCH5(PCH5), PCH6(PCH6), PCH7(PCH7),
|
||||
P0(P0), P1(P1), P2(P2), P3(P3), P4(P4), /* no P5 */ P6(P6), P7(P7),
|
||||
S0(S0), S1(S1), S2(S2), S3(S3), S4(S4), S5(S5), S6(S6), S7(S7) {
|
||||
}
|
||||
~Common() {}
|
||||
|
||||
private:
|
||||
Common(const Common&) = delete;
|
||||
Common& operator=(const Common&) = delete;
|
||||
};
|
||||
|
||||
void initCommon();
|
||||
Common* c;
|
||||
|
||||
unsigned char rData() const;
|
||||
unsigned short rAddr() const;
|
||||
@ -182,16 +44,27 @@ public:
|
||||
unsigned short rPC() const;
|
||||
|
||||
void setDataSegs(const unsigned char data);
|
||||
void addDataToRecalc(setpSeg& s);
|
||||
void addDataToRecalc(setpSeg& s) const;
|
||||
|
||||
std::map<const std::string, std::shared_ptr<Segment > >::const_iterator begin() const { return this->cache.begin(); }
|
||||
std::map<const std::string, std::shared_ptr<Segment > >::const_iterator end() const { return this->cache.end(); }
|
||||
std::map<const std::string, std::shared_ptr<Segment > >::const_iterator begin() const {
|
||||
return this->cache.begin();
|
||||
}
|
||||
|
||||
std::map<const std::string, std::shared_ptr<Segment > >::const_iterator end() const {
|
||||
return this->cache.end();
|
||||
}
|
||||
|
||||
private:
|
||||
std::map<const std::string, std::shared_ptr<Segment > > cache;
|
||||
|
||||
SegmentCache(const SegmentCache&) = delete;
|
||||
SegmentCache& operator=(const SegmentCache&) = delete;
|
||||
|
||||
Segment* get(const std::string& id) const;
|
||||
|
||||
public:
|
||||
void initCommon();
|
||||
Common* c;
|
||||
};
|
||||
|
||||
#endif /* SEGMENTCACHE_H */
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
#include "Trace.h"
|
||||
#include "SegmentCache.h"
|
||||
#include "Common.h"
|
||||
#include <iostream>
|
||||
#include <iomanip>
|
||||
#include <cassert>
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include <string>
|
||||
#include <memory>
|
||||
#include <iostream>
|
||||
#include "StateCalculator.h"
|
||||
|
||||
TransNetwork::TransNetwork(std::istream& in) {
|
||||
std::string c1, gate, c2;
|
||||
@ -21,6 +22,8 @@ TransNetwork::TransNetwork(std::istream& in) {
|
||||
}
|
||||
|
||||
this->segs.initCommon();
|
||||
|
||||
StateCalculator::recalc(this->segs.all());
|
||||
}
|
||||
|
||||
TransNetwork::~TransNetwork() {
|
||||
|
40
ptr_less.h
40
ptr_less.h
@ -1,20 +1,20 @@
|
||||
/*
|
||||
* File: ptr_less.h
|
||||
* Author: Christopher
|
||||
*
|
||||
* Created on December 14, 2013, 5:44 PM
|
||||
*/
|
||||
|
||||
#ifndef PTR_LESS_H
|
||||
#define PTR_LESS_H
|
||||
|
||||
template<typename T>
|
||||
struct ptr_less {
|
||||
|
||||
bool operator()(T* pa, T* pb) {
|
||||
return *pa < *pb;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#endif /* PTR_LESS_H */
|
||||
/*
|
||||
* File: ptr_less.h
|
||||
* Author: Christopher
|
||||
*
|
||||
* Created on December 14, 2013, 5:44 PM
|
||||
*/
|
||||
|
||||
#ifndef PTR_LESS_H
|
||||
#define PTR_LESS_H
|
||||
|
||||
template<typename T>
|
||||
struct ptr_less {
|
||||
|
||||
bool operator()(T* pa, T* pb) {
|
||||
return *pa < *pb;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#endif /* PTR_LESS_H */
|
||||
|
10
v6502.cpp
10
v6502.cpp
@ -1,5 +1,6 @@
|
||||
#include "addressbus.h"
|
||||
#include "Cpu6502.h"
|
||||
#include "Cpu6502Helper.h"
|
||||
#include "TransNetwork.h"
|
||||
#include "Trace.h"
|
||||
#include <cstdlib>
|
||||
@ -36,6 +37,7 @@ int main(int argc, char *argv[]) {
|
||||
TransNetwork tn(if_trans);
|
||||
Trace trace(tn.segs);
|
||||
Cpu6502 cpu(tn, mem, trace);
|
||||
Cpu6502Helper cpuhelper(cpu);
|
||||
|
||||
|
||||
|
||||
@ -44,22 +46,22 @@ int main(int argc, char *argv[]) {
|
||||
/* turn on the CPU */
|
||||
std::cout << "----------------------------------------" << std::endl;
|
||||
std::cout << "begin power-up..." << std::endl;
|
||||
cpu.powerOn();
|
||||
cpuhelper.powerOn();
|
||||
std::cout << "end power-up..." << std::endl;
|
||||
std::cout << "----------------------------------------" << std::endl;
|
||||
|
||||
/* run it a bit, before resetting */
|
||||
std::cout << "some power-up pre-reset cycles..." << std::endl;
|
||||
for (int i(0); i < 10; ++i) {
|
||||
cpu.tick();
|
||||
cpuhelper.tick();
|
||||
}
|
||||
std::cout << "----------------------------------------" << std::endl;
|
||||
|
||||
/* reset the CPU, and let it run for a little while, then exit */
|
||||
std::cout << "RESET..." << std::endl;
|
||||
cpu.reset();
|
||||
cpuhelper.reset();
|
||||
for (int i(0); i < 50; ++i) {
|
||||
cpu.tick();
|
||||
cpuhelper.tick();
|
||||
}
|
||||
|
||||
return EXIT_SUCCESS;
|
||||
|
Loading…
x
Reference in New Issue
Block a user