Fixed CPU start/stop control; runCPU is now strictly a worker function, not a control interface (PDP-11 only; other CPUs still need to be updated to match)
This commit is contained in:
parent
c858fd0699
commit
c7dbfc02be
18 changed files with 945 additions and 918 deletions
|
|
@ -65,7 +65,7 @@ if (NODE) {
|
|||
*/
|
||||
function BusPDP11(parmsBus, cpu, dbg)
|
||||
{
|
||||
Component.call(this, "Bus", parmsBus, BusPDP11);
|
||||
Component.call(this, "Bus", parmsBus, BusPDP11, MessagesPDP11.BUS);
|
||||
|
||||
this.cpu = cpu;
|
||||
this.dbg = dbg;
|
||||
|
|
@ -124,6 +124,10 @@ function BusPDP11(parmsBus, cpu, dbg)
|
|||
*
|
||||
* The false case is important if fIOBreakAll is set, because it allows the Debugger to selectively
|
||||
* ignore specific addresses.
|
||||
*
|
||||
* Finally, for debugging purposes, if an I/O address has a symbolic name, it will be saved here:
|
||||
*
|
||||
* [5]: symbolic name of I/O address
|
||||
*/
|
||||
this.aIOHandlers = [];
|
||||
this.fIOBreakAll = false;
|
||||
|
|
@ -186,6 +190,7 @@ BusPDP11.IOController = {
|
|||
var bus = this.controller;
|
||||
var afn = bus.aIOHandlers[off];
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".readByte(" + str.toOct(addr) + ")", 0, true);
|
||||
if (afn[0]) {
|
||||
return afn[0](addr);
|
||||
} else if (afn[2]) {
|
||||
|
|
@ -197,8 +202,11 @@ BusPDP11.IOController = {
|
|||
}
|
||||
} else if (addr & 0x1) {
|
||||
afn = bus.aIOHandlers[off & ~0x1];
|
||||
if (afn[2]) {
|
||||
return afn[2](addr & ~0x1) >> 8;
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".readByte(" + str.toOct(addr) + ")", 0, true);
|
||||
if (afn[2]) {
|
||||
return afn[2](addr & ~0x1) >> 8;
|
||||
}
|
||||
}
|
||||
}
|
||||
bus.println("warning: unconverted read access to byte @" + str.toOct(addr));
|
||||
|
|
@ -219,6 +227,7 @@ BusPDP11.IOController = {
|
|||
var bus = this.controller;
|
||||
var afn = bus.aIOHandlers[off];
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".writeByte(" + str.toOct(addr) + "," + str.toOct(b) + ")", 0, true);
|
||||
/*
|
||||
* If a writeByte() handler exists, call it; we're done
|
||||
*/
|
||||
|
|
@ -246,11 +255,14 @@ BusPDP11.IOController = {
|
|||
* data pre-inserted into (the high byte of) the original data.
|
||||
*/
|
||||
afn = bus.aIOHandlers[off & ~0x1];
|
||||
if (afn[3]) {
|
||||
addr &= ~0x1;
|
||||
w = afn[2]? afn[2](addr) : 0;
|
||||
afn[3]((w & 0xff) | (b << 8), addr);
|
||||
return;
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".writeByte(" + str.toOct(addr) + "," + str.toOct(b) + ")", 0, true);
|
||||
if (afn[3]) {
|
||||
addr &= ~0x1;
|
||||
w = afn[2]? afn[2](addr) : 0;
|
||||
afn[3]((w & 0xff) | (b << 8), addr);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
bus.println("warning: unconverted write access to byte @" + str.toOct(addr));
|
||||
|
|
@ -271,6 +283,7 @@ BusPDP11.IOController = {
|
|||
Component.assert(!(addr & 1)); // unaligned addresses should be getting trapped at a higher level
|
||||
var afn = bus.aIOHandlers[off];
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".readWord(" + str.toOct(addr) + ")", 0, true);
|
||||
if (afn[2]) {
|
||||
return afn[2](addr);
|
||||
} else if (afn[0]) {
|
||||
|
|
@ -295,6 +308,7 @@ BusPDP11.IOController = {
|
|||
Component.assert(!(addr & 1)); // unaligned addresses should be getting trapped at a higher level
|
||||
var afn = bus.aIOHandlers[off];
|
||||
if (afn) {
|
||||
if (bus.messageEnabled()) bus.printMessage(afn[5] + ".writeWord(" + str.toOct(addr) + "," + str.toOct(w) + ")", 0, true);
|
||||
if (afn[3]) {
|
||||
afn[3](w, addr);
|
||||
return;
|
||||
|
|
@ -972,7 +986,7 @@ BusPDP11.prototype.restoreMemory = function(a)
|
|||
};
|
||||
|
||||
/**
|
||||
* addIOHandlers(start, end, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord)
|
||||
* addIOHandlers(start, end, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord, sName)
|
||||
*
|
||||
* Add I/O notification handlers to the master list (aIOHandlers). The start and end addresses are typically
|
||||
* relative to the starting IOPAGE address, but they can also be absolute; we simply mask all addresses with
|
||||
|
|
@ -985,8 +999,9 @@ BusPDP11.prototype.restoreMemory = function(a)
|
|||
* @param {function(number,number)|null|undefined} fnWriteByte
|
||||
* @param {function(number)|null|undefined} fnReadWord
|
||||
* @param {function(number,number)|null|undefined} fnWriteWord
|
||||
* @param {string} [sName]
|
||||
*/
|
||||
BusPDP11.prototype.addIOHandlers = function(start, end, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord)
|
||||
BusPDP11.prototype.addIOHandlers = function(start, end, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord, sName)
|
||||
{
|
||||
for (var addr = start; addr <= end; addr += 2) {
|
||||
var off = addr & BusPDP11.IOPAGE_MASK;
|
||||
|
|
@ -994,7 +1009,7 @@ BusPDP11.prototype.addIOHandlers = function(start, end, fnReadByte, fnWriteByte,
|
|||
Component.warning("I/O address already registered: " + str.toHexLong(addr));
|
||||
continue;
|
||||
}
|
||||
this.aIOHandlers[off] = [fnReadByte, fnWriteByte, fnReadWord, fnWriteWord, false];
|
||||
this.aIOHandlers[off] = [fnReadByte, fnWriteByte, fnReadWord, fnWriteWord, false, sName || "unknown"];
|
||||
if (MAXDEBUG) this.log("addIOHandlers(" + str.toHexLong(addr) + ")");
|
||||
}
|
||||
};
|
||||
|
|
@ -1002,7 +1017,7 @@ BusPDP11.prototype.addIOHandlers = function(start, end, fnReadByte, fnWriteByte,
|
|||
/**
|
||||
* addIOTable(component, table)
|
||||
*
|
||||
* Add I/O notification handlers from the specified table (a batch version of addIOHandlers)
|
||||
* Add I/O notification handlers from the specified table (a batch version of addIOHandlers).
|
||||
*
|
||||
* @this {BusPDP11}
|
||||
* @param {Component} component
|
||||
|
|
@ -1016,7 +1031,7 @@ BusPDP11.prototype.addIOTable = function(component, table)
|
|||
var fnWriteByte = afn[1]? afn[1].bind(component) : null;
|
||||
var fnReadWord = afn[2]? afn[2].bind(component) : null;
|
||||
var fnWriteWord = afn[3]? afn[3].bind(component) : null;
|
||||
this.addIOHandlers(+port, +port, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord);
|
||||
this.addIOHandlers(+port, +port, fnReadByte, fnWriteByte, fnReadWord, fnWriteWord, afn[4]);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -983,7 +983,7 @@ ComputerPDP11.prototype.reset = function()
|
|||
*
|
||||
* Notify all (other) components with a start() method that the CPU has started.
|
||||
*
|
||||
* Note that we're called by runCPU(), which is why we exclude the CPU component,
|
||||
* Note that we're called by startCPU(), which is why we exclude the CPU component,
|
||||
* as well as ourselves.
|
||||
*
|
||||
* @this {ComputerPDP11}
|
||||
|
|
@ -1007,7 +1007,7 @@ ComputerPDP11.prototype.start = function(ms, nCycles)
|
|||
*
|
||||
* Notify all (other) components with a stop() method that the CPU has stopped.
|
||||
*
|
||||
* Note that we're called by runCPU(), which is why we exclude the CPU component,
|
||||
* Note that we're called by stopCPU(), which is why we exclude the CPU component,
|
||||
* as well as ourselves.
|
||||
*
|
||||
* @this {ComputerPDP11}
|
||||
|
|
|
|||
|
|
@ -303,10 +303,10 @@ CPUPDP11.prototype.autoStart = function()
|
|||
*/
|
||||
if (this.flags.autoStart || (!DEBUGGER || !this.dbg) && this.bindings["run"] === undefined) {
|
||||
/*
|
||||
* Now we ALSO set fUpdateFocus when calling runCPU(), on the assumption that in the "auto-starting" context,
|
||||
* a machine without focus is like a day without sunshine.
|
||||
* Now we ALSO set fUpdateFocus when calling startCPU(), on the assumption that in the "auto-starting"
|
||||
* context, a machine without focus is like a day without sunshine.
|
||||
*/
|
||||
this.runCPU(true);
|
||||
this.startCPU(true);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
|
@ -496,12 +496,12 @@ CPUPDP11.prototype.setBinding = function(sHTMLType, sBinding, control, sValue)
|
|||
control.onclick = function onClickRun() {
|
||||
if (!cpu.cmp || !cpu.cmp.checkPower()) return;
|
||||
/*
|
||||
* We no longer pass true to these runCPU()/stopCPU() calls, on the theory that if the "run"
|
||||
* We no longer pass true to these startCPU()/stopCPU() calls, on the theory that if the "run"
|
||||
* control is visible, then the computer is probably sufficiently visible as well; the problem
|
||||
* with setting fUpdateFocus to true is that it can jerk the web page around in annoying ways.
|
||||
*/
|
||||
if (!cpu.flags.running)
|
||||
cpu.runCPU();
|
||||
cpu.startCPU();
|
||||
else
|
||||
cpu.stopCPU();
|
||||
};
|
||||
|
|
@ -1053,20 +1053,13 @@ CPUPDP11.prototype.endBurst = function()
|
|||
};
|
||||
|
||||
/**
|
||||
* runCPU(fUpdateFocus)
|
||||
* runCPU()
|
||||
*
|
||||
* @this {CPUPDP11}
|
||||
* @param {boolean} [fUpdateFocus] is true to update Computer focus
|
||||
*/
|
||||
CPUPDP11.prototype.runCPU = function(fUpdateFocus)
|
||||
CPUPDP11.prototype.runCPU = function()
|
||||
{
|
||||
if (!this.setBusy(true)) {
|
||||
this.updateCPU();
|
||||
if (this.cmp) this.cmp.stop(usr.getTime(), this.getCycles());
|
||||
return;
|
||||
}
|
||||
|
||||
this.startCPU(fUpdateFocus);
|
||||
if (!this.flags.running) return;
|
||||
|
||||
/*
|
||||
* calcStartTime() initializes the cycle counter and timestamp for this runCPU() invocation, and optionally
|
||||
|
|
@ -1131,42 +1124,49 @@ CPUPDP11.prototype.runCPU = function(fUpdateFocus)
|
|||
this.stopCPU();
|
||||
this.updateCPU();
|
||||
if (this.cmp) this.cmp.stop(usr.getTime(), this.getCycles());
|
||||
this.setBusy(false);
|
||||
this.setError(e.stack || e.message);
|
||||
return;
|
||||
}
|
||||
|
||||
setTimeout(this.onRunTimeout, this.calcRemainingTime());
|
||||
if (this.flags.running) setTimeout(this.onRunTimeout, this.calcRemainingTime());
|
||||
};
|
||||
|
||||
/**
|
||||
* startCPU(fUpdateFocus)
|
||||
*
|
||||
* WARNING: Other components must use runCPU() to get the CPU running; this is a runCPU() helper function only.
|
||||
* For use by any component that wants to start the CPU.
|
||||
*
|
||||
* @param {boolean} [fUpdateFocus]
|
||||
* @return {boolean}
|
||||
*/
|
||||
CPUPDP11.prototype.startCPU = function(fUpdateFocus)
|
||||
{
|
||||
if (!this.flags.running) {
|
||||
/*
|
||||
* setSpeed() without a speed parameter leaves the selected speed in place, but also resets the
|
||||
* cycle counter and timestamp for the current series of runCPU() calls, calculates the maximum number
|
||||
* of cycles for each burst based on the last known effective CPU speed, and resets the nCyclesRecalc
|
||||
* threshold counter.
|
||||
*/
|
||||
this.setSpeed();
|
||||
if (this.cmp) this.cmp.start(this.msStartRun, this.getCycles());
|
||||
this.flags.running = true;
|
||||
this.flags.starting = true;
|
||||
if (this.chipset) this.chipset.start();
|
||||
var controlRun = this.bindings["run"];
|
||||
if (controlRun) controlRun.textContent = "Halt";
|
||||
if (this.cmp) {
|
||||
this.cmp.updateStatus(true);
|
||||
if (fUpdateFocus) this.cmp.updateFocus(true);
|
||||
}
|
||||
if (this.isError()) {
|
||||
return false;
|
||||
}
|
||||
if (this.flags.running) {
|
||||
this.println(this.toString() + " busy");
|
||||
return false;
|
||||
}
|
||||
/*
|
||||
* setSpeed() without a speed parameter leaves the selected speed in place, but also resets the
|
||||
* cycle counter and timestamp for the current series of runCPU() calls, calculates the maximum number
|
||||
* of cycles for each burst based on the last known effective CPU speed, and resets the nCyclesRecalc
|
||||
* threshold counter.
|
||||
*/
|
||||
this.setSpeed();
|
||||
this.flags.running = true;
|
||||
this.flags.starting = true;
|
||||
if (this.chipset) this.chipset.start();
|
||||
var controlRun = this.bindings["run"];
|
||||
if (controlRun) controlRun.textContent = "Halt";
|
||||
if (this.cmp) {
|
||||
this.cmp.start(this.msStartRun, this.getCycles());
|
||||
if (fUpdateFocus) this.cmp.updateFocus(true);
|
||||
}
|
||||
this.updateCPU(true);
|
||||
setTimeout(this.onRunTimeout, 0);
|
||||
return true;
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
@ -1196,15 +1196,18 @@ CPUPDP11.prototype.stepCPU = function(nMinCycles)
|
|||
*/
|
||||
CPUPDP11.prototype.stopCPU = function(fComplete)
|
||||
{
|
||||
this.isBusy(true);
|
||||
this.endBurst();
|
||||
this.addCycles(this.nRunCycles);
|
||||
this.nRunCycles = 0;
|
||||
if (this.flags.running) {
|
||||
this.endBurst();
|
||||
this.addCycles(this.nRunCycles);
|
||||
this.nRunCycles = 0;
|
||||
this.flags.running = false;
|
||||
if (this.chipset) this.chipset.stop();
|
||||
var controlRun = this.bindings["run"];
|
||||
if (controlRun) controlRun.textContent = "Run";
|
||||
if (this.cmp) {
|
||||
this.cmp.stop(usr.getTime(), this.getCycles());
|
||||
}
|
||||
this.updateCPU();
|
||||
}
|
||||
this.flags.complete = fComplete;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -912,8 +912,8 @@ CPUStatePDP11.prototype.trap = function(vector, reason)
|
|||
this.trapPSW = -1; // reset flag that we have a trap within a trap
|
||||
|
||||
if (DEBUG && this.dbg) {
|
||||
if (reason != PDP11.REASON.INTERRUPT) {
|
||||
this.dbg.println("trap to vector " + this.dbg.toBase(vector, 0, true) + (reason? " (reason " + reason + ")" : ""));
|
||||
if (this.messageEnabled(MessagesPDP11.TRAP)) {
|
||||
this.printMessage("trap to vector " + this.dbg.toBase(vector, 0, true) + (reason? " (reason " + reason + ")" : ""), MessagesPDP11.TRAP, true);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1719,7 +1719,11 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.opFlags &= ~PDP11.OPFLAG.TRAP_MASK;
|
||||
}
|
||||
|
||||
if (this.priorityReview) {
|
||||
/*
|
||||
* By requiring nMinCycles to be non-zero before checking the interrupt queue, we avoid
|
||||
* interrupting the natural flow of instructions when the Debugger is stepping through code.
|
||||
*/
|
||||
if (nMinCycles && this.priorityReview) {
|
||||
this.checkInterruptQueue();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1053,7 +1053,7 @@ if (DEBUGGER) {
|
|||
*
|
||||
* @this {DebuggerPDP11}
|
||||
* @param {string} sMessage is any caller-defined message string
|
||||
* @param {boolean} [fAddress] is true to display the current CS:IP
|
||||
* @param {boolean} [fAddress] is true to display the current PC
|
||||
*/
|
||||
DebuggerPDP11.prototype.message = function(sMessage, fAddress)
|
||||
{
|
||||
|
|
@ -1151,16 +1151,16 @@ if (DEBUGGER) {
|
|||
};
|
||||
|
||||
/**
|
||||
* runCPU(fUpdateFocus)
|
||||
* startCPU(fUpdateFocus)
|
||||
*
|
||||
* @this {DebuggerPDP11}
|
||||
* @param {boolean} [fUpdateFocus] is true to update focus
|
||||
* @return {boolean} true if run request successful, false if not
|
||||
*/
|
||||
DebuggerPDP11.prototype.runCPU = function(fUpdateFocus)
|
||||
DebuggerPDP11.prototype.startCPU = function(fUpdateFocus)
|
||||
{
|
||||
if (!this.isCPUAvail()) return false;
|
||||
this.cpu.runCPU(fUpdateFocus);
|
||||
if (!this.checkCPU()) return false;
|
||||
this.cpu.startCPU(fUpdateFocus);
|
||||
return true;
|
||||
};
|
||||
|
||||
|
|
@ -1175,7 +1175,7 @@ if (DEBUGGER) {
|
|||
*/
|
||||
DebuggerPDP11.prototype.stepCPU = function(nCycles, fRegs, fUpdateCPU)
|
||||
{
|
||||
if (!this.isCPUAvail()) return false;
|
||||
if (!this.checkCPU()) return false;
|
||||
|
||||
this.nCycles = 0;
|
||||
|
||||
|
|
@ -1212,7 +1212,7 @@ if (DEBUGGER) {
|
|||
}
|
||||
|
||||
/*
|
||||
* Because we called cpu.stepCPU() and not cpu.runCPU(), we must nudge the cpu's update code,
|
||||
* Because we called cpu.stepCPU() and not cpu.startCPU(), we must nudge the cpu's update code,
|
||||
* and then update our own state. Normally, the only time fUpdateCPU will be false is when doTrace()
|
||||
* is calling us in a loop, in which case it will perform its own updateCPU() when it's done.
|
||||
*/
|
||||
|
|
@ -1257,14 +1257,14 @@ if (DEBUGGER) {
|
|||
};
|
||||
|
||||
/**
|
||||
* isCPUAvail()
|
||||
* checkCPU()
|
||||
*
|
||||
* Make sure the CPU is ready (finished initializing), not busy (already running), and not in an error state.
|
||||
* Make sure the CPU is ready (finished initializing), powered, not already running, and not in an error state.
|
||||
*
|
||||
* @this {DebuggerPDP11}
|
||||
* @return {boolean}
|
||||
*/
|
||||
DebuggerPDP11.prototype.isCPUAvail = function()
|
||||
DebuggerPDP11.prototype.checkCPU = function()
|
||||
{
|
||||
if (!this.cpu)
|
||||
return false;
|
||||
|
|
@ -1272,7 +1272,7 @@ if (DEBUGGER) {
|
|||
return false;
|
||||
if (!this.cpu.isPowered())
|
||||
return false;
|
||||
if (this.cpu.isBusy())
|
||||
if (this.cpu.isRunning())
|
||||
return false;
|
||||
return !this.cpu.isError();
|
||||
};
|
||||
|
|
@ -3209,7 +3209,7 @@ if (DEBUGGER) {
|
|||
this.parseAddrOptions(dbgAddr, sOptions);
|
||||
this.setTempBreakpoint(dbgAddr);
|
||||
}
|
||||
if (!this.runCPU(true)) {
|
||||
if (!this.startCPU(true)) {
|
||||
if (!fQuiet) this.println("cpu busy or unavailable, run command ignored");
|
||||
}
|
||||
};
|
||||
|
|
@ -3268,7 +3268,7 @@ if (DEBUGGER) {
|
|||
|
||||
if (this.nStep) {
|
||||
this.setTempBreakpoint(dbgAddr);
|
||||
if (!this.runCPU()) {
|
||||
if (!this.startCPU()) {
|
||||
if (this.cmp) this.cmp.updateFocus();
|
||||
this.nStep = 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -218,6 +218,9 @@ var PDP11 = {
|
|||
PIRQ: 0xA0, // 240 PIRQ, program interrupt request
|
||||
MMU_FAULT: 0xA8 // 250 MMU aborts and traps
|
||||
},
|
||||
/*
|
||||
* PDP-11 trap reasons (for diagnostic purposes only)
|
||||
*/
|
||||
REASON: {
|
||||
BPT: 1,
|
||||
EMT: 2,
|
||||
|
|
@ -225,18 +228,18 @@ var PDP11 = {
|
|||
IOT: 4,
|
||||
TRAP: 5,
|
||||
RESERVED: 6,
|
||||
ODDMEMADDR: 22,
|
||||
NOMEMORY: 24,
|
||||
ODDMMUADDR: 26,
|
||||
MAPERROR: 28,
|
||||
PUSHERROR: 32,
|
||||
NOREGADDR: 34,
|
||||
STACKMODE1: 36,
|
||||
STACKERROR: 38,
|
||||
INTERRUPT: 44,
|
||||
TRAPMMU: 52,
|
||||
TRAPSP: 54,
|
||||
TRAPTF: 56
|
||||
ODDMEMADDR: 10,
|
||||
NOMEMORY: 12,
|
||||
ODDMMUADDR: 14,
|
||||
MAPERROR: 16,
|
||||
PUSHERROR: 18,
|
||||
NOREGADDR: 20,
|
||||
STACKMODE1: 22,
|
||||
STACKERROR: 24,
|
||||
INTERRUPT: 26,
|
||||
TRAPMMU: 28,
|
||||
TRAPSP: 30,
|
||||
TRAPTF: 32
|
||||
},
|
||||
/*
|
||||
* Internal memory access flags
|
||||
|
|
|
|||
|
|
@ -199,7 +199,7 @@ DevicePDP11.prototype.initBus = function(cmp, bus, cpu, dbg)
|
|||
switch(this.sDeviceName) {
|
||||
case DevicePDP11.UNIBUS_NAME:
|
||||
default:
|
||||
bus.addIOTable(this, DevicePDP11.UNIBUS_TABLE);
|
||||
bus.addIOTable(this, DevicePDP11.UNIBUS_IOTABLE);
|
||||
bus.addIODefaultHandlers(this.reset.bind(this), this.access.bind(this));
|
||||
break;
|
||||
}
|
||||
|
|
@ -951,8 +951,8 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
case 0x3FFFC0: /*017777700*/ // 017777700 - 017777777
|
||||
switch (physicalAddress & ~1) {
|
||||
//
|
||||
// Superseded by UNIBUS_TABLE (more of this code will be commented out
|
||||
// as it is replaced by read/write handlers in UNIBUS_TABLE; stay tuned).
|
||||
// Superseded by UNIBUS_IOTABLE (more of this code will be commented out
|
||||
// as it is replaced by read/write handlers in UNIBUS_IOTABLE; stay tuned).
|
||||
//
|
||||
// case 0x3FFFFE: // 017777776 // PSW
|
||||
// result = cpu.getPSW();
|
||||
|
|
@ -1537,12 +1537,12 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
/*
|
||||
* ES6 ALERT: As you can see below, I've finally started using computed property names.
|
||||
*/
|
||||
DevicePDP11.UNIBUS_TABLE = {
|
||||
[PDP11.UNIBUS.LKS]: /* 177546 */ [null, null, DevicePDP11.prototype.readLKS, DevicePDP11.prototype.writeLKS],
|
||||
[PDP11.UNIBUS.RCSR]: /* 177560 */ [null, null, DevicePDP11.prototype.readRCSR, DevicePDP11.prototype.writeRCSR],
|
||||
[PDP11.UNIBUS.XCSR]: /* 177564 */ [null, null, DevicePDP11.prototype.readXCSR, DevicePDP11.prototype.writeXCSR],
|
||||
[PDP11.UNIBUS.MMR0]: /* 177572 */ [null, null, DevicePDP11.prototype.readMMR0, DevicePDP11.prototype.writeMMR0],
|
||||
[PDP11.UNIBUS.PSW]: /* 177776 */ [null, null, DevicePDP11.prototype.readPSW, DevicePDP11.prototype.writePSW]
|
||||
DevicePDP11.UNIBUS_IOTABLE = {
|
||||
[PDP11.UNIBUS.LKS]: /* 177546 */ [null, null, DevicePDP11.prototype.readLKS, DevicePDP11.prototype.writeLKS, "LKS"],
|
||||
[PDP11.UNIBUS.RCSR]: /* 177560 */ [null, null, DevicePDP11.prototype.readRCSR, DevicePDP11.prototype.writeRCSR, "RCSR"],
|
||||
[PDP11.UNIBUS.XCSR]: /* 177564 */ [null, null, DevicePDP11.prototype.readXCSR, DevicePDP11.prototype.writeXCSR, "XCSR"],
|
||||
[PDP11.UNIBUS.MMR0]: /* 177572 */ [null, null, DevicePDP11.prototype.readMMR0, DevicePDP11.prototype.writeMMR0, "MMR0"],
|
||||
[PDP11.UNIBUS.PSW]: /* 177776 */ [null, null, DevicePDP11.prototype.readPSW, DevicePDP11.prototype.writePSW, "PSW"]
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -35,6 +35,7 @@
|
|||
|
||||
var MessagesPDP11 = {
|
||||
CPU: 0x00000001,
|
||||
TRAP: 0x00000010,
|
||||
BUS: 0x00000040,
|
||||
MEM: 0x00000080,
|
||||
KEYBOARD: 0x00010000,
|
||||
|
|
@ -65,6 +66,7 @@ var MessagesPDP11 = {
|
|||
*/
|
||||
MessagesPDP11.CATEGORIES = {
|
||||
"cpu": MessagesPDP11.CPU,
|
||||
"trap": MessagesPDP11.TRAP,
|
||||
"bus": MessagesPDP11.BUS,
|
||||
"mem": MessagesPDP11.MEM,
|
||||
"keyboard": MessagesPDP11.KEYBOARD, // "kbd" is also allowed as shorthand for "keyboard"; see doMessages()
|
||||
|
|
|
|||
|
|
@ -949,7 +949,7 @@ Component.prototype = {
|
|||
/**
|
||||
* setBusy(fBusy)
|
||||
*
|
||||
* Update the current busy state; if an fCancel request is pending, it will be honored now.
|
||||
* Update the current busy state; if a busyCancel request is pending, it will be honored now.
|
||||
*
|
||||
* @this {Component}
|
||||
* @param {boolean} fBusy
|
||||
|
|
@ -957,9 +957,7 @@ Component.prototype = {
|
|||
*/
|
||||
setBusy: function(fBusy) {
|
||||
if (this.flags.busyCancel) {
|
||||
if (this.flags.busy) {
|
||||
this.flags.busy = false;
|
||||
}
|
||||
this.flags.busy = false;
|
||||
this.flags.busyCancel = false;
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue