Systematic setup for loading kernel?

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.
User avatar
Pitchu
Member
Member
Posts: 56
Joined: Tue Feb 12, 2008 3:16 am
Location: Kashmir - Paradise On Earth

Systematic setup for loading kernel?

Post by Pitchu »

Hi
Firstly, I wanna give overview of what i have done :

1. I wrote a BootLoader/Bootsector that gives choice to load my OS or other OS and copied that BIN file(512 bytes) onto bootsector (not MBR) of the Active FAT32 partition of my HDD saving the old Bootsector onto spare sectors between 0-62 for normal booting if user selects other OS(XP in my case).

2. If MyOS is selected it loads the SecondStage BootLoader from the same partition.It is 4kb in size and detects hardware and stores that in a struct.

In the same SecondStage Bootloader I want to setup enviroment for Pmode (coz maybe kernel may not fit in less than 1MB) and enable Pmode.

I think I should do this :

a. GDT having 4 descriptors(code/data/stack) for Kernel including NULL.

I will set base=0 and limit=0xfffff for 4GB memory access in all descriptors except NULL,offcourse.
(Intention is to use Flat-Memory Model using Paging.)

b. NO LDT

c. SET CR3 to a physical address of Page-Directory which will contain page table addresses where pages will be mapped to frames linearly, i mean 0 to 0 address, i.e.
No translation for kernel.

d. Remap PIC to invoke 32 or greater interrupt numbers in IDT on firing.
I am confused whether to enter correponding enteries in IDT or let kernel do it?

e. IDT having 32 descriptors(NONE POPULATED).
I am confused whether to populate atleast some or not? Please suggest.


f. Enable A20, Set PE and PG bits.

g. Make a far JMP to flush the que or in other words let the processor units know about that mode has changed.
(I think latter is a better quote.)

h. Load kernel into memory and some part of it will do rest of necessary things like filling of IDT,loading of shell, etc.


Also I am not using QEMU or BOCHS.

Ya Allah,
It is all messed up inside my cranial cavity.

Hope this is a correct way! :roll:
User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Post by Combuster »

a. GDT having 4 descriptors(code/data/stack) for Kernel including NULL.
You only need three, including null. If you don't know why, do more research.
e. IDT having 32 descriptors(NONE POPULATED).
having an empty IDT is worth the same as having no IDT at all. In fact loading an IDT early in real mode will mess up the IVT if you plan to use bios calls later. Also, where did those 16 IRQs from the remapped PIC go?
h. Load kernel into memory and some part of it will do rest of necessary things like filling of IDT,loading of shell, etc.
Loading the kernel from disk after switching to protected mode? how do you manage that for all possible ATA and non-ATA devices?
In the same SecondStage Bootloader I want to setup enviroment for Pmode (coz maybe kernel may not fit in less than 1MB) and enable Pmode.
So, how do you get that kernel of yours into memory when you can't use bios calls from protected mode and the kernel can't fit into memory accessible from real mode?
Also I am not using QEMU or BOCHS.
You should.
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
User avatar
einsteinjunior
Member
Member
Posts: 90
Joined: Tue Sep 11, 2007 6:42 am

LDT not used

Post by einsteinjunior »

I just wish to know why most OS designers do not use the LDT.
Is something wrong with using it?
User avatar
AJ
Member
Member
Posts: 2646
Joined: Sun Oct 22, 2006 7:01 am
Location: Devon, UK
Contact:

Post by AJ »

Hi,

The LDT is used to store segment descriptors specific to a process. Segmentation is now considered 'legacy' - it is not supported in 64 bit mode - overall, you are better using paging as a protection mechanism. Even if you have a LDT, you cannot use it to store Task State Segments.

This is why most people seem to set up a GDT with 5 flat segments (NULL, ring 0 code / data, ring 3 code / data) plus TSS descriptors for each CPU core and leave it at that.

Cheers,
Adam
User avatar
einsteinjunior
Member
Member
Posts: 90
Joined: Tue Sep 11, 2007 6:42 am

Post by einsteinjunior »

So you are not using an emulator?
How do you do tests then?You should surely be some rich guy with many PCs for development and testing.....
If not then say goodbye to the good functionning of your PC.Hoping it can survive a crash......
Krox
Posts: 23
Joined: Fri Mar 21, 2008 3:52 am
Location: Germany

Post by Krox »

Combuster wrote:
a. GDT having 4 descriptors(code/data/stack) for Kernel including NULL.
You only need three, including null. If you don't know why, do more research.
Actually, you need 6 with most common OS-Designs: NULL, Ring0-Code, Ring0-Data, Ring3-Code, Ring3-Data, TSS. But okay... as long as you dont have multitasking, the first three are enough.

edit: oops, there was somebody faster... but nevermind
e. IDT having 32 descriptors(NONE POPULATED).
As said before, you need 16 more for the PIC (at least). And I would suggest, you populate the 32 exception-descriptors as soon as you are in PMode. A simple error-msg and hlt is enough. This will save you much time when debugging your kernel. Cause otherwise every exception will triple-fault and reset the PC, and you don't have a clue what went wrong.
21 is only half the truth...
User avatar
Pitchu
Member
Member
Posts: 56
Joined: Tue Feb 12, 2008 3:16 am
Location: Kashmir - Paradise On Earth

Post by Pitchu »

For Combuster :
having an empty IDT is worth the same as having no IDT at all. In fact loading an IDT early in real mode will mess up the IVT if you plan to use bios calls later. Also, where did those 16 IRQs from the remapped PIC go?
I am not going to use BIOS calls in my kernel.But I dont think loading IDT early in real mode will mess up the IVT as IDT has no meaning in Rmode and IVT has no meaning in Pmode.

Yeah..I have to think about 16 IRQs from the Remapped PIC.
Even If there is no problem with loading IDT in Rmode, still i think i shouldn't 'coz loading IDT also means installing ISRs, which means large code size and no distinction between kernel and second-stage bootloader.

Loading the kernel from disk after switching to protected mode? how do you manage that for all possible ATA and non-ATA devices?
Yep! You are correct.
What I am planning to have a mini-read module for ATA devices ONLY. I will use it to load kernel instead of IBM int 13H extensions which are not available in Pmode.

So, how do you get that kernel of yours into memory when you can't use bios calls from protected mode and the kernel can't fit into memory accessible from real mode?
I think you got it!
You only need three, including null. If you don't know why, do more research.
NULL/CODE/DATA....Why not STACK? I will get it soon, anyway thanks for that. :P


For einsteinjunior:

How do you do tests then?
Simple...Install a BootLoader using booatble CD/Floppy/Flash and copy the actual Bootsector to spare sectors as mentioned. This was only problematic part to do until my OS will Read/Write on HDD.
You should surely be some rich guy with many PCs for development and testing.....
If not then say goodbye to the good functionning of your PC.Hoping it can survive a crash......
Ah!
I am not a rich guy with dozens of PCs. I only owe a single Desktop with CRT monitor occupying half of my room with P4 processor.
Yeah it is a tedious way to compile and restart but gave me a mental strenght to visualise that I can do it.. :P
After I am able to load kernel into memory i will switch to QEMU/BOCHS....Which one is better and easy?
And so far as crashing is concerned.....Allah knows better.

For Krox:
And I would suggest, you populate the 32 exception-descriptors as soon as you are in PMode. A simple error-msg and hlt is enough. This will save you much time when debugging your kernel. Cause otherwise every exception will triple-fault and reset the PC, and you don't have a clue what went wrong.
Yeah...That is what my delimma was.
I will go for hlt or err msg to avoid triple fault and to denug easily. Thnx

Now, After all this what I wanna know is what to do if my kernel size is large enough such that it doesnt fit in less than 1MB space and kernel switches CPU to Pmode?
User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Post by Combuster »

I am not going to use BIOS calls in my kernel.But I dont think loading IDT early in real mode will mess up the IVT as IDT has no meaning in Rmode and IVT has no meaning in Pmode.
Which is exactly why I warned you - it will.
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
User avatar
Pitchu
Member
Member
Posts: 56
Joined: Tue Feb 12, 2008 3:16 am
Location: Kashmir - Paradise On Earth

Post by Pitchu »

May i know how?
User avatar
neon
Member
Member
Posts: 1567
Joined: Sun Feb 18, 2007 7:28 pm
Contact:

Post by neon »

having an empty IDT is worth the same as having no IDT at all. In fact loading an IDT early in real mode will mess up the IVT if you plan to use bios calls later. Also, where did those 16 IRQs from the remapped PIC go?
Im not entirely sure how true that is. ntrldr's very first thing is entering pmode and installing interrupts. Afterwords it switches to v86 mode to load and execute ntdetect.

Granted, some might mess up; but most BIOS calls should still work fine as the location of the IDT does not at all touch the IVT in memory.
OS Development Series | Wiki | os | ncc
char c[2]={"\x90\xC3"};int main(){void(*f)()=(void(__cdecl*)(void))(void*)&c;f();}
User avatar
JamesM
Member
Member
Posts: 2935
Joined: Tue Jul 10, 2007 5:27 am
Location: York, United Kingdom
Contact:

Post by JamesM »

IDTR contains the IVT offset in real mode. If you install an IDT, you change IDTR, so you lose all your bios interrupts.
User avatar
neon
Member
Member
Posts: 1567
Joined: Sun Feb 18, 2007 7:28 pm
Contact:

Post by neon »

JamesM wrote:IDTR contains the IVT offset in real mode. If you install an IDT, you change IDTR, so you lose all your bios interrupts.
Partially correct. While you do change the base address of the ivt, you do not lose all Bios interrupts (Although alot of them become unusable, though).

The default ivt copied into memory by the Bios will still be there when a new idt is installed. This allows us to execute Bios interrupts directly without using INT instruction via real or v86 modes. (I do this in my v86 monitor)

However:

a) Using the INT instruction to execute Bios interrupts will not work (of course) as its tied to your pmode IDT;

b) Need to be careful as some Bios interrupts execute via INT instruction and IO privilege levels. This may essentially make alot of Bios interrupts unavailable.
OS Development Series | Wiki | os | ncc
char c[2]={"\x90\xC3"};int main(){void(*f)()=(void(__cdecl*)(void))(void*)&c;f();}
User avatar
Pitchu
Member
Member
Posts: 56
Joined: Tue Feb 12, 2008 3:16 am
Location: Kashmir - Paradise On Earth

Post by Pitchu »

JamesM wrote:IDTR contains the IVT offset in real mode. If you install an IDT, you change IDTR, so you lose all your bios interrupts.
Wow!
This is not mentioned in 386 manual. Thanks James! :)
So, IDTR has significance in Rmode.
I think nothing special about GDTR,LDTR and TR in Rmode?

Neon wrote: The default ivt copied into memory by the Bios will still be there when a new idt is installed. This allows us to execute Bios interrupts directly without using INT instruction via real or v86 modes. (I do this in my v86 monitor)

However:

a) Using the INT instruction to execute Bios interrupts will not work (of course) as its tied to your pmode IDT;

b) Need to be careful as some Bios interrupts execute via INT instruction and IO privilege levels. This may essentially make alot of Bios interrupts unavailable.
Yeah....Taking above post of James into consideration this is correct. Thanks.


Doing Disk I/O in Pmode using ATA read module can load my kernel but I am not going to do that now.Thanks everybody. But the question is
If my kernel is larger than 1MB what to do?
User avatar
JoeKayzA
Member
Member
Posts: 79
Joined: Wed Aug 24, 2005 11:00 pm
Location: Graz/Austria

Post by JoeKayzA »

Pitchu wrote:But the question is
If my kernel is larger than 1MB what to do?
Load the file in multiple turns, and copy the buffer above 1MB each time (switch to pmode and back or use unreal mode or so). It's some overhead, but you probably won't notice any performance impact due to the disk latency.
Ready4Dis
Member
Member
Posts: 571
Joined: Sat Nov 18, 2006 9:11 am

Post by Ready4Dis »

JoeKayzA wrote:Load the file in multiple turns, and copy the buffer above 1MB each time (switch to pmode and back or use unreal mode or so). It's some overhead, but you probably won't notice any performance impact due to the disk latency.
This is how I do mine, I jump back and forth between r-mode and unreal mode (flat real mode) while loading, so I can load my kernel at 1mb. This way, I don't have anything in the way, and it can expand as big as it needs be. It takes up a bit more space than I really wanted, but it is much nicer than hoping you don't run out of space, and worrying about segments, etc.
Post Reply