1 /* Gstreamer
2 * Copyright (C) <2011> Intel Corporation
3 * Copyright (C) <2011> Collabora Ltd.
4 * Copyright (C) <2011> Thibault Saunier <thibault.saunier@collabora.com>
5 *
6 * Some bits C-c,C-v'ed and s/4/3 from h264parse and videoparsers/h264parse.c:
7 * Copyright (C) <2010> Mark Nauwelaerts <mark.nauwelaerts@collabora.co.uk>
8 * Copyright (C) <2010> Collabora Multimedia
9 * Copyright (C) <2010> Nokia Corporation
10 *
11 * (C) 2005 Michal Benes <michal.benes@itonis.tv>
12 * (C) 2008 Wim Taymans <wim.taymans@gmail.com>
13 *
14 * This library is free software; you can redistribute it and/or
15 * modify it under the terms of the GNU Library General Public
16 * License as published by the Free Software Foundation; either
17 * version 2 of the License, or (at your option) any later version.
18 *
19 * This library is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22 * Library General Public License for more details.
23 *
24 * You should have received a copy of the GNU Library General Public
25 * License along with this library; if not, write to the
26 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
27 * Boston, MA 02110-1301, USA.
28 */
29
30 /**
31 * SECTION:gsth264parser
32 * @title: GstH264Parser
33 * @short_description: Convenience library for h264 video
34 * bitstream parsing.
35 *
36 * It offers bitstream parsing in both AVC (length-prefixed) and Annex B
37 * (0x000001 start code prefix) format. To identify a NAL unit in a bitstream
38 * and parse its headers, first call:
39 *
40 * * #gst_h264_parser_identify_nalu to identify a NAL unit in an Annex B type bitstream
41 *
42 * * #gst_h264_parser_identify_nalu_avc to identify a NAL unit in an AVC type bitstream
43 *
44 * The following functions are then available for parsing the structure of the
45 * #GstH264NalUnit, depending on the #GstH264NalUnitType:
46 *
47 * * From #GST_H264_NAL_SLICE to #GST_H264_NAL_SLICE_IDR: #gst_h264_parser_parse_slice_hdr
48 *
49 * * #GST_H264_NAL_SEI: #gst_h264_parser_parse_sei
50 *
51 * * #GST_H264_NAL_SPS: #gst_h264_parser_parse_sps
52 *
53 * * #GST_H264_NAL_PPS: #gst_h264_parser_parse_pps
54 *
55 * * Any other: #gst_h264_parser_parse_nal
56 *
57 * One of these functions *must* be called on every NAL unit in the bitstream,
58 * in order to keep the internal structures of the #GstH264NalParser up to
59 * date. It is legal to call #gst_h264_parser_parse_nal on NAL units of any
60 * type, if no special parsing of the current NAL unit is required by the
61 * application.
62 *
63 * For more details about the structures, look at the ITU-T H.264 and ISO/IEC 14496-10 – MPEG-4
64 * Part 10 specifications, available at:
65 *
66 * * ITU-T H.264: http://www.itu.int/rec/T-REC-H.264
67 *
68 * * ISO/IEC 14496-10: http://www.iso.org/iso/iso_catalogue/catalogue_tc/catalogue_detail.htm?csnumber=56538
69 *
70 */
71
72 #ifdef HAVE_CONFIG_H
73 # include "config.h"
74 #endif
75
76 #include "nalutils.h"
77 #include "gsth264parser.h"
78
79 #include <gst/base/gstbytereader.h>
80 #include <gst/base/gstbitreader.h>
81 #include <string.h>
82
83 GST_DEBUG_CATEGORY_STATIC (h264_parser_debug);
84 #define GST_CAT_DEFAULT h264_parser_debug
85
86 static gboolean initialized = FALSE;
87 #define INITIALIZE_DEBUG_CATEGORY \
88 if (!initialized) { \
89 GST_DEBUG_CATEGORY_INIT (h264_parser_debug, "codecparsers_h264", 0, \
90 "h264 parser library"); \
91 initialized = TRUE; \
92 }
93
94 /**** Default scaling_lists according to Table 7-2 *****/
95 static const guint8 default_4x4_intra[16] = {
96 6, 13, 13, 20, 20, 20, 28, 28, 28, 28, 32, 32,
97 32, 37, 37, 42
98 };
99
100 static const guint8 default_4x4_inter[16] = {
101 10, 14, 14, 20, 20, 20, 24, 24, 24, 24, 27, 27,
102 27, 30, 30, 34
103 };
104
105 static const guint8 default_8x8_intra[64] = {
106 6, 10, 10, 13, 11, 13, 16, 16, 16, 16, 18, 18,
107 18, 18, 18, 23, 23, 23, 23, 23, 23, 25, 25, 25, 25, 25, 25, 25, 27, 27, 27,
108 27, 27, 27, 27, 27, 29, 29, 29, 29, 29, 29, 29, 31, 31, 31, 31, 31, 31, 33,
109 33, 33, 33, 33, 36, 36, 36, 36, 38, 38, 38, 40, 40, 42
110 };
111
112 static const guint8 default_8x8_inter[64] = {
113 9, 13, 13, 15, 13, 15, 17, 17, 17, 17, 19, 19,
114 19, 19, 19, 21, 21, 21, 21, 21, 21, 22, 22, 22, 22, 22, 22, 22, 24, 24, 24,
115 24, 24, 24, 24, 24, 25, 25, 25, 25, 25, 25, 25, 27, 27, 27, 27, 27, 27, 28,
116 28, 28, 28, 28, 30, 30, 30, 30, 32, 32, 32, 33, 33, 35
117 };
118
119 static const guint8 zigzag_8x8[64] = {
120 0, 1, 8, 16, 9, 2, 3, 10,
121 17, 24, 32, 25, 18, 11, 4, 5,
122 12, 19, 26, 33, 40, 48, 41, 34,
123 27, 20, 13, 6, 7, 14, 21, 28,
124 35, 42, 49, 56, 57, 50, 43, 36,
125 29, 22, 15, 23, 30, 37, 44, 51,
126 58, 59, 52, 45, 38, 31, 39, 46,
127 53, 60, 61, 54, 47, 55, 62, 63
128 };
129
130 static const guint8 zigzag_4x4[16] = {
131 0, 1, 4, 8,
132 5, 2, 3, 6,
133 9, 12, 13, 10,
134 7, 11, 14, 15,
135 };
136
137 typedef struct
138 {
139 guint par_n, par_d;
140 } PAR;
141
142 /* Table E-1 - Meaning of sample aspect ratio indicator (1..16) */
143 static const PAR aspect_ratios[17] = {
144 {0, 0},
145 {1, 1},
146 {12, 11},
147 {10, 11},
148 {16, 11},
149 {40, 33},
150 {24, 11},
151 {20, 11},
152 {32, 11},
153 {80, 33},
154 {18, 11},
155 {15, 11},
156 {64, 33},
157 {160, 99},
158 {4, 3},
159 {3, 2},
160 {2, 1}
161 };
162
163 /***** Utils ****/
164 #define EXTENDED_SAR 255
165
166 static GstH264SPS *
gst_h264_parser_get_sps(GstH264NalParser * nalparser,guint8 sps_id)167 gst_h264_parser_get_sps (GstH264NalParser * nalparser, guint8 sps_id)
168 {
169 GstH264SPS *sps;
170
171 sps = &nalparser->sps[sps_id];
172
173 if (sps->valid)
174 return sps;
175
176 return NULL;
177 }
178
179 static GstH264PPS *
gst_h264_parser_get_pps(GstH264NalParser * nalparser,guint8 pps_id)180 gst_h264_parser_get_pps (GstH264NalParser * nalparser, guint8 pps_id)
181 {
182 GstH264PPS *pps;
183
184 pps = &nalparser->pps[pps_id];
185
186 if (pps->valid)
187 return pps;
188
189 return NULL;
190 }
191
192 static gboolean
gst_h264_parse_nalu_header(GstH264NalUnit * nalu)193 gst_h264_parse_nalu_header (GstH264NalUnit * nalu)
194 {
195 guint8 *data = nalu->data + nalu->offset;
196 guint8 svc_extension_flag;
197 GstBitReader br;
198
199 if (nalu->size < 1)
200 return FALSE;
201
202 nalu->type = (data[0] & 0x1f);
203 nalu->ref_idc = (data[0] & 0x60) >> 5;
204 nalu->idr_pic_flag = (nalu->type == 5 ? 1 : 0);
205 nalu->header_bytes = 1;
206
207 nalu->extension_type = GST_H264_NAL_EXTENSION_NONE;
208
209 switch (nalu->type) {
210 case GST_H264_NAL_PREFIX_UNIT:
211 case GST_H264_NAL_SLICE_EXT:
212 if (nalu->size < 4)
213 return FALSE;
214 gst_bit_reader_init (&br, nalu->data + nalu->offset + nalu->header_bytes,
215 nalu->size - nalu->header_bytes);
216
217 svc_extension_flag = gst_bit_reader_get_bits_uint8_unchecked (&br, 1);
218 if (svc_extension_flag) { /* SVC */
219
220 nalu->extension_type = GST_H264_NAL_EXTENSION_SVC;
221
222 } else { /* MVC */
223 GstH264NalUnitExtensionMVC *const mvc = &nalu->extension.mvc;
224
225 nalu->extension_type = GST_H264_NAL_EXTENSION_MVC;
226 mvc->non_idr_flag = gst_bit_reader_get_bits_uint8_unchecked (&br, 1);
227 mvc->priority_id = gst_bit_reader_get_bits_uint8_unchecked (&br, 6);
228 mvc->view_id = gst_bit_reader_get_bits_uint16_unchecked (&br, 10);
229 mvc->temporal_id = gst_bit_reader_get_bits_uint8_unchecked (&br, 3);
230 mvc->anchor_pic_flag = gst_bit_reader_get_bits_uint8_unchecked (&br, 1);
231 mvc->inter_view_flag = gst_bit_reader_get_bits_uint8_unchecked (&br, 1);
232
233 /* Update IdrPicFlag (H.7.4.1.1) */
234 nalu->idr_pic_flag = !mvc->non_idr_flag;
235 }
236 nalu->header_bytes += 3;
237 break;
238 default:
239 break;
240 }
241
242 GST_DEBUG ("Nal type %u, ref_idc %u", nalu->type, nalu->ref_idc);
243 return TRUE;
244 }
245
246 /*
247 * gst_h264_pps_copy:
248 * @dst_pps: The destination #GstH264PPS to copy into
249 * @src_pps: The source #GstH264PPS to copy from
250 *
251 * Copies @src_pps into @dst_pps.
252 *
253 * Returns: %TRUE if everything went fine, %FALSE otherwise
254 */
255 static gboolean
gst_h264_pps_copy(GstH264PPS * dst_pps,const GstH264PPS * src_pps)256 gst_h264_pps_copy (GstH264PPS * dst_pps, const GstH264PPS * src_pps)
257 {
258 g_return_val_if_fail (dst_pps != NULL, FALSE);
259 g_return_val_if_fail (src_pps != NULL, FALSE);
260
261 gst_h264_pps_clear (dst_pps);
262
263 *dst_pps = *src_pps;
264
265 if (src_pps->slice_group_id)
266 dst_pps->slice_group_id = g_memdup (src_pps->slice_group_id,
267 src_pps->pic_size_in_map_units_minus1 + 1);
268
269 return TRUE;
270 }
271
272 /* Copy MVC-specific data for subset SPS header */
273 static gboolean
gst_h264_sps_mvc_copy(GstH264SPS * dst_sps,const GstH264SPS * src_sps)274 gst_h264_sps_mvc_copy (GstH264SPS * dst_sps, const GstH264SPS * src_sps)
275 {
276 GstH264SPSExtMVC *const dst_mvc = &dst_sps->extension.mvc;
277 const GstH264SPSExtMVC *const src_mvc = &src_sps->extension.mvc;
278 guint i, j, k;
279
280 g_assert (dst_sps->extension_type == GST_H264_NAL_EXTENSION_MVC);
281
282 dst_mvc->num_views_minus1 = src_mvc->num_views_minus1;
283 dst_mvc->view = g_new0 (GstH264SPSExtMVCView, dst_mvc->num_views_minus1 + 1);
284 if (!dst_mvc->view)
285 return FALSE;
286
287 dst_mvc->view[0].view_id = src_mvc->view[0].view_id;
288
289 for (i = 1; i <= dst_mvc->num_views_minus1; i++) {
290 GstH264SPSExtMVCView *const dst_view = &dst_mvc->view[i];
291 const GstH264SPSExtMVCView *const src_view = &src_mvc->view[i];
292
293 dst_view->view_id = src_view->view_id;
294
295 dst_view->num_anchor_refs_l0 = src_view->num_anchor_refs_l0;
296 for (j = 0; j < dst_view->num_anchor_refs_l0; j++)
297 dst_view->anchor_ref_l0[j] = src_view->anchor_ref_l0[j];
298
299 dst_view->num_anchor_refs_l1 = src_view->num_anchor_refs_l1;
300 for (j = 0; j < dst_view->num_anchor_refs_l1; j++)
301 dst_view->anchor_ref_l1[j] = src_view->anchor_ref_l1[j];
302
303 dst_view->num_non_anchor_refs_l0 = src_view->num_non_anchor_refs_l0;
304 for (j = 0; j < dst_view->num_non_anchor_refs_l0; j++)
305 dst_view->non_anchor_ref_l0[j] = src_view->non_anchor_ref_l0[j];
306
307 dst_view->num_non_anchor_refs_l1 = src_view->num_non_anchor_refs_l1;
308 for (j = 0; j < dst_view->num_non_anchor_refs_l1; j++)
309 dst_view->non_anchor_ref_l1[j] = src_view->non_anchor_ref_l1[j];
310 }
311
312 dst_mvc->num_level_values_signalled_minus1 =
313 src_mvc->num_level_values_signalled_minus1;
314 dst_mvc->level_value = g_new0 (GstH264SPSExtMVCLevelValue,
315 dst_mvc->num_level_values_signalled_minus1 + 1);
316 if (!dst_mvc->level_value)
317 return FALSE;
318
319 for (i = 0; i <= dst_mvc->num_level_values_signalled_minus1; i++) {
320 GstH264SPSExtMVCLevelValue *const dst_value = &dst_mvc->level_value[i];
321 const GstH264SPSExtMVCLevelValue *const src_value =
322 &src_mvc->level_value[i];
323
324 dst_value->level_idc = src_value->level_idc;
325
326 dst_value->num_applicable_ops_minus1 = src_value->num_applicable_ops_minus1;
327 dst_value->applicable_op = g_new0 (GstH264SPSExtMVCLevelValueOp,
328 dst_value->num_applicable_ops_minus1 + 1);
329 if (!dst_value->applicable_op)
330 return FALSE;
331
332 for (j = 0; j <= dst_value->num_applicable_ops_minus1; j++) {
333 GstH264SPSExtMVCLevelValueOp *const dst_op = &dst_value->applicable_op[j];
334 const GstH264SPSExtMVCLevelValueOp *const src_op =
335 &src_value->applicable_op[j];
336
337 dst_op->temporal_id = src_op->temporal_id;
338 dst_op->num_target_views_minus1 = src_op->num_target_views_minus1;
339 dst_op->target_view_id =
340 g_new (guint16, dst_op->num_target_views_minus1 + 1);
341 if (!dst_op->target_view_id)
342 return FALSE;
343
344 for (k = 0; k <= dst_op->num_target_views_minus1; k++)
345 dst_op->target_view_id[k] = src_op->target_view_id[k];
346 dst_op->num_views_minus1 = src_op->num_views_minus1;
347 }
348 }
349 return TRUE;
350 }
351
352 /*
353 * gst_h264_sps_copy:
354 * @dst_sps: The destination #GstH264SPS to copy into
355 * @src_sps: The source #GstH264SPS to copy from
356 *
357 * Copies @src_sps into @dst_sps.
358 *
359 * Returns: %TRUE if everything went fine, %FALSE otherwise
360 */
361 static gboolean
gst_h264_sps_copy(GstH264SPS * dst_sps,const GstH264SPS * src_sps)362 gst_h264_sps_copy (GstH264SPS * dst_sps, const GstH264SPS * src_sps)
363 {
364 g_return_val_if_fail (dst_sps != NULL, FALSE);
365 g_return_val_if_fail (src_sps != NULL, FALSE);
366
367 gst_h264_sps_clear (dst_sps);
368
369 *dst_sps = *src_sps;
370
371 switch (dst_sps->extension_type) {
372 case GST_H264_NAL_EXTENSION_MVC:
373 if (!gst_h264_sps_mvc_copy (dst_sps, src_sps))
374 return FALSE;
375 break;
376 }
377 return TRUE;
378 }
379
380 /****** Parsing functions *****/
381
382 static gboolean
gst_h264_parse_hrd_parameters(GstH264HRDParams * hrd,NalReader * nr)383 gst_h264_parse_hrd_parameters (GstH264HRDParams * hrd, NalReader * nr)
384 {
385 guint sched_sel_idx;
386
387 GST_DEBUG ("parsing \"HRD Parameters\"");
388
389 READ_UE_MAX (nr, hrd->cpb_cnt_minus1, 31);
390 READ_UINT8 (nr, hrd->bit_rate_scale, 4);
391 READ_UINT8 (nr, hrd->cpb_size_scale, 4);
392
393 for (sched_sel_idx = 0; sched_sel_idx <= hrd->cpb_cnt_minus1; sched_sel_idx++) {
394 READ_UE (nr, hrd->bit_rate_value_minus1[sched_sel_idx]);
395 READ_UE (nr, hrd->cpb_size_value_minus1[sched_sel_idx]);
396 READ_UINT8 (nr, hrd->cbr_flag[sched_sel_idx], 1);
397 }
398
399 READ_UINT8 (nr, hrd->initial_cpb_removal_delay_length_minus1, 5);
400 READ_UINT8 (nr, hrd->cpb_removal_delay_length_minus1, 5);
401 READ_UINT8 (nr, hrd->dpb_output_delay_length_minus1, 5);
402 READ_UINT8 (nr, hrd->time_offset_length, 5);
403
404 return TRUE;
405
406 error:
407 GST_WARNING ("error parsing \"HRD Parameters\"");
408 return FALSE;
409 }
410
411 static gboolean
gst_h264_parse_vui_parameters(GstH264SPS * sps,NalReader * nr)412 gst_h264_parse_vui_parameters (GstH264SPS * sps, NalReader * nr)
413 {
414 GstH264VUIParams *vui = &sps->vui_parameters;
415
416 GST_DEBUG ("parsing \"VUI Parameters\"");
417
418 /* set default values for fields that might not be present in the bitstream
419 and have valid defaults */
420 vui->video_format = 5;
421 vui->colour_primaries = 2;
422 vui->transfer_characteristics = 2;
423 vui->matrix_coefficients = 2;
424
425 READ_UINT8 (nr, vui->aspect_ratio_info_present_flag, 1);
426 if (vui->aspect_ratio_info_present_flag) {
427 READ_UINT8 (nr, vui->aspect_ratio_idc, 8);
428 if (vui->aspect_ratio_idc == EXTENDED_SAR) {
429 READ_UINT16 (nr, vui->sar_width, 16);
430 READ_UINT16 (nr, vui->sar_height, 16);
431 vui->par_n = vui->sar_width;
432 vui->par_d = vui->sar_height;
433 } else if (vui->aspect_ratio_idc <= 16) {
434 vui->par_n = aspect_ratios[vui->aspect_ratio_idc].par_n;
435 vui->par_d = aspect_ratios[vui->aspect_ratio_idc].par_d;
436 }
437 }
438
439 READ_UINT8 (nr, vui->overscan_info_present_flag, 1);
440 if (vui->overscan_info_present_flag)
441 READ_UINT8 (nr, vui->overscan_appropriate_flag, 1);
442
443 READ_UINT8 (nr, vui->video_signal_type_present_flag, 1);
444 if (vui->video_signal_type_present_flag) {
445
446 READ_UINT8 (nr, vui->video_format, 3);
447 READ_UINT8 (nr, vui->video_full_range_flag, 1);
448 READ_UINT8 (nr, vui->colour_description_present_flag, 1);
449 if (vui->colour_description_present_flag) {
450 READ_UINT8 (nr, vui->colour_primaries, 8);
451 READ_UINT8 (nr, vui->transfer_characteristics, 8);
452 READ_UINT8 (nr, vui->matrix_coefficients, 8);
453 }
454 }
455
456 READ_UINT8 (nr, vui->chroma_loc_info_present_flag, 1);
457 if (vui->chroma_loc_info_present_flag) {
458 READ_UE_MAX (nr, vui->chroma_sample_loc_type_top_field, 5);
459 READ_UE_MAX (nr, vui->chroma_sample_loc_type_bottom_field, 5);
460 }
461
462 READ_UINT8 (nr, vui->timing_info_present_flag, 1);
463 if (vui->timing_info_present_flag) {
464 READ_UINT32 (nr, vui->num_units_in_tick, 32);
465 if (vui->num_units_in_tick == 0)
466 GST_WARNING ("num_units_in_tick = 0 detected in stream "
467 "(incompliant to H.264 E.2.1).");
468
469 READ_UINT32 (nr, vui->time_scale, 32);
470 if (vui->time_scale == 0)
471 GST_WARNING ("time_scale = 0 detected in stream "
472 "(incompliant to H.264 E.2.1).");
473
474 READ_UINT8 (nr, vui->fixed_frame_rate_flag, 1);
475 }
476
477 READ_UINT8 (nr, vui->nal_hrd_parameters_present_flag, 1);
478 if (vui->nal_hrd_parameters_present_flag) {
479 if (!gst_h264_parse_hrd_parameters (&vui->nal_hrd_parameters, nr))
480 goto error;
481 }
482
483 READ_UINT8 (nr, vui->vcl_hrd_parameters_present_flag, 1);
484 if (vui->vcl_hrd_parameters_present_flag) {
485 if (!gst_h264_parse_hrd_parameters (&vui->vcl_hrd_parameters, nr))
486 goto error;
487 }
488
489 if (vui->nal_hrd_parameters_present_flag ||
490 vui->vcl_hrd_parameters_present_flag)
491 READ_UINT8 (nr, vui->low_delay_hrd_flag, 1);
492
493 READ_UINT8 (nr, vui->pic_struct_present_flag, 1);
494 READ_UINT8 (nr, vui->bitstream_restriction_flag, 1);
495 if (vui->bitstream_restriction_flag) {
496 READ_UINT8 (nr, vui->motion_vectors_over_pic_boundaries_flag, 1);
497 READ_UE (nr, vui->max_bytes_per_pic_denom);
498 READ_UE_MAX (nr, vui->max_bits_per_mb_denom, 16);
499 READ_UE_MAX (nr, vui->log2_max_mv_length_horizontal, 16);
500 READ_UE_MAX (nr, vui->log2_max_mv_length_vertical, 16);
501 READ_UE (nr, vui->num_reorder_frames);
502 READ_UE (nr, vui->max_dec_frame_buffering);
503 }
504
505 return TRUE;
506
507 error:
508 GST_WARNING ("error parsing \"VUI Parameters\"");
509 return FALSE;
510 }
511
512 static gboolean
gst_h264_parser_parse_scaling_list(NalReader * nr,guint8 scaling_lists_4x4[6][16],guint8 scaling_lists_8x8[6][64],const guint8 fallback_4x4_inter[16],const guint8 fallback_4x4_intra[16],const guint8 fallback_8x8_inter[64],const guint8 fallback_8x8_intra[64],guint8 n_lists)513 gst_h264_parser_parse_scaling_list (NalReader * nr,
514 guint8 scaling_lists_4x4[6][16], guint8 scaling_lists_8x8[6][64],
515 const guint8 fallback_4x4_inter[16], const guint8 fallback_4x4_intra[16],
516 const guint8 fallback_8x8_inter[64], const guint8 fallback_8x8_intra[64],
517 guint8 n_lists)
518 {
519 guint i;
520
521 static const guint8 *default_lists[12] = {
522 default_4x4_intra, default_4x4_intra, default_4x4_intra,
523 default_4x4_inter, default_4x4_inter, default_4x4_inter,
524 default_8x8_intra, default_8x8_inter,
525 default_8x8_intra, default_8x8_inter,
526 default_8x8_intra, default_8x8_inter
527 };
528
529 GST_DEBUG ("parsing scaling lists");
530
531 for (i = 0; i < 12; i++) {
532 gboolean use_default = FALSE;
533
534 if (i < n_lists) {
535 guint8 scaling_list_present_flag;
536
537 READ_UINT8 (nr, scaling_list_present_flag, 1);
538 if (scaling_list_present_flag) {
539 guint8 *scaling_list;
540 guint size;
541 guint j;
542 guint8 last_scale, next_scale;
543
544 if (i < 6) {
545 scaling_list = scaling_lists_4x4[i];
546 size = 16;
547 } else {
548 scaling_list = scaling_lists_8x8[i - 6];
549 size = 64;
550 }
551
552 last_scale = 8;
553 next_scale = 8;
554 for (j = 0; j < size; j++) {
555 if (next_scale != 0) {
556 gint32 delta_scale;
557
558 READ_SE (nr, delta_scale);
559 next_scale = (last_scale + delta_scale) & 0xff;
560 }
561 if (j == 0 && next_scale == 0) {
562 /* Use default scaling lists (7.4.2.1.1.1) */
563 memcpy (scaling_list, default_lists[i], size);
564 break;
565 }
566 last_scale = scaling_list[j] =
567 (next_scale == 0) ? last_scale : next_scale;
568 }
569 } else
570 use_default = TRUE;
571 } else
572 use_default = TRUE;
573
574 if (use_default) {
575 switch (i) {
576 case 0:
577 memcpy (scaling_lists_4x4[0], fallback_4x4_intra, 16);
578 break;
579 case 1:
580 memcpy (scaling_lists_4x4[1], scaling_lists_4x4[0], 16);
581 break;
582 case 2:
583 memcpy (scaling_lists_4x4[2], scaling_lists_4x4[1], 16);
584 break;
585 case 3:
586 memcpy (scaling_lists_4x4[3], fallback_4x4_inter, 16);
587 break;
588 case 4:
589 memcpy (scaling_lists_4x4[4], scaling_lists_4x4[3], 16);
590 break;
591 case 5:
592 memcpy (scaling_lists_4x4[5], scaling_lists_4x4[4], 16);
593 break;
594 case 6:
595 memcpy (scaling_lists_8x8[0], fallback_8x8_intra, 64);
596 break;
597 case 7:
598 memcpy (scaling_lists_8x8[1], fallback_8x8_inter, 64);
599 break;
600 case 8:
601 memcpy (scaling_lists_8x8[2], scaling_lists_8x8[0], 64);
602 break;
603 case 9:
604 memcpy (scaling_lists_8x8[3], scaling_lists_8x8[1], 64);
605 break;
606 case 10:
607 memcpy (scaling_lists_8x8[4], scaling_lists_8x8[2], 64);
608 break;
609 case 11:
610 memcpy (scaling_lists_8x8[5], scaling_lists_8x8[3], 64);
611 break;
612
613 default:
614 break;
615 }
616 }
617 }
618
619 return TRUE;
620
621 error:
622 GST_WARNING ("error parsing scaling lists");
623 return FALSE;
624 }
625
626 static gboolean
slice_parse_ref_pic_list_modification_1(GstH264SliceHdr * slice,NalReader * nr,guint list,gboolean is_mvc)627 slice_parse_ref_pic_list_modification_1 (GstH264SliceHdr * slice,
628 NalReader * nr, guint list, gboolean is_mvc)
629 {
630 GstH264RefPicListModification *entries;
631 guint8 *ref_pic_list_modification_flag, *n_ref_pic_list_modification;
632 guint32 modification_of_pic_nums_idc;
633 gsize max_entries;
634 guint i = 0;
635
636 if (list == 0) {
637 entries = slice->ref_pic_list_modification_l0;
638 max_entries = G_N_ELEMENTS (slice->ref_pic_list_modification_l0);
639 ref_pic_list_modification_flag = &slice->ref_pic_list_modification_flag_l0;
640 n_ref_pic_list_modification = &slice->n_ref_pic_list_modification_l0;
641 } else {
642 entries = slice->ref_pic_list_modification_l1;
643 max_entries = G_N_ELEMENTS (slice->ref_pic_list_modification_l1);
644 ref_pic_list_modification_flag = &slice->ref_pic_list_modification_flag_l1;
645 n_ref_pic_list_modification = &slice->n_ref_pic_list_modification_l1;
646 }
647
648 READ_UINT8 (nr, *ref_pic_list_modification_flag, 1);
649 if (*ref_pic_list_modification_flag) {
650 while (1) {
651 READ_UE (nr, modification_of_pic_nums_idc);
652 if (modification_of_pic_nums_idc == 0 ||
653 modification_of_pic_nums_idc == 1) {
654 READ_UE_MAX (nr, entries[i].value.abs_diff_pic_num_minus1,
655 slice->max_pic_num - 1);
656 } else if (modification_of_pic_nums_idc == 2) {
657 READ_UE (nr, entries[i].value.long_term_pic_num);
658 } else if (is_mvc && (modification_of_pic_nums_idc == 4 ||
659 modification_of_pic_nums_idc == 5)) {
660 READ_UE (nr, entries[i].value.abs_diff_view_idx_minus1);
661 }
662 entries[i++].modification_of_pic_nums_idc = modification_of_pic_nums_idc;
663 if (modification_of_pic_nums_idc == 3)
664 break;
665 if (i >= max_entries)
666 goto error;
667 }
668 }
669 *n_ref_pic_list_modification = i;
670 return TRUE;
671
672 error:
673 GST_WARNING ("error parsing \"Reference picture list %u modification\"",
674 list);
675 return FALSE;
676 }
677
678 static gboolean
slice_parse_ref_pic_list_modification(GstH264SliceHdr * slice,NalReader * nr,gboolean is_mvc)679 slice_parse_ref_pic_list_modification (GstH264SliceHdr * slice, NalReader * nr,
680 gboolean is_mvc)
681 {
682 if (!GST_H264_IS_I_SLICE (slice) && !GST_H264_IS_SI_SLICE (slice)) {
683 if (!slice_parse_ref_pic_list_modification_1 (slice, nr, 0, is_mvc))
684 return FALSE;
685 }
686
687 if (GST_H264_IS_B_SLICE (slice)) {
688 if (!slice_parse_ref_pic_list_modification_1 (slice, nr, 1, is_mvc))
689 return FALSE;
690 }
691 return TRUE;
692 }
693
694 static gboolean
gst_h264_slice_parse_dec_ref_pic_marking(GstH264SliceHdr * slice,GstH264NalUnit * nalu,NalReader * nr)695 gst_h264_slice_parse_dec_ref_pic_marking (GstH264SliceHdr * slice,
696 GstH264NalUnit * nalu, NalReader * nr)
697 {
698 GstH264DecRefPicMarking *dec_ref_pic_m;
699
700 GST_DEBUG ("parsing \"Decoded reference picture marking\"");
701
702 dec_ref_pic_m = &slice->dec_ref_pic_marking;
703
704 if (nalu->idr_pic_flag) {
705 READ_UINT8 (nr, dec_ref_pic_m->no_output_of_prior_pics_flag, 1);
706 READ_UINT8 (nr, dec_ref_pic_m->long_term_reference_flag, 1);
707 } else {
708 READ_UINT8 (nr, dec_ref_pic_m->adaptive_ref_pic_marking_mode_flag, 1);
709 if (dec_ref_pic_m->adaptive_ref_pic_marking_mode_flag) {
710 guint32 mem_mgmt_ctrl_op;
711 GstH264RefPicMarking *refpicmarking;
712
713 dec_ref_pic_m->n_ref_pic_marking = 0;
714 while (1) {
715 #ifndef OHOS_OPT_CVE
716 refpicmarking =
717 &dec_ref_pic_m->ref_pic_marking[dec_ref_pic_m->n_ref_pic_marking];
718 #endif
719 READ_UE (nr, mem_mgmt_ctrl_op);
720 if (mem_mgmt_ctrl_op == 0)
721 break;
722
723 #ifdef OHOS_OPT_CVE
724 if (dec_ref_pic_m->n_ref_pic_marking >=
725 G_N_ELEMENTS (dec_ref_pic_m->ref_pic_marking))
726 goto error;
727
728 refpicmarking =
729 &dec_ref_pic_m->ref_pic_marking[dec_ref_pic_m->n_ref_pic_marking];
730 #endif
731
732 refpicmarking->memory_management_control_operation = mem_mgmt_ctrl_op;
733
734 if (mem_mgmt_ctrl_op == 1 || mem_mgmt_ctrl_op == 3)
735 READ_UE (nr, refpicmarking->difference_of_pic_nums_minus1);
736
737 if (mem_mgmt_ctrl_op == 2)
738 READ_UE (nr, refpicmarking->long_term_pic_num);
739
740 if (mem_mgmt_ctrl_op == 3 || mem_mgmt_ctrl_op == 6)
741 READ_UE (nr, refpicmarking->long_term_frame_idx);
742
743 if (mem_mgmt_ctrl_op == 4)
744 READ_UE (nr, refpicmarking->max_long_term_frame_idx_plus1);
745
746 dec_ref_pic_m->n_ref_pic_marking++;
747 }
748 }
749 }
750
751 return TRUE;
752
753 error:
754 GST_WARNING ("error parsing \"Decoded reference picture marking\"");
755 return FALSE;
756 }
757
758 static gboolean
gst_h264_slice_parse_pred_weight_table(GstH264SliceHdr * slice,NalReader * nr,guint8 chroma_array_type)759 gst_h264_slice_parse_pred_weight_table (GstH264SliceHdr * slice,
760 NalReader * nr, guint8 chroma_array_type)
761 {
762 GstH264PredWeightTable *p;
763 gint16 default_luma_weight, default_chroma_weight;
764 gint i;
765
766 GST_DEBUG ("parsing \"Prediction weight table\"");
767
768 p = &slice->pred_weight_table;
769
770 READ_UE_MAX (nr, p->luma_log2_weight_denom, 7);
771 /* set default values */
772 default_luma_weight = 1 << p->luma_log2_weight_denom;
773 for (i = 0; i < G_N_ELEMENTS (p->luma_weight_l0); i++)
774 p->luma_weight_l0[i] = default_luma_weight;
775 if (GST_H264_IS_B_SLICE (slice)) {
776 for (i = 0; i < G_N_ELEMENTS (p->luma_weight_l1); i++)
777 p->luma_weight_l1[i] = default_luma_weight;
778 }
779
780 if (chroma_array_type != 0) {
781 READ_UE_MAX (nr, p->chroma_log2_weight_denom, 7);
782 /* set default values */
783 default_chroma_weight = 1 << p->chroma_log2_weight_denom;
784 for (i = 0; i < G_N_ELEMENTS (p->chroma_weight_l0); i++) {
785 p->chroma_weight_l0[i][0] = default_chroma_weight;
786 p->chroma_weight_l0[i][1] = default_chroma_weight;
787 }
788 if (GST_H264_IS_B_SLICE (slice)) {
789 for (i = 0; i < G_N_ELEMENTS (p->chroma_weight_l1); i++) {
790 p->chroma_weight_l1[i][0] = default_chroma_weight;
791 p->chroma_weight_l1[i][1] = default_chroma_weight;
792 }
793 }
794 }
795
796 for (i = 0; i <= slice->num_ref_idx_l0_active_minus1; i++) {
797 guint8 luma_weight_l0_flag;
798
799 READ_UINT8 (nr, luma_weight_l0_flag, 1);
800 if (luma_weight_l0_flag) {
801 READ_SE_ALLOWED (nr, p->luma_weight_l0[i], -128, 127);
802 READ_SE_ALLOWED (nr, p->luma_offset_l0[i], -128, 127);
803 }
804 if (chroma_array_type != 0) {
805 guint8 chroma_weight_l0_flag;
806 gint j;
807
808 READ_UINT8 (nr, chroma_weight_l0_flag, 1);
809 if (chroma_weight_l0_flag) {
810 for (j = 0; j < 2; j++) {
811 READ_SE_ALLOWED (nr, p->chroma_weight_l0[i][j], -128, 127);
812 READ_SE_ALLOWED (nr, p->chroma_offset_l0[i][j], -128, 127);
813 }
814 }
815 }
816 }
817
818 if (GST_H264_IS_B_SLICE (slice)) {
819 for (i = 0; i <= slice->num_ref_idx_l1_active_minus1; i++) {
820 guint8 luma_weight_l1_flag;
821
822 READ_UINT8 (nr, luma_weight_l1_flag, 1);
823 if (luma_weight_l1_flag) {
824 READ_SE_ALLOWED (nr, p->luma_weight_l1[i], -128, 127);
825 READ_SE_ALLOWED (nr, p->luma_offset_l1[i], -128, 127);
826 }
827 if (chroma_array_type != 0) {
828 guint8 chroma_weight_l1_flag;
829 gint j;
830
831 READ_UINT8 (nr, chroma_weight_l1_flag, 1);
832 if (chroma_weight_l1_flag) {
833 for (j = 0; j < 2; j++) {
834 READ_SE_ALLOWED (nr, p->chroma_weight_l1[i][j], -128, 127);
835 READ_SE_ALLOWED (nr, p->chroma_offset_l1[i][j], -128, 127);
836 }
837 }
838 }
839 }
840 }
841
842 return TRUE;
843
844 error:
845 GST_WARNING ("error parsing \"Prediction weight table\"");
846 return FALSE;
847 }
848
849 static GstH264ParserResult
gst_h264_parser_parse_buffering_period(GstH264NalParser * nalparser,GstH264BufferingPeriod * per,NalReader * nr)850 gst_h264_parser_parse_buffering_period (GstH264NalParser * nalparser,
851 GstH264BufferingPeriod * per, NalReader * nr)
852 {
853 GstH264SPS *sps;
854 guint8 sps_id;
855
856 GST_DEBUG ("parsing \"Buffering period\"");
857
858 READ_UE_MAX (nr, sps_id, GST_H264_MAX_SPS_COUNT - 1);
859 sps = gst_h264_parser_get_sps (nalparser, sps_id);
860 if (!sps) {
861 GST_WARNING ("couldn't find associated sequence parameter set with id: %d",
862 sps_id);
863 return GST_H264_PARSER_BROKEN_LINK;
864 }
865 per->sps = sps;
866
867 if (sps->vui_parameters_present_flag) {
868 GstH264VUIParams *vui = &sps->vui_parameters;
869
870 if (vui->nal_hrd_parameters_present_flag) {
871 GstH264HRDParams *hrd = &vui->nal_hrd_parameters;
872 const guint8 nbits = hrd->initial_cpb_removal_delay_length_minus1 + 1;
873 guint8 sched_sel_idx;
874
875 for (sched_sel_idx = 0; sched_sel_idx <= hrd->cpb_cnt_minus1;
876 sched_sel_idx++) {
877 READ_UINT32 (nr, per->nal_initial_cpb_removal_delay[sched_sel_idx],
878 nbits);
879 READ_UINT32 (nr,
880 per->nal_initial_cpb_removal_delay_offset[sched_sel_idx], nbits);
881 }
882 }
883
884 if (vui->vcl_hrd_parameters_present_flag) {
885 GstH264HRDParams *hrd = &vui->vcl_hrd_parameters;
886 const guint8 nbits = hrd->initial_cpb_removal_delay_length_minus1 + 1;
887 guint8 sched_sel_idx;
888
889 for (sched_sel_idx = 0; sched_sel_idx <= hrd->cpb_cnt_minus1;
890 sched_sel_idx++) {
891 READ_UINT32 (nr, per->vcl_initial_cpb_removal_delay[sched_sel_idx],
892 nbits);
893 READ_UINT32 (nr,
894 per->vcl_initial_cpb_removal_delay_offset[sched_sel_idx], nbits);
895 }
896 }
897 }
898
899 return GST_H264_PARSER_OK;
900
901 error:
902 GST_WARNING ("error parsing \"Buffering period\"");
903 return GST_H264_PARSER_ERROR;
904 }
905
906 static gboolean
gst_h264_parse_clock_timestamp(GstH264ClockTimestamp * tim,GstH264VUIParams * vui,NalReader * nr)907 gst_h264_parse_clock_timestamp (GstH264ClockTimestamp * tim,
908 GstH264VUIParams * vui, NalReader * nr)
909 {
910 guint8 full_timestamp_flag;
911 guint8 time_offset_length;
912
913 GST_DEBUG ("parsing \"Clock timestamp\"");
914
915 /* defalt values */
916 tim->time_offset = 0;
917
918 READ_UINT8 (nr, tim->ct_type, 2);
919 READ_UINT8 (nr, tim->nuit_field_based_flag, 1);
920 READ_UINT8 (nr, tim->counting_type, 5);
921 READ_UINT8 (nr, full_timestamp_flag, 1);
922 READ_UINT8 (nr, tim->discontinuity_flag, 1);
923 READ_UINT8 (nr, tim->cnt_dropped_flag, 1);
924 READ_UINT8 (nr, tim->n_frames, 8);
925
926 if (full_timestamp_flag) {
927 tim->seconds_flag = TRUE;
928 READ_UINT8 (nr, tim->seconds_value, 6);
929
930 tim->minutes_flag = TRUE;
931 READ_UINT8 (nr, tim->minutes_value, 6);
932
933 tim->hours_flag = TRUE;
934 READ_UINT8 (nr, tim->hours_value, 5);
935 } else {
936 READ_UINT8 (nr, tim->seconds_flag, 1);
937 if (tim->seconds_flag) {
938 READ_UINT8 (nr, tim->seconds_value, 6);
939 READ_UINT8 (nr, tim->minutes_flag, 1);
940 if (tim->minutes_flag) {
941 READ_UINT8 (nr, tim->minutes_value, 6);
942 READ_UINT8 (nr, tim->hours_flag, 1);
943 if (tim->hours_flag)
944 READ_UINT8 (nr, tim->hours_value, 5);
945 }
946 }
947 }
948
949 time_offset_length = 24;
950 if (vui->nal_hrd_parameters_present_flag)
951 time_offset_length = vui->nal_hrd_parameters.time_offset_length;
952 else if (vui->vcl_hrd_parameters_present_flag)
953 time_offset_length = vui->vcl_hrd_parameters.time_offset_length;
954
955 if (time_offset_length > 0)
956 READ_UINT32 (nr, tim->time_offset, time_offset_length);
957
958 return TRUE;
959
960 error:
961 GST_WARNING ("error parsing \"Clock timestamp\"");
962 return FALSE;
963 }
964
965 static GstH264ParserResult
gst_h264_parser_parse_pic_timing(GstH264NalParser * nalparser,GstH264PicTiming * tim,NalReader * nr)966 gst_h264_parser_parse_pic_timing (GstH264NalParser * nalparser,
967 GstH264PicTiming * tim, NalReader * nr)
968 {
969 GST_DEBUG ("parsing \"Picture timing\"");
970 if (!nalparser->last_sps || !nalparser->last_sps->valid) {
971 GST_WARNING ("didn't get the associated sequence paramater set for the "
972 "current access unit");
973 goto error;
974 }
975
976 if (nalparser->last_sps->vui_parameters_present_flag) {
977 GstH264VUIParams *vui = &nalparser->last_sps->vui_parameters;
978
979 if (vui->nal_hrd_parameters_present_flag) {
980 READ_UINT32 (nr, tim->cpb_removal_delay,
981 vui->nal_hrd_parameters.cpb_removal_delay_length_minus1 + 1);
982 READ_UINT32 (nr, tim->dpb_output_delay,
983 vui->nal_hrd_parameters.dpb_output_delay_length_minus1 + 1);
984 } else if (vui->vcl_hrd_parameters_present_flag) {
985 READ_UINT32 (nr, tim->cpb_removal_delay,
986 vui->vcl_hrd_parameters.cpb_removal_delay_length_minus1 + 1);
987 READ_UINT32 (nr, tim->dpb_output_delay,
988 vui->vcl_hrd_parameters.dpb_output_delay_length_minus1 + 1);
989 }
990
991 if (vui->pic_struct_present_flag) {
992 const guint8 num_clock_ts_table[9] = {
993 1, 1, 1, 2, 2, 3, 3, 2, 3
994 };
995 guint8 num_clock_num_ts;
996 guint i;
997
998 tim->pic_struct_present_flag = TRUE;
999 READ_UINT8 (nr, tim->pic_struct, 4);
1000 CHECK_ALLOWED ((gint8) tim->pic_struct, 0, 8);
1001
1002 num_clock_num_ts = num_clock_ts_table[tim->pic_struct];
1003 for (i = 0; i < num_clock_num_ts; i++) {
1004 READ_UINT8 (nr, tim->clock_timestamp_flag[i], 1);
1005 if (tim->clock_timestamp_flag[i]) {
1006 if (!gst_h264_parse_clock_timestamp (&tim->clock_timestamp[i], vui,
1007 nr))
1008 goto error;
1009 }
1010 }
1011 }
1012 }
1013
1014 return GST_H264_PARSER_OK;
1015
1016 error:
1017 GST_WARNING ("error parsing \"Picture timing\"");
1018 return GST_H264_PARSER_ERROR;
1019 }
1020
1021 static GstH264ParserResult
gst_h264_parser_parse_registered_user_data(GstH264NalParser * nalparser,GstH264RegisteredUserData * rud,NalReader * nr,guint payload_size)1022 gst_h264_parser_parse_registered_user_data (GstH264NalParser * nalparser,
1023 GstH264RegisteredUserData * rud, NalReader * nr, guint payload_size)
1024 {
1025 guint8 *data = NULL;
1026 guint i;
1027
1028 rud->data = NULL;
1029 rud->size = 0;
1030
1031 if (payload_size < 2)
1032 return GST_H264_PARSER_ERROR;
1033
1034 READ_UINT8 (nr, rud->country_code, 8);
1035 --payload_size;
1036
1037 if (rud->country_code == 0xFF) {
1038 READ_UINT8 (nr, rud->country_code_extension, 8);
1039 --payload_size;
1040 } else {
1041 rud->country_code_extension = 0;
1042 }
1043
1044 if (payload_size < 8)
1045 return GST_H264_PARSER_ERROR;
1046
1047 data = g_malloc (payload_size);
1048 for (i = 0; i < payload_size / 8; ++i) {
1049 READ_UINT8 (nr, data[i], 8);
1050 }
1051
1052 GST_MEMDUMP ("SEI user data", data, payload_size / 8);
1053
1054 rud->data = data;
1055 rud->size = payload_size;
1056 return GST_H264_PARSER_OK;
1057
1058 error:
1059 {
1060 GST_WARNING ("error parsing \"Registered User Data\"");
1061 g_free (data);
1062 return GST_H264_PARSER_ERROR;
1063 }
1064 }
1065
1066 static GstH264ParserResult
gst_h264_parser_parse_recovery_point(GstH264NalParser * nalparser,GstH264RecoveryPoint * rp,NalReader * nr)1067 gst_h264_parser_parse_recovery_point (GstH264NalParser * nalparser,
1068 GstH264RecoveryPoint * rp, NalReader * nr)
1069 {
1070 GstH264SPS *const sps = nalparser->last_sps;
1071
1072 GST_DEBUG ("parsing \"Recovery point\"");
1073 if (!sps || !sps->valid) {
1074 GST_WARNING ("didn't get the associated sequence paramater set for the "
1075 "current access unit");
1076 goto error;
1077 }
1078
1079 READ_UE_MAX (nr, rp->recovery_frame_cnt, sps->max_frame_num - 1);
1080 READ_UINT8 (nr, rp->exact_match_flag, 1);
1081 READ_UINT8 (nr, rp->broken_link_flag, 1);
1082 READ_UINT8 (nr, rp->changing_slice_group_idc, 2);
1083
1084 return GST_H264_PARSER_OK;
1085
1086 error:
1087 GST_WARNING ("error parsing \"Recovery point\"");
1088 return GST_H264_PARSER_ERROR;
1089 }
1090
1091 /* Parse SEI stereo_video_info() message */
1092 static GstH264ParserResult
gst_h264_parser_parse_stereo_video_info(GstH264NalParser * nalparser,GstH264StereoVideoInfo * info,NalReader * nr)1093 gst_h264_parser_parse_stereo_video_info (GstH264NalParser * nalparser,
1094 GstH264StereoVideoInfo * info, NalReader * nr)
1095 {
1096 GST_DEBUG ("parsing \"Stereo Video info\"");
1097
1098 READ_UINT8 (nr, info->field_views_flag, 1);
1099 if (info->field_views_flag) {
1100 READ_UINT8 (nr, info->top_field_is_left_view_flag, 1);
1101 } else {
1102 READ_UINT8 (nr, info->current_frame_is_left_view_flag, 1);
1103 READ_UINT8 (nr, info->next_frame_is_second_view_flag, 1);
1104 }
1105 READ_UINT8 (nr, info->left_view_self_contained_flag, 1);
1106 READ_UINT8 (nr, info->right_view_self_contained_flag, 1);
1107
1108 return GST_H264_PARSER_OK;
1109
1110 error:
1111 GST_WARNING ("error parsing \"Stereo Video info\"");
1112 return GST_H264_PARSER_ERROR;
1113 }
1114
1115 /* Parse SEI frame_packing_arrangement() message */
1116 static GstH264ParserResult
gst_h264_parser_parse_frame_packing(GstH264NalParser * nalparser,GstH264FramePacking * frame_packing,NalReader * nr,guint payload_size)1117 gst_h264_parser_parse_frame_packing (GstH264NalParser * nalparser,
1118 GstH264FramePacking * frame_packing, NalReader * nr, guint payload_size)
1119 {
1120 guint8 frame_packing_extension_flag;
1121 guint start_pos;
1122
1123 GST_DEBUG ("parsing \"Frame Packing Arrangement\"");
1124
1125 start_pos = nal_reader_get_pos (nr);
1126 READ_UE (nr, frame_packing->frame_packing_id);
1127 READ_UINT8 (nr, frame_packing->frame_packing_cancel_flag, 1);
1128
1129 if (!frame_packing->frame_packing_cancel_flag) {
1130 READ_UINT8 (nr, frame_packing->frame_packing_type, 7);
1131 READ_UINT8 (nr, frame_packing->quincunx_sampling_flag, 1);
1132 READ_UINT8 (nr, frame_packing->content_interpretation_type, 6);
1133 READ_UINT8 (nr, frame_packing->spatial_flipping_flag, 1);
1134 READ_UINT8 (nr, frame_packing->frame0_flipped_flag, 1);
1135 READ_UINT8 (nr, frame_packing->field_views_flag, 1);
1136 READ_UINT8 (nr, frame_packing->current_frame_is_frame0_flag, 1);
1137 READ_UINT8 (nr, frame_packing->frame0_self_contained_flag, 1);
1138 READ_UINT8 (nr, frame_packing->frame1_self_contained_flag, 1);
1139
1140 if (!frame_packing->quincunx_sampling_flag &&
1141 frame_packing->frame_packing_type !=
1142 GST_H264_FRAME_PACKING_TEMPORAL_INTERLEAVING) {
1143 READ_UINT8 (nr, frame_packing->frame0_grid_position_x, 4);
1144 READ_UINT8 (nr, frame_packing->frame0_grid_position_y, 4);
1145 READ_UINT8 (nr, frame_packing->frame1_grid_position_x, 4);
1146 READ_UINT8 (nr, frame_packing->frame1_grid_position_y, 4);
1147 }
1148
1149 /* Skip frame_packing_arrangement_reserved_byte */
1150 if (!nal_reader_skip (nr, 8))
1151 goto error;
1152
1153 READ_UE_MAX (nr, frame_packing->frame_packing_repetition_period, 16384);
1154 }
1155
1156 READ_UINT8 (nr, frame_packing_extension_flag, 1);
1157
1158 /* All data that follows within a frame packing arrangement SEI message
1159 after the value 1 for frame_packing_arrangement_extension_flag shall
1160 be ignored (D.2.25) */
1161 if (frame_packing_extension_flag) {
1162 nal_reader_skip_long (nr,
1163 payload_size - (nal_reader_get_pos (nr) - start_pos));
1164 }
1165
1166 return GST_H264_PARSER_OK;
1167
1168 error:
1169 GST_WARNING ("error parsing \"Frame Packing Arrangement\"");
1170 return GST_H264_PARSER_ERROR;
1171 }
1172
1173 static GstH264ParserResult
gst_h264_parser_parse_sei_message(GstH264NalParser * nalparser,NalReader * nr,GstH264SEIMessage * sei)1174 gst_h264_parser_parse_sei_message (GstH264NalParser * nalparser,
1175 NalReader * nr, GstH264SEIMessage * sei)
1176 {
1177 guint32 payloadSize;
1178 guint8 payload_type_byte, payload_size_byte;
1179 guint remaining, payload_size;
1180 GstH264ParserResult res;
1181
1182 GST_DEBUG ("parsing \"Sei message\"");
1183
1184 memset (sei, 0, sizeof (*sei));
1185
1186 do {
1187 READ_UINT8 (nr, payload_type_byte, 8);
1188 sei->payloadType += payload_type_byte;
1189 } while (payload_type_byte == 0xff);
1190
1191 payloadSize = 0;
1192 do {
1193 READ_UINT8 (nr, payload_size_byte, 8);
1194 payloadSize += payload_size_byte;
1195 }
1196 while (payload_size_byte == 0xff);
1197
1198 remaining = nal_reader_get_remaining (nr);
1199 payload_size = payloadSize * 8 < remaining ? payloadSize * 8 : remaining;
1200
1201 GST_DEBUG ("SEI message received: payloadType %u, payloadSize = %u bits",
1202 sei->payloadType, payload_size);
1203
1204 switch (sei->payloadType) {
1205 case GST_H264_SEI_BUF_PERIOD:
1206 /* size not set; might depend on emulation_prevention_three_byte */
1207 res = gst_h264_parser_parse_buffering_period (nalparser,
1208 &sei->payload.buffering_period, nr);
1209 break;
1210 case GST_H264_SEI_PIC_TIMING:
1211 /* size not set; might depend on emulation_prevention_three_byte */
1212 res = gst_h264_parser_parse_pic_timing (nalparser,
1213 &sei->payload.pic_timing, nr);
1214 break;
1215 case GST_H264_SEI_REGISTERED_USER_DATA:
1216 res = gst_h264_parser_parse_registered_user_data (nalparser,
1217 &sei->payload.registered_user_data, nr, payload_size);
1218 break;
1219 case GST_H264_SEI_RECOVERY_POINT:
1220 res = gst_h264_parser_parse_recovery_point (nalparser,
1221 &sei->payload.recovery_point, nr);
1222 break;
1223 case GST_H264_SEI_STEREO_VIDEO_INFO:
1224 res = gst_h264_parser_parse_stereo_video_info (nalparser,
1225 &sei->payload.stereo_video_info, nr);
1226 break;
1227 case GST_H264_SEI_FRAME_PACKING:
1228 res = gst_h264_parser_parse_frame_packing (nalparser,
1229 &sei->payload.frame_packing, nr, payload_size);
1230 break;
1231 default:
1232 /* Just consume payloadSize bytes, which does not account for
1233 emulation prevention bytes */
1234 if (!nal_reader_skip_long (nr, payload_size))
1235 goto error;
1236 res = GST_H264_PARSER_OK;
1237 break;
1238 }
1239
1240 /* When SEI message doesn't end at byte boundary,
1241 * check remaining bits fit the specification.
1242 */
1243 if (!nal_reader_is_byte_aligned (nr)) {
1244 guint8 bit_equal_to_one;
1245 READ_UINT8 (nr, bit_equal_to_one, 1);
1246 if (!bit_equal_to_one)
1247 GST_WARNING ("Bit non equal to one.");
1248
1249 while (!nal_reader_is_byte_aligned (nr)) {
1250 guint8 bit_equal_to_zero;
1251 READ_UINT8 (nr, bit_equal_to_zero, 1);
1252 if (bit_equal_to_zero)
1253 GST_WARNING ("Bit non equal to zero.");
1254 }
1255 }
1256
1257 return res;
1258
1259 error:
1260 GST_WARNING ("error parsing \"Sei message\"");
1261 return GST_H264_PARSER_ERROR;
1262 }
1263
1264 /******** API *************/
1265
1266 /**
1267 * gst_h264_nal_parser_new:
1268 *
1269 * Creates a new #GstH264NalParser. It should be freed with
1270 * gst_h264_nal_parser_free after use.
1271 *
1272 * Returns: a new #GstH264NalParser
1273 */
1274 GstH264NalParser *
gst_h264_nal_parser_new(void)1275 gst_h264_nal_parser_new (void)
1276 {
1277 GstH264NalParser *nalparser;
1278
1279 nalparser = g_slice_new0 (GstH264NalParser);
1280 INITIALIZE_DEBUG_CATEGORY;
1281
1282 return nalparser;
1283 }
1284
1285 /**
1286 * gst_h264_nal_parser_free:
1287 * @nalparser: the #GstH264NalParser to free
1288 *
1289 * Frees @nalparser and sets it to %NULL
1290 */
1291 void
gst_h264_nal_parser_free(GstH264NalParser * nalparser)1292 gst_h264_nal_parser_free (GstH264NalParser * nalparser)
1293 {
1294 guint i;
1295
1296 for (i = 0; i < GST_H264_MAX_SPS_COUNT; i++)
1297 gst_h264_sps_clear (&nalparser->sps[i]);
1298 for (i = 0; i < GST_H264_MAX_PPS_COUNT; i++)
1299 gst_h264_pps_clear (&nalparser->pps[i]);
1300 g_slice_free (GstH264NalParser, nalparser);
1301
1302 nalparser = NULL;
1303 }
1304
1305 /**
1306 * gst_h264_parser_identify_nalu_unchecked:
1307 * @nalparser: a #GstH264NalParser
1308 * @data: The data to parse
1309 * @offset: the offset from which to parse @data
1310 * @size: the size of @data
1311 * @nalu: The #GstH264NalUnit where to store parsed nal headers
1312 *
1313 * Parses @data and fills @nalu from the next nalu data from @data.
1314 *
1315 * This differs from @gst_h264_parser_identify_nalu in that it doesn't
1316 * check whether the packet is complete or not.
1317 *
1318 * Note: Only use this function if you already know the provided @data
1319 * is a complete NALU, else use @gst_h264_parser_identify_nalu.
1320 *
1321 * Returns: a #GstH264ParserResult
1322 */
1323 GstH264ParserResult
gst_h264_parser_identify_nalu_unchecked(GstH264NalParser * nalparser,const guint8 * data,guint offset,gsize size,GstH264NalUnit * nalu)1324 gst_h264_parser_identify_nalu_unchecked (GstH264NalParser * nalparser,
1325 const guint8 * data, guint offset, gsize size, GstH264NalUnit * nalu)
1326 {
1327 gint off1;
1328
1329 memset (nalu, 0, sizeof (*nalu));
1330
1331 if (size < offset + 4) {
1332 GST_DEBUG ("Can't parse, buffer has too small size %" G_GSIZE_FORMAT
1333 ", offset %u", size, offset);
1334 return GST_H264_PARSER_ERROR;
1335 }
1336
1337 off1 = scan_for_start_codes (data + offset, size - offset);
1338
1339 if (off1 < 0) {
1340 GST_DEBUG ("No start code prefix in this buffer");
1341 return GST_H264_PARSER_NO_NAL;
1342 }
1343
1344 if (offset + off1 == size - 1) {
1345 GST_DEBUG ("Missing data to identify nal unit");
1346
1347 return GST_H264_PARSER_ERROR;
1348 }
1349
1350 nalu->sc_offset = offset + off1;
1351
1352
1353 nalu->offset = offset + off1 + 3;
1354 nalu->data = (guint8 *) data;
1355 nalu->size = size - nalu->offset;
1356
1357 if (!gst_h264_parse_nalu_header (nalu)) {
1358 GST_WARNING ("error parsing \"NAL unit header\"");
1359 nalu->size = 0;
1360 return GST_H264_PARSER_BROKEN_DATA;
1361 }
1362
1363 nalu->valid = TRUE;
1364
1365 /* sc might have 2 or 3 0-bytes */
1366 if (nalu->sc_offset > 0 && data[nalu->sc_offset - 1] == 00
1367 && (nalu->type == GST_H264_NAL_SPS || nalu->type == GST_H264_NAL_PPS
1368 || nalu->type == GST_H264_NAL_AU_DELIMITER))
1369 nalu->sc_offset--;
1370
1371 if (nalu->type == GST_H264_NAL_SEQ_END ||
1372 nalu->type == GST_H264_NAL_STREAM_END) {
1373 GST_DEBUG ("end-of-seq or end-of-stream nal found");
1374 nalu->size = 1;
1375 return GST_H264_PARSER_OK;
1376 }
1377
1378 return GST_H264_PARSER_OK;
1379 }
1380
1381 /**
1382 * gst_h264_parser_identify_nalu:
1383 * @nalparser: a #GstH264NalParser
1384 * @data: The data to parse, containing an Annex B coded NAL unit
1385 * @offset: the offset in @data from which to parse the NAL unit
1386 * @size: the size of @data
1387 * @nalu: The #GstH264NalUnit to store the identified NAL unit in
1388 *
1389 * Parses the headers of an Annex B coded NAL unit from @data and puts the
1390 * result into @nalu.
1391 *
1392 * Returns: a #GstH264ParserResult
1393 */
1394 GstH264ParserResult
gst_h264_parser_identify_nalu(GstH264NalParser * nalparser,const guint8 * data,guint offset,gsize size,GstH264NalUnit * nalu)1395 gst_h264_parser_identify_nalu (GstH264NalParser * nalparser,
1396 const guint8 * data, guint offset, gsize size, GstH264NalUnit * nalu)
1397 {
1398 GstH264ParserResult res;
1399 gint off2;
1400
1401 res =
1402 gst_h264_parser_identify_nalu_unchecked (nalparser, data, offset, size,
1403 nalu);
1404
1405 if (res != GST_H264_PARSER_OK)
1406 goto beach;
1407
1408 /* The two NALs are exactly 1 byte size and are placed at the end of an AU,
1409 * there is no need to wait for the following */
1410 if (nalu->type == GST_H264_NAL_SEQ_END ||
1411 nalu->type == GST_H264_NAL_STREAM_END)
1412 goto beach;
1413
1414 off2 = scan_for_start_codes (data + nalu->offset, size - nalu->offset);
1415 if (off2 < 0) {
1416 GST_DEBUG ("Nal start %d, No end found", nalu->offset);
1417
1418 return GST_H264_PARSER_NO_NAL_END;
1419 }
1420
1421 /* Mini performance improvement:
1422 * We could have a way to store how many 0s were skipped to avoid
1423 * parsing them again on the next NAL */
1424 while (off2 > 0 && data[nalu->offset + off2 - 1] == 00)
1425 off2--;
1426
1427 nalu->size = off2;
1428 if (nalu->size < 2)
1429 return GST_H264_PARSER_BROKEN_DATA;
1430
1431 GST_DEBUG ("Complete nal found. Off: %d, Size: %d", nalu->offset, nalu->size);
1432
1433 beach:
1434 return res;
1435 }
1436
1437
1438 /**
1439 * gst_h264_parser_identify_nalu_avc:
1440 * @nalparser: a #GstH264NalParser
1441 * @data: The data to parse, containing an AVC coded NAL unit
1442 * @offset: the offset in @data from which to parse the NAL unit
1443 * @size: the size of @data
1444 * @nal_length_size: the size in bytes of the AVC nal length prefix.
1445 * @nalu: The #GstH264NalUnit to store the identified NAL unit in
1446 *
1447 * Parses the headers of an AVC coded NAL unit from @data and puts the result
1448 * into @nalu.
1449 *
1450 * Returns: a #GstH264ParserResult
1451 */
1452 GstH264ParserResult
gst_h264_parser_identify_nalu_avc(GstH264NalParser * nalparser,const guint8 * data,guint offset,gsize size,guint8 nal_length_size,GstH264NalUnit * nalu)1453 gst_h264_parser_identify_nalu_avc (GstH264NalParser * nalparser,
1454 const guint8 * data, guint offset, gsize size, guint8 nal_length_size,
1455 GstH264NalUnit * nalu)
1456 {
1457 GstBitReader br;
1458
1459 memset (nalu, 0, sizeof (*nalu));
1460
1461 if (size < offset + nal_length_size) {
1462 GST_DEBUG ("Can't parse, buffer has too small size %" G_GSIZE_FORMAT
1463 ", offset %u", size, offset);
1464 return GST_H264_PARSER_ERROR;
1465 }
1466
1467 size = size - offset;
1468 gst_bit_reader_init (&br, data + offset, size);
1469
1470 nalu->size = gst_bit_reader_get_bits_uint32_unchecked (&br,
1471 nal_length_size * 8);
1472 nalu->sc_offset = offset;
1473 nalu->offset = offset + nal_length_size;
1474
1475 if (size < nalu->size + nal_length_size) {
1476 nalu->size = 0;
1477
1478 return GST_H264_PARSER_NO_NAL_END;
1479 }
1480
1481 nalu->data = (guint8 *) data;
1482
1483 if (!gst_h264_parse_nalu_header (nalu)) {
1484 GST_WARNING ("error parsing \"NAL unit header\"");
1485 nalu->size = 0;
1486 return GST_H264_PARSER_BROKEN_DATA;
1487 }
1488
1489 nalu->valid = TRUE;
1490
1491 return GST_H264_PARSER_OK;
1492 }
1493
1494 /**
1495 * gst_h264_parser_parse_nal:
1496 * @nalparser: a #GstH264NalParser
1497 * @nalu: The #GstH264NalUnit to parse
1498 *
1499 * This function should be called in the case one doesn't need to
1500 * parse a specific structure. It is necessary to do so to make
1501 * sure @nalparser is up to date.
1502 *
1503 * Returns: a #GstH264ParserResult
1504 */
1505 GstH264ParserResult
gst_h264_parser_parse_nal(GstH264NalParser * nalparser,GstH264NalUnit * nalu)1506 gst_h264_parser_parse_nal (GstH264NalParser * nalparser, GstH264NalUnit * nalu)
1507 {
1508 GstH264SPS sps;
1509 GstH264PPS pps;
1510
1511 switch (nalu->type) {
1512 case GST_H264_NAL_SPS:
1513 return gst_h264_parser_parse_sps (nalparser, nalu, &sps, FALSE);
1514 break;
1515 case GST_H264_NAL_PPS:
1516 return gst_h264_parser_parse_pps (nalparser, nalu, &pps);
1517 }
1518
1519 return GST_H264_PARSER_OK;
1520 }
1521
1522 /**
1523 * gst_h264_parser_parse_sps:
1524 * @nalparser: a #GstH264NalParser
1525 * @nalu: The #GST_H264_NAL_SPS #GstH264NalUnit to parse
1526 * @sps: The #GstH264SPS to fill.
1527 * @parse_vui_params: Whether to parse the vui_params or not
1528 *
1529 * Parses @nalu containing a Sequence Parameter Set, and fills @sps.
1530 *
1531 * Returns: a #GstH264ParserResult
1532 */
1533 GstH264ParserResult
gst_h264_parser_parse_sps(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GstH264SPS * sps,gboolean parse_vui_params)1534 gst_h264_parser_parse_sps (GstH264NalParser * nalparser, GstH264NalUnit * nalu,
1535 GstH264SPS * sps, gboolean parse_vui_params)
1536 {
1537 GstH264ParserResult res = gst_h264_parse_sps (nalu, sps, parse_vui_params);
1538
1539 if (res == GST_H264_PARSER_OK) {
1540 GST_DEBUG ("adding sequence parameter set with id: %d to array", sps->id);
1541
1542 if (!gst_h264_sps_copy (&nalparser->sps[sps->id], sps))
1543 return GST_H264_PARSER_ERROR;
1544 nalparser->last_sps = &nalparser->sps[sps->id];
1545 }
1546 return res;
1547 }
1548
1549 /* Parse seq_parameter_set_data() */
1550 static gboolean
gst_h264_parse_sps_data(NalReader * nr,GstH264SPS * sps,gboolean parse_vui_params)1551 gst_h264_parse_sps_data (NalReader * nr, GstH264SPS * sps,
1552 gboolean parse_vui_params)
1553 {
1554 gint width, height;
1555 guint subwc[] = { 1, 2, 2, 1 };
1556 guint subhc[] = { 1, 2, 1, 1 };
1557
1558 memset (sps, 0, sizeof (*sps));
1559
1560 /* set default values for fields that might not be present in the bitstream
1561 and have valid defaults */
1562 sps->extension_type = GST_H264_NAL_EXTENSION_NONE;
1563 sps->chroma_format_idc = 1;
1564 memset (sps->scaling_lists_4x4, 16, 96);
1565 memset (sps->scaling_lists_8x8, 16, 384);
1566
1567 READ_UINT8 (nr, sps->profile_idc, 8);
1568 READ_UINT8 (nr, sps->constraint_set0_flag, 1);
1569 READ_UINT8 (nr, sps->constraint_set1_flag, 1);
1570 READ_UINT8 (nr, sps->constraint_set2_flag, 1);
1571 READ_UINT8 (nr, sps->constraint_set3_flag, 1);
1572 READ_UINT8 (nr, sps->constraint_set4_flag, 1);
1573 READ_UINT8 (nr, sps->constraint_set5_flag, 1);
1574
1575 /* skip reserved_zero_2bits */
1576 if (!nal_reader_skip (nr, 2))
1577 goto error;
1578
1579 READ_UINT8 (nr, sps->level_idc, 8);
1580
1581 READ_UE_MAX (nr, sps->id, GST_H264_MAX_SPS_COUNT - 1);
1582
1583 if (sps->profile_idc == 100 || sps->profile_idc == 110 ||
1584 sps->profile_idc == 122 || sps->profile_idc == 244 ||
1585 sps->profile_idc == 44 || sps->profile_idc == 83 ||
1586 sps->profile_idc == 86 || sps->profile_idc == 118 ||
1587 sps->profile_idc == 128) {
1588 READ_UE_MAX (nr, sps->chroma_format_idc, 3);
1589 if (sps->chroma_format_idc == 3)
1590 READ_UINT8 (nr, sps->separate_colour_plane_flag, 1);
1591
1592 READ_UE_MAX (nr, sps->bit_depth_luma_minus8, 6);
1593 READ_UE_MAX (nr, sps->bit_depth_chroma_minus8, 6);
1594 READ_UINT8 (nr, sps->qpprime_y_zero_transform_bypass_flag, 1);
1595
1596 READ_UINT8 (nr, sps->scaling_matrix_present_flag, 1);
1597 if (sps->scaling_matrix_present_flag) {
1598 guint8 n_lists;
1599
1600 n_lists = (sps->chroma_format_idc != 3) ? 8 : 12;
1601 if (!gst_h264_parser_parse_scaling_list (nr,
1602 sps->scaling_lists_4x4, sps->scaling_lists_8x8,
1603 default_4x4_inter, default_4x4_intra,
1604 default_8x8_inter, default_8x8_intra, n_lists))
1605 goto error;
1606 }
1607 }
1608
1609 READ_UE_MAX (nr, sps->log2_max_frame_num_minus4, 12);
1610
1611 sps->max_frame_num = 1 << (sps->log2_max_frame_num_minus4 + 4);
1612
1613 READ_UE_MAX (nr, sps->pic_order_cnt_type, 2);
1614 if (sps->pic_order_cnt_type == 0) {
1615 READ_UE_MAX (nr, sps->log2_max_pic_order_cnt_lsb_minus4, 12);
1616 } else if (sps->pic_order_cnt_type == 1) {
1617 guint i;
1618
1619 READ_UINT8 (nr, sps->delta_pic_order_always_zero_flag, 1);
1620 READ_SE (nr, sps->offset_for_non_ref_pic);
1621 READ_SE (nr, sps->offset_for_top_to_bottom_field);
1622 READ_UE_MAX (nr, sps->num_ref_frames_in_pic_order_cnt_cycle, 255);
1623
1624 for (i = 0; i < sps->num_ref_frames_in_pic_order_cnt_cycle; i++)
1625 READ_SE (nr, sps->offset_for_ref_frame[i]);
1626 }
1627
1628 READ_UE (nr, sps->num_ref_frames);
1629 READ_UINT8 (nr, sps->gaps_in_frame_num_value_allowed_flag, 1);
1630 READ_UE (nr, sps->pic_width_in_mbs_minus1);
1631 READ_UE (nr, sps->pic_height_in_map_units_minus1);
1632 READ_UINT8 (nr, sps->frame_mbs_only_flag, 1);
1633
1634 if (!sps->frame_mbs_only_flag)
1635 READ_UINT8 (nr, sps->mb_adaptive_frame_field_flag, 1);
1636
1637 READ_UINT8 (nr, sps->direct_8x8_inference_flag, 1);
1638 READ_UINT8 (nr, sps->frame_cropping_flag, 1);
1639 if (sps->frame_cropping_flag) {
1640 READ_UE (nr, sps->frame_crop_left_offset);
1641 READ_UE (nr, sps->frame_crop_right_offset);
1642 READ_UE (nr, sps->frame_crop_top_offset);
1643 READ_UE (nr, sps->frame_crop_bottom_offset);
1644 }
1645
1646 READ_UINT8 (nr, sps->vui_parameters_present_flag, 1);
1647 if (sps->vui_parameters_present_flag && parse_vui_params) {
1648 if (!gst_h264_parse_vui_parameters (sps, nr))
1649 goto error;
1650 }
1651
1652 /* calculate ChromaArrayType */
1653 if (!sps->separate_colour_plane_flag)
1654 sps->chroma_array_type = sps->chroma_format_idc;
1655
1656 /* Calculate width and height */
1657 width = (sps->pic_width_in_mbs_minus1 + 1);
1658 width *= 16;
1659 height = (sps->pic_height_in_map_units_minus1 + 1);
1660 height *= 16 * (2 - sps->frame_mbs_only_flag);
1661 GST_LOG ("initial width=%d, height=%d", width, height);
1662 if (width < 0 || height < 0) {
1663 GST_WARNING ("invalid width/height in SPS");
1664 goto error;
1665 }
1666
1667 sps->width = width;
1668 sps->height = height;
1669
1670 if (sps->frame_cropping_flag) {
1671 const guint crop_unit_x = subwc[sps->chroma_format_idc];
1672 const guint crop_unit_y =
1673 subhc[sps->chroma_format_idc] * (2 - sps->frame_mbs_only_flag);
1674
1675 width -= (sps->frame_crop_left_offset + sps->frame_crop_right_offset)
1676 * crop_unit_x;
1677 height -= (sps->frame_crop_top_offset + sps->frame_crop_bottom_offset)
1678 * crop_unit_y;
1679
1680 sps->crop_rect_width = width;
1681 sps->crop_rect_height = height;
1682 sps->crop_rect_x = sps->frame_crop_left_offset * crop_unit_x;
1683 sps->crop_rect_y = sps->frame_crop_top_offset * crop_unit_y;
1684
1685 GST_LOG ("crop_rectangle x=%u y=%u width=%u, height=%u", sps->crop_rect_x,
1686 sps->crop_rect_y, width, height);
1687 }
1688
1689 sps->fps_num_removed = 0;
1690 sps->fps_den_removed = 1;
1691
1692 return TRUE;
1693
1694 error:
1695 return FALSE;
1696 }
1697
1698 /* Parse subset_seq_parameter_set() data for MVC */
1699 static gboolean
gst_h264_parse_sps_mvc_data(NalReader * nr,GstH264SPS * sps,gboolean parse_vui_params)1700 gst_h264_parse_sps_mvc_data (NalReader * nr, GstH264SPS * sps,
1701 gboolean parse_vui_params)
1702 {
1703 GstH264SPSExtMVC *const mvc = &sps->extension.mvc;
1704 guint8 bit_equal_to_one;
1705 guint i, j, k;
1706
1707 READ_UINT8 (nr, bit_equal_to_one, 1);
1708 if (!bit_equal_to_one)
1709 return FALSE;
1710
1711 sps->extension_type = GST_H264_NAL_EXTENSION_MVC;
1712
1713 READ_UE_MAX (nr, mvc->num_views_minus1, GST_H264_MAX_VIEW_COUNT - 1);
1714
1715 mvc->view = g_new0 (GstH264SPSExtMVCView, mvc->num_views_minus1 + 1);
1716 if (!mvc->view)
1717 goto error_allocation_failed;
1718
1719 for (i = 0; i <= mvc->num_views_minus1; i++)
1720 READ_UE_MAX (nr, mvc->view[i].view_id, GST_H264_MAX_VIEW_ID);
1721
1722 for (i = 1; i <= mvc->num_views_minus1; i++) {
1723 /* for RefPicList0 */
1724 READ_UE_MAX (nr, mvc->view[i].num_anchor_refs_l0, 15);
1725 for (j = 0; j < mvc->view[i].num_anchor_refs_l0; j++) {
1726 READ_UE_MAX (nr, mvc->view[i].anchor_ref_l0[j], GST_H264_MAX_VIEW_ID);
1727 }
1728
1729 /* for RefPicList1 */
1730 READ_UE_MAX (nr, mvc->view[i].num_anchor_refs_l1, 15);
1731 for (j = 0; j < mvc->view[i].num_anchor_refs_l1; j++) {
1732 READ_UE_MAX (nr, mvc->view[i].anchor_ref_l1[j], GST_H264_MAX_VIEW_ID);
1733 }
1734 }
1735
1736 for (i = 1; i <= mvc->num_views_minus1; i++) {
1737 /* for RefPicList0 */
1738 READ_UE_MAX (nr, mvc->view[i].num_non_anchor_refs_l0, 15);
1739 for (j = 0; j < mvc->view[i].num_non_anchor_refs_l0; j++) {
1740 READ_UE_MAX (nr, mvc->view[i].non_anchor_ref_l0[j], GST_H264_MAX_VIEW_ID);
1741 }
1742
1743 /* for RefPicList1 */
1744 READ_UE_MAX (nr, mvc->view[i].num_non_anchor_refs_l1, 15);
1745 for (j = 0; j < mvc->view[i].num_non_anchor_refs_l1; j++) {
1746 READ_UE_MAX (nr, mvc->view[i].non_anchor_ref_l1[j], GST_H264_MAX_VIEW_ID);
1747 }
1748 }
1749
1750 READ_UE_MAX (nr, mvc->num_level_values_signalled_minus1, 63);
1751
1752 mvc->level_value =
1753 g_new0 (GstH264SPSExtMVCLevelValue,
1754 mvc->num_level_values_signalled_minus1 + 1);
1755 if (!mvc->level_value)
1756 goto error_allocation_failed;
1757
1758 for (i = 0; i <= mvc->num_level_values_signalled_minus1; i++) {
1759 GstH264SPSExtMVCLevelValue *const level_value = &mvc->level_value[i];
1760
1761 READ_UINT8 (nr, level_value->level_idc, 8);
1762
1763 READ_UE_MAX (nr, level_value->num_applicable_ops_minus1, 1023);
1764 level_value->applicable_op =
1765 g_new0 (GstH264SPSExtMVCLevelValueOp,
1766 level_value->num_applicable_ops_minus1 + 1);
1767 if (!level_value->applicable_op)
1768 goto error_allocation_failed;
1769
1770 for (j = 0; j <= level_value->num_applicable_ops_minus1; j++) {
1771 GstH264SPSExtMVCLevelValueOp *const op = &level_value->applicable_op[j];
1772
1773 READ_UINT8 (nr, op->temporal_id, 3);
1774
1775 READ_UE_MAX (nr, op->num_target_views_minus1, 1023);
1776 op->target_view_id = g_new (guint16, op->num_target_views_minus1 + 1);
1777 if (!op->target_view_id)
1778 goto error_allocation_failed;
1779
1780 for (k = 0; k <= op->num_target_views_minus1; k++)
1781 READ_UE_MAX (nr, op->target_view_id[k], GST_H264_MAX_VIEW_ID);
1782 READ_UE_MAX (nr, op->num_views_minus1, 1023);
1783 }
1784 }
1785 return TRUE;
1786
1787 error_allocation_failed:
1788 GST_WARNING ("failed to allocate memory");
1789 gst_h264_sps_clear (sps);
1790 return FALSE;
1791
1792 error:
1793 gst_h264_sps_clear (sps);
1794 return FALSE;
1795 }
1796
1797 /**
1798 * gst_h264_parse_sps:
1799 * @nalu: The #GST_H264_NAL_SPS #GstH264NalUnit to parse
1800 * @sps: The #GstH264SPS to fill.
1801 * @parse_vui_params: Whether to parse the vui_params or not
1802 *
1803 * Parses @data, and fills the @sps structure.
1804 *
1805 * Returns: a #GstH264ParserResult
1806 */
1807 GstH264ParserResult
gst_h264_parse_sps(GstH264NalUnit * nalu,GstH264SPS * sps,gboolean parse_vui_params)1808 gst_h264_parse_sps (GstH264NalUnit * nalu, GstH264SPS * sps,
1809 gboolean parse_vui_params)
1810 {
1811 NalReader nr;
1812
1813 INITIALIZE_DEBUG_CATEGORY;
1814 GST_DEBUG ("parsing SPS");
1815
1816 nal_reader_init (&nr, nalu->data + nalu->offset + nalu->header_bytes,
1817 nalu->size - nalu->header_bytes);
1818
1819 if (!gst_h264_parse_sps_data (&nr, sps, parse_vui_params))
1820 goto error;
1821
1822 sps->valid = TRUE;
1823
1824 return GST_H264_PARSER_OK;
1825
1826 error:
1827 GST_WARNING ("error parsing \"Sequence parameter set\"");
1828 sps->valid = FALSE;
1829 return GST_H264_PARSER_ERROR;
1830 }
1831
1832 /**
1833 * gst_h264_parser_parse_subset_sps:
1834 * @nalparser: a #GstH264NalParser
1835 * @nalu: The #GST_H264_NAL_SUBSET_SPS #GstH264NalUnit to parse
1836 * @sps: The #GstH264SPS to fill.
1837 * @parse_vui_params: Whether to parse the vui_params or not
1838 *
1839 * Parses @data, and fills in the @sps structure.
1840 *
1841 * This function fully parses @data and allocates all the necessary
1842 * data structures needed for MVC extensions. The resulting @sps
1843 * structure shall be deallocated with gst_h264_sps_clear() when it is
1844 * no longer needed.
1845 *
1846 * Note: if the caller doesn't need any of the MVC-specific data, then
1847 * gst_h264_parser_parse_sps() is more efficient because those extra
1848 * syntax elements are not parsed and no extra memory is allocated.
1849 *
1850 * Returns: a #GstH264ParserResult
1851 *
1852 * Since: 1.6
1853 */
1854 GstH264ParserResult
gst_h264_parser_parse_subset_sps(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GstH264SPS * sps,gboolean parse_vui_params)1855 gst_h264_parser_parse_subset_sps (GstH264NalParser * nalparser,
1856 GstH264NalUnit * nalu, GstH264SPS * sps, gboolean parse_vui_params)
1857 {
1858 GstH264ParserResult res;
1859
1860 res = gst_h264_parse_subset_sps (nalu, sps, parse_vui_params);
1861 if (res == GST_H264_PARSER_OK) {
1862 GST_DEBUG ("adding sequence parameter set with id: %d to array", sps->id);
1863
1864 if (!gst_h264_sps_copy (&nalparser->sps[sps->id], sps)) {
1865 gst_h264_sps_clear (sps);
1866 return GST_H264_PARSER_ERROR;
1867 }
1868 nalparser->last_sps = &nalparser->sps[sps->id];
1869 }
1870 return res;
1871 }
1872
1873 /**
1874 * gst_h264_parse_subset_sps:
1875 * @nalu: The #GST_H264_NAL_SUBSET_SPS #GstH264NalUnit to parse
1876 * @sps: The #GstH264SPS to fill.
1877 * @parse_vui_params: Whether to parse the vui_params or not
1878 *
1879 * Parses @data, and fills in the @sps structure.
1880 *
1881 * This function fully parses @data and allocates all the necessary
1882 * data structures needed for MVC extensions. The resulting @sps
1883 * structure shall be deallocated with gst_h264_sps_clear() when it is
1884 * no longer needed.
1885 *
1886 * Note: if the caller doesn't need any of the MVC-specific data, then
1887 * gst_h264_parser_parse_sps() is more efficient because those extra
1888 * syntax elements are not parsed and no extra memory is allocated.
1889 *
1890 * Returns: a #GstH264ParserResult
1891 *
1892 * Since: 1.6
1893 */
1894 GstH264ParserResult
gst_h264_parse_subset_sps(GstH264NalUnit * nalu,GstH264SPS * sps,gboolean parse_vui_params)1895 gst_h264_parse_subset_sps (GstH264NalUnit * nalu, GstH264SPS * sps,
1896 gboolean parse_vui_params)
1897 {
1898 NalReader nr;
1899
1900 INITIALIZE_DEBUG_CATEGORY;
1901 GST_DEBUG ("parsing Subset SPS");
1902
1903 nal_reader_init (&nr, nalu->data + nalu->offset + nalu->header_bytes,
1904 nalu->size - nalu->header_bytes);
1905
1906 if (!gst_h264_parse_sps_data (&nr, sps, TRUE))
1907 goto error;
1908
1909 if (sps->profile_idc == GST_H264_PROFILE_MULTIVIEW_HIGH ||
1910 sps->profile_idc == GST_H264_PROFILE_STEREO_HIGH) {
1911 if (!gst_h264_parse_sps_mvc_data (&nr, sps, parse_vui_params))
1912 goto error;
1913 }
1914
1915 sps->valid = TRUE;
1916 return GST_H264_PARSER_OK;
1917
1918 error:
1919 GST_WARNING ("error parsing \"Subset sequence parameter set\"");
1920 gst_h264_sps_clear (sps);
1921 sps->valid = FALSE;
1922 return GST_H264_PARSER_ERROR;
1923 }
1924
1925 /**
1926 * gst_h264_parse_pps:
1927 * @nalparser: a #GstH264NalParser
1928 * @nalu: The #GST_H264_NAL_PPS #GstH264NalUnit to parse
1929 * @pps: The #GstH264PPS to fill.
1930 *
1931 * Parses @data, and fills the @pps structure.
1932 *
1933 * The resulting @pps data structure shall be deallocated with the
1934 * gst_h264_pps_clear() function when it is no longer needed, or prior
1935 * to parsing a new PPS NAL unit.
1936 *
1937 * Returns: a #GstH264ParserResult
1938 */
1939 GstH264ParserResult
gst_h264_parse_pps(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GstH264PPS * pps)1940 gst_h264_parse_pps (GstH264NalParser * nalparser, GstH264NalUnit * nalu,
1941 GstH264PPS * pps)
1942 {
1943 NalReader nr;
1944 GstH264SPS *sps;
1945 gint sps_id;
1946 guint8 pic_scaling_matrix_present_flag;
1947 gint qp_bd_offset;
1948
1949 INITIALIZE_DEBUG_CATEGORY;
1950 GST_DEBUG ("parsing PPS");
1951
1952 nal_reader_init (&nr, nalu->data + nalu->offset + nalu->header_bytes,
1953 nalu->size - nalu->header_bytes);
1954
1955 memset (pps, 0, sizeof (*pps));
1956
1957 READ_UE_MAX (&nr, pps->id, GST_H264_MAX_PPS_COUNT - 1);
1958 READ_UE_MAX (&nr, sps_id, GST_H264_MAX_SPS_COUNT - 1);
1959
1960 sps = gst_h264_parser_get_sps (nalparser, sps_id);
1961 if (!sps) {
1962 GST_WARNING ("couldn't find associated sequence parameter set with id: %d",
1963 sps_id);
1964 return GST_H264_PARSER_BROKEN_LINK;
1965 }
1966 pps->sequence = sps;
1967 qp_bd_offset = 6 * (sps->bit_depth_luma_minus8 +
1968 sps->separate_colour_plane_flag);
1969
1970 /* set default values for fields that might not be present in the bitstream
1971 and have valid defaults */
1972 memcpy (&pps->scaling_lists_4x4, &sps->scaling_lists_4x4, 96);
1973 memcpy (&pps->scaling_lists_8x8, &sps->scaling_lists_8x8, 384);
1974
1975 READ_UINT8 (&nr, pps->entropy_coding_mode_flag, 1);
1976 READ_UINT8 (&nr, pps->pic_order_present_flag, 1);
1977 READ_UE_MAX (&nr, pps->num_slice_groups_minus1, 7);
1978 if (pps->num_slice_groups_minus1 > 0) {
1979 READ_UE_MAX (&nr, pps->slice_group_map_type, 6);
1980
1981 if (pps->slice_group_map_type == 0) {
1982 gint i;
1983
1984 for (i = 0; i <= pps->num_slice_groups_minus1; i++)
1985 READ_UE (&nr, pps->run_length_minus1[i]);
1986 } else if (pps->slice_group_map_type == 2) {
1987 gint i;
1988
1989 for (i = 0; i < pps->num_slice_groups_minus1; i++) {
1990 READ_UE (&nr, pps->top_left[i]);
1991 READ_UE (&nr, pps->bottom_right[i]);
1992 }
1993 } else if (pps->slice_group_map_type >= 3 && pps->slice_group_map_type <= 5) {
1994 READ_UINT8 (&nr, pps->slice_group_change_direction_flag, 1);
1995 READ_UE (&nr, pps->slice_group_change_rate_minus1);
1996 } else if (pps->slice_group_map_type == 6) {
1997 gint bits;
1998 gint i;
1999
2000 READ_UE (&nr, pps->pic_size_in_map_units_minus1);
2001 bits = g_bit_storage (pps->num_slice_groups_minus1);
2002
2003 pps->slice_group_id =
2004 g_new (guint8, pps->pic_size_in_map_units_minus1 + 1);
2005 for (i = 0; i <= pps->pic_size_in_map_units_minus1; i++)
2006 READ_UINT8 (&nr, pps->slice_group_id[i], bits);
2007 }
2008 }
2009
2010 READ_UE_MAX (&nr, pps->num_ref_idx_l0_active_minus1, 31);
2011 READ_UE_MAX (&nr, pps->num_ref_idx_l1_active_minus1, 31);
2012 READ_UINT8 (&nr, pps->weighted_pred_flag, 1);
2013 READ_UINT8 (&nr, pps->weighted_bipred_idc, 2);
2014 READ_SE_ALLOWED (&nr, pps->pic_init_qp_minus26, -(26 + qp_bd_offset), 25);
2015 READ_SE_ALLOWED (&nr, pps->pic_init_qs_minus26, -26, 25);
2016 READ_SE_ALLOWED (&nr, pps->chroma_qp_index_offset, -12, 12);
2017 pps->second_chroma_qp_index_offset = pps->chroma_qp_index_offset;
2018 READ_UINT8 (&nr, pps->deblocking_filter_control_present_flag, 1);
2019 READ_UINT8 (&nr, pps->constrained_intra_pred_flag, 1);
2020 READ_UINT8 (&nr, pps->redundant_pic_cnt_present_flag, 1);
2021
2022 if (!nal_reader_has_more_data (&nr))
2023 goto done;
2024
2025 READ_UINT8 (&nr, pps->transform_8x8_mode_flag, 1);
2026
2027 READ_UINT8 (&nr, pic_scaling_matrix_present_flag, 1);
2028 if (pic_scaling_matrix_present_flag) {
2029 guint8 n_lists;
2030
2031 n_lists = 6 + ((sps->chroma_format_idc != 3) ? 2 : 6) *
2032 pps->transform_8x8_mode_flag;
2033
2034 if (sps->scaling_matrix_present_flag) {
2035 if (!gst_h264_parser_parse_scaling_list (&nr,
2036 pps->scaling_lists_4x4, pps->scaling_lists_8x8,
2037 sps->scaling_lists_4x4[3], sps->scaling_lists_4x4[0],
2038 sps->scaling_lists_8x8[3], sps->scaling_lists_8x8[0], n_lists))
2039 goto error;
2040 } else {
2041 if (!gst_h264_parser_parse_scaling_list (&nr,
2042 pps->scaling_lists_4x4, pps->scaling_lists_8x8,
2043 default_4x4_inter, default_4x4_intra,
2044 default_8x8_inter, default_8x8_intra, n_lists))
2045 goto error;
2046 }
2047 }
2048
2049 READ_SE_ALLOWED (&nr, pps->second_chroma_qp_index_offset, -12, 12);
2050
2051 done:
2052 pps->valid = TRUE;
2053 return GST_H264_PARSER_OK;
2054
2055 error:
2056 GST_WARNING ("error parsing \"Picture parameter set\"");
2057 pps->valid = FALSE;
2058 gst_h264_pps_clear (pps);
2059 return GST_H264_PARSER_ERROR;
2060 }
2061
2062 /**
2063 * gst_h264_parser_parse_pps:
2064 * @nalparser: a #GstH264NalParser
2065 * @nalu: The #GST_H264_NAL_PPS #GstH264NalUnit to parse
2066 * @pps: The #GstH264PPS to fill.
2067 *
2068 * Parses @nalu containing a Picture Parameter Set, and fills @pps.
2069 *
2070 * The resulting @pps data structure must be deallocated by the caller using
2071 * gst_h264_pps_clear().
2072 *
2073 * Returns: a #GstH264ParserResult
2074 */
2075 GstH264ParserResult
gst_h264_parser_parse_pps(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GstH264PPS * pps)2076 gst_h264_parser_parse_pps (GstH264NalParser * nalparser,
2077 GstH264NalUnit * nalu, GstH264PPS * pps)
2078 {
2079 GstH264ParserResult res = gst_h264_parse_pps (nalparser, nalu, pps);
2080
2081 if (res == GST_H264_PARSER_OK) {
2082 GST_DEBUG ("adding picture parameter set with id: %d to array", pps->id);
2083
2084 if (!gst_h264_pps_copy (&nalparser->pps[pps->id], pps))
2085 return GST_H264_PARSER_ERROR;
2086 nalparser->last_pps = &nalparser->pps[pps->id];
2087 }
2088
2089 return res;
2090 }
2091
2092 /**
2093 * gst_h264_pps_clear:
2094 * @pps: The #GstH264PPS to free
2095 *
2096 * Clears all @pps internal resources.
2097 *
2098 * Since: 1.4
2099 */
2100 void
gst_h264_pps_clear(GstH264PPS * pps)2101 gst_h264_pps_clear (GstH264PPS * pps)
2102 {
2103 g_return_if_fail (pps != NULL);
2104
2105 g_free (pps->slice_group_id);
2106 pps->slice_group_id = NULL;
2107 }
2108
2109 /**
2110 * gst_h264_parser_parse_slice_hdr:
2111 * @nalparser: a #GstH264NalParser
2112 * @nalu: The #GST_H264_NAL_SLICE to #GST_H264_NAL_SLICE_IDR #GstH264NalUnit to parse
2113 * @slice: The #GstH264SliceHdr to fill.
2114 * @parse_pred_weight_table: Whether to parse the pred_weight_table or not
2115 * @parse_dec_ref_pic_marking: Whether to parse the dec_ref_pic_marking or not
2116 *
2117 * Parses @nalu containing a coded slice, and fills @slice.
2118 *
2119 * Returns: a #GstH264ParserResult
2120 */
2121 GstH264ParserResult
gst_h264_parser_parse_slice_hdr(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GstH264SliceHdr * slice,gboolean parse_pred_weight_table,gboolean parse_dec_ref_pic_marking)2122 gst_h264_parser_parse_slice_hdr (GstH264NalParser * nalparser,
2123 GstH264NalUnit * nalu, GstH264SliceHdr * slice,
2124 gboolean parse_pred_weight_table, gboolean parse_dec_ref_pic_marking)
2125 {
2126 NalReader nr;
2127 gint pps_id;
2128 GstH264PPS *pps;
2129 GstH264SPS *sps;
2130
2131 memset (slice, 0, sizeof (*slice));
2132
2133 if (!nalu->size) {
2134 GST_DEBUG ("Invalid Nal Unit");
2135 return GST_H264_PARSER_ERROR;
2136 }
2137
2138 nal_reader_init (&nr, nalu->data + nalu->offset + nalu->header_bytes,
2139 nalu->size - nalu->header_bytes);
2140
2141 READ_UE (&nr, slice->first_mb_in_slice);
2142 READ_UE (&nr, slice->type);
2143
2144 GST_DEBUG ("parsing \"Slice header\", slice type %u", slice->type);
2145
2146 READ_UE_MAX (&nr, pps_id, GST_H264_MAX_PPS_COUNT - 1);
2147 pps = gst_h264_parser_get_pps (nalparser, pps_id);
2148
2149 if (!pps) {
2150 GST_WARNING ("couldn't find associated picture parameter set with id: %d",
2151 pps_id);
2152
2153 return GST_H264_PARSER_BROKEN_LINK;
2154 }
2155
2156 slice->pps = pps;
2157 sps = pps->sequence;
2158 if (!sps) {
2159 GST_WARNING ("couldn't find associated sequence parameter set with id: %d",
2160 pps->id);
2161 return GST_H264_PARSER_BROKEN_LINK;
2162 }
2163
2164 /* Check we can actually parse this slice (AVC, MVC headers only) */
2165 if (sps->extension_type && sps->extension_type != GST_H264_NAL_EXTENSION_MVC) {
2166 GST_WARNING ("failed to parse unsupported slice header");
2167 return GST_H264_PARSER_BROKEN_DATA;
2168 }
2169
2170 /* set default values for fields that might not be present in the bitstream
2171 and have valid defaults */
2172 slice->num_ref_idx_l0_active_minus1 = pps->num_ref_idx_l0_active_minus1;
2173 slice->num_ref_idx_l1_active_minus1 = pps->num_ref_idx_l1_active_minus1;
2174
2175 if (sps->separate_colour_plane_flag)
2176 READ_UINT8 (&nr, slice->colour_plane_id, 2);
2177
2178 READ_UINT16 (&nr, slice->frame_num, sps->log2_max_frame_num_minus4 + 4);
2179
2180 if (!sps->frame_mbs_only_flag) {
2181 READ_UINT8 (&nr, slice->field_pic_flag, 1);
2182 if (slice->field_pic_flag)
2183 READ_UINT8 (&nr, slice->bottom_field_flag, 1);
2184 }
2185
2186 /* calculate MaxPicNum */
2187 if (slice->field_pic_flag)
2188 slice->max_pic_num = 2 * sps->max_frame_num;
2189 else
2190 slice->max_pic_num = sps->max_frame_num;
2191
2192 if (nalu->idr_pic_flag)
2193 READ_UE_MAX (&nr, slice->idr_pic_id, G_MAXUINT16);
2194
2195 if (sps->pic_order_cnt_type == 0) {
2196 READ_UINT16 (&nr, slice->pic_order_cnt_lsb,
2197 sps->log2_max_pic_order_cnt_lsb_minus4 + 4);
2198
2199 if (pps->pic_order_present_flag && !slice->field_pic_flag)
2200 READ_SE (&nr, slice->delta_pic_order_cnt_bottom);
2201 }
2202
2203 if (sps->pic_order_cnt_type == 1 && !sps->delta_pic_order_always_zero_flag) {
2204 READ_SE (&nr, slice->delta_pic_order_cnt[0]);
2205 if (pps->pic_order_present_flag && !slice->field_pic_flag)
2206 READ_SE (&nr, slice->delta_pic_order_cnt[1]);
2207 }
2208
2209 if (pps->redundant_pic_cnt_present_flag)
2210 READ_UE_MAX (&nr, slice->redundant_pic_cnt, G_MAXINT8);
2211
2212 if (GST_H264_IS_B_SLICE (slice))
2213 READ_UINT8 (&nr, slice->direct_spatial_mv_pred_flag, 1);
2214
2215 if (GST_H264_IS_P_SLICE (slice) || GST_H264_IS_SP_SLICE (slice) ||
2216 GST_H264_IS_B_SLICE (slice)) {
2217 guint8 num_ref_idx_active_override_flag;
2218
2219 READ_UINT8 (&nr, num_ref_idx_active_override_flag, 1);
2220 if (num_ref_idx_active_override_flag) {
2221 READ_UE_MAX (&nr, slice->num_ref_idx_l0_active_minus1, 31);
2222
2223 if (GST_H264_IS_B_SLICE (slice))
2224 READ_UE_MAX (&nr, slice->num_ref_idx_l1_active_minus1, 31);
2225 }
2226 }
2227
2228 if (!slice_parse_ref_pic_list_modification (slice, &nr,
2229 GST_H264_IS_MVC_NALU (nalu)))
2230 goto error;
2231
2232 if ((pps->weighted_pred_flag && (GST_H264_IS_P_SLICE (slice)
2233 || GST_H264_IS_SP_SLICE (slice)))
2234 || (pps->weighted_bipred_idc == 1 && GST_H264_IS_B_SLICE (slice))) {
2235 if (!gst_h264_slice_parse_pred_weight_table (slice, &nr,
2236 sps->chroma_array_type))
2237 goto error;
2238 }
2239
2240 if (nalu->ref_idc != 0) {
2241 if (!gst_h264_slice_parse_dec_ref_pic_marking (slice, nalu, &nr))
2242 goto error;
2243 }
2244
2245 if (pps->entropy_coding_mode_flag && !GST_H264_IS_I_SLICE (slice) &&
2246 !GST_H264_IS_SI_SLICE (slice))
2247 READ_UE_MAX (&nr, slice->cabac_init_idc, 2);
2248
2249 READ_SE_ALLOWED (&nr, slice->slice_qp_delta, -87, 77);
2250
2251 if (GST_H264_IS_SP_SLICE (slice) || GST_H264_IS_SI_SLICE (slice)) {
2252 guint8 sp_for_switch_flag;
2253
2254 if (GST_H264_IS_SP_SLICE (slice))
2255 READ_UINT8 (&nr, sp_for_switch_flag, 1);
2256 READ_SE_ALLOWED (&nr, slice->slice_qs_delta, -51, 51);
2257 }
2258
2259 if (pps->deblocking_filter_control_present_flag) {
2260 READ_UE_MAX (&nr, slice->disable_deblocking_filter_idc, 2);
2261 if (slice->disable_deblocking_filter_idc != 1) {
2262 READ_SE_ALLOWED (&nr, slice->slice_alpha_c0_offset_div2, -6, 6);
2263 READ_SE_ALLOWED (&nr, slice->slice_beta_offset_div2, -6, 6);
2264 }
2265 }
2266
2267 if (pps->num_slice_groups_minus1 > 0 &&
2268 pps->slice_group_map_type >= 3 && pps->slice_group_map_type <= 5) {
2269 /* Ceil(Log2(PicSizeInMapUnits / SliceGroupChangeRate + 1)) [7-33] */
2270 guint32 PicWidthInMbs = sps->pic_width_in_mbs_minus1 + 1;
2271 guint32 PicHeightInMapUnits = sps->pic_height_in_map_units_minus1 + 1;
2272 guint32 PicSizeInMapUnits = PicWidthInMbs * PicHeightInMapUnits;
2273 guint32 SliceGroupChangeRate = pps->slice_group_change_rate_minus1 + 1;
2274 const guint n = ceil_log2 (PicSizeInMapUnits / SliceGroupChangeRate + 1);
2275 READ_UINT16 (&nr, slice->slice_group_change_cycle, n);
2276 }
2277
2278 slice->header_size = nal_reader_get_pos (&nr);
2279 slice->n_emulation_prevention_bytes = nal_reader_get_epb_count (&nr);
2280
2281 return GST_H264_PARSER_OK;
2282
2283 error:
2284 GST_WARNING ("error parsing \"Slice header\"");
2285 return GST_H264_PARSER_ERROR;
2286 }
2287
2288 /* Free MVC-specific data from subset SPS header */
2289 static void
gst_h264_sps_mvc_clear(GstH264SPS * sps)2290 gst_h264_sps_mvc_clear (GstH264SPS * sps)
2291 {
2292 GstH264SPSExtMVC *const mvc = &sps->extension.mvc;
2293 guint i, j;
2294
2295 g_assert (sps->extension_type == GST_H264_NAL_EXTENSION_MVC);
2296
2297 g_free (mvc->view);
2298 mvc->view = NULL;
2299
2300 for (i = 0; i <= mvc->num_level_values_signalled_minus1; i++) {
2301 GstH264SPSExtMVCLevelValue *const level_value = &mvc->level_value[i];
2302
2303 for (j = 0; j <= level_value->num_applicable_ops_minus1; j++) {
2304 g_free (level_value->applicable_op[j].target_view_id);
2305 level_value->applicable_op[j].target_view_id = NULL;
2306 }
2307 g_free (level_value->applicable_op);
2308 level_value->applicable_op = NULL;
2309 }
2310 g_free (mvc->level_value);
2311 mvc->level_value = NULL;
2312
2313 /* All meaningful MVC info are now gone, just pretend to be a
2314 * standard AVC struct now */
2315 sps->extension_type = GST_H264_NAL_EXTENSION_NONE;
2316 }
2317
2318 /**
2319 * gst_h264_sps_clear:
2320 * @sps: The #GstH264SPS to free
2321 *
2322 * Clears all @sps internal resources.
2323 *
2324 * Since: 1.6
2325 */
2326 void
gst_h264_sps_clear(GstH264SPS * sps)2327 gst_h264_sps_clear (GstH264SPS * sps)
2328 {
2329 g_return_if_fail (sps != NULL);
2330
2331 switch (sps->extension_type) {
2332 case GST_H264_NAL_EXTENSION_MVC:
2333 gst_h264_sps_mvc_clear (sps);
2334 break;
2335 }
2336 }
2337
2338 static void
h264_sei_message_clear(GstH264SEIMessage * sei_msg)2339 h264_sei_message_clear (GstH264SEIMessage * sei_msg)
2340 {
2341 switch (sei_msg->payloadType) {
2342 case GST_H264_SEI_REGISTERED_USER_DATA:{
2343 GstH264RegisteredUserData *rud = &sei_msg->payload.registered_user_data;
2344
2345 g_free ((guint8 *) rud->data);
2346 rud->data = NULL;
2347 break;
2348 }
2349 default:
2350 break;
2351 }
2352 }
2353
2354 /**
2355 * gst_h264_parser_parse_sei:
2356 * @nalparser: a #GstH264NalParser
2357 * @nalu: The #GST_H264_NAL_SEI #GstH264NalUnit to parse
2358 * @messages: The GArray of #GstH264SEIMessage to fill. The caller must free it when done.
2359 *
2360 * Parses @nalu containing one or more Supplementary Enhancement Information messages,
2361 * and allocates and fills the @messages array.
2362 *
2363 * Returns: a #GstH264ParserResult
2364 */
2365 GstH264ParserResult
gst_h264_parser_parse_sei(GstH264NalParser * nalparser,GstH264NalUnit * nalu,GArray ** messages)2366 gst_h264_parser_parse_sei (GstH264NalParser * nalparser, GstH264NalUnit * nalu,
2367 GArray ** messages)
2368 {
2369 NalReader nr;
2370 GstH264SEIMessage sei;
2371 GstH264ParserResult res;
2372
2373 GST_DEBUG ("parsing SEI nal");
2374 nal_reader_init (&nr, nalu->data + nalu->offset + nalu->header_bytes,
2375 nalu->size - nalu->header_bytes);
2376 *messages = g_array_new (FALSE, FALSE, sizeof (GstH264SEIMessage));
2377 g_array_set_clear_func (*messages, (GDestroyNotify) h264_sei_message_clear);
2378
2379 do {
2380 res = gst_h264_parser_parse_sei_message (nalparser, &nr, &sei);
2381 if (res == GST_H264_PARSER_OK)
2382 g_array_append_val (*messages, sei);
2383 else
2384 break;
2385 } while (nal_reader_has_more_data (&nr));
2386
2387 return res;
2388 }
2389
2390 /**
2391 * gst_h264_quant_matrix_8x8_get_zigzag_from_raster:
2392 * @out_quant: (out): The resulting quantization matrix
2393 * @quant: The source quantization matrix
2394 *
2395 * Converts quantization matrix @quant from raster scan order to
2396 * zigzag scan order and store the resulting factors into @out_quant.
2397 *
2398 * Note: it is an error to pass the same table in both @quant and
2399 * @out_quant arguments.
2400 *
2401 * Since: 1.4
2402 */
2403 void
gst_h264_quant_matrix_8x8_get_zigzag_from_raster(guint8 out_quant[64],const guint8 quant[64])2404 gst_h264_quant_matrix_8x8_get_zigzag_from_raster (guint8 out_quant[64],
2405 const guint8 quant[64])
2406 {
2407 guint i;
2408
2409 g_return_if_fail (out_quant != quant);
2410
2411 for (i = 0; i < 64; i++)
2412 out_quant[i] = quant[zigzag_8x8[i]];
2413 }
2414
2415 /**
2416 * gst_h264_quant_matrix_8x8_get_raster_from_zigzag:
2417 * @out_quant: (out): The resulting quantization matrix
2418 * @quant: The source quantization matrix
2419 *
2420 * Converts quantization matrix @quant from zigzag scan order to
2421 * raster scan order and store the resulting factors into @out_quant.
2422 *
2423 * Note: it is an error to pass the same table in both @quant and
2424 * @out_quant arguments.
2425 *
2426 * Since: 1.4
2427 */
2428 void
gst_h264_quant_matrix_8x8_get_raster_from_zigzag(guint8 out_quant[64],const guint8 quant[64])2429 gst_h264_quant_matrix_8x8_get_raster_from_zigzag (guint8 out_quant[64],
2430 const guint8 quant[64])
2431 {
2432 guint i;
2433
2434 g_return_if_fail (out_quant != quant);
2435
2436 for (i = 0; i < 64; i++)
2437 out_quant[zigzag_8x8[i]] = quant[i];
2438 }
2439
2440 /**
2441 * gst_h264_quant_matrix_4x4_get_zigzag_from_raster:
2442 * @out_quant: (out): The resulting quantization matrix
2443 * @quant: The source quantization matrix
2444 *
2445 * Converts quantization matrix @quant from raster scan order to
2446 * zigzag scan order and store the resulting factors into @out_quant.
2447 *
2448 * Note: it is an error to pass the same table in both @quant and
2449 * @out_quant arguments.
2450 *
2451 * Since: 1.4
2452 */
2453 void
gst_h264_quant_matrix_4x4_get_zigzag_from_raster(guint8 out_quant[16],const guint8 quant[16])2454 gst_h264_quant_matrix_4x4_get_zigzag_from_raster (guint8 out_quant[16],
2455 const guint8 quant[16])
2456 {
2457 guint i;
2458
2459 g_return_if_fail (out_quant != quant);
2460
2461 for (i = 0; i < 16; i++)
2462 out_quant[i] = quant[zigzag_4x4[i]];
2463 }
2464
2465 /**
2466 * gst_h264_quant_matrix_4x4_get_raster_from_zigzag:
2467 * @out_quant: (out): The resulting quantization matrix
2468 * @quant: The source quantization matrix
2469 *
2470 * Converts quantization matrix @quant from zigzag scan order to
2471 * raster scan order and store the resulting factors into @out_quant.
2472 *
2473 * Note: it is an error to pass the same table in both @quant and
2474 * @out_quant arguments.
2475 *
2476 * Since: 1.4
2477 */
2478 void
gst_h264_quant_matrix_4x4_get_raster_from_zigzag(guint8 out_quant[16],const guint8 quant[16])2479 gst_h264_quant_matrix_4x4_get_raster_from_zigzag (guint8 out_quant[16],
2480 const guint8 quant[16])
2481 {
2482 guint i;
2483
2484 g_return_if_fail (out_quant != quant);
2485
2486 for (i = 0; i < 16; i++)
2487 out_quant[zigzag_4x4[i]] = quant[i];
2488 }
2489
2490 /**
2491 * gst_h264_video_calculate_framerate:
2492 * @sps: Current Sequence Parameter Set
2493 * @field_pic_flag: Current @field_pic_flag, obtained from latest slice header
2494 * @pic_struct: @pic_struct value if available, 0 otherwise
2495 * @fps_num: (out): The resulting fps numerator
2496 * @fps_den: (out): The resulting fps denominator
2497 *
2498 * Calculate framerate of a video sequence using @sps VUI information,
2499 * @field_pic_flag from a slice header and @pic_struct from #GstH264PicTiming SEI
2500 * message.
2501 *
2502 * If framerate is variable or can't be determined, @fps_num will be set to 0
2503 * and @fps_den to 1.
2504 */
2505 void
gst_h264_video_calculate_framerate(const GstH264SPS * sps,guint field_pic_flag,guint pic_struct,gint * fps_num,gint * fps_den)2506 gst_h264_video_calculate_framerate (const GstH264SPS * sps,
2507 guint field_pic_flag, guint pic_struct, gint * fps_num, gint * fps_den)
2508 {
2509 gint num = 0;
2510 gint den = 1;
2511
2512 /* To calculate framerate, we use this formula:
2513 * time_scale 1 1
2514 * fps = ----------------- x --------------- x ------------------------
2515 * num_units_in_tick DeltaTfiDivisor (field_pic_flag ? 2 : 1)
2516 *
2517 * See H264 specification E2.1 for more details.
2518 */
2519
2520 if (sps) {
2521 if (sps->vui_parameters_present_flag) {
2522 const GstH264VUIParams *vui = &sps->vui_parameters;
2523 if (vui->timing_info_present_flag) {
2524 int delta_tfi_divisor = 1;
2525 num = vui->time_scale;
2526 den = vui->num_units_in_tick;
2527
2528 if (vui->pic_struct_present_flag) {
2529 switch (pic_struct) {
2530 case 1:
2531 case 2:
2532 delta_tfi_divisor = 1;
2533 break;
2534 case 0:
2535 case 3:
2536 case 4:
2537 delta_tfi_divisor = 2;
2538 break;
2539 case 5:
2540 case 6:
2541 delta_tfi_divisor = 3;
2542 break;
2543 case 7:
2544 delta_tfi_divisor = 4;
2545 break;
2546 case 8:
2547 delta_tfi_divisor = 6;
2548 break;
2549 }
2550 } else {
2551 delta_tfi_divisor = field_pic_flag ? 1 : 2;
2552 }
2553 den *= delta_tfi_divisor;
2554
2555 /* Picture is two fields ? */
2556 den *= (field_pic_flag ? 2 : 1);
2557 }
2558 }
2559 }
2560
2561 *fps_num = num;
2562 *fps_den = den;
2563 }
2564