ffmpeg拉流長時間堵塞解決方式


由於網絡堵塞或者推流端錯誤導致拉流端沒有流數據,ffmpeg主要會堵塞兩個函數,直到下次流數據的到來

  1. avformat_open_input()
    該函數是在打開流數據時,如果沒有這個流的ip,http有自己的timeout,當鏈接失敗,ffmpeg會自動斷開.但是如果有這個ip,但是無法鏈接,就會堵塞,解決方式是添加超時控制.
    函數在ffmpeg源碼的ffmpeg_opt.c文件中,

    我設置了3秒超時時間,添加如下代碼
    av_dict_set(&o->g->format_opts, "rw_timeout", "3000000", 0);

  2. av_read_frame()
    該函數是鏈接成功后,由於網絡堵塞或者其它問題導致packet丟失,無法讀取,導致堵塞,
    函數在ffmpeg.c文件中,解決方式也是添加超時
    f->ctx->interrupt_callback.callback = CheckInterrupt;
    f->ctx->interrupt_callback.opaque = (void*)f->ctx;
    time_t start_time;
    start_time = time(NULL);
    int l = time(&start_time);
    f->ctx->st = l;
    return av_read_frame(f->ctx, pkt);

    下面是回調函數:
    static int CheckInterrupt(void *ctx)
    {
    AVFormatContext p = (AVFormatContext)ctx;
    time_t et;
    et = time(NULL);
    int l = time(&et);
    av_log(NULL, AV_LOG_WARNING,"start time%d\n",p->st);
    av_log(NULL, AV_LOG_WARNING,"end time%d\n",l);
    return l - p->st >= 10 ? 1 : 0;//3秒超時
    }

    需要注意的是,我在f->ctx結構體中添加了st變量,由時間戳作為評判超時的依據,需要把變量類型統一,所以需要添加變量如下:
    在avformat.h文件的AVFormatContext結構體中添加:
    int st;


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2026 CODEPRJ.COM