Exemple #1
0
static void demux_demuxers_seek(demuxer_t *demuxer,float rel_seek_secs,float audio_delay,int flags) {
  dd_priv_t* priv;
  float pos;
  priv=demuxer->priv;

  priv->ad->stream->eof = 0;
  priv->sd->stream->eof = 0;

  // Seek video
  demux_seek(priv->vd,rel_seek_secs,audio_delay,flags);
  // Get the new pos
  pos = demuxer->video->pts;
  if (!pos) {
    demux_fill_buffer(priv->vd, demuxer->video);
    if (demuxer->video->first)
      pos = demuxer->video->first->pts;
  }

  if(priv->ad != priv->vd && demuxer->audio->sh) {
    sh_audio_t* sh = demuxer->audio->sh;
    demux_seek(priv->ad,pos,audio_delay,1);
    // In case the demuxer don't set pts
    if(!demuxer->audio->pts)
      demuxer->audio->pts = pos-((ds_tell_pts(demuxer->audio)-sh->a_in_buffer_len)/(float)sh->i_bps);
  }

  if(priv->sd != priv->vd)
      demux_seek(priv->sd,pos,audio_delay,1);

}
/// Returns a_pts
double calc_a_pts(sh_audio_t *sh_audio, demux_stream_t *d_audio)
{
    double a_pts;
    if(!sh_audio || !d_audio)
        return MP_NOPTS_VALUE;
    // first calculate the end pts of audio that has been output by decoder
    a_pts = sh_audio->pts;
    // If we cannot get any useful information at all from the demuxer layer
    // just count the decoded bytes. This is still better than constantly
    // resetting to 0.
    if (sh_audio->pts_bytes && a_pts == MP_NOPTS_VALUE &&
        !d_audio->pts && !sh_audio->i_bps)
        a_pts = 0;
    if (a_pts != MP_NOPTS_VALUE)
        // Good, decoder supports new way of calculating audio pts.
        // sh_audio->pts is the timestamp of the latest input packet with
        // known pts that the decoder has decoded. sh_audio->pts_bytes is
        // the amount of bytes the decoder has written after that timestamp.
        a_pts += sh_audio->pts_bytes / (double) sh_audio->o_bps;
    else {
        // Decoder doesn't support new way of calculating pts (or we're
        // being called before it has decoded anything with known timestamp).
        // Use the old method of audio pts calculation: take the timestamp
        // of last packet with known pts the decoder has read data from,
        // and add amount of bytes read after the beginning of that packet
        // divided by input bps. This will be inaccurate if the input/output
        // ratio is not constant for every audio packet or if it is constant
        // but not accurately known in sh_audio->i_bps.

        a_pts = d_audio->pts;
        // ds_tell_pts returns bytes read after last timestamp from
        // demuxing layer, decoder might use sh_audio->a_in_buffer for bytes
        // it has read but not decoded
        if (sh_audio->i_bps)
            a_pts += (ds_tell_pts(d_audio) - sh_audio->a_in_buffer_len) /
                     (double)sh_audio->i_bps;
    }
    return a_pts;
}
static void demux_demuxers_seek(demuxer_t *demuxer,float rel_seek_secs,float audio_delay,int flags) {
  dd_priv_t* priv;
  float pos;
  priv=demuxer->priv;

  priv->ad->stream->eof = 0;
  priv->sd->stream->eof = 0;

  // Seek video
  demux_seek(priv->vd,rel_seek_secs,audio_delay,flags);
  // Get the new pos
  pos = demuxer->video->pts;
  if (!pos) {
    // since the video demuxer might provide multiple
    // streams (e.g. subs) we might have to call
    // demux_fill_buffer multiple times.
    int limit = 10;
    do {
      demux_fill_buffer(priv->vd, demuxer->video);
    } while (--limit && !demuxer->video->first);
    if (demuxer->video->first)
      pos = demuxer->video->first->pts;
  }

  if(priv->ad != priv->vd && demuxer->audio->sh) {
    sh_audio_t* sh = demuxer->audio->sh;
    demux_seek(priv->ad,pos,audio_delay,1);
    // In case the demuxer don't set pts
    if(!demuxer->audio->pts)
      demuxer->audio->pts = pos-((ds_tell_pts(demuxer->audio)-sh->a_in_buffer_len)/(float)sh->i_bps);
  }

  if(priv->sd != priv->vd)
      demux_seek(priv->sd,pos,audio_delay,1);

}
static int decode_audio(sh_audio_t *sh_audio,unsigned char *buf,int minlen,int maxlen)
{
	DMO_AudioDecoder* ds_adec = sh_audio->context;
//	int len=-1;
        int size_in=0;
        int size_out=0;
        int srcsize=DMO_AudioDecoder_GetSrcSize(ds_adec, maxlen);
        mp_msg(MSGT_DECAUDIO,MSGL_DBG3,"DMO says: srcsize=%d  (buffsize=%d)  out_size=%d\n",srcsize,sh_audio->a_in_buffer_size,maxlen);
        if(srcsize>sh_audio->a_in_buffer_size) srcsize=sh_audio->a_in_buffer_size; // !!!!!!
        if(sh_audio->a_in_buffer_len<srcsize){
          sh_audio->a_in_buffer_len+=
            demux_read_data(sh_audio->ds,&sh_audio->a_in_buffer[sh_audio->a_in_buffer_len],
            srcsize-sh_audio->a_in_buffer_len);
        }
        DMO_AudioDecoder_Convert(ds_adec, sh_audio->a_in_buffer,sh_audio->a_in_buffer_len,
            buf,maxlen, &size_in,&size_out);
        mp_dbg(MSGT_DECAUDIO,MSGL_DBG2,"DMO: audio %d -> %d converted  (in_buf_len=%d of %d)  %d\n",size_in,size_out,sh_audio->a_in_buffer_len,sh_audio->a_in_buffer_size,ds_tell_pts(sh_audio->ds));
        if(size_in>=sh_audio->a_in_buffer_len){
          sh_audio->a_in_buffer_len=0;
        } else {
          sh_audio->a_in_buffer_len-=size_in;
          memmove(sh_audio->a_in_buffer,&sh_audio->a_in_buffer[size_in],sh_audio->a_in_buffer_len);
        }
//        len=size_out;
  return size_out;
}