Problem with VESA LFB on VMWare

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.
Post Reply
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Problem with VESA LFB on VMWare

Post by BlackIce »

Hello All,
I'm playing with my small investigation OS and got stuck with vesa lfb on VMWare. When I run my OS in the Bosch or VirtualPC it looks ok, but the same code doesn't not produce the same results on VMWare workstation. Please see the screens attached. I've spent a week reading docs/specs from different informational resources from inet, but still have no idea how to fix this. I would be very glad if someone give me some advise or at last show the general research direction. On the sreenshots is the same kernel running in different emulators.
Bosch_info.png
Bosch_gfx.png
VirtualPC_info.png
The attachment VirtualPC_gfx.png is no longer available
Thanks.
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Re: Problem with VESA LFB on VMWare

Post by BlackIce »

VirtualPC_gfx.png
VMWare_info.png
Attachments
VMWare_gfx.png
User avatar
Brendan
Member
Member
Posts: 8561
Joined: Sat Jan 15, 2005 12:00 am
Location: At his keyboard!
Contact:

Re: Problem with VESA LFB on VMWare

Post by Brendan »

Hi,

That last picture looks like the second MiB of pixel data has overwritten the first MiB of pixel data, and the third MiB of pixel data is fine. It's almost as if something is causing the 21st address line (A20) to be ignored... ;)


Cheers,

Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
User avatar
Shaun
Member
Member
Posts: 43
Joined: Mon Sep 17, 2012 3:14 am
Contact:

Re: Problem with VESA LFB on VMWare

Post by Shaun »

could you show us some pieces of the vesa drawing code?
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Re: Problem with VESA LFB on VMWare

Post by BlackIce »

Brendan wrote: That last picture looks like the second MiB of pixel data has overwritten the first MiB of pixel data, and the third MiB of pixel data is fine. It's almost as if something is causing the 21st address line (A20) to be ignored... ;)
Thanks Brendan! I've added code that enables gate A20 and now it works fine on VMWare as well! Accordingly to intel manuals, first far jump or call after switching to the protected mode should open this gate automatically. That is why I did not add the code to specially enable this gate before.
virusest wrote:could you show us some pieces of the vesa drawing code?
Yes, please:

Code: Select all

void gfx_drawRainbow()
{
    const DWORD dwWidth  = g_pMode->XResolution;
    const DWORD dwHeight = g_pMode->YResolution;
    const DWORD dwColors = 4;

    DWORD dwSize = dwWidth * dwHeight * dwColors;

    DWORD dwSteps = 256 * 5;
    float fStepSize = (float)dwHeight / (float)dwSteps;

    BYTE bRed   = 255;
    BYTE bGreen = 0;
    BYTE bBlue  = 0;

    for( DWORD i = 0; i < dwSteps; i++ ) 
    {
        if( bRed == 255 && bBlue == 0 && bGreen < 255 )
            bGreen++;
        else if( bRed > 0 && bGreen == 255 && bBlue == 0 )
            bRed--;
        else if( bRed == 0 && bGreen == 255 && bBlue < 255 )
            bBlue++;
        else if( bRed == 0 && bGreen > 0 && bBlue == 255 )
            bGreen--;
        else if( bRed < 255 && bGreen == 0 && bBlue == 255 )
            bRed++;
        else if( bRed == 255 && bGreen == 0 && bBlue > 0 )
            bBlue--;

        for( DWORD y = i * fStepSize; y < fStepSize * (i+1); y++ )
        {
            for( DWORD x = 0; x < dwWidth; x++ )
            {
                gfx_putPixel( x, y, RGB( bRed, bGreen, bBlue ) );
            }
        }
    }
}

void gfx_putPixel( DWORD x, DWORD y, DWORD color )
{
    DWORD dwOffset = y * g_pMode->XResolution + x; //y * g_pMode->BytesPerScanLine + x * g_pMode->BitsPerPixel / 4;
    g_pLFB[dwOffset] = color;
}

User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Re: Problem with VESA LFB on VMWare

Post by Combuster »

BlackIce wrote:first far jump or call after switching to the protected mode should open this gate automatically. That is why I did not add the code to specially enable this gate before.
And most processors I've seen don't do that. So either that's a new feature or a misinterpretation.
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
User avatar
dozniak
Member
Member
Posts: 723
Joined: Thu Jul 12, 2012 7:29 am
Location: Tallinn, Estonia

Re: Problem with VESA LFB on VMWare

Post by dozniak »

BlackIce wrote:

Code: Select all

        for( DWORD y = i * fStepSize; y < fStepSize * (i+1); y++ )
        {
            for( DWORD x = 0; x < dwWidth; x++ )
            {
                gfx_putPixel( x, y, RGB( bRed, bGreen, bBlue ) );
            }
        }
    }
}
How long does it usually take to draw this rainbow, pixel by pixel?
Learn to read.
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Re: Problem with VESA LFB on VMWare

Post by BlackIce »

I haven't measured this :), but I think it takes a while... however on real h/w rainbow appears immediately. I just use this code to test that everything is OK with my LFB. Performance is not critical at this moment. :)
User avatar
Shaun
Member
Member
Posts: 43
Joined: Mon Sep 17, 2012 3:14 am
Contact:

Re: Problem with VESA LFB on VMWare

Post by Shaun »

BlackIce wrote:
Brendan wrote: That last picture looks like the second MiB of pixel data has overwritten the first MiB of pixel data, and the third MiB of pixel data is fine. It's almost as if something is causing the 21st address line (A20) to be ignored... ;)
Thanks Brendan! I've added code that enables gate A20 and now it works fine on VMWare as well! Accordingly to intel manuals, first far jump or call after switching to the protected mode should open this gate automatically. That is why I did not add the code to specially enable this gate before.
virusest wrote:could you show us some pieces of the vesa drawing code?
Yes, please:

Code: Select all

void gfx_drawRainbow()
{
    const DWORD dwWidth  = g_pMode->XResolution;
    const DWORD dwHeight = g_pMode->YResolution;
    const DWORD dwColors = 4;

    DWORD dwSize = dwWidth * dwHeight * dwColors;

    DWORD dwSteps = 256 * 5;
    float fStepSize = (float)dwHeight / (float)dwSteps;

    BYTE bRed   = 255;
    BYTE bGreen = 0;
    BYTE bBlue  = 0;

    for( DWORD i = 0; i < dwSteps; i++ ) 
    {
        if( bRed == 255 && bBlue == 0 && bGreen < 255 )
            bGreen++;
        else if( bRed > 0 && bGreen == 255 && bBlue == 0 )
            bRed--;
        else if( bRed == 0 && bGreen == 255 && bBlue < 255 )
            bBlue++;
        else if( bRed == 0 && bGreen > 0 && bBlue == 255 )
            bGreen--;
        else if( bRed < 255 && bGreen == 0 && bBlue == 255 )
            bRed++;
        else if( bRed == 255 && bGreen == 0 && bBlue > 0 )
            bBlue--;

        for( DWORD y = i * fStepSize; y < fStepSize * (i+1); y++ )
        {
            for( DWORD x = 0; x < dwWidth; x++ )
            {
                gfx_putPixel( x, y, RGB( bRed, bGreen, bBlue ) );
            }
        }
    }
}

void gfx_putPixel( DWORD x, DWORD y, DWORD color )
{
    DWORD dwOffset = y * g_pMode->XResolution + x; //y * g_pMode->BytesPerScanLine + x * g_pMode->BitsPerPixel / 4;
    g_pLFB[dwOffset] = color;
}

thanks a lot for your sharing.

i have a question, where does your g_pLFB point to?
0xA0000 in protected mode if you use banked mode, or
0xd0000000(VMware),0xe0000000(bochs) if you enable bit 14 in mode number when you move to graphic mode ?

if the later case, did you map 0xe0000000 to a valid place?
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Re: Problem with VESA LFB on VMWare

Post by BlackIce »

g_pLFB is a pointer to linear frame buffer, it points directly to the video memory and initialized by 0xD0000000 for VMWare, etc... I do not use banked mode. Bit 14 was enabled upon initialization - that's indicates linear frame buffer mode.

I do not use any special mapping. My small kernel doesn't use paging at all. I've just created flat data segment with base 0 and limit 4Gb.
User avatar
Shaun
Member
Member
Posts: 43
Joined: Mon Sep 17, 2012 3:14 am
Contact:

Re: Problem with VESA LFB on VMWare

Post by Shaun »

BlackIce wrote:g_pLFB is a pointer to linear frame buffer, it points directly to the video memory and initialized by 0xD0000000 for VMWare, etc... I do not use banked mode. Bit 14 was enabled upon initialization - that's indicates linear frame buffer mode.

I do not use any special mapping. My small kernel doesn't use paging at all. I've just created flat data segment with base 0 and limit 4Gb.

thanks again, i got it. your posts really do me a big favor and settle a puzzle which stuck me for a long time up.

sorry for my poor English, by the way, do you have any ideas about displaying picture in grapic mode?
BlackIce
Posts: 8
Joined: Fri Feb 08, 2013 9:58 am

Re: Problem with VESA LFB on VMWare

Post by BlackIce »

Well, it depends on your needs. At first it looks so trivial: you should copy array of color data into screen memory. Digging into details you've probably heard about stuff like creating off-screen surfaces, clipping, scaling/stretching, texture filtering, bit blitting. That's all you need to consider to have your picture correctly displayed in some frame.

...I see that RGB macro stolen from wingdi.h doesn't work well for vesa. All my rainbows are inverted. The actual position of each color component should be taken from mode info structure...
User avatar
Griwes
Member
Member
Posts: 374
Joined: Sat Jul 30, 2011 10:07 am
Libera.chat IRC: Griwes
Location: Wrocław/Racibórz, Poland
Contact:

Re: Problem with VESA LFB on VMWare

Post by Griwes »

BlackIce wrote:The actual position of each color component should be taken from mode info structure...
Remember: not only position, but also size. I've made a mistake of forgetting about using size fields, and I kept getting light purple text instead of grey one in 16bit mode :D
Reaver Project :: Repository :: Ohloh project page
<klange> This is a horror story about what happens when you need a hammer and all you have is the skulls of the damned.
<drake1> as long as the lock is read and modified by atomic operations
Post Reply