⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mov.c

📁 Trolltech公司发布的图形界面操作系统。可在qt-embedded-2.3.7平台上编译为嵌入式图形界面操作系统。
💻 C
📖 第 1 页 / 共 3 页
字号:
    MOVContext *c;    AVStream *st;#ifdef DEBUG    print_atom("mdhd", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];        get_byte(pb); /* version */    get_byte(pb); get_byte(pb);    get_byte(pb); /* flags */    get_be32(pb); /* creation time */    get_be32(pb); /* modification time */    c->streams[c->total_streams]->time_scale = get_be32(pb);#ifdef DEBUG    printf("track[%i].time_scale = %li\n", c->fc->nb_streams-1, c->streams[c->total_streams]->time_scale); /* time scale */#endif    get_be32(pb); /* duration */    get_be16(pb); /* language */    get_be16(pb); /* quality */        return 0;}static int parse_hdlr(const MOVParseTableEntry *parse_table, ByteIOContext *pb, UINT32 atom_type, INT64 atom_offset, INT64 atom_size, void *param){    MOVContext *c;    int len = 0;    char *buf;    UINT32 type;    AVStream *st;    UINT32 ctype;#ifdef DEBUG    print_atom("hdlr", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];    get_byte(pb); /* version */    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */    /* component type */    ctype = get_le32(pb);    type = get_le32(pb); /* component subtype */#ifdef DEBUG    printf("ctype= %c%c%c%c (0x%08lx)\n", *((char *)&ctype), ((char *)&ctype)[1], ((char *)&ctype)[2], ((char *)&ctype)[3], (long) ctype);    printf("stype= %c%c%c%c\n", *((char *)&type), ((char *)&type)[1], ((char *)&type)[2], ((char *)&type)[3]);#endif#ifdef DEBUG/* XXX: yeah this is ugly... */    if(ctype == MKTAG('m', 'h', 'l', 'r')) { /* MOV */        if(type == MKTAG('v', 'i', 'd', 'e'))            puts("hdlr: vide");        else if(type == MKTAG('s', 'o', 'u', 'n'))            puts("hdlr: soun");    } else if(ctype == 0) { /* MP4 */        if(type == MKTAG('v', 'i', 'd', 'e'))            puts("hdlr: vide");        else if(type == MKTAG('s', 'o', 'u', 'n'))            puts("hdlr: soun");        else if(type == MKTAG('o', 'd', 's', 'm'))            puts("hdlr: odsm");        else if(type == MKTAG('s', 'd', 's', 'm'))            puts("hdlr: sdsm");    } else puts("hdlr: meta");#endif    if(ctype == MKTAG('m', 'h', 'l', 'r')) { /* MOV */        /* helps parsing the string hereafter... */        c->mp4 = 0;        if(type == MKTAG('v', 'i', 'd', 'e'))            st->codec.codec_type = CODEC_TYPE_VIDEO;        else if(type == MKTAG('s', 'o', 'u', 'n'))            st->codec.codec_type = CODEC_TYPE_AUDIO;    } else if(ctype == 0) { /* MP4 */        /* helps parsing the string hereafter... */        c->mp4 = 1;        if(type == MKTAG('v', 'i', 'd', 'e'))            st->codec.codec_type = CODEC_TYPE_VIDEO;        else if(type == MKTAG('s', 'o', 'u', 'n'))            st->codec.codec_type = CODEC_TYPE_AUDIO;    }    get_be32(pb); /* component  manufacture */    get_be32(pb); /* component flags */    get_be32(pb); /* component flags mask */    if(atom_size <= 24)        return 0; /* nothing left to read */    /* XXX: MP4 uses a C string, not a pascal one */    /* component name */    if(c->mp4) {        /* .mp4: C string */        while(get_byte(pb) && (++len < (atom_size - 24)));    } else {        /* .mov: PASCAL string */        len = get_byte(pb);        buf = av_malloc(len+1);        get_buffer(pb, buf, len);        buf[len] = '\0';#ifdef DEBUG        printf("**buf='%s'\n", buf);#endif        av_free(buf);    }#if 0    len = get_byte(pb);    /* XXX: use a better heuristic */    if(len < 32) {        /* assume that it is a Pascal like string */        buf = av_malloc(len+1);        get_buffer(pb, buf, len);        buf[len] = '\0';#ifdef DEBUG        printf("**buf='%s'\n", buf);#endif        av_free(buf);    } else {        /* MP4 string */        for(;;) {            if (len == 0)                break;            len = get_byte(pb);        }    }#endif        return 0;}static int mp4_read_descr_len(ByteIOContext *pb){    int c, len, count;    len = 0;    count = 0;    for(;;) {        c = get_byte(pb);        len = (len << 7) | (c & 0x7f);        if ((c & 0x80) == 0)            break;        if (++count == 4)            break;    }    return len;}static int mp4_read_descr(ByteIOContext *pb, int *tag){    int len;    *tag = get_byte(pb);    len = mp4_read_descr_len(pb);#ifdef DEBUG    printf("MPEG4 description: tag=0x%02x len=%d\n", *tag, len);#endif    return len;}static int parse_stsd(const MOVParseTableEntry *parse_table, ByteIOContext *pb, UINT32 atom_type, INT64 atom_offset, INT64 atom_size, void *param){    MOVContext *c;    int entries, size, samp_sz, frames_per_sample, id;    UINT32 format;    AVStream *st;    MOVStreamContext *sc;#ifdef DEBUG    print_atom("stsd", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];    sc = (MOVStreamContext *)st->priv_data;    get_byte(pb); /* version */    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */    entries = get_be32(pb);    while(entries--) {        size = get_be32(pb); /* size */        format = get_le32(pb); /* data format */                get_be32(pb); /* reserved */        get_be16(pb); /* reserved */        get_be16(pb); /* index */        /* for MPEG4: set codec type by looking for it */        id = codec_get_id(mov_video_tags, format);        if (id >= 0) {            AVCodec *codec;            codec = avcodec_find_decoder(id);            if (codec)                st->codec.codec_type = codec->type;        }#ifdef DEBUG        printf("size=%d 4CC= %c%c%c%c codec_type=%d\n",                size,                (format >> 0) & 0xff,               (format >> 8) & 0xff,               (format >> 16) & 0xff,               (format >> 24) & 0xff,               st->codec.codec_type);#endif        if(st->codec.codec_type==CODEC_TYPE_VIDEO) {            st->codec.codec_tag = format;            st->codec.codec_id = codec_get_id(mov_video_tags, format);            get_be16(pb); /* version */            get_be16(pb); /* revision level */            get_be32(pb); /* vendor */            get_be32(pb); /* temporal quality */            get_be32(pb); /* spacial quality */            st->codec.width = get_be16(pb); /* width */            st->codec.height = get_be16(pb); /* height */#if 1            if (st->codec.codec_id == CODEC_ID_MPEG4) {                /* in some MPEG4 the width/height are not correct, so                   we ignore this info */                st->codec.width = 0;                st->codec.height = 0;            }#endif            get_be32(pb); /* horiz resolution */            get_be32(pb); /* vert resolution */            get_be32(pb); /* data size, always 0 */            frames_per_sample = get_be16(pb); /* frame per samples */#ifdef DEBUG	    printf("frames/samples = %d\n", frames_per_sample);#endif            url_fskip(pb, 32); /* codec name */            get_be16(pb); /* depth */            get_be16(pb); /* colortable id */                        st->codec.frame_rate = 25 * FRAME_RATE_BASE;                        size -= (16+8*4+2+32+2*2);            while (size >= 8) {                int atom_size, atom_type;                INT64 start_pos;                                atom_size = get_be32(pb);                atom_type = get_le32(pb);                size -= 8;#ifdef DEBUG                printf("VIDEO: atom_type=%c%c%c%c atom_size=%d size_left=%d\n",                        (atom_type >> 0) & 0xff,                       (atom_type >> 8) & 0xff,                       (atom_type >> 16) & 0xff,                       (atom_type >> 24) & 0xff,                       atom_size, size);#endif                start_pos = url_ftell(pb);                switch(atom_type) {                case MKTAG('e', 's', 'd', 's'):                    {                        int tag, len;                        /* Well, broken but suffisant for some MP4 streams */                        get_be32(pb); /* version + flags */                        len = mp4_read_descr(pb, &tag);                        if (tag == 0x03) {                            /* MP4ESDescrTag */                            get_be16(pb); /* ID */                            get_byte(pb); /* priority */                            len = mp4_read_descr(pb, &tag);                            if (tag != 0x04)                                goto fail;                            /* MP4DecConfigDescrTag */                            get_byte(pb); /* objectTypeId */                            get_be32(pb); /* streamType + buffer size */                            get_be32(pb); /* max bit rate */                            get_be32(pb); /* avg bit rate */                            len = mp4_read_descr(pb, &tag);                            if (tag != 0x05)                                goto fail;                            /* MP4DecSpecificDescrTag */#ifdef DEBUG                            printf("Specific MPEG4 header len=%d\n", len);#endif                            sc->header_data = av_mallocz(len);                            if (sc->header_data) {                                get_buffer(pb, sc->header_data, len);                                sc->header_len = len;                            }                        }                        /* in any case, skip garbage */                    }                    break;                default:                    break;                }            fail:                url_fskip(pb, (atom_size - 8) -                           ((url_ftell(pb) - start_pos)));                size -= atom_size - 8;            }            if (size > 0) {                /* unknown extension */                url_fskip(pb, size);            }        } else {            st->codec.codec_tag = format;            get_be16(pb); /* version */            get_be16(pb); /* revision level */            get_be32(pb); /* vendor */            st->codec.channels = get_be16(pb);/* channel count */            samp_sz = get_be16(pb); /* sample size */#ifdef DEBUG            if(samp_sz != 16)                puts("!!! stsd: audio sample size is not 16 bit !");#endif                        st->codec.codec_id = codec_get_id(mov_audio_tags, format);            /* handle specific s8 codec */            if (st->codec.codec_id == CODEC_ID_PCM_S16BE && samp_sz == 8)            st->codec.codec_id = CODEC_ID_PCM_S8;            get_be16(pb); /* compression id = 0*/            get_be16(pb); /* packet size = 0 */                        st->codec.sample_rate = ((get_be32(pb) >> 16));            st->codec.bit_rate = 0;#if 0            get_be16(pb); get_be16(pb); /*  */            get_be16(pb); /*  */            get_be16(pb); /*  */            get_be16(pb); /*  */            get_be16(pb); /*  */#endif                        if(size > 16)                url_fskip(pb, size-(16+20));        }    }/*    if(len) {    buf = av_malloc(len+1);        get_buffer(pb, buf, len);        buf[len] = '\0';        puts(buf);        av_free(buf);    }*/    return 0;}static int parse_stco(const MOVParseTableEntry *parse_table, ByteIOContext *pb, UINT32 atom_type, INT64 atom_offset, INT64 atom_size, void *param){    MOVContext *c;    int entries, i;    AVStream *st;    MOVStreamContext *sc;#ifdef DEBUG    print_atom("stco", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];    sc = (MOVStreamContext *)st->priv_data;        get_byte(pb); /* version */    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */    entries = get_be32(pb);    sc->chunk_count = entries;    sc->chunk_offsets = av_malloc(entries * sizeof(INT64));    if(atom_type == MKTAG('s', 't', 'c', 'o')) {        for(i=0; i<entries; i++) {            sc->chunk_offsets[i] = get_be32(pb);        }    } else if(atom_type == MKTAG('c', 'o', '6', '4')) {        for(i=0; i<entries; i++) {            sc->chunk_offsets[i] = get_be64(pb);        }    } else        return -1;#ifdef DEBUG/*    for(i=0; i<entries; i++) {        printf("chunk offset=0x%Lx\n", sc->chunk_offsets[i]);    }*/#endif    return 0;}static int parse_stsc(const MOVParseTableEntry *parse_table, ByteIOContext *pb, UINT32 atom_type, INT64 atom_offset, INT64 atom_size, void *param){    MOVContext *c;    int entries, i;    AVStream *st;    MOVStreamContext *sc;#ifdef DEBUG    print_atom("stsc", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];    sc = (MOVStreamContext *)st->priv_data;        get_byte(pb); /* version */    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */    entries = get_be32(pb);#ifdef DEBUGprintf("track[%i].stsc.entries = %i\n", c->fc->nb_streams-1, entries);#endif    sc->sample_to_chunk_sz = entries;    sc->sample_to_chunk = av_malloc(entries * sizeof(MOV_sample_to_chunk_tbl));    for(i=0; i<entries; i++) {        sc->sample_to_chunk[i].first = get_be32(pb);        sc->sample_to_chunk[i].count = get_be32(pb);        sc->sample_to_chunk[i].id = get_be32(pb);#ifdef DEBUG/*        printf("sample_to_chunk first=%ld count=%ld, id=%ld\n", sc->sample_to_chunk[i].first, sc->sample_to_chunk[i].count, sc->sample_to_chunk[i].id); */#endif    }    return 0;}static int parse_stsz(const MOVParseTableEntry *parse_table, ByteIOContext *pb, UINT32 atom_type, INT64 atom_offset, INT64 atom_size, void *param){    MOVContext *c;    int entries, i;    AVStream *st;    MOVStreamContext *sc;#ifdef DEBUG    print_atom("stsz", atom_type, atom_offset, atom_size);#endif    c = (MOVContext *)param;    st = c->fc->streams[c->fc->nb_streams-1];    sc = (MOVStreamContext *)st->priv_data;        get_byte(pb); /* version */    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */        sc->sample_size = get_be32(pb);    entries = get_be32(pb);    sc->sample_count = entries;#ifdef DEBUG    printf("sample_size = %ld sample_count = %ld\n", sc->sample_size, sc->sample_count);#endif    if(sc->sample_size)        return 0; /* there isn't any table following */    sc->sample_sizes = av_malloc(entries * sizeof(long));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -