1 // FLVParser.h: Flash Video file format parser, for Gnash.
3 // Copyright (C) 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
5 // This program is free software; you can redistribute it and/or modify
6 // it under the terms of the GNU General Public License as published by
7 // the Free Software Foundation; either version 3 of the License, or
8 // (at your option) any later version.
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software
17 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21 // Information about the FLV format can be found at http://osflash.org/flv
23 #ifndef GNASH_FLVPARSER_H
24 #define GNASH_FLVPARSER_H
27 #include "MediaParser.h" // for inheritance
28 #include "SimpleBuffer.h"
34 #include <boost/thread/mutex.hpp>
39 /// Extra video info found in some FLV embedded streams
41 /// This is basically composed by an header for the audio stream
43 class ExtraVideoInfoFlv
: public VideoInfo::ExtraInfo
47 /// Construct an ExtraVideoInfoFlv
50 /// Video header data. Ownership transferred.
53 /// Video header data size
55 /// @todo take a SimpleBuffer by auto_ptr
57 ExtraVideoInfoFlv(boost::uint8_t* extradata
, size_t datasize
)
64 /// Video stream header
65 boost::scoped_array
<boost::uint8_t> data
;
67 /// Video stream header size
71 /// Extra audoi info found in some FLV embedded streams
73 /// This is basically composed by an header for the audio stream
75 class ExtraAudioInfoFlv
: public AudioInfo::ExtraInfo
79 /// Construct an ExtraAudioInfoFlv
82 /// Audio header data. Ownership transferred.
85 /// Audio header data size
87 /// @todo take a SimpleBuffer by auto_ptr
89 ExtraAudioInfoFlv(boost::uint8_t* extradata
, size_t datasize
)
96 /// Audio stream header
97 boost::scoped_array
<boost::uint8_t> data
;
99 /// Audio stream header size
103 /// The FLVParser class parses FLV streams
104 class DSOEXPORT FLVParser
: public MediaParser
109 /// The size of padding for all buffers that might be read by FFMPEG.
111 /// This possibly also applies to other media handlers (gst).
112 /// Ideally this would be taken from the current Handler, but we don't
113 /// know about it here.
114 static const size_t paddingBytes
= 8;
117 /// Create an FLV parser reading input from
118 /// the given IOChannel
121 /// IOChannel to use for input.
122 /// Ownership transferred.
124 FLVParser(std::auto_ptr
<IOChannel
> lt
);
126 /// Kills the parser...
129 // see dox in MediaParser.h
130 virtual bool seek(boost::uint32_t&);
132 // see dox in MediaParser.h
133 virtual bool parseNextChunk();
135 // see dox in MediaParser.h
136 boost::uint64_t getBytesLoaded() const;
138 // see dox in MediaParser.h
139 bool indexingCompleted() const
141 return _indexingCompleted
;
144 /// Retrieve any parsed metadata tags up to a specified timestamp.
146 /// This copies pointers to a SimpleBuffer of AMF data from _metaTags,
147 /// then removes those pointers from the MetaTags map. Any metadata later
148 /// than the timestamp is kept until fetchMetaTags is called again (or
149 /// the dtor is called).
151 /// @param ts The latest timestamp to retrieve metadata for.
152 /// @param tags This is filled with shared pointers to metatags in
153 /// timestamp order. Ownership of the data is shared. It
154 /// is destroyed automatically along with the last owner.
156 virtual void fetchMetaTags(OrderedMetaTags
& tags
, boost::uint64_t ts
);
162 FLV_AUDIO_TAG
= 0x08,
163 FLV_VIDEO_TAG
= 0x09,
167 struct FLVTag
: public boost::noncopyable
169 FLVTag(boost::uint8_t* stream
)
172 body_size(getUInt24(stream
+1)),
173 timestamp(getUInt24(stream
+4) | (stream
[7] << 24) )
178 boost::uint32_t body_size
;
179 boost::uint32_t timestamp
;
182 struct FLVAudioTag
: public boost::noncopyable
184 FLVAudioTag(const boost::uint8_t& byte
)
186 codec( (byte
& 0xf0) >> 4 ),
187 samplerate( flv_audio_rates
[(byte
& 0x0C) >> 2] ),
188 samplesize( 1 + ((byte
& 0x02) >> 1)),
189 stereo( (byte
& 0x01) )
193 /// Equals audioCodecType
194 boost::uint8_t codec
;
196 boost::uint16_t samplerate
;
198 /// Size of each sample, in bytes
199 boost::uint8_t samplesize
;
205 static const boost::uint16_t flv_audio_rates
[];
211 FLV_VIDEO_KEYFRAME
= 1,
212 FLV_VIDEO_INTERLACED
= 2,
213 FLV_VIDEO_DISPOSABLE
= 3
216 struct FLVVideoTag
: public boost::noncopyable
218 FLVVideoTag(const boost::uint8_t& byte
)
220 frametype( (byte
& 0xf0) >> 4 ),
225 boost::uint8_t frametype
;
226 /// Equals videoCodecType
227 boost::uint8_t codec
;
230 /// Parses next tag from the file
232 /// Returns true if something was parsed, false otherwise.
233 /// Sets _parsingComplete=true on end of file.
235 bool parseNextTag(bool index_only
);
237 std::auto_ptr
<EncodedAudioFrame
> parseAudioTag(const FLVTag
& flvtag
,
238 const FLVAudioTag
& audiotag
, boost::uint32_t thisTagPos
);
240 std::auto_ptr
<EncodedVideoFrame
> parseVideoTag(const FLVTag
& flvtag
,
241 const FLVVideoTag
& videotag
, boost::uint32_t thisTagPos
);
243 void indexAudioTag(const FLVTag
& tag
, boost::uint32_t thisTagPos
);
245 void indexVideoTag(const FLVTag
& tag
, const FLVVideoTag
& videotag
,
246 boost::uint32_t thisTagPos
);
248 /// Parses the header of the file
251 /// Reads three bytes in FLV (big endian) byte order.
252 /// @param in Pointer to read 3 bytes from.
253 /// @return 24-bit integer.
254 static boost::uint32_t getUInt24(boost::uint8_t* in
);
256 /// The position where the parsing should continue from.
257 /// Will be reset on seek, and will be protected by the _streamMutex
258 boost::uint64_t _lastParsedPosition
;
260 /// Position of next tag to index
261 boost::uint64_t _nextPosToIndex
;
263 /// Audio frame cursor position
265 /// This is the video frame number that will
266 /// be referenced by nextVideoFrame and nextVideoFrameTimestamp
268 size_t _nextAudioFrame
;
270 /// Video frame cursor position
272 /// This is the video frame number that will
273 /// be referenced by nextVideoFrame and nextVideoFrameTimestamp
275 size_t _nextVideoFrame
;
277 /// Audio stream is present
280 /// Audio stream is present
283 std::auto_ptr
<EncodedAudioFrame
>
284 readAudioFrame(boost::uint32_t dataSize
, boost::uint32_t timestamp
);
286 std::auto_ptr
<EncodedVideoFrame
>
287 readVideoFrame(boost::uint32_t dataSize
, boost::uint32_t timestamp
);
289 /// Position in input stream for each cue point
291 /// second: position in input stream
292 typedef std::map
<boost::uint64_t, long> CuePointsMap
;
293 CuePointsMap _cuePoints
;
295 bool _indexingCompleted
;
299 boost::mutex _metaTagsMutex
;
302 } // end of gnash::media namespace
303 } // end of gnash namespace