• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            Khan's Notebook GCC/GNU/Linux Delphi/Window Java/Anywhere

            路漫漫,長修遠,我們不能沒有錢
            隨筆 - 173, 文章 - 0, 評論 - 257, 引用 - 0
            數據加載中……

            ffmpeg分析系列之五(打開輸入的文件)

            1. 打開文件:

            if (!fmt || !(fmt->flags & AVFMT_NOFILE)) { 

                
            因 fmt == NULL, 上面成立, 再看下面的代碼:

                    ByteIOContext *pb = NULL; // 字節IO上下文

                    if ((err=url_fopen(&pb, filename, URL_RDONLY)) < 0) { // 只讀方式打開輸入的文件
                        goto fail;
                    }
                    if (buf_size > 0) { // 因 buf_size == 0, 不成立
                        url_setbufsize(pb, buf_size);

                    }


            進入url_fopen函數:

            int url_fopen(ByteIOContext **s, // 輸出參數: 字節IO上下文
                          const char *filename, // 文件名
                          int flags) // 標志
            {
                URLContext *h; // URL(統一資源定位)上下文
                int err;

                err = url_open(&h, filename, flags); // 打開URL
                if (err < 0)
                    return err;
                err = url_fdopen(s, h); // 用URL上下文打開字節IO上下文
                if (err < 0) {
                    url_close(h);
                    return err;
                }
                return 0;
            }


            進入url_open函數:

            int url_open(URLContext **puc, // 輸出參數: URL上下文

            const char *filename, // 文件名

            int flags) // 標志

            {
                URLProtocol *up;
                const char *p;
                char proto_str[128], *q;

                // 提取協議
                p = filename;
                q = proto_str;
                while (*!= '\0' && *!= ':') { // 未結束, 并未遇到分隔符':'
                    if (!isalpha(*p)) // 如果不是英文字母
                        goto file_proto;
                    if ((- proto_str) < sizeof(proto_str) - 1)
                        *q++ = *p; // 記錄協議字符串
                    p++;
                }

                if (*== '\0' || is_dos_path(filename)) { // 如果上面是因為結束而跳出, 或且
            文件名是DOS路徑

                file_proto:
                    strcpy(proto_str, "file"); // 文件協議
                } else {
                    *= '\0'; // 追加結束符
                }

                up = first_protocol;
                while (up != NULL) {
                    if (!strcmp(proto_str, up->name)) // 協議匹配
                        return url_open_protocol (puc, up, filename, flags); // 用這個協議打開URL
                    up = up->next;
                }
                *puc = NULL;
                return AVERROR(ENOENT);
            }


            進入url_open_protocol函數:

            int url_open_protocol (URLContext **puc, // 輸出參數: URL上下文

            struct URLProtocol *up, // URL協議

            const char *filename, // 文件名

            int flags// 標志
            {
                URLContext *uc;
                int err;

                // 網絡初始化
            #if CONFIG_NETWORK
                if (!ff_network_init())
                    return AVERROR(EIO);
            #endif

                // 分配URL上下文并加上文件名的存儲空間
                uc = av_mallocz(sizeof(URLContext) + strlen(filename) + 1);
                if (!uc) {
                    err = AVERROR(ENOMEM);
                    goto fail;
                }

                // 初始化URL上下文
            #if LIBAVFORMAT_VERSION_MAJOR >= 53
                uc->av_class = &urlcontext_class;
            #endif

                // 記錄文件名
                uc->filename = (char *) &uc[1];
                strcpy(uc->filename, filename);
             
                uc->prot = up
            // URL協議

                uc->flags = flags// 標志
                uc->is_streamed = 0// 默認不是流, 可以在up->url_open函數里修改
                uc->max_packet_size = 0; // 
            包最大多大, 默認為0, 可以在up->url_open函數里修改

                // 打開URL
                err = up->url_open(uc, filename, flags);
                if (err < 0) {
                    av_free(uc);
                    goto fail;
                }

             

                if( (flags & (URL_WRONLY | URL_RDWR)// 如果以可寫方式打開

                   || !strcmp(up->name, "file")// 或且是文件協議

                     // 如果不是流并且不可以url_seek

                    if(!uc->is_streamed && url_seek(uc, 0, SEEK_SET) < 0)
                        uc->is_streamed= 1
            // 強制為流

                // 輸出
            參數: URL上下文

                *puc = uc;
                return 0;
             fail:
                *puc = NULL;
            #if CONFIG_NETWORK
                ff_network_close();
            #endif
                return err;
            }


            先來看看url_get_max_packet_size函數

            int url_get_max_packet_size(URLContext *h)
            {
                return h->max_packet_size; // 包最大多大, 被上面初始化為0
            }


            進入url_fdopen函數:

            int url_fdopen(

            ByteIOContext **s, // 輸出參數: 字節IO上下文

            URLContext *h// URL上下文
            {
                uint8_t *buffer;
                int buffer_size, max_packet_size;

                max_packet_size = url_get_max_packet_size(h);
                if (max_packet_size) {
                    buffer_size = max_packet_size;
                } else {
                    buffer_size = IO_BUFFER_SIZE; // 緩沖大小為IO_BUFFER_SIZE
                }
                buffer = av_malloc(buffer_size); // 分配緩沖
                if (!buffer)
                    return AVERROR(ENOMEM);

                *= av_mallocz(sizeof(ByteIOContext)); // 分配字節IO上下文

                if(!*s) {
                    av_free(buffer);
                    return AVERROR(ENOMEM);
                }

                if (init_put_byte(*s, buffer, buffer_size,
                                  (h->flags & URL_WRONLY || h->flags & URL_RDWR), h,
                                  url_read, url_write, url_seek) < 0) {
                    av_free(buffer);
                    av_freep(s);
                    return AVERROR(EIO);
                }
                (*s)->is_streamed = h->is_streamed// 是否為流
                (*s)->max_packet_size = max_packet_size// 包最大多大
                if(h->prot) {
                    (*s)->read_pause = (int (*)(void *, int))h->prot->url_read_pause; // 讀暫停函數
                    (*s)->read_seek = (int64_t (*)(void *, int, int64_t, int))h->prot->url_read_seek; // 讀seek函數
                }
                return 0;
            }


            進入init_put_byte函數:

            int init_put_byte(ByteIOContext *s, // 字節IO上下文
                              unsigned char *buffer, // 緩沖
                              int buffer_size, // 緩沖的大小
                              int write_flag, // 寫標志
                              void *opaque, // URL上下文
                              int (*read_packet)(void *opaque, uint8_t *buf, int buf_size), // 讀包
                              int (*write_packet)(void *opaque, uint8_t *buf, int buf_size),// 寫包
                              int64_t (*seek)(void *opaque, int64_t offset, int whence)) // 調整文件指針
            {
                s->buffer = buffer;
                s->buffer_size = buffer_size;
                s->buf_ptr = buffer;
                s->opaque = opaque;
                url_resetbuf(s, write_flag ? URL_WRONLY : URL_RDONLY);
                s->write_packet = write_packet;
                s->read_packet = read_packet;
                s->seek = seek;
                s->pos = 0;
                s->must_flush = 0;
                s->eof_reached = 0;
                s->error = 0;
                s->is_streamed = 0;
                s->max_packet_size = 0;
                s->update_checksum= NULL;
                if(!read_packet && !write_flag){
                    s->pos = buffer_size;
                    s->buf_end = s->buffer + buffer_size;
                }
                s->read_pause = NULL;
                s->read_seek = NULL;
                return 0;
            }

            @import url(http://m.shnenglu.com/cutesoft_client/cuteeditor/Load.ashx?type=style&file=SyntaxHighlighter.css);@import url(/css/cuteeditor.css);

            posted on 2012-12-14 01:34 Khan 閱讀(1170) 評論(0)  編輯 收藏 引用 所屬分類: GCC/G++ 、跨平臺開發

            久久99热只有频精品8| 久久精品女人天堂AV麻| 亚洲精品乱码久久久久久中文字幕 | 久久综合五月丁香久久激情| 亚洲七七久久精品中文国产| 亚洲日本va中文字幕久久| 久久国产乱子伦精品免费强| 少妇被又大又粗又爽毛片久久黑人 | 免费一级做a爰片久久毛片潮| 欧美伊人久久大香线蕉综合| 97久久综合精品久久久综合| 日韩电影久久久被窝网| 国产成人综合久久综合| 久久综合亚洲鲁鲁五月天| 精品国产一区二区三区久久蜜臀| 怡红院日本一道日本久久| 伊人热热久久原色播放www| 亚洲国产精品久久久久婷婷软件| 久久人人爽人人爽人人片AV不| 久久99精品久久久久久齐齐| 国产午夜免费高清久久影院| 久久WWW免费人成一看片| 天天综合久久久网| 亚洲色大成网站WWW久久九九| 人妻少妇精品久久| 国产女人aaa级久久久级| 99国产欧美久久久精品蜜芽| 国产成人久久精品一区二区三区| 久久久久久一区国产精品| 国内精品久久久久久久影视麻豆| 久久精品九九亚洲精品| 亚洲中文字幕久久精品无码喷水| 日韩影院久久| 欧美精品国产综合久久| 欧美性猛交xxxx免费看久久久| 久久精品国产第一区二区| 久久996热精品xxxx| 久久精品国产亚洲7777| 亚洲国产日韩欧美综合久久| 久久久久久久综合狠狠综合| 亚洲中文字幕伊人久久无码|