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
5 #include "base/logging.h"
6 #include "base/memory/scoped_ptr.h"
7 #include "base/stl_util.h"
8
9 #include "media/filters/h264_parser.h"
10
11 namespace media {
12
IsPSlice() const13 bool H264SliceHeader::IsPSlice() const {
14 return (slice_type % 5 == kPSlice);
15 }
16
IsBSlice() const17 bool H264SliceHeader::IsBSlice() const {
18 return (slice_type % 5 == kBSlice);
19 }
20
IsISlice() const21 bool H264SliceHeader::IsISlice() const {
22 return (slice_type % 5 == kISlice);
23 }
24
IsSPSlice() const25 bool H264SliceHeader::IsSPSlice() const {
26 return (slice_type % 5 == kSPSlice);
27 }
28
IsSISlice() const29 bool H264SliceHeader::IsSISlice() const {
30 return (slice_type % 5 == kSISlice);
31 }
32
H264NALU()33 H264NALU::H264NALU() {
34 memset(this, 0, sizeof(*this));
35 }
36
H264SPS()37 H264SPS::H264SPS() {
38 memset(this, 0, sizeof(*this));
39 }
40
H264PPS()41 H264PPS::H264PPS() {
42 memset(this, 0, sizeof(*this));
43 }
44
H264SliceHeader()45 H264SliceHeader::H264SliceHeader() {
46 memset(this, 0, sizeof(*this));
47 }
48
H264SEIMessage()49 H264SEIMessage::H264SEIMessage() {
50 memset(this, 0, sizeof(*this));
51 }
52
53 #define READ_BITS_OR_RETURN(num_bits, out) \
54 do { \
55 int _out; \
56 if (!br_.ReadBits(num_bits, &_out)) { \
57 DVLOG(1) \
58 << "Error in stream: unexpected EOS while trying to read " #out; \
59 return kInvalidStream; \
60 } \
61 *out = _out; \
62 } while (0)
63
64 #define READ_BOOL_OR_RETURN(out) \
65 do { \
66 int _out; \
67 if (!br_.ReadBits(1, &_out)) { \
68 DVLOG(1) \
69 << "Error in stream: unexpected EOS while trying to read " #out; \
70 return kInvalidStream; \
71 } \
72 *out = _out != 0; \
73 } while (0)
74
75 #define READ_UE_OR_RETURN(out) \
76 do { \
77 if (ReadUE(out) != kOk) { \
78 DVLOG(1) << "Error in stream: invalid value while trying to read " #out; \
79 return kInvalidStream; \
80 } \
81 } while (0)
82
83 #define READ_SE_OR_RETURN(out) \
84 do { \
85 if (ReadSE(out) != kOk) { \
86 DVLOG(1) << "Error in stream: invalid value while trying to read " #out; \
87 return kInvalidStream; \
88 } \
89 } while (0)
90
91 #define IN_RANGE_OR_RETURN(val, min, max) \
92 do { \
93 if ((val) < (min) || (val) > (max)) { \
94 DVLOG(1) << "Error in stream: invalid value, expected " #val " to be" \
95 << " in range [" << (min) << ":" << (max) << "]" \
96 << " found " << (val) << " instead"; \
97 return kInvalidStream; \
98 } \
99 } while (0)
100
101 #define TRUE_OR_RETURN(a) \
102 do { \
103 if (!(a)) { \
104 DVLOG(1) << "Error in stream: invalid value, expected " << #a; \
105 return kInvalidStream; \
106 } \
107 } while (0)
108
109 enum AspectRatioIdc {
110 kExtendedSar = 255,
111 };
112
113 // ISO 14496 part 10
114 // VUI parameters: Table E-1 "Meaning of sample aspect ratio indicator"
115 static const int kTableSarWidth[] = {
116 0, 1, 12, 10, 16, 40, 24, 20, 32, 80, 18, 15, 64, 160, 4, 3, 2
117 };
118 static const int kTableSarHeight[] = {
119 0, 1, 11, 11, 11, 33, 11, 11, 11, 33, 11, 11, 33, 99, 3, 2, 1
120 };
121 COMPILE_ASSERT(arraysize(kTableSarWidth) == arraysize(kTableSarHeight),
122 sar_tables_must_have_same_size);
123
H264Parser()124 H264Parser::H264Parser() {
125 Reset();
126 }
127
~H264Parser()128 H264Parser::~H264Parser() {
129 STLDeleteValues(&active_SPSes_);
130 STLDeleteValues(&active_PPSes_);
131 }
132
Reset()133 void H264Parser::Reset() {
134 stream_ = NULL;
135 bytes_left_ = 0;
136 }
137
SetStream(const uint8 * stream,off_t stream_size)138 void H264Parser::SetStream(const uint8* stream, off_t stream_size) {
139 DCHECK(stream);
140 DCHECK_GT(stream_size, 0);
141
142 stream_ = stream;
143 bytes_left_ = stream_size;
144 }
145
GetPPS(int pps_id)146 const H264PPS* H264Parser::GetPPS(int pps_id) {
147 return active_PPSes_[pps_id];
148 }
149
GetSPS(int sps_id)150 const H264SPS* H264Parser::GetSPS(int sps_id) {
151 return active_SPSes_[sps_id];
152 }
153
IsStartCode(const uint8 * data)154 static inline bool IsStartCode(const uint8* data) {
155 return data[0] == 0x00 && data[1] == 0x00 && data[2] == 0x01;
156 }
157
158 // static
FindStartCode(const uint8 * data,off_t data_size,off_t * offset,off_t * start_code_size)159 bool H264Parser::FindStartCode(const uint8* data, off_t data_size,
160 off_t* offset, off_t* start_code_size) {
161 DCHECK_GE(data_size, 0);
162 off_t bytes_left = data_size;
163
164 while (bytes_left >= 3) {
165 if (IsStartCode(data)) {
166 // Found three-byte start code, set pointer at its beginning.
167 *offset = data_size - bytes_left;
168 *start_code_size = 3;
169
170 // If there is a zero byte before this start code,
171 // then it's actually a four-byte start code, so backtrack one byte.
172 if (*offset > 0 && *(data - 1) == 0x00) {
173 --(*offset);
174 ++(*start_code_size);
175 }
176
177 return true;
178 }
179
180 ++data;
181 --bytes_left;
182 }
183
184 // End of data: offset is pointing to the first byte that was not considered
185 // as a possible start of a start code.
186 // Note: there is no security issue when receiving a negative |data_size|
187 // since in this case, |bytes_left| is equal to |data_size| and thus
188 // |*offset| is equal to 0 (valid offset).
189 *offset = data_size - bytes_left;
190 *start_code_size = 0;
191 return false;
192 }
193
LocateNALU(off_t * nalu_size,off_t * start_code_size)194 bool H264Parser::LocateNALU(off_t* nalu_size, off_t* start_code_size) {
195 // Find the start code of next NALU.
196 off_t nalu_start_off = 0;
197 off_t annexb_start_code_size = 0;
198 if (!FindStartCode(stream_, bytes_left_,
199 &nalu_start_off, &annexb_start_code_size)) {
200 DVLOG(4) << "Could not find start code, end of stream?";
201 return false;
202 }
203
204 // Move the stream to the beginning of the NALU (pointing at the start code).
205 stream_ += nalu_start_off;
206 bytes_left_ -= nalu_start_off;
207
208 const uint8* nalu_data = stream_ + annexb_start_code_size;
209 off_t max_nalu_data_size = bytes_left_ - annexb_start_code_size;
210 if (max_nalu_data_size <= 0) {
211 DVLOG(3) << "End of stream";
212 return false;
213 }
214
215 // Find the start code of next NALU;
216 // if successful, |nalu_size_without_start_code| is the number of bytes from
217 // after previous start code to before this one;
218 // if next start code is not found, it is still a valid NALU since there
219 // are some bytes left after the first start code: all the remaining bytes
220 // belong to the current NALU.
221 off_t next_start_code_size = 0;
222 off_t nalu_size_without_start_code = 0;
223 if (!FindStartCode(nalu_data, max_nalu_data_size,
224 &nalu_size_without_start_code, &next_start_code_size)) {
225 nalu_size_without_start_code = max_nalu_data_size;
226 }
227 *nalu_size = nalu_size_without_start_code + annexb_start_code_size;
228 *start_code_size = annexb_start_code_size;
229 return true;
230 }
231
ReadUE(int * val)232 H264Parser::Result H264Parser::ReadUE(int* val) {
233 int num_bits = -1;
234 int bit;
235 int rest;
236
237 // Count the number of contiguous zero bits.
238 do {
239 READ_BITS_OR_RETURN(1, &bit);
240 num_bits++;
241 } while (bit == 0);
242
243 if (num_bits > 31)
244 return kInvalidStream;
245
246 // Calculate exp-Golomb code value of size num_bits.
247 *val = (1 << num_bits) - 1;
248
249 if (num_bits > 0) {
250 READ_BITS_OR_RETURN(num_bits, &rest);
251 *val += rest;
252 }
253
254 return kOk;
255 }
256
ReadSE(int * val)257 H264Parser::Result H264Parser::ReadSE(int* val) {
258 int ue;
259 Result res;
260
261 // See Chapter 9 in the spec.
262 res = ReadUE(&ue);
263 if (res != kOk)
264 return res;
265
266 if (ue % 2 == 0)
267 *val = -(ue / 2);
268 else
269 *val = ue / 2 + 1;
270
271 return kOk;
272 }
273
AdvanceToNextNALU(H264NALU * nalu)274 H264Parser::Result H264Parser::AdvanceToNextNALU(H264NALU* nalu) {
275 off_t start_code_size;
276 off_t nalu_size_with_start_code;
277 if (!LocateNALU(&nalu_size_with_start_code, &start_code_size)) {
278 DVLOG(4) << "Could not find next NALU, bytes left in stream: "
279 << bytes_left_;
280 return kEOStream;
281 }
282
283 nalu->data = stream_ + start_code_size;
284 nalu->size = nalu_size_with_start_code - start_code_size;
285 DVLOG(4) << "NALU found: size=" << nalu_size_with_start_code;
286
287 // Initialize bit reader at the start of found NALU.
288 if (!br_.Initialize(nalu->data, nalu->size))
289 return kEOStream;
290
291 // Move parser state to after this NALU, so next time AdvanceToNextNALU
292 // is called, we will effectively be skipping it;
293 // other parsing functions will use the position saved
294 // in bit reader for parsing, so we don't have to remember it here.
295 stream_ += nalu_size_with_start_code;
296 bytes_left_ -= nalu_size_with_start_code;
297
298 // Read NALU header, skip the forbidden_zero_bit, but check for it.
299 int data;
300 READ_BITS_OR_RETURN(1, &data);
301 TRUE_OR_RETURN(data == 0);
302
303 READ_BITS_OR_RETURN(2, &nalu->nal_ref_idc);
304 READ_BITS_OR_RETURN(5, &nalu->nal_unit_type);
305
306 DVLOG(4) << "NALU type: " << static_cast<int>(nalu->nal_unit_type)
307 << " at: " << reinterpret_cast<const void*>(nalu->data)
308 << " size: " << nalu->size
309 << " ref: " << static_cast<int>(nalu->nal_ref_idc);
310
311 return kOk;
312 }
313
314 // Default scaling lists (per spec).
315 static const int kDefault4x4Intra[kH264ScalingList4x4Length] = {
316 6, 13, 13, 20, 20, 20, 28, 28, 28, 28, 32, 32, 32, 37, 37, 42, };
317
318 static const int kDefault4x4Inter[kH264ScalingList4x4Length] = {
319 10, 14, 14, 20, 20, 20, 24, 24, 24, 24, 27, 27, 27, 30, 30, 34, };
320
321 static const int kDefault8x8Intra[kH264ScalingList8x8Length] = {
322 6, 10, 10, 13, 11, 13, 16, 16, 16, 16, 18, 18, 18, 18, 18, 23,
323 23, 23, 23, 23, 23, 25, 25, 25, 25, 25, 25, 25, 27, 27, 27, 27,
324 27, 27, 27, 27, 29, 29, 29, 29, 29, 29, 29, 31, 31, 31, 31, 31,
325 31, 33, 33, 33, 33, 33, 36, 36, 36, 36, 38, 38, 38, 40, 40, 42, };
326
327 static const int kDefault8x8Inter[kH264ScalingList8x8Length] = {
328 9, 13, 13, 15, 13, 15, 17, 17, 17, 17, 19, 19, 19, 19, 19, 21,
329 21, 21, 21, 21, 21, 22, 22, 22, 22, 22, 22, 22, 24, 24, 24, 24,
330 24, 24, 24, 24, 25, 25, 25, 25, 25, 25, 25, 27, 27, 27, 27, 27,
331 27, 28, 28, 28, 28, 28, 30, 30, 30, 30, 32, 32, 32, 33, 33, 35, };
332
DefaultScalingList4x4(int i,int scaling_list4x4[][kH264ScalingList4x4Length])333 static inline void DefaultScalingList4x4(
334 int i,
335 int scaling_list4x4[][kH264ScalingList4x4Length]) {
336 DCHECK_LT(i, 6);
337
338 if (i < 3)
339 memcpy(scaling_list4x4[i], kDefault4x4Intra, sizeof(kDefault4x4Intra));
340 else if (i < 6)
341 memcpy(scaling_list4x4[i], kDefault4x4Inter, sizeof(kDefault4x4Inter));
342 }
343
DefaultScalingList8x8(int i,int scaling_list8x8[][kH264ScalingList8x8Length])344 static inline void DefaultScalingList8x8(
345 int i,
346 int scaling_list8x8[][kH264ScalingList8x8Length]) {
347 DCHECK_LT(i, 6);
348
349 if (i % 2 == 0)
350 memcpy(scaling_list8x8[i], kDefault8x8Intra, sizeof(kDefault8x8Intra));
351 else
352 memcpy(scaling_list8x8[i], kDefault8x8Inter, sizeof(kDefault8x8Inter));
353 }
354
FallbackScalingList4x4(int i,const int default_scaling_list_intra[],const int default_scaling_list_inter[],int scaling_list4x4[][kH264ScalingList4x4Length])355 static void FallbackScalingList4x4(
356 int i,
357 const int default_scaling_list_intra[],
358 const int default_scaling_list_inter[],
359 int scaling_list4x4[][kH264ScalingList4x4Length]) {
360 static const int kScalingList4x4ByteSize =
361 sizeof(scaling_list4x4[0][0]) * kH264ScalingList4x4Length;
362
363 switch (i) {
364 case 0:
365 memcpy(scaling_list4x4[i], default_scaling_list_intra,
366 kScalingList4x4ByteSize);
367 break;
368
369 case 1:
370 memcpy(scaling_list4x4[i], scaling_list4x4[0], kScalingList4x4ByteSize);
371 break;
372
373 case 2:
374 memcpy(scaling_list4x4[i], scaling_list4x4[1], kScalingList4x4ByteSize);
375 break;
376
377 case 3:
378 memcpy(scaling_list4x4[i], default_scaling_list_inter,
379 kScalingList4x4ByteSize);
380 break;
381
382 case 4:
383 memcpy(scaling_list4x4[i], scaling_list4x4[3], kScalingList4x4ByteSize);
384 break;
385
386 case 5:
387 memcpy(scaling_list4x4[i], scaling_list4x4[4], kScalingList4x4ByteSize);
388 break;
389
390 default:
391 NOTREACHED();
392 break;
393 }
394 }
395
FallbackScalingList8x8(int i,const int default_scaling_list_intra[],const int default_scaling_list_inter[],int scaling_list8x8[][kH264ScalingList8x8Length])396 static void FallbackScalingList8x8(
397 int i,
398 const int default_scaling_list_intra[],
399 const int default_scaling_list_inter[],
400 int scaling_list8x8[][kH264ScalingList8x8Length]) {
401 static const int kScalingList8x8ByteSize =
402 sizeof(scaling_list8x8[0][0]) * kH264ScalingList8x8Length;
403
404 switch (i) {
405 case 0:
406 memcpy(scaling_list8x8[i], default_scaling_list_intra,
407 kScalingList8x8ByteSize);
408 break;
409
410 case 1:
411 memcpy(scaling_list8x8[i], default_scaling_list_inter,
412 kScalingList8x8ByteSize);
413 break;
414
415 case 2:
416 memcpy(scaling_list8x8[i], scaling_list8x8[0], kScalingList8x8ByteSize);
417 break;
418
419 case 3:
420 memcpy(scaling_list8x8[i], scaling_list8x8[1], kScalingList8x8ByteSize);
421 break;
422
423 case 4:
424 memcpy(scaling_list8x8[i], scaling_list8x8[2], kScalingList8x8ByteSize);
425 break;
426
427 case 5:
428 memcpy(scaling_list8x8[i], scaling_list8x8[3], kScalingList8x8ByteSize);
429 break;
430
431 default:
432 NOTREACHED();
433 break;
434 }
435 }
436
ParseScalingList(int size,int * scaling_list,bool * use_default)437 H264Parser::Result H264Parser::ParseScalingList(int size,
438 int* scaling_list,
439 bool* use_default) {
440 // See chapter 7.3.2.1.1.1.
441 int last_scale = 8;
442 int next_scale = 8;
443 int delta_scale;
444
445 *use_default = false;
446
447 for (int j = 0; j < size; ++j) {
448 if (next_scale != 0) {
449 READ_SE_OR_RETURN(&delta_scale);
450 IN_RANGE_OR_RETURN(delta_scale, -128, 127);
451 next_scale = (last_scale + delta_scale + 256) & 0xff;
452
453 if (j == 0 && next_scale == 0) {
454 *use_default = true;
455 return kOk;
456 }
457 }
458
459 scaling_list[j] = (next_scale == 0) ? last_scale : next_scale;
460 last_scale = scaling_list[j];
461 }
462
463 return kOk;
464 }
465
ParseSPSScalingLists(H264SPS * sps)466 H264Parser::Result H264Parser::ParseSPSScalingLists(H264SPS* sps) {
467 // See 7.4.2.1.1.
468 bool seq_scaling_list_present_flag;
469 bool use_default;
470 Result res;
471
472 // Parse scaling_list4x4.
473 for (int i = 0; i < 6; ++i) {
474 READ_BOOL_OR_RETURN(&seq_scaling_list_present_flag);
475
476 if (seq_scaling_list_present_flag) {
477 res = ParseScalingList(arraysize(sps->scaling_list4x4[i]),
478 sps->scaling_list4x4[i],
479 &use_default);
480 if (res != kOk)
481 return res;
482
483 if (use_default)
484 DefaultScalingList4x4(i, sps->scaling_list4x4);
485
486 } else {
487 FallbackScalingList4x4(
488 i, kDefault4x4Intra, kDefault4x4Inter, sps->scaling_list4x4);
489 }
490 }
491
492 // Parse scaling_list8x8.
493 for (int i = 0; i < ((sps->chroma_format_idc != 3) ? 2 : 6); ++i) {
494 READ_BOOL_OR_RETURN(&seq_scaling_list_present_flag);
495
496 if (seq_scaling_list_present_flag) {
497 res = ParseScalingList(arraysize(sps->scaling_list8x8[i]),
498 sps->scaling_list8x8[i],
499 &use_default);
500 if (res != kOk)
501 return res;
502
503 if (use_default)
504 DefaultScalingList8x8(i, sps->scaling_list8x8);
505
506 } else {
507 FallbackScalingList8x8(
508 i, kDefault8x8Intra, kDefault8x8Inter, sps->scaling_list8x8);
509 }
510 }
511
512 return kOk;
513 }
514
ParsePPSScalingLists(const H264SPS & sps,H264PPS * pps)515 H264Parser::Result H264Parser::ParsePPSScalingLists(const H264SPS& sps,
516 H264PPS* pps) {
517 // See 7.4.2.2.
518 bool pic_scaling_list_present_flag;
519 bool use_default;
520 Result res;
521
522 for (int i = 0; i < 6; ++i) {
523 READ_BOOL_OR_RETURN(&pic_scaling_list_present_flag);
524
525 if (pic_scaling_list_present_flag) {
526 res = ParseScalingList(arraysize(pps->scaling_list4x4[i]),
527 pps->scaling_list4x4[i],
528 &use_default);
529 if (res != kOk)
530 return res;
531
532 if (use_default)
533 DefaultScalingList4x4(i, pps->scaling_list4x4);
534
535 } else {
536 if (sps.seq_scaling_matrix_present_flag) {
537 // Table 7-2 fallback rule A in spec.
538 FallbackScalingList4x4(
539 i, kDefault4x4Intra, kDefault4x4Inter, pps->scaling_list4x4);
540 } else {
541 // Table 7-2 fallback rule B in spec.
542 FallbackScalingList4x4(i,
543 sps.scaling_list4x4[0],
544 sps.scaling_list4x4[3],
545 pps->scaling_list4x4);
546 }
547 }
548 }
549
550 if (pps->transform_8x8_mode_flag) {
551 for (int i = 0; i < ((sps.chroma_format_idc != 3) ? 2 : 6); ++i) {
552 READ_BOOL_OR_RETURN(&pic_scaling_list_present_flag);
553
554 if (pic_scaling_list_present_flag) {
555 res = ParseScalingList(arraysize(pps->scaling_list8x8[i]),
556 pps->scaling_list8x8[i],
557 &use_default);
558 if (res != kOk)
559 return res;
560
561 if (use_default)
562 DefaultScalingList8x8(i, pps->scaling_list8x8);
563
564 } else {
565 if (sps.seq_scaling_matrix_present_flag) {
566 // Table 7-2 fallback rule A in spec.
567 FallbackScalingList8x8(
568 i, kDefault8x8Intra, kDefault8x8Inter, pps->scaling_list8x8);
569 } else {
570 // Table 7-2 fallback rule B in spec.
571 FallbackScalingList8x8(i,
572 sps.scaling_list8x8[0],
573 sps.scaling_list8x8[1],
574 pps->scaling_list8x8);
575 }
576 }
577 }
578 }
579 return kOk;
580 }
581
ParseAndIgnoreHRDParameters(bool * hrd_parameters_present)582 H264Parser::Result H264Parser::ParseAndIgnoreHRDParameters(
583 bool* hrd_parameters_present) {
584 int data;
585 READ_BOOL_OR_RETURN(&data); // {nal,vcl}_hrd_parameters_present_flag
586 if (!data)
587 return kOk;
588
589 *hrd_parameters_present = true;
590
591 int cpb_cnt_minus1;
592 READ_UE_OR_RETURN(&cpb_cnt_minus1);
593 IN_RANGE_OR_RETURN(cpb_cnt_minus1, 0, 31);
594 READ_BITS_OR_RETURN(8, &data); // bit_rate_scale, cpb_size_scale
595 for (int i = 0; i <= cpb_cnt_minus1; ++i) {
596 READ_UE_OR_RETURN(&data); // bit_rate_value_minus1[i]
597 READ_UE_OR_RETURN(&data); // cpb_size_value_minus1[i]
598 READ_BOOL_OR_RETURN(&data); // cbr_flag
599 }
600 READ_BITS_OR_RETURN(20, &data); // cpb/dpb delays, etc.
601
602 return kOk;
603 }
604
ParseVUIParameters(H264SPS * sps)605 H264Parser::Result H264Parser::ParseVUIParameters(H264SPS* sps) {
606 bool aspect_ratio_info_present_flag;
607 READ_BOOL_OR_RETURN(&aspect_ratio_info_present_flag);
608 if (aspect_ratio_info_present_flag) {
609 int aspect_ratio_idc;
610 READ_BITS_OR_RETURN(8, &aspect_ratio_idc);
611 if (aspect_ratio_idc == kExtendedSar) {
612 READ_BITS_OR_RETURN(16, &sps->sar_width);
613 READ_BITS_OR_RETURN(16, &sps->sar_height);
614 } else {
615 const int max_aspect_ratio_idc = arraysize(kTableSarWidth) - 1;
616 IN_RANGE_OR_RETURN(aspect_ratio_idc, 0, max_aspect_ratio_idc);
617 sps->sar_width = kTableSarWidth[aspect_ratio_idc];
618 sps->sar_height = kTableSarHeight[aspect_ratio_idc];
619 }
620 }
621
622 int data;
623 // Read and ignore overscan and video signal type info.
624 READ_BOOL_OR_RETURN(&data); // overscan_info_present_flag
625 if (data)
626 READ_BOOL_OR_RETURN(&data); // overscan_appropriate_flag
627
628 READ_BOOL_OR_RETURN(&data); // video_signal_type_present_flag
629 if (data) {
630 READ_BITS_OR_RETURN(3, &data); // video_format
631 READ_BOOL_OR_RETURN(&data); // video_full_range_flag
632 READ_BOOL_OR_RETURN(&data); // colour_description_present_flag
633 if (data)
634 READ_BITS_OR_RETURN(24, &data); // color description syntax elements
635 }
636
637 READ_BOOL_OR_RETURN(&data); // chroma_loc_info_present_flag
638 if (data) {
639 READ_UE_OR_RETURN(&data); // chroma_sample_loc_type_top_field
640 READ_UE_OR_RETURN(&data); // chroma_sample_loc_type_bottom_field
641 }
642
643 // Read and ignore timing info.
644 READ_BOOL_OR_RETURN(&data); // timing_info_present_flag
645 if (data) {
646 READ_BITS_OR_RETURN(16, &data); // num_units_in_tick
647 READ_BITS_OR_RETURN(16, &data); // num_units_in_tick
648 READ_BITS_OR_RETURN(16, &data); // time_scale
649 READ_BITS_OR_RETURN(16, &data); // time_scale
650 READ_BOOL_OR_RETURN(&data); // fixed_frame_rate_flag
651 }
652
653 // Read and ignore NAL HRD parameters, if present.
654 bool hrd_parameters_present = false;
655 Result res = ParseAndIgnoreHRDParameters(&hrd_parameters_present);
656 if (res != kOk)
657 return res;
658
659 // Read and ignore VCL HRD parameters, if present.
660 res = ParseAndIgnoreHRDParameters(&hrd_parameters_present);
661 if (res != kOk)
662 return res;
663
664 if (hrd_parameters_present) // One of NAL or VCL params present is enough.
665 READ_BOOL_OR_RETURN(&data); // low_delay_hrd_flag
666
667 READ_BOOL_OR_RETURN(&data); // pic_struct_present_flag
668 READ_BOOL_OR_RETURN(&sps->bitstream_restriction_flag);
669 if (sps->bitstream_restriction_flag) {
670 READ_BOOL_OR_RETURN(&data); // motion_vectors_over_pic_boundaries_flag
671 READ_UE_OR_RETURN(&data); // max_bytes_per_pic_denom
672 READ_UE_OR_RETURN(&data); // max_bits_per_mb_denom
673 READ_UE_OR_RETURN(&data); // log2_max_mv_length_horizontal
674 READ_UE_OR_RETURN(&data); // log2_max_mv_length_vertical
675 READ_UE_OR_RETURN(&sps->max_num_reorder_frames);
676 READ_UE_OR_RETURN(&sps->max_dec_frame_buffering);
677 TRUE_OR_RETURN(sps->max_dec_frame_buffering >= sps->max_num_ref_frames);
678 IN_RANGE_OR_RETURN(
679 sps->max_num_reorder_frames, 0, sps->max_dec_frame_buffering);
680 }
681
682 return kOk;
683 }
684
FillDefaultSeqScalingLists(H264SPS * sps)685 static void FillDefaultSeqScalingLists(H264SPS* sps) {
686 for (int i = 0; i < 6; ++i)
687 for (int j = 0; j < kH264ScalingList4x4Length; ++j)
688 sps->scaling_list4x4[i][j] = 16;
689
690 for (int i = 0; i < 6; ++i)
691 for (int j = 0; j < kH264ScalingList8x8Length; ++j)
692 sps->scaling_list8x8[i][j] = 16;
693 }
694
ParseSPS(int * sps_id)695 H264Parser::Result H264Parser::ParseSPS(int* sps_id) {
696 // See 7.4.2.1.
697 int data;
698 Result res;
699
700 *sps_id = -1;
701
702 scoped_ptr<H264SPS> sps(new H264SPS());
703
704 READ_BITS_OR_RETURN(8, &sps->profile_idc);
705 READ_BOOL_OR_RETURN(&sps->constraint_set0_flag);
706 READ_BOOL_OR_RETURN(&sps->constraint_set1_flag);
707 READ_BOOL_OR_RETURN(&sps->constraint_set2_flag);
708 READ_BOOL_OR_RETURN(&sps->constraint_set3_flag);
709 READ_BOOL_OR_RETURN(&sps->constraint_set4_flag);
710 READ_BOOL_OR_RETURN(&sps->constraint_set5_flag);
711 READ_BITS_OR_RETURN(2, &data); // reserved_zero_2bits
712 READ_BITS_OR_RETURN(8, &sps->level_idc);
713 READ_UE_OR_RETURN(&sps->seq_parameter_set_id);
714 TRUE_OR_RETURN(sps->seq_parameter_set_id < 32);
715
716 if (sps->profile_idc == 100 || sps->profile_idc == 110 ||
717 sps->profile_idc == 122 || sps->profile_idc == 244 ||
718 sps->profile_idc == 44 || sps->profile_idc == 83 ||
719 sps->profile_idc == 86 || sps->profile_idc == 118 ||
720 sps->profile_idc == 128) {
721 READ_UE_OR_RETURN(&sps->chroma_format_idc);
722 TRUE_OR_RETURN(sps->chroma_format_idc < 4);
723
724 if (sps->chroma_format_idc == 3)
725 READ_BOOL_OR_RETURN(&sps->separate_colour_plane_flag);
726
727 READ_UE_OR_RETURN(&sps->bit_depth_luma_minus8);
728 TRUE_OR_RETURN(sps->bit_depth_luma_minus8 < 7);
729
730 READ_UE_OR_RETURN(&sps->bit_depth_chroma_minus8);
731 TRUE_OR_RETURN(sps->bit_depth_chroma_minus8 < 7);
732
733 READ_BOOL_OR_RETURN(&sps->qpprime_y_zero_transform_bypass_flag);
734 READ_BOOL_OR_RETURN(&sps->seq_scaling_matrix_present_flag);
735
736 if (sps->seq_scaling_matrix_present_flag) {
737 DVLOG(4) << "Scaling matrix present";
738 res = ParseSPSScalingLists(sps.get());
739 if (res != kOk)
740 return res;
741 } else {
742 FillDefaultSeqScalingLists(sps.get());
743 }
744 } else {
745 sps->chroma_format_idc = 1;
746 FillDefaultSeqScalingLists(sps.get());
747 }
748
749 if (sps->separate_colour_plane_flag)
750 sps->chroma_array_type = 0;
751 else
752 sps->chroma_array_type = sps->chroma_format_idc;
753
754 READ_UE_OR_RETURN(&sps->log2_max_frame_num_minus4);
755 TRUE_OR_RETURN(sps->log2_max_frame_num_minus4 < 13);
756
757 READ_UE_OR_RETURN(&sps->pic_order_cnt_type);
758 TRUE_OR_RETURN(sps->pic_order_cnt_type < 3);
759
760 sps->expected_delta_per_pic_order_cnt_cycle = 0;
761 if (sps->pic_order_cnt_type == 0) {
762 READ_UE_OR_RETURN(&sps->log2_max_pic_order_cnt_lsb_minus4);
763 TRUE_OR_RETURN(sps->log2_max_pic_order_cnt_lsb_minus4 < 13);
764 } else if (sps->pic_order_cnt_type == 1) {
765 READ_BOOL_OR_RETURN(&sps->delta_pic_order_always_zero_flag);
766 READ_SE_OR_RETURN(&sps->offset_for_non_ref_pic);
767 READ_SE_OR_RETURN(&sps->offset_for_top_to_bottom_field);
768 READ_UE_OR_RETURN(&sps->num_ref_frames_in_pic_order_cnt_cycle);
769 TRUE_OR_RETURN(sps->num_ref_frames_in_pic_order_cnt_cycle < 255);
770
771 for (int i = 0; i < sps->num_ref_frames_in_pic_order_cnt_cycle; ++i) {
772 READ_SE_OR_RETURN(&sps->offset_for_ref_frame[i]);
773 sps->expected_delta_per_pic_order_cnt_cycle +=
774 sps->offset_for_ref_frame[i];
775 }
776 }
777
778 READ_UE_OR_RETURN(&sps->max_num_ref_frames);
779 READ_BOOL_OR_RETURN(&sps->gaps_in_frame_num_value_allowed_flag);
780
781 if (sps->gaps_in_frame_num_value_allowed_flag)
782 return kUnsupportedStream;
783
784 READ_UE_OR_RETURN(&sps->pic_width_in_mbs_minus1);
785 READ_UE_OR_RETURN(&sps->pic_height_in_map_units_minus1);
786
787 READ_BOOL_OR_RETURN(&sps->frame_mbs_only_flag);
788 if (!sps->frame_mbs_only_flag)
789 READ_BOOL_OR_RETURN(&sps->mb_adaptive_frame_field_flag);
790
791 READ_BOOL_OR_RETURN(&sps->direct_8x8_inference_flag);
792
793 READ_BOOL_OR_RETURN(&sps->frame_cropping_flag);
794 if (sps->frame_cropping_flag) {
795 READ_UE_OR_RETURN(&sps->frame_crop_left_offset);
796 READ_UE_OR_RETURN(&sps->frame_crop_right_offset);
797 READ_UE_OR_RETURN(&sps->frame_crop_top_offset);
798 READ_UE_OR_RETURN(&sps->frame_crop_bottom_offset);
799 }
800
801 READ_BOOL_OR_RETURN(&sps->vui_parameters_present_flag);
802 if (sps->vui_parameters_present_flag) {
803 DVLOG(4) << "VUI parameters present";
804 res = ParseVUIParameters(sps.get());
805 if (res != kOk)
806 return res;
807 }
808
809 // If an SPS with the same id already exists, replace it.
810 *sps_id = sps->seq_parameter_set_id;
811 delete active_SPSes_[*sps_id];
812 active_SPSes_[*sps_id] = sps.release();
813
814 return kOk;
815 }
816
ParsePPS(int * pps_id)817 H264Parser::Result H264Parser::ParsePPS(int* pps_id) {
818 // See 7.4.2.2.
819 const H264SPS* sps;
820 Result res;
821
822 *pps_id = -1;
823
824 scoped_ptr<H264PPS> pps(new H264PPS());
825
826 READ_UE_OR_RETURN(&pps->pic_parameter_set_id);
827 READ_UE_OR_RETURN(&pps->seq_parameter_set_id);
828 TRUE_OR_RETURN(pps->seq_parameter_set_id < 32);
829
830 sps = GetSPS(pps->seq_parameter_set_id);
831 TRUE_OR_RETURN(sps);
832
833 READ_BOOL_OR_RETURN(&pps->entropy_coding_mode_flag);
834 READ_BOOL_OR_RETURN(&pps->bottom_field_pic_order_in_frame_present_flag);
835
836 READ_UE_OR_RETURN(&pps->num_slice_groups_minus1);
837 if (pps->num_slice_groups_minus1 > 1) {
838 DVLOG(1) << "Slice groups not supported";
839 return kUnsupportedStream;
840 }
841
842 READ_UE_OR_RETURN(&pps->num_ref_idx_l0_default_active_minus1);
843 TRUE_OR_RETURN(pps->num_ref_idx_l0_default_active_minus1 < 32);
844
845 READ_UE_OR_RETURN(&pps->num_ref_idx_l1_default_active_minus1);
846 TRUE_OR_RETURN(pps->num_ref_idx_l1_default_active_minus1 < 32);
847
848 READ_BOOL_OR_RETURN(&pps->weighted_pred_flag);
849 READ_BITS_OR_RETURN(2, &pps->weighted_bipred_idc);
850 TRUE_OR_RETURN(pps->weighted_bipred_idc < 3);
851
852 READ_SE_OR_RETURN(&pps->pic_init_qp_minus26);
853 IN_RANGE_OR_RETURN(pps->pic_init_qp_minus26, -26, 25);
854
855 READ_SE_OR_RETURN(&pps->pic_init_qs_minus26);
856 IN_RANGE_OR_RETURN(pps->pic_init_qs_minus26, -26, 25);
857
858 READ_SE_OR_RETURN(&pps->chroma_qp_index_offset);
859 IN_RANGE_OR_RETURN(pps->chroma_qp_index_offset, -12, 12);
860 pps->second_chroma_qp_index_offset = pps->chroma_qp_index_offset;
861
862 READ_BOOL_OR_RETURN(&pps->deblocking_filter_control_present_flag);
863 READ_BOOL_OR_RETURN(&pps->constrained_intra_pred_flag);
864 READ_BOOL_OR_RETURN(&pps->redundant_pic_cnt_present_flag);
865
866 if (br_.HasMoreRBSPData()) {
867 READ_BOOL_OR_RETURN(&pps->transform_8x8_mode_flag);
868 READ_BOOL_OR_RETURN(&pps->pic_scaling_matrix_present_flag);
869
870 if (pps->pic_scaling_matrix_present_flag) {
871 DVLOG(4) << "Picture scaling matrix present";
872 res = ParsePPSScalingLists(*sps, pps.get());
873 if (res != kOk)
874 return res;
875 }
876
877 READ_SE_OR_RETURN(&pps->second_chroma_qp_index_offset);
878 }
879
880 // If a PPS with the same id already exists, replace it.
881 *pps_id = pps->pic_parameter_set_id;
882 delete active_PPSes_[*pps_id];
883 active_PPSes_[*pps_id] = pps.release();
884
885 return kOk;
886 }
887
ParseRefPicListModification(int num_ref_idx_active_minus1,H264ModificationOfPicNum * ref_list_mods)888 H264Parser::Result H264Parser::ParseRefPicListModification(
889 int num_ref_idx_active_minus1,
890 H264ModificationOfPicNum* ref_list_mods) {
891 H264ModificationOfPicNum* pic_num_mod;
892
893 if (num_ref_idx_active_minus1 >= 32)
894 return kInvalidStream;
895
896 for (int i = 0; i < 32; ++i) {
897 pic_num_mod = &ref_list_mods[i];
898 READ_UE_OR_RETURN(&pic_num_mod->modification_of_pic_nums_idc);
899 TRUE_OR_RETURN(pic_num_mod->modification_of_pic_nums_idc < 4);
900
901 switch (pic_num_mod->modification_of_pic_nums_idc) {
902 case 0:
903 case 1:
904 READ_UE_OR_RETURN(&pic_num_mod->abs_diff_pic_num_minus1);
905 break;
906
907 case 2:
908 READ_UE_OR_RETURN(&pic_num_mod->long_term_pic_num);
909 break;
910
911 case 3:
912 // Per spec, list cannot be empty.
913 if (i == 0)
914 return kInvalidStream;
915 return kOk;
916
917 default:
918 return kInvalidStream;
919 }
920 }
921
922 // If we got here, we didn't get loop end marker prematurely,
923 // so make sure it is there for our client.
924 int modification_of_pic_nums_idc;
925 READ_UE_OR_RETURN(&modification_of_pic_nums_idc);
926 TRUE_OR_RETURN(modification_of_pic_nums_idc == 3);
927
928 return kOk;
929 }
930
ParseRefPicListModifications(H264SliceHeader * shdr)931 H264Parser::Result H264Parser::ParseRefPicListModifications(
932 H264SliceHeader* shdr) {
933 Result res;
934
935 if (!shdr->IsISlice() && !shdr->IsSISlice()) {
936 READ_BOOL_OR_RETURN(&shdr->ref_pic_list_modification_flag_l0);
937 if (shdr->ref_pic_list_modification_flag_l0) {
938 res = ParseRefPicListModification(shdr->num_ref_idx_l0_active_minus1,
939 shdr->ref_list_l0_modifications);
940 if (res != kOk)
941 return res;
942 }
943 }
944
945 if (shdr->IsBSlice()) {
946 READ_BOOL_OR_RETURN(&shdr->ref_pic_list_modification_flag_l1);
947 if (shdr->ref_pic_list_modification_flag_l1) {
948 res = ParseRefPicListModification(shdr->num_ref_idx_l1_active_minus1,
949 shdr->ref_list_l1_modifications);
950 if (res != kOk)
951 return res;
952 }
953 }
954
955 return kOk;
956 }
957
ParseWeightingFactors(int num_ref_idx_active_minus1,int chroma_array_type,int luma_log2_weight_denom,int chroma_log2_weight_denom,H264WeightingFactors * w_facts)958 H264Parser::Result H264Parser::ParseWeightingFactors(
959 int num_ref_idx_active_minus1,
960 int chroma_array_type,
961 int luma_log2_weight_denom,
962 int chroma_log2_weight_denom,
963 H264WeightingFactors* w_facts) {
964
965 int def_luma_weight = 1 << luma_log2_weight_denom;
966 int def_chroma_weight = 1 << chroma_log2_weight_denom;
967
968 for (int i = 0; i < num_ref_idx_active_minus1 + 1; ++i) {
969 READ_BOOL_OR_RETURN(&w_facts->luma_weight_flag);
970 if (w_facts->luma_weight_flag) {
971 READ_SE_OR_RETURN(&w_facts->luma_weight[i]);
972 IN_RANGE_OR_RETURN(w_facts->luma_weight[i], -128, 127);
973
974 READ_SE_OR_RETURN(&w_facts->luma_offset[i]);
975 IN_RANGE_OR_RETURN(w_facts->luma_offset[i], -128, 127);
976 } else {
977 w_facts->luma_weight[i] = def_luma_weight;
978 w_facts->luma_offset[i] = 0;
979 }
980
981 if (chroma_array_type != 0) {
982 READ_BOOL_OR_RETURN(&w_facts->chroma_weight_flag);
983 if (w_facts->chroma_weight_flag) {
984 for (int j = 0; j < 2; ++j) {
985 READ_SE_OR_RETURN(&w_facts->chroma_weight[i][j]);
986 IN_RANGE_OR_RETURN(w_facts->chroma_weight[i][j], -128, 127);
987
988 READ_SE_OR_RETURN(&w_facts->chroma_offset[i][j]);
989 IN_RANGE_OR_RETURN(w_facts->chroma_offset[i][j], -128, 127);
990 }
991 } else {
992 for (int j = 0; j < 2; ++j) {
993 w_facts->chroma_weight[i][j] = def_chroma_weight;
994 w_facts->chroma_offset[i][j] = 0;
995 }
996 }
997 }
998 }
999
1000 return kOk;
1001 }
1002
ParsePredWeightTable(const H264SPS & sps,H264SliceHeader * shdr)1003 H264Parser::Result H264Parser::ParsePredWeightTable(const H264SPS& sps,
1004 H264SliceHeader* shdr) {
1005 READ_UE_OR_RETURN(&shdr->luma_log2_weight_denom);
1006 TRUE_OR_RETURN(shdr->luma_log2_weight_denom < 8);
1007
1008 if (sps.chroma_array_type != 0)
1009 READ_UE_OR_RETURN(&shdr->chroma_log2_weight_denom);
1010 TRUE_OR_RETURN(shdr->chroma_log2_weight_denom < 8);
1011
1012 Result res = ParseWeightingFactors(shdr->num_ref_idx_l0_active_minus1,
1013 sps.chroma_array_type,
1014 shdr->luma_log2_weight_denom,
1015 shdr->chroma_log2_weight_denom,
1016 &shdr->pred_weight_table_l0);
1017 if (res != kOk)
1018 return res;
1019
1020 if (shdr->IsBSlice()) {
1021 res = ParseWeightingFactors(shdr->num_ref_idx_l1_active_minus1,
1022 sps.chroma_array_type,
1023 shdr->luma_log2_weight_denom,
1024 shdr->chroma_log2_weight_denom,
1025 &shdr->pred_weight_table_l1);
1026 if (res != kOk)
1027 return res;
1028 }
1029
1030 return kOk;
1031 }
1032
ParseDecRefPicMarking(H264SliceHeader * shdr)1033 H264Parser::Result H264Parser::ParseDecRefPicMarking(H264SliceHeader* shdr) {
1034 if (shdr->idr_pic_flag) {
1035 READ_BOOL_OR_RETURN(&shdr->no_output_of_prior_pics_flag);
1036 READ_BOOL_OR_RETURN(&shdr->long_term_reference_flag);
1037 } else {
1038 READ_BOOL_OR_RETURN(&shdr->adaptive_ref_pic_marking_mode_flag);
1039
1040 H264DecRefPicMarking* marking;
1041 if (shdr->adaptive_ref_pic_marking_mode_flag) {
1042 size_t i;
1043 for (i = 0; i < arraysize(shdr->ref_pic_marking); ++i) {
1044 marking = &shdr->ref_pic_marking[i];
1045
1046 READ_UE_OR_RETURN(&marking->memory_mgmnt_control_operation);
1047 if (marking->memory_mgmnt_control_operation == 0)
1048 break;
1049
1050 if (marking->memory_mgmnt_control_operation == 1 ||
1051 marking->memory_mgmnt_control_operation == 3)
1052 READ_UE_OR_RETURN(&marking->difference_of_pic_nums_minus1);
1053
1054 if (marking->memory_mgmnt_control_operation == 2)
1055 READ_UE_OR_RETURN(&marking->long_term_pic_num);
1056
1057 if (marking->memory_mgmnt_control_operation == 3 ||
1058 marking->memory_mgmnt_control_operation == 6)
1059 READ_UE_OR_RETURN(&marking->long_term_frame_idx);
1060
1061 if (marking->memory_mgmnt_control_operation == 4)
1062 READ_UE_OR_RETURN(&marking->max_long_term_frame_idx_plus1);
1063
1064 if (marking->memory_mgmnt_control_operation > 6)
1065 return kInvalidStream;
1066 }
1067
1068 if (i == arraysize(shdr->ref_pic_marking)) {
1069 DVLOG(1) << "Ran out of dec ref pic marking fields";
1070 return kUnsupportedStream;
1071 }
1072 }
1073 }
1074
1075 return kOk;
1076 }
1077
ParseSliceHeader(const H264NALU & nalu,H264SliceHeader * shdr)1078 H264Parser::Result H264Parser::ParseSliceHeader(const H264NALU& nalu,
1079 H264SliceHeader* shdr) {
1080 // See 7.4.3.
1081 const H264SPS* sps;
1082 const H264PPS* pps;
1083 Result res;
1084
1085 memset(shdr, 0, sizeof(*shdr));
1086
1087 shdr->idr_pic_flag = (nalu.nal_unit_type == 5);
1088 shdr->nal_ref_idc = nalu.nal_ref_idc;
1089 shdr->nalu_data = nalu.data;
1090 shdr->nalu_size = nalu.size;
1091
1092 READ_UE_OR_RETURN(&shdr->first_mb_in_slice);
1093 READ_UE_OR_RETURN(&shdr->slice_type);
1094 TRUE_OR_RETURN(shdr->slice_type < 10);
1095
1096 READ_UE_OR_RETURN(&shdr->pic_parameter_set_id);
1097
1098 pps = GetPPS(shdr->pic_parameter_set_id);
1099 TRUE_OR_RETURN(pps);
1100
1101 sps = GetSPS(pps->seq_parameter_set_id);
1102 TRUE_OR_RETURN(sps);
1103
1104 if (sps->separate_colour_plane_flag) {
1105 DVLOG(1) << "Interlaced streams not supported";
1106 return kUnsupportedStream;
1107 }
1108
1109 READ_BITS_OR_RETURN(sps->log2_max_frame_num_minus4 + 4, &shdr->frame_num);
1110 if (!sps->frame_mbs_only_flag) {
1111 READ_BOOL_OR_RETURN(&shdr->field_pic_flag);
1112 if (shdr->field_pic_flag) {
1113 DVLOG(1) << "Interlaced streams not supported";
1114 return kUnsupportedStream;
1115 }
1116 }
1117
1118 if (shdr->idr_pic_flag)
1119 READ_UE_OR_RETURN(&shdr->idr_pic_id);
1120
1121 if (sps->pic_order_cnt_type == 0) {
1122 READ_BITS_OR_RETURN(sps->log2_max_pic_order_cnt_lsb_minus4 + 4,
1123 &shdr->pic_order_cnt_lsb);
1124 if (pps->bottom_field_pic_order_in_frame_present_flag &&
1125 !shdr->field_pic_flag)
1126 READ_SE_OR_RETURN(&shdr->delta_pic_order_cnt_bottom);
1127 }
1128
1129 if (sps->pic_order_cnt_type == 1 && !sps->delta_pic_order_always_zero_flag) {
1130 READ_SE_OR_RETURN(&shdr->delta_pic_order_cnt[0]);
1131 if (pps->bottom_field_pic_order_in_frame_present_flag &&
1132 !shdr->field_pic_flag)
1133 READ_SE_OR_RETURN(&shdr->delta_pic_order_cnt[1]);
1134 }
1135
1136 if (pps->redundant_pic_cnt_present_flag) {
1137 READ_UE_OR_RETURN(&shdr->redundant_pic_cnt);
1138 TRUE_OR_RETURN(shdr->redundant_pic_cnt < 128);
1139 }
1140
1141 if (shdr->IsBSlice())
1142 READ_BOOL_OR_RETURN(&shdr->direct_spatial_mv_pred_flag);
1143
1144 if (shdr->IsPSlice() || shdr->IsSPSlice() || shdr->IsBSlice()) {
1145 READ_BOOL_OR_RETURN(&shdr->num_ref_idx_active_override_flag);
1146 if (shdr->num_ref_idx_active_override_flag) {
1147 READ_UE_OR_RETURN(&shdr->num_ref_idx_l0_active_minus1);
1148 if (shdr->IsBSlice())
1149 READ_UE_OR_RETURN(&shdr->num_ref_idx_l1_active_minus1);
1150 } else {
1151 shdr->num_ref_idx_l0_active_minus1 =
1152 pps->num_ref_idx_l0_default_active_minus1;
1153 if (shdr->IsBSlice()) {
1154 shdr->num_ref_idx_l1_active_minus1 =
1155 pps->num_ref_idx_l1_default_active_minus1;
1156 }
1157 }
1158 }
1159 if (shdr->field_pic_flag) {
1160 TRUE_OR_RETURN(shdr->num_ref_idx_l0_active_minus1 < 32);
1161 TRUE_OR_RETURN(shdr->num_ref_idx_l1_active_minus1 < 32);
1162 } else {
1163 TRUE_OR_RETURN(shdr->num_ref_idx_l0_active_minus1 < 16);
1164 TRUE_OR_RETURN(shdr->num_ref_idx_l1_active_minus1 < 16);
1165 }
1166
1167 if (nalu.nal_unit_type == H264NALU::kCodedSliceExtension) {
1168 return kUnsupportedStream;
1169 } else {
1170 res = ParseRefPicListModifications(shdr);
1171 if (res != kOk)
1172 return res;
1173 }
1174
1175 if ((pps->weighted_pred_flag && (shdr->IsPSlice() || shdr->IsSPSlice())) ||
1176 (pps->weighted_bipred_idc == 1 && shdr->IsBSlice())) {
1177 res = ParsePredWeightTable(*sps, shdr);
1178 if (res != kOk)
1179 return res;
1180 }
1181
1182 if (nalu.nal_ref_idc != 0) {
1183 res = ParseDecRefPicMarking(shdr);
1184 if (res != kOk)
1185 return res;
1186 }
1187
1188 if (pps->entropy_coding_mode_flag && !shdr->IsISlice() &&
1189 !shdr->IsSISlice()) {
1190 READ_UE_OR_RETURN(&shdr->cabac_init_idc);
1191 TRUE_OR_RETURN(shdr->cabac_init_idc < 3);
1192 }
1193
1194 READ_SE_OR_RETURN(&shdr->slice_qp_delta);
1195
1196 if (shdr->IsSPSlice() || shdr->IsSISlice()) {
1197 if (shdr->IsSPSlice())
1198 READ_BOOL_OR_RETURN(&shdr->sp_for_switch_flag);
1199 READ_SE_OR_RETURN(&shdr->slice_qs_delta);
1200 }
1201
1202 if (pps->deblocking_filter_control_present_flag) {
1203 READ_UE_OR_RETURN(&shdr->disable_deblocking_filter_idc);
1204 TRUE_OR_RETURN(shdr->disable_deblocking_filter_idc < 3);
1205
1206 if (shdr->disable_deblocking_filter_idc != 1) {
1207 READ_SE_OR_RETURN(&shdr->slice_alpha_c0_offset_div2);
1208 IN_RANGE_OR_RETURN(shdr->slice_alpha_c0_offset_div2, -6, 6);
1209
1210 READ_SE_OR_RETURN(&shdr->slice_beta_offset_div2);
1211 IN_RANGE_OR_RETURN(shdr->slice_beta_offset_div2, -6, 6);
1212 }
1213 }
1214
1215 if (pps->num_slice_groups_minus1 > 0) {
1216 DVLOG(1) << "Slice groups not supported";
1217 return kUnsupportedStream;
1218 }
1219
1220 size_t epb = br_.NumEmulationPreventionBytesRead();
1221 shdr->header_bit_size = (shdr->nalu_size - epb) * 8 - br_.NumBitsLeft();
1222
1223 return kOk;
1224 }
1225
ParseSEI(H264SEIMessage * sei_msg)1226 H264Parser::Result H264Parser::ParseSEI(H264SEIMessage* sei_msg) {
1227 int byte;
1228
1229 memset(sei_msg, 0, sizeof(*sei_msg));
1230
1231 READ_BITS_OR_RETURN(8, &byte);
1232 while (byte == 0xff) {
1233 sei_msg->type += 255;
1234 READ_BITS_OR_RETURN(8, &byte);
1235 }
1236 sei_msg->type += byte;
1237
1238 READ_BITS_OR_RETURN(8, &byte);
1239 while (byte == 0xff) {
1240 sei_msg->payload_size += 255;
1241 READ_BITS_OR_RETURN(8, &byte);
1242 }
1243 sei_msg->payload_size += byte;
1244
1245 DVLOG(4) << "Found SEI message type: " << sei_msg->type
1246 << " payload size: " << sei_msg->payload_size;
1247
1248 switch (sei_msg->type) {
1249 case H264SEIMessage::kSEIRecoveryPoint:
1250 READ_UE_OR_RETURN(&sei_msg->recovery_point.recovery_frame_cnt);
1251 READ_BOOL_OR_RETURN(&sei_msg->recovery_point.exact_match_flag);
1252 READ_BOOL_OR_RETURN(&sei_msg->recovery_point.broken_link_flag);
1253 READ_BITS_OR_RETURN(2, &sei_msg->recovery_point.changing_slice_group_idc);
1254 break;
1255
1256 default:
1257 DVLOG(4) << "Unsupported SEI message";
1258 break;
1259 }
1260
1261 return kOk;
1262 }
1263
1264 } // namespace media
1265