Enable the Debugger to get/set front panel switches as register SW
This commit is contained in:
parent
d5c7bf0b5d
commit
b3bf213cd9
8 changed files with 563 additions and 454 deletions
|
|
@ -57,30 +57,40 @@ function PanelPDP11(parmsPanel)
|
|||
|
||||
/*
|
||||
* If there are any live registers, LEDs, etc, to display, this will provide a count.
|
||||
*
|
||||
* TODO: Add some UI for fDisplayLiveRegs (either an XML property, or a UI checkbox, or both).
|
||||
*/
|
||||
this.cLiveRegs = 0;
|
||||
this.fDisplayLiveRegs = true;
|
||||
this.fLampTest = false;
|
||||
this.fExamine = this.fDeposit = false;
|
||||
|
||||
/*
|
||||
* regCNSW contains the Console (Front Panel) Switch Register, which is also available as a
|
||||
* regSwitches contains the Console (Front Panel) Switch Register, which is also available as a
|
||||
* read-only register at 177570 (but only the low 16 bits).
|
||||
*
|
||||
* regAddr is an internal register containing the contents of the Front Panel's ADDRESS display,
|
||||
* and regData corresponds to the DATA display. They are updated by setAddr() and setData(),
|
||||
* which in turn take care of calling setLEDArray().
|
||||
*/
|
||||
this.regCNSW = 0;
|
||||
this.regSwitches = 0;
|
||||
this.regAddr = this.regData = 0;
|
||||
this.regMisc = 0x14;
|
||||
|
||||
/*
|
||||
* The panel hardware has the following additional (supported) state; note that there are several
|
||||
* settings on a real Front Panel that we don't support (eg, stepping one cycle vs. one instruction).
|
||||
*
|
||||
* While my initial intent is to eventually support all the ADDRSEL switch settings, I probably
|
||||
* won't bother with any DATASEL switch settings; instead, I will automatically display the data
|
||||
* register (regData) [the equivalent of selecting 'DISPLAY REGISTER'] except when data is being
|
||||
* examined or deposited [the equivalent of selecting 'DATA PATHS'].
|
||||
*/
|
||||
this.fLampTest = false; // lamp (LED) test in progress
|
||||
this.fExamine = false; // true if the previously pressed switch was the 'EXAM' switch
|
||||
this.fDeposit = false; // true if the previously pressed switch was the 'DEP' switch
|
||||
this.nAddrSel = PanelPDP11.ADDRSEL.CONS_PHY;
|
||||
|
||||
/*
|
||||
* Every LED has a simple numeric value, assigned when setBinding() is called:
|
||||
*
|
||||
* 0 if off, 1 if on
|
||||
* zero if "off", non-zero if "on"
|
||||
*
|
||||
* initBus() will call displayLEDs() to ensure that every LED is set to its initial value.
|
||||
*/
|
||||
|
|
@ -122,6 +132,17 @@ function PanelPDP11(parmsPanel)
|
|||
|
||||
Component.subclass(PanelPDP11);
|
||||
|
||||
PanelPDP11.ADDRSEL = {
|
||||
KERNEL_I: 0, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
KERNEL_D: 1, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
SUPER_I: 2, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
SUPER_D: 3, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
USER_I: 4, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
USER_D: 5, // use a 16-bit virtual address where bits 16 to 21 are always OFF
|
||||
PROG_PHY: 6, // display the 22-bit physical address of the current bus cycle generated by the MMU
|
||||
CONS_PHY: 7 // use a 22-bit physical address to perform console operations (e.g., LOAD ADRS, EXAM, & DEP)
|
||||
};
|
||||
|
||||
/*
|
||||
* To get the current state of a switch; eg::
|
||||
*
|
||||
|
|
@ -132,6 +153,7 @@ Component.subclass(PanelPDP11);
|
|||
* "step" behavior when pressed more than once in a row). Ditto for the LED table.
|
||||
*/
|
||||
PanelPDP11.SWITCH = {
|
||||
S0: 'S0',
|
||||
DEP: 'DEP',
|
||||
ENABLE: 'ENABLE',
|
||||
EXAM: 'EXAM',
|
||||
|
|
@ -144,6 +166,28 @@ PanelPDP11.LED = {
|
|||
B22: 'B22'
|
||||
};
|
||||
|
||||
/**
|
||||
* getSW()
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @return {number}
|
||||
*/
|
||||
PanelPDP11.prototype.getSW = function()
|
||||
{
|
||||
return this.regSwitches;
|
||||
};
|
||||
|
||||
/**
|
||||
* setSW(value)
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @param {number} value
|
||||
*/
|
||||
PanelPDP11.prototype.setSW = function(value)
|
||||
{
|
||||
this.setSwitches(value);
|
||||
};
|
||||
|
||||
/**
|
||||
* getSwitch(name)
|
||||
*
|
||||
|
|
@ -163,7 +207,6 @@ PanelPDP11.prototype.getSwitch = function(name)
|
|||
*/
|
||||
PanelPDP11.prototype.reset = function()
|
||||
{
|
||||
this.regMisc = (this.regMisc & ~0x77) | 0x14; // kernel 16 bit
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
@ -639,7 +682,15 @@ PanelPDP11.prototype.processDeposit = function(value, index)
|
|||
if (this.fDeposit) {
|
||||
this.setAddr(this.regAddr + 2);
|
||||
}
|
||||
this.bus.setWordDirect(this.regAddr, this.setData(this.regCNSW));
|
||||
var w = this.setData(this.regSwitches);
|
||||
if (this.nAddrSel == PanelPDP11.ADDRSEL.CONS_PHY) {
|
||||
this.bus.setWordDirect(this.regAddr, w);
|
||||
} else {
|
||||
/*
|
||||
* TODO: This code is obviously incomplete, since it doesn't take into account the precise ADDRSEL mode.
|
||||
*/
|
||||
this.cpu.setWordDirect(this.regAddr, w);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -656,7 +707,16 @@ PanelPDP11.prototype.processExamine = function(value, index)
|
|||
if (this.fExamine) {
|
||||
this.setAddr(this.regAddr + 2);
|
||||
}
|
||||
this.setData(this.bus.getWordDirect(this.regAddr));
|
||||
var w;
|
||||
if (this.nAddrSel == PanelPDP11.ADDRSEL.CONS_PHY) {
|
||||
w = this.bus.getWordDirect(this.regAddr);
|
||||
} else {
|
||||
/*
|
||||
* TODO: This code is obviously incomplete, since it doesn't take into account the precise ADDRSEL mode.
|
||||
*/
|
||||
w = this.cpu.getWordDirect(this.regAddr);
|
||||
}
|
||||
this.setData(w);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -670,7 +730,7 @@ PanelPDP11.prototype.processExamine = function(value, index)
|
|||
PanelPDP11.prototype.processLoadAddr = function(value, index)
|
||||
{
|
||||
if (!value && !this.cpu.isRunning()) {
|
||||
this.setAddr(this.regCNSW);
|
||||
this.setAddr(this.regSwitches);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -696,9 +756,9 @@ PanelPDP11.prototype.processLampTest = function(value, index)
|
|||
PanelPDP11.prototype.processSwitchReg = function(value, index)
|
||||
{
|
||||
if (value) {
|
||||
this.regCNSW |= 1 << index;
|
||||
this.regSwitches |= 1 << index;
|
||||
} else {
|
||||
this.regCNSW &= ~(1 << index);
|
||||
this.regSwitches &= ~(1 << index);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -746,18 +806,46 @@ PanelPDP11.prototype.setLED = function(sBinding, value)
|
|||
};
|
||||
|
||||
/**
|
||||
* setLEDArray(sPrefix, data, nLEDs)
|
||||
* setLEDArray(sPrefix, value, nLEDs)
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @param {string} sPrefix
|
||||
* @param {number} data
|
||||
* @param {number} value
|
||||
* @param {number} nLEDs
|
||||
*/
|
||||
PanelPDP11.prototype.setLEDArray = function(sPrefix, data, nLEDs)
|
||||
PanelPDP11.prototype.setLEDArray = function(sPrefix, value, nLEDs)
|
||||
{
|
||||
for (var i = 0; i < nLEDs; i++) {
|
||||
var sBinding = sPrefix + i;
|
||||
this.setLED(sBinding, data & (1 << i));
|
||||
this.setLED(sBinding, value & (1 << i));
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* hasSwitches(value)
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @return {boolean}
|
||||
*/
|
||||
PanelPDP11.prototype.hasSwitches = function()
|
||||
{
|
||||
return this.bindings[PanelPDP11.SWITCH.S0] !== undefined;
|
||||
};
|
||||
|
||||
/**
|
||||
* setSwitches(value)
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @param {number} value
|
||||
*/
|
||||
PanelPDP11.prototype.setSwitches = function(value)
|
||||
{
|
||||
if (this.hasSwitches()) {
|
||||
this.regSwitches = value;
|
||||
for (var i = 0; i < 22; i++) {
|
||||
this.switches['S'+i][0] = (value & (1 << i))? 1 : 0;
|
||||
}
|
||||
this.displaySwitches();
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -817,7 +905,7 @@ PanelPDP11.prototype.updateStatus = function(fForce)
|
|||
* readCNSW(addr)
|
||||
*
|
||||
* If addr is set, then this a normal read, so we should return normal results (ie, switches);
|
||||
* if addr is NOT set, then this is a read-before-write, so we must return the value being updated (ie, data).
|
||||
* if addr is NOT set, then this is a read-before-write, so we must return the value being updated.
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @param {number} addr (eg, PDP11.UNIBUS.CNSW or 177570)
|
||||
|
|
@ -825,19 +913,19 @@ PanelPDP11.prototype.updateStatus = function(fForce)
|
|||
*/
|
||||
PanelPDP11.prototype.readCNSW = function(addr)
|
||||
{
|
||||
return (addr? this.regCNSW : this.regData) & 0xffff;
|
||||
return (addr? this.regSwitches : this.regData) & 0xffff;
|
||||
};
|
||||
|
||||
/**
|
||||
* writeCNSW(data, addr)
|
||||
* writeCNSW(value, addr)
|
||||
*
|
||||
* @this {PanelPDP11}
|
||||
* @param {number} data
|
||||
* @param {number} value
|
||||
* @param {number} addr (eg, PDP11.UNIBUS.CNSW or 177570)
|
||||
*/
|
||||
PanelPDP11.prototype.writeCNSW = function(data, addr)
|
||||
PanelPDP11.prototype.writeCNSW = function(value, addr)
|
||||
{
|
||||
this.regData = data;
|
||||
this.regData = value;
|
||||
};
|
||||
|
||||
PanelPDP11.UNIBUS_IOTABLE = {
|
||||
|
|
|
|||
Loading…
Reference in a new issue