First post, by jakethompson1
- Rank
- Oldbie
I have a PVGA1A-based ISA VGA card. It has eight 64Kx4 chips for video memory.
In 640x480x16 mode (and likely other modes) it has a strange failure with jail bars, and it does not have anything to do with CRT vs. LCD.
I had to learn about planar memory layout to debug this. 16-color mode has a 64K window at a000:0. Instead of byte 0, bits 7-4 being pixel (0,0); byte 0, bits 3-0 being pixel (0, 1), etc. as you might expect, it's bit 0 of every pixel packed together for "plane 0", bit 1 of every pixel packed together for "plane 1", and so on.
You can write to any combination of planes by ORing together 1<<plane number and writing that value to port 3c5 (after writing index 02 to port 3c4). An obvious use for writing multiple planes at once is to clear the screen to all black (0000b) or all white (1111b).
You can read one plane at a time by writing the plane number to port 3cf (after writing index 04 to port 3ce).
With that knowledge I was able to debug the issue. First switch to mode 12h (which will automatically zero out video RAM).
Switch to plane 1 and fill it with FF bytes. That should set every pixel to 0010b (dark green) and plane 3 should remain filled with 00 bytes. Instead, plane 3 magically changes to F0 bytes. And we get light/dark green jailbars.
Zero out video RAM again.
Switch to plane 3 and fill it with FF bytes. That should set every pixel to 1000b (dark gray). Instead, it sets 0F bytes and we get black/gray jailbars.
I assume this is one of the 64Kx4 chips being bad? Or could the addressing logic inside the PVGA1A have gone bad? Any idea on the mapping from planes to DRAM chips? Seems like it's likely the seventh or eighth memory chip that is bad?
C:\>debug
-a
0B6F:0100 mov ax,12 ; put the screen in 640x480x16 mode
0B6F:0103 int 10
0B6F:0105 int3
0B6F:0106
-g=100
AX=0012 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000
DS=0B6F ES=0B6F SS=0B6F CS=0B6F IP=0105 NV UP EI PL NZ NA PO NC
0B6F:0105 CC INT 3
-o 3c4 2
-o 3c5 8 ; writes to a000 segment should ONLY go to plane 3
-o 3ce 4
-o 3cf 3 ; reads from a000 segment should come from plane 3
-f a000:0 l 9600 ff ; should produce entirely gray screen
-d a000:0 l 10 ; actually produces black/gray jailbars
A000:0000 0F 0F 0F 0F 0F 0F 0F 0F-0F 0F 0F 0F 0F 0F 0F 0F ................
-f a000:0 l 9600 f0 ; should produce gray/black jailbars
-d a000:0 l 10 ; actually produces entirely black screen
A000:0000 00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00 ................
-f a000:0 l 9600 0f ; should produce black/gray jailbars
-d a000:0 l 10 ; it does that
A000:0000 0F 0F 0F 0F 0F 0F 0F 0F-0F 0F 0F 0F 0F 0F 0F 0F ................
-f a000:0 l 9600 a5 ; just testing memory
-d a000:0 l 10 ; the high nibble fails
A000:0000 05 05 05 05 05 05 05 05-05 05 05 05 05 05 05 05 ................
-f a000:0 l 9600 5a ; just testing memory
-d a000:0 l 10 ; the high nibble fails
A000:0000 0A 0A 0A 0A 0A 0A 0A 0A-0A 0A 0A 0A 0A 0A 0A 0A ................
-g=100 ; now clear the screen
AX=0012 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000
DS=0B6F ES=0B6F SS=0B6F CS=0B6F IP=0105 NV UP EI PL NZ NA PO NC
0B6F:0105 CC INT 3
-o 3c4 2
-o 3c5 2 ; writes go to plane 1 only
-o 3ce 4
-o 3cf 1 ; reads come from plane 1 only
-f a000:0 l 9600 ff ; should be entirely dark green screen
; it should not affect plane 3 at all
; instead, light green/dark green jailbars
-o 3ce 4
-o 3cf 3 ; switch to reading from plane 3
-d a000:0 l 10 ; now the high nibble is stuck on instead of off???
A000:0000 F0 F0 F0 F0 F0 F0 F0 F0-F0 F0 F0 F0 F0 F0 F0 F0 ................