I am trying to make a custom cursor for my 32-bit OS and would like to know how to offset a memory address (0xb800 for text) by a variable (0xb8000+XVAR). I tried the following but the text just diapered off my screen:
mov al, ' '
mov ah, 0xff
mov edx, 0xb8000+160*3
add edx, CURSORX
mov word [edx], ax
For anyone that needs to know, this is what it looks like without trying to offset: And this is what it looks like when I try to offset: Best regards, Markian.
mov al, ' ' mov ah, 0xff mov edx, 0xb8000+160*3 add edx, CURSORX mov word [edx], ax
The add edx, CURSORX
instruction is adding the offset address of the CURSORX variable! To add the value of your variable proper, you must use the square brackets in NASM.
If the mov word [edx], ax
instruction works fine (you say without the add
it does), it is because the DS segment register is 0. Because your code snippet solely depends on the DS segment register (which is 0), make sure that the offset that NASM gives to the CURSORX variable is also relative to that same zero.
If this is bootloader code and you used an [ORG 0x7C00]
directive, all would have been fine (segment-wise).
But if you have used [ORG 0]
, then make ES=0x07C0
and use a segment override on add edx, [es:CURSORX]
.
In comments you mention that CURSORX is a byte. You need to extend the byte before using it in the dword-sized addition.
movzx edx, byte [es:cursorx]
mov word [0xB8000 + 160 * 3 + edx], 0xFF20
And if your 'cursor offset' is expressed in characters, then don't forget to double it before using, because of how the text video memory is organized (character byte, attribute byte)
movzx edx, byte [es:cursorx]
mov word [0xB8000 + 160 * 3 + edx * 2], 0xFF20