Baby steps #7

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
tm-

Baby steps #7

Post by tm- »

I was reading that tutorial and there are lines:

Code: Select all

   mov  bx, 0x08   ; select descriptor 1
   mov  ds, bx   ; 8h = 1000b
And I don't have any idea what those lines are doing. Selecting descriptor..? By ds register..? Please, someone help me a little.
Argh

Re:Baby steps #7

Post by Argh »

That *looks* like exactly what the comments say. It's picking descriptor 1 (after null descriptor 0) for the data segment from the loaded GDT. Since the code probably doesn't crash, descriptor 1 probably describes a data segment. More than that I can't really say, since I don't have the rest of the code. Share?
tm-

Re:Baby steps #7

Post by tm- »

Yes, it's there: http://www.mega-tokyo.com/forum/index.p ... 42;start=0

I was just wondering that how can i access to that descriptor by bx register? Ds stands for data segment and the code resets its value right?
dh

Re:Baby steps #7

Post by dh »

Looks to me like bx is the address of the memory and ds is the data. Maybe somebody could confirm/fix this.

Cheers, DH.
Argh

Re:Baby steps #7

Post by Argh »

Oh, I'm silly, I should have read the title.

I don't understand your first question.

The purpose of the two statements to extend ds, that is, make its limit 4 gigabytes (normal real mode segment limits are 64k). The use of bx in particular isn't important. It could have been any other register that you can load segment registers from (well, not ax in this example, unless you save and restore it).

Once ds has been extended, you can restore its original value of 0, and it will have a base of 0 and a limit of 4 gigabytes. You can then use 32-bit addressing for data, while still being in real mode. BIOS and string operations still use 16 bit addressing, however.
tm-

Re:Baby steps #7

Post by tm- »

This is a bit difficult for me because I have just started OS developing.. I don't know much about GDT..
But now I think I got the point: lgdt instruction loads the global descriptor table and the beginning of the table is 0 (gdt-variable is 0 and passed as a parameter as the beginning of the table) and then memory address 0x00 is null descriptor and one descriptor is a byte long(??) so the descriptor number 1 is 0x08(because of null descriptor), number 2 is 0x80(??).
Is the descriptor number 1 for data segment? ???

Correct me if I'm wrong.
jimboynugget

Re:Baby steps #7

Post by jimboynugget »

My understanding of the code is that it loads DS with the offset of the descriptor in the GDT that describes the segment that will be used for data access. You can't do this directly (using something like "mov DS,0x08"), so you have to put the value into BX (or another register) first. Once DS is set, the values in the descriptor such as base, length, limit, and other gubbins are used to define exactly what memory will be accessed when you do something like "mov [DS:CX], 0xFFFF".

The next descriptor (number 2) is at offset 0x10 (16 bytes) from the start of the GDT. Number 3 is at 0x18 (24 bytes in), and so on....

I'm new to this too so I could be talking complete rubbish. :P
User avatar
Candy
Member
Member
Posts: 3882
Joined: Tue Oct 17, 2006 11:33 pm
Location: Eindhoven

Re:Baby steps #7

Post by Candy »

jimboynugget wrote: My understanding of the code is that it loads DS with the offset of the descriptor in the GDT that describes the segment that will be used for data access.
That's almost correct, but just a slight bit off. It's the offset (which is always 8-byte aligned), but the lowest 3 bits aren't always 0. The 3rd bit from the right is for choosing between the GDT and the LDT and the 2nd and 1st bit are for the selector privilege level (from 0-3). So, 0x08 is the first valid one in the GDT, 0x14 is the second valid one in the LDT, 0x17 is the same but then in PL3 etc.
I'm new to this too so I could be talking complete rubbish.
In fact, you're 95% correct.
tm-

Re:Baby steps #7

Post by tm- »

Is there a website where I could find the numbers of different descriptors? I mean 0 is null descriptor, 1 is data segment descriptor...? Where is the whole list of them?

And what means that, I have to create/set up my own GDT when entering to pmode? Do I just have to set the right values to segment registers from the right descriptors like above with the DS register?
Argh

Re:Baby steps #7

Post by Argh »

The first descriptor is always null, but after that it depends on how the particular GDT is laid out (that is, what's actually in it). In the "baby steps #7" the GDT has only two entries, a null (required), and a flat data.

One could just as well have a GDT with a null, flat code, and flat data. In which case you'd load ds with 0x10.
dh

Re:Baby steps #7

Post by dh »

Thanks for filling me in ;D
User avatar
Candy
Member
Member
Posts: 3882
Joined: Tue Oct 17, 2006 11:33 pm
Location: Eindhoven

Re:Baby steps #7

Post by Candy »

Just for the record, the first isn't just null, it's never used. Loading values below 4 should always give you a null selector even though the GDT may contain something else instead. You can then use those 8 bytes for something else :)
Argh

Re:Baby steps #7

Post by Argh »

Candy wrote: You can then use those 8 bytes for something else :)
Like, say, the structure lgdt likes.
Post Reply