DASH Media Packaging SDK
 All Classes Namespaces Functions Variables Typedefs Enumerator
wvm_media_parser.h
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 // Media parser for a Widevine Media Format (WVM) file.
5 
6 #ifndef MEDIA_FORMATS_WVM_WVM_MEDIA_PARSER_H_
7 #define MEDIA_FORMATS_WVM_WVM_MEDIA_PARSER_H_
8 
9 #include <deque>
10 #include <map>
11 #include <string>
12 #include <vector>
13 
14 #include "packager/base/memory/scoped_ptr.h"
15 #include "packager/media/base/media_parser.h"
16 #include "packager/media/base/network_util.h"
17 #include "packager/media/filters/h264_byte_to_unit_stream_converter.h"
18 
19 namespace edash_packager {
20 namespace media {
21 
22 class AesCbcCtsDecryptor;
23 class KeySource;
24 struct EncryptionKey;
25 
26 namespace wvm {
27 
29  public:
32  uint32_t demux_stream_id;
33  uint32_t parsed_audio_or_video_stream_id;
34  scoped_refptr<MediaSample> media_sample;
35 };
36 
38  public:
40  ~PrevSampleData();
41  void Reset();
42  scoped_refptr<MediaSample> audio_sample;
43  scoped_refptr<MediaSample> video_sample;
44  uint32_t audio_stream_id;
45  uint32_t video_stream_id;
46  int64_t audio_sample_duration;
47  int64_t video_sample_duration;
48 };
49 
50 class WvmMediaParser : public MediaParser {
51  public:
53  ~WvmMediaParser() override;
54 
55  // MediaParser implementation overrides.
56  void Init(const InitCB& init_cb,
57  const NewSampleCB& new_sample_cb,
58  KeySource* decryption_key_source) override;
59 
60  void Flush() override;
61 
62  bool Parse(const uint8_t* buf, int size) override;
63 
64  private:
65  enum Tag {
66  CypherVersion = 0,
67  TrackOffset = 1,
68  TrackSize = 2,
69  TrackDuration = 3,
70  TrackBitRate = 4,
71  TrackTrickPlayRate = 5,
72  TrackAdaptationInterval = 6,
73  TrackFlags = 7,
74  VideoType = 8,
75  VideoProfile = 9,
76  VideoLevel = 10,
77  VideoWidth = 11,
78  VideoHeight = 12,
79  VideoTicksPerFrame = 13,
80  VideoBitRate = 14,
81  AudioType = 15,
82  AudioProfile = 16,
83  AudioNumChannels = 17,
84  AudioSampleFrequency = 18,
85  AudioBitRate = 19,
86  TrackVersion = 20,
87  Title = 21,
88  Copyright = 22,
89  ChapterIndex = 23,
90  TimeIndex = 24,
91  Thumbnail = 25,
92  ObjectSeqNum = 26,
93  ThumbnailOffset = 27,
94  ThumbnailSize = 28,
95  NumEntries = 29,
96  Chapters = 30,
97  VideoPixelWidth = 31,
98  VideoPixelHeight = 32,
99  FileSize = 33,
100  SparseDownloadUrl = 34,
101  SparseDownloadRangeTranslations = 35,
102  SparseDownloadMap = 36,
103  AudioSampleSize = 37,
104  Audio_EsDescriptor = 38,
105  AVCDecoderConfigurationRecord = 39,
106  Audio_EC3SpecificData = 40,
107  AudioIdentifier = 41,
108  VideoStreamId = 42,
109  VideoStreamType = 43,
110  AudioStreamId = 44,
111  AudioStreamType = 45,
112  Audio_DtsSpecificData = 46,
113  Audio_AC3SpecificData = 47,
114  Unset = 48
115  };
116 
117  enum State {
118  StartCode1 = 0,
119  StartCode2,
120  StartCode3,
121  StartCode4,
122  PackHeader1,
123  PackHeader2,
124  PackHeader3,
125  PackHeader4,
126  PackHeader5,
127  PackHeader6,
128  PackHeader7,
129  PackHeader8,
130  PackHeader9,
131  PackHeader10,
132  PackHeaderStuffingSkip,
133  SystemHeader1,
134  SystemHeader2,
135  SystemHeaderSkip,
136  PesStreamId,
137  PesPacketLength1,
138  PesPacketLength2,
139  PesExtension1,
140  PesExtension2,
141  PesExtension3,
142  Pts1,
143  Pts2,
144  Pts3,
145  Pts4,
146  Pts5,
147  Dts1,
148  Dts2,
149  Dts3,
150  Dts4,
151  Dts5,
152  PesHeaderData,
153  PesPayload,
154  EsPayload,
155  PsmPayload,
156  EcmPayload,
157  IndexPayload,
158  Padding,
159  ProgramEnd
160  };
161 
162  bool ProcessEcm();
163 
164  // Index denotes 'search index' in the WVM content.
165  bool ParseIndexEntry();
166 
167  bool DemuxNextPes(bool is_program_end);
168 
169  void StartMediaSampleDemux();
170 
171  template <typename T>
172  Tag GetTag(const uint8_t& tag,
173  const uint32_t& length,
174  const uint8_t* start_index,
175  T* value) {
176  if (length == sizeof(uint8_t)) {
177  *value = (uint8_t)(*start_index);
178  } else if (length == sizeof(int8_t)) {
179  *value = (int8_t)(*start_index);
180  } else if (length == sizeof(uint16_t)) {
181  *value = (uint16_t)(ntohsFromBuffer(start_index));
182  } else if (length == sizeof(int16_t)) {
183  *value = (int16_t)(ntohsFromBuffer(start_index));
184  } else if (length == sizeof(uint32_t)) {
185  *value = (uint32_t)(ntohlFromBuffer(start_index));
186  } else if (length == sizeof(int32_t)) {
187  *value = (int32_t)(ntohlFromBuffer(start_index));
188  } else if (length == sizeof(uint64_t)) {
189  *value = (uint64_t)(ntohllFromBuffer(start_index));
190  } else if (length == sizeof(int64_t)) {
191  *value = (int64_t)(ntohllFromBuffer(start_index));
192  } else {
193  *value = 0;
194  }
195  return Tag(tag);
196  }
197 
198  // |must_process_encrypted| setting determines if Output() should attempt
199  // to ouput media sample as encrypted.
200  bool Output(bool must_process_encrypted);
201 
202  bool GetAssetKey(const uint32_t asset_id, EncryptionKey* encryption_key);
203 
204  // Callback invoked by the ES media parser
205  // to emit a new audio/video access unit.
206  bool EmitSample(uint32_t parsed_audio_or_video_stream_id,
207  uint32_t stream_id,
208  scoped_refptr<MediaSample>& new_sample,
209  bool isLastSample);
210 
211  bool EmitPendingSamples();
212 
213  bool EmitLastSample(uint32_t stream_id,
214  scoped_refptr<MediaSample>& new_sample);
215 
216  // List of callbacks.t
217  InitCB init_cb_;
218  NewSampleCB new_sample_cb_;
219 
220  // Whether |init_cb_| has been invoked.
221  bool is_initialized_;
222  // Internal content parsing state.
223  State parse_state_;
224 
225  bool is_psm_needed_;
226  uint32_t skip_bytes_;
227  bool metadata_is_complete_;
228  uint8_t current_program_id_;
229  uint32_t pes_stream_id_;
230  uint32_t prev_pes_stream_id_;
231  uint16_t pes_packet_bytes_;
232  uint8_t pes_flags_1_;
233  uint8_t pes_flags_2_;
234  uint8_t prev_pes_flags_1_;
235  uint8_t pes_header_data_bytes_;
236  uint64_t timestamp_;
237  uint64_t pts_;
238  uint64_t dts_;
239  uint8_t index_program_id_;
240  scoped_refptr<MediaSample> media_sample_;
241  uint32_t crypto_unit_start_pos_;
242  PrevSampleData prev_media_sample_data_;
243  H264ByteToUnitStreamConverter byte_to_unit_stream_converter_;
244 
245  std::vector<uint8_t, std::allocator<uint8_t> > ecm_;
246  std::vector<uint8_t> psm_data_;
247  std::vector<uint8_t> index_data_;
248  std::map<std::string, uint32_t> program_demux_stream_map_;
249  int stream_id_count_;
250  std::vector<scoped_refptr<StreamInfo> > stream_infos_;
251  std::deque<DemuxStreamIdMediaSample> media_sample_queue_;
252  std::vector<uint8_t> sample_data_;
253  KeySource* decryption_key_source_;
254  scoped_ptr<AesCbcCtsDecryptor> content_decryptor_;
255 
256  DISALLOW_COPY_AND_ASSIGN(WvmMediaParser);
257 };
258 
259 } // namespace wvm
260 } // namespace media
261 } // namespace edash_packager
262 
263 #endif // MEDIA_FORMATS_WVM_WVM_MEDIA_PARSER_H_
bool Parse(const uint8_t *buf, int size) override
base::Callback< bool(uint32_t track_id, const scoped_refptr< MediaSample > &media_sample)> NewSampleCB
Definition: media_parser.h:43
KeySource is responsible for encryption key acquisition.
Definition: key_source.h:29
base::Callback< void(const std::vector< scoped_refptr< StreamInfo > > &stream_info)> InitCB
Definition: media_parser.h:34
void Init(const InitCB &init_cb, const NewSampleCB &new_sample_cb, KeySource *decryption_key_source) override