FFMPEG:avcodec_发送_数据包();使用多线程时出错

FFMPEG:avcodec_发送_数据包();使用多线程时出错,ffmpeg,pthreads,Ffmpeg,Pthreads,我写了两个线程来解码IP摄像头的RTSP流,如下所示: RTSP_read_paket函数用于从RTSP链路读取数据包,数据包存储在名为Packet_buf的队列中 std::queue<AVPacket> Packet_buf; bool pkt_pending_k = false; int RTSP_read_packet (string url) { rtsp_init(url); int ret; AVPacket packet; av_i

我写了两个线程来解码IP摄像头的RTSP流,如下所示:

RTSP_read_paket函数用于从RTSP链路读取数据包,数据包存储在名为Packet_buf的队列中

std::queue<AVPacket> Packet_buf;
bool pkt_pending_k = false;

int RTSP_read_packet (string url)
{
    rtsp_init(url);

    int ret;
    AVPacket packet;
    av_init_packet(&packet);

    while(1)
    {
       ret = av_read_frame(pFormatCtx,&packet);
       if(ret==0)
       {
           if (packet.stream_index == video_stream_index)
           {
               Packet_buf.push(packet);
               if((ready1 == false))
               {
                    ready1 = true;
                    conv1.notify_one();
               }
           }
           av_packet_unref(&packet);
           cout<<"number of RTSP packet: "<<Packet_buf.size()<<endl;
       }
    }
    return 0;
}
任何人都可以帮我找到问题,谢谢

p/s: rtsp_init函数:

int rtsp_init (string url)
{
    av_register_all();
    avdevice_register_all();
    avcodec_register_all();
    avformat_network_init();
    const char  *filenameSrc = url.c_str();

    pFormatCtx = avformat_alloc_context();
    if ( pFormatCtx == NULL )
            return -8;

    AVDictionary *options = NULL;
    av_dict_set(&options,"rtsp_flags","prefer_tcp",0);
    av_dict_set(&options,"stimeout","1000000",0);
    int avret = avformat_open_input( &pFormatCtx, filenameSrc, NULL, &options );
    av_dict_free(&options);

    if ( avret != 0 ) {
            std::cout << "Open File Error 12" << std::endl;
            return -12;
        }

    avret = avformat_find_stream_info( pFormatCtx, NULL );
    if (  avret < 0 ) {
            std::cout << "Get Stream Information Error 13" << std::endl;
            avformat_close_input( &pFormatCtx );
            pFormatCtx = NULL;
            return -13;
     }
    av_dump_format( pFormatCtx, 0, filenameSrc, 0 );

    video_stream_index = av_find_best_stream(pFormatCtx,AVMEDIA_TYPE_VIDEO,-1,-1,NULL,0);
    if ( video_stream_index < 0 ) {
        std::cout << "Video stream was not found Error 14" << std::endl;
        avformat_close_input( &pFormatCtx );
        pFormatCtx = NULL;
        return -14;
    }

    pCodecCtx = avcodec_alloc_context3(NULL);
    avret = avcodec_parameters_to_context(pCodecCtx,pFormatCtx->streams[video_stream_index]->codecpar);
    if(avret<0)
    {
        std::cout << "codec not found Error 15" << std::endl;
        return -15;
    }

    pCodec  = avcodec_find_decoder( pCodecCtx->codec_id );
    avret = avcodec_open2( pCodecCtx, pCodec, NULL );
    if ( avret < 0) {
        std::cout << "Open Codec Error 16" << std::endl;
       return -16;
    }

    pFrame    = av_frame_alloc();
    pFrameRGB = av_frame_alloc();

    pFrame->width = pCodecCtx->width;
    pFrame->height = pCodecCtx->height;
    pFrame->format = pCodecCtx->pix_fmt;
    avret = av_frame_get_buffer(pFrame,0);
    if (avret < 0)
    {
        return -17;
    }

    pFrameRGB->width = pCodecCtx->width;
    pFrameRGB->height = pCodecCtx->height;
    pFrameRGB->format = AV_PIX_FMT_BGR24;

    avret = av_frame_get_buffer(pFrameRGB, 0);
    if (avret < 0)
    {
        return -18;
    }

    return ( EXIT_SUCCESS );
}
intrtsp_init(字符串url)
{
av_寄存器_all();
avdevice_register_all();
avcodec_寄存器_all();
avformat_network_init();
const char*filenameSrc=url.c_str();
pFormatCtx=avformat_alloc_context();
if(pFormatCtx==NULL)
返回-8;
AVDictionary*options=NULL;
av命令集(&选项,“rtsp标志”,“首选tcp”,0);
av指令集(选项和“刺激”、“1000000”、“0”);
int avret=avformat\u open\u输入(&pFormatCtx、filenameSrc、NULL和options);
av_dict_free(&options);
如果(avret!=0){
标准:曲线宽度;
pFrameRGB->height=pCodecCtx->height;
pFrameRGB->format=AV_PIX_FMT_BGR24;
avret=av_帧_获取_缓冲区(pFrameRGB,0);
if(avret<0)
{
返回-18;
}
返回(退出成功);
}

init代码在哪里?看起来您没有初始化编解码器上下文。我如上所述添加了init函数,当我将所有函数放在一个线程(main()进程)中时,它工作得很好。我想问题在于我使用队列的方式,但我不知道具体情况。@Trầ诺克ốcViệ你没有找到解决办法吗?
ret = avcodec_send_packet(pCodecCtx, &avpkt);
int rtsp_init (string url)
{
    av_register_all();
    avdevice_register_all();
    avcodec_register_all();
    avformat_network_init();
    const char  *filenameSrc = url.c_str();

    pFormatCtx = avformat_alloc_context();
    if ( pFormatCtx == NULL )
            return -8;

    AVDictionary *options = NULL;
    av_dict_set(&options,"rtsp_flags","prefer_tcp",0);
    av_dict_set(&options,"stimeout","1000000",0);
    int avret = avformat_open_input( &pFormatCtx, filenameSrc, NULL, &options );
    av_dict_free(&options);

    if ( avret != 0 ) {
            std::cout << "Open File Error 12" << std::endl;
            return -12;
        }

    avret = avformat_find_stream_info( pFormatCtx, NULL );
    if (  avret < 0 ) {
            std::cout << "Get Stream Information Error 13" << std::endl;
            avformat_close_input( &pFormatCtx );
            pFormatCtx = NULL;
            return -13;
     }
    av_dump_format( pFormatCtx, 0, filenameSrc, 0 );

    video_stream_index = av_find_best_stream(pFormatCtx,AVMEDIA_TYPE_VIDEO,-1,-1,NULL,0);
    if ( video_stream_index < 0 ) {
        std::cout << "Video stream was not found Error 14" << std::endl;
        avformat_close_input( &pFormatCtx );
        pFormatCtx = NULL;
        return -14;
    }

    pCodecCtx = avcodec_alloc_context3(NULL);
    avret = avcodec_parameters_to_context(pCodecCtx,pFormatCtx->streams[video_stream_index]->codecpar);
    if(avret<0)
    {
        std::cout << "codec not found Error 15" << std::endl;
        return -15;
    }

    pCodec  = avcodec_find_decoder( pCodecCtx->codec_id );
    avret = avcodec_open2( pCodecCtx, pCodec, NULL );
    if ( avret < 0) {
        std::cout << "Open Codec Error 16" << std::endl;
       return -16;
    }

    pFrame    = av_frame_alloc();
    pFrameRGB = av_frame_alloc();

    pFrame->width = pCodecCtx->width;
    pFrame->height = pCodecCtx->height;
    pFrame->format = pCodecCtx->pix_fmt;
    avret = av_frame_get_buffer(pFrame,0);
    if (avret < 0)
    {
        return -17;
    }

    pFrameRGB->width = pCodecCtx->width;
    pFrameRGB->height = pCodecCtx->height;
    pFrameRGB->format = AV_PIX_FMT_BGR24;

    avret = av_frame_get_buffer(pFrameRGB, 0);
    if (avret < 0)
    {
        return -18;
    }

    return ( EXIT_SUCCESS );
}