[BACK]Return to cdbr.S CVS log [TXT][DIR] Up to [local] / sys / arch / i386 / stand / cdbr

Annotation of sys/arch/i386/stand/cdbr/cdbr.S, Revision 1.1.1.1

1.1       nbrk        1: /*     $OpenBSD: cdbr.S,v 1.2 2004/08/24 15:24:05 tom Exp $    */
                      2:
                      3: /*
                      4:  * Copyright (c) 2004 Tom Cosgrove <tom.cosgrove@arches-consulting.com>
                      5:  * Copyright (c) 2001 John Baldwin <jhb@FreeBSD.org>
                      6:  * All rights reserved.
                      7:  *
                      8:  * Redistribution and use in source and binary forms, with or without
                      9:  * modification, are permitted provided that the following conditions
                     10:  * are met:
                     11:  * 1. Redistributions of source code must retain the above copyright
                     12:  *    notice, this list of conditions and the following disclaimer.
                     13:  * 2. Redistributions in binary form must reproduce the above copyright
                     14:  *    notice, this list of conditions and the following disclaimer in the
                     15:  *    documentation and/or other materials provided with the distribution.
                     16:  * 3. Neither the name of the author nor the names of any co-contributors
                     17:  *    may be used to endorse or promote products derived from this software
                     18:  *    without specific prior written permission.
                     19:  *
                     20:  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
                     21:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     22:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     23:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
                     24:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     25:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     26:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     27:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     28:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     29:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     30:  * SUCH DAMAGE.
                     31:  */
                     32:
                     33:        .file   "cdbr.S"
                     34:
                     35: /* #include <machine/asm.h> */
                     36: /* #include <assym.h> */
                     37:
                     38: /*
                     39:  * This program is a CD boot sector, similar to the partition boot record
                     40:  * (pbr, also called biosboot) used by hard disks.  It is implemented as a
                     41:  * "no-emulation" boot sector, as described in the "El Torito" Bootable
                     42:  * CD-ROM Format Specification.
                     43:  *
                     44:  * The function of this boot sector is to load and start the next-stage
                     45:  * cdboot program, which will load the kernel.
                     46:  *
                     47:  * The El Torito standard allows us to specify where we want to be loaded,
                     48:  * but for maximum compatibility we choose the default load address of
                     49:  * 0x07C00.
                     50:  *
                     51:  * Memory layout:
                     52:  *
                     53:  * 0x00000 -> 0x003FF  real mode interrupt vector table
                     54:  * 0x00400 -> 0x00500  BIOS data segment
                     55:  *
                     56:  * 0x00000 -> 0x073FF  our stack (grows down)          (from 29k)
                     57:  * 0x07400 -> 0x07BFF  we relocate to here             (at 29k)
                     58:  * 0x07C00 -> 0x08400  BIOS loads us here              (at 31k, for 2k)
                     59:  * 0x07C00 -> ...      /cdboot
                     60:  *
                     61:  * The BIOS loads us at physical address 0x07C00.  We then relocate to
                     62:  * 0x07400, seg:offset 0740:0000.  We then load /cdboot at seg:offset
                     63:  * 07C0:0000.
                     64:  */
                     65: #define BOOTSEG                0x7c0                   /* segment we're loaded to */
                     66: #define BOOTSECTSIZE   0x800                   /* our size in bytes */
                     67: #define BOOTRELOCSEG   0x740                   /* segment we relocate to */
                     68: #define BOOTSTACKOFF  ((BOOTRELOCSEG << 4) - 4)        /* starts here, grows down */
                     69:
                     70: /* Constants for reading from the CD */
                     71: #define ERROR_TIMEOUT          0x80            /* BIOS timeout on read */
                     72: #define NUM_RETRIES            3               /* Num times to retry */
                     73: #define SECTOR_SIZE            0x800           /* size of a sector */
                     74: #define SECTOR_SHIFT           11              /* number of place to shift */
                     75: #define BUFFER_LEN             0x100           /* number of sectors in buffr */
                     76: #define MAX_READ               0x10000         /* max we can read at a time */
                     77: #define MAX_READ_PARAS         MAX_READ >> 4
                     78: #define MAX_READ_SEC           MAX_READ >> SECTOR_SHIFT
                     79: #define MEM_READ_BUFFER                0x9000          /* buffer to read from CD */
                     80: #define MEM_VOLDESC            MEM_READ_BUFFER /* volume descriptor */
                     81: #define MEM_DIR                        MEM_VOLDESC+SECTOR_SIZE /* Lookup buffer */
                     82: #define VOLDESC_LBA            0x10            /* LBA of vol descriptor */
                     83: #define VD_PRIMARY             1               /* Primary VD */
                     84: #define VD_END                 255             /* VD Terminator */
                     85: #define VD_ROOTDIR             156             /* Offset of Root Dir Record */
                     86: #define DIR_LEN                        0               /* Offset of Dir Rec length */
                     87: #define DIR_EA_LEN             1               /* Offset of EA length */
                     88: #define DIR_EXTENT             2               /* Offset of 64-bit LBA */
                     89: #define DIR_SIZE               10              /* Offset of 64-bit length */
                     90: #define DIR_NAMELEN            32              /* Offset of 8-bit name len */
                     91: #define DIR_NAME               33              /* Offset of dir name */
                     92:
                     93:        .text
                     94:        .code16
                     95:
                     96:        .globl  start
                     97: start:
                     98:        /* Set up stack */
                     99:        xorw    %ax, %ax
                    100:        movw    %ax, %ss
                    101:        movw    $BOOTSTACKOFF, %sp
                    102:
                    103:        /* Relocate so we can load cdboot where we were */
                    104:        movw    $BOOTSEG, %ax
                    105:        movw    %ax, %ds
                    106:        movw    $BOOTRELOCSEG, %ax
                    107:        movw    %ax, %es
                    108:        xorw    %si, %si
                    109:        xorw    %di, %di
                    110:        movw    $BOOTSECTSIZE, %cx      /* Bytes in cdbr, relocate it all */
                    111:        cld
                    112:        rep
                    113:        movsb
                    114:
                    115:        /* Jump to relocated self */
                    116:        ljmp $BOOTRELOCSEG, $reloc
                    117: reloc:
                    118:
                    119:        /*
                    120:         * Set up %ds and %es: %ds is our data segment (= %cs), %es is
                    121:         * used to specify the segment address of the destination buffer
                    122:         * for cd reads.  We initially have %es = %ds.
                    123:         */
                    124:        movw    %cs, %ax
                    125:        movw    %ax, %ds
                    126:        movw    %ax, %es
                    127:
                    128:        movb    %dl, drive              /* Store the boot drive number */
                    129:
                    130:        movw    $signon, %si            /* Say "hi", and give boot drive */
                    131:        call    display_string
                    132:        movb    drive, %al
                    133:        call    hex_byte
                    134:        movw    $crlf, %si
                    135:        call    display_string
                    136:
                    137: /*
                    138:  * Load Volume Descriptor
                    139:  */
                    140:        movl    $VOLDESC_LBA, %eax      /* Get the sector # for vol desc */
                    141: load_vd:
                    142:        pushl   %eax
                    143:        movb    $1, %dh                 /* One sector */
                    144:        movw    $MEM_VOLDESC, %bx       /* Destination */
                    145:        call    read                    /* Read it in */
                    146:        popl    %eax
                    147:        cmpb    $VD_PRIMARY, (%bx)      /* Primary vol descriptor? */
                    148:        je      have_vd                 /* Yes */
                    149:        inc     %eax                    /* Try the next one */
                    150:        cmpb    $VD_END, (%bx)          /* Is it the last one? */
                    151:        jne     load_vd                 /* No, so go try the next one */
                    152:        movw    $msg_novd, %si          /* No pri vol descriptor */
                    153:        jmp     err_stop                /* Panic */
                    154: have_vd:                               /* Have Primary VD */
                    155:
                    156: /*
                    157:  * Look for the next-stage loader binary at pre-defined paths (loader_paths)
                    158:  */
                    159:        movw    $loader_paths, %si      /* Point to start of array */
                    160: lookup_path:
                    161:        movw    %si, loader             /* remember the one we're looking for */
                    162:        pushw   %si                     /* Save file name pointer */
                    163:        call    lookup                  /* Try to find file */
                    164:        popw    %di                     /* Restore file name pointer */
                    165:        jnc     lookup_found            /* Found this file */
                    166:        xorb    %al, %al                /* Look for next */
                    167:        movw    $0xffff, %cx            /*  path name by */
                    168:        repnz                           /*  scanning for */
                    169:        scasb                           /*  nul char */
                    170:        movw    %di, %si                /* Point %si at next path */
                    171:        movb    (%si), %al              /* Get first char of next path */
                    172:        orb     %al, %al                /* Is it double nul? */
                    173:        jnz     lookup_path             /* No, try it */
                    174:        movw    $msg_failed, %si        /* Failed message */
                    175:        jmp     err_stop                /* Print it and halt */
                    176:
                    177: lookup_found:                          /* Found a loader file */
                    178:
                    179: /*
                    180:  * Load the binary into the buffer.  Due to real mode addressing limitations
                    181:  * we have to read it in in 64k chunks.
                    182:  */
                    183:        movl    DIR_SIZE(%bx), %eax     /* Read file length */
                    184:        add     $SECTOR_SIZE-1, %eax    /* Convert length to sectors */
                    185:        shr     $SECTOR_SHIFT, %eax
                    186:        cmp     $BUFFER_LEN, %eax
                    187:        jbe     load_sizeok
                    188:        movw    $msg_load2big, %si      /* Error message */
                    189:        jmp     err_stop
                    190: load_sizeok:
                    191:        movzbw  %al, %cx                /* Num sectors to read */
                    192:        movl    DIR_EXTENT(%bx), %eax   /* Load extent */
                    193:        xorl    %edx, %edx
                    194:        movb    DIR_EA_LEN(%bx), %dl
                    195:        addl    %edx, %eax              /* Skip extended */
                    196:
                    197:        /* Use %bx to hold the segment (para) number */
                    198:        movw    $BOOTSEG, %bx           /* We put cdboot here too */
                    199: load_loop:
                    200:        movb    %cl, %dh
                    201:        cmpb    $MAX_READ_SEC, %cl      /* Truncate to max read size */
                    202:        jbe     load_notrunc
                    203:        movb    $MAX_READ_SEC, %dh
                    204: load_notrunc:
                    205:        subb    %dh, %cl                /* Update count */
                    206:        pushl   %eax                    /* Save */
                    207:        movw    %bx, %es                /* %bx had the segment (para) number */
                    208:        xorw    %bx, %bx                /* %es:0000  for destination */
                    209:        call    read                    /* Read it in */
                    210:        popl    %eax                    /* Restore */
                    211:        addl    $MAX_READ_SEC, %eax     /* Update LBA */
                    212:        addw    $MAX_READ_PARAS, %bx    /* Update dest addr */
                    213:        jcxz    load_done               /* Done? */
                    214:        jmp     load_loop               /* Keep going */
                    215: load_done:
                    216:
                    217:        /* Now we can start the loaded program */
                    218:
                    219:        movw    loader, %cx             /* Tell cdboot where it is */
                    220:                                        /* (Older versions of cdbr have */
                    221:                                        /*  %cx == 0 from the jcxz load_done) */
                    222:        movb    drive, %dl              /* Get the boot drive number */
                    223:        ljmp    $BOOTSEG, $0            /* Go run cdboot */
                    224:
                    225: /*
                    226:  * Lookup the file in the path at [SI] from the root directory.
                    227:  *
                    228:  * Trashes: All but BX
                    229:  * Returns: CF = 0 (success), BX = pointer to record
                    230:  *          CF = 1 (not found)
                    231:  */
                    232: lookup:
                    233:        movw    $VD_ROOTDIR + MEM_VOLDESC, %bx  /* Root directory record */
                    234:
                    235: lookup_dir:
                    236:        lodsb                           /* Get first char of path */
                    237:        cmpb    $0, %al                 /* Are we done? */
                    238:        je      lookup_done             /* Yes */
                    239:        cmpb    $'/', %al               /* Skip path separator */
                    240:        je      lookup_dir
                    241:        decw    %si                     /* Undo lodsb side effect */
                    242:        call    find_file               /* Lookup first path item */
                    243:        jnc     lookup_dir              /* Try next component */
                    244:        ret
                    245: lookup_done:
                    246:        movw    $msg_loading, %si       /* Success message - say which file */
                    247:        call    display_string
                    248:        mov     loader, %si
                    249:        call    display_string
                    250:        mov     $crlf, %si
                    251:        call    display_string
                    252:        clc                             /* Clear carry */
                    253:        ret
                    254:
                    255: /*
                    256:  * Lookup file at [SI] in directory whose record is at [BX].
                    257:  *
                    258:  * Trashes: All but returns
                    259:  * Returns: CF = 0 (success), BX = pointer to record, SI = next path item
                    260:  *          CF = 1 (not found), SI = preserved
                    261:  */
                    262: find_file:
                    263:        mov     DIR_EXTENT(%bx), %eax   /* Load extent */
                    264:        xor     %edx, %edx
                    265:        mov     DIR_EA_LEN(%bx), %dl
                    266:        add     %edx, %eax              /* Skip extended attributes */
                    267:        mov     %eax, rec_lba           /* Save LBA */
                    268:        mov     DIR_SIZE(%bx), %eax     /* Save size */
                    269:        mov     %eax, rec_size
                    270:        xor     %cl, %cl                /* Zero length */
                    271:        push    %si                     /* Save */
                    272: ff_namelen:
                    273:        inc     %cl                     /* Update length */
                    274:        lodsb                           /* Read char */
                    275:        cmp     $0, %al                 /* Nul? */
                    276:        je      ff_namedone             /* Yes */
                    277:        cmp     $'/', %al               /* Path separator? */
                    278:        jnz     ff_namelen              /* No, keep going */
                    279: ff_namedone:
                    280:        dec     %cl                     /* Adjust length and save */
                    281:        mov     %cl, name_len
                    282:        pop     %si                     /* Restore */
                    283: ff_load:
                    284:        mov     rec_lba, %eax           /* Load LBA */
                    285:        mov     $MEM_DIR, %ebx          /* Address buffer */
                    286:        mov     $1, %dh                 /* One sector */
                    287:        call    read                    /* Read directory block */
                    288:        incl    rec_lba                 /* Update LBA to next block */
                    289: ff_scan:
                    290:        mov     %ebx, %edx              /* Check for EOF */
                    291:        sub     $MEM_DIR, %edx
                    292:        cmp     %edx, rec_size
                    293:        ja      ff_scan_1
                    294:        stc                             /* EOF reached */
                    295:        ret
                    296: ff_scan_1:
                    297:        cmpb    $0, DIR_LEN(%bx)        /* Last record in block? */
                    298:        je      ff_nextblock
                    299:        push    %si                     /* Save */
                    300:        movzbw  DIR_NAMELEN(%bx), %si   /* Find end of string */
                    301: ff_checkver:
                    302:        cmpb    $'0', DIR_NAME-1(%bx,%si)       /* Less than '0'? */
                    303:        jb      ff_checkver_1
                    304:        cmpb    $'9', DIR_NAME-1(%bx,%si)       /* Greater than '9'? */
                    305:        ja      ff_checkver_1
                    306:        dec     %si                     /* Next char */
                    307:        jnz     ff_checkver
                    308:        jmp     ff_checklen             /* All numbers in name, so */
                    309:                                        /*  no version */
                    310: ff_checkver_1:
                    311:        movzbw  DIR_NAMELEN(%bx), %cx
                    312:        cmp     %cx, %si                /* Did we find any digits? */
                    313:        je      ff_checkdot             /* No */
                    314:        cmpb    $';', DIR_NAME-1(%bx,%si)       /* Check for semicolon */
                    315:        jne     ff_checkver_2
                    316:        dec     %si                     /* Skip semicolon */
                    317:        mov     %si, %cx
                    318:        mov     %cl, DIR_NAMELEN(%bx)   /* Adjust length */
                    319:        jmp     ff_checkdot
                    320: ff_checkver_2:
                    321:        mov     %cx, %si                /* Restore %si to end of string */
                    322: ff_checkdot:
                    323:        cmpb    $'.', DIR_NAME-1(%bx,%si)       /* Trailing dot? */
                    324:        jne     ff_checklen                     /* No */
                    325:        decb    DIR_NAMELEN(%bx)        /* Adjust length */
                    326: ff_checklen:
                    327:        pop     %si                     /* Restore */
                    328:        movzbw  name_len, %cx           /* Load length of name */
                    329:        cmp     %cl, DIR_NAMELEN(%bx)   /* Does length match? */
                    330:        je      ff_checkname            /* Yes, check name */
                    331: ff_nextrec:
                    332:        add     DIR_LEN(%bx), %bl       /* Next record */
                    333:        adc     $0, %bh
                    334:        jmp     ff_scan
                    335: ff_nextblock:
                    336:        subl    $SECTOR_SIZE, rec_size  /* Adjust size */
                    337:        jnc     ff_load                 /* If subtract ok, keep going */
                    338:        ret                             /* End of file, so not found */
                    339: ff_checkname:
                    340:        lea     DIR_NAME(%bx), %di      /* Address name in record */
                    341:        push    %si                     /* Save */
                    342:        repe    cmpsb                   /* Compare name */
                    343:        jcxz    ff_match                /* We have a winner! */
                    344:        pop     %si                     /* Restore */
                    345:        jmp     ff_nextrec              /* Keep looking */
                    346: ff_match:
                    347:        add     $2, %sp                 /* Discard saved %si */
                    348:        clc                             /* Clear carry */
                    349:        ret
                    350:
                    351: /*
                    352:  * Load DH sectors starting at LBA %eax into address %es:%bx.
                    353:  *
                    354:  * Preserves %bx, %cx, %dx, %si, %es
                    355:  * Trashes %eax
                    356:  */
                    357: read:
                    358:        pushw   %si                     /* Save */
                    359:        pushw   %cx                     /* Save since some BIOSs trash */
                    360:        movl    %eax, edd_lba           /* LBA to read from */
                    361:        movw    %es, %ax                /* Get the segment */
                    362:        movw    %ax, edd_addr + 2       /*  and store */
                    363:        movw    %bx, edd_addr           /* Store offset too */
                    364: read_retry:
                    365:        call    twiddle                 /* Entertain the user */
                    366:        pushw   %dx                     /* Save */
                    367:        movw    $edd_packet, %si        /* Address Packet */
                    368:        movb    %dh, edd_len            /* Set length */
                    369:        movb    drive, %dl              /* BIOS Device */
                    370:        movb    $0x42, %ah              /* BIOS: Extended Read */
                    371:        int     $0x13                   /* Call BIOS */
                    372:        popw    %dx                     /* Restore */
                    373:        jc      read_fail               /* Worked? */
                    374:        popw    %cx                     /* Restore */
                    375:        popw    %si
                    376:        ret                             /* Return */
                    377: read_fail:
                    378:        cmpb    $ERROR_TIMEOUT, %ah     /* Timeout? */
                    379:        je      read_retry              /* Yes, Retry */
                    380: read_error:
                    381:        pushw   %ax                     /* Save error */
                    382:        movw    $msg_badread, %si       /* "Read error: 0x" */
                    383:        call    display_string
                    384:        popw    %ax                     /* Retrieve error code */
                    385:        movb    %ah, %al                /* Into %al */
                    386:        call    hex_byte                /* Display error code */
                    387:        jmp     stay_stopped            /* ... then hang */
                    388:
                    389: /*
                    390:  * Display the ASCIZ error message in %esi then halt
                    391:  */
                    392: err_stop:
                    393:        call    display_string
                    394:
                    395: stay_stopped:
                    396:        sti                             /* Ensure Ctl-Alt-Del will work */
                    397:        hlt                             /* (don't require power cycle) */
                    398:        jmp     stay_stopped            /* (Just to make sure) */
                    399:
                    400: /*
                    401:  * Output the "twiddle"
                    402:  */
                    403: twiddle:
                    404:        push    %ax                     /* Save */
                    405:        push    %bx                     /* Save */
                    406:        mov     twiddle_index, %al      /* Load index */
                    407:        mov     twiddle_chars, %bx      /* Address table */
                    408:        inc     %al                     /* Next */
                    409:        and     $3, %al                 /*  char */
                    410:        mov     %al, twiddle_index      /* Save index for next call */
                    411:        xlat                            /* Get char */
                    412:        call    display_char            /* Output it */
                    413:        mov     $8, %al                 /* Backspace */
                    414:        call    display_char            /* Output it */
                    415:        pop     %bx                     /* Restore */
                    416:        pop     %ax                     /* Restore */
                    417:        ret
                    418:
                    419: /*
                    420:  * Display the ASCIZ string pointed to by %si.
                    421:  *
                    422:  * Destroys %si, possibly others.
                    423:  */
                    424: display_string:
                    425:        pushw   %ax
                    426:        cld
                    427: 1:
                    428:        lodsb                   /* %al = *%si++ */
                    429:        testb   %al, %al
                    430:        jz      1f
                    431:        call    display_char
                    432:        jmp     1b
                    433:
                    434: /*
                    435:  * Write out value in %eax in hex
                    436:  */
                    437: hex_long:
                    438:        pushl   %eax
                    439:        shrl    $16, %eax
                    440:        call    hex_word
                    441:        popl    %eax
                    442:        /* fall thru */
                    443:
                    444: /*
                    445:  * Write out value in %ax in hex
                    446:  */
                    447: hex_word:
                    448:        pushw   %ax
                    449:        mov     %ah, %al
                    450:        call    hex_byte
                    451:        popw    %ax
                    452:        /* fall thru */
                    453: /*
                    454:  * Write out value in %al in hex
                    455:  */
                    456: hex_byte:
                    457:        pushw   %ax
                    458:        shrb    $4, %al
                    459:        call    hex_nibble
                    460:        popw    %ax
                    461:        /* fall thru */
                    462:
                    463: /* Write out nibble in %al */
                    464: hex_nibble:
                    465:        and     $0x0F, %al
                    466:        add     $'0', %al
                    467:        cmpb    $'9', %al
                    468:        jbe     display_char
                    469:        addb    $'A'-'9'-1, %al
                    470:        /* fall thru to display_char */
                    471:
                    472: /*
                    473:  * Display the character in %al
                    474:  */
                    475: display_char:
                    476:        pushw   %ax
                    477:
                    478:        pushw   %bx
                    479:        movb    $0x0e, %ah
                    480:        movw    $1, %bx
                    481:        int     $0x10
                    482:        popw    %bx
                    483: 1:     popw    %ax
                    484:        ret
                    485:
                    486: /*
                    487:  * Data
                    488:  */
                    489: drive:         .byte   0                       /* Given to us by the BIOS */
                    490: signon:                .asciz  "CD-ROM: "
                    491: crlf:          .asciz  "\r\n"
                    492: msg_load2big:  .asciz  "File too big"
                    493: msg_badread:   .asciz  "Read error: 0x"
                    494: msg_novd:      .asciz  "No Primary Volume Descriptor"
                    495: msg_loading:   .asciz  "Loading "
                    496:
                    497: /* State for searching dir */
                    498: rec_lba:       .long   0x0                     /* LBA (adjusted for EA) */
                    499: rec_size:      .long   0x0                     /* File size */
                    500: name_len:      .byte   0x0                     /* Length of current name */
                    501:
                    502: twiddle_index: .byte   0x0
                    503: twiddle_chars: .ascii  "|/-\\"
                    504:
                    505: /* Packet for LBA (CD) read */
                    506: edd_packet:    .byte   0x10                    /* Length */
                    507:                .byte   0                       /* Reserved */
                    508: edd_len:       .byte   0x0                     /* Num to read */
                    509:                .byte   0                       /* Reserved */
                    510: edd_addr:      .word   0x0, 0x0                /* Seg:Off */
                    511: edd_lba:       .quad   0x0                     /* LBA */
                    512:
                    513: /* The data from here must be last in the file, only followed by 0x00 bytes */
                    514:
                    515: loader:                .word   0                       /* The path we end up using */
                    516:
                    517: msg_failed:    .ascii  "Can't find "           /* This string runs into... */
                    518:
                    519: /* loader_paths is a list of ASCIZ strings followed by a term NUL byte */
                    520: loader_paths:  .asciz  "/cdboot"
                    521:                .asciz  "/CDBOOT"
                    522:                .ascii  "/", OSREV, "/", MACH, "/cdboot"
                    523:                .byte   0                       /* NUL-term line above */
                    524:                .ascii  "/", OSREV, "/", MACH_U, "/CDBOOT"
                    525:                .byte   0                       /* NUL-term line above */
                    526:                .byte   0                       /* Terminate the list */
                    527:
                    528:        . = BOOTSECTSIZE
                    529:
                    530:        .end

CVSweb