[SOLVED]I might just need the best bootloader in the world..

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
bashcommando
Member
Member
Posts: 62
Joined: Mon Jan 06, 2014 4:23 pm

Re: I might just need the best bootloader in the world...

Post by bashcommando »

bubach wrote:It probably would have taken you less time to try that for yourself then to come here and ask us..... Also I forgot to mention that I used fasm but if the padding code to make it 512 bytes is the only thing that keeps you from using nasm... and you can't even find a nasm bootloader to copy the syntax from? You might be beyond all hope of ever getting somewhere. Sorry.

Code: Select all

boot.asm:248: error: mismatch in operand sizes
boot.asm:263: error: mismatch in operand sizes
boot.asm:282: error: mismatch in operand sizes
boot.asm:309: error: operation size not specified
boot.asm:360: warning: uninitialized space declared in .text section: zeroing
Thats is what happened when I did the resb fix. I thought I did something wrong when there were just plain errors in the code, which is why I thought resb broke it. That is why I asked if I should. I got fasm and got more errors in the code. Is there a fix or no? Because I don't want to mess up your code. I will try to fix it and I will post the fixed code here as well just for future reference.
Building an operating system is like building an airplane, you don't want it to crash.
User avatar
bashcommando
Member
Member
Posts: 62
Joined: Mon Jan 06, 2014 4:23 pm

Re: I might just need the best bootloader in the world...

Post by bashcommando »

bubach wrote:It probably would have taken you less time to try that for yourself then to come here and ask us..... Also I forgot to mention that I used fasm but if the padding code to make it 512 bytes is the only thing that keeps you from using nasm... and you can't even find a nasm bootloader to copy the syntax from? You might be beyond all hope of ever getting somewhere. Sorry.
And as promised: The patched code

Code: Select all

;------------------------------------------------------------;
;                 BOS - FAT12 bootsector                     ;
;------------------------------------------------------------;
;  - FAT12 compatible.                                       ;
;  - Loads a binary file from the floppy, max ~576kb.        ;
;  - Sets A20 and protected mode.                            ;
;                                                            ;
;  Thanks to: Petroff Heroj and John S. Fine for examples.   ;
;                                                            ;
;          by: Christoffer Bubach, 2003-2005                 ;
;                                                            ;
;------------------------------------------------------------;
;Patched by bashcommando no credit needed;
; other notes:
;  this code is public domain, and you can use it for
;  anything you want. but if you do, please act polite and
;  give credit. ;-)
;
;            mem map
;  0x0000:0x0000 -> 0x0000:0x0500  BIOS stuff
;  0x0000:0x0500 -> 0x0000:0x2100  root
;  0x0000:0x2100 -> 0x0000:0x3300  fat
;  0x0000:0x3300 -> 0x0000:0x7c00  18,25kb free space
;  0x0000:0x7c00 -> 0x0000:0x7e00  bootsector
;  0x0000:0x7e00 <- 0x0000:0xffff  32,5kb stack
;  0x1000:0x0000 -> 0x9000:0xffff  576kb free space
;  0xa000:0x0000 -> .............  VGA mem etc.

use16
org 0x7C00

boot:     jmp     near start
          nop

;------------------------------------------;
;  Standard BIOS Parameter Block, "BPB".   ;
;------------------------------------------;
          bpbOEM          db  'BOS 0.03'
          bpbSectSize     dw  512
          bpbClustSize    db  1
          bpbReservedSec  dw  1
          bpbFats         db  2
          bpbRootSize     dw  224
          bpbTotalSect    dw  2880
          bpbMedia        db  240
          bpbFatSize      dw  9
          bpbTrackSect    dw  18
          bpbHeads        dw  2
          bpbHiddenSect   dd  0
          bpbLargeSect    dd  0
     ;---------------------------------;
     ;  extended BPB for FAT12/FAT16   ;
     ;---------------------------------;
          bpbDriveNo      db  0
          bpbReserved     db  0
          bpbSignature    db  0                       ; 0 = nothing more. 41 = three more (below)..
;          bpbID           dd  1
;          bpbVolumeLabel  db  'BOOT FLOPPY'
;          bpbFileSystem   db  'FAT12   '


;----------------------------------------;
;   starting point of bootsector code    ;
;----------------------------------------;
start:
          cli

          xor     ax, ax                              ; initialize all the necessary
          mov     ds, ax                              ; registers.
          mov     es, ax
          mov     ss, ax
          mov     sp, 0xFFFF                          ; Stack..

          mov     [bpbDriveNo], dl

          sti


;----------------------------------;
;   clear screen and print some    ;
;----------------------------------;
          mov     ax, 3                               ; Set mode 0x03
          int     0x10

          mov     bp, loading                         ; Print loading message.
          mov     ax, 0x1301
          mov     bx, 7
          mov     cx, 12
          mov     dx, 0x0102
          int     0x10

          mov     bl, 2                               ; Set cursor.
          mov     ah, 2
          mov     dx, 0x0201
          int     0x10

          mov     ah, 9                               ; Print 14 green dots.
          mov     al, '.'
          mov     cx, 14
          int     0x10


;---------------------------;
;    load FAT and root      ;
;---------------------------;
          mov     di, 0x0050                          ; Load the root to
          mov     ax, 19                              ; 0x0000:0x0500 (0x500/0x10)
          mov     cx, 14
          call    read_sectors

          mov     di, 0x0210                          ; Load the fat to
          mov     ax, 1                               ; 0x0000:0x2100
          mov     cx, 9
          call    read_sectors


     ;------------------------;
     ;  search for the file   ;
     ;------------------------;
          mov     dx, [bpbRootSize]
          mov     bx, 0x0500
     filesearch:
          cld
          mov     si, filename
          mov     cx, 11
          mov     di, bx
          repe    cmpsb
          je      found
          add     bx, 32
          dec     dx
          jz      error
          jmp     filesearch


;-----------------------------------;
;      variables & functions        ;
;-----------------------------------;
          loading         db  'Starting BOS'
          filename        db  'KERNEL  SYS'
          failure         db  'Read error!'
          a20_on          db  1


     ;-----------------------------------------------;
     ;   read a number of sectors (one at a time)    ;
     ;-----------------------------------------------;
     ;  in:                                          ;
     ;    di = segment to save at                    ;
     ;    ax = sector to read                        ;
     ;    cx = number of sectors                     ;
     ;  out:                                         ;
     ;    di = updated (added for next read)         ;
     ;    ax = updated (added for next read)         ;
     ;-----------------------------------------------;
     read_sectors:
          pusha
          mov     bl, byte [bpbTrackSect]             ; bl = number of sectors per track
          div     bl                                  ; al = ax / bl
          mov     cl, ah                              ; cl = real sector number
          add     cl, 1

          xor     ah, ah                              ; del the rest of the div before
          mov     bl, byte [bpbHeads]                 ; bl = number of heads
          div     bl                                  ; ah = rest of ( ax / bx ), al = ax / bx
          mov     ch, al                              ; ch = number of track
          mov     dh, ah                              ; dh = the head number

          mov     ax, cx                              ; save cx in ax
          mov     cx, 6                               ; try it 6 times
     .next_try:
          push    es
          push    cx
          mov     cx, ax                              ; restore cx
          push    cx

          xor     ax, ax
          mov     dl, [bpbDriveNo]                    ; reset drive
          push    dx
          int     0x13
          jc      .failed

          pop     dx
          pop     cx
          xor     bx, bx
          mov     es, di
          mov     ax, 0x0201                          ; function 2, 1 sector
          int     0x13
          jnc     .ok                                 ; if it was ok, check next..

     .failed:
          pop     dx
          pop     ax

          pop     cx
          pop     es
          loop    .next_try                           ; else try once again if there is an error
          jmp     error                               ; if cx = 0 and the read operation always failed, halt
     .ok:
          pop     cx                                  ; from the next_try loop
          pop     es
          popa
          add     di, 32                              ; add 32 (512/16) to segment
          inc     ax                                  ; add sector counter
          loop    read_sectors
          ret


     ;----------------------------------------------------;
     ;  show a message and wait for a key before reboot   ;
     ;----------------------------------------------------;
     error:
          ;push    0x0000
          ;pop     es
          mov     bp, failure
          mov     ax, 0x1301
          mov     bx, 4
          mov     cx, 43
          mov     dx, 0x0401
          int     0x10

          mov     ah, 0
          int     0x16
          int     0x19


;-----------------------------------;
;   the file is found, load it.     ;
;-----------------------------------;
found:
          mov     bp, [bx+26]                         ; bp=cluster number from directory entry
          mov     di, 0x1000                          ; 1000 (segment)

     .next_block:
          xor     cx, cx
          mov     cl, [bpbClustSize]                  ; reset sector count to 1 cluster
          mov     si, bp                              ; si=next should-be cluster for
                                                      ; contiguous reads
     .next_contiguous:
          mov     ax, 3                               ; 3
          mul     si                                  ; multiply cluster number by 3
                                                      ; dx assumed to be 0, it's a floppy!
          shr     ax, 1                               ; divide by two
          push    bp
          xchg    bp, ax                              ; bp=ax
          mov     ax, word [0x2100+bp]                ; ax=FAT element with junk
                                                      ; (addressing with bp)
          pop     bp
          jc      .odd_cluster                   ; jump if the value was odd

     .even_cluster:
          and     ax, 0x0FFF                          ; leave only lower 12 bits
          jmp     .got_cluster                        ; got it

     .odd_cluster:
          push    cx                                  ; preserve sector count
          mov     cl, 4                               ; shift four bits right
          shr     ax, cl                              ; (leave only bits 4-15)
          pop     cx                                  ; restore sector count

     .got_cluster:
          inc     si                                  ; si=current cluster+1
          cmp     ax, si                              ; next cluster=current cluster+1?
          jne     .force_read                    ; is it still contiguous?

          add     cl, [bpbClustSize]                  ; increase sector count by 1 cluster
          adc     ch, 0
          jmp     .next_contiguous

     .force_read:
          xchg    bp, ax                              ; ax=bp (base cluster), bp=new cluster
          dec     ax                                  ; decrease by 2 to get the actual... (1)
          dec     ax                                  ; ...cluster number (2)

          xor     dx, dx
          mov     dl, [bpbClustSize]
          mul     dx                                  ; multiply by sectors per cluster
                                                      ; (dx ignored)
          add     ax, 33                              ; assume data-area start at sector 33
          call    read_sectors                        ; read cx sectors at ax to es:0 :)

          cmp     bp, 0x0FF8                          ; the new cluster is EOF (FF8-FFF)?
          jb      .next_block                    ; if not in this range, read next block

;-----------------------;
;  the file is loaded   ;
;-----------------------;
quit:
a20:                                                  ; Enable A20
          in      al, 0x64
          test    al, 2
          jnz     a20
          mov     al, 0xD1
          out     0x64, al
     .d6:
          in      al, 0x64
          and     ax, 2
          jnz     .d6
          mov     al, 0xDF
          out     0x60, al

     .a20_check:
          mov     al, byte [fs:0]                     ; check a20, is it on?
          mov     ah, al
          not     al
          xchg    al, byte [gs:0x10]
          cmp     ah, byte [fs:0]
          mov     [gs:0x10], al
          jz      floppy_off
          mov     byte [a20_on], 0                         ; it's not on save for file..

floppy_off:
          mov     dx, 0x3F2                           ; turn of the floppy motor.
          mov     al, 0
          out     dx, al

pmode:
          cli                                         ; set protected mode (32-bit)
          lgdt    [gdtr]
          mov     eax, cr0
          or      eax, 1
          mov     cr0, eax

          jmp     0x08:flush


;----------------------------------------;
; start of 32-bit area.                  ;
;     flush segments and jump to kernel  ;
;----------------------------------------;
use32
flush:
          mov     eax, 0x10                           ; refresh all segment registers
          mov     ds, eax
          mov     es, eax
          mov     fs, eax
          mov     gs, eax
          mov     ss, eax
          mov     esp, 0xfffc

          mov     eax, 0xB05B007                      ; report "BOSboot".. ;-)
          mov     bl, [a20_on]                        ; report if a20 is on.
          jmp     0x08:0x10000                        ; jump to loaded file (64kb in mem)



;--------------------------------;
;  global descriptor table (gdt) ;
;--------------------------------;
gdt:                      dw  0x0000, 0x0000, 0x0000, 0x0000
codesel:                  dw  0xFFFF, 0x0000, 0x9800, 0x00CF
datasel:                  dw  0xFFFF, 0x0000, 0x9200, 0x00CF
gdt_end:

gdtr:                     dw  gdt_end - gdt - 1
                          dd  gdt

;-------------------------------------;
; set the BOOT-signature at byte 510. ;
;-------------------------------------;
          resb boot+512-2-$
          dw 0xAA55
Building an operating system is like building an airplane, you don't want it to crash.
Post Reply