Added Debugger "int" command to manually request interrupts

This commit is contained in:
Jeff Parsons 2016-08-06 13:39:46 -07:00
commit 276c36334e
11 changed files with 1328 additions and 44 deletions

View file

@ -631,7 +631,7 @@ FileDump.prototype.loadMap = function(sMapFile, done)
done(new Error("unrecognized line (" + s + ") in MAP file: " + sMapName), null);
return;
}
sMapData = JSON.stringify(aSymbols);
sMapData = obj.fJSONComments? JSON.stringify(aSymbols, null, 2) : JSON.stringify(aSymbols);
if (sMapData) {
obj.json = '{' + obj.json + ',"symbols":' + sMapData + '}';
}

View file

@ -205,7 +205,8 @@ ChipSet.VT100 = {
ERASE: 0x5,
READ: 0x6,
STANDBY: 0x7
}
},
WORDMASK: 0x3fff // NVR words are 14-bit
},
DC012: { // generates scan counts for the Video Processor
PORT: 0xA2, // write-only
@ -678,11 +679,11 @@ ChipSet.prototype.getNVRAddr = function()
};
/**
* advanceNVR()
* doNVRCommand()
*/
ChipSet.prototype.advanceNVR = function()
ChipSet.prototype.doNVRCommand = function()
{
var addr;
var addr, data;
var bit = this.bNVRLatch & 0x1;
var bCmd = (this.bNVRLatch >> 1) & 0x7;
@ -696,7 +697,8 @@ ChipSet.prototype.advanceNVR = function()
case ChipSet.VT100.NVR.CMD.ERASE:
addr = this.getNVRAddr();
this.aNVRWords[addr] = 0x3fff;
this.aNVRWords[addr] = ChipSet.VT100.NVR.WORDMASK;
this.printMessage("doNVRCommand(): erase data at addr " + str.toHexWord(addr));
break;
case ChipSet.VT100.NVR.CMD.ACCEPT_DATA:
@ -705,17 +707,32 @@ ChipSet.prototype.advanceNVR = function()
case ChipSet.VT100.NVR.CMD.WRITE:
addr = this.getNVRAddr();
this.aNVRWords[addr] = this.wNVRData & 0x3fff;
data = this.wNVRData & ChipSet.VT100.NVR.WORDMASK;
this.aNVRWords[addr] = data;
this.printMessage("doNVRCommand(): write data " + str.toHexWord(data) + " to addr " + str.toHexWord(addr));
break;
case ChipSet.VT100.NVR.CMD.READ:
addr = this.getNVRAddr();
this.wNVRData = this.aNVRWords[addr];
data = this.aNVRWords[addr];
/*
* Since we don't explicitly initialize aNVRWords[], we pretend any uninitialized words contains WORDMASK.
*/
if (data == null) data = ChipSet.VT100.NVR.WORDMASK;
this.wNVRData = data;
this.printMessage("doNVRCommand(): read data " + str.toHexWord(data) + " from addr " + str.toHexWord(addr));
break;
case ChipSet.VT100.NVR.CMD.SHIFT_OUT:
this.bNVROut = this.wNVRData & 0x2000;
this.wNVRData <<= 1;
/*
* Since WORDMASK is 0x3fff, this will mask the shifted data with 0x4000, which is the bit we want to isolate.
*/
this.bNVROut = this.wNVRData & (ChipSet.VT100.NVR.WORDMASK + 1);
break;
default:
this.printMessage("doNVRCommand(): unrecognized command " + str.toHexByte(bCmd));
break;
}
};
@ -738,7 +755,7 @@ ChipSet.prototype.inVT100FlagsBuffer = function(port, addrFrom)
if (this.getVT100LBA(7)) {
b |= ChipSet.VT100.FLAGS_BUFFER.NVR_CLK;
if (b != this.bFlagsBuffer) {
this.advanceNVR();
this.doNVRCommand();
}
}
b &= ~ChipSet.VT100.FLAGS_BUFFER.NVR_DATA;

View file

@ -230,30 +230,31 @@ if (DEBUGGER) {
*/
Debugger.COMMANDS = {
'?': "help/print",
'a [#]': "assemble", // TODO: Implement this command someday
'b [#]': "breakpoint", // multiple variations (use b? to list them)
'c': "clear output",
'd [#]': "dump memory", // additional syntax: d [#] [l#], where l# is a number of bytes to dump
'e [#]': "edit memory",
'f': "frequencies",
'g [#]': "go [to #]",
'h': "halt",
'i [#]': "input port #",
'if': "eval expression",
'k': "stack trace",
"ln": "list nearest symbol(s)",
'm': "messages",
'o [#]': "output port #",
'p': "step over", // other variations: pr (step and dump registers)
'print': "print expression",
'r': "dump/set registers",
'reset': "reset machine",
's': "set options",
't [#]': "trace", // other variations: tr (trace and dump registers)
'u [#]': "unassemble",
'v': "print version",
'var': "assign variable"
'?': "help/print",
'a [#]': "assemble", // TODO: Implement this command someday
'b [#]': "breakpoint", // multiple variations (use b? to list them)
'c': "clear output",
'd [#]': "dump memory", // additional syntax: d [#] [l#], where l# is a number of bytes to dump
'e [#]': "edit memory",
'f': "frequencies",
'g [#]': "go [to #]",
'h': "halt",
'i [#]': "input port #",
'if': "eval expression",
'int [#]': "request interrupt",
'k': "stack trace",
"ln": "list nearest symbol(s)",
'm': "messages",
'o [#]': "output port #",
'p': "step over", // other variations: pr (step and dump registers)
'print': "print expression",
'r': "dump/set registers",
'reset': "reset machine",
's': "set options",
't [#]': "trace", // other variations: tr (trace and dump registers)
'u [#]': "unassemble",
'v': "print version",
'var': "assign variable"
};
Debugger.STYLE_8080 = 8080;
@ -3288,7 +3289,7 @@ if (DEBUGGER) {
{
var s = "commands:";
for (var sCommand in Debugger.COMMANDS) {
s += '\n' + str.pad(sCommand, 7) + Debugger.COMMANDS[sCommand];
s += '\n' + str.pad(sCommand, 9) + Debugger.COMMANDS[sCommand];
}
if (!this.checksEnabled()) s += "\nnote: frequency/history disabled if no exec breakpoints";
this.println(s);
@ -3799,6 +3800,26 @@ if (DEBUGGER) {
}
};
/**
* doInt(sLevel)
*
* @this {Debugger}
* @param {string} sLevel
* @return {boolean} true if success, false if error
*/
Debugger.prototype.doInt = function(sLevel)
{
if (!this.cpu.getIF()) {
this.println("interrupts disabled (use rif=1 to enable)");
return false;
}
var nLevel = this.parseExpression(sLevel);
if (nLevel == null) return false;
this.println("requesting interrupt level " + nLevel);
this.cpu.requestINTR(nLevel);
return true;
};
/**
* doVar(sCmd)
*
@ -4686,6 +4707,12 @@ if (DEBUGGER) {
}
break;
}
if (asArgs[0] == "int") {
if (!this.doInt(asArgs[1])) {
result = false;
}
break;
}
this.doInput(asArgs[1]);
break;
case 'k':