Annotation of qemu/roms/SLOF/llfw/romfs.S, revision 1.1

1.1     ! root        1: /******************************************************************************
        !             2:  * Copyright (c) 2004, 2008 IBM Corporation
        !             3:  * All rights reserved.
        !             4:  * This program and the accompanying materials
        !             5:  * are made available under the terms of the BSD License
        !             6:  * which accompanies this distribution, and is available at
        !             7:  * http://www.opensource.org/licenses/bsd-license.php
        !             8:  *
        !             9:  * Contributors:
        !            10:  *     IBM Corporation - initial implementation
        !            11:  *****************************************************************************/
        !            12: #include "macros.h"
        !            13: #include "romfs.h"
        !            14: 
        !            15: /*******************************************************************
        !            16:  * Wrapper for romfs_lookup.
        !            17:  *
        !            18:  * Input:
        !            19:  * R3 = address of filename string
        !            20:  * R4 = address of struct romfs_t
        !            21:  *              0: file size (return)
        !            22:  *              8: flags     (return)
        !            23:  *             10: fileaddr  (return and input: tells if first search)
        !            24:  *             18: nextfile  (return)
        !            25:  *             20: namep     (return)
        !            26:  *
        !            27:  * Find File Procedure
        !            28:  * - set filename and rombase, on return 0 file properties are stored
        !            29:  *   in romfs_t else struct not valid
        !            30:  * 
        !            31:  * Listing procedure
        !            32:  * - clear romfs_t (important!)
        !            33:  * - set filename = NULL and rombase and call returns first file 
        !            34:  *   with properties in romfs_t including next-file pointer
        !            35:  * - if nextpointer is non-zero then just the next file is returned
        !            36:  *
        !            37:  * Returns:
        !            38:  * <Success>: 
        !            39:  *      R3 = 0
        !            40:  *     romfs_t is updated
        !            41:  * <FileNotFound>:
        !            42:  *      R3 = 1
        !            43:  *     romfs_t not touched
        !            44:  *
        !            45:  * Potentially modifies the following registers:
        !            46:  *
        !            47:  
        !            48:  Example usage from C:
        !            49: 
        !            50:   int list_bootrom()
        !            51:   {
        !            52:        struct romfs_t rfs;
        !            53:        int i;
        !            54: 
        !            55:        printf("Build: "__TIME__" "__DATE__" \n");
        !            56: 
        !            57:        i = 0;
        !            58:        memset((void*) &rfs, 0, sizeof(struct romfs_t));
        !            59:        printf("         No. File      Data          Size  Name\n");
        !            60: 
        !            61:        while (romfs_stat(NULL, &rfs) == 0) {
        !            62:                i++;
        !            63:                printf("         %02d: %08X  %08X   %7d  %s\n",
        !            64:                                i, rfs.fileaddr, rfs.datap, 
        !            65:                                rfs.size, rfs.namep);
        !            66:        }
        !            67:        if (0 == i) {
        !            68:                printf("Error in reading ROMFS\n");
        !            69:                return 1;
        !            70:        }
        !            71:        return 0;
        !            72:   }
        !            73:  *******************************************************************/
        !            74: #define RFS_T_SIZE     0x00
        !            75: #define RFS_T_FLAGS    0x08
        !            76: #define RFS_T_FILEADDR 0x10
        !            77: #define RFS_T_NEXT     0x18
        !            78: #define RFS_T_NAME     0x20
        !            79: #define RFS_T_DATA     0x28
        !            80: 
        !            81: #define RFS_H_NEXT     0x00
        !            82: #define RFS_H_SIZE     0x08
        !            83: #define RFS_H_FLAGS    0x10
        !            84: #define RFS_H_DATA     0x18
        !            85: #define RFS_H_NAME     0x20
        !            86: 
        !            87: ENTRY(romfs_stat_file)
        !            88:        /* save link register and romfs_t pointer         */
        !            89:        mflr    r15
        !            90:        mr      r16, r4
        !            91: 
        !            92:        /* if filename R3 is 0 then its a listing request */
        !            93:        /* if not then just continue to lookup name       */
        !            94:        /* save R4 to R8 which is the address of header   */
        !            95:        li      r7, 0
        !            96:        cmpd    r3, r7
        !            97:        beq     romfs_list
        !            98:        bl      romfs_lookup
        !            99:        mfsprg  r8, 1
        !           100: 
        !           101:        /* if file found then go to romfs_fill_properties */
        !           102:        /* else return 1 to caller                        */
        !           103:        cmpwi   r3, 0
        !           104:        beq     romfs_fill_properties
        !           105:        b       romfs_stat_end
        !           106: 
        !           107:   romfs_list:
        !           108:        /* check if fileaddr == 0, in this case its       */
        !           109:        /* the first search on this handle, so return all */
        !           110:        /* info for file at rombase (R8=R4)               */
        !           111:        ld      r6, RFS_T_FILEADDR(r4)
        !           112:        mfsprg  r8, 1
        !           113:        li      r7, 0
        !           114:        cmpd    r7, r6
        !           115:        beq     romfs_fill_properties
        !           116: 
        !           117:        /* check if next file != 0   by looking into      */
        !           118:        /* romfs_t, if not then return (next = 0) 1       */
        !           119:        li      r7, 0
        !           120:        ld      r4, RFS_T_NEXT(r4)
        !           121:        cmpd    r7, r4
        !           122:        li      r3, 1
        !           123:        beq     romfs_stat_end
        !           124: 
        !           125:        /* now next file is available so move R8 to next  */
        !           126:        /* file address                                   */
        !           127:        mr      r8, r4
        !           128: 
        !           129:   romfs_fill_properties:
        !           130:        /* set properties in romfs_t takes R8 as address  */
        !           131:        /* to file header and R16 as address of romfs_t   */
        !           132:        mfsprg  r3, 1
        !           133:        std     r8, RFS_T_FILEADDR(r16)
        !           134: 
        !           135:        ld      r4, RFS_H_NEXT(r8)
        !           136:        li      r7, 0
        !           137:        cmpd    r7, r4
        !           138:        beq     $ + (2 * 4) /* =0 so add no rombase */
        !           139:        add     r4, r4, r3
        !           140:        std     r4, RFS_T_NEXT(r16)
        !           141: 
        !           142:        ld      r4, RFS_H_SIZE(r8)
        !           143:        std     r4, RFS_T_SIZE(r16)
        !           144:        ld      r4, RFS_H_FLAGS(r8)
        !           145:        std     r4, RFS_T_FLAGS(r16)
        !           146: 
        !           147:        ld      r4, RFS_H_DATA(r8)
        !           148:        add     r4, r4, r3
        !           149:        std     r4, RFS_T_DATA(r16)
        !           150: 
        !           151:        addi    r4, r8, RFS_H_NAME
        !           152:        std     r4, RFS_T_NAME(r16)
        !           153: 
        !           154:        li      r3, 0
        !           155: 
        !           156:        /* restore romfs_t pointer and link register      */
        !           157:   romfs_stat_end:
        !           158:        mr      r5, r16
        !           159:        mtlr    r15
        !           160:        blr
        !           161: 
        !           162: /*******************************************************************
        !           163:  * Copies the data of file referenced by name string to address 
        !           164:  * requires root address of filesystem.
        !           165:  * FIXME: ignores flags
        !           166:  *
        !           167:  * Input:
        !           168:  * R3 = address of filename string
        !           169:  * R4 = ROMBASE
        !           170:  * R5 = destination address
        !           171:  *
        !           172:  * Returns:
        !           173:  * <Success>: R3 = 0, R6 = size, <FileNotFound>: R3 = 1
        !           174:  * R5 is kept
        !           175:  *  
        !           176:  * Potentially modifies the following registers:
        !           177:  * ctr, r15, r16, r17, r18
        !           178:  * 
        !           179:  * Uses the following calls with subsequent register modification:
        !           180:  * - romfs_lookup
        !           181:  *******************************************************************/
        !           182: ASM_ENTRY(romfs_load)
        !           183:        mflr    r15
        !           184:        
        !           185:        /* save R5 twice              */
        !           186:        /* lookup file, input regs    */
        !           187:        /* are already set            */
        !           188:        /* if not found, just return  */
        !           189:        mr      r16, r5
        !           190:        mr      r17, r5
        !           191:        bl      romfs_lookup
        !           192:        cmpwi   r3, 1
        !           193:        bne     0f
        !           194:        mtlr    r15
        !           195:        blr     /* abort, not found   */
        !           196: 
        !           197:        /* save data size for return  */
        !           198:        /* found, copy data           */
        !           199:        /* data size is in R6         */
        !           200: 0:
        !           201:        //mr    r3, r6
        !           202:        mtctr   r6
        !           203:        addi    r16, r16, -1 /* dest  */
        !           204:        addi    r5, r5, -1   /* source*/
        !           205: 
        !           206:        /* data is expected to be     */
        !           207:        /* 8 byte aligned             */
        !           208:        /* copy loop                  */
        !           209: 0:     lbzu    r18, 1(r5)
        !           210:        stbu    r18, 1(r16)
        !           211:        bdnz    0b
        !           212: 
        !           213:        /* restore size, keep padding */
        !           214:        /* restore target address     */
        !           215:        /* return                     */
        !           216:        mr      r5, r17
        !           217:        mtlr    r15
        !           218:        blr
        !           219: 
        !           220: /*******************************************************************
        !           221:  * looks up a file based on filename 
        !           222:  *
        !           223:  * Input:
        !           224:  * R3 = address of filename string
        !           225:  * R4 = ROMBASE
        !           226:  *
        !           227:  * Returns:
        !           228:  * <Success>: 
        !           229:  *      R3 = 0
        !           230:  *      R4 = address of file header
        !           231:  *      R5 = address of data (real address)
        !           232:  *      R6 = size of data
        !           233:  *      R7 = flags for file
        !           234:  * <FileNotFound>:
        !           235:  *      R3 = 1
        !           236:  *
        !           237:  * Potentially modifies the following registers:
        !           238:  * R3, R4, R5, R6, R7, R8, R9
        !           239:  * 
        !           240:  * Uses the following calls with subsequent register modification:
        !           241:  * - romfs_namematch
        !           242:  *******************************************************************/
        !           243: ASM_ENTRY(romfs_lookup)
        !           244:        mflr    r9
        !           245:        
        !           246:   romfs_lookup_next:
        !           247:        /* save current file base        */
        !           248:        mr      r8, r4
        !           249:        /* name to look for              */
        !           250:        mr      r10, r3 
        !           251:        /* name of file                  */
        !           252:        mr      r5,  r4
        !           253:        addi    r5,  r5, (4 /* elems     */ * 8 /* elem-size */)
        !           254:        mr      r11, r5 /* for namematch */
        !           255:        /* compare                       */
        !           256:        bl      romfs_namematch
        !           257:        cmpwi   r12, 1
        !           258:        bne     romfs_lookup_match
        !           259: 
        !           260:        /* load next pointer             */
        !           261:        /* check if next is 0            */
        !           262:        /* apply root-offset             */
        !           263:        ld      r5, 0(r4)
        !           264:        cmpwi   r5, 0
        !           265:        add     r4, r4, r5
        !           266:        bne     romfs_lookup_next
        !           267:        /* last file reached, abort      */
        !           268:        li      r3, 1
        !           269:        mtlr    r9
        !           270:        blr
        !           271: 
        !           272:        /* here the name did match       */
        !           273:        /* r4 is still usable here and   */
        !           274:        /* pointing to the initial file  */
        !           275:        /* load r5 with data ptr         */
        !           276:        /* load r6 with data size        */
        !           277:        /* load r7 with flags            */
        !           278:        /* get abs addr of data          */
        !           279:   romfs_lookup_match:
        !           280:        li      r3, 0
        !           281:        ld      r5, (3 * 8)(r4) /* data  */
        !           282:        ld      r6, (1 * 8)(r4) /* len   */
        !           283:        ld      r7, (2 * 8)(r4) /* flags */
        !           284:        add     r5, r5, r8
        !           285:        mtlr    r9
        !           286:        blr
        !           287: 
        !           288: /*******************************************************************
        !           289:  * compares two strings in memory, 
        !           290:  * both must be null-terminated and 8-byte aligned
        !           291:  *
        !           292:  * Input:
        !           293:  * R10 = string 1
        !           294:  * R11 = string 2
        !           295:  *
        !           296:  * Returns:
        !           297:  * <Match>: R12 = 0 <NoMatch>: R12 = 1
        !           298:  *
        !           299:  * Potentially modifies the following registers:
        !           300:  * R10, R11, r12, r13, r14 
        !           301:  *******************************************************************/
        !           302: romfs_namematch:
        !           303:        subi    r10, r10, 8
        !           304:        subi    r11, r11, 8
        !           305: 
        !           306:        /* 
        !           307:         * load chars as 8byte chunk from current pos, name is 
        !           308:         * always 8 byte aligned :)
        !           309:         */
        !           310:   romfs_cmp_loop:
        !           311:        ldu     r13, 8(r10) /* A */
        !           312:        ldu     r14, 8(r11) /* B */
        !           313: 
        !           314:        cmpd    r13, r14
        !           315:        li      r12, 1
        !           316:        beq     1f
        !           317:        blr
        !           318: 
        !           319: 1:     andi.   r14, r14, 0xff
        !           320:        bne     romfs_cmp_loop
        !           321: 
        !           322:        li      r12, 0
        !           323:        blr
        !           324: 
        !           325: /*******************************************************************
        !           326:  * wrapper for romfs_lookup
        !           327:  * this function saves the registers from r13 - r15 on the stack
        !           328:  * calls romfs_lookup
        !           329:  * restores the saved registers
        !           330:  *
        !           331:  * the return parameters are copied to (r5) and (r5) has to
        !           332:  * be 0x20 big
        !           333:  *******************************************************************/
        !           334: ENTRY(c_romfs_lookup)
        !           335:        stdu    r1,-0x50(r1)            # allocate space on stack
        !           336: 
        !           337:        mflr    r0                      # save link register
        !           338:        std     r0,0x30(r1)
        !           339: 
        !           340:        std     r15,0x38(r1)            # save r15
        !           341:        std     r14,0x40(r1)            # save r14
        !           342:        std     r13,0x48(r1)            # and r13
        !           343:        
        !           344:        mr      r15,r5                  # save the pointer for the return value
        !           345: 
        !           346:        bl      romfs_lookup            # do the thing
        !           347: 
        !           348:        ld      r0,0x30(r1)             # restore link register
        !           349:        mtlr    r0
        !           350: 
        !           351:        std     r4,0x00(r15)            # copy return values
        !           352:        std     r5,0x08(r15)            # to the return pointer
        !           353:        std     r6,0x10(r15)
        !           354:        std     r7,0x18(r15)
        !           355: 
        !           356:        ld      r13,0x48(r1)            # restore registers from stack
        !           357:        ld      r14,0x40(r1)
        !           358:        ld      r15,0x38(r1)
        !           359: 
        !           360:        addi    r1,r1,0x50              # cleanup stack
        !           361: 
        !           362:        blr

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.