Author Topic: Can someone take a look at this VESA graphics code and tell me what's wrong?  (Read 12218 times)

Offline ben321

  • Full Member
  • **
  • Posts: 185
I used Photoshop (along with a palette file with the correct VGA palette) and converted this Mario game screenshot I found online to 640x400 with 256 colors (for VESA mode 0x100) and saved it as raw (resulting image file contains color palette indexes). I then used HxD hex editor to split it into 4 files of 64KiB each (except for the last part which was 58KiB).  I then wrote all the code in ASM to create an EXE file with the image data embedded (each image part file given a separate section of the EXE file). I tested it in the latest release of DosBox. I thought I did everything by the book, but it's not working completely. The resulting image displayed at first appears to be normal, but then you notice in the sky near the top of the image that there's a couple short black lines, that look as if the system is somehow writing data back over the image data after the image data is written. I thought that the 64KiB block of system memory that maps to video RAM (addresses starting at 0xA0000) were NOT supposed to be used by any system resources that might write back over it. Yet for some strange reason, something seems to be writing back over VRAM.

I assembled the program in NASM and linked it in ALINK. The command lines I used for that are as follows.
nasm.exe -f obj -o VESATEST.OBJ VESATEST.ASM
alink.exe -oEXE -entry start -o VESATEST.EXE VESATEST.OBJ
I've attached 3 files. The source code, a copy of the image grabbed from the EXE using GIMP's raw image loader and a copy of the VGA palette (showing what it should look like), and a screenshot from DosBox (showing what it actually looks like).

If any of my code is wrong, please tell me where. I want to make sure I fix it, so I can go on to actually make use of these higher resolution graphics modes. I made sure to put comments in my code, to help anybody who wants to debug it see what each set of lines of code is supposed to do.

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Hi Ben,

I do not see anything wrong with your code. I am not in a position to test it at the moment.

What I do when I'm stumped is to modify the code, skip over sections, and see of I can identify where the problem is occurring. I would start by commenting out the copy of that last, odd sized section. If that doesn't reveal anything, put it back and remove the copy of another cevtion. This may not help you, but it shouldn't hurt. (we hope)

Long ago, when I used to fool with high-res graphics, I used to  put he CPU into "big real mode", sometimes called "voodoo mode". Best name. IMO, would be "relimited real mode". You put the CPU into protected mode, point one ot more segment registers at a descriptor with a 4G limitt, and then swap back int real mode. This lets you use BIOS interrupts again. but you can address the entire graphics memory, even though it's more than 64k. This mode does not play nicely with other modes (Windows) so you may not be able to use it (easily). Nice to be able to address the whole block of graphics at once, though...

Good luck finding the problem with your code!

Best,
Frank


Offline ben321

  • Full Member
  • **
  • Posts: 185
Hi Ben,

I do not see anything wrong with your code. I am not in a position to test it at the moment.

What I do when I'm stumped is to modify the code, skip over sections, and see of I can identify where the problem is occurring. I would start by commenting out the copy of that last, odd sized section. If that doesn't reveal anything, put it back and remove the copy of another cevtion. This may not help you, but it shouldn't hurt. (we hope)

Long ago, when I used to fool with high-res graphics, I used to  put he CPU into "big real mode", sometimes called "voodoo mode". Best name. IMO, would be "relimited real mode". You put the CPU into protected mode, point one ot more segment registers at a descriptor with a 4G limitt, and then swap back int real mode. This lets you use BIOS interrupts again. but you can address the entire graphics memory, even though it's more than 64k. This mode does not play nicely with other modes (Windows) so you may not be able to use it (easily). Nice to be able to address the whole block of graphics at once, though...

Good luck finding the problem with your code!

Best,
Frank

The issue is actually happening in the first segment near its end, not in the last segment (the odd sized segment). There's a reason that the last segment MUST be a different size. 640x400 resolution at 8 bits per pixel, equals 256000 bytes. However the 640x400 VESA mode is broken up into 4 blocks, of 64KB (64*1024=65536 bytes) each, with the exception of the last block. 256000 is NOT an integer multiple of 65536, so the last block MUST be smaller than 64KB. It turns out that it's exactly 58KB.

Getting into protected mode and then backing back out accomplishes what exactly? How does that work differently than staying in real mode after bootup? Also getting into protected mode is a major undertaking in and of itself (even more so if you actually want working interrupts in protected mode, without which it's impossible to even do something as simple as having the software accept keystrokes from your keyboard). Backing back out of protected mode is an even more major undertaking. You need to write code undo all of the changes you used to get into protected mode in the first place. At my assembly skill level, I would consider just writing code to get INTO protected mode to be a complete piece of software in and of itself, not a stepping stone to a bigger piece of software.

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Okay. I know nothing, nothing.

Frank