VGA programming problems

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
User avatar
iansjack
Member
Member
Posts: 4703
Joined: Sat Mar 31, 2012 3:07 am
Location: Chichester, UK

Re: VGA programming problems

Post by iansjack »

It seems to be a very common mistake to not load enough sectors. The answer to this is to keep your kernel in some object format (normally elf) so that the loader knows how much text and variable space to load, and how much space to set aside for uninitialized variables.
abstractmath
Member
Member
Posts: 46
Joined: Mon Sep 07, 2020 5:50 pm

Re: VGA programming problems

Post by abstractmath »

Okay, so one last question: I'm putting my video mode into 320 x 200 with an 8 bit color depth. Shouldn't this mean I get 256 different colors? Because from what I can see, there's only 64 actual colors that get displayed on screen and I don't really understand how I can access all 256 colors, instead of just the 64 that I seem to be able to get.
Octocontrabass
Member
Member
Posts: 5572
Joined: Mon Mar 25, 2013 7:01 pm

Re: VGA programming problems

Post by Octocontrabass »

VGA is kinda funny because it's backwards compatible with EGA, which itself is somewhat backwards compatible with CGA.

CGA was capable of 16 colors. EGA was capable of 64 colors, so EGA added an attribute controller to map the 16 CGA colors to the 64 EGA colors when running in a CGA-compatible mode. VGA was capable of 262,144 colors, so VGA added a palette controller to map those 64 EGA colors to the 262,144 VGA colors when running in an EGA-compatible mode.

The BIOS sets a CGA-compatible text mode before handing control to your bootloader. This means the attribute controller is configured to map 16 CGA colors to 64 EGA colors, and the palette controller is configured to map 64 EGA colors to 262,144 VGA colors.

Your code doesn't touch the palette controller at all, so it's still set up to output the 64 EGA colors.
User avatar
bzt
Member
Member
Posts: 1584
Joined: Thu Oct 13, 2016 4:55 pm
Contact:

Re: VGA programming problems

Post by bzt »

I think you are little bit confused about video cards and their capabilities.
Octocontrabass wrote:CGA was capable of 16 colors.
Nope. CGA: "CGA uses a 16-color gamut, but not all colors are available at all times".
Octocontrabass wrote:EGA was capable of 64 colors, so EGA added an attribute controller
Again, no, EGA: "EGA produces a display of up to 16 colors". It introduced the palette, which had 2 bits per channel, thus giving 4*4*4 = 64 possible colors, but you could only use 16 of them at any given time.
Octocontrabass wrote:VGA was capable of 262,144 colors, so VGA added a palette controller
Nope and nope. VGA was capable of 256 colors tops, and palette was already introduced with the EGA. It is true that in VGA there's 6 bits per channel, thus giving 64*64*64 = 262,144 possible colors, but just as with CGA and EGA, the VGA card was unable to use all those colors at all times.

It was the SVGA mode (standardized by VESA) that first was capable of displaying 65536 colors (using 16 bits 5/6/5 bits packed pixel format without DAC). And that's still less than 262144!
Octocontrabass wrote:The BIOS sets a CGA-compatible text mode before handing control to your bootloader.
Nope again. BIOS sets a VGA-compatible text mode, which means even though the buffer starts at 0xB8000 as with CGA, the attributes are handled differently for CGA text mode (CGA had configurable blinking/intensity bit, while VGA has a configurable intensity/font map selector bit, allowing 512 glyphs). And also while the attributes index a 16 colors palette of 2x2x2 channels on EGA, on VGA they index 6x6x6 channels. By programming the DAC, you can have a nice and smooth fade in/out effect in VGA text mode, something impossible with CGA or EGA.
Octocontrabass wrote:This means the attribute controller is configured to map 16 CGA colors to 64 EGA colors, and the palette controller is configured to map 64 EGA colors to 262,144 VGA colors.
This absolutely not true. There are only 16 possible colors in the EGA palette, and 256 in VGA. By default the VGA palette's first 16 color used the same values as the EGA palette's channels shifted by 4 (meaning the first 16 VGA colors looked exactly as the EGA colors), and the rest had a rainbow-like mapping.
Octocontrabass wrote:Your code doesn't touch the palette controller at all, so it's still set up to output the 64 EGA colors.
Nope, if you don't touch the DAC registers, then VGA is still set up to use all available 256 colors. The default palette is backward compatible with EGA, meaning the first 16 colors encode the same colors. The next 16 colors (16-31) encode a grayscale gradient, not possible with EGA, and colors 32-63 are also different than what the full EGA channels would produce.

Cheers,
bzt
thewrongchristian
Member
Member
Posts: 426
Joined: Tue Apr 03, 2018 2:44 am

Re: VGA programming problems

Post by thewrongchristian »

I guess the upshot of all this is just leave VGA in the past, and especially forget about programming VGA registers, for the following reasons:
  • - VGA is obsolete. It came out in 1987, and was hardly cutting edge then.
    - Modern GFX may not be VGA compatible, hiding behind SVGA BIOS or EFI.
    - Default VGA frame buffer mapping is frankly a PITA. Any GFX card you'll have contact with will provide a flat framebuffer.
    - VGA resolutions higher than 320x200 are plane based, and limited to a pallette of 16 colours.
    - Modern GFX have nice big resolutions and RGB pixels.
In terms of loading your kernel properly, unless you're interested in doing a bootloader, don't bother. Just link your kernel as a multiboot ELF kernel, and offload the loading of it to an existing bootloader, which can also set you up with a nice linear framebuffer as well.
User avatar
bzt
Member
Member
Posts: 1584
Joined: Thu Oct 13, 2016 4:55 pm
Contact:

Re: VGA programming problems

Post by bzt »

thewrongchristian wrote:I guess the upshot of all this is just leave VGA in the past, and especially forget about programming VGA registers, for the following reasons:
  • - VGA is obsolete. It came out in 1987, and was hardly cutting edge then.
    - Modern GFX may not be VGA compatible, hiding behind SVGA BIOS or EFI.
    - Default VGA frame buffer mapping is frankly a PITA. Any GFX card you'll have contact with will provide a flat framebuffer.
    - VGA resolutions higher than 320x200 are plane based, and limited to a pallette of 16 colours.
    - Modern GFX have nice big resolutions and RGB pixels.
You're absolutely right. Plus one reason: under UEFI, text mode and palette modes don't exists any more, only linear framebuffer with RGB pixels available.
thewrongchristian wrote:In terms of loading your kernel properly, unless you're interested in doing a bootloader, don't bother. Just link your kernel as a multiboot ELF kernel, and offload the loading of it to an existing bootloader, which can also set you up with a nice linear framebuffer as well.
You can also try BOOTBOOT, which also sets up a framebuffer for you regardless to the platform (either be BIOS VBE, UEFI GOP, RPi VC, etc. you don't have to care). It also maps the buffer where your kernel wants it to be.

Cheers,
bzt
Octocontrabass
Member
Member
Posts: 5572
Joined: Mon Mar 25, 2013 7:01 pm

Re: VGA programming problems

Post by Octocontrabass »

bzt wrote:Nope. CGA: "CGA uses a 16-color gamut, but not all colors are available at all times".
I didn't say all the colors were available at the same time, but in text mode, all 16 colors are indeed available at the same time.
bzt wrote:Again, no, EGA: "EGA produces a display of up to 16 colors". It introduced the palette, which had 2 bits per channel, thus giving 4*4*4 = 64 possible colors, but you could only use 16 of them at any given time.
Again, I didn't say all the colors were available at the same time. Wikipedia is referring to the attribute controller, which is also present in VGA due to VGA being register-compatible with EGA.
bzt wrote:Nope and nope. VGA was capable of 256 colors tops, and palette was already introduced with the EGA. It is true that in VGA there's 6 bits per channel, thus giving 64*64*64 = 262,144 possible colors, but just as with CGA and EGA, the VGA card was unable to use all those colors at all times.
I didn't say all the colors were available at the same time. VGA introduced another palette (which doesn't seem to have a commonly-used name, although you call it the DAC), and in CGA- and EGA-compatible modes, it's used to translate the 6-bit values produced by the attribute controller into 18-bit RGB. Mode 13h bypasses the attribute controller and the values written to memory are sent directly to the palette controller (DAC?) untranslated.
bzt wrote:Nope again. BIOS sets a VGA-compatible text mode, which means even though the buffer starts at 0xB8000 as with CGA, the attributes are handled differently for CGA text mode (CGA had configurable blinking/intensity bit, while VGA has a configurable intensity/font map selector bit, allowing 512 glyphs).
No, the attributes are handled the same. The font select introduced in EGA uses the foreground intensity bit. Blinking uses the background intensity bit.
bzt wrote:And also while the attributes index a 16 colors palette of 2x2x2 channels on EGA, on VGA they index 6x6x6 channels. By programming the DAC, you can have a nice and smooth fade in/out effect in VGA text mode, something impossible with CGA or EGA.
The 16 text-mode attributes still index 64 colors on EGA and VGA; VGA just adds another translation step in the DAC.
bzt wrote:This absolutely not true. There are only 16 possible colors in the EGA palette, and 256 in VGA. By default the VGA palette's first 16 color used the same values as the EGA palette's channels shifted by 4 (meaning the first 16 VGA colors looked exactly as the EGA colors), and the rest had a rainbow-like mapping.
Please re-read the section you linked. The VGA ROM configures the DAC differently depending on the mode. The rainbow palette only appears if you use the VGA ROM to set mode 13h. When you set the registers yourself, you'll see whichever colors were last programmed into the DAC, unless you also program the DAC.
bzt wrote:The default palette is backward compatible with EGA, meaning the first 16 colors encode the same colors.
In EGA-compatible modes, the DAC is programmed to output the 64 EGA colors, so that software expecting EGA could reprogram the attribute controller to select any of the 64 EGA colors.
nexos
Member
Member
Posts: 1081
Joined: Tue Feb 18, 2020 3:29 pm
Libera.chat IRC: nexos

Re: VGA programming problems

Post by nexos »

As has been said before, leave VGA behind. Use VBE or GOP. Also, developing a bootloader is a pain. You could try using NexBoot, which sets up a VBE framebuffer, and can load multiple OSes. Plus, UEFI support is coming very soon. Hope that isn't spamming...
"How did you do this?"
"It's very simple — you read the protocol and write the code." - Bill Joy
Projects: NexNix | libnex | nnpkg
User avatar
Octacone
Member
Member
Posts: 1138
Joined: Fri Aug 07, 2015 6:13 am

Re: VGA programming problems

Post by Octacone »

nexos wrote:As has been said before, leave VGA behind. Use VBE or GOP. Also, developing a bootloader is a pain. You could try using NexBoot, which sets up a VBE framebuffer, and can load multiple OSes. Plus, UEFI support is coming very soon. Hope that isn't spamming...
That is bullshit! Developing a bootloader is not hard!
Stop discouraging people from doing custom stuff. (All of you)
I was learning Assembly and writing my bootloader along the way.
It still works to this day and can boot on real hardware without any problems.

To OP:
Leave VGA behind. You should either use VBE (By utilizing a virtual 8086 monitor) or write a proprietary driver (not impossible for Intel HD Graphics).
OS: Basic OS
About: 32 Bit Monolithic Kernel Written in C++ and Assembly, Custom FAT 32 Bootloader
nexos
Member
Member
Posts: 1081
Joined: Tue Feb 18, 2020 3:29 pm
Libera.chat IRC: nexos

Re: VGA programming problems

Post by nexos »

Developing a BIOS bootloader isn't. Now a UEFI one, well that is a different story.
"How did you do this?"
"It's very simple — you read the protocol and write the code." - Bill Joy
Projects: NexNix | libnex | nnpkg
kzinti
Member
Member
Posts: 898
Joined: Mon Feb 02, 2015 7:11 pm

Re: VGA programming problems

Post by kzinti »

nexos wrote:Developing a BIOS bootloader isn't. Now a UEFI one, well that is a different story.
No it is not hard to write a UEFI bootloader. If anything it is easier than a BIOS one.

The main difficulty comes from using gnuefi: don't use it. It's garbage.
abstractmath
Member
Member
Posts: 46
Joined: Mon Sep 07, 2020 5:50 pm

Re: VGA programming problems

Post by abstractmath »

Right, so I will not be using a pre-made bootloader. I'm doing this for learning purposes. I'm also confused about why I'm not getting the full 256 colors. Do I need to change the palette controller or not?
Octocontrabass
Member
Member
Posts: 5572
Joined: Mon Mar 25, 2013 7:01 pm

Re: VGA programming problems

Post by Octocontrabass »

abstractmath wrote:I'm also confused about why I'm not getting the full 256 colors.
The BIOS has programmed the palette controller (DAC?) to produce 64 EGA colors.
abstractmath wrote:Do I need to change the palette controller or not?
If you want 256 unique colors, yes.
User avatar
bzt
Member
Member
Posts: 1584
Joined: Thu Oct 13, 2016 4:55 pm
Contact:

Re: VGA programming problems

Post by bzt »

abstractmath wrote:I'm also confused about why I'm not getting the full 256 colors. Do I need to change the palette controller or not?
No, of course you don't need to change the palette controller. What you need to change is the mode. For VGA you can have either a mode with 16 colors, or with 256 colors, no other options exists (there's no such thing as 64 color mode, and BIOS was never programmed to produce 64 EGA colors. In 256 mode VGA maps the first 16 entry in the palette to the same RGB values as the default EGA 16 colors, that's where the compatibility ends. The remaining 240 colors has nothing to do with EGA).

Try these sources:
XFree86, it has a properly working VGA driver (and also some SVGA drivers). Well commented C source.
FreeVGA's source
kzinti wrote:No it is not hard to write a UEFI bootloader. If anything it is easier than a BIOS one.
I've several decades of experience with developing bare metal and pre-OS environments. If anything UEFI is the worst of all for several reasons. Linus is right on this one, BIOS is much much simpler.
kzinti wrote:The main difficulty comes from using gnuefi: don't use it. It's garbage.
Again, with my experience quite the contrary. If you're not your own enemy, then forget that bloated EDK, that's garbage and use only gnuefi. Not only your build environment will be simpler and faster, but the resulting code is going to be a lot smaller. The one and only difficulty gnuefi adds is the need of uefi_call_wrapper() in your code, little price for all the benefits! Gnuefi does not make UEFI coding difficult! Stupid interfaces, badly designed protocols and buggy hardware do!

Disclaimer: I'm not affiliated with gnuefi in any way, I'm an independent third party who have tried both. My opinion on this is strictly from technical and usability point of view.

Cheers,
bzt
nexos
Member
Member
Posts: 1081
Joined: Tue Feb 18, 2020 3:29 pm
Libera.chat IRC: nexos

Re: VGA programming problems

Post by nexos »

For UEFI, I use a MinGW toolchain on Linux and then use the gnu-efi headers to access the interface. It works for me.
"How did you do this?"
"It's very simple — you read the protocol and write the code." - Bill Joy
Projects: NexNix | libnex | nnpkg
Post Reply