コード例 #1
0
ファイル: parser_h264.c プロジェクト: 2crazyzgb/tvheadend
int
h264_decode_pic_parameter_set(elementary_stream_t *st, bitstream_t *bs)
{
  h264_private_t *p;
  uint32_t pps_id, sps_id;

  if((p = st->es_priv) == NULL) {
    p = st->es_priv = calloc(1, sizeof(h264_private_t));
    p->start = dispatch_clock;
  }
  
  pps_id = read_golomb_ue(bs);
  if(pps_id >= MAX_PPS_COUNT)
    return 0;

  sps_id = read_golomb_ue(bs);
  if(sps_id >= MAX_SPS_COUNT)
    return -1;
  if (!p->sps[sps_id].valid)
    return -1;

  p->pps[pps_id].sps_id = sps_id;
  p->pps[pps_id].valid = 1;
  return 0;
}
コード例 #2
0
ファイル: parser_h264.c プロジェクト: etmtvdp/tvheadend
int
h264_decode_pic_parameter_set(elementary_stream_t *st, bitstream_t *bs)
{
  h264_private_t *p;
  int pps_id, sps_id;

  if((p = st->es_priv) == NULL)
    p = st->es_priv = calloc(1, sizeof(h264_private_t));
  
  pps_id = read_golomb_ue(bs);
  sps_id = read_golomb_ue(bs);
  p->pps[pps_id].sps = sps_id;
  return 0;
}
コード例 #3
0
ファイル: parser_h264.c プロジェクト: etmtvdp/tvheadend
static int 
decode_vui(h264_private_t *p, bitstream_t *bs, int sps_id)
{
  p->sps[sps_id].aspect_num = 0;
  p->sps[sps_id].aspect_den = 1;

  if(read_bits1(bs)) {
    int aspect = read_bits(bs, 8);

    if(aspect == 255) {
      uint16_t num = read_bits(bs, 16);
      uint16_t den = read_bits(bs, 16);
      p->sps[sps_id].aspect_num = num;
      p->sps[sps_id].aspect_den = den;
    } else if(aspect < 17) {
      p->sps[sps_id].aspect_num =  h264_aspect[aspect][0];
      p->sps[sps_id].aspect_den =  h264_aspect[aspect][1];
    }
  }

  if(read_bits1(bs)){      /* overscan_info_present_flag */
    read_bits1(bs);      /* overscan_appropriate_flag */
  }

  if(read_bits1(bs)){      /* video_signal_type_present_flag */
    read_bits(bs, 3);    /* video_format */
    read_bits1(bs);      /* video_full_range_flag */
    if(read_bits1(bs)){  /* colour_description_present_flag */
      read_bits(bs, 8); /* colour_primaries */
      read_bits(bs, 8); /* transfer_characteristics */
      read_bits(bs, 8); /* matrix_coefficients */
    }
  }

  if(read_bits1(bs)){      /* chroma_location_info_present_flag */
    read_golomb_ue(bs);  /* chroma_sample_location_type_top_field */
    read_golomb_ue(bs);  /* chroma_sample_location_type_bottom_field */
  }

  if(!read_bits1(bs)) /* We need timing info */
    return 0;
    

  p->sps[sps_id].units_in_tick = read_bits(bs, 32);
  p->sps[sps_id].time_scale    = read_bits(bs, 32);
  p->sps[sps_id].fixed_rate    = read_bits1(bs);
  return 0;
}
コード例 #4
0
ファイル: parser_h264.c プロジェクト: 2crazyzgb/tvheadend
static int 
decode_vui(h264_sps_t *sps, bitstream_t *bs)
{
  sps->aspect_num = 1;
  sps->aspect_den = 1;

  if (read_bits1(bs)) {
    uint32_t aspect = read_bits(bs, 8);
    if(aspect == 255) {
      sps->aspect_num = read_bits(bs, 16);
      sps->aspect_den = read_bits(bs, 16);
    } else if(aspect < ARRAY_SIZE(h264_aspect)) {
      sps->aspect_num = h264_aspect[aspect][0];
      sps->aspect_den = h264_aspect[aspect][1];
    }
  }

  if (read_bits1(bs))   /* overscan_info_present_flag */
    skip_bits1(bs);     /* overscan_appropriate_flag */

  if (read_bits1(bs)) { /* video_signal_type_present_flag */
    skip_bits(bs, 3);   /* video_format */
    skip_bits1(bs);     /* video_full_range_flag */
    if(read_bits1(bs)){ /* colour_description_present_flag */
      skip_bits(bs, 8); /* colour_primaries */
      skip_bits(bs, 8); /* transfer_characteristics */
      skip_bits(bs, 8); /* matrix_coefficients */
    }
  }

  if (read_bits1(bs)) { /* chroma_location_info_present_flag */
    read_golomb_ue(bs); /* chroma_sample_location_type_top_field */
    read_golomb_ue(bs); /* chroma_sample_location_type_bottom_field */
  }

  if (!read_bits1(bs))   /* We need timing info */
    return 0;

  if (remaining_bits(bs) < 65)
    return 0;

  sps->units_in_tick = read_bits(bs, 32);
  sps->time_scale    = read_bits(bs, 32);
  sps->fixed_rate    = read_bits1(bs);
  return 0;
}
コード例 #5
0
ファイル: bitstream.c プロジェクト: wmyrda/tvheadend
signed int
read_golomb_se(bitstream_t *bs)
{
  int v, pos;
  v = read_golomb_ue(bs);
  if(v == 0)
    return 0;

  pos = v & 1;
  v = (v + 1) >> 1;
  return pos ? v : -v;
}
コード例 #6
0
ファイル: parser_h264.c プロジェクト: etmtvdp/tvheadend
int
h264_decode_slice_header(elementary_stream_t *st, bitstream_t *bs, int *pkttype,
			 int *duration, int *isfield)
{
  h264_private_t *p;
  int slice_type, pps_id, sps_id, fnum;

  if((p = st->es_priv) == NULL)
    return -1;

  read_golomb_ue(bs); /* first_mb_in_slice */
  slice_type = read_golomb_ue(bs);
  
  if(slice_type > 4)
    slice_type -= 5;  /* Fixed slice type per frame */

  switch(slice_type) {
  case 0:
    *pkttype = PKT_P_FRAME;
    break;
  case 1:
    *pkttype = PKT_B_FRAME;
    break;
  case 2:
    *pkttype = PKT_I_FRAME;
    break;
  default:
    return -1;
  }

  pps_id = read_golomb_ue(bs);
  sps_id = p->pps[pps_id].sps;
  if(p->sps[sps_id].max_frame_num_bits == 0)
    return -1;

  fnum = read_bits(bs, p->sps[sps_id].max_frame_num_bits);

  int field = 0;
  int timebase = 180000;

  if(!p->sps[sps_id].mbs_only_flag) {
    if(read_bits1(bs)) {
      read_bits1(bs); // bottom field
      field = 1;
    }
  }

  *isfield = field;

  if(p->sps[sps_id].time_scale != 0) {
    int d = timebase * p->sps[sps_id].units_in_tick / p->sps[sps_id].time_scale;
    *duration = d;
  } else {
    *duration = 0;
  }

  if(p->sps[sps_id].cbpsize != 0)
    st->es_vbv_size = p->sps[sps_id].cbpsize;

  st->es_vbv_delay = -1;

  if(p->sps[sps_id].width && p->sps[sps_id].height && !st->es_buf.sb_err)
    parser_set_stream_vsize(st, p->sps[sps_id].width, 
			    p->sps[sps_id].height *
			    (2 - p->sps[sps_id].mbs_only_flag));

  if(p->sps[sps_id].aspect_num && p->sps[sps_id].aspect_den) {

    int w = p->sps[sps_id].aspect_num * st->es_width;
    int h = p->sps[sps_id].aspect_den * st->es_height;

    if(w && h) { 
      int d = gcd(w, h);
      st->es_aspect_num = w / d;
      st->es_aspect_den = h / d;
    }

  } else {
    st->es_aspect_num = 0;
    st->es_aspect_den = 1;
  }

  return 0;
}
コード例 #7
0
ファイル: parser_h264.c プロジェクト: etmtvdp/tvheadend
int
h264_decode_seq_parameter_set(elementary_stream_t *st, bitstream_t *bs)
{
  int profile_idc, level_idc, poc_type;
  unsigned int sps_id, tmp, i, width, height;
  int cbpsize = -1;
  h264_private_t *p;

  if((p = st->es_priv) == NULL)
    p = st->es_priv = calloc(1, sizeof(h264_private_t));

  profile_idc= read_bits(bs, 8);
  read_bits1(bs);   //constraint_set0_flag
  read_bits1(bs);   //constraint_set1_flag
  read_bits1(bs);   //constraint_set2_flag
  read_bits1(bs);   //constraint_set3_flag
  read_bits(bs, 4); // reserved
  level_idc= read_bits(bs, 8);
  sps_id= read_golomb_ue(bs);


  i = 0;
  while(h264_lev2cpbsize[i][0] != -1) {
    if(h264_lev2cpbsize[i][0] >= level_idc) {
      cbpsize = h264_lev2cpbsize[i][1];
      break;
    }
    i++;
  }
  if(cbpsize < 0)
    return -1;

  p->sps[sps_id].cbpsize = cbpsize * 125; /* Convert from kbit to bytes */


  if(profile_idc >= 100){ //high profile
    if(read_golomb_ue(bs) == 3) //chroma_format_idc
      read_bits1(bs);  //residual_color_transform_flag
    read_golomb_ue(bs);  //bit_depth_luma_minus8
    read_golomb_ue(bs);  //bit_depth_chroma_minus8
    read_bits1(bs);

    if(read_bits1(bs)) {
      /* Scaling matrices */
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);

      decode_scaling_list(bs, 64);
      decode_scaling_list(bs, 64);

    }
  }

  p->sps[sps_id].max_frame_num_bits = read_golomb_ue(bs) + 4;
  poc_type= read_golomb_ue(bs);
 
  if(poc_type == 0){ //FIXME #define
    read_golomb_ue(bs);
  } else if(poc_type == 1){//FIXME #define
    read_bits1(bs);
    read_golomb_se(bs);
    read_golomb_se(bs);
    tmp = read_golomb_ue(bs); /* poc_cycle_length */
    for(i = 0; i < tmp; i++)
      read_golomb_se(bs);

  }else if(poc_type != 2){
    /* Illegal poc */
    return -1;
  }

  tmp = read_golomb_ue(bs);

  read_bits1(bs);

  width = read_golomb_ue(bs) + 1; /* mb width */
  height = read_golomb_ue(bs) + 1; /* mb height */

  p->sps[sps_id].width = width * 16;
  p->sps[sps_id].height = height * 16;

  p->sps[sps_id].mbs_only_flag = read_bits1(bs);
  if(!p->sps[sps_id].mbs_only_flag)
    p->sps[sps_id].aff = read_bits1(bs);

  read_bits1(bs);

  /* CROP */
  if(read_bits1(bs)){
    tmp = read_golomb_ue(bs);
    tmp = read_golomb_ue(bs);
    tmp = read_golomb_ue(bs);
    tmp = read_golomb_ue(bs);
  }

  if(read_bits1(bs)) {
    decode_vui(p, bs, sps_id);
    return 0;
  } else {
    return -1;
  }
}
コード例 #8
0
ファイル: parser_h264.c プロジェクト: 2crazyzgb/tvheadend
int
h264_decode_slice_header(elementary_stream_t *st, bitstream_t *bs, int *pkttype,
			 int *isfield)
{
  h264_private_t *p;
  h264_pps_t *pps;
  h264_sps_t *sps;
  uint32_t slice_type, pps_id, width, height, v;
  uint64_t d;

  *pkttype = 0;
  *isfield = 0;

  if ((p = st->es_priv) == NULL)
    return -1;

  read_golomb_ue(bs); /* first_mb_in_slice */
  slice_type = read_golomb_ue(bs);

  if (slice_type > 4)
    slice_type -= 5;  /* Fixed slice type per frame */

  pps_id = read_golomb_ue(bs);
  if (pps_id >= MAX_PPS_COUNT)
    return -1;
  pps = &p->pps[pps_id];
  if (!pps->valid)
    return -1;
  sps = &p->sps[pps->sps_id];
  if (!sps->valid)
    return -1;

  if (!sps->max_frame_num_bits)
    return -1;

  switch(slice_type) {
  case 0:
    *pkttype = PKT_P_FRAME;
    break;
  case 1:
    *pkttype = PKT_B_FRAME;
    break;
  case 2:
    *pkttype = PKT_I_FRAME;
    break;
  default:
    return -1;
  }

  skip_bits(bs, sps->max_frame_num_bits);

  if (!sps->mbs_only_flag)
    if (read_bits1(bs)) {
      skip_bits1(bs); // bottom field
      *isfield = 1;
    }

  d = 0;
  if (sps->time_scale)
    d = 180000 * (uint64_t)sps->units_in_tick / (uint64_t)sps->time_scale;
  if (d == 0 && st->es_frame_duration == 0 && p->start + 4 < dispatch_clock) {
    tvhwarn("parser", "H264 stream has not timing information, using 30fps");
    d = 3000; /* 90000/30 = 3000 : 30fps */
  }

  if (sps->cbpsize)
    st->es_vbv_size = sps->cbpsize;

  st->es_vbv_delay = -1;

  width  = sps->width;
  height = sps->height * (2 - sps->mbs_only_flag);

  if (width && height && d)
    parser_set_stream_vparam(st, width, height, d);

  if (sps->aspect_num && sps->aspect_den) {
    width  *= sps->aspect_num;
    height *= sps->aspect_den;
    if (width && height) {
      v = gcdU32(width, height);
      st->es_aspect_num = width / v;
      st->es_aspect_den = height / v;
    }
  } else {
    st->es_aspect_num = 0;
    st->es_aspect_den = 1;
  }

  return 0;
}
コード例 #9
0
ファイル: parser_h264.c プロジェクト: 2crazyzgb/tvheadend
int
h264_decode_seq_parameter_set(elementary_stream_t *st, bitstream_t *bs)
{
  uint32_t profile_idc, level_idc, poc_type;
  uint32_t sps_id, tmp, i, width, height;
  uint32_t cbpsize, mbs_only_flag, aff;
  uint32_t max_frame_num_bits;
  uint32_t crop_left, crop_right, crop_top, crop_bottom;
  h264_private_t *p;
  h264_sps_t *sps;

  if ((p = st->es_priv) == NULL) {
    p = st->es_priv = calloc(1, sizeof(h264_private_t));
    p->start = dispatch_clock;
  }

  profile_idc = read_bits(bs, 8);
  skip_bits1(bs);   //constraint_set0_flag
  skip_bits1(bs);   //constraint_set1_flag
  skip_bits1(bs);   //constraint_set2_flag
  skip_bits1(bs);   //constraint_set3_flag
  skip_bits(bs, 4); // reserved
  level_idc = read_bits(bs, 8);

  sps_id = read_golomb_ue(bs);
  if(sps_id >= MAX_SPS_COUNT)
    return -1;
  sps = &p->sps[sps_id];

  i = 0;
  cbpsize = -1;
  while (h264_lev2cpbsize[i][0] != -1) {
    if (h264_lev2cpbsize[i][0] >= level_idc) {
      cbpsize = h264_lev2cpbsize[i][1];
      break;
    }
    i++;
  }
  if (cbpsize == -1)
    return -1;

  if (profile_idc >= 100){ //high profile
    tmp = read_golomb_ue(bs);
    if (tmp == 3)          //chroma_format_idc
      read_bits1(bs);      //residual_color_transform_flag
    read_golomb_ue(bs);    //bit_depth_luma_minus8
    read_golomb_ue(bs);    //bit_depth_chroma_minus8
    read_bits1(bs);        //transform_bypass

    if(read_bits1(bs)) {
      /* Scaling matrices */
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);
      decode_scaling_list(bs, 16);

      decode_scaling_list(bs, 64);
      decode_scaling_list(bs, 64);

    }
  }

  max_frame_num_bits = read_golomb_ue(bs) + 4;
  poc_type = read_golomb_ue(bs); // pic_order_cnt_type

  if(poc_type == 0){
    read_golomb_ue(bs);
  } else if(poc_type == 1){
    skip_bits1(bs);
    read_golomb_se(bs);
    read_golomb_se(bs);
    tmp = read_golomb_ue(bs); /* poc_cycle_length */
    for(i = 0; i < tmp; i++)
      read_golomb_se(bs);

  }else if(poc_type != 2){
    /* Illegal poc */
    return -1;
  }

  tmp = read_golomb_ue(bs);

  read_bits1(bs);

  width  = read_golomb_ue(bs) + 1; /* mb width */
  height = read_golomb_ue(bs) + 1; /* mb height */

  mbs_only_flag = read_bits1(bs);
  aff = 0;
  if(!mbs_only_flag)
    aff = read_bits1(bs);

  read_bits1(bs);

  /* CROP */
  crop_left = crop_right = crop_top = crop_bottom = 0;
  if (read_bits1(bs)){
    crop_left   = read_golomb_ue(bs) * 2;
    crop_right  = read_golomb_ue(bs) * 2;
    crop_top    = read_golomb_ue(bs) * 2;
    crop_bottom = read_golomb_ue(bs) * 2;
  }

  if (read_bits1(bs)) /* vui present */
    if (decode_vui(sps, bs))
      return -1;

  sps->max_frame_num_bits = max_frame_num_bits;
  sps->mbs_only_flag = mbs_only_flag;
  sps->aff = aff;
  sps->cbpsize = cbpsize * 125; /* Convert from kbit to bytes */
  sps->width   = width  * 16 - crop_left - crop_right;
  sps->height  = height * 16 - crop_top  - crop_bottom;
  sps->valid   = 1;

  return 0;
}