From 3e2b825bef43127568bc0b7eaab43ceb2c5d8076 Mon Sep 17 00:00:00 2001 From: Jeff Date: Mon, 13 Mar 2017 17:02:26 -0700 Subject: [PATCH] Fixed MACRO-10 processing of literals (requires internal labels that don't conflict with MACRO-10 labels) --- apps/pdp10/tapes/diags/klad/dakad/DAKAD.MAC | 21 +++++++------- .../machine/ka10/test/debugger/machine.xml | 2 +- modules/pdp10/lib/debugger.js | 29 +++++++++---------- modules/pdp10/lib/macro10.js | 22 ++++++++------ 4 files changed, 39 insertions(+), 35 deletions(-) diff --git a/apps/pdp10/tapes/diags/klad/dakad/DAKAD.MAC b/apps/pdp10/tapes/diags/klad/dakad/DAKAD.MAC index 07414bb0d..b85eaaa10 100644 --- a/apps/pdp10/tapes/diags/klad/dakad/DAKAD.MAC +++ b/apps/pdp10/tapes/diags/klad/dakad/DAKAD.MAC @@ -35,16 +35,17 @@ DEFINE SFLAG (A)< JRST 2,.+1(1) ;SET A FLAG> SUBTTL DIAGNOSTIC SECTION -START: SETZM USER# ;CLEAR USER CONTROL WORD - JSP 0,.+1 ;GET FLAGS - TLNE USERF ;IN USER MODE? - SETOM USER ;YES, SET USER CONTROL WORD - SKIPN MONFLG ;SPECIAL USER MODE? - SETZM USER ;YES, CLEAR USER CONTROL WORD - SKIPN USER - JRST C00 - SKIPL MONCTL - TTCALL 3,PGMNAM ;MENTION OUR NAME +START: +; SETZM USER# ;CLEAR USER CONTROL WORD +; JSP 0,.+1 ;GET FLAGS +; TLNE USERF ;IN USER MODE? +; SETOM USER ;YES, SET USER CONTROL WORD +; SKIPN MONFLG ;SPECIAL USER MODE? +; SETZM USER ;YES, CLEAR USER CONTROL WORD +; SKIPN USER +; JRST C00 +; SKIPL MONCTL +; TTCALL 3,PGMNAM ;MENTION OUR NAME JRST STARTA PGMNAM: ASCIZ/ diff --git a/devices/pdp10/machine/ka10/test/debugger/machine.xml b/devices/pdp10/machine/ka10/test/debugger/machine.xml index d5d6634a6..e8e85b514 100644 --- a/devices/pdp10/machine/ka10/test/debugger/machine.xml +++ b/devices/pdp10/machine/ka10/test/debugger/machine.xml @@ -8,5 +8,5 @@ - + diff --git a/modules/pdp10/lib/debugger.js b/modules/pdp10/lib/debugger.js index f1c3920e1..900d5888c 100644 --- a/modules/pdp10/lib/debugger.js +++ b/modules/pdp10/lib/debugger.js @@ -1703,12 +1703,16 @@ class DebuggerPDP10 extends Debugger { break; } sOperand = match[2]; - if (i) { + if (i || aOperands.length == 1) { /* * If this is NOT the first operand, then replace all periods NOT preceded * by a digit with the current address. */ - sOperand = sOperand.replace(/(^|[^0-9])\./g, "$1" + this.toStrOffset(addr)); + if (!sOperand) { + sOperand = "0"; + } else { + sOperand = sOperand.replace(/(^|[^0-9])\./g, "$1" + this.toStrOffset(addr)); + } } var operand = this.parseExpression(sOperand); if (operand == undefined) { @@ -1718,17 +1722,15 @@ class DebuggerPDP10 extends Debugger { if (!i && aOperands.length > 1) { if (opMask == PDP10.OPCODE.OPIO) { if (operand < 0 || operand > PDP10.OPCODE.IO_MASK) { - this.println("device code out of range: " + sOperand); - opCode = -1; - break; + operand &= PDP10.OPCODE.IO_MASK; + this.println("device code (" + sOperand + ") truncated to " + this.toStrBase(operand)); } opCode += (operand * PDP10.OPCODE.IO_SCALE); } else { if (operand < 0 || operand > PDP10.OPCODE.A_MASK) { - this.println("accumulator address out of range: " + sOperand); - opCode = -1; - break; + operand &= PDP10.OPCODE.A_MASK; + this.println("accumulator (" + sOperand + ") truncated to " + this.toStrBase(operand)); } opCode += (operand << PDP10.OPCODE.A_SHIFT); } @@ -1748,15 +1750,12 @@ class DebuggerPDP10 extends Debugger { break; } if (operand < 0 || operand > PDP10.OPCODE.X_MASK) { - this.println("memory index out of range: " + sOperand); - opCode = -1; - break; + operand &= PDP10.OPCODE.X_MASK; + this.println("index (" + sOperand + ") truncated to " + this.toStrBase(operand)); } opCode += operand << PDP10.OPCODE.X_SHIFT; } - if (match[1]) { - opCode += PDP10.OPCODE.I_BIT; - } + if (match[1]) opCode += PDP10.OPCODE.I_BIT; } } // @@ -2552,7 +2551,7 @@ class DebuggerPDP10 extends Debugger { return; } - if (sOpcode.indexOf(':') >= 0) { + if (sOpcode[0] == '/' || sOpcode.indexOf(':') >= 0) { var dbg = this; if (this.macro10) { dbg.println("assembly already in progress"); diff --git a/modules/pdp10/lib/macro10.js b/modules/pdp10/lib/macro10.js index e358bc405..850caef2f 100644 --- a/modules/pdp10/lib/macro10.js +++ b/modules/pdp10/lib/macro10.js @@ -123,6 +123,9 @@ class Macro10 { * auto-generated label based on the current line number), but they are never immediately invoked; * instead, after we've finished processing all the lines in the original input file, we run through * all the LITERAL entries in the Macros table and process the associated statement(s). + * + * REPEAT and LITERAL blocks are assigned internal labels, using a leading underscore ('_') so that + * they don't conflict with normal MACRO-10 labels. */ /** @@ -222,9 +225,10 @@ class Macro10 { } for (i = 0; i < this.aLiterals.length; i++) { - var macro = this.tblMacros[this.aLiterals[i]]; + var name = this.aLiterals[i]; + var macro = this.tblMacros[name]; if (!macro) { - this.error("missing definition for literal: " + this.aLiterals[i]); + this.error("missing definition for literal: " + name); continue; } this.parseText(macro.sText); @@ -301,7 +305,7 @@ class Macro10 { sLine = this.addASCII(sLine); } - var reLine = /\s*([A-Z$%.][0-9A-Z$%.]*[:=]|)\s*([A-Z$%.][0-9A-Z$%.]*|)\s*([^;]+|)\s*(;?.*)/i; + var reLine = /\s*([A-Z$%._][0-9A-Z$%.]*[:=]|)\s*([A-Z$%.][0-9A-Z$%.]*|)\s*([^;]+|)\s*(;?.*)/i; var match = sLine.match(reLine); if (!match || match[4] && match[4].slice(0, 1) != ';') { this.error("failed to parse line: " + sLine); @@ -420,7 +424,7 @@ class Macro10 { return true; } - if (name[0] != '@') return false; + if (name[0] != '_') return false; switch(name.substr(1)) { case Macro10.PSEUDO_OP.IFE: @@ -628,7 +632,7 @@ class Macro10 { var match, sReserved = null; if (match = sOperands.match(/([A-Z$%.][0-9A-Z$%.]*)#/i)) { var sLabel = match[1]; - var name = '@' + sLabel; + var name = '_' + sLabel; this.tblMacros[name] = {name: name, nOperand: 0, aParms: [], aDefaults: [], sText: sLabel + ": 0"}; this.aLiterals.push(name); sReserved = match[0]; @@ -726,7 +730,7 @@ class Macro10 { * REPEAT block instead. * * REPEAT blocks piggy-back on this code because they're essentially anonymous immediately-invoked macros; - * we use an illegal MACRO-10 symbol ('@REPEAT') to name the anonymous macro while it's being defined, and the + * we use an illegal MACRO-10 symbol ('_REPEAT') to name the anonymous macro while it's being defined, and the * macro's nOperand field will contain the repeat count (-1 for regular macros). * * The piggy-backing continues with other pseudo-ops like IFE, which again contain an anonymous block of text @@ -765,9 +769,9 @@ class Macro10 { else if (sOperator == Macro10.PSEUDO_OP.LITERAL) { this.chMacroOpen = '['; this.chMacroClose = ']'; - name = '@' + Str.toDec(this.nLocation, 5); + name = '_' + Str.toDec(this.nLocation, 5); this.aLiterals.push(name); - match = [sOperands[0], sOperands.substr(1)]; + match = [sOperands[0], name + ": " + sOperands.substr(1)]; aParms = []; nOperand = this.nLine; iBracket = 0; @@ -781,7 +785,7 @@ class Macro10 { sOperands = sOperands.substr(sOperand.length + 1); sOperand = sOperand.trim(); match = sOperands.match(/\s*(<|)(.*)/i); - name = '@' + sOperator; + name = '_' + sOperator; aParms = []; nOperand = this.parseExpression(sOperand) || 0; iBracket = 1;