Ticket #4912: minimal_test.c

File minimal_test.c, 3.3 KB (added by tr3wory, 11 years ago)

Sample code describing the problem.

Line 
1
2#include <libavcodec/avcodec.h>
3#include <libavformat/avformat.h>
4
5#include <stdio.h>
6#include <assert.h>
7
8void printAndExit(const char* msg) {
9 printf("%s\n",msg);
10 exit(1);
11}
12
13void exitIfError(int av_error) {
14 if (av_error < 0)
15 {
16 char buffer[AV_ERROR_MAX_STRING_SIZE] = {0};
17 av_strerror(av_error,buffer,sizeof(buffer));
18 printAndExit(buffer);
19 }
20}
21
22
23int main()
24{
25 AVFormatContext* m_formatCtx = NULL;
26 unsigned int m_videoStreamIdx = -1;
27 AVCodec* m_codec = NULL;
28 AVCodecContext* m_codecCtx = NULL;
29 AVFrame* m_lastFrame = NULL;
30
31 const char* filename = "cant_read_2nd_frame.flv";
32// av_log_set_level(AV_LOG_TRACE);
33
34 av_register_all();
35
36 exitIfError( avformat_open_input(&m_formatCtx,filename,NULL,NULL) );
37
38 // Find stream info
39 exitIfError( avformat_find_stream_info(m_formatCtx,NULL));
40
41 // Find the first video stream
42 m_videoStreamIdx = 0;
43 for (; m_videoStreamIdx < m_formatCtx->nb_streams; ++m_videoStreamIdx)
44 if (m_formatCtx->streams[m_videoStreamIdx]->codec->codec_type == AVMEDIA_TYPE_VIDEO)
45 break;
46
47 if (m_videoStreamIdx == m_formatCtx->nb_streams) printAndExit("Can't find video stream!");
48
49 m_codec = avcodec_find_decoder(m_formatCtx->streams[m_videoStreamIdx]->codec->codec_id);
50 if (m_codec == NULL) printAndExit("Unsupported codec!");
51
52 m_codecCtx = avcodec_alloc_context3(m_codec);
53 if (m_codecCtx == NULL) printAndExit("Error while creating codec context!");
54
55 exitIfError( avcodec_copy_context(m_codecCtx, m_formatCtx->streams[m_videoStreamIdx]->codec) );
56
57 m_codecCtx->refcounted_frames = 0; //the decoded frames must not be freed by the caller and are only valid until the next decode call.
58
59 exitIfError( avcodec_open2(m_codecCtx,m_codec,NULL) );
60
61 m_lastFrame = av_frame_alloc();
62 if (m_lastFrame == NULL) printAndExit("Couldn't alloc frame!");
63
64 AVPacket packet;
65 int isFrameFinished = 0;
66
67 // Read 1st frame
68 exitIfError( av_read_frame(m_formatCtx, &packet) );
69 assert(packet.stream_index == (signed)m_videoStreamIdx);
70 exitIfError( avcodec_decode_video2(m_codecCtx,m_lastFrame,&isFrameFinished,&packet) );
71 assert(isFrameFinished == 1);
72 av_free_packet(&packet);
73
74 // Read 2nd frame
75 exitIfError( av_read_frame(m_formatCtx, &packet) );
76 assert(packet.stream_index == (signed)m_videoStreamIdx);
77 exitIfError( avcodec_decode_video2(m_codecCtx,m_lastFrame,&isFrameFinished,&packet) );
78 assert(isFrameFinished == 0); // No frame decoded this time
79 av_free_packet(&packet);
80
81 // Seek to the beginning
82 avcodec_flush_buffers(m_codecCtx);
83 exitIfError(av_seek_frame(m_formatCtx,m_videoStreamIdx,0,AVSEEK_FLAG_BACKWARD));
84
85 // Read 1st frame
86 exitIfError( av_read_frame(m_formatCtx, &packet) );
87 assert(packet.stream_index == (signed)m_videoStreamIdx);
88 exitIfError( avcodec_decode_video2(m_codecCtx,m_lastFrame,&isFrameFinished,&packet) );
89 assert(isFrameFinished == 1);
90 av_free_packet(&packet);
91
92 // Read 2nd frame
93 exitIfError( av_read_frame(m_formatCtx, &packet) );
94 assert(packet.stream_index == (signed)m_videoStreamIdx);
95 exitIfError( avcodec_decode_video2(m_codecCtx,m_lastFrame,&isFrameFinished,&packet) );
96 assert(isFrameFinished == 1); // Success
97 av_free_packet(&packet);
98
99
100 printf("Done.\n");
101 return 0;
102}
103