Added another example of an I/O address handler (XCSR)
This commit is contained in:
parent
da617d454d
commit
a451bbc5bc
6 changed files with 391 additions and 334 deletions
|
|
@ -591,7 +591,7 @@ PDP11.opCLR = function(opCode)
|
|||
*/
|
||||
PDP11.opCLRB = function(opCode)
|
||||
{
|
||||
this.updateNZCFlags(this.writeByteByMode(opCode, 0, PDP11.WRITE.ZERO));
|
||||
this.updateNZCFlags(this.writeByteByMode(opCode, 0));
|
||||
this.nStepCycles -= 1;
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -205,9 +205,9 @@ CPUStatePDP11.prototype.resetRegs = function()
|
|||
* Define getAddr(), readWord(), etc, handlers appropriate for the current MMU mode.
|
||||
*
|
||||
* The initial goal is to eliminate unnecessary calls to mapVirtualToPhysical(); for example,
|
||||
* readWordByVirtual() always does this:
|
||||
* readWordFromVirtual() always does this:
|
||||
*
|
||||
* return this.readWordByPhysical(this.mapVirtualToPhysical(virtualAddress, PDP11.ACCESS.READ));
|
||||
* return this.readWordFromPhysical(this.mapVirtualToPhysical(virtualAddress, PDP11.ACCESS.READ));
|
||||
*
|
||||
* and getAddrVirtual() -- formerly getAddrByMode() -- always does this:
|
||||
*
|
||||
|
|
@ -222,11 +222,11 @@ CPUStatePDP11.prototype.initMemoryAccess = function()
|
|||
if (this.mmuEnable) {
|
||||
this.addrDSpace = PDP11.ACCESS.DSPACE;
|
||||
this.getAddr = this.getAddrVirtual;
|
||||
this.readWord = this.readWordByVirtual;
|
||||
this.readWord = this.readWordFromVirtual;
|
||||
} else {
|
||||
this.addrDSpace = 0;
|
||||
this.getAddr = this.getAddrPhysical;
|
||||
this.readWord = this.readWordByPhysical;
|
||||
this.readWord = this.readWordFromPhysical;
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -594,7 +594,7 @@ CPUStatePDP11.prototype.interrupt = function(delay, priority, vector, callback)
|
|||
}
|
||||
this.interruptQueue.splice(i + 1, 0, {
|
||||
"delay": delay,
|
||||
"priority": priority & 0xe0,
|
||||
"priority": (priority << 5) & 0xe0,
|
||||
"vector": vector,
|
||||
"callback": callback
|
||||
});
|
||||
|
|
@ -771,8 +771,8 @@ CPUStatePDP11.prototype.trap = function(vector, reason)
|
|||
this.MMR2 = vector;
|
||||
}
|
||||
this.mmuMode = 0; // read from kernel D space
|
||||
if ((newPC = this.readWordByVirtual(vector | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((newPSW = this.readWordByVirtual(((vector + 2) & 0xffff) | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((newPC = this.readWordFromVirtual(vector | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((newPSW = this.readWordFromVirtual(((vector + 2) & 0xffff) | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
this.setPSW((newPSW & 0xcfff) | ((this.trapPSW >> 2) & 0x3000)); // set new this.PSW with previous mode
|
||||
if (doubleTrap) {
|
||||
this.regCPUErr |= PDP11.CPUERR.RED;
|
||||
|
|
@ -964,13 +964,13 @@ CPUStatePDP11.prototype.mapVirtualToPhysical = function(virtualAddress, accessFl
|
|||
};
|
||||
|
||||
/**
|
||||
* readWordByPhysical(physicalAddress) [formerly readWordByAddr]
|
||||
* readWordFromPhysical(physicalAddress) [formerly readWordByAddr]
|
||||
*
|
||||
* @this {CPUStatePDP11}
|
||||
* @param {number} physicalAddress
|
||||
* @return {number}
|
||||
*/
|
||||
CPUStatePDP11.prototype.readWordByPhysical = function(physicalAddress)
|
||||
CPUStatePDP11.prototype.readWordFromPhysical = function(physicalAddress)
|
||||
{
|
||||
if (physicalAddress >= BusPDP11.MAX_ADDRESS) {
|
||||
return this.regsGen[physicalAddress - BusPDP11.MAX_ADDRESS];
|
||||
|
|
@ -987,25 +987,25 @@ CPUStatePDP11.prototype.readWordByPhysical = function(physicalAddress)
|
|||
};
|
||||
|
||||
/**
|
||||
* readWordByVirtual(virtualAddress)
|
||||
* readWordFromVirtual(virtualAddress)
|
||||
*
|
||||
* @this {CPUStatePDP11}
|
||||
* @param {number} virtualAddress (input address is 17 bit (I&D))
|
||||
*/
|
||||
CPUStatePDP11.prototype.readWordByVirtual = function(virtualAddress)
|
||||
CPUStatePDP11.prototype.readWordFromVirtual = function(virtualAddress)
|
||||
{
|
||||
return this.readWordByPhysical(this.mapVirtualToPhysical(virtualAddress, PDP11.ACCESS.READ));
|
||||
return this.readWordFromPhysical(this.mapVirtualToPhysical(virtualAddress, PDP11.ACCESS.READ));
|
||||
};
|
||||
|
||||
/**
|
||||
* writeWordByPhysical(physicalAddress, data) [formerly writeWordByAddr]
|
||||
* writeWordToPhysical(physicalAddress, data) [formerly writeWordByAddr]
|
||||
*
|
||||
* @this {CPUStatePDP11}
|
||||
* @param {number} physicalAddress
|
||||
* @param {number} data
|
||||
* @return {number}
|
||||
*/
|
||||
CPUStatePDP11.prototype.writeWordByPhysical = function(physicalAddress, data)
|
||||
CPUStatePDP11.prototype.writeWordToPhysical = function(physicalAddress, data)
|
||||
{
|
||||
data &= 0xffff;
|
||||
if (physicalAddress >= BusPDP11.MAX_ADDRESS) {
|
||||
|
|
@ -1024,13 +1024,13 @@ CPUStatePDP11.prototype.writeWordByPhysical = function(physicalAddress, data)
|
|||
};
|
||||
|
||||
/**
|
||||
* readByteByPhysical(physicalAddress) [formerly readByteByAddr]
|
||||
* readByteFromPhysical(physicalAddress) [formerly readByteByAddr]
|
||||
*
|
||||
* @this {CPUStatePDP11}
|
||||
* @param {number} physicalAddress
|
||||
* @return {number}
|
||||
*/
|
||||
CPUStatePDP11.prototype.readByteByPhysical = function(physicalAddress)
|
||||
CPUStatePDP11.prototype.readByteFromPhysical = function(physicalAddress)
|
||||
{
|
||||
var result;
|
||||
if (physicalAddress >= BusPDP11.MAX_ADDRESS) {
|
||||
|
|
@ -1048,14 +1048,14 @@ CPUStatePDP11.prototype.readByteByPhysical = function(physicalAddress)
|
|||
};
|
||||
|
||||
/**
|
||||
* writeByteByPhysical(physicalAddress, data) [formerly writeByteByAddr]
|
||||
* writeByteToPhysical(physicalAddress, data) [formerly writeByteByAddr]
|
||||
*
|
||||
* @this {CPUStatePDP11}
|
||||
* @param {number} physicalAddress
|
||||
* @param {number} data
|
||||
* @return {number}
|
||||
*/
|
||||
CPUStatePDP11.prototype.writeByteByPhysical = function(physicalAddress, data)
|
||||
CPUStatePDP11.prototype.writeByteToPhysical = function(physicalAddress, data)
|
||||
{
|
||||
data &= 0xff;
|
||||
if (physicalAddress >= BusPDP11.MAX_ADDRESS) {
|
||||
|
|
@ -1081,7 +1081,7 @@ CPUStatePDP11.prototype.writeByteByPhysical = function(physicalAddress, data)
|
|||
*/
|
||||
CPUStatePDP11.prototype.popWord = function()
|
||||
{
|
||||
var result = this.readWordByVirtual(this.regsGen[6] | PDP11.ACCESS.DSPACE);
|
||||
var result = this.readWordFromVirtual(this.regsGen[6] | PDP11.ACCESS.DSPACE);
|
||||
if (result >= 0) {
|
||||
this.regsGen[6] = (this.regsGen[6] + 2) & 0xffff;
|
||||
}
|
||||
|
|
@ -1113,7 +1113,7 @@ CPUStatePDP11.prototype.pushWord = function(data)
|
|||
}
|
||||
}
|
||||
if ((physicalAddress = this.mapVirtualToPhysical(virtualAddress | PDP11.ACCESS.DSPACE, PDP11.ACCESS.WRITE)) >= 0) {
|
||||
return this.writeWordByPhysical(physicalAddress, data);
|
||||
return this.writeWordToPhysical(physicalAddress, data);
|
||||
}
|
||||
return physicalAddress;
|
||||
};
|
||||
|
|
@ -1185,7 +1185,7 @@ CPUStatePDP11.prototype.getVirtualByMode = function(addressMode, accessFlags)
|
|||
stepSize = 2;
|
||||
virtualAddress = this.regsGen[reg];
|
||||
if (reg !== 7) virtualAddress |= this.addrDSpace;
|
||||
if ((virtualAddress = this.readWordByVirtual(virtualAddress)) < 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(virtualAddress)) < 0) {
|
||||
return virtualAddress;
|
||||
}
|
||||
// if (reg === 7) LOG_ADDRESS(virtualAddress); // @#n not operational
|
||||
|
|
@ -1203,13 +1203,13 @@ CPUStatePDP11.prototype.getVirtualByMode = function(addressMode, accessFlags)
|
|||
stepSize = -2;
|
||||
virtualAddress = (this.regsGen[reg] - 2) & 0xffff;
|
||||
if (reg !== 7) virtualAddress |= this.addrDSpace;
|
||||
if ((virtualAddress = this.readWordByVirtual(virtualAddress)) < 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(virtualAddress)) < 0) {
|
||||
return virtualAddress;
|
||||
}
|
||||
virtualAddress |= this.addrDSpace;
|
||||
break;
|
||||
case 6: // Mode 6: d(R)
|
||||
if ((virtualAddress = this.readWordByVirtual(this.regsGen[7])) < 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(this.regsGen[7])) < 0) {
|
||||
return virtualAddress;
|
||||
}
|
||||
this.regsGen[7] = (this.regsGen[7] + 2) & 0xffff;
|
||||
|
|
@ -1222,7 +1222,7 @@ CPUStatePDP11.prototype.getVirtualByMode = function(addressMode, accessFlags)
|
|||
}
|
||||
return virtualAddress | this.addrDSpace;
|
||||
case 7: // Mode 7: @d(R)
|
||||
if ((virtualAddress = this.readWordByVirtual(this.regsGen[7])) < 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(this.regsGen[7])) < 0) {
|
||||
return virtualAddress;
|
||||
}
|
||||
this.regsGen[7] = (this.regsGen[7] + 2) & 0xffff;
|
||||
|
|
@ -1233,7 +1233,7 @@ CPUStatePDP11.prototype.getVirtualByMode = function(addressMode, accessFlags)
|
|||
virtualAddress = (virtualAddress + this.regsGen[reg]) & 0xffff;
|
||||
//LOG_ADDRESS(virtualAddress);
|
||||
}
|
||||
if ((virtualAddress = this.readWordByVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) < 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) < 0) {
|
||||
return virtualAddress;
|
||||
}
|
||||
return virtualAddress | this.addrDSpace;
|
||||
|
|
@ -1306,7 +1306,7 @@ CPUStatePDP11.prototype.readWordByMode = function(addressMode)
|
|||
result = this.regsGen[addressMode & PDP11.OPREG.MASK];
|
||||
} else {
|
||||
/*
|
||||
* NOTE: This used to call readWordByPhysical(), after calling getAddrVirtual(), but the latter is
|
||||
* NOTE: This used to call readWordFromPhysical(), after calling getAddrVirtual(), but the latter is
|
||||
* just a wrapper around mapVirtualToPhysical() on the result from getVirtualByMode(), so now we call
|
||||
* getVirtualByMode() directly, knowing that the current readWord() will call the correct function.
|
||||
*/
|
||||
|
|
@ -1328,7 +1328,7 @@ CPUStatePDP11.prototype.readByteByMode = function(addressMode)
|
|||
if (!(addressMode & 0x38)) {
|
||||
result = this.regsGen[addressMode & 7] & 0xff;
|
||||
} else {
|
||||
result = this.readByteByPhysical(this.getAddr(addressMode, PDP11.ACCESS.READ_BYTE));
|
||||
result = this.readByteFromPhysical(this.getAddr(addressMode, PDP11.ACCESS.READ_BYTE));
|
||||
}
|
||||
return result;
|
||||
};
|
||||
|
|
@ -1352,7 +1352,7 @@ CPUStatePDP11.prototype.updateWordByMode = function(addressMode, src, fnOp)
|
|||
this.regsGen[reg] = (data = fnOp.call(this, src, this.regsGen[reg]) & 0xffff);
|
||||
} else {
|
||||
var addr = this.getAddr(addressMode, PDP11.ACCESS.UPDATE);
|
||||
this.writeWordByPhysical(addr, (data = fnOp.call(this, src, this.readWordByPhysical(addr))));
|
||||
this.writeWordToPhysical(addr, (data = fnOp.call(this, src, this.readWordFromPhysical(addr))));
|
||||
}
|
||||
return data;
|
||||
};
|
||||
|
|
@ -1376,7 +1376,7 @@ CPUStatePDP11.prototype.updateByteByMode = function(addressMode, src, fnOp)
|
|||
this.regsGen[reg] = (this.regsGen[reg] & 0xff00) | ((data = fnOp.call(this, src, this.regsGen[reg]) & 0xff));
|
||||
} else {
|
||||
var addr = this.getAddr(addressMode, PDP11.ACCESS.UPDATE_BYTE);
|
||||
this.writeByteByPhysical(addr, (data = fnOp.call(this, src, this.readByteByPhysical(addr))));
|
||||
this.writeByteToPhysical(addr, (data = fnOp.call(this, src, this.readByteFromPhysical(addr))));
|
||||
}
|
||||
return data;
|
||||
};
|
||||
|
|
@ -1396,7 +1396,7 @@ CPUStatePDP11.prototype.writeWordByMode = function(addressMode, data)
|
|||
if (!(addressMode & PDP11.OPMODE.MASK)) {
|
||||
this.regsGen[addressMode & PDP11.OPREG.MASK] = data & 0xffff;
|
||||
} else {
|
||||
this.writeWordByPhysical(this.getAddr(addressMode, PDP11.ACCESS.WRITE), data);
|
||||
this.writeWordToPhysical(this.getAddr(addressMode, PDP11.ACCESS.WRITE), data);
|
||||
}
|
||||
return data;
|
||||
};
|
||||
|
|
@ -1416,16 +1416,15 @@ CPUStatePDP11.prototype.writeByteByMode = function(addressMode, data, writeFlags
|
|||
{
|
||||
if (!(addressMode & PDP11.OPMODE.MASK)) {
|
||||
var reg = addressMode & PDP11.OPREG.MASK;
|
||||
if (!writeFlags) {
|
||||
this.regsGen[reg] = (this.regsGen[reg] & ~0xff) | (data & 0xff);
|
||||
} else if (writeFlags & PDP11.WRITE.ZERO) {
|
||||
this.regsGen[reg] &= ~0xff;
|
||||
} else {
|
||||
this.assert(writeFlags & PDP11.WRITE.SIGNEXT);
|
||||
if (!data) {
|
||||
this.regsGen[reg] &= ~0xff; // TODO: Profile to determine if this is a win
|
||||
} else if (writeFlags & PDP11.WRITE.SIGNEXT) {
|
||||
this.regsGen[reg] = ((data << 24) >> 24) & 0xffff;
|
||||
} else {
|
||||
this.regsGen[reg] = (this.regsGen[reg] & ~0xff) | (data & 0xff);
|
||||
}
|
||||
} else {
|
||||
this.writeByteByPhysical(this.getAddr(addressMode, PDP11.ACCESS.WRITE_BYTE), data);
|
||||
this.writeByteToPhysical(this.getAddr(addressMode, PDP11.ACCESS.WRITE_BYTE), data);
|
||||
}
|
||||
return data;
|
||||
};
|
||||
|
|
@ -1600,7 +1599,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
* it to detect if our new decode() function has processed (ie, "consumed") the opcode,
|
||||
* by setting it to -1. If it has, then we can skip the older opcode decode logic below.
|
||||
*/
|
||||
this.regOp = opCode = this.readWordByVirtual(this.regsGen[7]);
|
||||
this.regOp = opCode = this.readWordFromVirtual(this.regsGen[7]);
|
||||
if (opCode >= 0) this.regsGen[7] = (this.regsGen[7] + 2) & 0xffff;
|
||||
|
||||
this.decode(opCode);
|
||||
|
|
@ -1616,7 +1615,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagV = 0;
|
||||
// } else {
|
||||
// if ((dstAddr = this.getAddr(opCode, PDP11.ACCESS.WRITE)) >= 0) {
|
||||
// if (this.writeWordByPhysical(dstAddr, src) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, src) >= 0) {
|
||||
// this.flagN = this.flagZ = src;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1651,9 +1650,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagZ = result;
|
||||
// this.flagV = 0;
|
||||
// } else {
|
||||
// if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// result = dst & ~src;
|
||||
// if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = result;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1669,9 +1668,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagZ = result;
|
||||
// this.flagV = 0;
|
||||
// } else {
|
||||
// if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// result = dst | src;
|
||||
// if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = result;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1689,9 +1688,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagZ = this.flagC = result;
|
||||
// this.flagV = (src ^ result) & (dst ^ result);
|
||||
// } else {
|
||||
// if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// result = src + dst;
|
||||
// if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = this.flagC = result;
|
||||
// this.flagV = (src ^ result) & (dst ^ result);
|
||||
// }
|
||||
|
|
@ -1709,7 +1708,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagV = 0;
|
||||
// } else {
|
||||
// if ((dstAddr = this.getAddr(opCode, PDP11.ACCESS.WRITE_BYTE)) >= 0) { // write byte
|
||||
// if (this.writeByteByPhysical(dstAddr, src) >= 0) {
|
||||
// if (this.writeByteToPhysical(dstAddr, src) >= 0) {
|
||||
// this.flagN = this.flagZ = src << 8;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1739,9 +1738,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
case 0xC000: /*0140000*/ // BICB 14SSDD
|
||||
//LOG_INSTRUCTION(opCode, 2, "BICB");
|
||||
// if ((src = this.readByteByMode(opCode >> 6)) >= 0) {
|
||||
// if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >= 0) {
|
||||
// if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >= 0) {
|
||||
// result = dst & ~src;
|
||||
// if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = result << 8;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1751,9 +1750,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
case 0xD000: /*0150000*/ // BISB 15SSDD
|
||||
//LOG_INSTRUCTION(opCode, 2, "BISB");
|
||||
// if ((src = this.readByteByMode(opCode >> 6)) >= 0) {
|
||||
// if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >= 0) {
|
||||
// if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >= 0) {
|
||||
// result = dst | src;
|
||||
// if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = result << 8;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -1770,9 +1769,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagZ = this.flagC = result;
|
||||
// this.flagV = (src ^ dst) & (dst ^ result);
|
||||
// } else {
|
||||
// if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
// result = dst - src;
|
||||
// if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
// this.flagN = this.flagZ = this.flagC = result;
|
||||
// this.flagV = (src ^ dst) & (dst ^ result);
|
||||
// }
|
||||
|
|
@ -1909,9 +1908,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = dst;
|
||||
this.flagV = 0;
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >= 0) {
|
||||
dst ^= this.regsGen[(opCode >> 6) & 7];
|
||||
if (this.writeWordByPhysical(dstAddr, dst) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, dst) >= 0) {
|
||||
this.flagN = this.flagZ = dst;
|
||||
this.flagV = 0;
|
||||
}
|
||||
|
|
@ -2019,10 +2018,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = dst & 0xff00;
|
||||
this.flagV = this.flagC = 0;
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = (dst << 8) | (dst >> 8);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = dst & 0xff00;
|
||||
this.flagV = this.flagC = 0;
|
||||
}
|
||||
|
|
@ -2036,7 +2035,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagC = this.flagV = this.flagZ = 0;
|
||||
// } else {
|
||||
// if ((dstAddr = this.getAddr(opCode, PDP11.ACCESS.WRITE)) >= 0) { // write word
|
||||
// if (this.writeWordByPhysical(dstAddr, 0) >= 0) {
|
||||
// if (this.writeWordToPhysical(dstAddr, 0) >= 0) {
|
||||
// this.flagN = this.flagC = this.flagV = this.flagZ = 0;
|
||||
// }
|
||||
// }
|
||||
|
|
@ -2047,10 +2046,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = ~dst;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result;
|
||||
this.flagC = 0x10000;
|
||||
this.flagV = 0;
|
||||
|
|
@ -2067,10 +2066,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = result;
|
||||
this.flagV = result & (result ^ dst);
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = dst + 1;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result;
|
||||
this.flagV = result & (result ^ dst);
|
||||
}
|
||||
|
|
@ -2087,10 +2086,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = result;
|
||||
this.flagV = (result ^ dst) & dst;
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = dst - 1;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result;
|
||||
this.flagV = (result ^ dst) & dst;
|
||||
}
|
||||
|
|
@ -2102,10 +2101,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = -dst;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result & dst;
|
||||
}
|
||||
|
|
@ -2116,10 +2115,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = dst + ((this.flagC >> 16) & 1);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result & (result ^ dst);
|
||||
}
|
||||
|
|
@ -2130,10 +2129,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = dst - ((this.flagC >> 16) & 1);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = (result ^ dst) & dst;
|
||||
}
|
||||
|
|
@ -2157,10 +2156,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ (this.flagC >> 1);
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = ((this.flagC & 0x10000) | dst) >> 1;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = (dst << 16);
|
||||
this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ (this.flagC >> 1);
|
||||
|
|
@ -2178,10 +2177,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ dst;
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = (dst << 1) | ((this.flagC >> 16) & 1);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ dst;
|
||||
}
|
||||
|
|
@ -2199,10 +2198,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagN = this.flagZ = result;
|
||||
this.flagV = this.flagN ^ (this.flagC >> 1);
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = (dst & 0x8000) | (dst >> 1);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = dst << 16;
|
||||
this.flagN = this.flagZ = result;
|
||||
this.flagV = this.flagN ^ (this.flagC >> 1);
|
||||
|
|
@ -2220,10 +2219,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ dst;
|
||||
} else {
|
||||
if ((dst = this.readWordByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
if ((dst = this.readWordFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE))) >=
|
||||
0) {
|
||||
result = dst << 1;
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result;
|
||||
this.flagV = result ^ dst;
|
||||
}
|
||||
|
|
@ -2233,7 +2232,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
case 0xD00: /*0006400*/ // MARK 0064nn
|
||||
//LOG_INSTRUCTION(opCode, 8, "MARK");
|
||||
virtualAddress = (this.regsGen[7] + ((opCode & 0x3F) /*077*/ << 1)) & 0xffff;
|
||||
if ((src = this.readWordByVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((src = this.readWordFromVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
this.regsGen[7] = this.regsGen[5];
|
||||
this.regsGen[5] = src;
|
||||
this.regsGen[6] = (virtualAddress + 2) & 0xffff;
|
||||
|
|
@ -2256,7 +2255,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
if ((virtualAddress = this.getVirtualByMode(opCode, 0)) >= 0) {
|
||||
if ((this.PSW & 0xf000) !== 0xf000) virtualAddress &= 0xffff;
|
||||
this.mmuMode = (this.PSW >> 12) & 3;
|
||||
if ((src = this.readWordByVirtual(virtualAddress)) >= 0) {
|
||||
if ((src = this.readWordFromVirtual(virtualAddress)) >= 0) {
|
||||
this.mmuMode = (this.PSW >> 14) & 3;
|
||||
if (this.pushWord(src) >= 0) {
|
||||
this.flagN = this.flagZ = src;
|
||||
|
|
@ -2285,7 +2284,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.mmuMode = (this.PSW >> 12) & 3;
|
||||
if ((dstAddr = this.mapVirtualToPhysical(virtualAddress, PDP11.ACCESS.WRITE)) >= 0) {
|
||||
this.mmuMode = (this.PSW >> 14) & 3;
|
||||
if (this.writeWordByPhysical(dstAddr, dst) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, dst) >= 0) {
|
||||
this.flagN = this.flagZ = dst;
|
||||
this.flagV = 0;
|
||||
}
|
||||
|
|
@ -2301,7 +2300,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
*/
|
||||
if ((dstAddr = this.getAddr(opCode, PDP11.ACCESS.WRITE)) >= 0) { // write word
|
||||
result = -((this.flagN >> 15) & 1);
|
||||
if (this.writeWordByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagZ = result;
|
||||
this.flagV = 0;
|
||||
}
|
||||
|
|
@ -2314,7 +2313,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// this.flagN = this.flagC = this.flagV = this.flagZ = 0;
|
||||
// } else {
|
||||
// if ((dstAddr = this.getAddr(opCode, PDP11.ACCESS.WRITE_BYTE)) >= 0) { // write byte
|
||||
// if (this.writeByteByPhysical(dstAddr, 0) >= 0) {
|
||||
// if (this.writeByteToPhysical(dstAddr, 0) >= 0) {
|
||||
// this.flagN = this.flagC = this.flagV = this.flagZ = 0;
|
||||
// }
|
||||
// }
|
||||
|
|
@ -2325,10 +2324,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = ~dst;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result << 8;
|
||||
this.flagC = 0x10000;
|
||||
this.flagV = 0;
|
||||
|
|
@ -2340,10 +2339,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = dst + 1;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = (result & (result ^ dst)) << 8;
|
||||
}
|
||||
|
|
@ -2354,10 +2353,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = dst - 1;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = ((result ^ dst) & dst) << 8;
|
||||
}
|
||||
|
|
@ -2368,10 +2367,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = -dst;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = (result & dst) << 8;
|
||||
}
|
||||
|
|
@ -2382,10 +2381,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = dst + ((this.flagC >> 16) & 1);
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = this.flagC = result << 8;
|
||||
this.flagV = (result & (result ^ dst)) << 8;
|
||||
}
|
||||
|
|
@ -2396,10 +2395,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = dst - ((this.flagC >> 16) & 1);
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagN = this.flagZ = this.flagC = result << 8;
|
||||
this.flagV = ((result ^ dst) & dst) << 8;
|
||||
}
|
||||
|
|
@ -2417,10 +2416,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = (((this.flagC & 0x10000) >> 8) | dst) >> 1;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = (dst << 16);
|
||||
this.flagN = this.flagZ = (result << 8);
|
||||
this.flagV = this.flagN ^ (this.flagC >> 1);
|
||||
|
|
@ -2432,10 +2431,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = (dst << 1) | ((this.flagC >> 16) & 1);
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = (result ^ dst) << 8;
|
||||
}
|
||||
|
|
@ -2446,10 +2445,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = (dst & 0x80) | (dst >> 1);
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = dst << 16;
|
||||
this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = this.flagN ^ (this.flagC >> 1);
|
||||
|
|
@ -2461,10 +2460,10 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
/*
|
||||
* TODO: Here's an example where getAddr() could be called in the register-only case.
|
||||
*/
|
||||
if ((dst = this.readByteByPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
if ((dst = this.readByteFromPhysical(dstAddr = this.getAddr(opCode, PDP11.ACCESS.UPDATE_BYTE))) >=
|
||||
0) {
|
||||
result = dst << 1;
|
||||
if (this.writeByteByPhysical(dstAddr, result) >= 0) {
|
||||
if (this.writeByteToPhysical(dstAddr, result) >= 0) {
|
||||
this.flagC = this.flagN = this.flagZ = result << 8;
|
||||
this.flagV = (result ^ dst) << 8;
|
||||
}
|
||||
|
|
@ -2492,7 +2491,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
} else {
|
||||
if ((virtualAddress = this.getVirtualByMode(opCode, 0)) >= 0) {
|
||||
this.mmuMode = (this.PSW >> 12) & 3;
|
||||
if ((src = this.readWordByVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((src = this.readWordFromVirtual(virtualAddress | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
this.mmuMode = (this.PSW >> 14) & 3;
|
||||
if (this.pushWord(src) >= 0) {
|
||||
this.flagN = this.flagZ = src;
|
||||
|
|
@ -2520,7 +2519,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
this.mmuMode = (this.PSW >> 12) & 3;
|
||||
if ((dstAddr = this.mapVirtualToPhysical(virtualAddress | PDP11.ACCESS.DSPACE, PDP11.ACCESS.WRITE)) >= 0) {
|
||||
this.mmuMode = (this.PSW >> 14) & 3;
|
||||
if (this.writeWordByPhysical(dstAddr, dst) >= 0) {
|
||||
if (this.writeWordToPhysical(dstAddr, dst) >= 0) {
|
||||
this.flagN = this.flagZ = dst;
|
||||
this.flagV = 0;
|
||||
}
|
||||
|
|
@ -2534,7 +2533,7 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
// src = this.getPSW() & 0xff;
|
||||
// if (instruction & 0x38) {
|
||||
// if ((dstAddr = this.getAddr(instruction, PDP11.ACCESS.WRITE_BYTE)) >= 0) { // write byte
|
||||
// if (this.writeByteByPhysical(dstAddr, src) >= 0) {
|
||||
// if (this.writeByteToPhysical(dstAddr, src) >= 0) {
|
||||
// this.flagN = this.flagZ = src << 8;
|
||||
// this.flagV = 0;
|
||||
// }
|
||||
|
|
@ -2625,9 +2624,9 @@ CPUStatePDP11.prototype.stepCPU = function(nMinCycles)
|
|||
case 0x6: /*0000006*/ // RTT 000006
|
||||
//LOG_INSTRUCTION(opCode, 0, "RTT");
|
||||
dstAddr = this.regsGen[6];
|
||||
if ((virtualAddress = this.readWordByVirtual(dstAddr | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((virtualAddress = this.readWordFromVirtual(dstAddr | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
dstAddr = (dstAddr + 2) & 0xffff;
|
||||
if ((savePSW = this.readWordByVirtual(dstAddr | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
if ((savePSW = this.readWordFromVirtual(dstAddr | PDP11.ACCESS.DSPACE)) >= 0) {
|
||||
this.regsGen[6] = (dstAddr + 2) & 0xffff;
|
||||
savePSW &= 0xf8ff;
|
||||
if (this.PSW & 0xc000) { // user / super restrictions
|
||||
|
|
|
|||
|
|
@ -234,8 +234,7 @@ var PDP11 = {
|
|||
*/
|
||||
WRITE: {
|
||||
NORMAL: 0x0, // write byte or word normally
|
||||
ZERO: 0x1, // zero byte or word
|
||||
SIGNEXT: 0x2 // sign-extend a byte to a word
|
||||
SIGNEXT: 0x1 // sign-extend a byte to a word
|
||||
},
|
||||
CPUERR: {
|
||||
RED: 0x0004, // red zone stack limit
|
||||
|
|
@ -307,6 +306,10 @@ var PDP11 = {
|
|||
SIZE_HI: 0o177762, // Upper Size Register (always zero) (11/70 only?)
|
||||
SIZE_LO: 0o177760, // Lower Size Register (last 32-word block) (11/70 only?)
|
||||
DISPLAY: 0o177570, // Console Switch and Display
|
||||
XBUF: 0o177566, // Console Terminal: Transmitter Data Buffer Register
|
||||
XCSR: 0o177564, // Console Terminal: Transmitter Status Register
|
||||
RBUF: 0o177562, // Console Terminal: Receiver Data Buffer Register
|
||||
RCSR: 0o177560, // Console Terminal: Receiver Status Register
|
||||
MMR0: 0o177572, // 777572 17777572
|
||||
MMR1: 0o177574, // 777574 17777574
|
||||
MMR2: 0o177576, // 777576 17777576
|
||||
|
|
@ -407,6 +410,17 @@ var PDP11 = {
|
|||
KDSAR5: 0o172372, // Kernel D Space Address Register 5
|
||||
KDSAR6: 0o172374, // Kernel D Space Address Register 6
|
||||
KDSAR7: 0o172376, // Kernel D Space Address Register 7
|
||||
},
|
||||
DL11: {
|
||||
DELAY: 8,
|
||||
PRI: 4,
|
||||
VEC: 0o64,
|
||||
XCSR: {
|
||||
READY: 0x80, // Transmitter Ready (read-only)
|
||||
INT_ENABLE: 0x40, // Transmitter Interrupt Enable (read-write)
|
||||
MAINT: 0x04, // Maintenance (read-write)
|
||||
BREAK: 0x01 // BREAK (read-write)
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -204,7 +204,7 @@ DevicePDP11.prototype.initBus = function(cmp, bus, cpu, dbg)
|
|||
* readPSW(addr)
|
||||
*
|
||||
* @this {DevicePDP11}
|
||||
* @param {number} addr (eg, PDP11.UNIBUS.PSW)
|
||||
* @param {number} addr (eg, 177776)
|
||||
* @return {number}
|
||||
*/
|
||||
DevicePDP11.prototype.readPSW = function(addr)
|
||||
|
|
@ -217,7 +217,7 @@ DevicePDP11.prototype.readPSW = function(addr)
|
|||
*
|
||||
* @this {DevicePDP11}
|
||||
* @param {number} data
|
||||
* @param {number} addr (ie, PDP11.UNIBUS.PSW)
|
||||
* @param {number} addr (eg, 177776)
|
||||
*/
|
||||
DevicePDP11.prototype.writePSW = function(data, addr)
|
||||
{
|
||||
|
|
@ -226,6 +226,43 @@ DevicePDP11.prototype.writePSW = function(data, addr)
|
|||
this.cpu.opFlags |= PDP11.OPFLAG.SKIP_FLAGS;
|
||||
};
|
||||
|
||||
/**
|
||||
* readXCSR(addr)
|
||||
*
|
||||
* @this {DevicePDP11}
|
||||
* @param {number} addr (eg, 177564)
|
||||
* @return {number}
|
||||
*/
|
||||
DevicePDP11.prototype.readXCSR = function(addr)
|
||||
{
|
||||
return this.tty.xcsr;
|
||||
};
|
||||
|
||||
/**
|
||||
* writeXCSR(data, addr)
|
||||
*
|
||||
* @this {DevicePDP11}
|
||||
* @param {number} data
|
||||
* @param {number} addr (eg, 177564)
|
||||
*/
|
||||
DevicePDP11.prototype.writeXCSR = function(data, addr)
|
||||
{
|
||||
/*
|
||||
* If the device is READY and INT_ENABLE is transitioning to *set*, generate an interrupt.
|
||||
*/
|
||||
var device = this;
|
||||
if ((this.tty.xcsr & (PDP11.DL11.XCSR.READY | PDP11.DL11.XCSR.INT_ENABLE)) == PDP11.DL11.XCSR.READY && (data & PDP11.DL11.XCSR.INT_ENABLE)) {
|
||||
this.cpu.interrupt(PDP11.DL11.DELAY, PDP11.DL11.PRI, PDP11.DL11.VEC, function() {
|
||||
device.tty.xcsr |= PDP11.DL11.XCSR.READY;
|
||||
return !!(device.tty.xcsr & PDP11.DL11.XCSR.INT_ENABLE);
|
||||
});
|
||||
}
|
||||
/*
|
||||
* In any event, update all bits from data *except* for READY.
|
||||
*/
|
||||
this.tty.xcsr = (this.tty.xcsr & PDP11.DL11.XCSR.READY) | (data & ~PDP11.DL11.XCSR.READY);
|
||||
};
|
||||
|
||||
/**
|
||||
* rk11_go()
|
||||
*
|
||||
|
|
@ -295,7 +332,7 @@ DevicePDP11.prototype.rk11_go = function()
|
|||
break;
|
||||
}
|
||||
rk11.rkds = (drive << 13) | (rk11.rkds & 0x1ff0) | ((rk11.rkda % 9) & 0xf);
|
||||
this.cpu.interrupt(20, 5 << 5, 0x90, /*0220*/ function() {
|
||||
this.cpu.interrupt(20, 5, 0x90, /*0220*/ function() {
|
||||
rk11.rkcs = (rk11.rkcs & 0xfffe) | 0x80; // turn off go & set done
|
||||
return !!(rk11.rkcs & 0x40);
|
||||
});
|
||||
|
|
@ -327,7 +364,7 @@ DevicePDP11.prototype.rk11_end = function(err, meta, block, address, count)
|
|||
rk11.rkcs |= 0xc000; // err
|
||||
break;
|
||||
}
|
||||
this.cpu.interrupt(20, 5 << 5, 0x90, /*0220*/ function() {
|
||||
this.cpu.interrupt(20, 5, 0x90, /*0220*/ function() {
|
||||
rk11.rkcs = (rk11.rkcs & 0xfffe) | 0x80; // turn off go & set done
|
||||
return !!(rk11.rkcs & 0x40);
|
||||
});
|
||||
|
|
@ -408,7 +445,7 @@ DevicePDP11.prototype.rl11_go = function()
|
|||
case 7: // Read data without header check
|
||||
break;
|
||||
}
|
||||
this.cpu.interrupt(20, 5 << 5, 0x70, /*0160*/ function() {
|
||||
this.cpu.interrupt(20, 5, 0x70, /*0160*/ function() {
|
||||
rl11.csr |= 0x81; // turn off go & set ready
|
||||
return !!(rl11.csr & 0x40);
|
||||
});
|
||||
|
|
@ -442,7 +479,7 @@ DevicePDP11.prototype.rl11_end = function(err, meta, block, address, count)
|
|||
rl11.csr |= 0xa000; // NXM
|
||||
break;
|
||||
}
|
||||
this.cpu.interrupt(20, 5 << 5, 0x70, /*0160*/ function() {
|
||||
this.cpu.interrupt(20, 5, 0x70, /*0160*/ function() {
|
||||
rl11.csr |= 0x81; // turn off go & set ready
|
||||
return !!(rl11.csr & 0x40);
|
||||
});
|
||||
|
|
@ -551,7 +588,7 @@ DevicePDP11.prototype.rp11_go = function(drive)
|
|||
default:
|
||||
break;
|
||||
}
|
||||
this.cpu.interrupt(3, 5 << 5, 0xAC, /*0254*/ function() {
|
||||
this.cpu.interrupt(3, 5, 0xAC, /*0254*/ function() {
|
||||
rp11.rpcs1 = (rp11.rpcs1 & 0xfffe) | 0x80; // Turn go off and ready on
|
||||
rp11.rpds[drive] |= 0x80; // ATA
|
||||
return !!(rp11.rpcs1 & 0x40);
|
||||
|
|
@ -594,7 +631,7 @@ DevicePDP11.prototype.rp11_end = function(err, meta, block, address, count)
|
|||
rp11.rpcs1 |= 0xc000; // set SC & TRE
|
||||
break;
|
||||
}
|
||||
this.cpu.interrupt(20, 5 << 5, 0xAC, /*0254*/ function() {
|
||||
this.cpu.interrupt(20, 5, 0xAC, /*0254*/ function() {
|
||||
rp11.rpds[meta.drive] |= 0x80;
|
||||
rp11.rpcs1 = (rp11.rpcs1 & 0xfffe) | 0x80; // Turn go off and ready on
|
||||
return !!(rp11.rpcs1 & 0x40);
|
||||
|
|
@ -610,7 +647,7 @@ DevicePDP11.prototype.kw11_interrupt = function()
|
|||
{
|
||||
this.kw11.csr |= 0x80;
|
||||
if (this.kw11.csr & 0x40) {
|
||||
this.cpu.interrupt(0, 6 << 5, 0x40 /*0100*/);
|
||||
this.cpu.interrupt(0, 6, 0x40 /*0100*/);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -734,7 +771,7 @@ DevicePDP11.prototype.readData = function(meta, block, address, count)
|
|||
return;
|
||||
}
|
||||
for (word = 0; word < meta.blocksize && count > 0; word++) {
|
||||
if (this.cpu.writeWordByPhysical((meta.mapped? this.cpu.mapUnibus(address) : address), meta.cache[block][word]) < 0) {
|
||||
if (this.cpu.writeWordToPhysical((meta.mapped? this.cpu.mapUnibus(address) : address), meta.cache[block][word]) < 0) {
|
||||
meta.postProcess(2, meta, block, address, count); // NXM
|
||||
return;
|
||||
}
|
||||
|
|
@ -768,7 +805,7 @@ DevicePDP11.prototype.writeData = function(meta, block, address, count)
|
|||
}
|
||||
}
|
||||
for (word = 0; word < meta.blocksize && count > 0; word++) {
|
||||
data = this.cpu.readWordByPhysical((meta.mapped? this.cpu.mapUnibus(address) : address));
|
||||
data = this.cpu.readWordFromPhysical((meta.mapped? this.cpu.mapUnibus(address) : address));
|
||||
if (data < 0) {
|
||||
meta.postProcess(2, meta, block, address, count); // NXM
|
||||
return;
|
||||
|
|
@ -1057,7 +1094,7 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
tty.del = 0;
|
||||
}
|
||||
tty.xcsr &= ~0x80; /*0200*/
|
||||
cpu.interrupt(100, 4 << 5, 0x34, /*064*/ function() {
|
||||
cpu.interrupt(100, 4, 0x34, /*064*/ function() {
|
||||
tty.xcsr |= 0x80; /*0200*/
|
||||
return !!(tty.xcsr & 0x40); /*0100*/
|
||||
});
|
||||
|
|
@ -1065,20 +1102,20 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
result = 0;
|
||||
break;
|
||||
case 0x3FFF74: /*017777564*/ // console xcsr
|
||||
if (data < 0) {
|
||||
result = tty.xcsr;
|
||||
} else {
|
||||
result = this.insertData(tty.xcsr, physicalAddress, data, byteFlag);
|
||||
if (result >= 0) {
|
||||
if ((tty.xcsr & 0xC0) /*0300*/ == 0x80 /*0200*/&& (result & 0x40) /*0100*/) {
|
||||
cpu.interrupt(8, 4 << 5, 0x34, /*064*/ function() {
|
||||
tty.xcsr |= 0x80; /*0200*/
|
||||
return !!(tty.xcsr & 0x40); /*0100*/
|
||||
});
|
||||
}
|
||||
tty.xcsr = (tty.xcsr & 0x80) /*0200*/ | (result & ~0x80) /*0200*/;
|
||||
}
|
||||
}
|
||||
// if (data < 0) {
|
||||
// result = tty.xcsr;
|
||||
// } else {
|
||||
// result = this.insertData(tty.xcsr, physicalAddress, data, byteFlag);
|
||||
// if (result >= 0) {
|
||||
// if ((tty.xcsr & 0xC0) /*0300*/ == 0x80 /*0200*/&& (result & 0x40) /*0100*/) {
|
||||
// cpu.interrupt(8, 4, 0x34, /*064*/ function() {
|
||||
// tty.xcsr |= 0x80; /*0200*/
|
||||
// return !!(tty.xcsr & 0x40); /*0100*/
|
||||
// });
|
||||
// }
|
||||
// tty.xcsr = (tty.xcsr & 0x80) /*0200*/ | (result & ~0x80) /*0200*/;
|
||||
// }
|
||||
// }
|
||||
break;
|
||||
case 0x3FFF72: /*017777562*/ // console rbuf
|
||||
result = 0;
|
||||
|
|
@ -1089,7 +1126,7 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
if (tty.rbuf.length > 0) {
|
||||
setTimeout(function() {
|
||||
tty.rcsr |= 0x80; /*0200*/
|
||||
if (tty.rcsr & 0x40) /*0100*/ cpu.interrupt(40, 4 << 5, 0x30) /*060*/;
|
||||
if (tty.rcsr & 0x40) /*0100*/ cpu.interrupt(40, 4, 0x30) /*060*/;
|
||||
}, 50);
|
||||
}
|
||||
}
|
||||
|
|
@ -1182,7 +1219,7 @@ DevicePDP11.prototype.access = function(physicalAddress, data, byteFlag)
|
|||
this.rp11_go(idx);
|
||||
} else {
|
||||
if ((result & 0xc0) == 0xc0) {
|
||||
cpu.interrupt(0, 5 << 5, 0xAC) /*0254*/;
|
||||
cpu.interrupt(0, 5, 0xAC) /*0254*/;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1409,7 +1446,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.PSW]: [null, null, DevicePDP11.prototype.readPSW, DevicePDP11.prototype.writePSW]
|
||||
[PDP11.UNIBUS.PSW]: [
|
||||
null, null, DevicePDP11.prototype.readPSW, DevicePDP11.prototype.writePSW
|
||||
],
|
||||
[PDP11.UNIBUS.XCSR]: [
|
||||
null, null, DevicePDP11.prototype.readXCSR, DevicePDP11.prototype.writeXCSR
|
||||
]
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
|||
Loading…
Reference in a new issue