Quantcast
Channel: Confusion in Memory segmentation in x86 - Stack Overflow

Answer by Jester for Confusion in Memory segmentation in x86

$
0
0

Make sure it isn't a memory reference accidentally. Since your gdb output seems like at&t, it would normally show a $ for immediates. As such, it's suspicious that what you really have is loading bx with the content of memory at address 0xb800. Can you check the machine code?

The machine code is 0xb8001e8b

Indeed, that's machine code for loading from memory. Looking at the as86 manual, you can see:

#      Prefix for immediate operands.       mov ax,#1234       Immediate value, ax becomes 1234.

As such, you should prefix your immediates with a # sign. Note this applies to all immediates.

While this fixes the problem you asked about, see @amdn's answer for other issues you have.


Answer by amdn for Confusion in Memory segmentation in x86

$
0
0

There are a couple of problems with the routine _put_in_mem, it doesn't preserve registers DS and SI which must be preserved according to 16-bit x86 calling conventions, see section 6 of this document, and it doesn't store the character and attribute bytes properly.

.global _put_in_mem_put_in_mem:push bpmov bp, spmov cx, [bp + 4]mov si, [bp + 6]   # si must be preserved across function callsmov bx, 0xb800mov ds, bx         # ds must be preserved across function callsmov [si], cxadd bx, 0x1mov cx, 0x7        # low byte 0x7, upper byte = character = 0x00mov [si], cx       # si has not changed... overwriting with 0x0007pop bpret

Here's one way to fix it:

.global _put_in_mem_put_in_mem:push bpmov bp, spmov cx, [bp + 4]   # cx = xxcc, where cc is ASCII charactermov ch, 0x7        # attribute byte: light-grey on blackmov bx, [bp + 6]   # bx = offset into VGA video buffermov ax, 0xb800     # VGA video buffer base at 0xb800 x 16mov es, ax         # use ES segment register instead of DSmov es:[bx], cx    # store ASCII at es:[bx], attribute at es:[bx+1]pop bpret

The VGA attribute byte follows the character byte in text mode. An attribute of 0x7 means to display as light-grey on black background... see http://wiki.osdev.org/Printing_To_Screen and http://en.wikipedia.org/wiki/VGA-compatible_text_mode

Confusion in Memory segmentation in x86

$
0
0

Here I made a code for writing ASCII characters into VGA Memory:

.global _put_in_mem_put_in_mem:push bpmov bp, spmov cx, [bp + 4]mov si, [bp + 6]mov bx, 0xb800mov ds, bxmov [si], cxadd bx, 0x1mov cx, 0x7mov [si], cxpop bpret

This is called through a kernel.c file shown below:

void main(){ extern void put_in_mem(); char c = 'e'; put_in_mem(c, 0xA0);}

The above code was meant to print "e" on the beginning of the second line in QEmu, but it did not. I tried to debug this using GDB and found that the command

mov bx, 0xb800

in GDB has become

mov    -0x4800,%bx

and the value in ebx after this command is 0x0.
Why has the value not loaded in the bx register?

Further, I thought that the move instructions use ds register as their segment base and offset all the addresses from the contents of ds. So according to this reasoning, I assumed that when

mov [si], cx

instruction the contents of cx register will be placed at the address 0xb8a0. Is this correct? Can mov instruction be affected by any other segement registers (like cs, es etc.) as well?



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>