top of page
Search
Writer's picturePankajan Kajan

Create my own os

Updated: Apr 5, 2019


The codes are available in the git: https://github.com/pankajan05/S-os


Today I decided to write my own os for computer architecture and operating system. In this subject I know about how a operating system work and get the basic ideas of the operating system So I like to have my own os. So I refer some books and search youtube for create os. From that I get some ideas and started to create my own os.

First I select a name for my os. I refer google for is there any os in that name. but no os in that name. So I named to my os as s operating system. I used atom text editor because it is easy to use. I create a folder named "s os". I make four files.


This is the file that is use.


1.kernel.cpp //it is the c++ file that is for print the os name in the display.



2.loader.s //it will the assembly language file that is for the kernel file . It will create the kernel of the operating system



3.makefile //it is for compiling the other files so i create this file. it have the details of the compiling file and i don't need to type full of the coding.



4.linker.ld //it is the linker file that link the kernel.o and the loader.o





the loader.o is the file that is create from compiling the assembly language file using the assembler

the kernel.o is the file that is create from the compiling the cpp file using the gcc. Thid linker.ld the file is use to link the loader.o and the kernel.o.


"make loader.o" command to compile source code of loader.cpp and make loader.o.

"make linker.o" command to compile the linker.s and make linker.o file.

"make Skernel.bin" command to make the Skernel.bin file using the linker.ld file that link the 2 files.


Now I have the Skernel.bin file that enough to run our operating system kernel.

"gemu-system-i386 -kernel kernel.bin" - This command will run our kernel.bin in the gemu program.


Now I am going to make my iso file of the S os so I add these commands to my makefile.

Skernel.iso: Skernel.bin

mkdir iso //This will make the iso folder

mkdir iso/boot // Inside the iso folder it create boot

mkdir iso/boot/grub //Inside the boot folder it create grub folder

cp $< iso/boot/ //It copy the Skernel.bin and paste it inside the boot folder

echo 'set timeout=0'> iso/boot/grub/grub.cfg //it will write tht grub.cfg file

echo 'set default=0'>> iso/boot/grub/grub.cfg //it will write tht grub.cfg file

echo ''>> iso/boot/grub/grub.cfg //it will write tht grub.cfg file

echo 'menuentry "S operating system"{'>> iso/boot/grub/grub.cfg //it will write tht grub.cfg

echo ' multiboot /boot/Skernel.bin'>> iso/boot/grub/grub.cfg //it will write tht grub.cfg

echo ' boot'>> iso/boot/grub/grub.cfg //it will write tht grub.cfg file

echo '}'>> iso/boot/grub/grub.cfg //it will write tht grub.cfg file


//are comments to explain the commands


These commands make these folders and create the grub file

But we want a single iso file for that reason we add these commands with them

grub-mkrescue --output=$@ iso

rm -rf iso

This two commands will create a installable iso file. We can install that file in our virtual box. or we can boot that file in a pendrive as bootable pendrive. I install the iso file in the virtual box.

This image show the s operating system that run on the virtual box successfully.

If i want to run the virtual machine for that reason i add these commands to makefile file. So i can run my virtual machine through the command.

run: Skernel.iso

(killall VirtualBox && sleep 1) || true

VirtualBox --startvm "S os" &

So these commands will run the S os in the virtual box.


After this I want to communicate with the hardware devices like keyboard and the mouse. If I want to communicate with the hardware devices I want to have the memory segments. In my main memory previously we only run the kernel. But now we want to run other programs also. So I want to develop a memory segments. In my memory kernel segment have the kernel programs and the kernel data part and the program segment also have the program part and the data part. So I must divide these part. For that reason I use Global Descriptor Table(GDT). This table will help to divide the memory segment and keep the records of the memory segment that can use by program.



I like to use c++ to create the GDT table program. I can also use the assembly language but I didn't have very big knowledge in the assembly language. c++ is very easy to understand.

I create a header file 'gdt.h' and the 'gdt.cpp'. These two files are create my Global Descriptor Table.




Now we have the GDT table. now we want communicate with the hardware devices.


when we click the keyboard key then it must sent the data so it must produce a interrupt. That received by the program interrupt controller(PIC). It is decided any action is perform or not. In between our keyboard and processor there must we a way to communicate. There must be a method to send data out or receive data out. Processor have multipluxer and demultipluxer. They do this job. processor send data and port number to the multipluxer and multipluxer send data using the port number. So here I create the port class in cpp and there are two method read data and write data. The data can be different bit of data for that reason I use different bit of integers.


Here I create the port.h header file


This is the port.cpp file


After that i modify kernel.cpp that must print a new line. For that reason i modify it. '\n' command now will be work correctly. Now I can print the character in another line also. mostly the black dos window have 25 height and 80 width using that i print the character in new line.


Now I am going to create Interrupt Descriptor Table that contain the information about the interrupt number,handler,some flag, memory segment, access right. Before we execute the handler we must keep the memory segments. The handler job is change the memory segments. mostly we execute the instructions that are in the user space when the keyboard key is press, it must change to the kernel space. This job is done by the handler. The handler get the interrupt as the parameter. To get the interrupt number as a parameter the cpu must push that into a stack that in the user space. For every single interrupt we must write code. I write the handler in the assembler language because we must handle the register and other files I write it using the c++.

In the interrupt handler that i create using the c++ that keep the entries in structure call gateDiscriptor. After that I create an array to hold the entries that can have 256 entries. And In the Interrupt handler constructor that only take the specific interrupt. others are ignore by the compiler.

I create another structure that have the interrptDescriptortable Pointer that can use by the processor.





These are the files that use to handle the interrupts.


Now we are going to create a driver to keyboard so we can get the interrupt from the keyboard and we can print the character for the interrupt. I create keyboard.h and keyboard.cpp for the driver of the keyboard. It is derived from the interrupt handler. when we press a key it produce interrupt for press the key and the release the key. so I do coding for except the key release. After that i only get the interrupt for the key press only. The interrupt we can't understand what key we press. so we must print the character for that i get the interrupt for the key and using the interrupt number i print the charactar for the interrupt I do it only for the number key and character key other i don't do anything so you can see the interrupt number for that keys like alt, ctrl and shift. The key codes are different to keyboards. I write the case for my keyboard keycodes.. I use the key code and print the particular character for the key code.





Here I only print the small letters only so I try to modify to print the capital letters So I modify the switch case to print the capital letter for that reason I use a boolean variable Shift If i press the left shift then it activate the variable to true after that i can print the capital letters. After that i press the right shift then it change the varible to false then it print the small letters only. I use this to number keys also.


Now I like to use the mouse. When we move the mouse it will produce three bites. I store them in the array of 8 bit integer name as buffer. Using the buffer it determine the movement of the mouse and it move in the dos window. Here I create mouse.cpp and mouse.h these files are for the drivers. It act as the drivers. when i move the mouse it will produce the interrupt and using the interrupt it will move the mouse.

And I add driver class to store the drivers and it show the available devices.









This is the final of my S operating system.

78 views0 comments

Recent Posts

See All

DevOps

Comments


bottom of page