flat assembler
Message board for the users of flat assembler.

Index > OS Construction > Can Somebody Modify this boot loader for me...............

Author
Thread Post new topic Reply to topic
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 17 Aug 2013, 06:16
Actually I want to modify this bootloader such that the user is asked to put a kernel file name, and then the boot loader will load the kernel (format *.bin) from the respective file......
BTW (there's a print_string function there and the kernel file string is kern_filename)
All the main variables are in the last.
I am sorry if this is silly, but with my current assembly knowledge I don't even know a single piece of what to do for modifying this bootloader
Here's the Boot Code (Below the License)(HUGGGEEEE)
Code:
MikeOS -- License
==================================================================


Copyright (C) 2006 - 2013 MikeOS Developers -- http://mikeos.berlios.de

All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:

    * Redistributions of source code must retain the above copyright
      notice, this list of conditions and the following disclaimer.

    * Redistributions in binary form must reproduce the above copyright
      notice, this list of conditions and the following disclaimer in the
      documentation and/or other materials provided with the distribution.

    * Neither the name MikeOS nor the names of any MikeOS contributors
      may be used to endorse or promote products derived from this software
      without specific prior written permission.

THIS SOFTWARE IS PROVIDED BY MIKEOS DEVELOPERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL MIKEOS DEVELOPERS BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.


==================================================================
    

Code:
; =====================================================;=====================================================
; The Mike Operating System bootloader
; Copyright (C) 2006 - 2013 MikeOS Developers -- see doc/LICENSE.TXT
;
; Based on a free boot loader by E Dehling. It scans the FAT12
; floppy for KERNEL.BIN (the MikeOS kernel), loads it and executes it.
; This must grow no larger than 512 bytes (one sector), with the final
; two bytes being the boot signature (AA55h). Note that in FAT12,
; a cluster is the same as a sector: 512 bytes.
; ==================================================================


        BITS 16

        jmp short bootloader_start      ; Jump past disk description section
        nop                             ; Pad out before disk description


; ------------------------------------------------------------------
; Disk description table, to make it a valid floppy
; Note: some of these values are hard-coded in the source!
; Values are those used by IBM for 1.44 MB, 3.5" diskette

OEMLabel                db "MIKEBOOT"   ; Disk label
BytesPerSector          dw 512          ; Bytes per sector
SectorsPerCluster       db 1            ; Sectors per cluster
ReservedForBoot         dw 1            ; Reserved sectors for boot record
NumberOfFats            db 2            ; Number of copies of the FAT
RootDirEntries          dw 224          ; Number of entries in root dir
                                        ; (224 * 32 = 7168 = 14 sectors to read)
LogicalSectors          dw 2880         ; Number of logical sectors
MediumByte              db 0F0h         ; Medium descriptor byte
SectorsPerFat           dw 9            ; Sectors per FAT
SectorsPerTrack         dw 18           ; Sectors per track (36/cylinder)
Sides                   dw 2            ; Number of sides/heads
HiddenSectors           dd 0            ; Number of hidden sectors
LargeSectors            dd 0            ; Number of LBA sectors
DriveNo                 dw 0            ; Drive No: 0
Signature               db 41           ; Drive signature: 41 for floppy
VolumeID                dd 00000000h    ; Volume ID: any number
VolumeLabel             db "MIKEOS     "; Volume Label: any 11 chars
FileSystem              db "FAT12   "   ; File system type: don't change!


; ------------------------------------------------------------------
; Main bootloader code

bootloader_start:
        mov ax, 07C0h                   ; Set up 4K of stack space above buffer
        add ax, 544                     ; 8k buffer = 512 paragraphs + 32 paragraphs (loader)
        cli                             ; Disable interrupts while changing stack
        mov ss, ax
        mov sp, 4096
        sti                             ; Restore interrupts

        mov ax, 07C0h                   ; Set data segment to where we're loaded
        mov ds, ax
        
        ; NOTE: A few early BIOSes are reported to improperly set DL

        cmp dl, 0
        je no_change
        mov [bootdev], dl               ; Save boot device number
        mov ah, 8                       ; Get drive parameters
        int 13h
        jc fatal_disk_error
        and cx, 3Fh                     ; Maximum sector number
        mov [SectorsPerTrack], cx       ; Sector numbers start at 1
        movzx dx, dh                    ; Maximum head number
        add dx, 1                       ; Head numbers start at 0 - add 1 for total
        mov [Sides], dx
        
no_change:
        mov eax, 0                      ; Needed for some older BIOSes


; First, we need to load the root directory from the disk. Technical details:
; Start of root = ReservedForBoot + NumberOfFats * SectorsPerFat = logical 19
; Number of root = RootDirEntries * 32 bytes/entry / 512 bytes/sector = 14
; Start of user data = (start of root) + (number of root) = logical 334

        ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
        
floppy_ok:                              ; Ready to read first block of data
        mov ax, 19                      ; Root dir starts at logical sector 19
        call l2hts

        mov si, buffer                  ; Set ES:BX to point to our buffer (see end of code)
        mov bx, ds
        mov es, bx
        mov bx, si

        mov ah, 2                       ; Params for int 13h: read floppy sectors
        mov al, 14                      ; And read 14 of them
        pusha                           ; Prepare to enter loop


read_root_dir:
        popa                            ; In case registers are altered by int 13h
        pusha

        stc                             ; A few BIOSes do not set properly on error
        int 13h                         ; Read sectors using BIOS

        jnc search_dir                  ; If read went OK, skip ahead
        call reset_floppy               ; Otherwise, reset floppy controller and try again
        jnc read_root_dir               ; Floppy reset OK?

        jmp reboot                      ; If not, fatal double error


search_dir:
        popa

        mov ax, ds                      ; Root dir is now in [buffer]
        mov es, ax                      ; Set DI to this info
        mov di, buffer

        mov cx, word [RootDirEntries]   ; Search all (224) entries
        mov ax, 0                       ; Searching at offset 0


next_root_entry:
        xchg cx, dx                     ; We use CX in the inner loop...

        mov si, kern_filename           ; Start searching for kernel filename
        mov cx, 11
        rep cmpsb
        je found_file_to_load           ; Pointer DI will be at offset 11

        add ax, 32                      ; Bump searched entries by 1 (32 bytes per entry)

        mov di, buffer                  ; Point to next entry
        add di, ax

        xchg dx, cx                     ; Get the original CX back
        loop next_root_entry

        mov si, file_not_found          ; If kernel is not found, bail out
        call print_string
        jmp reboot

        
found_file_to_load:                     ; Fetch cluster and load FAT into RAM
        mov ax, word [es:di+0Fh]        ; Offset 11 + 15 = 26, contains 1st cluster
        mov word [cluster], ax

        mov ax, 1                       ; Sector 1 = first sector of first FAT
        call l2hts

        mov di, buffer                  ; ES:BX points to our buffer
        mov bx, di

        mov ah, 2                       ; int 13h params: read (FAT) sectors
        mov al, 9                       ; All 9 sectors of 1st FAT

        pusha                           ; Prepare to enter loop


read_fat:
        popa                            ; In case registers are altered by int 13h
        pusha

        stc
        int 13h                         ; Read sectors using the BIOS

        jnc read_fat_ok                 ; If read went OK, skip ahead
        call reset_floppy               ; Otherwise, reset floppy controller and try again
        jnc read_fat                    ; Floppy reset OK?

; ******************************************************************
fatal_disk_error:
; ******************************************************************
        
        mov si, disk_error              ; If not, print error message and reboot
        call print_string
        jmp reboot                      ; Fatal double error


read_fat_ok:
        popa

        mov ax, 2000h                   ; Segment where we'll load the kernel
        mov es, ax
        mov bx, 0

        mov ah, 2                       ; int 13h floppy read params
        mov al, 1

        push ax                         ; Save in case we (or int calls) lose it


; Now we must load the FAT from the disk. Here's how we find out where it starts:
; FAT cluster 0 = media descriptor = 0F0h
; FAT cluster 1 = filler cluster = 0FFh
; Cluster start = ((cluster number) - 2) * SectorsPerCluster + (start of user)
;               = (cluster number) + 31

load_file_sector:
        mov ax, word [cluster]          ; Convert sector to logical
        add ax, 31

        call l2hts                      ; Make appropriate params for int 13h

        mov ax, 2000h                   ; Set buffer past what we've already read
        mov es, ax
        mov bx, word [pointer]

        pop ax                          ; Save in case we (or int calls) lose it
        push ax

        stc
        int 13h

        jnc calculate_next_cluster      ; If there's no error...

        call reset_floppy               ; Otherwise, reset floppy and retry
        jmp load_file_sector


        ; In the FAT, cluster values are stored in 12 bits, so we have to
        ; do a bit of maths to work out whether we're dealing with a byte
        ; and 4 bits of the next byte -- or the last 4 bits of one byte
        ; and then the subsequent byte!

calculate_next_cluster:
        mov ax, [cluster]
        mov dx, 0
        mov bx, 3
        mul bx
        mov bx, 2
        div bx                          ; DX = [cluster] mod 2
        mov si, buffer
        add si, ax                      ; AX = word in FAT for the 12 bit entry
        mov ax, word [ds:si]

        or dx, dx                       ; If DX = 0 [cluster] is even; if DX = 1 then it's odd

        jz even                         ; If [cluster] is even, drop last 4 bits of word
                                        ; with next cluster; if odd, drop first 4 bits

odd:
        shr ax, 4                       ; Shift out first 4 bits (they belong to another entry)
        jmp short next_cluster_cont


even:
        and ax, 0FFFh                   ; Mask out final 4 bits


next_cluster_cont:
        mov word [cluster], ax          ; Store cluster

        cmp ax, 0FF8h                   ; FF8h = end of file marker in FAT12
        jae end

        add word [pointer], 512         ; Increase buffer pointer 1 sector length
        jmp load_file_sector


end:                                    ; We've got the file to load!
        pop ax                          ; Clean up the stack (AX was pushed earlier)
        mov dl, byte [bootdev]          ; Provide kernel with boot device info

        jmp 2000h:0000h                 ; Jump to entry point of loaded kernel!


; ------------------------------------------------------------------
; BOOTLOADER SUBROUTINES

reboot:
        mov ax, 0
        int 16h                         ; Wait for keystroke
        mov ax, 0
        int 19h                         ; Reboot the system


print_string:                           ; Output string in SI to screen
        pusha

        mov ah, 0Eh                     ; int 10h teletype function

.repeat:
        lodsb                           ; Get char from string
        cmp al, 0
        je .done                        ; If char is zero, end of string
        int 10h                         ; Otherwise, print it
        jmp short .repeat

.done:
        popa
        ret


reset_floppy:           ; IN: [bootdev] = boot device; OUT: carry set on error
        push ax
        push dx
        mov ax, 0
        mov dl, byte [bootdev]
        stc
        int 13h
        pop dx
        pop ax
        ret


l2hts:                  ; Calculate head, track and sector settings for int 13h
                        ; IN: logical sector in AX, OUT: correct registers for int 13h
        push bx
        push ax

        mov bx, ax                      ; Save logical sector

        mov dx, 0                       ; First the sector
        div word [SectorsPerTrack]
        add dl, 01h                     ; Physical sectors start at 1
        mov cl, dl                      ; Sectors belong in CL for int 13h
        mov ax, bx

        mov dx, 0                       ; Now calculate the head
        div word [SectorsPerTrack]
        mov dx, 0
        div word [Sides]
        mov dh, dl                      ; Head/side
        mov ch, al                      ; Track

        pop ax
        pop bx

        mov dl, byte [bootdev]          ; Set correct device

        ret


; ------------------------------------------------------------------
; STRINGS AND VARIABLES

        kern_filename   db "KERNEL  BIN"        ; MikeOS kernel filename

        disk_error      db "Floppy error! Press any key...", 0
        file_not_found  db "KERNEL.BIN not found!", 0
        bootdev         db 0    ; Boot device number
        cluster         dw 0    ; Cluster of the file we want to load
        pointer         dw 0    ; Pointer into Buffer, for loading kernel


; ------------------------------------------------------------------
; END OF BOOT SECTOR AND BUFFER START

        times 510-($-$$) db 0   ; Pad remainder of boot sector with zeros
        dw 0AA55h               ; Boot signature (DO NOT CHANGE!)


buffer:                         ; Disk buffer begins (8k after this, stack starts)


; ==================================================================

    

_________________
"Those who can make you believe in absurdities can make you commit atrocities" -- Voltaire https://github.com/Benderx2/R3X
XD


Last edited by sid123 on 17 Aug 2013, 10:32; edited 5 times in total
Post 17 Aug 2013, 06:16
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4121
Location: vpcmpistri
bitRAKE 17 Aug 2013, 08:32
Maybe try feryno's boot manager? It's no longer on his website, but a copy is available through the wayback machine:

http://web.archive.org/web/20050312161837/http://feryno.host.sk/projects/bmf5doc/index.html

IIRC, it already has the features you desire and source code is included.

_________________
¯\(°_o)/¯ “languages are not safe - uses can be” Bjarne Stroustrup
Post 17 Aug 2013, 08:32
View user's profile Send private message Visit poster's website Reply with quote
egos



Joined: 10 Feb 2009
Posts: 144
egos 17 Aug 2013, 09:56
I can write simple stage 2 based on this code. 100$ Smile
Post 17 Aug 2013, 09:56
View user's profile Send private message Reply with quote
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 17 Aug 2013, 10:21
Am... I don't think it's that difficult to modify this,(to my knowledge)
the kern_filename could be set to "times 256 db 0" and then we could scan for input (But that's what I DON'T KNOW Sad )
Post 17 Aug 2013, 10:21
View user's profile Send private message Reply with quote
egos



Joined: 10 Feb 2009
Posts: 144
egos 17 Aug 2013, 10:33
There is not enough space. Use stage 2 that holds a copy of the stage 1. Rewrite file name and then run a modified copy.


Last edited by egos on 17 Aug 2013, 10:35; edited 1 time in total
Post 17 Aug 2013, 10:33
View user's profile Send private message Reply with quote
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 17 Aug 2013, 10:34
I don't understand what you mean (Sorry Razz)
Post 17 Aug 2013, 10:34
View user's profile Send private message Reply with quote
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 17 Aug 2013, 10:34
egos wrote:
There is not enough space. Use stage 2 that holds a copy of the stage 1. Rewrite file name and then run a copy.

I don't understand what you mean (Sorry Razz)
EDIT :
Ooooooooooooooo Idea You mean to write a code like :
Code:
%INCLUDE 'bootload.asm'
/
....................................
Whatever code scan......
...................................
/
    

_________________
"Those who can make you believe in absurdities can make you commit atrocities" -- Voltaire https://github.com/Benderx2/R3X
XD
Post 17 Aug 2013, 10:34
View user's profile Send private message Reply with quote
TightCoderEx



Joined: 14 Feb 2013
Posts: 58
Location: Alberta
TightCoderEx 17 Aug 2013, 16:39
There are probably as many versions of Boot Loader's out there as there are people. The link points to details of one of eleven I've done for myself, none of which incorporate and existing file system, meaning fat12/16/32 NTFS EXT EXT2 etc.

My latest version loads the second stage 50:0 -> 7B0:0 jumps to it and then loads the rest of the image 7B0:0 -> 8B00:0, thus giving me a 500 some odd K disk image in memory.
Code:
  Load_Data:
    ; Build Disk Access Packet on stack
        xor     eax, eax
        push    eax
        push     ax
        push     8                      ; Absolute start sector (zero indexed).

        push     80                     ; segment 50H
        push     ax                     ; Offset 0

        push     59                     ; Number of sectors between 50:0 & 7c0:0

        push     16                     ; Size of DAP

        push     ss
        pop      ds
        mov      si, sp                 ; DS:SI pointer to stack
        mov     dx, [bp+11*2]           ; Retrieve boot drive, probably 80H HD, SD or USB
        mov     ah, 0x42
        int     DISK_IO
        jc     @F

        jmp     0x50:0                  ; Jump to second stage.
    

Right now I use Pure64 as the backbone "0S" while I'm developing the user interface portion of my kernel. Then I'll go back to the "OS" part and refine drivers and initialization procedures of my own design. This way I'll be able to test on real hardware and get details of what's going on in real time, not using Bochs, QEMU or any other kind of emulation.

In order to give you any constructive help I need to know;
(1) What mode you're in when you get to the kernel stage of development "real/protected/long".
(2) What is the operating system. In real mode BIOS is probably your operating system
(3) What code are you using for system initialization if not staying in real mode.

In principle, OS development is pretty simple, but the combinations and permutations after you enter @ 7C0:0 are seemingly infinite. So in order to help you constructively, I need to know more details about the system your developing hardware wise and what your objectives are, beyond loading a kernel file.
Post 17 Aug 2013, 16:39
View user's profile Send private message Visit poster's website Reply with quote
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 17 Oct 2013, 13:08
TightCoderEx wrote:
There are probably as many versions of Boot Loader's out there as there are people. The link points to details of one of eleven I've done for myself, none of which incorporate and existing file system, meaning fat12/16/32 NTFS EXT EXT2 etc.

My latest version loads the second stage 50:0 -> 7B0:0 jumps to it and then loads the rest of the image 7B0:0 -> 8B00:0, thus giving me a 500 some odd K disk image in memory.
Code:
  Load_Data:
    ; Build Disk Access Packet on stack
        xor     eax, eax
        push    eax
        push     ax
        push     8                      ; Absolute start sector (zero indexed).

        push     80                     ; segment 50H
        push     ax                     ; Offset 0

        push     59                     ; Number of sectors between 50:0 & 7c0:0

        push     16                     ; Size of DAP

        push     ss
        pop      ds
        mov      si, sp                 ; DS:SI pointer to stack
        mov     dx, [bp+11*2]           ; Retrieve boot drive, probably 80H HD, SD or USB
        mov     ah, 0x42
        int     DISK_IO
        jc     @F

        jmp     0x50:0                  ; Jump to second stage.
    

Right now I use Pure64 as the backbone "0S" while I'm developing the user interface portion of my kernel. Then I'll go back to the "OS" part and refine drivers and initialization procedures of my own design. This way I'll be able to test on real hardware and get details of what's going on in real time, not using Bochs, QEMU or any other kind of emulation.

In order to give you any constructive help I need to know;
(1) What mode you're in when you get to the kernel stage of development "real/protected/long".
(2) What is the operating system. In real mode BIOS is probably your operating system
(3) What code are you using for system initialization if not staying in real mode.

In principle, OS development is pretty simple, but the combinations and permutations after you enter @ 7C0:0 are seemingly infinite. So in order to help you constructively, I need to know more details about the system your developing hardware wise and what your objectives are, beyond loading a kernel file.

1) Real Mode (BIOS Interrupts and speed!)
2) BIOS (As you said)
3) No Code!
If you want more info please tell me.
BTW My Kernel structure is like this :
+KERNEL 0-24K
+DISK BUFFER 24K-32K(FAT16)
+EXTERNAL SPACE (to load apps on it) 32K-64K
Note: I have developed the Kernel so that it sometimes uses segmentation
to break out the 64K Limit, but that's only in rare cases like when an app crashes and another program (I call it MEMx86) breaks the segment out and halts the application and then restores the 64K Limit (Because of maintaining compatibility with MikeOS Apps). (Multitasking is ENABLED)
I can write this stuff if i am given more than 512 Bytes,but to be honest I am a
very messy coder (I admit it) and thus I require lots of memory space.
But the main problem how would I load my Kernel after the second stage?
+BOOTLOAD
+SECOND STAGE (This will destroy the Memory Structure)
+KERNEL (Now the Kernel will be loaded somewhere at 5K)
+DISK BUFFER (Will now start at 29K and end at 37K)
+APPS (They will now load at 37K instead of MikeOS 32K will cause incompatibility with MikeOS Awesome programs... + Less Memory Space Although that can be solved by using MEMx86)
~Help would be appreciated
PS: I look for a Boot-Manager (Like GRUB), rather than changing the bootloader but I you know GRUB launches in PMode but I run the Kernel in RMode
Post 17 Oct 2013, 13:08
View user's profile Send private message Reply with quote
egos



Joined: 10 Feb 2009
Posts: 144
egos 18 Oct 2013, 12:30
You can use such stage 2/stage 2 extension that is loaded into extended memory (when it is really needed) but is able to load your kernel into base memory. Or you can implement MB entry point (in your kernel) which will be used to move kernel into base memory, to set RM, and to jump to native RM entry point. Also you can convert your kernel to other format and boot it by corresponding boot loaders.
Post 18 Oct 2013, 12:30
View user's profile Send private message Reply with quote
sid123



Joined: 30 Jul 2013
Posts: 339
Location: Asia, Singapore
sid123 01 Nov 2013, 13:04
I did it!
Here it is :
Image

_________________
"Those who can make you believe in absurdities can make you commit atrocities" -- Voltaire https://github.com/Benderx2/R3X
XD
Post 01 Nov 2013, 13:04
View user's profile Send private message Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  


< Last Thread | Next Thread >
Forum Rules:
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Copyright © 1999-2025, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.