• Please review our updated Terms and Rules here

Accessing VRAM in tiny model .com program for MSDOS

if save_DS is a memory location, and your just a .COM, you probably want

cs: mov ax, save_DS

because you have no idea where DS is currently set.
 
mov ax,save_DS

This needs to be a memory var in your code segment, because you don't know what any register is set to once control is passed back. So save_DS needs to be in your code segment somewhere, and the line above should be "CS: mov ax,SAVE_DS" as previously mentioned. (And saving it would be the same, like "mov ax, ds / CS: mov SAVE_DS,ax"
 
if save_DS is a memory location, and your just a .COM, you probably want

cs: mov ax, save_DS

because you have no idea where DS is currently set.

This needs to be a memory var in your code segment, because you don't know what any register is set to once control is passed back. So save_DS needs to be in your code segment somewhere, and the line above should be "CS: mov ax,SAVE_DS" as previously mentioned. (And saving it would be the same, like "mov ax, ds / CS: mov SAVE_DS,ax"

Thanks a lot!. I got errors compiling in TASM, there is probably a different syntaxis for this in every assembler.

EDIT: in TASM it works like this: mov CS:[save_DS],ds. Thanks again, it seems to work as intended now, and I managed to reduce the .com size (and ram usage) to 1.5K, that's awesome :).
 
Last edited:
Well, if you assume that there's a stack to service interrupts, there's probably a word available for storing DS. If you're allowing interrupt service, the situation becomes, er, interesting...

If you save DS onstack, then it becomes possible to create a reentrant bit of code.
 
Completely outside the box here but potentially useful...a common trick with menu programs was to use a batch file wrappers. For example:

menu.bat
Code:
:start
menuprog.exe
if errorlevel 1 goto end
cls
call run.bat
goto start
:end

run.bat
Code:
cd\progdir
prog.exe
cd\menudir

The user runs menu.bat. The menu program creates run.bat when the user selects a program to run. If the user wants to exit the menu, the menu program returns 1.

With this method, your menu program can be as large as you want because it's not resident while the selected program is running.
 
True, but the downside to this trick is that the entire menu program has to reload every time. If it's small and doesn't do much, that's not usually a problem. (If it is a problem, there's always Ralf Brown's SWAPPO library.)
 
Code is here: source. it was done in c by jsmolina, then I wanted to convert it to assembly, just for fun, and to use little ram.

It can be done better, or faster... But speed is not a problem, the program is always stuck waiting for a key press.
If I add a wait_vsync function before drawing things I can remove the CGA snow (I copied a little function from Trixter, but I think waiting for vertical retrace, is good enough for this). It is a bit slower, but it does not matter, the goal here was to fit in 1 or 2KB so that it does not mess with games or programs. I could also remove the map array, and read it from a file, but I don't think 300 bytes would make any difference in ram.
 
Last edited:
No high-level language can beat that, at least not on this age/capabilities of CPU.
Also a great example of why zero/null termination on x86 is slow rubbish. On top of how often it goes bits-up face-down in terms of memory overflows, unending writes, security woes, etc. etm.

Code:
msg:    db 5, 'Howdy'
...

    mov   ax, 0xB800
    mov   es, ax
    mov   si, offset msg
    lodsb
    xor   cx, cx
    mov   cl, al
    mov   ah, 0x07
.rep:
    lodsb
    stosw
    loop .rep
 
Back
Top