• 代码片段_配置文件解析_1


    配置文件的内容格式如下:

    # Copyright (c) 2013 Peng Donglin.
    #
    # Authors: Peng Donglin  <pengdonglin137@163.com>
    #
    
    # this is a config file
    # 
    # imagenum            : the number of images included in output file 
    # output              : the file name of update package
    #
    # enable              :  
    #                       0: the corresponding image will not be included in update package
    #                       1: the corresponding image will be included int update package
    # type                : 
    #                       0: HEAD_INFO_TYPE_UPDATE_FILE
    #                       1: HEAD_INFO_TYPE_TOOL
    #                       2: HEAD_INFO_TYPE_IVA
    # filename            : the image name which will be deal with
    # flashoffset         : tht offset of corresponding image in /dev/mtdx
    # flashtype           : Nand or Nor
    # imageorder          : the order number of image  at the same partition
    # erase_or_not        : 1 erase /dev/mtdx   0 not erase /dev/mtdx
    #                       if imageorder is not 0, the erase_or_not must be 0
    # reserve             : the size of area not to be erased at the end of /dev/mtdx
    # imagetype           : yaffs/jffs2/data/oob_raw/ubi 
    #                       data : the image which does not have oob area
    #                       oob_raw : the image which has oob area, but not yaffs or jffs2, such as sony's spl and sony's uboot
    #                       ubi: first of all, copy the image to the memory(/tmp/filename),then use function ubiformat to write the image into /dev/mtdx
    # mtd                 : the dev node which the corresponding image will be write in 
    # oob_usr_offset      : the offset of oob_usr  in  oob area
    # oob_usr_length      : the length of oob_usr data
    
    < MAIN >
    
    output          = dvr_img.bin
    
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = u-boot_evb_nandspl_bs.bin.raw
    flashoffset     = 0x0
    flashtype       = Nand
    imageorder      = 0
    erase_or_not    = 1
    reserve         = 0x0
    imagetype       = oob_raw
    mtd             = /dev/mtd0
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = u-boot_evb_bs.bin.raw
    flashoffset     = 0x0
    flashtype       = Nand
    imageorder      = 0
    erase_or_not    = 1
    reserve         = 0x400000
    imagetype       = oob_raw
    mtd             = /dev/mtd1
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = ubenv0.bin
    flashoffset     = 0xB00000
    flashtype       = Nand
    imageorder      = 1
    erase_or_not    = 0
    reserve         = 0x0
    imagetype       = data
    mtd             = /dev/mtd1
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = ubenv1.bin
    flashoffset     = 0xB80000
    flashtype       = Nand
    imageorder      = 2
    erase_or_not    = 0
    reserve         = 0x0
    imagetype       = data
    mtd             = /dev/mtd1
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = ubifs_fw.ubi
    flashoffset     = 0x0
    flashtype       = Nand
    imageorder      = 0
    erase_or_not    = 1
    reserve         = 0x0
    imagetype       = ubi
    mtd             = /dev/mtd2
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = ubifs_rootfs.ubi
    flashoffset     = 0x0
    flashtype       = Nand
    imageorder      = 0
    erase_or_not    = 1
    reserve         = 0x0
    imagetype       = data
    mtd             = /dev/mtd3
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    < HEADER >
    enable          = 1
    type            = 0
    filename        = ubifs_local.ubi
    flashoffset     = 0x0
    flashtype       = Nand
    imageorder      = 0
    erase_or_not    = 1
    reserve         = 0x0
    imagetype       = data
    mtd             = /dev/mtd5
    
    blocksize       = 128KiB
    pagesize        = 2KiB
    oobsize         = 64
    
    oob_usr_offset  = 0
    oob_usr_length  = 32
    
    #note: the header that describes uptool should be placed at the end.
    < HEADER >
    enable          = 1
    type            = 1
    filename        = uptool
    
    < END >

    解析:

    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include <fcntl.h>
    #include <strings.h>
    #include <unistd.h>
    
    #include <sys/types.h>
    #include <sys/stat.h>
    
    #include "mk_dvr_img.h"
    
    #define err_msg(fmt, ...) ({                                
        fprintf(stderr, "Error: " fmt "
    ", ##__VA_ARGS__); 
        -1;                                                 
    })
    
    struct head_info heads[10] ;
    int heads_count = 0;
    char update_filename[256] = {0};
    
    static char *appcmd_strim(char *s, const char *skip_str)
    {
        char *e = s+strlen(s)-1;
        while(*s && strchr(skip_str,*s)) {*s++=0;};
        while(*e && e>s && strchr(skip_str,*e)) {*e=0;e--;};
        return s;
    }
    
    static int get_multiplier(const char *str)
    {
        if (!str)
            return 1;
    
        /* Remove spaces before the specifier */
        while (*str == ' ' || *str == '	')
            str += 1;
    
        if (!strcmp(str, "KiB"))
            return 1024;
        if (!strcmp(str, "MiB"))
            return 1024 * 1024;
        if (!strcmp(str, "GiB"))
            return 1024 * 1024 * 1024;
    
        return -1;
    }
    
    
    static unsigned int get_bytes(const char *str)
    {
        char *endp;
        unsigned int bytes = (unsigned int)strtoul(str, &endp, 0);
    
        if (endp == str || bytes < 0)
            return err_msg("incorrect amount of bytes: "%s"", str);
    
        if (*endp != '') {
            int mult = get_multiplier(endp);
    
            if (mult == -1)
                return err_msg("bad size specifier: "%s" - "
                           "should be 'KiB', 'MiB' or 'GiB'", endp);
            bytes *= mult;
        }
    
        return bytes;
    }
    
    
    static int parse_cfg(const char *filename)
    {
        FILE * fp = NULL;
        size_t len = 0;
        ssize_t read;
        char * line = NULL;
        int type = -1;
        int index = -1;
        int enable_flag = 0;
    
        fp = fopen(filename, "r");
        if(fp == NULL)
        {
            perror("fail to open config file");
            return -1;
        }
    
        printf("e[1;32mBegin to analyse %s
    e[0m", filename);
    
        while ((read = getline(&line, &len, fp)) != -1)
        {
            char *sval, *str = appcmd_strim(line, "	 ;
    ");
            int slen = str?strlen(str):0;
            if(slen<2)
                continue;
    
            /* comment */
            if (!str || *str==0 || *str=='#' || *str==';')
                continue;
    
            if(*str == '<' && str[slen-1] == '>')
            {
                str = appcmd_strim(str,"<> ");
                if(str &&strlen(str)>0)
                {
                    if(strcmp(str, "MAIN") == 0)
                    {
                        type = 0;
                        enable_flag = 0;
                        printf("
    
    ");
                    }
                    else if(strcmp(str, "HEADER") == 0)
                    {
                        type = 1;
                        enable_flag = 0;
                    }
                    else if(strcmp(str, "END") == 0)
                    {
                        heads_count = index+1;
                        fprintf(stderr, "e[1;32mparse end
    e[0m");
                        return 0;
                    }
                    else
                    {
                        type = 2;
                    }
                }
    
                continue;
            }
    
            if(enable_flag)
            {
                continue;
            }
            sval = strchr(str, '=');
            if (!sval)    continue;
            *sval++=0;
            str = appcmd_strim(str,"	 ;
    ");
            sval = appcmd_strim(sval,"	 ;
    ");
    
            if(str && *str&& sval&&*sval)
            {
                if(type == 0)
                {
                    if(strcmp(str, "output") == 0)
                    {
                        strcpy(update_filename, sval);
                        printf("output file name = %s
    ", update_filename);
                    }
                }
                else if(type == 1)
                {
                    if(strcmp(str, "enable") == 0)
                    {
                        if(0 == get_bytes((const char *)sval))
                        {
                            enable_flag = 1;
                            continue;
                        }
                        else
                        {
                            index++;
                            enable_flag = 0;
                            printf("
    ");
                        }
                    }
                    else if(strcmp(str, "type") == 0)
                    {
                        heads[index].type = get_bytes((const char *)sval);
                        printf("type = %d
    ", heads[index].type);
                    }
                    else if(strcmp(str, "filename") == 0)
                    {
                        strcpy(heads[index].name, sval);
                        printf("filename = %s
    ", heads[index].name);
                    }
                    else if(strcmp(str, "flashoffset")== 0)
                    {
                        heads[index].flash_offset = get_bytes((const char *)sval);
                        printf("flashoffset = %#x
    ", heads[index].flash_offset);
                    }
                    else if(strcmp(str, "flashtype") == 0)
                    {
                        heads[index].flashType = strcmp(sval, "Nand")?NorFlash:NandFlash;
                        printf("flashtype = %s
    ", sval);
                    }
                    else if(strcmp(str, "imageorder") == 0)
                    {
                        heads[index].flash_num = get_bytes((const char *)sval);
                        printf("imageorder = %d
    ", heads[index].flash_num);
                    }
                    else if(strcmp(str, "erase_or_not") == 0)
                    {
                        heads[index].erase_or_not = get_bytes((const char *)sval);
                        printf("erase_or_not = %d
    ", heads[index].erase_or_not);
                    }
                    else if(strcmp(str, "reserve") == 0)
                    {
                        heads[index].reserve = get_bytes((const char *)sval);
                        printf("reserve = %#x
    ", heads[index].reserve);
                    }
                    else if(strcmp(str, "imagetype") == 0)
                    {
                        if(strcmp(sval, "yaffs") == 0)
                        {
                            heads[index].imageType = YAFFS;
                        }
                        else if(strcmp(sval, "jffs2") == 0)
                        {
                            heads[index].imageType = JFFS2;
                        }
                        else if(strcmp(sval, "data") == 0)
                        {
                            heads[index].imageType = DATA;
                        }
                        else if(strcmp(sval, "oob_raw") == 0)
                        {
                            heads[index].imageType = OOB_RAW;
                        }
                        else if(strcmp(sval, "ubi") == 0)
                        {
                            heads[index].imageType = UBI;
                        }
                        printf("imagetype = %d
    ", heads[index].imageType);
                    }
                    else if(strcmp(str, "mtd") == 0)
                    {
                        strcpy(heads[index].flash_addr, sval);
                        printf("mtd = %s
    ", heads[index].flash_addr);
                    }
                    else if(strcmp(str, "blocksize") == 0)
                    {
                        heads[index].blockSize = get_bytes((const char *)sval);
                        printf("blocksize = %#x
    ", heads[index].blockSize);
                    }
                    else if(strcmp(str, "pagesize") == 0)
                    {
                        heads[index].pageSize = get_bytes((const char *)sval);
                        printf("pagesize = %#x
    ", heads[index].pageSize);
                    }
                    else if(strcmp(str, "oobsize") == 0)
                    {
                        heads[index].oobSize = get_bytes((const char *)sval);
                        printf("oobsize = %d
    ", heads[index].oobSize);
                    }
                    else if(strcmp(str, "oob_usr_offset") == 0)
                    {
                        heads[index].oob_usr_offset = get_bytes((const char *)sval);
                        printf("oob_usr_offset = %#x
    ", heads[index].oob_usr_offset);
                    }
                    else if(strcmp(str, "oob_usr_length") == 0)
                    {
                        heads[index].oob_usr_length = get_bytes((const char *)sval);
                        printf("oob_usr_length = %d
    ", heads[index].oob_usr_length);
                    }
    
                }
                else if(type == 2)
                {
                    continue;
                }
            }
    
        }
    
        return 0;
    }
    
    
    int mk_dvr_img(int img_fd,struct head_info *info)
    {
        char *src = NULL;
        int fd = -1 , ret = 0;
        char buffer[2048];
        memset(buffer,0,2048);
        fd = open(info->name,O_RDONLY);
        if(fd < 0) GOTOERR(ret,fd,EXIT);
    
        src = (char *)mmap(NULL,info->size,PROT_READ,MAP_SHARED,fd,0);
        if(src == MAP_FAILED) GOTOERR(ret,-1,EXIT);
    
        info->dvr_crc = crc32((unsigned char const *)src,info->size);
    
        ret = lseek(img_fd,info->file_offset,SEEK_SET);
        if (ret <0) GOTOERR(ret,-1,EXIT);
    
        ret = write(img_fd,src, info->size );
        if (ret <0) GOTOERR(ret,-1,EXIT);
    
        //printf("offset is %d
    ",lseek(img_fd,0,SEEK_CUR));
    
        ret = 0;
    EXIT:
        munmap(src,info->size );
        close(fd);
        return ret;
    }
    
    
    int main(int argc, const char *argv[])
    {
        int ret_val = -1;
        int start_offset = 0, prev_offset = 0;
        struct stat file_stat;
        size_t uptool_offset = 0,uptool_size = 0;
        int i;
        int img_fd = -1;
        char *dst = NULL;
        struct update_file_head *update_head;
    
        if(argc != 2)
        {
            printf("Usage: ./parse_cfg  config.cfg
    ");
            goto EXIT;
        }
    
        bzero(heads,sizeof(heads) );
        ret_val = parse_cfg(argv[1]);
        if(ret_val < 0)
        {
            fprintf(stderr, "fail to parse config
    ");
            goto EXIT;
        }
    
        if(heads_count <= 0)
        {
            printf("e[1;31mthe number of image can not be zero 
    e[0m");
            goto EXIT;
        }
    
        img_fd = open(update_filename,O_RDWR | O_CREAT | O_TRUNC,0600);
        if(img_fd < 0)
        {
            printf("is open %s faild?/
    ",update_filename);
            goto EXIT;
        }
    
        start_offset = heads_count * sizeof(struct head_info) + HEAD_INFO_OFFSET;
        prev_offset = start_offset;
    
        for(i=0;i<heads_count;++i)
        {
            bzero(&file_stat,sizeof(file_stat) );
            ret_val = stat(heads[i].name,&file_stat);
            if((ret_val < 0) || (file_stat.st_size <= 0) )
            {
                if (errno == ENOENT) {printf("unable open file:%s
    ",heads[i].name);goto EXIT;}
                else if(file_stat.st_size <= 0) {printf("%s has 0 length.
    ",heads[i].name);GOTOERR(ret_val,-1,EXIT);}
                else GOTOERR(ret_val,ret_val,EXIT);
            }
    
            heads[i].size = file_stat.st_size;
            heads[i].dvr_crc = 0;
            heads[i].file_offset = prev_offset;
    
            if(strcmp("uptool",heads[i].name) == 0)
            {
                uptool_offset = heads[i].file_offset;
                uptool_size = heads[i].size;
            }
    
            prev_offset += heads[i].size;
            printf("head index = %d name = %s flash_addr = %s size = %x file_offset = %x 
    ",
                i, heads[i].name, heads[i].flash_addr, heads[i].size, heads[i].file_offset);
        }
    
        ret_val = lseek(img_fd,HEAD_INFO_OFFSET + heads_count*sizeof(struct  head_info),SEEK_SET);
        if(ret_val < 0) GOTOERR(ret_val,-1,EXIT);
        for(i=0;i<heads_count;++i){
            ret_val = mk_dvr_img(img_fd,&heads[i]);
            if(ret_val < 0) GOTOERR(ret_val,ret_val,EXIT);
        }
    
        ret_val = lseek(img_fd,HEAD_INFO_OFFSET,SEEK_SET);
        if(ret_val < 0) GOTOERR(ret_val,-1,EXIT);
        for(i=0;i<heads_count;++i){
            ret_val = write(img_fd,(char *)&heads[i],sizeof(heads[i]));
            if(ret_val < 0) GOTOERR(ret_val,-1,EXIT);
        }
    
        dst = (char *)mmap(NULL,prev_offset,PROT_READ|PROT_WRITE,MAP_SHARED,img_fd,0);
        if(dst == MAP_FAILED) GOTOERR(ret_val,-1,EXIT);
    
        update_head = (struct update_file_head *)dst;
        bzero(update_head,sizeof(struct update_file_head) );
        update_head->mark = BSTAR_UPDATE_FILE_MARK;
        update_head->ipc_mark = IPC_UPDATE_FILE_MARK;
        update_head->version = IPC_UPDATE_PROG_VER;
        update_head->datasize = prev_offset - HEAD_INFO_OFFSET;
        update_head->crc = crc32((unsigned char const *)dst + HEAD_INFO_OFFSET, update_head->datasize);
        update_head->data_start_offset = HEAD_INFO_OFFSET;
        update_head->head_info_num = heads_count;
        update_head->uptool_offset = uptool_offset;
        update_head->uptool_size = uptool_size;
    
    
        printf("update_head.crc                 = %x
    ", update_head->crc);
        printf("update_head->mark               =%d
    ", update_head->mark);
        printf("update_head->ipc_mark           = %d
    ", update_head->ipc_mark);
        printf("update_head->version            = %d
    ", update_head->version);
        printf("update_head->datasize           = %d
    ", update_head->datasize);
        printf("update_head->data_start_offset  = %d
    ", update_head->data_start_offset);
        printf("update_head->head_info_num      = %d
    ", update_head->head_info_num);
        printf("update_head->uptool_offset      = %x
    ", update_head->uptool_offset);
        printf("update_head->uptool_size        = %d
    ", update_head->uptool_size);
        printf("update_head->modCUUID           = %s", update_head->modCUUID);
    
        printf("
    ");
    
        for(i=0; i<heads_count; i++)
        {
            printf("name:                %s
    ", heads[i].name);
            printf("version:             %s
    ", heads[i].version);
            printf("flash_addr:          %s
    ", heads[i].flash_addr);
            printf("dvr_crc:             %x
    ", heads[i].dvr_crc);
            printf("size:                %x
    ", heads[i].size);
            printf("file_offset:         %x
    ", heads[i].file_offset);
            printf("type:                %d
    ", heads[i].type);
            printf("flashType:           %d
    ", heads[i].flashType);
            printf("flash_offset:        %x
    ", heads[i].flash_offset);
            printf("erase_or_not:        %d
    ", heads[i].erase_or_not);
            printf("flash_num:           %d
    ", heads[i].flash_num);
            printf("reserve  :           %d
    ", heads[i].reserve);
            printf("blockSize:           %d
    ", heads[i].blockSize);
            printf("pageSize:            %d
    ", heads[i].pageSize);
            printf("oobSize:             %d
    ", heads[i].oobSize);
            printf("oob_usr_offset:      %d
    ", heads[i].oob_usr_offset);
            printf("oob_usr_length:      %d
    ", heads[i].oob_usr_length);
            printf("imageType:           %d
    ", heads[i].imageType);
            printf("
    ");
        }
    
        ret_val = 0;
        printf("e[1;32mSucceed!!e[0m
    ");
    EXIT:
        if(dst) munmap(dst,prev_offset);
        if(img_fd > 0)  close(img_fd);
        if(ret_val < 0)
        {
            printf("e[1;31mFailed!!e[0m
    ");
        }
        return ret_val;
    }
  • 相关阅读:
    combination sum II
    Combination sum
    Swap Nodes in Pairs(交换节点)
    4 sum
    3 sum closest
    五大常用算法:分治、动态规划、贪心、回溯和分支界定
    3sum(从数组中找出三个数的和为0)
    从系统相册选择照片时,没有选框,相册无选框
    iOS Xcode 调试技巧 全局断点这样加才有意思
    将任意对象存进数据库
  • 原文地址:https://www.cnblogs.com/pengdonglin137/p/3523585.html
Copyright © 2020-2023  润新知