writing your own operating system - by thewomble

Upload: sanathd

Post on 10-Apr-2018

220 views

Category:

Documents


0 download

TRANSCRIPT

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    1/9

    Writing your own operating system - By thewomble

    This tutorial will teach you howto write your own operating system using assembly language.Containsbootsector example code.

    By: [email protected] (Questions welcome. Spam not)More at: http://www.groovyweb.cjb.net, http://www.axion-network.net

    How to write an operating systemWriting an operating system is something that can not only be interesting (if you're one of thosepeople that get turned on by Int 13....) but it is also a great learning experience. Through creatingyour own operating system you will learn exactly what goes on behind the scenes, elevating youabovethe average programmer that just writes in Visual Basic.

    In this tutorial you will be tought by examples, and by the end you should have created your ownoperating system.

    Tools:

    EasyOs easyos.zip 300kbEasyOS is a very simple operating system, it contains all the tools needed to build an operatingsystem.(Not written by me, although I did add bits to it and mess it up a bit)

    A quick explanation of assembly: (see here for a good tutorial)

    si and ah Think of si as something to put text into, and ah as something to put numbers into.mov This (mov)es data. mov ah,0 would move 0 into ah. (The data on the right is moved into theleft)Int Think of these as functions. Different int's do different things when ah is different. Ahem. Eg.when ah = 0 and you call int 10 it prints si to the screen.Stuff To put words and stuff in your program you can't just do mov si,'some words' (well, you can

    butyou wont like the resutls) so instead you have to declare the words first. You do this by putting thename of what you want the words to be called by, then the data type (nearly always db) then thewords themselves.Eg:name db 'some words'Jump To give sections of code a label, just type the label and add a : at the end, eg code: .You can then use jmp to jump to it, eg jmp code If To do an if in assembly you use cmp, egcmp al,0 (if al=0). On the next line you then put je code, and if al=0 then the program jumps tothe section of code called code. If you use jne code, then if al is not 0 the program will jump to

    code.The stack The stack is where stuff is stored. push pushes stuff into it, pop pulls stuff out.The following example would put cx into dx:push cx pop dx

    Now you know everything there is to know about assembly, you can now understand most of theprogram thatboot's EasyOs. Drives (hard drives and floppy's) are split into lots of bits, all 512 bytes long(enough to fit 512 letters in). These are calle sectors. The first sector is what the computer looksfor when it boots. It is called the bootsector.Open the folder src and then open boot.asm. Or if you are lazy, just look at the code below (itsthe same).; This is a comment[ORG 0x7C00] ;This just tells the program where it is in the memory. Not important

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    2/9

    [BITS 16] ;Not important too.

    jmp start ; Jump over BIOS parameter block

    start: ;The label for the start of the actual program

    push cs ;Put cs onto the stackpop ds ;Take it out and put it into ds

    mov si,Print_loading ;Print loading messagecall printstring ;Call is like jump, but it goes back. Like a function

    ;The complicated bit: Loads the next programmov ah,02h ;When ah=, int13 reads a disk sectormov al,4 ;Al is how many sectors to readmov ch,0 ;The track to read frommov cl,2 ;Sector Idmov dh,0 ;Head

    mov dl,0 ;Drive (0 is floppy)mov bx,0x1000 ;Es and Bx put together are where to load the program too (see

    jmp 0x1000:0x00)mov es,bxmov bx,0x00int 13h ;Int 13 is all functions for disks

    mov si,putdot ;Print a ".".call printstring

    jmp 0x1000:0x00 ;Run Bootinit from stack.

    printstring: ;Print string routine.

    mov ah,0eh ;Mov ah into 0, so int 10 printsstringloop: ;The following code loads each seperate charcter so itcan be printedlodsbcmp al,00 ;If al =0, then the string has all been loaded

    je endstringint 10h ;When int 10 is called, and ah=, it prints

    jmp stringloopendstring:ret ;Ret returns

    putdot db '.',0Print_loading db 13,10,'Loading Easy OS v0.01a...',0times 425 db 0 ;wastes 425 bytes on purpose, so the sector is full (The program must be 512bytes long)

    You may have noticed that numbers, like int 10h, end in h. They don't have to, it just looks funky(there is a real reason, but it's boring).Anyway, now copy the program called copyboot in the folder called utils to the folder withtest.asm in.

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    3/9

    Open the dos prompt and type:(Make sure a blank floppy is inserted)copyboot test.com 0copyboot is the name of the program, test.com the name of the file to copy, and 0 is the sector.In the program above all it does is print a string then load whats at sector 1.The program that easyos loads under the src folder called bootinit. If you assemble it with nasm,then copy it to sector 1 and restart, the bootsector will load it.There isn't much more to be learnt from EasyOs, so run either setup.exe or make.bat to build thewhole thing.The difference is setup.exe lets you setup a root password for EasyOs.If you just run make.bat the passwords is the default password: monty (named after my psychoticdog).Now restart and be amazed. Wow. Pretty crappy, but it isn't that bad.

    Fat 12No, its not a fat people supprt group but a file system. If you try and access the floppy diskWindows will say it need s to be formatted. Formatted? You ask.Formatting is basically organising the sectors so you can give them names.Underneath Windows and Fat,

    you are still just accessing sectors. I won't go into Fat here, check outhttp://www.maverick.subnet.dk/for some info. Anyway,the bootsector needs to have some information in it that when Windows reads it it tells it it is fat.The following BootSector was disgustingly ripped by me of NYAOS (I have no idea what i standsfor).With your A* qualification in assembly language you can no doubt understand it.; NYAOS Boot Sector (C) Copyright Sean Tash 1998; assemble with:; nasm -f bin -o bootsect.bin bootsect.asm

    bits 16org 0x7C00

    start: jmp short beginnop

    bsOEM db "NYAOS1.0" ; OEM StringbsSectSize dw 512 ; Bytes per sectorbsClustSize db 1 ; Sectors per clusterbsRessect dw 1 ; # of reserved sectorsbsFatCnt db 2 ; # of fat copiesbsRootSize dw 224 ; size of root directorybsTotalSect dw 2880 ; total # of sectors if < 32 megbsMedia db 0xF0 ; Media DescriptorbsFatSize dw 9 ; Size of each FATbsTrackSect dw 18 ; Sectors per trackbsHeadCnt dw 2 ; number of read-write heads

    bsHidenSect dd 0 ; number of hidden sectorsbsHugeSect dd 0 ; if bsTotalSect is 0 this value is; the number of sectors

    bsBootDrv db 0 ; holds drive that the bs came frombsReserv db 0 ; not used for anythingbsBootSign db 29h ; boot signature 29hbsVolID dd 0 ; Disk volume ID also used for temp

    ; sector # / # sectors to loadbsVoLabel db "NO NAME " ; Volume LabelbsFSType db "FAT12 " ; File System type

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    4/9

    begin: cli ; disable interruptsmov [bsBootDrv],dl ; save drive numbermov ax,0x9000 ; put stack at 0x98000mov ss,axmov sp,0x8000

    mov cx,[bsTrackSect] ; update int 1E FDC param tablemov bx,0x0078lds si,[ds:bx]mov byte [si+4], clmov byte [si+9], 0x0F

    sti ; enable interruptspush dsmov dl,[bsBootDrv] ; reset controllerxor ax,axint 0x13pop dsjc bootfail2 ; display error message

    jmp _l1bootfail2: jmp bootfail

    _l1:mov ax,0x0000mov es,axmov ds,ax

    mov si,MsgLoad ; display load messagecall putstr

    ; find the root directory

    xor ax,ax

    mov al,[bsFatCnt]mov bx,[bsFatSize]mul bxadd ax,word [bsHidenSect]adc ax,word [bsHidenSect+2]add ax,word [bsRessect] ; ax holds root directory locationmov word [BootSig],ax

    call checkroot

    xor ax,axadd ax,word [start]add ax,word [bsVolID] ; sector number

    add ax,word [BootSig]sub ax,2 ; correction for a mis-calcmov cx,word [bsVolID+2] ; number of sectors

    mov bx,0x8000mov es,bx

    nextsector: push ax ; save registerspush cx

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    5/9

    push dxpush es

    xor bx,bx ; set zero offsetcall readsect ; read a sector

    mov si,MsgDot ; display a dotcall putstr

    pop es ; restore registerspop dxpop cxpop axmov bx,esadd bx,20h ; increment address 512 bytesmov es,bxinc ax ; read next sectorloopnz nextsector

    mov ax,0x8000 ; set segment registers and jump

    mov es,axmov ds,axpush axmov ax,0push axretf

    checkroot:push ax ; save registerspush bxpush cxpush dxpush si

    push di

    mov ax,0x8000 ; put root directory at 0x80000mov es,axmov ax,32 ; AX = ((32*RootSize)/512) + 2mul word [bsRootSize]div word [bsSectSize]mov cx,ax ; cx holds # of sectors in rootmov word [start],axmov ax,word [BootSig] ; get prev. saved loc. for root dir

    r1: xor bx,bxpush cx ; save count

    push ax ; save sector numberpush espush dxcall readsectxor bx,bx

    l_1: mov di,bx ; set address to check frommov cx,11 ; check 11 bytesmov si,FileName ; address of string to check withrepz cmpsbje foundit

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    6/9

    add bx,32 ; check next entrycmp bx,[bsSectSize] ; end of sector?je l_2jmp l_1

    l_2: pop dx ; restore registerspop espop axpop cxinc ax ; read next sectorloopnz r1jmp bootfail

    foundit: pop dx ; get these off the stackpop espop axpop cx

    mov di,0x1A ; get clustor #add di,bxpush bx ; save bx for finding # of sectorsmov ax,[es:di]

    xor bx,bx ; calculate sector #mov bl,[bsClustSize]mul bx ; ax holds sector #mov word [bsVolID],ax

    pop bx ; get location of directory entrymov di,0x1Cadd di,bxmov ax,[es:di] ; put number of bytes in axxor dx,dxmov bx,[bsClustSize] ; # of bytes / 512div bxinc ax

    mov word [bsVolID+2],ax ; save number of sectors to load

    pop di ; restore registerspop sipop dxpop cxpop bxpop ax

    ret ; return to caller

    putstr: ; SI = address of string to displaylodsb

    or al,aljz short putstrdmov ah,0x0Emov bx,0x0007int 0x10jmp putstr

    putstrd: retn ; return to caller

    bootfail: ; display failure messagemov si,MsgBad ; display error message

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    7/9

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    8/9

    pop es ;and put that into esin ax,0x40 ;generate "random" number (timer)shl ax,4 ;multiply random # with 16mov di,ax ;box offset (random)mov al,255 ;color of the boxmov bx,50 ;height=50

    pl: add di,270 ;di+270 (320-width(50))mov cx,50 ;# bytes to copy to bufferrep stosb ;and do itdec bx ;decrement bxjnz pl ;jump if bx not zeromov bh,0xFA ;assume bl = 0 (-> bx = FA00)

    Smudge: mov al,[bx+1] ;right color to almov cl,[bx-1] ;left color to cladd ax,cx ;and add it to axmov cl,[bx-320] ;upper color to cladd ax,cx ;and add it to axmov cl,[bx+320] ;lower color to cladd ax,cx ;and add it to axshr ax,2 ;divide with 4

    mov [bx],al ;and but the avarage color to bufferdec bx ;decrement bxjnz Smudge ;jump if bx not zeromov ax,0xA000 ;vga segmov es,ax ;put it to esmov ch,0xFA ;# bytes to copy to vgaxor di,di ;zero vga offsetxor si,si ;zero buffer offsetrep movsb ;and do thatin al,0x60 ;check for keysdec al ;was it esc?jnz Main ;nope, continuemov ax,3 ;text mode

    int 10h ;get back into text modexor ah,ah ;yes, return to OSint 0x18 ;back to good old kernel

    ;Note:- This was, as you can guess, ripped by from an os. So when it goes back to the 'good olkernel' it just restarts.

    Build it with nasm, but rather than faffing around copyboot, just name is as OSLOADER.COM andcopy it to the floppy.Now restart and enjoy the funkiness. Woah dood.

    CTime to escape assembly language. The boot sector has to be written in assembly, but nothing

    else does.Unfortunately you can't just go and write a cool shell with Visual C++. First of all, its has to be a.com program,not .exe. .exe programs are just .com with a bit of extra info. at the start giving some info on whatthe program is.It's very easy to add .exe capabililty to an os, or you can download a program called exe2com.The serious problem though is that you can create your own ints to make things easier.EasyOs does this (look in kernel.asm under the src folder) and Dos does this too (Dos makes int21).By default, compilers build a program with these ints.

  • 8/8/2019 Writing Your Own Operating System - By Thewomble

    9/9

    For linux loversThe following code is for Gcc on linux and nasm for dos or linux. Dos/ Windows users candownload Djgpp from http://www.delorie.com/djgpp/,which is like gcc. The linegcc -c -O2 -Wall -g -o hello.o hello.cTells gcc to build a plain binary. I don't know who wrote the following, e-mail me if you do.