]> git.ipfire.org Git - thirdparty/tvheadend.git/commitdiff
hevc parser: fix scaling_list_pred_mode condition, other cosmetic stuff, fixes #4046...
authorJaroslav Kysela <perex@perex.cz>
Tue, 1 Nov 2016 16:50:23 +0000 (17:50 +0100)
committerJaroslav Kysela <perex@perex.cz>
Tue, 1 Nov 2016 16:50:23 +0000 (17:50 +0100)
src/parsers/bitstream.c
src/parsers/parser_hevc.c

index 5f21449b0c6e1b11feb3a01ff7635449818c48ba..921ee0ef0b534d79796d5adf62f01ff61ccbd80c 100644 (file)
@@ -73,7 +73,7 @@ read_bits64(bitstream_t *bs, uint32_t num)
     num--;
 
     if(bs->rdata[bs->offset / 8] & (1 << (7 - (bs->offset & 7))))
-      r |= 1 << num;
+      r |= (int64_t)1 << num;
 
     bs->offset++;
   }
index cb713be41acc9a8981b4db547abd0ff7b49f4b8e..901523314b8b708f9c2b9b5ec53d325af845145e 100644 (file)
@@ -149,34 +149,46 @@ static void hvcc_update_ptl(HEVCDecoderConfigurationRecord *hvcc,
     hvcc->general_constraint_indicator_flags &= ptl->constraint_indicator_flags;
 }
 
-static void hvcc_parse_ptl(bitstream_t *gb,
-                           HEVCDecoderConfigurationRecord *hvcc,
-                           unsigned int max_sub_layers_minus1)
+static int hvcc_parse_ptl(bitstream_t *gb,
+                          HEVCDecoderConfigurationRecord *hvcc,
+                          unsigned int max_sub_layers)
 {
     unsigned int i;
     HVCCProfileTierLevel general_ptl;
     uint8_t sub_layer_profile_present_flag[MAX_SUB_LAYERS];
     uint8_t sub_layer_level_present_flag[MAX_SUB_LAYERS];
 
+    if (remaining_bits(gb) < 2+1+5 + 32 + 4 + 16 + 16 + 12)
+      return -1;
+
     general_ptl.profile_space               = read_bits(gb, 2);
     general_ptl.tier_flag                   = read_bits1(gb);
     general_ptl.profile_idc                 = read_bits(gb, 5);
     general_ptl.profile_compatibility_flags = read_bits(gb, 32);
+    if (general_ptl.profile_idc == 0) {
+      for (i = 0; i < 32; i++)
+        if (general_ptl.profile_compatibility_flags & (1 << (31-i)))
+          general_ptl.profile_idc = i;
+    }
     general_ptl.constraint_indicator_flags  = read_bits64(gb, 48);
+
+    if (remaining_bits(gb) < 8 + (8*2 * (max_sub_layers - 1 > 0)))
+      return -1;
+
     general_ptl.level_idc                   = read_bits(gb, 8);
     if (hvcc)
         hvcc_update_ptl(hvcc, &general_ptl);
 
-    for (i = 0; i < max_sub_layers_minus1; i++) {
+    for (i = 0; i < max_sub_layers - 1; i++) {
         sub_layer_profile_present_flag[i] = read_bits1(gb);
         sub_layer_level_present_flag[i]   = read_bits1(gb);
     }
 
-    if (max_sub_layers_minus1 > 0)
-        for (i = max_sub_layers_minus1; i < 8; i++)
+    if (max_sub_layers - 1 > 0)
+        for (i = max_sub_layers - 1; i < 8; i++)
             skip_bits(gb, 2); // reserved_zero_2bits[i]
 
-    for (i = 0; i < max_sub_layers_minus1; i++) {
+    for (i = 0; i < max_sub_layers - 1; i++) {
         if (sub_layer_profile_present_flag[i]) {
             /*
              * sub_layer_profile_space[i]                     u(2)
@@ -197,15 +209,16 @@ static void hvcc_parse_ptl(bitstream_t *gb,
         if (sub_layer_level_present_flag[i])
             skip_bits(gb, 8);
     }
+    return 0;
 }
 
 static void skip_sub_layer_hrd_parameters(bitstream_t *gb,
-                                          unsigned int cpb_cnt_minus1,
+                                          unsigned int cpb_cnt,
                                           uint8_t sub_pic_hrd_params_present_flag)
 {
     unsigned int i;
 
-    for (i = 0; i <= cpb_cnt_minus1; i++) {
+    for (i = 0; i < cpb_cnt; i++) {
         read_golomb_ue(gb); // bit_rate_value_minus1
         read_golomb_ue(gb); // cpb_size_value_minus1
 
@@ -219,7 +232,7 @@ static void skip_sub_layer_hrd_parameters(bitstream_t *gb,
 }
 
 static int skip_hrd_parameters(bitstream_t *gb, uint8_t cprms_present_flag,
-                                unsigned int max_sub_layers_minus1)
+                                unsigned int max_sub_layers)
 {
     unsigned int i;
     uint8_t sub_pic_hrd_params_present_flag = 0;
@@ -261,8 +274,8 @@ static int skip_hrd_parameters(bitstream_t *gb, uint8_t cprms_present_flag,
         }
     }
 
-    for (i = 0; i <= max_sub_layers_minus1; i++) {
-        unsigned int cpb_cnt_minus1            = 0;
+    for (i = 0; i < max_sub_layers; i++) {
+        unsigned int cpb_cnt                   = 0;
         uint8_t low_delay_hrd_flag             = 0;
         uint8_t fixed_pic_rate_within_cvs_flag = 0;
         uint8_t fixed_pic_rate_general_flag    = read_bits1(gb);
@@ -276,18 +289,16 @@ static int skip_hrd_parameters(bitstream_t *gb, uint8_t cprms_present_flag,
             low_delay_hrd_flag = read_bits1(gb);
 
         if (!low_delay_hrd_flag) {
-            cpb_cnt_minus1 = read_golomb_ue(gb);
-            if (cpb_cnt_minus1 > 31)
+            cpb_cnt = read_golomb_ue(gb) + 1;
+            if (cpb_cnt > 32)
                 return -1;
         }
 
         if (nal_hrd_parameters_present_flag)
-            skip_sub_layer_hrd_parameters(gb, cpb_cnt_minus1,
-                                          sub_pic_hrd_params_present_flag);
+            skip_sub_layer_hrd_parameters(gb, cpb_cnt, sub_pic_hrd_params_present_flag);
 
         if (vcl_hrd_parameters_present_flag)
-            skip_sub_layer_hrd_parameters(gb, cpb_cnt_minus1,
-                                          sub_pic_hrd_params_present_flag);
+            skip_sub_layer_hrd_parameters(gb, cpb_cnt, sub_pic_hrd_params_present_flag);
     }
 
     return 0;
@@ -304,7 +315,7 @@ static void skip_timing_info(bitstream_t *gb)
 
 static void hvcc_parse_vui(bitstream_t *gb,
                            HEVCDecoderConfigurationRecord *hvcc,
-                           unsigned int max_sub_layers_minus1)
+                           unsigned int max_sub_layers)
 {
     unsigned int min_spatial_segmentation_idc;
 
@@ -350,7 +361,7 @@ static void hvcc_parse_vui(bitstream_t *gb,
         skip_timing_info(gb);
 
         if (read_bits1(gb)) // vui_hrd_parameters_present_flag
-            skip_hrd_parameters(gb, 1, max_sub_layers_minus1);
+            skip_hrd_parameters(gb, 1, max_sub_layers);
     }
 
     if (read_bits1(gb)) { // bitstream_restriction_flag
@@ -390,7 +401,7 @@ static void skip_sub_layer_ordering_info(bitstream_t *gb)
 static int hvcc_parse_vps(bitstream_t *gb,
                           HEVCDecoderConfigurationRecord *hvcc)
 {
-    unsigned int vps_max_sub_layers_minus1;
+    unsigned int vps_max_sub_layers;
 
     /*
      * vps_video_parameter_set_id u(4)
@@ -399,7 +410,7 @@ static int hvcc_parse_vps(bitstream_t *gb,
      */
     skip_bits(gb, 12);
 
-    vps_max_sub_layers_minus1 = read_bits(gb, 3);
+    vps_max_sub_layers = read_bits(gb, 3) + 1;
 
     /*
      * numTemporalLayers greater than 1 indicates that the stream to which this
@@ -409,8 +420,7 @@ static int hvcc_parse_vps(bitstream_t *gb,
      * indicates that the stream is not temporally scalable. Value 0 indicates
      * that it is unknown whether the stream is temporally scalable.
      */
-    hvcc->numTemporalLayers = MAX(hvcc->numTemporalLayers,
-                                  vps_max_sub_layers_minus1 + 1);
+    hvcc->numTemporalLayers = MAX(hvcc->numTemporalLayers, vps_max_sub_layers);
 
     /*
      * vps_temporal_id_nesting_flag u(1)
@@ -418,7 +428,8 @@ static int hvcc_parse_vps(bitstream_t *gb,
      */
     skip_bits(gb, 17);
 
-    hvcc_parse_ptl(gb, hvcc, vps_max_sub_layers_minus1);
+    if (hvcc_parse_ptl(gb, hvcc, vps_max_sub_layers))
+      return -1;
 
     /* nothing useful for hvcC past this point */
     return 0;
@@ -513,12 +524,12 @@ static int parse_rps(bitstream_t *gb, unsigned int rps_idx,
 static int hvcc_parse_sps(bitstream_t *gb,
                           HEVCDecoderConfigurationRecord *hvcc)
 {
-    unsigned int i, sps_max_sub_layers_minus1, log2_max_pic_order_cnt_lsb_minus4;
+    unsigned int i, sps_max_sub_layers, log2_max_pic_order_cnt_lsb_minus4;
     unsigned int num_short_term_ref_pic_sets, num_delta_pocs[MAX_SHORT_TERM_RPS_COUNT];
 
     skip_bits(gb, 4); // sps_video_parameter_set_id
 
-    sps_max_sub_layers_minus1 = read_bits (gb, 3);
+    sps_max_sub_layers = read_bits (gb, 3) + 1;
 
     /*
      * numTemporalLayers greater than 1 indicates that the stream to which this
@@ -528,12 +539,11 @@ static int hvcc_parse_sps(bitstream_t *gb,
      * indicates that the stream is not temporally scalable. Value 0 indicates
      * that it is unknown whether the stream is temporally scalable.
      */
-    hvcc->numTemporalLayers = MAX(hvcc->numTemporalLayers,
-                                  sps_max_sub_layers_minus1 + 1);
+    hvcc->numTemporalLayers = MAX(hvcc->numTemporalLayers, sps_max_sub_layers);
 
     hvcc->temporalIdNested = read_bits1(gb);
 
-    hvcc_parse_ptl(gb, hvcc, sps_max_sub_layers_minus1);
+    hvcc_parse_ptl(gb, hvcc, sps_max_sub_layers);
 
     read_golomb_ue(gb); // sps_seq_parameter_set_id
 
@@ -557,8 +567,8 @@ static int hvcc_parse_sps(bitstream_t *gb,
     log2_max_pic_order_cnt_lsb_minus4 = read_golomb_ue(gb);
 
     /* sps_sub_layer_ordering_info_present_flag */
-    i = read_bits1(gb) ? 0 : sps_max_sub_layers_minus1;
-    for (; i <= sps_max_sub_layers_minus1; i++)
+    i = read_bits1(gb) ? 1 : sps_max_sub_layers;
+    for (; i < sps_max_sub_layers; i++)
         skip_sub_layer_ordering_info(gb);
 
     read_golomb_ue(gb); // log2_min_luma_coding_block_size_minus3
@@ -608,7 +618,7 @@ static int hvcc_parse_sps(bitstream_t *gb,
     skip_bits1(gb); // strong_intra_smoothing_enabled_flag
 
     if (read_bits1(gb)) // vui_parameters_present_flag
-        hvcc_parse_vui(gb, hvcc, sps_max_sub_layers_minus1);
+        hvcc_parse_vui(gb, hvcc, sps_max_sub_layers);
 
     /* nothing useful for hvcC past this point */
     return 0;
@@ -1309,7 +1319,7 @@ hevc_decode_vps(elementary_stream_t *st, bitstream_t *bs)
   if (max_sub_layers > MAX_SUB_LAYERS)
     return;
 
-  hvcc_parse_ptl(bs, NULL, max_sub_layers - 1);
+  hvcc_parse_ptl(bs, NULL, max_sub_layers);
 
   sub_layer_ordering_info_present = read_bits1(bs);
   u = sub_layer_ordering_info_present ? 0 : max_sub_layers - 1;
@@ -1441,7 +1451,7 @@ hevc_decode_sps(elementary_stream_t *st, bitstream_t *bs)
     return;
   skip_bits1(bs);     /* temporal_id_nesting */
 
-  hvcc_parse_ptl(bs, NULL, max_sub_layers - 1);
+  hvcc_parse_ptl(bs, NULL, max_sub_layers);
 
   sps_id = read_golomb_ue(bs);
   if (sps_id >= MAX_SPS_COUNT)
@@ -1500,7 +1510,7 @@ hevc_decode_sps(elementary_stream_t *st, bitstream_t *bs)
     if (read_bits1(bs)) { /* scaling_list_data */
       for (u = 0; u < 4; u++) {
         for (v = 0; v < 6; v += ((u == 3) ? 3 : 1)) {
-          if (read_bits1(bs)) { /* scaling_list_pred_mode */
+          if (!read_bits1(bs)) { /* scaling_list_pred_mode */
             read_golomb_ue(bs); /* delta */
           } else {
             if (u > 1)