VOGONS


UniPCemu VGA BIOS troubleshooting?

Topic actions

Reply 20 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

Let's just say that monochrome graphics modes (any CGA/EGA/VGA modes other than mode 0Fh) on the VGA BIOS give interesting results, from the screen not being properly filled, the screen only taking up half the screen somehow (no issues on color VGA though) or some text displayed (things like basic text glyphs drawn by the software) with lots of corrupted gibberish on top of it for some weird reason.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 21 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

OK. Since the B/W monitor detection is now properly working, I've noticed another issue: mode sets.
Somehow, when the B/W monitor is detected, mode sets for graphics modes other than Fh (which is a monochrome mode) seems to mess up. Like for example, Jazz Jackrabbit, which uses mode X or mode 13h I think, stays in mode 7h (which is a text mode) instead of properly switching to grayscale graphics mode.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 22 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

Oh. One nice thing occurred. While fixing the VGA (and EGA documented odd/even mode), the EGA monochrome suddenly also started to work and post properly (I think because of the fixed odd/even mode mapping).

Since the VGA-specific POST registers (POS registers and 46E8h register support (instead of 3C3h register, which is for motherboard VGA only (and that is unused by the BIOS ROM)) don't exist on the EGA, I've defaulted then to be a hard 'on' state, while on (S)VGA, they're actually obeyed, with VGA now using 46E8h (and 102h for card enable storage, but this isn't emulated at all. 46E8h now completely controls the card's memory mapping being enabled (combined with the misc output register of course) and disables all non-POS and non-46E8h I/O address mapping) instead of the old 3C3h I/O port (which is only used on SVGA and not on the IBM VGA card itself).

The VGA monochrome monitor still causes the VGA BIOS to behave erratically somehow. It's messing up the video settings it seems?

Checkit displaying mode 00/01h only fills half the screen.
Mode 04h too, but no grid appears, just the text portion. The 'Y' or 'N' is also displayed as Ç for some weird reason.
Mode Dh is displaying the text as well, but the 'Y'/'N' becomes a full block cursor only. The display has corrupted lines every 'character cell' horizontally, with almost all text having garbled pixels on top of it.
Mod 13h displays like mode 04h. Except no Ç character, it's displaying the text just fine.
Mode 06h displays correctly full-screen, as does the text. But no dotted lines visible either. Maybe it's remained in text mode? (Just checked, yes, it's in text mode instead. Probably that's the case for mode 13h as well somehow).
Mode 0Eh is garbled, like mode Dh.
Mode 0Fh renders without issues.
Mode 10h is garbled also, like mode 0Eh and mode Dh.
Mode 11h is text mode also.
Mode 12h is garbled. And text mode.

So it seems only mode 0Fh ends up in graphics mode, all others somehow seem to load text mode instead, which they shouldnt!

Edit: Just took a look at the INT10h handling of mode switches. When the adapter is in monochome mode (port 3B4h), it refuses to switch to color graphics modes and vise versa? So it can't enter any color modes (other than mode 7h and Fh) when it's using the MDA adapter space (failing the request by passing through to the motherboard BIOS, which is IRET on i440fx for example)!

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 23 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

OK. After more looking into the POST routine, I found the cause:
- When the POST detects the base address to use for the first time, it simply checks for MDA and CGA while the VGA is disabled. Since neither is found, CGA-compatible (and VGA-compatible) addresses are used. It writes to the VGA misc output register, but it won't respond due to being disabled during powerup and because it isn't enabled until afterwards.
- Then the VGA's I/O and memory addresses are enabled (using port 46E8h and 102h (the latter might be optional, not sure)). It uses 46E8h to enable the POS register, uses the POS register to enable the card, then switches the VGA from configuration mode to active mode (enable I/O ports and video buffer decoding on the card). It also writes some value (0) to port 4AE8h, but I don't know what that is doing.
- It configures it's assumed monochrome or color base address based on the found video cards before (if none are found, it defaults to color mode).
- At C7h it stores the base address into the BDA.
- Then it setups a color or monochrome mode for further testing (based on the earlier settings).
- It initializes the attribute controller settings.
- It checks for DAC output (using the feedback in the input status register's MUX)
- It performs a VRAM test.
- It polls monitor information using the RGB outputs during active display and the first DAC entry (forced by clearing the DAC mask register). In my emulator, it will either detect one of the two monochrome settings and set bits 2-3 of BDA 89h (meaning monochrome monitor attached (bit 2) and grayscale summing enabled (bit 1)) or detect a color monitor and clears those two bits in BDA 89h (meaning color monitor attached and grayscale summing disabled).
- It then optionally performs more video RAM tests.
- It reads the feature connector settings and stores it in the BDA.
- Then comes the problem: it calls a function to set the VGA initial video mode. Depending on if a monochrome monitor is attached or not, this will cause it to enable a color mode or the default monochrome text mode (mode 7h). If a color monitor is attached, it will set it to mode 3h and no problems occur with software.
But if a monochrome monitor is attached, it will set it to mode 7h, which will cause the video mode sets to no longer be able to set a color mode, even with grayscale summing enabled!

Edit: My latest IDA commented disassembly of the POST routine (and some INT10h routines as well) for the VGA BIOS:
https://www.dropbox.com/scl/fi/phgqbeo7vabq6v … t=ukzjh72v&dl=0

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 24 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

OK. Checking the ET4000/W32i BIOS, I see something weird:
the documentation mentions the reading of the monitor ID pins, but somehow, instead of reading the monitor ID pins using the switch sense pin (as documented) combined with the feature control register reads (whose bits 2-5 return the ID2-3 and some extra pins), masking off the 4-5 pins, and then uses that for a lookup table to determine the switch sense/feature bits byte at the BDA (offset 88h).
So it somehow reads the feature 0-1 pins as the ID0/ID1 pins for some weird reason (and aborts reading the higher pins if the result is 01h for the lower 2 bits).

Edit: It looks like the ET4000AX BIOS does the exact same thing. So it's something common to the chipset.
Modifying those bits to report ID0/ID1 results in 8Bh for monochrome (ID0/ID1 being 0 ID2 being 1) and 89h when color (switches 0110b).
Although oddly, it reports the top bit set for both cases?
Looking into the lookup table it uses to convert the looked up value returned from the feature ID function has the following results:
index=(base) address=value
0=33B 33E=00
1=341 344=01
2=347 34A=03
3=34D 350=43 =03h
4=353 356=04
5=359 35C=05
6=35f 362=06
7=365 368=07
8=36B 36E=09
9=371 374=49 =09h
A=377 37A=0A
B=37D 380=0B
C=383 386=83
D=389 38C=C3 = 83h
E=38f 392=89
F=395 398=C9 = 89h
the output bit 6 is cleared in the result. So those starting with C are actually starting with 8. And those starting with 4, start with 0.

Looking more into what's fed into it. It all starts with the feature control reads.
It can become AX=10h for feature bits 01b read.
It can otherwise become C30h for both set while read.
It's 0 otherwise.

CX is always 0 due to reading the switches from the ID pins, so the top bit in the lookup table is never cleared. So those are the actual lookup values from the ID pins using the feature control input and the top 2 bits from register 3CAh.

So the switches I'll need to cases 9 and B, are actually:
9 is just 9 (SW1 and SW2 on). nice.
B is B (SW3 on). nice.

But, the switch decoding logic is flawed. Since most cases are actually invalidated during reads, color mode has only SW0 set SW1 clear, but it results in the final entry, thus 89h. It sets feat3, but there's no other way.

Edit: Went with the classic switches of SW2 for monochrome and SW1 for color monitors, as is documented. That extra bit in the feature bits can't be helped, it seems a bug in the Tseng BIOS ROMs.
Other than that, the 'monochrome' mode is interesting. Grayscale summing is applied, although not everywhere. Prince of Persia seems to be proper greyscale, but Jazz Jackrabbit for example is only truly driving grayscale on the main menu and while loading the world, all else being in normal color. Even the main menu is in actual color, once you choose an option for a fraction of a second. That can be seen by POSTing with a monochrome monitor and then changing it to a color monitor.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 25 of 25, by superfury

User metadata
Rank l33t++
Rank
l33t++

Something slightly related that I've implemented just now is that the lower 2 bits of the initial mode is actually latched by the hardware when REST goes from low to high (in other words, the ISA's reset finishes. Although I've implemented it when the reset is started instead, as I have no other inputs to drive it at the hardware level right now). So the lower 2 bits of the ID aren't updating on the feature connector inputs after reset has finished, while the upper 2 ID pins do actually update still.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io