VT100 video buffer bias fixed

This commit is contained in:
Jeff Parsons 2016-08-02 18:53:01 -07:00 committed by Jeff Parsons
commit e82a1d5b52
3 changed files with 29 additions and 36 deletions

View file

@ -26,5 +26,5 @@
<chipset id="chipset" model="VT100"/> <chipset id="chipset" model="VT100"/>
<keyboard id="keyboard"/> <keyboard id="keyboard"/>
<panel ref="/devices/pc8080/panel/wide.xml"/> <panel ref="/devices/pc8080/panel/wide.xml"/>
<debugger id="debugger" messages="port|mem|halt" commands="s 8086"/> <debugger id="debugger" messages="port|mem" commands="s 8086"/>
</machine> </machine>

View file

@ -194,6 +194,9 @@ ChipSet.VT100 = {
DC011: { // generates Line Buffer Addresses (LBAs) for the Video Processor DC011: { // generates Line Buffer Addresses (LBAs) for the Video Processor
PORT: 0xC2, // write-only PORT: 0xC2, // write-only
INIT: 0x00 INIT: 0x00
},
LBA: { // used to simulate LBA0 through LBA7 (LBA7 is used to drive NVR_CLK)
INIT: 0x00
} }
}; };
@ -312,7 +315,8 @@ ChipSet.VT100.init = [
ChipSet.VT100.NVR_LATCH.INIT, ChipSet.VT100.NVR_LATCH.INIT,
ChipSet.VT100.FLAGS_BUFFER.NO_AVO | ChipSet.VT100.FLAGS_BUFFER.NO_GFX, ChipSet.VT100.FLAGS_BUFFER.NO_AVO | ChipSet.VT100.FLAGS_BUFFER.NO_GFX,
ChipSet.VT100.DC012.INIT, ChipSet.VT100.DC012.INIT,
ChipSet.VT100.DC011.INIT ChipSet.VT100.DC011.INIT,
ChipSet.VT100.LBA.INIT
] ]
]; ];
@ -344,7 +348,7 @@ ChipSet.prototype.save = function()
state.set(0, [this.bStatus0, this.bStatus1, this.bStatus2, this.wShiftData, this.bShiftCount, this.bSound1, this.bSound2]); state.set(0, [this.bStatus0, this.bStatus1, this.bStatus2, this.wShiftData, this.bShiftCount, this.bSound1, this.bSound2]);
break; break;
case ChipSet.VT100.MODEL: case ChipSet.VT100.MODEL:
state.set(0, [this.bBrightnessLatch, this.bNVRLatch]); state.set(0, [this.bBrightnessLatch, this.bNVRLatch, this.bFlagsBuffer, this.bDC012, this.bDC011, this.bLBA]);
break; break;
} }
return state.data(); return state.data();
@ -379,6 +383,7 @@ ChipSet.prototype.restore = function(data)
this.bFlagsBuffer = a[2]; this.bFlagsBuffer = a[2];
this.bDC012 = a[3]; this.bDC012 = a[3];
this.bDC011 = a[4]; this.bDC011 = a[4];
this.bLBA = a[5];
return true; return true;
} }
} }
@ -413,19 +418,6 @@ ChipSet.prototype.stop = function()
*/ */
}; };
/**
* isVideoEnabled()
*
* TODO: Consider moving this and the related ports (ie, DC011 and DC012) into the Video component.
*
* @this {ChipSet}
* @return {boolean}
*/
ChipSet.prototype.isVideoEnabled = function()
{
return this.model != ChipSet.VT100.MODEL || this.bDC011 != 0;
};
/** /**
* updateStatus0(bit, fSet) * updateStatus0(bit, fSet)
* *
@ -604,7 +596,8 @@ ChipSet.prototype.outSIWatchdog = function(port, b, addrFrom)
*/ */
ChipSet.prototype.inVT100FlagsBuffer = function(port, addrFrom) ChipSet.prototype.inVT100FlagsBuffer = function(port, addrFrom)
{ {
var b = this.bFlagsBuffer; this.bLBA++;
var b = this.bFlagsBuffer = (this.bFlagsBuffer & ~ChipSet.VT100.FLAGS_BUFFER.NVR_CLK) | ((this.bLBA & 0x80)? ChipSet.VT100.FLAGS_BUFFER.NVR_CLK : 0);
this.printMessageIO(port, null, addrFrom, "FLAGS.BUFFER", b, true); this.printMessageIO(port, null, addrFrom, "FLAGS.BUFFER", b, true);
return b; return b;
}; };

View file

@ -279,10 +279,13 @@ Video.VT100 = {
}, },
LINETERM: 0x7F, LINETERM: 0x7F,
LINEATTR: { LINEATTR: {
ADDRMASK: 0x1F, ADDRMASK: 0x0F,
ADDRBIAS: 0x10, // 1 == ADDRBIAS_LO, 0 = ADDRBIAS_HI
FONTMASK: 0x60, FONTMASK: 0x60,
SCROLL: 0x80 SCROLL: 0x80
} },
ADDRBIAS_LO: 0x2000,
ADDRBIAS_HI: 0x4000
}; };
/** /**
@ -635,7 +638,7 @@ Video.prototype.powerUp = function(data, fRepower)
fBreak = true; fBreak = true;
} }
} }
b = (font & Video.VT100.LINEATTR.FONTMASK) | ((addrNext >> 8) & Video.VT100.LINEATTR.ADDRMASK); b = (font & Video.VT100.LINEATTR.FONTMASK) | ((addrNext >> 8) & Video.VT100.LINEATTR.ADDRMASK) | Video.VT100.LINEATTR.ADDRBIAS;
this.bus.setByteDirect(addr++, b); this.bus.setByteDirect(addr++, b);
this.bus.setByteDirect(addr++, addrNext & 0xff); this.bus.setByteDirect(addr++, addrNext & 0xff);
if (fBreak) break; if (fBreak) break;
@ -978,7 +981,8 @@ Video.prototype.updateVT100 = function()
if ((data & Video.VT100.LINETERM) == Video.VT100.LINETERM) { if ((data & Video.VT100.LINETERM) == Video.VT100.LINETERM) {
var b = this.bus.getByteDirect(addr++); var b = this.bus.getByteDirect(addr++);
fontNext = b & Video.VT100.LINEATTR.FONTMASK; fontNext = b & Video.VT100.LINEATTR.FONTMASK;
addrNext = this.addrBuffer | ((b & Video.VT100.LINEATTR.ADDRMASK) << 8) | this.bus.getByteDirect(addr); addrNext = ((b & Video.VT100.LINEATTR.ADDRMASK) << 8) | this.bus.getByteDirect(addr);
addrNext += (b & Video.VT100.LINEATTR.ADDRBIAS)? Video.VT100.ADDRBIAS_LO : Video.VT100.ADDRBIAS_HI;
break; break;
} }
if (nCols < this.abLineBuffer.length) { if (nCols < this.abLineBuffer.length) {
@ -992,7 +996,6 @@ Video.prototype.updateVT100 = function()
* Skip the first few "fill lines" * Skip the first few "fill lines"
*/ */
if (nFill) { if (nFill) {
this.assert(nCols === 0); // "fill lines" are typically zero-length
nFill--; nFill--;
continue; continue;
} }
@ -1004,22 +1007,19 @@ Video.prototype.updateVT100 = function()
this.abLineBuffer[nCols++] = 0; // character code 0 is a empty font character this.abLineBuffer[nCols++] = 0; // character code 0 is a empty font character
} }
this.assert(font >= 0); // font isn't valid on the first line, but that's always a "fill line"
/* /*
* Display the line buffer * Display the line buffer; ordinarily, font would always be valid after processing the "fill lines",
* but if the buffer was filled with garbage, the usual LINETERM might be missing, so font might not be set.
*/ */
for (var iCol = 0; iCol < nCols; iCol++) { if (font >= 0) {
data = this.abLineBuffer[iCol]; for (var iCol = 0; iCol < nCols; iCol++) {
if (!this.fCellCacheValid || data !== this.aCellCache[iCell]) { data = this.abLineBuffer[iCol];
/* if (!this.fCellCacheValid || data !== this.aCellCache[iCell]) {
* TODO: If bit 8 is set, we must select a different font variation, depending on which per-character this.updateChar(font, iCol, nRows, data, this.contextBuffer);
* screen attribute is currently enabled (ie, reverse video or underline). cUpdated++;
*/ }
this.updateChar(font, iCol, nRows, data, this.contextBuffer); iCell++;
cUpdated++;
} }
iCell++;
} }
nRows++; nRows++;
} }
@ -1090,7 +1090,7 @@ Video.prototype.updateScreen = function(n)
this.printMessage("updateScreen(" + n + "): clean=" + fClean + ", update=" + fUpdate + ", cycles=" + nCycles + ", delta=" + nCyclesDelta); this.printMessage("updateScreen(" + n + "): clean=" + fClean + ", update=" + fUpdate + ", cycles=" + nCycles + ", delta=" + nCyclesDelta);
} }
if (!fUpdate || this.chipset && !this.chipset.isVideoEnabled()) { if (!fUpdate) {
return; return;
} }