xref: /haiku/src/add-ons/media/plugins/ffmpeg/AVCodecDecoder.h (revision da4dbfa47a47beb355289f3dd685797cee69ab77)
1 /*
2  * Copyright (C) 2001 Carlos Hasan.
3  * Copyright (C) 2001 François Revol.
4  * Copyright (C) 2001 Axel Dörfler.
5  * Copyright (C) 2004 Marcus Overhagen.
6  * Copyright (C) 2009 Stephan Aßmus <superstippi@gmx.de>.
7  * Copyright (C) 2015 Adrien Destugues <pulkomandy@pulkomandy.tk>.
8  *
9  * All rights reserved. Distributed under the terms of the MIT License.
10  */
11 #ifndef AVCODEC_DECODER_H
12 #define AVCODEC_DECODER_H
13 
14 //! libavcodec based decoder for Haiku
15 
16 
17 #include <MediaFormats.h>
18 
19 
20 extern "C" {
21 	#include "avcodec.h"
22 	#include "avfilter.h"
23 	#include "buffersink.h"
24 	#include "buffersrc.h"
25 	#include "imgutils.h"
26 	#include "swresample.h"
27 	#include "swscale.h"
28 	#include "timestamp.h"
29 }
30 
31 
32 #include "DecoderPlugin.h"
33 #include "ReaderPlugin.h"
34 
35 #include "CodecTable.h"
36 #include "gfx_util.h"
37 
38 
39 #if 1
40 #define USE_SWS_FOR_COLOR_SPACE_CONVERSION 1
41 #else
42 #define USE_SWS_FOR_COLOR_SPACE_CONVERSION 0
43 // NOTE: David's color space conversion is much faster than the FFmpeg
44 // version. Perhaps the SWS code can be used for unsupported conversions?
45 // Otherwise the alternative code could simply be removed from this file.
46 #endif
47 
48 
49 class AVCodecDecoder : public Decoder {
50 public:
51 						AVCodecDecoder();
52 
53 	virtual				~AVCodecDecoder();
54 
55 	virtual	void		GetCodecInfo(media_codec_info* mci);
56 
57 	virtual	status_t	Setup(media_format* ioEncodedFormat,
58 							const void* infoBuffer, size_t infoSize);
59 
60 	virtual	status_t	NegotiateOutputFormat(media_format* inOutFormat);
61 
62 	virtual	status_t	Decode(void* outBuffer, int64* outFrameCount,
63 							media_header* mediaHeader,
64 							media_decode_info* info);
65 
66 	virtual	status_t	SeekedTo(int64 trame, bigtime_t time);
67 
68 
69 private:
70 			void		_ResetTempPacket();
71 
72 			status_t	_NegotiateAudioOutputFormat(media_format* inOutFormat);
73 
74 			status_t	_NegotiateVideoOutputFormat(media_format* inOutFormat);
75 
76 			status_t	_DecodeAudio(void* outBuffer, int64* outFrameCount,
77 							media_header* mediaHeader,
78 							media_decode_info* info);
79 
80 			status_t	_DecodeVideo(void* outBuffer, int64* outFrameCount,
81 							media_header* mediaHeader,
82 							media_decode_info* info);
83 
84 			status_t	_DecodeNextAudioFrame();
85 			void		_ApplyEssentialAudioContainerPropertiesToContext();
86 			status_t	_ResetRawDecodedAudio();
87 			void		_CheckAndFixConditionsThatHintAtBrokenAudioCodeBelow();
88 			void		_MoveAudioFramesToRawDecodedAudioAndUpdateStartTimes();
89 			status_t	_DecodeNextAudioFrameChunk();
90 			status_t	_DecodeSomeAudioFramesIntoEmptyDecodedDataBuffer();
91 			void		_UpdateMediaHeaderForAudioFrame();
92 
93 			status_t	_DecodeNextVideoFrame();
94 			void		_ApplyEssentialVideoContainerPropertiesToContext();
95 			status_t	_LoadNextChunkIfNeededAndAssignStartTime();
96 			status_t	_CopyChunkToChunkBufferAndAddPadding(const void* chunk,
97 							size_t chunkSize);
98 			status_t	_HandleNewVideoFrameAndUpdateSystemState();
99 			status_t	_FlushOneVideoFrameFromDecoderBuffer();
100 			void		_UpdateMediaHeaderForVideoFrame();
101 			status_t	_DeinterlaceAndColorConvertVideoFrame();
102 
103 			// video deinterlace filter graph
104 			status_t	_InitFilterGraph(enum AVPixelFormat pixfmt,
105 							int32 width, int32 height);
106 			status_t	_ProcessFilterGraph(AVFrame *dst,
107 							const AVFrame *src, enum AVPixelFormat pixfmt,
108 							int32 width, int32 height);
109 
110 			media_header		fHeader;
111 									// Contains the properties of the current
112 									// decoded audio / video frame
113 
114 			media_format		fInputFormat;
115 
116 			int64				fFrame;
117 			bool				fIsAudio;
118 
119 			// FFmpeg related members
120 			const AVCodec*		fCodec;
121 			AVCodecContext*		fCodecContext;
122 			SwrContext*			fResampleContext;
123 			uint8_t*			fDecodedData;
124 			size_t				fDecodedDataSizeInBytes;
125 			AVFrame*			fPostProcessedDecodedPicture;
126 			AVFrame*			fRawDecodedPicture;
127 			AVFrame*			fRawDecodedAudio;
128 
129 			bool 				fCodecInitDone;
130 
131 			gfx_convert_func	fFormatConversionFunc;
132 #if USE_SWS_FOR_COLOR_SPACE_CONVERSION
133 			SwsContext*			fSwsContext;
134 #endif
135 
136 			char*				fExtraData;
137 			int					fExtraDataSize;
138 			int					fBlockAlign;
139 
140 			color_space			fOutputColorSpace;
141 			int32				fOutputFrameCount;
142 			float				fOutputFrameRate;
143 			int					fOutputFrameSize;
144 									// sample size * channel count
145 			int					fInputFrameSize;
146 									// sample size * channel count
147 									// or just sample size for planar formats
148 
149 			uint8_t*			fChunkBuffer;
150 			size_t				fChunkBufferSize;
151 			bool				fAudioDecodeError;
152 
153 			AVFrame*			fDecodedDataBuffer;
154 			int32				fDecodedDataBufferOffset;
155 			int32				fDecodedDataBufferSize;
156 
157 			AVPacket*			fTempPacket;
158 
159 			// video deinterlace feature
160 			AVFilterContext*	fBufferSinkContext;
161 			AVFilterContext*	fBufferSourceContext;
162 			AVFilterGraph*		fFilterGraph;
163 			AVFrame*			fFilterFrame;
164 			int32				fLastWidth;
165 			int32				fLastHeight;
166 			enum AVPixelFormat	fLastPixfmt;
167 };
168 
169 #endif // AVCODEC_DECODER_H
170