Page 1 of 1

Cannot understand why unreal mode works

Posted: Sun Oct 28, 2007 3:35 pm
by madeofstaples
Ok, I need to enter unreal mode to access more than 64kb's above 1MB (right?).

A20 needs to be enabled, of course, (though you can access every odd MB without it, I guess).

First of all, does it matter WHEN I enter unreal mode with respect to when I enable A20? (from the wiki example, it appears A20 is not enabled to enter unreal mode, but can it be beforehand?)

In the example code on http://www.osdev.org/wiki/Unreal_Mode, why are these things necessary?:

First,

Code: Select all

push ds      ; save real mode
("save real mode"? what??)

Code: Select all

mov  bx, 0x08   ; select descriptor 1
mov  ds, bx   ; 8h = 1000b
The above causes the processor to load the information for descriptor 1 in the GDT, right?
Do I need to also "mov es, bx" if I want to access above 1MB with es?

So then when we switch back to real mode, why this??

Code: Select all

pop ds      ; get back old segment
Doesn't that cause the CPU to NOT use the information from descriptor 1? since (ds&0xF8)!=0x08? (i.e, descriptor 1 is NOT selected??)

When I searched the forums I found this post which confused me even more!
Candy wrote:It's the theory behind unreal mode by the way - you load the segment registers in pmode (loading the second unwritable half with the pmode-valid information) which is never changed back - so if you index with eax or ecx in realmode the offsets aren't invalid (since it checks the pmode-style register just without reloading them for realmode values, so you keep the old limit and base) and you can access 4GB of information. Which also explains the BIOS warning - if your BIOS functions reload the segment register, you're screwed. They also don't use 32-bit offsets.
So, it sounds like after switching back to real mode, touching any segment registers ruins my ability to access the extra memory??? Which goes back to my question about the wiki code...

Also, maybe I'm missing something in the Intel Manual... How does the processor use segment registers when you try to access a 32-bit offset? (or, why does unreal mode allow 32-bit offsets to be used?)

Re: Cannot understand why unreal mode works

Posted: Sun Oct 28, 2007 10:21 pm
by Dex
I do not use un-realmode any more, but i used too, so here goes:

1. you can enable A20 first, yes.
The above causes the processor to load the information for descriptor 1 in the GDT, right?
2. Yes.
Do I need to also "mov es, bx" if I want to access above 1MB with es?
3. Yes.
So then when we switch back to real mode, why this??

Code: Select all

pop ds      ; get back old segment
Doesn't that cause the CPU to NOT use the information from descriptor 1? since (ds&0xF8)!=0x08? (i.e, descriptor 1 is NOT selected??)
4. No, Changing a segment register in real (or unreal) mode
changes only the segment base. The limit, which was set to 0xFFFFF
during our brief visit to protected mode, remains unchanged.

Re: Cannot understand why unreal mode works

Posted: Mon Oct 29, 2007 10:57 am
by madeofstaples
Dex wrote:I do not use un-realmode any more, but i used too, so here goes:

1. you can enable A20 first, yes.
It is my understanding that it is necessary to enter unreal mode temporarily in the boot process in order to load the kernel to anywhere above 1MB+64kb? Or am I making a mountain out of a mole hill?

This brings up a new question about the granularity bit of the GDT used to enter unreal mode. In the wiki example, it's set to 0, or 1 byte granularity... but with only 20 bits for a limit, that only gives access to... the first MB of memory?? which we already HAVE access to? Should granularity be set to 1?
Dex wrote:
The above causes the processor to load the information for descriptor 1 in the GDT, right?
2. Yes.
Do I need to also "mov es, bx" if I want to access above 1MB with es?
3. Yes.
So then when we switch back to real mode, why this??

Code: Select all

pop ds      ; get back old segment
Doesn't that cause the CPU to NOT use the information from descriptor 1? since (ds&0xF8)!=0x08? (i.e, descriptor 1 is NOT selected??)
4. No, Changing a segment register in real (or unreal) mode
changes only the segment base. The limit, which was set to 0xFFFFF
during our brief visit to protected mode, remains unchanged.
Here is where I'm confused. I bet I just have some misconception about how the processor works... are there specific parts of the intel manual i should be reading, or any other resources you've accumulated for your work in unreal mode? I'd appreciate it a lot.

Thanks

Re: Cannot understand why unreal mode works

Posted: Mon Oct 29, 2007 11:11 am
by JAAman
madeofstaples wrote: It is my understanding that it is necessary to enter unreal mode temporarily in the boot process in order to load the kernel to anywhere above 1MB+64kb? Or am I making a mountain out of a mole hill?
no -- its not required, it is one way of doing t, but not the only way (or even necessarily the best way... but thats more a matter of style) -- you can also write a PMode driver (which is what a lot of people do), or load your kernel below 1MB, or (if your loading less than 64k, you can load it above 1MB in RMode)
This brings up a new question about the granularity bit of the GDT used to enter unreal mode. In the wiki example, it's set to 0, or 1 byte granularity... but with only 20 bits for a limit, that only gives access to... the first MB of memory?? which we already HAVE access to? Should granularity be set to 1?
probably... i havent looked at that page, so im not sure
Here is where I'm confused. I bet I just have some misconception about how the processor works... are there specific parts of the intel manual i should be reading, or any other resources you've accumulated for your work in unreal mode? I'd appreciate it a lot.
there isnt much about UMode in the manuals, and for a good reason -- intel expects that once the system is running (which happens entirely within the BIOS), you will move out of UMode, and use either RMode or PMode (preferably PMode...)

Re: Cannot understand why unreal mode works

Posted: Mon Oct 29, 2007 12:12 pm
by madeofstaples
JAAman wrote:
madeofstaples wrote: It is my understanding that it is necessary to enter unreal mode temporarily in the boot process in order to load the kernel to anywhere above 1MB+64kb? Or am I making a mountain out of a mole hill?
no -- its not required, it is one way of doing t, but not the only way (or even necessarily the best way... but thats more a matter of style) -- you can also write a PMode driver (which is what a lot of people do), or load your kernel below 1MB, or (if your loading less than 64k, you can load it above 1MB in RMode)
My kernel isn't that big yet but I'd like to not have to worry if it grows too much. So to be on the safe side, loading below 1MB in RMode is out.

That makes a lot of sense, though, about the PMode driver. I guess I was assuming you had to set up the GDT before entering PMode, but looking back at the Intel manual, I can cal LGDT again to set the GDT that I want to ultimately use for my kernel while still in protected mode. Thanks, I'll probably just do that!
JAAman wrote:
This brings up a new question about the granularity bit of the GDT used to enter unreal mode. In the wiki example, it's set to 0, or 1 byte granularity... but with only 20 bits for a limit, that only gives access to... the first MB of memory?? which we already HAVE access to? Should granularity be set to 1?
probably... i havent looked at that page, so im not sure
That makes me feel a lot more sane.

Posted: Mon Oct 29, 2007 12:43 pm
by Combuster
Descriptor Cache

With the G bit clear, the maximum limit for a selector is indeed 1MB. However, you can still load the base with higher values so that when you load 0xffff in a segment register you can access to 0xffff0+0xfffff which is from just below 1MB to just below 2MB instead of the original 1MB+64k

Posted: Wed Oct 31, 2007 9:21 am
by inflater
Is it possible to make code segment and stack 32bit, and when I would load the program above 1 MB, to simply "jump" to it, using unreal mode? I think this can be achieved only in pmode...

If I can do that... well I can reincarnate PortixOS Pascal again ;)