How many dumb questions are we allowed. Here is my first.
I've been playing around with some bootloader code I have downloaded, and there is something I just can't seem to figure out. I'm sure it is a segment thing and have read all I can find on segmented memory, but I still don't get it.
How come the following code works
JMP 0800:0000
where this does not:
JMP 0800
This is called after the kernel is loaded by means of
MOV AH, 02h ; read sector from floppy
MOV AL, 1 ; one sector
MOV CH, 0 ;
MOV CL, 2 ; sector 2
MOV DH, 0 ; head
MOV DL,0 ; floppy
MOV BX,0800h
MOV ES, BX
MOV BX, 0
INT 13h
Earlier in the boot code, DS is set equal to CS. Also notice the MOV BX,0800.
Can someone tell me exactly what is going on with the JMP. Appearently MOV BX,0800 and then later JMP 0800:0000 are the same address (becuase it works), but I do not get it.
So what physical address are we talking about here also. The boot code (as always) starts at 7C00. What is CS in this case (becuase DS get set to the same thing)?
Basically what I am after is to understand how to address all 640K within real-mode. And how we manipulate DS to help us do that?
Mark
real mode, segments, and NASM?
- Pype.Clicker
- Member
- Posts: 5964
- Joined: Wed Oct 18, 2006 2:31 am
- Location: In a galaxy, far, far away
- Contact:
Re:real mode, segments, and NASM?
jmp 0800:0000 == jmp <segment>:<offset> (linear address = 0x8000 + 0)
jmp 0800 == jmp <near offset> = jmp <current CS value>:0800
There are 2 common start address for the boot sector: either 0000:7C00 or 07C0:0000, depending on your BIOS. Yeah, i know, it suxx, but that's the way it is. The only way you can get rid of this dependency is by enforcing the location yourself:
jmp 0800 == jmp <near offset> = jmp <current CS value>:0800
There are 2 common start address for the boot sector: either 0000:7C00 or 07C0:0000, depending on your BIOS. Yeah, i know, it suxx, but that's the way it is. The only way you can get rid of this dependency is by enforcing the location yourself:
Code: Select all
org 0x7C00
jmp 0000:there
there: ;; nasm will assume its first byte has the offset 7C00, so the offset of "there" will be fine in the jump. Check it using your disassembler if you doubt.
;; the real boot sector starts here and *knows* CS=0 and IP=7C00 :)
Re:real mode, segments, and NASM?
Au - so maybe it is the BIOS call I was not understanding.
MOV BX,0800
must be telling the bios interupt the segment, not the offset.
_mark()
MOV BX,0800
must be telling the bios interupt the segment, not the offset.
_mark()
Re:real mode, segments, and NASM?
OR
ES = 0800
BX = 0
Rather.
So in this case (I still have to go read up on int13), but ES must be used to specify the segment.
Thanks
_mark()
ES = 0800
BX = 0
Rather.
So in this case (I still have to go read up on int13), but ES must be used to specify the segment.
Thanks
_mark()
- Pype.Clicker
- Member
- Posts: 5964
- Joined: Wed Oct 18, 2006 2:31 am
- Location: In a galaxy, far, far away
- Contact:
Re:real mode, segments, and NASM?
look closer at your code !
what you give to the BIOS is es=0800 and bx=0000, but there is no mov <segment>,<constant> instruction in x86, so you must put the constant in a generic-purpose register and then MOVe it back to the segment register.
Code: Select all
mov bx,0800
mov es,bx
mov bx,0
Re:real mode, segments, and NASM?
That's right, the code is loading the kernel at 0x800:0x0 and then the jmp is jumping to the same address (0x800:0x0).
A simple jmp 0x800 instruction jumps to the offset 0x800 is the current code segment, so this has nothing to do with your kernel address.
A simple jmp 0x800 instruction jumps to the offset 0x800 is the current code segment, so this has nothing to do with your kernel address.