CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 5 of 5
  1. #1
    Join Date
    May 2010
    Posts
    8

    Unhappy Issues with very simple bootloader off USB

    Hi, I've been working on a very simple bootloader that should run off a usb flash drive or similar attached device. All it does is load the next 1024 bytes off an unformatted disk into ram, and jump to it.

    The issue I'm having is that I can't get it to run on real hardware. I make the image, flash it to the thumb drive with flashnul, and can then boot the flash drive in QEMU and it works fine. However, if I reboot and try it for real, The bootloader boots, copies the data (i think), and then hangs.

    I have used both INT 13h AH=02h (read sectors) and INT 13h AH=42h (extended read sectors), and can't get either to work on real hardware. Any advice would be most helpful.

    Here's my bootloader code (it's not really my code, its more or less lots of copy pastas from a bunch of other forums). The rest of the project should be attached.
    I am using NASM for my assembly (should work with YASM aswell)

    At the moment on real HW it prints A and stops. No indication of failure - it just halts.

    Code:
    [bits 16]
    [org 0x7C00]
    
    
    ; Prepare Stack Segment
        mov sp, 0x7A00              ; Move Stack into SP
        mov bp, sp                  ; Store current Stack Base
    
    	; print an A to make sure the bootloader actually loaded
        mov ah, 0x0E                ; Print Character to Screen
        mov bh, 0x00                ; No Page Numbering
        mov bl, 0x07                ; White Text, Black Background
        mov al, 65                  ; Print Letter A
        int 0x10
    
    ; Check if INT0x13 Extentions are Supported
    
        mov ah, 0x41                ; Set Function 0x41
        mov word bx, 0x55AA          
        push dx                     ; Save old Drive Identifier
        ;mov dl, 0x80                ; Load 'Active' ID Into dl, commented out to keep bios setting of dl (should be active drive)
        int 0x13                    ; Call Interupt
        jc short unsupported        ; If Extentions aren't Supported, Jump
        xor ax, ax
        add ax, 1                   ; clear carry flag
    
        mov si, DAPS                ; Load DAPS Struct to DS:SI
        mov ah, 0x42                ; Read Functions (AL Ignored)
        ;mov dl, 0x80                ; Active Boot Drive
        int 0x13
        jc short unsupported 	; If something goes wrong...
    	;
    	mov dx, 0
        mov bx,0x0080 ; set up the memory offset so DS:DX is 0x0080:0x0000 (so the next program can run from org 0x0000)
    	push bx
        pop ds ; sets the offset for the program just read, so it runs from org 0x0000
    	jmp 0x0080:0x0000 ; hopefully jump to the code we just loaded into ram
    	;
    
        unsupported:
        mov ah, 0x0E                ; Print Letter F, Gives Indication of Failure
        mov bh, 0x00
        mov bl, 0x07
        mov al, 70
        int 0x10
    	jmp $ ; hang on error
    	
    	; Disk Address Packet Structure (for extended read)
        DAPS: db 0x10               ; Size of Structure (16 bytes, always this for DAPS)
              db 0                  ; Always 0
              db 2                  ; Number of Sectors to Read (2x512)
              db 0                  ; Always 0 
              dw 0x0800             ; Target Location for Reading To (0x0800 = 0x0080:0x0000)
              dw 0                  ; Page Table (0, Disabled)
              dd 1                  ; Read from 2nd block (code I want to load)
              dd 0                  ; Large LBAs, dunno what this does
    	
    times 510-($-$$) db 0 ; fill rest of bootloader with 0s
    
    db 0x55, 0xAA               ; Add Boot Record Signature
    	
    ; Code that I want to run is stuck on here after compilation (compiled as separate image and added with copy /b)
    Attached Files Attached Files

  2. #2
    Join Date
    Jun 2010
    Location
    Germany
    Posts
    2,675

    Re: Issues with very simple bootloader off USB

    I don't see anything in your code that is obviously wrong. However, you shouldn't make assumptions about the initial state of any register (not even CS:IP - common combinations are both 0000:7C00 and 07C0:0000, but theoretically it can be any combination that amounts to the same linear address), but AFAICT you are making assumptions about the values of CS, DS, SS and DL.

    BTW, I didn't know that there is the number of the boot drive passed in DL or that there is a dedicated number for the active boot drive. (I don't have personal experience with booting from anything that's neither a floppy nor a HDD, however.) But according to anything I read about that, at least the drive number passed in DL is not a standard and thus can't be relied upon.

    Maybe carefully reading http://wiki.osdev.org/Boot_sequence and obeserving any potential gotcha could also take you further.
    I was thrown out of college for cheating on the metaphysics exam; I looked into the soul of the boy sitting next to me.

    This is a snakeskin jacket! And for me it's a symbol of my individuality, and my belief... in personal freedom.

  3. #3
    Join Date
    May 2010
    Posts
    8

    Re: Issues with very simple bootloader off USB

    Thankyou for your post. That website was very helpful (it is now bookmarked :P), but I was still unable to resolve the issue. I copied my image to a floppy disk and stuck it in an old pentium 2 pc (that has proper, IDE floppy drive), and it works fine. I'm convinced now it's something to do with the way USB floppy emulation is handled in USB devices, and the drive id in the dl register.

  4. #4
    Join Date
    May 2010
    Posts
    8

    Re: Issues with very simple bootloader off USB

    I think I have found the issue, here: http://bootloader.wikidot.com/linux:boot:usb-grub

    When a USB device is emulated as a floppy disk drive, the value of dl is in fact 00h. However, instead of the bios emulating the entire disk as a floppy drive, it instead tries to emulate the first partition on the usb drive as device 00h. So, my loader is trying to load the program from the offset of the first partition (plus 512 bytes), when none actually exists.

    The only way to overcome this would be to somehow get the bios to emulate the USB drive as a HDD (mine gives no option), or to make a partition table that points partition 1 to the start of my program.

    The plot thickens...

  5. #5
    Join Date
    Jun 2010
    Location
    Germany
    Posts
    2,675

    Re: Issues with very simple bootloader off USB

    Quote Originally Posted by Crozone View Post
    I think I have found the issue, here: http://bootloader.wikidot.com/linux:boot:usb-grub


    The only way to overcome this would be to somehow get the bios to emulate the USB drive as a HDD (mine gives no option), or to make a partition table that points partition 1 to the start of my program.
    If you want to deploy what you're writing there in any way, I'd say the second option is definitely preferable because it doesn't require the user to manipulate any BIOS settings (thereby potentially messing up the booting ability from other USB devices). Aside from that, I can't remember ever having seen a BIOS setting for that anyway.

    I don't understand anyway why you want to boot from a partition-less USB drive but you certainly have your resons for that.

    This thread made me learn something about the USB boot process myself. As I said, I didn't know much about that yet.
    I was thrown out of college for cheating on the metaphysics exam; I looked into the soul of the boy sitting next to me.

    This is a snakeskin jacket! And for me it's a symbol of my individuality, and my belief... in personal freedom.

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured